From 6a9e529272517755904b7afa639f6db59ddb793e Mon Sep 17 00:00:00 2001 From: Thomas Gleixner Date: Mon, 18 Feb 2019 23:13:06 +0100 Subject: x86/speculation/mds: Add mds_clear_cpu_buffers() The Microarchitectural Data Sampling (MDS) vulernabilities are mitigated by clearing the affected CPU buffers. The mechanism for clearing the buffers uses the unused and obsolete VERW instruction in combination with a microcode update which triggers a CPU buffer clear when VERW is executed. Provide a inline function with the assembly magic. The argument of the VERW instruction must be a memory operand as documented: "MD_CLEAR enumerates that the memory-operand variant of VERW (for example, VERW m16) has been extended to also overwrite buffers affected by MDS. This buffer overwriting functionality is not guaranteed for the register operand variant of VERW." Documentation also recommends to use a writable data segment selector: "The buffer overwriting occurs regardless of the result of the VERW permission check, as well as when the selector is null or causes a descriptor load segment violation. However, for lowest latency we recommend using a selector that indicates a valid writable data segment." Add x86 specific documentation about MDS and the internal workings of the mitigation. Signed-off-by: Thomas Gleixner Reviewed-by: Borislav Petkov Reviewed-by: Greg Kroah-Hartman Reviewed-by: Frederic Weisbecker Reviewed-by: Jon Masters Tested-by: Jon Masters --- Documentation/index.rst | 1 + Documentation/x86/conf.py | 10 +++++ Documentation/x86/index.rst | 8 ++++ Documentation/x86/mds.rst | 99 +++++++++++++++++++++++++++++++++++++++++++++ 4 files changed, 118 insertions(+) create mode 100644 Documentation/x86/conf.py create mode 100644 Documentation/x86/index.rst create mode 100644 Documentation/x86/mds.rst (limited to 'Documentation') diff --git a/Documentation/index.rst b/Documentation/index.rst index c858c2e66e36..63864826dcd6 100644 --- a/Documentation/index.rst +++ b/Documentation/index.rst @@ -101,6 +101,7 @@ implementation. :maxdepth: 2 sh/index + x86/index Filesystem Documentation ------------------------ diff --git a/Documentation/x86/conf.py b/Documentation/x86/conf.py new file mode 100644 index 000000000000..33c5c3142e20 --- /dev/null +++ b/Documentation/x86/conf.py @@ -0,0 +1,10 @@ +# -*- coding: utf-8; mode: python -*- + +project = "X86 architecture specific documentation" + +tags.add("subproject") + +latex_documents = [ + ('index', 'x86.tex', project, + 'The kernel development community', 'manual'), +] diff --git a/Documentation/x86/index.rst b/Documentation/x86/index.rst new file mode 100644 index 000000000000..ef389dcf1b1d --- /dev/null +++ b/Documentation/x86/index.rst @@ -0,0 +1,8 @@ +========================== +x86 architecture specifics +========================== + +.. toctree:: + :maxdepth: 1 + + mds diff --git a/Documentation/x86/mds.rst b/Documentation/x86/mds.rst new file mode 100644 index 000000000000..1096738d50f2 --- /dev/null +++ b/Documentation/x86/mds.rst @@ -0,0 +1,99 @@ +Microarchitectural Data Sampling (MDS) mitigation +================================================= + +.. _mds: + +Overview +-------- + +Microarchitectural Data Sampling (MDS) is a family of side channel attacks +on internal buffers in Intel CPUs. The variants are: + + - Microarchitectural Store Buffer Data Sampling (MSBDS) (CVE-2018-12126) + - Microarchitectural Fill Buffer Data Sampling (MFBDS) (CVE-2018-12130) + - Microarchitectural Load Port Data Sampling (MLPDS) (CVE-2018-12127) + +MSBDS leaks Store Buffer Entries which can be speculatively forwarded to a +dependent load (store-to-load forwarding) as an optimization. The forward +can also happen to a faulting or assisting load operation for a different +memory address, which can be exploited under certain conditions. Store +buffers are partitioned between Hyper-Threads so cross thread forwarding is +not possible. But if a thread enters or exits a sleep state the store +buffer is repartitioned which can expose data from one thread to the other. + +MFBDS leaks Fill Buffer Entries. Fill buffers are used internally to manage +L1 miss situations and to hold data which is returned or sent in response +to a memory or I/O operation. Fill buffers can forward data to a load +operation and also write data to the cache. When the fill buffer is +deallocated it can retain the stale data of the preceding operations which +can then be forwarded to a faulting or assisting load operation, which can +be exploited under certain conditions. Fill buffers are shared between +Hyper-Threads so cross thread leakage is possible. + +MLPDS leaks Load Port Data. Load ports are used to perform load operations +from memory or I/O. The received data is then forwarded to the register +file or a subsequent operation. In some implementations the Load Port can +contain stale data from a previous operation which can be forwarded to +faulting or assisting loads under certain conditions, which again can be +exploited eventually. Load ports are shared between Hyper-Threads so cross +thread leakage is possible. + + +Exposure assumptions +-------------------- + +It is assumed that attack code resides in user space or in a guest with one +exception. The rationale behind this assumption is that the code construct +needed for exploiting MDS requires: + + - to control the load to trigger a fault or assist + + - to have a disclosure gadget which exposes the speculatively accessed + data for consumption through a side channel. + + - to control the pointer through which the disclosure gadget exposes the + data + +The existence of such a construct in the kernel cannot be excluded with +100% certainty, but the complexity involved makes it extremly unlikely. + +There is one exception, which is untrusted BPF. The functionality of +untrusted BPF is limited, but it needs to be thoroughly investigated +whether it can be used to create such a construct. + + +Mitigation strategy +------------------- + +All variants have the same mitigation strategy at least for the single CPU +thread case (SMT off): Force the CPU to clear the affected buffers. + +This is achieved by using the otherwise unused and obsolete VERW +instruction in combination with a microcode update. The microcode clears +the affected CPU buffers when the VERW instruction is executed. + +For virtualization there are two ways to achieve CPU buffer +clearing. Either the modified VERW instruction or via the L1D Flush +command. The latter is issued when L1TF mitigation is enabled so the extra +VERW can be avoided. If the CPU is not affected by L1TF then VERW needs to +be issued. + +If the VERW instruction with the supplied segment selector argument is +executed on a CPU without the microcode update there is no side effect +other than a small number of pointlessly wasted CPU cycles. + +This does not protect against cross Hyper-Thread attacks except for MSBDS +which is only exploitable cross Hyper-thread when one of the Hyper-Threads +enters a C-state. + +The kernel provides a function to invoke the buffer clearing: + + mds_clear_cpu_buffers() + +The mitigation is invoked on kernel/userspace, hypervisor/guest and C-state +(idle) transitions. + +According to current knowledge additional mitigations inside the kernel +itself are not required because the necessary gadgets to expose the leaked +data cannot be controlled in a way which allows exploitation from malicious +user space or VM guests. -- cgit v1.2.3 From 04dcbdb8057827b043b3c71aa397c4c63e67d086 Mon Sep 17 00:00:00 2001 From: Thomas Gleixner Date: Mon, 18 Feb 2019 23:42:51 +0100 Subject: x86/speculation/mds: Clear CPU buffers on exit to user Add a static key which controls the invocation of the CPU buffer clear mechanism on exit to user space and add the call into prepare_exit_to_usermode() and do_nmi() right before actually returning. Add documentation which kernel to user space transition this covers and explain why some corner cases are not mitigated. Signed-off-by: Thomas Gleixner Reviewed-by: Greg Kroah-Hartman Reviewed-by: Borislav Petkov Reviewed-by: Frederic Weisbecker Reviewed-by: Jon Masters Tested-by: Jon Masters --- Documentation/x86/mds.rst | 52 ++++++++++++++++++++++++++++++++++++ arch/x86/entry/common.c | 3 +++ arch/x86/include/asm/nospec-branch.h | 13 +++++++++ arch/x86/kernel/cpu/bugs.c | 3 +++ arch/x86/kernel/nmi.c | 4 +++ arch/x86/kernel/traps.c | 8 ++++++ 6 files changed, 83 insertions(+) (limited to 'Documentation') diff --git a/Documentation/x86/mds.rst b/Documentation/x86/mds.rst index 1096738d50f2..54d935bf283b 100644 --- a/Documentation/x86/mds.rst +++ b/Documentation/x86/mds.rst @@ -97,3 +97,55 @@ According to current knowledge additional mitigations inside the kernel itself are not required because the necessary gadgets to expose the leaked data cannot be controlled in a way which allows exploitation from malicious user space or VM guests. + +Mitigation points +----------------- + +1. Return to user space +^^^^^^^^^^^^^^^^^^^^^^^ + + When transitioning from kernel to user space the CPU buffers are flushed + on affected CPUs when the mitigation is not disabled on the kernel + command line. The migitation is enabled through the static key + mds_user_clear. + + The mitigation is invoked in prepare_exit_to_usermode() which covers + most of the kernel to user space transitions. There are a few exceptions + which are not invoking prepare_exit_to_usermode() on return to user + space. These exceptions use the paranoid exit code. + + - Non Maskable Interrupt (NMI): + + Access to sensible data like keys, credentials in the NMI context is + mostly theoretical: The CPU can do prefetching or execute a + misspeculated code path and thereby fetching data which might end up + leaking through a buffer. + + But for mounting other attacks the kernel stack address of the task is + already valuable information. So in full mitigation mode, the NMI is + mitigated on the return from do_nmi() to provide almost complete + coverage. + + - Double fault (#DF): + + A double fault is usually fatal, but the ESPFIX workaround, which can + be triggered from user space through modify_ldt(2) is a recoverable + double fault. #DF uses the paranoid exit path, so explicit mitigation + in the double fault handler is required. + + - Machine Check Exception (#MC): + + Another corner case is a #MC which hits between the CPU buffer clear + invocation and the actual return to user. As this still is in kernel + space it takes the paranoid exit path which does not clear the CPU + buffers. So the #MC handler repopulates the buffers to some + extent. Machine checks are not reliably controllable and the window is + extremly small so mitigation would just tick a checkbox that this + theoretical corner case is covered. To keep the amount of special + cases small, ignore #MC. + + - Debug Exception (#DB): + + This takes the paranoid exit path only when the INT1 breakpoint is in + kernel space. #DB on a user space address takes the regular exit path, + so no extra mitigation required. diff --git a/arch/x86/entry/common.c b/arch/x86/entry/common.c index 7bc105f47d21..19f650d729f5 100644 --- a/arch/x86/entry/common.c +++ b/arch/x86/entry/common.c @@ -31,6 +31,7 @@ #include #include #include +#include #define CREATE_TRACE_POINTS #include @@ -212,6 +213,8 @@ __visible inline void prepare_exit_to_usermode(struct pt_regs *regs) #endif user_enter_irqoff(); + + mds_user_clear_cpu_buffers(); } #define SYSCALL_EXIT_WORK_FLAGS \ diff --git a/arch/x86/include/asm/nospec-branch.h b/arch/x86/include/asm/nospec-branch.h index 67cb9b2082b1..65b747286d96 100644 --- a/arch/x86/include/asm/nospec-branch.h +++ b/arch/x86/include/asm/nospec-branch.h @@ -318,6 +318,8 @@ DECLARE_STATIC_KEY_FALSE(switch_to_cond_stibp); DECLARE_STATIC_KEY_FALSE(switch_mm_cond_ibpb); DECLARE_STATIC_KEY_FALSE(switch_mm_always_ibpb); +DECLARE_STATIC_KEY_FALSE(mds_user_clear); + #include /** @@ -343,6 +345,17 @@ static inline void mds_clear_cpu_buffers(void) asm volatile("verw %[ds]" : : [ds] "m" (ds) : "cc"); } +/** + * mds_user_clear_cpu_buffers - Mitigation for MDS vulnerability + * + * Clear CPU buffers if the corresponding static key is enabled + */ +static inline void mds_user_clear_cpu_buffers(void) +{ + if (static_branch_likely(&mds_user_clear)) + mds_clear_cpu_buffers(); +} + #endif /* __ASSEMBLY__ */ /* diff --git a/arch/x86/kernel/cpu/bugs.c b/arch/x86/kernel/cpu/bugs.c index 01874d54f4fd..dbb45014de1b 100644 --- a/arch/x86/kernel/cpu/bugs.c +++ b/arch/x86/kernel/cpu/bugs.c @@ -63,6 +63,9 @@ DEFINE_STATIC_KEY_FALSE(switch_mm_cond_ibpb); /* Control unconditional IBPB in switch_mm() */ DEFINE_STATIC_KEY_FALSE(switch_mm_always_ibpb); +/* Control MDS CPU buffer clear before returning to user space */ +DEFINE_STATIC_KEY_FALSE(mds_user_clear); + void __init check_bugs(void) { identify_boot_cpu(); diff --git a/arch/x86/kernel/nmi.c b/arch/x86/kernel/nmi.c index 18bc9b51ac9b..086cf1d1d71d 100644 --- a/arch/x86/kernel/nmi.c +++ b/arch/x86/kernel/nmi.c @@ -34,6 +34,7 @@ #include #include #include +#include #define CREATE_TRACE_POINTS #include @@ -533,6 +534,9 @@ nmi_restart: write_cr2(this_cpu_read(nmi_cr2)); if (this_cpu_dec_return(nmi_state)) goto nmi_restart; + + if (user_mode(regs)) + mds_user_clear_cpu_buffers(); } NOKPROBE_SYMBOL(do_nmi); diff --git a/arch/x86/kernel/traps.c b/arch/x86/kernel/traps.c index 9b7c4ca8f0a7..85fe1870f873 100644 --- a/arch/x86/kernel/traps.c +++ b/arch/x86/kernel/traps.c @@ -58,6 +58,7 @@ #include #include #include +#include #include #include #include @@ -366,6 +367,13 @@ dotraplinkage void do_double_fault(struct pt_regs *regs, long error_code) regs->ip = (unsigned long)general_protection; regs->sp = (unsigned long)&gpregs->orig_ax; + /* + * This situation can be triggered by userspace via + * modify_ldt(2) and the return does not take the regular + * user space exit, so a CPU buffer clear is required when + * MDS mitigation is enabled. + */ + mds_user_clear_cpu_buffers(); return; } #endif -- cgit v1.2.3 From 07f07f55a29cb705e221eda7894dd67ab81ef343 Mon Sep 17 00:00:00 2001 From: Thomas Gleixner Date: Mon, 18 Feb 2019 23:04:01 +0100 Subject: x86/speculation/mds: Conditionally clear CPU buffers on idle entry Add a static key which controls the invocation of the CPU buffer clear mechanism on idle entry. This is independent of other MDS mitigations because the idle entry invocation to mitigate the potential leakage due to store buffer repartitioning is only necessary on SMT systems. Add the actual invocations to the different halt/mwait variants which covers all usage sites. mwaitx is not patched as it's not available on Intel CPUs. The buffer clear is only invoked before entering the C-State to prevent that stale data from the idling CPU is spilled to the Hyper-Thread sibling after the Store buffer got repartitioned and all entries are available to the non idle sibling. When coming out of idle the store buffer is partitioned again so each sibling has half of it available. Now CPU which returned from idle could be speculatively exposed to contents of the sibling, but the buffers are flushed either on exit to user space or on VMENTER. When later on conditional buffer clearing is implemented on top of this, then there is no action required either because before returning to user space the context switch will set the condition flag which causes a flush on the return to user path. Note, that the buffer clearing on idle is only sensible on CPUs which are solely affected by MSBDS and not any other variant of MDS because the other MDS variants cannot be mitigated when SMT is enabled, so the buffer clearing on idle would be a window dressing exercise. This intentionally does not handle the case in the acpi/processor_idle driver which uses the legacy IO port interface for C-State transitions for two reasons: - The acpi/processor_idle driver was replaced by the intel_idle driver almost a decade ago. Anything Nehalem upwards supports it and defaults to that new driver. - The legacy IO port interface is likely to be used on older and therefore unaffected CPUs or on systems which do not receive microcode updates anymore, so there is no point in adding that. Signed-off-by: Thomas Gleixner Reviewed-by: Borislav Petkov Reviewed-by: Greg Kroah-Hartman Reviewed-by: Frederic Weisbecker Reviewed-by: Jon Masters Tested-by: Jon Masters --- Documentation/x86/mds.rst | 42 ++++++++++++++++++++++++++++++++++++ arch/x86/include/asm/irqflags.h | 4 ++++ arch/x86/include/asm/mwait.h | 7 ++++++ arch/x86/include/asm/nospec-branch.h | 12 +++++++++++ arch/x86/kernel/cpu/bugs.c | 3 +++ 5 files changed, 68 insertions(+) (limited to 'Documentation') diff --git a/Documentation/x86/mds.rst b/Documentation/x86/mds.rst index 54d935bf283b..87ce8ac9f36e 100644 --- a/Documentation/x86/mds.rst +++ b/Documentation/x86/mds.rst @@ -149,3 +149,45 @@ Mitigation points This takes the paranoid exit path only when the INT1 breakpoint is in kernel space. #DB on a user space address takes the regular exit path, so no extra mitigation required. + + +2. C-State transition +^^^^^^^^^^^^^^^^^^^^^ + + When a CPU goes idle and enters a C-State the CPU buffers need to be + cleared on affected CPUs when SMT is active. This addresses the + repartitioning of the store buffer when one of the Hyper-Threads enters + a C-State. + + When SMT is inactive, i.e. either the CPU does not support it or all + sibling threads are offline CPU buffer clearing is not required. + + The idle clearing is enabled on CPUs which are only affected by MSBDS + and not by any other MDS variant. The other MDS variants cannot be + protected against cross Hyper-Thread attacks because the Fill Buffer and + the Load Ports are shared. So on CPUs affected by other variants, the + idle clearing would be a window dressing exercise and is therefore not + activated. + + The invocation is controlled by the static key mds_idle_clear which is + switched depending on the chosen mitigation mode and the SMT state of + the system. + + The buffer clear is only invoked before entering the C-State to prevent + that stale data from the idling CPU from spilling to the Hyper-Thread + sibling after the store buffer got repartitioned and all entries are + available to the non idle sibling. + + When coming out of idle the store buffer is partitioned again so each + sibling has half of it available. The back from idle CPU could be then + speculatively exposed to contents of the sibling. The buffers are + flushed either on exit to user space or on VMENTER so malicious code + in user space or the guest cannot speculatively access them. + + The mitigation is hooked into all variants of halt()/mwait(), but does + not cover the legacy ACPI IO-Port mechanism because the ACPI idle driver + has been superseded by the intel_idle driver around 2010 and is + preferred on all affected CPUs which are expected to gain the MD_CLEAR + functionality in microcode. Aside of that the IO-Port mechanism is a + legacy interface which is only used on older systems which are either + not affected or do not receive microcode updates anymore. diff --git a/arch/x86/include/asm/irqflags.h b/arch/x86/include/asm/irqflags.h index 058e40fed167..8a0e56e1dcc9 100644 --- a/arch/x86/include/asm/irqflags.h +++ b/arch/x86/include/asm/irqflags.h @@ -6,6 +6,8 @@ #ifndef __ASSEMBLY__ +#include + /* Provide __cpuidle; we can't safely include */ #define __cpuidle __attribute__((__section__(".cpuidle.text"))) @@ -54,11 +56,13 @@ static inline void native_irq_enable(void) static inline __cpuidle void native_safe_halt(void) { + mds_idle_clear_cpu_buffers(); asm volatile("sti; hlt": : :"memory"); } static inline __cpuidle void native_halt(void) { + mds_idle_clear_cpu_buffers(); asm volatile("hlt": : :"memory"); } diff --git a/arch/x86/include/asm/mwait.h b/arch/x86/include/asm/mwait.h index 39a2fb29378a..eb0f80ce8524 100644 --- a/arch/x86/include/asm/mwait.h +++ b/arch/x86/include/asm/mwait.h @@ -6,6 +6,7 @@ #include #include +#include #define MWAIT_SUBSTATE_MASK 0xf #define MWAIT_CSTATE_MASK 0xf @@ -40,6 +41,8 @@ static inline void __monitorx(const void *eax, unsigned long ecx, static inline void __mwait(unsigned long eax, unsigned long ecx) { + mds_idle_clear_cpu_buffers(); + /* "mwait %eax, %ecx;" */ asm volatile(".byte 0x0f, 0x01, 0xc9;" :: "a" (eax), "c" (ecx)); @@ -74,6 +77,8 @@ static inline void __mwait(unsigned long eax, unsigned long ecx) static inline void __mwaitx(unsigned long eax, unsigned long ebx, unsigned long ecx) { + /* No MDS buffer clear as this is AMD/HYGON only */ + /* "mwaitx %eax, %ebx, %ecx;" */ asm volatile(".byte 0x0f, 0x01, 0xfb;" :: "a" (eax), "b" (ebx), "c" (ecx)); @@ -81,6 +86,8 @@ static inline void __mwaitx(unsigned long eax, unsigned long ebx, static inline void __sti_mwait(unsigned long eax, unsigned long ecx) { + mds_idle_clear_cpu_buffers(); + trace_hardirqs_on(); /* "mwait %eax, %ecx;" */ asm volatile("sti; .byte 0x0f, 0x01, 0xc9;" diff --git a/arch/x86/include/asm/nospec-branch.h b/arch/x86/include/asm/nospec-branch.h index 65b747286d96..4e970390110f 100644 --- a/arch/x86/include/asm/nospec-branch.h +++ b/arch/x86/include/asm/nospec-branch.h @@ -319,6 +319,7 @@ DECLARE_STATIC_KEY_FALSE(switch_mm_cond_ibpb); DECLARE_STATIC_KEY_FALSE(switch_mm_always_ibpb); DECLARE_STATIC_KEY_FALSE(mds_user_clear); +DECLARE_STATIC_KEY_FALSE(mds_idle_clear); #include @@ -356,6 +357,17 @@ static inline void mds_user_clear_cpu_buffers(void) mds_clear_cpu_buffers(); } +/** + * mds_idle_clear_cpu_buffers - Mitigation for MDS vulnerability + * + * Clear CPU buffers if the corresponding static key is enabled + */ +static inline void mds_idle_clear_cpu_buffers(void) +{ + if (static_branch_likely(&mds_idle_clear)) + mds_clear_cpu_buffers(); +} + #endif /* __ASSEMBLY__ */ /* diff --git a/arch/x86/kernel/cpu/bugs.c b/arch/x86/kernel/cpu/bugs.c index 29ed8e8dfee2..916995167301 100644 --- a/arch/x86/kernel/cpu/bugs.c +++ b/arch/x86/kernel/cpu/bugs.c @@ -66,6 +66,9 @@ DEFINE_STATIC_KEY_FALSE(switch_mm_always_ibpb); /* Control MDS CPU buffer clear before returning to user space */ DEFINE_STATIC_KEY_FALSE(mds_user_clear); EXPORT_SYMBOL_GPL(mds_user_clear); +/* Control MDS CPU buffer clear before idling (halt, mwait) */ +DEFINE_STATIC_KEY_FALSE(mds_idle_clear); +EXPORT_SYMBOL_GPL(mds_idle_clear); void __init check_bugs(void) { -- cgit v1.2.3 From bc1241700acd82ec69fde98c5763ce51086269f8 Mon Sep 17 00:00:00 2001 From: Thomas Gleixner Date: Mon, 18 Feb 2019 22:04:08 +0100 Subject: x86/speculation/mds: Add mitigation control for MDS Now that the mitigations are in place, add a command line parameter to control the mitigation, a mitigation selector function and a SMT update mechanism. This is the minimal straight forward initial implementation which just provides an always on/off mode. The command line parameter is: mds=[full|off] This is consistent with the existing mitigations for other speculative hardware vulnerabilities. The idle invocation is dynamically updated according to the SMT state of the system similar to the dynamic update of the STIBP mitigation. The idle mitigation is limited to CPUs which are only affected by MSBDS and not any other variant, because the other variants cannot be mitigated on SMT enabled systems. Signed-off-by: Thomas Gleixner Reviewed-by: Borislav Petkov Reviewed-by: Jon Masters Tested-by: Jon Masters --- Documentation/admin-guide/kernel-parameters.txt | 22 ++++++++ arch/x86/include/asm/processor.h | 5 ++ arch/x86/kernel/cpu/bugs.c | 70 +++++++++++++++++++++++++ 3 files changed, 97 insertions(+) (limited to 'Documentation') diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt index 858b6c0b9a15..dddb024eb523 100644 --- a/Documentation/admin-guide/kernel-parameters.txt +++ b/Documentation/admin-guide/kernel-parameters.txt @@ -2356,6 +2356,28 @@ Format: , Specifies range of consoles to be captured by the MDA. + mds= [X86,INTEL] + Control mitigation for the Micro-architectural Data + Sampling (MDS) vulnerability. + + Certain CPUs are vulnerable to an exploit against CPU + internal buffers which can forward information to a + disclosure gadget under certain conditions. + + In vulnerable processors, the speculatively + forwarded data can be used in a cache side channel + attack, to access data to which the attacker does + not have direct access. + + This parameter controls the MDS mitigation. The + options are: + + full - Enable MDS mitigation on vulnerable CPUs + off - Unconditionally disable MDS mitigation + + Not specifying this option is equivalent to + mds=full. + mem=nn[KMG] [KNL,BOOT] Force usage of a specific amount of memory Amount of memory to be used when the kernel is not able to see the whole system memory or for test. diff --git a/arch/x86/include/asm/processor.h b/arch/x86/include/asm/processor.h index 33051436c864..1f0295783325 100644 --- a/arch/x86/include/asm/processor.h +++ b/arch/x86/include/asm/processor.h @@ -992,4 +992,9 @@ enum l1tf_mitigations { extern enum l1tf_mitigations l1tf_mitigation; +enum mds_mitigations { + MDS_MITIGATION_OFF, + MDS_MITIGATION_FULL, +}; + #endif /* _ASM_X86_PROCESSOR_H */ diff --git a/arch/x86/kernel/cpu/bugs.c b/arch/x86/kernel/cpu/bugs.c index 916995167301..c7b29d200d27 100644 --- a/arch/x86/kernel/cpu/bugs.c +++ b/arch/x86/kernel/cpu/bugs.c @@ -37,6 +37,7 @@ static void __init spectre_v2_select_mitigation(void); static void __init ssb_select_mitigation(void); static void __init l1tf_select_mitigation(void); +static void __init mds_select_mitigation(void); /* The base value of the SPEC_CTRL MSR that always has to be preserved. */ u64 x86_spec_ctrl_base; @@ -108,6 +109,8 @@ void __init check_bugs(void) l1tf_select_mitigation(); + mds_select_mitigation(); + #ifdef CONFIG_X86_32 /* * Check whether we are able to run this kernel safely on SMP. @@ -213,6 +216,50 @@ static void x86_amd_ssb_disable(void) wrmsrl(MSR_AMD64_LS_CFG, msrval); } +#undef pr_fmt +#define pr_fmt(fmt) "MDS: " fmt + +/* Default mitigation for L1TF-affected CPUs */ +static enum mds_mitigations mds_mitigation __ro_after_init = MDS_MITIGATION_FULL; + +static const char * const mds_strings[] = { + [MDS_MITIGATION_OFF] = "Vulnerable", + [MDS_MITIGATION_FULL] = "Mitigation: Clear CPU buffers" +}; + +static void __init mds_select_mitigation(void) +{ + if (!boot_cpu_has_bug(X86_BUG_MDS)) { + mds_mitigation = MDS_MITIGATION_OFF; + return; + } + + if (mds_mitigation == MDS_MITIGATION_FULL) { + if (boot_cpu_has(X86_FEATURE_MD_CLEAR)) + static_branch_enable(&mds_user_clear); + else + mds_mitigation = MDS_MITIGATION_OFF; + } + pr_info("%s\n", mds_strings[mds_mitigation]); +} + +static int __init mds_cmdline(char *str) +{ + if (!boot_cpu_has_bug(X86_BUG_MDS)) + return 0; + + if (!str) + return -EINVAL; + + if (!strcmp(str, "off")) + mds_mitigation = MDS_MITIGATION_OFF; + else if (!strcmp(str, "full")) + mds_mitigation = MDS_MITIGATION_FULL; + + return 0; +} +early_param("mds", mds_cmdline); + #undef pr_fmt #define pr_fmt(fmt) "Spectre V2 : " fmt @@ -617,6 +664,26 @@ static void update_indir_branch_cond(void) static_branch_disable(&switch_to_cond_stibp); } +/* Update the static key controlling the MDS CPU buffer clear in idle */ +static void update_mds_branch_idle(void) +{ + /* + * Enable the idle clearing if SMT is active on CPUs which are + * affected only by MSBDS and not any other MDS variant. + * + * The other variants cannot be mitigated when SMT is enabled, so + * clearing the buffers on idle just to prevent the Store Buffer + * repartitioning leak would be a window dressing exercise. + */ + if (!boot_cpu_has_bug(X86_BUG_MSBDS_ONLY)) + return; + + if (sched_smt_active()) + static_branch_enable(&mds_idle_clear); + else + static_branch_disable(&mds_idle_clear); +} + void arch_smt_update(void) { /* Enhanced IBRS implies STIBP. No update required. */ @@ -638,6 +705,9 @@ void arch_smt_update(void) break; } + if (mds_mitigation == MDS_MITIGATION_FULL) + update_mds_branch_idle(); + mutex_unlock(&spec_ctrl_mutex); } -- cgit v1.2.3 From 8a4b06d391b0a42a373808979b5028f5c84d9c6a Mon Sep 17 00:00:00 2001 From: Thomas Gleixner Date: Mon, 18 Feb 2019 22:51:43 +0100 Subject: x86/speculation/mds: Add sysfs reporting for MDS Add the sysfs reporting file for MDS. It exposes the vulnerability and mitigation state similar to the existing files for the other speculative hardware vulnerabilities. Signed-off-by: Thomas Gleixner Reviewed-by: Greg Kroah-Hartman Reviewed-by: Borislav Petkov Reviewed-by: Jon Masters Tested-by: Jon Masters --- Documentation/ABI/testing/sysfs-devices-system-cpu | 1 + arch/x86/kernel/cpu/bugs.c | 25 ++++++++++++++++++++++ drivers/base/cpu.c | 8 +++++++ include/linux/cpu.h | 2 ++ 4 files changed, 36 insertions(+) (limited to 'Documentation') diff --git a/Documentation/ABI/testing/sysfs-devices-system-cpu b/Documentation/ABI/testing/sysfs-devices-system-cpu index 9605dbd4b5b5..2db5c3407fd6 100644 --- a/Documentation/ABI/testing/sysfs-devices-system-cpu +++ b/Documentation/ABI/testing/sysfs-devices-system-cpu @@ -484,6 +484,7 @@ What: /sys/devices/system/cpu/vulnerabilities /sys/devices/system/cpu/vulnerabilities/spectre_v2 /sys/devices/system/cpu/vulnerabilities/spec_store_bypass /sys/devices/system/cpu/vulnerabilities/l1tf + /sys/devices/system/cpu/vulnerabilities/mds Date: January 2018 Contact: Linux kernel mailing list Description: Information about CPU vulnerabilities diff --git a/arch/x86/kernel/cpu/bugs.c b/arch/x86/kernel/cpu/bugs.c index c7b29d200d27..7ab16a6ed064 100644 --- a/arch/x86/kernel/cpu/bugs.c +++ b/arch/x86/kernel/cpu/bugs.c @@ -1172,6 +1172,22 @@ static ssize_t l1tf_show_state(char *buf) } #endif +static ssize_t mds_show_state(char *buf) +{ + if (!hypervisor_is_type(X86_HYPER_NATIVE)) { + return sprintf(buf, "%s; SMT Host state unknown\n", + mds_strings[mds_mitigation]); + } + + if (boot_cpu_has(X86_BUG_MSBDS_ONLY)) { + return sprintf(buf, "%s; SMT %s\n", mds_strings[mds_mitigation], + sched_smt_active() ? "mitigated" : "disabled"); + } + + return sprintf(buf, "%s; SMT %s\n", mds_strings[mds_mitigation], + sched_smt_active() ? "vulnerable" : "disabled"); +} + static char *stibp_state(void) { if (spectre_v2_enabled == SPECTRE_V2_IBRS_ENHANCED) @@ -1238,6 +1254,10 @@ static ssize_t cpu_show_common(struct device *dev, struct device_attribute *attr if (boot_cpu_has(X86_FEATURE_L1TF_PTEINV)) return l1tf_show_state(buf); break; + + case X86_BUG_MDS: + return mds_show_state(buf); + default: break; } @@ -1269,4 +1289,9 @@ ssize_t cpu_show_l1tf(struct device *dev, struct device_attribute *attr, char *b { return cpu_show_common(dev, attr, buf, X86_BUG_L1TF); } + +ssize_t cpu_show_mds(struct device *dev, struct device_attribute *attr, char *buf) +{ + return cpu_show_common(dev, attr, buf, X86_BUG_MDS); +} #endif diff --git a/drivers/base/cpu.c b/drivers/base/cpu.c index eb9443d5bae1..2fd6ca1021c2 100644 --- a/drivers/base/cpu.c +++ b/drivers/base/cpu.c @@ -546,11 +546,18 @@ ssize_t __weak cpu_show_l1tf(struct device *dev, return sprintf(buf, "Not affected\n"); } +ssize_t __weak cpu_show_mds(struct device *dev, + struct device_attribute *attr, char *buf) +{ + return sprintf(buf, "Not affected\n"); +} + static DEVICE_ATTR(meltdown, 0444, cpu_show_meltdown, NULL); static DEVICE_ATTR(spectre_v1, 0444, cpu_show_spectre_v1, NULL); static DEVICE_ATTR(spectre_v2, 0444, cpu_show_spectre_v2, NULL); static DEVICE_ATTR(spec_store_bypass, 0444, cpu_show_spec_store_bypass, NULL); static DEVICE_ATTR(l1tf, 0444, cpu_show_l1tf, NULL); +static DEVICE_ATTR(mds, 0444, cpu_show_mds, NULL); static struct attribute *cpu_root_vulnerabilities_attrs[] = { &dev_attr_meltdown.attr, @@ -558,6 +565,7 @@ static struct attribute *cpu_root_vulnerabilities_attrs[] = { &dev_attr_spectre_v2.attr, &dev_attr_spec_store_bypass.attr, &dev_attr_l1tf.attr, + &dev_attr_mds.attr, NULL }; diff --git a/include/linux/cpu.h b/include/linux/cpu.h index 5041357d0297..3c87ad888ed3 100644 --- a/include/linux/cpu.h +++ b/include/linux/cpu.h @@ -57,6 +57,8 @@ extern ssize_t cpu_show_spec_store_bypass(struct device *dev, struct device_attribute *attr, char *buf); extern ssize_t cpu_show_l1tf(struct device *dev, struct device_attribute *attr, char *buf); +extern ssize_t cpu_show_mds(struct device *dev, + struct device_attribute *attr, char *buf); extern __printf(4, 5) struct device *cpu_device_create(struct device *parent, void *drvdata, -- cgit v1.2.3 From 22dd8365088b6403630b82423cf906491859b65e Mon Sep 17 00:00:00 2001 From: Thomas Gleixner Date: Wed, 20 Feb 2019 09:40:40 +0100 Subject: x86/speculation/mds: Add mitigation mode VMWERV In virtualized environments it can happen that the host has the microcode update which utilizes the VERW instruction to clear CPU buffers, but the hypervisor is not yet updated to expose the X86_FEATURE_MD_CLEAR CPUID bit to guests. Introduce an internal mitigation mode VMWERV which enables the invocation of the CPU buffer clearing even if X86_FEATURE_MD_CLEAR is not set. If the system has no updated microcode this results in a pointless execution of the VERW instruction wasting a few CPU cycles. If the microcode is updated, but not exposed to a guest then the CPU buffers will be cleared. That said: Virtual Machines Will Eventually Receive Vaccine Signed-off-by: Thomas Gleixner Reviewed-by: Borislav Petkov Reviewed-by: Jon Masters Tested-by: Jon Masters --- Documentation/x86/mds.rst | 27 +++++++++++++++++++++++++++ arch/x86/include/asm/processor.h | 1 + arch/x86/kernel/cpu/bugs.c | 18 ++++++++++++------ 3 files changed, 40 insertions(+), 6 deletions(-) (limited to 'Documentation') diff --git a/Documentation/x86/mds.rst b/Documentation/x86/mds.rst index 87ce8ac9f36e..3d6f943f1afb 100644 --- a/Documentation/x86/mds.rst +++ b/Documentation/x86/mds.rst @@ -93,11 +93,38 @@ The kernel provides a function to invoke the buffer clearing: The mitigation is invoked on kernel/userspace, hypervisor/guest and C-state (idle) transitions. +As a special quirk to address virtualization scenarios where the host has +the microcode updated, but the hypervisor does not (yet) expose the +MD_CLEAR CPUID bit to guests, the kernel issues the VERW instruction in the +hope that it might actually clear the buffers. The state is reflected +accordingly. + According to current knowledge additional mitigations inside the kernel itself are not required because the necessary gadgets to expose the leaked data cannot be controlled in a way which allows exploitation from malicious user space or VM guests. +Kernel internal mitigation modes +-------------------------------- + + ======= ============================================================ + off Mitigation is disabled. Either the CPU is not affected or + mds=off is supplied on the kernel command line + + full Mitigation is eanbled. CPU is affected and MD_CLEAR is + advertised in CPUID. + + vmwerv Mitigation is enabled. CPU is affected and MD_CLEAR is not + advertised in CPUID. That is mainly for virtualization + scenarios where the host has the updated microcode but the + hypervisor does not expose MD_CLEAR in CPUID. It's a best + effort approach without guarantee. + ======= ============================================================ + +If the CPU is affected and mds=off is not supplied on the kernel command +line then the kernel selects the appropriate mitigation mode depending on +the availability of the MD_CLEAR CPUID bit. + Mitigation points ----------------- diff --git a/arch/x86/include/asm/processor.h b/arch/x86/include/asm/processor.h index 1f0295783325..aca1ef8cc79f 100644 --- a/arch/x86/include/asm/processor.h +++ b/arch/x86/include/asm/processor.h @@ -995,6 +995,7 @@ extern enum l1tf_mitigations l1tf_mitigation; enum mds_mitigations { MDS_MITIGATION_OFF, MDS_MITIGATION_FULL, + MDS_MITIGATION_VMWERV, }; #endif /* _ASM_X86_PROCESSOR_H */ diff --git a/arch/x86/kernel/cpu/bugs.c b/arch/x86/kernel/cpu/bugs.c index 7ab16a6ed064..95cda38c8785 100644 --- a/arch/x86/kernel/cpu/bugs.c +++ b/arch/x86/kernel/cpu/bugs.c @@ -224,7 +224,8 @@ static enum mds_mitigations mds_mitigation __ro_after_init = MDS_MITIGATION_FULL static const char * const mds_strings[] = { [MDS_MITIGATION_OFF] = "Vulnerable", - [MDS_MITIGATION_FULL] = "Mitigation: Clear CPU buffers" + [MDS_MITIGATION_FULL] = "Mitigation: Clear CPU buffers", + [MDS_MITIGATION_VMWERV] = "Vulnerable: Clear CPU buffers attempted, no microcode", }; static void __init mds_select_mitigation(void) @@ -235,10 +236,9 @@ static void __init mds_select_mitigation(void) } if (mds_mitigation == MDS_MITIGATION_FULL) { - if (boot_cpu_has(X86_FEATURE_MD_CLEAR)) - static_branch_enable(&mds_user_clear); - else - mds_mitigation = MDS_MITIGATION_OFF; + if (!boot_cpu_has(X86_FEATURE_MD_CLEAR)) + mds_mitigation = MDS_MITIGATION_VMWERV; + static_branch_enable(&mds_user_clear); } pr_info("%s\n", mds_strings[mds_mitigation]); } @@ -705,8 +705,14 @@ void arch_smt_update(void) break; } - if (mds_mitigation == MDS_MITIGATION_FULL) + switch (mds_mitigation) { + case MDS_MITIGATION_FULL: + case MDS_MITIGATION_VMWERV: update_mds_branch_idle(); + break; + case MDS_MITIGATION_OFF: + break; + } mutex_unlock(&spec_ctrl_mutex); } -- cgit v1.2.3 From 65fd4cb65b2dad97feb8330b6690445910b56d6a Mon Sep 17 00:00:00 2001 From: Thomas Gleixner Date: Tue, 19 Feb 2019 11:10:49 +0100 Subject: Documentation: Move L1TF to separate directory Move L!TF to a separate directory so the MDS stuff can be added at the side. Otherwise the all hardware vulnerabilites have their own top level entry. Should have done that right away. Signed-off-by: Thomas Gleixner Reviewed-by: Greg Kroah-Hartman Reviewed-by: Jon Masters --- Documentation/ABI/testing/sysfs-devices-system-cpu | 2 +- Documentation/admin-guide/hw-vuln/index.rst | 12 + Documentation/admin-guide/hw-vuln/l1tf.rst | 614 +++++++++++++++++++++ Documentation/admin-guide/index.rst | 6 +- Documentation/admin-guide/kernel-parameters.txt | 2 +- Documentation/admin-guide/l1tf.rst | 614 --------------------- arch/x86/kernel/cpu/bugs.c | 2 +- arch/x86/kvm/vmx/vmx.c | 4 +- 8 files changed, 633 insertions(+), 623 deletions(-) create mode 100644 Documentation/admin-guide/hw-vuln/index.rst create mode 100644 Documentation/admin-guide/hw-vuln/l1tf.rst delete mode 100644 Documentation/admin-guide/l1tf.rst (limited to 'Documentation') diff --git a/Documentation/ABI/testing/sysfs-devices-system-cpu b/Documentation/ABI/testing/sysfs-devices-system-cpu index 2db5c3407fd6..744c6d764b0c 100644 --- a/Documentation/ABI/testing/sysfs-devices-system-cpu +++ b/Documentation/ABI/testing/sysfs-devices-system-cpu @@ -498,7 +498,7 @@ Description: Information about CPU vulnerabilities "Mitigation: $M" CPU is affected and mitigation $M is in effect Details about the l1tf file can be found in - Documentation/admin-guide/l1tf.rst + Documentation/admin-guide/hw-vuln/l1tf.rst What: /sys/devices/system/cpu/smt /sys/devices/system/cpu/smt/active diff --git a/Documentation/admin-guide/hw-vuln/index.rst b/Documentation/admin-guide/hw-vuln/index.rst new file mode 100644 index 000000000000..8ce2009f1981 --- /dev/null +++ b/Documentation/admin-guide/hw-vuln/index.rst @@ -0,0 +1,12 @@ +======================== +Hardware vulnerabilities +======================== + +This section describes CPU vulnerabilities and provides an overview of the +possible mitigations along with guidance for selecting mitigations if they +are configurable at compile, boot or run time. + +.. toctree:: + :maxdepth: 1 + + l1tf diff --git a/Documentation/admin-guide/hw-vuln/l1tf.rst b/Documentation/admin-guide/hw-vuln/l1tf.rst new file mode 100644 index 000000000000..9af977384168 --- /dev/null +++ b/Documentation/admin-guide/hw-vuln/l1tf.rst @@ -0,0 +1,614 @@ +L1TF - L1 Terminal Fault +======================== + +L1 Terminal Fault is a hardware vulnerability which allows unprivileged +speculative access to data which is available in the Level 1 Data Cache +when the page table entry controlling the virtual address, which is used +for the access, has the Present bit cleared or other reserved bits set. + +Affected processors +------------------- + +This vulnerability affects a wide range of Intel processors. The +vulnerability is not present on: + + - Processors from AMD, Centaur and other non Intel vendors + + - Older processor models, where the CPU family is < 6 + + - A range of Intel ATOM processors (Cedarview, Cloverview, Lincroft, + Penwell, Pineview, Silvermont, Airmont, Merrifield) + + - The Intel XEON PHI family + + - Intel processors which have the ARCH_CAP_RDCL_NO bit set in the + IA32_ARCH_CAPABILITIES MSR. If the bit is set the CPU is not affected + by the Meltdown vulnerability either. These CPUs should become + available by end of 2018. + +Whether a processor is affected or not can be read out from the L1TF +vulnerability file in sysfs. See :ref:`l1tf_sys_info`. + +Related CVEs +------------ + +The following CVE entries are related to the L1TF vulnerability: + + ============= ================= ============================== + CVE-2018-3615 L1 Terminal Fault SGX related aspects + CVE-2018-3620 L1 Terminal Fault OS, SMM related aspects + CVE-2018-3646 L1 Terminal Fault Virtualization related aspects + ============= ================= ============================== + +Problem +------- + +If an instruction accesses a virtual address for which the relevant page +table entry (PTE) has the Present bit cleared or other reserved bits set, +then speculative execution ignores the invalid PTE and loads the referenced +data if it is present in the Level 1 Data Cache, as if the page referenced +by the address bits in the PTE was still present and accessible. + +While this is a purely speculative mechanism and the instruction will raise +a page fault when it is retired eventually, the pure act of loading the +data and making it available to other speculative instructions opens up the +opportunity for side channel attacks to unprivileged malicious code, +similar to the Meltdown attack. + +While Meltdown breaks the user space to kernel space protection, L1TF +allows to attack any physical memory address in the system and the attack +works across all protection domains. It allows an attack of SGX and also +works from inside virtual machines because the speculation bypasses the +extended page table (EPT) protection mechanism. + + +Attack scenarios +---------------- + +1. Malicious user space +^^^^^^^^^^^^^^^^^^^^^^^ + + Operating Systems store arbitrary information in the address bits of a + PTE which is marked non present. This allows a malicious user space + application to attack the physical memory to which these PTEs resolve. + In some cases user-space can maliciously influence the information + encoded in the address bits of the PTE, thus making attacks more + deterministic and more practical. + + The Linux kernel contains a mitigation for this attack vector, PTE + inversion, which is permanently enabled and has no performance + impact. The kernel ensures that the address bits of PTEs, which are not + marked present, never point to cacheable physical memory space. + + A system with an up to date kernel is protected against attacks from + malicious user space applications. + +2. Malicious guest in a virtual machine +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + + The fact that L1TF breaks all domain protections allows malicious guest + OSes, which can control the PTEs directly, and malicious guest user + space applications, which run on an unprotected guest kernel lacking the + PTE inversion mitigation for L1TF, to attack physical host memory. + + A special aspect of L1TF in the context of virtualization is symmetric + multi threading (SMT). The Intel implementation of SMT is called + HyperThreading. The fact that Hyperthreads on the affected processors + share the L1 Data Cache (L1D) is important for this. As the flaw allows + only to attack data which is present in L1D, a malicious guest running + on one Hyperthread can attack the data which is brought into the L1D by + the context which runs on the sibling Hyperthread of the same physical + core. This context can be host OS, host user space or a different guest. + + If the processor does not support Extended Page Tables, the attack is + only possible, when the hypervisor does not sanitize the content of the + effective (shadow) page tables. + + While solutions exist to mitigate these attack vectors fully, these + mitigations are not enabled by default in the Linux kernel because they + can affect performance significantly. The kernel provides several + mechanisms which can be utilized to address the problem depending on the + deployment scenario. The mitigations, their protection scope and impact + are described in the next sections. + + The default mitigations and the rationale for choosing them are explained + at the end of this document. See :ref:`default_mitigations`. + +.. _l1tf_sys_info: + +L1TF system information +----------------------- + +The Linux kernel provides a sysfs interface to enumerate the current L1TF +status of the system: whether the system is vulnerable, and which +mitigations are active. The relevant sysfs file is: + +/sys/devices/system/cpu/vulnerabilities/l1tf + +The possible values in this file are: + + =========================== =============================== + 'Not affected' The processor is not vulnerable + 'Mitigation: PTE Inversion' The host protection is active + =========================== =============================== + +If KVM/VMX is enabled and the processor is vulnerable then the following +information is appended to the 'Mitigation: PTE Inversion' part: + + - SMT status: + + ===================== ================ + 'VMX: SMT vulnerable' SMT is enabled + 'VMX: SMT disabled' SMT is disabled + ===================== ================ + + - L1D Flush mode: + + ================================ ==================================== + 'L1D vulnerable' L1D flushing is disabled + + 'L1D conditional cache flushes' L1D flush is conditionally enabled + + 'L1D cache flushes' L1D flush is unconditionally enabled + ================================ ==================================== + +The resulting grade of protection is discussed in the following sections. + + +Host mitigation mechanism +------------------------- + +The kernel is unconditionally protected against L1TF attacks from malicious +user space running on the host. + + +Guest mitigation mechanisms +--------------------------- + +.. _l1d_flush: + +1. L1D flush on VMENTER +^^^^^^^^^^^^^^^^^^^^^^^ + + To make sure that a guest cannot attack data which is present in the L1D + the hypervisor flushes the L1D before entering the guest. + + Flushing the L1D evicts not only the data which should not be accessed + by a potentially malicious guest, it also flushes the guest + data. Flushing the L1D has a performance impact as the processor has to + bring the flushed guest data back into the L1D. Depending on the + frequency of VMEXIT/VMENTER and the type of computations in the guest + performance degradation in the range of 1% to 50% has been observed. For + scenarios where guest VMEXIT/VMENTER are rare the performance impact is + minimal. Virtio and mechanisms like posted interrupts are designed to + confine the VMEXITs to a bare minimum, but specific configurations and + application scenarios might still suffer from a high VMEXIT rate. + + The kernel provides two L1D flush modes: + - conditional ('cond') + - unconditional ('always') + + The conditional mode avoids L1D flushing after VMEXITs which execute + only audited code paths before the corresponding VMENTER. These code + paths have been verified that they cannot expose secrets or other + interesting data to an attacker, but they can leak information about the + address space layout of the hypervisor. + + Unconditional mode flushes L1D on all VMENTER invocations and provides + maximum protection. It has a higher overhead than the conditional + mode. The overhead cannot be quantified correctly as it depends on the + workload scenario and the resulting number of VMEXITs. + + The general recommendation is to enable L1D flush on VMENTER. The kernel + defaults to conditional mode on affected processors. + + **Note**, that L1D flush does not prevent the SMT problem because the + sibling thread will also bring back its data into the L1D which makes it + attackable again. + + L1D flush can be controlled by the administrator via the kernel command + line and sysfs control files. See :ref:`mitigation_control_command_line` + and :ref:`mitigation_control_kvm`. + +.. _guest_confinement: + +2. Guest VCPU confinement to dedicated physical cores +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + + To address the SMT problem, it is possible to make a guest or a group of + guests affine to one or more physical cores. The proper mechanism for + that is to utilize exclusive cpusets to ensure that no other guest or + host tasks can run on these cores. + + If only a single guest or related guests run on sibling SMT threads on + the same physical core then they can only attack their own memory and + restricted parts of the host memory. + + Host memory is attackable, when one of the sibling SMT threads runs in + host OS (hypervisor) context and the other in guest context. The amount + of valuable information from the host OS context depends on the context + which the host OS executes, i.e. interrupts, soft interrupts and kernel + threads. The amount of valuable data from these contexts cannot be + declared as non-interesting for an attacker without deep inspection of + the code. + + **Note**, that assigning guests to a fixed set of physical cores affects + the ability of the scheduler to do load balancing and might have + negative effects on CPU utilization depending on the hosting + scenario. Disabling SMT might be a viable alternative for particular + scenarios. + + For further information about confining guests to a single or to a group + of cores consult the cpusets documentation: + + https://www.kernel.org/doc/Documentation/cgroup-v1/cpusets.txt + +.. _interrupt_isolation: + +3. Interrupt affinity +^^^^^^^^^^^^^^^^^^^^^ + + Interrupts can be made affine to logical CPUs. This is not universally + true because there are types of interrupts which are truly per CPU + interrupts, e.g. the local timer interrupt. Aside of that multi queue + devices affine their interrupts to single CPUs or groups of CPUs per + queue without allowing the administrator to control the affinities. + + Moving the interrupts, which can be affinity controlled, away from CPUs + which run untrusted guests, reduces the attack vector space. + + Whether the interrupts with are affine to CPUs, which run untrusted + guests, provide interesting data for an attacker depends on the system + configuration and the scenarios which run on the system. While for some + of the interrupts it can be assumed that they won't expose interesting + information beyond exposing hints about the host OS memory layout, there + is no way to make general assumptions. + + Interrupt affinity can be controlled by the administrator via the + /proc/irq/$NR/smp_affinity[_list] files. Limited documentation is + available at: + + https://www.kernel.org/doc/Documentation/IRQ-affinity.txt + +.. _smt_control: + +4. SMT control +^^^^^^^^^^^^^^ + + To prevent the SMT issues of L1TF it might be necessary to disable SMT + completely. Disabling SMT can have a significant performance impact, but + the impact depends on the hosting scenario and the type of workloads. + The impact of disabling SMT needs also to be weighted against the impact + of other mitigation solutions like confining guests to dedicated cores. + + The kernel provides a sysfs interface to retrieve the status of SMT and + to control it. It also provides a kernel command line interface to + control SMT. + + The kernel command line interface consists of the following options: + + =========== ========================================================== + nosmt Affects the bring up of the secondary CPUs during boot. The + kernel tries to bring all present CPUs online during the + boot process. "nosmt" makes sure that from each physical + core only one - the so called primary (hyper) thread is + activated. Due to a design flaw of Intel processors related + to Machine Check Exceptions the non primary siblings have + to be brought up at least partially and are then shut down + again. "nosmt" can be undone via the sysfs interface. + + nosmt=force Has the same effect as "nosmt" but it does not allow to + undo the SMT disable via the sysfs interface. + =========== ========================================================== + + The sysfs interface provides two files: + + - /sys/devices/system/cpu/smt/control + - /sys/devices/system/cpu/smt/active + + /sys/devices/system/cpu/smt/control: + + This file allows to read out the SMT control state and provides the + ability to disable or (re)enable SMT. The possible states are: + + ============== =================================================== + on SMT is supported by the CPU and enabled. All + logical CPUs can be onlined and offlined without + restrictions. + + off SMT is supported by the CPU and disabled. Only + the so called primary SMT threads can be onlined + and offlined without restrictions. An attempt to + online a non-primary sibling is rejected + + forceoff Same as 'off' but the state cannot be controlled. + Attempts to write to the control file are rejected. + + notsupported The processor does not support SMT. It's therefore + not affected by the SMT implications of L1TF. + Attempts to write to the control file are rejected. + ============== =================================================== + + The possible states which can be written into this file to control SMT + state are: + + - on + - off + - forceoff + + /sys/devices/system/cpu/smt/active: + + This file reports whether SMT is enabled and active, i.e. if on any + physical core two or more sibling threads are online. + + SMT control is also possible at boot time via the l1tf kernel command + line parameter in combination with L1D flush control. See + :ref:`mitigation_control_command_line`. + +5. Disabling EPT +^^^^^^^^^^^^^^^^ + + Disabling EPT for virtual machines provides full mitigation for L1TF even + with SMT enabled, because the effective page tables for guests are + managed and sanitized by the hypervisor. Though disabling EPT has a + significant performance impact especially when the Meltdown mitigation + KPTI is enabled. + + EPT can be disabled in the hypervisor via the 'kvm-intel.ept' parameter. + +There is ongoing research and development for new mitigation mechanisms to +address the performance impact of disabling SMT or EPT. + +.. _mitigation_control_command_line: + +Mitigation control on the kernel command line +--------------------------------------------- + +The kernel command line allows to control the L1TF mitigations at boot +time with the option "l1tf=". The valid arguments for this option are: + + ============ ============================================================= + full Provides all available mitigations for the L1TF + vulnerability. Disables SMT and enables all mitigations in + the hypervisors, i.e. unconditional L1D flushing + + SMT control and L1D flush control via the sysfs interface + is still possible after boot. Hypervisors will issue a + warning when the first VM is started in a potentially + insecure configuration, i.e. SMT enabled or L1D flush + disabled. + + full,force Same as 'full', but disables SMT and L1D flush runtime + control. Implies the 'nosmt=force' command line option. + (i.e. sysfs control of SMT is disabled.) + + flush Leaves SMT enabled and enables the default hypervisor + mitigation, i.e. conditional L1D flushing + + SMT control and L1D flush control via the sysfs interface + is still possible after boot. Hypervisors will issue a + warning when the first VM is started in a potentially + insecure configuration, i.e. SMT enabled or L1D flush + disabled. + + flush,nosmt Disables SMT and enables the default hypervisor mitigation, + i.e. conditional L1D flushing. + + SMT control and L1D flush control via the sysfs interface + is still possible after boot. Hypervisors will issue a + warning when the first VM is started in a potentially + insecure configuration, i.e. SMT enabled or L1D flush + disabled. + + flush,nowarn Same as 'flush', but hypervisors will not warn when a VM is + started in a potentially insecure configuration. + + off Disables hypervisor mitigations and doesn't emit any + warnings. + It also drops the swap size and available RAM limit restrictions + on both hypervisor and bare metal. + + ============ ============================================================= + +The default is 'flush'. For details about L1D flushing see :ref:`l1d_flush`. + + +.. _mitigation_control_kvm: + +Mitigation control for KVM - module parameter +------------------------------------------------------------- + +The KVM hypervisor mitigation mechanism, flushing the L1D cache when +entering a guest, can be controlled with a module parameter. + +The option/parameter is "kvm-intel.vmentry_l1d_flush=". It takes the +following arguments: + + ============ ============================================================== + always L1D cache flush on every VMENTER. + + cond Flush L1D on VMENTER only when the code between VMEXIT and + VMENTER can leak host memory which is considered + interesting for an attacker. This still can leak host memory + which allows e.g. to determine the hosts address space layout. + + never Disables the mitigation + ============ ============================================================== + +The parameter can be provided on the kernel command line, as a module +parameter when loading the modules and at runtime modified via the sysfs +file: + +/sys/module/kvm_intel/parameters/vmentry_l1d_flush + +The default is 'cond'. If 'l1tf=full,force' is given on the kernel command +line, then 'always' is enforced and the kvm-intel.vmentry_l1d_flush +module parameter is ignored and writes to the sysfs file are rejected. + + +Mitigation selection guide +-------------------------- + +1. No virtualization in use +^^^^^^^^^^^^^^^^^^^^^^^^^^^ + + The system is protected by the kernel unconditionally and no further + action is required. + +2. Virtualization with trusted guests +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + + If the guest comes from a trusted source and the guest OS kernel is + guaranteed to have the L1TF mitigations in place the system is fully + protected against L1TF and no further action is required. + + To avoid the overhead of the default L1D flushing on VMENTER the + administrator can disable the flushing via the kernel command line and + sysfs control files. See :ref:`mitigation_control_command_line` and + :ref:`mitigation_control_kvm`. + + +3. Virtualization with untrusted guests +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +3.1. SMT not supported or disabled +"""""""""""""""""""""""""""""""""" + + If SMT is not supported by the processor or disabled in the BIOS or by + the kernel, it's only required to enforce L1D flushing on VMENTER. + + Conditional L1D flushing is the default behaviour and can be tuned. See + :ref:`mitigation_control_command_line` and :ref:`mitigation_control_kvm`. + +3.2. EPT not supported or disabled +"""""""""""""""""""""""""""""""""" + + If EPT is not supported by the processor or disabled in the hypervisor, + the system is fully protected. SMT can stay enabled and L1D flushing on + VMENTER is not required. + + EPT can be disabled in the hypervisor via the 'kvm-intel.ept' parameter. + +3.3. SMT and EPT supported and active +""""""""""""""""""""""""""""""""""""" + + If SMT and EPT are supported and active then various degrees of + mitigations can be employed: + + - L1D flushing on VMENTER: + + L1D flushing on VMENTER is the minimal protection requirement, but it + is only potent in combination with other mitigation methods. + + Conditional L1D flushing is the default behaviour and can be tuned. See + :ref:`mitigation_control_command_line` and :ref:`mitigation_control_kvm`. + + - Guest confinement: + + Confinement of guests to a single or a group of physical cores which + are not running any other processes, can reduce the attack surface + significantly, but interrupts, soft interrupts and kernel threads can + still expose valuable data to a potential attacker. See + :ref:`guest_confinement`. + + - Interrupt isolation: + + Isolating the guest CPUs from interrupts can reduce the attack surface + further, but still allows a malicious guest to explore a limited amount + of host physical memory. This can at least be used to gain knowledge + about the host address space layout. The interrupts which have a fixed + affinity to the CPUs which run the untrusted guests can depending on + the scenario still trigger soft interrupts and schedule kernel threads + which might expose valuable information. See + :ref:`interrupt_isolation`. + +The above three mitigation methods combined can provide protection to a +certain degree, but the risk of the remaining attack surface has to be +carefully analyzed. For full protection the following methods are +available: + + - Disabling SMT: + + Disabling SMT and enforcing the L1D flushing provides the maximum + amount of protection. This mitigation is not depending on any of the + above mitigation methods. + + SMT control and L1D flushing can be tuned by the command line + parameters 'nosmt', 'l1tf', 'kvm-intel.vmentry_l1d_flush' and at run + time with the matching sysfs control files. See :ref:`smt_control`, + :ref:`mitigation_control_command_line` and + :ref:`mitigation_control_kvm`. + + - Disabling EPT: + + Disabling EPT provides the maximum amount of protection as well. It is + not depending on any of the above mitigation methods. SMT can stay + enabled and L1D flushing is not required, but the performance impact is + significant. + + EPT can be disabled in the hypervisor via the 'kvm-intel.ept' + parameter. + +3.4. Nested virtual machines +"""""""""""""""""""""""""""" + +When nested virtualization is in use, three operating systems are involved: +the bare metal hypervisor, the nested hypervisor and the nested virtual +machine. VMENTER operations from the nested hypervisor into the nested +guest will always be processed by the bare metal hypervisor. If KVM is the +bare metal hypervisor it will: + + - Flush the L1D cache on every switch from the nested hypervisor to the + nested virtual machine, so that the nested hypervisor's secrets are not + exposed to the nested virtual machine; + + - Flush the L1D cache on every switch from the nested virtual machine to + the nested hypervisor; this is a complex operation, and flushing the L1D + cache avoids that the bare metal hypervisor's secrets are exposed to the + nested virtual machine; + + - Instruct the nested hypervisor to not perform any L1D cache flush. This + is an optimization to avoid double L1D flushing. + + +.. _default_mitigations: + +Default mitigations +------------------- + + The kernel default mitigations for vulnerable processors are: + + - PTE inversion to protect against malicious user space. This is done + unconditionally and cannot be controlled. The swap storage is limited + to ~16TB. + + - L1D conditional flushing on VMENTER when EPT is enabled for + a guest. + + The kernel does not by default enforce the disabling of SMT, which leaves + SMT systems vulnerable when running untrusted guests with EPT enabled. + + The rationale for this choice is: + + - Force disabling SMT can break existing setups, especially with + unattended updates. + + - If regular users run untrusted guests on their machine, then L1TF is + just an add on to other malware which might be embedded in an untrusted + guest, e.g. spam-bots or attacks on the local network. + + There is no technical way to prevent a user from running untrusted code + on their machines blindly. + + - It's technically extremely unlikely and from today's knowledge even + impossible that L1TF can be exploited via the most popular attack + mechanisms like JavaScript because these mechanisms have no way to + control PTEs. If this would be possible and not other mitigation would + be possible, then the default might be different. + + - The administrators of cloud and hosting setups have to carefully + analyze the risk for their scenarios and make the appropriate + mitigation choices, which might even vary across their deployed + machines and also result in other changes of their overall setup. + There is no way for the kernel to provide a sensible default for this + kind of scenarios. diff --git a/Documentation/admin-guide/index.rst b/Documentation/admin-guide/index.rst index 0a491676685e..42247516962a 100644 --- a/Documentation/admin-guide/index.rst +++ b/Documentation/admin-guide/index.rst @@ -17,14 +17,12 @@ etc. kernel-parameters devices -This section describes CPU vulnerabilities and provides an overview of the -possible mitigations along with guidance for selecting mitigations if they -are configurable at compile, boot or run time. +This section describes CPU vulnerabilities and their mitigations. .. toctree:: :maxdepth: 1 - l1tf + hw-vuln/index Here is a set of documents aimed at users who are trying to track down problems and bugs in particular. diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt index dddb024eb523..9afcb240a673 100644 --- a/Documentation/admin-guide/kernel-parameters.txt +++ b/Documentation/admin-guide/kernel-parameters.txt @@ -2114,7 +2114,7 @@ Default is 'flush'. - For details see: Documentation/admin-guide/l1tf.rst + For details see: Documentation/admin-guide/hw-vuln/l1tf.rst l2cr= [PPC] diff --git a/Documentation/admin-guide/l1tf.rst b/Documentation/admin-guide/l1tf.rst deleted file mode 100644 index 9af977384168..000000000000 --- a/Documentation/admin-guide/l1tf.rst +++ /dev/null @@ -1,614 +0,0 @@ -L1TF - L1 Terminal Fault -======================== - -L1 Terminal Fault is a hardware vulnerability which allows unprivileged -speculative access to data which is available in the Level 1 Data Cache -when the page table entry controlling the virtual address, which is used -for the access, has the Present bit cleared or other reserved bits set. - -Affected processors -------------------- - -This vulnerability affects a wide range of Intel processors. The -vulnerability is not present on: - - - Processors from AMD, Centaur and other non Intel vendors - - - Older processor models, where the CPU family is < 6 - - - A range of Intel ATOM processors (Cedarview, Cloverview, Lincroft, - Penwell, Pineview, Silvermont, Airmont, Merrifield) - - - The Intel XEON PHI family - - - Intel processors which have the ARCH_CAP_RDCL_NO bit set in the - IA32_ARCH_CAPABILITIES MSR. If the bit is set the CPU is not affected - by the Meltdown vulnerability either. These CPUs should become - available by end of 2018. - -Whether a processor is affected or not can be read out from the L1TF -vulnerability file in sysfs. See :ref:`l1tf_sys_info`. - -Related CVEs ------------- - -The following CVE entries are related to the L1TF vulnerability: - - ============= ================= ============================== - CVE-2018-3615 L1 Terminal Fault SGX related aspects - CVE-2018-3620 L1 Terminal Fault OS, SMM related aspects - CVE-2018-3646 L1 Terminal Fault Virtualization related aspects - ============= ================= ============================== - -Problem -------- - -If an instruction accesses a virtual address for which the relevant page -table entry (PTE) has the Present bit cleared or other reserved bits set, -then speculative execution ignores the invalid PTE and loads the referenced -data if it is present in the Level 1 Data Cache, as if the page referenced -by the address bits in the PTE was still present and accessible. - -While this is a purely speculative mechanism and the instruction will raise -a page fault when it is retired eventually, the pure act of loading the -data and making it available to other speculative instructions opens up the -opportunity for side channel attacks to unprivileged malicious code, -similar to the Meltdown attack. - -While Meltdown breaks the user space to kernel space protection, L1TF -allows to attack any physical memory address in the system and the attack -works across all protection domains. It allows an attack of SGX and also -works from inside virtual machines because the speculation bypasses the -extended page table (EPT) protection mechanism. - - -Attack scenarios ----------------- - -1. Malicious user space -^^^^^^^^^^^^^^^^^^^^^^^ - - Operating Systems store arbitrary information in the address bits of a - PTE which is marked non present. This allows a malicious user space - application to attack the physical memory to which these PTEs resolve. - In some cases user-space can maliciously influence the information - encoded in the address bits of the PTE, thus making attacks more - deterministic and more practical. - - The Linux kernel contains a mitigation for this attack vector, PTE - inversion, which is permanently enabled and has no performance - impact. The kernel ensures that the address bits of PTEs, which are not - marked present, never point to cacheable physical memory space. - - A system with an up to date kernel is protected against attacks from - malicious user space applications. - -2. Malicious guest in a virtual machine -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - - The fact that L1TF breaks all domain protections allows malicious guest - OSes, which can control the PTEs directly, and malicious guest user - space applications, which run on an unprotected guest kernel lacking the - PTE inversion mitigation for L1TF, to attack physical host memory. - - A special aspect of L1TF in the context of virtualization is symmetric - multi threading (SMT). The Intel implementation of SMT is called - HyperThreading. The fact that Hyperthreads on the affected processors - share the L1 Data Cache (L1D) is important for this. As the flaw allows - only to attack data which is present in L1D, a malicious guest running - on one Hyperthread can attack the data which is brought into the L1D by - the context which runs on the sibling Hyperthread of the same physical - core. This context can be host OS, host user space or a different guest. - - If the processor does not support Extended Page Tables, the attack is - only possible, when the hypervisor does not sanitize the content of the - effective (shadow) page tables. - - While solutions exist to mitigate these attack vectors fully, these - mitigations are not enabled by default in the Linux kernel because they - can affect performance significantly. The kernel provides several - mechanisms which can be utilized to address the problem depending on the - deployment scenario. The mitigations, their protection scope and impact - are described in the next sections. - - The default mitigations and the rationale for choosing them are explained - at the end of this document. See :ref:`default_mitigations`. - -.. _l1tf_sys_info: - -L1TF system information ------------------------ - -The Linux kernel provides a sysfs interface to enumerate the current L1TF -status of the system: whether the system is vulnerable, and which -mitigations are active. The relevant sysfs file is: - -/sys/devices/system/cpu/vulnerabilities/l1tf - -The possible values in this file are: - - =========================== =============================== - 'Not affected' The processor is not vulnerable - 'Mitigation: PTE Inversion' The host protection is active - =========================== =============================== - -If KVM/VMX is enabled and the processor is vulnerable then the following -information is appended to the 'Mitigation: PTE Inversion' part: - - - SMT status: - - ===================== ================ - 'VMX: SMT vulnerable' SMT is enabled - 'VMX: SMT disabled' SMT is disabled - ===================== ================ - - - L1D Flush mode: - - ================================ ==================================== - 'L1D vulnerable' L1D flushing is disabled - - 'L1D conditional cache flushes' L1D flush is conditionally enabled - - 'L1D cache flushes' L1D flush is unconditionally enabled - ================================ ==================================== - -The resulting grade of protection is discussed in the following sections. - - -Host mitigation mechanism -------------------------- - -The kernel is unconditionally protected against L1TF attacks from malicious -user space running on the host. - - -Guest mitigation mechanisms ---------------------------- - -.. _l1d_flush: - -1. L1D flush on VMENTER -^^^^^^^^^^^^^^^^^^^^^^^ - - To make sure that a guest cannot attack data which is present in the L1D - the hypervisor flushes the L1D before entering the guest. - - Flushing the L1D evicts not only the data which should not be accessed - by a potentially malicious guest, it also flushes the guest - data. Flushing the L1D has a performance impact as the processor has to - bring the flushed guest data back into the L1D. Depending on the - frequency of VMEXIT/VMENTER and the type of computations in the guest - performance degradation in the range of 1% to 50% has been observed. For - scenarios where guest VMEXIT/VMENTER are rare the performance impact is - minimal. Virtio and mechanisms like posted interrupts are designed to - confine the VMEXITs to a bare minimum, but specific configurations and - application scenarios might still suffer from a high VMEXIT rate. - - The kernel provides two L1D flush modes: - - conditional ('cond') - - unconditional ('always') - - The conditional mode avoids L1D flushing after VMEXITs which execute - only audited code paths before the corresponding VMENTER. These code - paths have been verified that they cannot expose secrets or other - interesting data to an attacker, but they can leak information about the - address space layout of the hypervisor. - - Unconditional mode flushes L1D on all VMENTER invocations and provides - maximum protection. It has a higher overhead than the conditional - mode. The overhead cannot be quantified correctly as it depends on the - workload scenario and the resulting number of VMEXITs. - - The general recommendation is to enable L1D flush on VMENTER. The kernel - defaults to conditional mode on affected processors. - - **Note**, that L1D flush does not prevent the SMT problem because the - sibling thread will also bring back its data into the L1D which makes it - attackable again. - - L1D flush can be controlled by the administrator via the kernel command - line and sysfs control files. See :ref:`mitigation_control_command_line` - and :ref:`mitigation_control_kvm`. - -.. _guest_confinement: - -2. Guest VCPU confinement to dedicated physical cores -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - - To address the SMT problem, it is possible to make a guest or a group of - guests affine to one or more physical cores. The proper mechanism for - that is to utilize exclusive cpusets to ensure that no other guest or - host tasks can run on these cores. - - If only a single guest or related guests run on sibling SMT threads on - the same physical core then they can only attack their own memory and - restricted parts of the host memory. - - Host memory is attackable, when one of the sibling SMT threads runs in - host OS (hypervisor) context and the other in guest context. The amount - of valuable information from the host OS context depends on the context - which the host OS executes, i.e. interrupts, soft interrupts and kernel - threads. The amount of valuable data from these contexts cannot be - declared as non-interesting for an attacker without deep inspection of - the code. - - **Note**, that assigning guests to a fixed set of physical cores affects - the ability of the scheduler to do load balancing and might have - negative effects on CPU utilization depending on the hosting - scenario. Disabling SMT might be a viable alternative for particular - scenarios. - - For further information about confining guests to a single or to a group - of cores consult the cpusets documentation: - - https://www.kernel.org/doc/Documentation/cgroup-v1/cpusets.txt - -.. _interrupt_isolation: - -3. Interrupt affinity -^^^^^^^^^^^^^^^^^^^^^ - - Interrupts can be made affine to logical CPUs. This is not universally - true because there are types of interrupts which are truly per CPU - interrupts, e.g. the local timer interrupt. Aside of that multi queue - devices affine their interrupts to single CPUs or groups of CPUs per - queue without allowing the administrator to control the affinities. - - Moving the interrupts, which can be affinity controlled, away from CPUs - which run untrusted guests, reduces the attack vector space. - - Whether the interrupts with are affine to CPUs, which run untrusted - guests, provide interesting data for an attacker depends on the system - configuration and the scenarios which run on the system. While for some - of the interrupts it can be assumed that they won't expose interesting - information beyond exposing hints about the host OS memory layout, there - is no way to make general assumptions. - - Interrupt affinity can be controlled by the administrator via the - /proc/irq/$NR/smp_affinity[_list] files. Limited documentation is - available at: - - https://www.kernel.org/doc/Documentation/IRQ-affinity.txt - -.. _smt_control: - -4. SMT control -^^^^^^^^^^^^^^ - - To prevent the SMT issues of L1TF it might be necessary to disable SMT - completely. Disabling SMT can have a significant performance impact, but - the impact depends on the hosting scenario and the type of workloads. - The impact of disabling SMT needs also to be weighted against the impact - of other mitigation solutions like confining guests to dedicated cores. - - The kernel provides a sysfs interface to retrieve the status of SMT and - to control it. It also provides a kernel command line interface to - control SMT. - - The kernel command line interface consists of the following options: - - =========== ========================================================== - nosmt Affects the bring up of the secondary CPUs during boot. The - kernel tries to bring all present CPUs online during the - boot process. "nosmt" makes sure that from each physical - core only one - the so called primary (hyper) thread is - activated. Due to a design flaw of Intel processors related - to Machine Check Exceptions the non primary siblings have - to be brought up at least partially and are then shut down - again. "nosmt" can be undone via the sysfs interface. - - nosmt=force Has the same effect as "nosmt" but it does not allow to - undo the SMT disable via the sysfs interface. - =========== ========================================================== - - The sysfs interface provides two files: - - - /sys/devices/system/cpu/smt/control - - /sys/devices/system/cpu/smt/active - - /sys/devices/system/cpu/smt/control: - - This file allows to read out the SMT control state and provides the - ability to disable or (re)enable SMT. The possible states are: - - ============== =================================================== - on SMT is supported by the CPU and enabled. All - logical CPUs can be onlined and offlined without - restrictions. - - off SMT is supported by the CPU and disabled. Only - the so called primary SMT threads can be onlined - and offlined without restrictions. An attempt to - online a non-primary sibling is rejected - - forceoff Same as 'off' but the state cannot be controlled. - Attempts to write to the control file are rejected. - - notsupported The processor does not support SMT. It's therefore - not affected by the SMT implications of L1TF. - Attempts to write to the control file are rejected. - ============== =================================================== - - The possible states which can be written into this file to control SMT - state are: - - - on - - off - - forceoff - - /sys/devices/system/cpu/smt/active: - - This file reports whether SMT is enabled and active, i.e. if on any - physical core two or more sibling threads are online. - - SMT control is also possible at boot time via the l1tf kernel command - line parameter in combination with L1D flush control. See - :ref:`mitigation_control_command_line`. - -5. Disabling EPT -^^^^^^^^^^^^^^^^ - - Disabling EPT for virtual machines provides full mitigation for L1TF even - with SMT enabled, because the effective page tables for guests are - managed and sanitized by the hypervisor. Though disabling EPT has a - significant performance impact especially when the Meltdown mitigation - KPTI is enabled. - - EPT can be disabled in the hypervisor via the 'kvm-intel.ept' parameter. - -There is ongoing research and development for new mitigation mechanisms to -address the performance impact of disabling SMT or EPT. - -.. _mitigation_control_command_line: - -Mitigation control on the kernel command line ---------------------------------------------- - -The kernel command line allows to control the L1TF mitigations at boot -time with the option "l1tf=". The valid arguments for this option are: - - ============ ============================================================= - full Provides all available mitigations for the L1TF - vulnerability. Disables SMT and enables all mitigations in - the hypervisors, i.e. unconditional L1D flushing - - SMT control and L1D flush control via the sysfs interface - is still possible after boot. Hypervisors will issue a - warning when the first VM is started in a potentially - insecure configuration, i.e. SMT enabled or L1D flush - disabled. - - full,force Same as 'full', but disables SMT and L1D flush runtime - control. Implies the 'nosmt=force' command line option. - (i.e. sysfs control of SMT is disabled.) - - flush Leaves SMT enabled and enables the default hypervisor - mitigation, i.e. conditional L1D flushing - - SMT control and L1D flush control via the sysfs interface - is still possible after boot. Hypervisors will issue a - warning when the first VM is started in a potentially - insecure configuration, i.e. SMT enabled or L1D flush - disabled. - - flush,nosmt Disables SMT and enables the default hypervisor mitigation, - i.e. conditional L1D flushing. - - SMT control and L1D flush control via the sysfs interface - is still possible after boot. Hypervisors will issue a - warning when the first VM is started in a potentially - insecure configuration, i.e. SMT enabled or L1D flush - disabled. - - flush,nowarn Same as 'flush', but hypervisors will not warn when a VM is - started in a potentially insecure configuration. - - off Disables hypervisor mitigations and doesn't emit any - warnings. - It also drops the swap size and available RAM limit restrictions - on both hypervisor and bare metal. - - ============ ============================================================= - -The default is 'flush'. For details about L1D flushing see :ref:`l1d_flush`. - - -.. _mitigation_control_kvm: - -Mitigation control for KVM - module parameter -------------------------------------------------------------- - -The KVM hypervisor mitigation mechanism, flushing the L1D cache when -entering a guest, can be controlled with a module parameter. - -The option/parameter is "kvm-intel.vmentry_l1d_flush=". It takes the -following arguments: - - ============ ============================================================== - always L1D cache flush on every VMENTER. - - cond Flush L1D on VMENTER only when the code between VMEXIT and - VMENTER can leak host memory which is considered - interesting for an attacker. This still can leak host memory - which allows e.g. to determine the hosts address space layout. - - never Disables the mitigation - ============ ============================================================== - -The parameter can be provided on the kernel command line, as a module -parameter when loading the modules and at runtime modified via the sysfs -file: - -/sys/module/kvm_intel/parameters/vmentry_l1d_flush - -The default is 'cond'. If 'l1tf=full,force' is given on the kernel command -line, then 'always' is enforced and the kvm-intel.vmentry_l1d_flush -module parameter is ignored and writes to the sysfs file are rejected. - - -Mitigation selection guide --------------------------- - -1. No virtualization in use -^^^^^^^^^^^^^^^^^^^^^^^^^^^ - - The system is protected by the kernel unconditionally and no further - action is required. - -2. Virtualization with trusted guests -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - - If the guest comes from a trusted source and the guest OS kernel is - guaranteed to have the L1TF mitigations in place the system is fully - protected against L1TF and no further action is required. - - To avoid the overhead of the default L1D flushing on VMENTER the - administrator can disable the flushing via the kernel command line and - sysfs control files. See :ref:`mitigation_control_command_line` and - :ref:`mitigation_control_kvm`. - - -3. Virtualization with untrusted guests -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -3.1. SMT not supported or disabled -"""""""""""""""""""""""""""""""""" - - If SMT is not supported by the processor or disabled in the BIOS or by - the kernel, it's only required to enforce L1D flushing on VMENTER. - - Conditional L1D flushing is the default behaviour and can be tuned. See - :ref:`mitigation_control_command_line` and :ref:`mitigation_control_kvm`. - -3.2. EPT not supported or disabled -"""""""""""""""""""""""""""""""""" - - If EPT is not supported by the processor or disabled in the hypervisor, - the system is fully protected. SMT can stay enabled and L1D flushing on - VMENTER is not required. - - EPT can be disabled in the hypervisor via the 'kvm-intel.ept' parameter. - -3.3. SMT and EPT supported and active -""""""""""""""""""""""""""""""""""""" - - If SMT and EPT are supported and active then various degrees of - mitigations can be employed: - - - L1D flushing on VMENTER: - - L1D flushing on VMENTER is the minimal protection requirement, but it - is only potent in combination with other mitigation methods. - - Conditional L1D flushing is the default behaviour and can be tuned. See - :ref:`mitigation_control_command_line` and :ref:`mitigation_control_kvm`. - - - Guest confinement: - - Confinement of guests to a single or a group of physical cores which - are not running any other processes, can reduce the attack surface - significantly, but interrupts, soft interrupts and kernel threads can - still expose valuable data to a potential attacker. See - :ref:`guest_confinement`. - - - Interrupt isolation: - - Isolating the guest CPUs from interrupts can reduce the attack surface - further, but still allows a malicious guest to explore a limited amount - of host physical memory. This can at least be used to gain knowledge - about the host address space layout. The interrupts which have a fixed - affinity to the CPUs which run the untrusted guests can depending on - the scenario still trigger soft interrupts and schedule kernel threads - which might expose valuable information. See - :ref:`interrupt_isolation`. - -The above three mitigation methods combined can provide protection to a -certain degree, but the risk of the remaining attack surface has to be -carefully analyzed. For full protection the following methods are -available: - - - Disabling SMT: - - Disabling SMT and enforcing the L1D flushing provides the maximum - amount of protection. This mitigation is not depending on any of the - above mitigation methods. - - SMT control and L1D flushing can be tuned by the command line - parameters 'nosmt', 'l1tf', 'kvm-intel.vmentry_l1d_flush' and at run - time with the matching sysfs control files. See :ref:`smt_control`, - :ref:`mitigation_control_command_line` and - :ref:`mitigation_control_kvm`. - - - Disabling EPT: - - Disabling EPT provides the maximum amount of protection as well. It is - not depending on any of the above mitigation methods. SMT can stay - enabled and L1D flushing is not required, but the performance impact is - significant. - - EPT can be disabled in the hypervisor via the 'kvm-intel.ept' - parameter. - -3.4. Nested virtual machines -"""""""""""""""""""""""""""" - -When nested virtualization is in use, three operating systems are involved: -the bare metal hypervisor, the nested hypervisor and the nested virtual -machine. VMENTER operations from the nested hypervisor into the nested -guest will always be processed by the bare metal hypervisor. If KVM is the -bare metal hypervisor it will: - - - Flush the L1D cache on every switch from the nested hypervisor to the - nested virtual machine, so that the nested hypervisor's secrets are not - exposed to the nested virtual machine; - - - Flush the L1D cache on every switch from the nested virtual machine to - the nested hypervisor; this is a complex operation, and flushing the L1D - cache avoids that the bare metal hypervisor's secrets are exposed to the - nested virtual machine; - - - Instruct the nested hypervisor to not perform any L1D cache flush. This - is an optimization to avoid double L1D flushing. - - -.. _default_mitigations: - -Default mitigations -------------------- - - The kernel default mitigations for vulnerable processors are: - - - PTE inversion to protect against malicious user space. This is done - unconditionally and cannot be controlled. The swap storage is limited - to ~16TB. - - - L1D conditional flushing on VMENTER when EPT is enabled for - a guest. - - The kernel does not by default enforce the disabling of SMT, which leaves - SMT systems vulnerable when running untrusted guests with EPT enabled. - - The rationale for this choice is: - - - Force disabling SMT can break existing setups, especially with - unattended updates. - - - If regular users run untrusted guests on their machine, then L1TF is - just an add on to other malware which might be embedded in an untrusted - guest, e.g. spam-bots or attacks on the local network. - - There is no technical way to prevent a user from running untrusted code - on their machines blindly. - - - It's technically extremely unlikely and from today's knowledge even - impossible that L1TF can be exploited via the most popular attack - mechanisms like JavaScript because these mechanisms have no way to - control PTEs. If this would be possible and not other mitigation would - be possible, then the default might be different. - - - The administrators of cloud and hosting setups have to carefully - analyze the risk for their scenarios and make the appropriate - mitigation choices, which might even vary across their deployed - machines and also result in other changes of their overall setup. - There is no way for the kernel to provide a sensible default for this - kind of scenarios. diff --git a/arch/x86/kernel/cpu/bugs.c b/arch/x86/kernel/cpu/bugs.c index 95cda38c8785..373ae1dcd301 100644 --- a/arch/x86/kernel/cpu/bugs.c +++ b/arch/x86/kernel/cpu/bugs.c @@ -1107,7 +1107,7 @@ static void __init l1tf_select_mitigation(void) pr_info("You may make it effective by booting the kernel with mem=%llu parameter.\n", half_pa); pr_info("However, doing so will make a part of your RAM unusable.\n"); - pr_info("Reading https://www.kernel.org/doc/html/latest/admin-guide/l1tf.html might help you decide.\n"); + pr_info("Reading https://www.kernel.org/doc/html/latest/admin-guide/hw-vuln/l1tf.html might help you decide.\n"); return; } diff --git a/arch/x86/kvm/vmx/vmx.c b/arch/x86/kvm/vmx/vmx.c index 544bd24a9c1e..b0597507bde7 100644 --- a/arch/x86/kvm/vmx/vmx.c +++ b/arch/x86/kvm/vmx/vmx.c @@ -6801,8 +6801,8 @@ free_partial_vcpu: return ERR_PTR(err); } -#define L1TF_MSG_SMT "L1TF CPU bug present and SMT on, data leak possible. See CVE-2018-3646 and https://www.kernel.org/doc/html/latest/admin-guide/l1tf.html for details.\n" -#define L1TF_MSG_L1D "L1TF CPU bug present and virtualization mitigation disabled, data leak possible. See CVE-2018-3646 and https://www.kernel.org/doc/html/latest/admin-guide/l1tf.html for details.\n" +#define L1TF_MSG_SMT "L1TF CPU bug present and SMT on, data leak possible. See CVE-2018-3646 and https://www.kernel.org/doc/html/latest/admin-guide/hw-vuln/l1tf.html for details.\n" +#define L1TF_MSG_L1D "L1TF CPU bug present and virtualization mitigation disabled, data leak possible. See CVE-2018-3646 and https://www.kernel.org/doc/html/latest/admin-guide/hw-vuln/l1tf.html for details.\n" static int vmx_vm_init(struct kvm *kvm) { -- cgit v1.2.3 From 5999bbe7a6ea3c62029532ec84dc06003a1fa258 Mon Sep 17 00:00:00 2001 From: Thomas Gleixner Date: Tue, 19 Feb 2019 00:02:31 +0100 Subject: Documentation: Add MDS vulnerability documentation Add the initial MDS vulnerability documentation. Signed-off-by: Thomas Gleixner Reviewed-by: Jon Masters --- Documentation/ABI/testing/sysfs-devices-system-cpu | 3 +- Documentation/admin-guide/hw-vuln/index.rst | 1 + Documentation/admin-guide/hw-vuln/l1tf.rst | 1 + Documentation/admin-guide/hw-vuln/mds.rst | 307 +++++++++++++++++++++ Documentation/admin-guide/kernel-parameters.txt | 2 + 5 files changed, 312 insertions(+), 2 deletions(-) create mode 100644 Documentation/admin-guide/hw-vuln/mds.rst (limited to 'Documentation') diff --git a/Documentation/ABI/testing/sysfs-devices-system-cpu b/Documentation/ABI/testing/sysfs-devices-system-cpu index 744c6d764b0c..141a7bb58b80 100644 --- a/Documentation/ABI/testing/sysfs-devices-system-cpu +++ b/Documentation/ABI/testing/sysfs-devices-system-cpu @@ -497,8 +497,7 @@ Description: Information about CPU vulnerabilities "Vulnerable" CPU is affected and no mitigation in effect "Mitigation: $M" CPU is affected and mitigation $M is in effect - Details about the l1tf file can be found in - Documentation/admin-guide/hw-vuln/l1tf.rst + See also: Documentation/admin-guide/hw-vuln/index.rst What: /sys/devices/system/cpu/smt /sys/devices/system/cpu/smt/active diff --git a/Documentation/admin-guide/hw-vuln/index.rst b/Documentation/admin-guide/hw-vuln/index.rst index 8ce2009f1981..ffc064c1ec68 100644 --- a/Documentation/admin-guide/hw-vuln/index.rst +++ b/Documentation/admin-guide/hw-vuln/index.rst @@ -10,3 +10,4 @@ are configurable at compile, boot or run time. :maxdepth: 1 l1tf + mds diff --git a/Documentation/admin-guide/hw-vuln/l1tf.rst b/Documentation/admin-guide/hw-vuln/l1tf.rst index 9af977384168..31653a9f0e1b 100644 --- a/Documentation/admin-guide/hw-vuln/l1tf.rst +++ b/Documentation/admin-guide/hw-vuln/l1tf.rst @@ -445,6 +445,7 @@ The default is 'cond'. If 'l1tf=full,force' is given on the kernel command line, then 'always' is enforced and the kvm-intel.vmentry_l1d_flush module parameter is ignored and writes to the sysfs file are rejected. +.. _mitigation_selection: Mitigation selection guide -------------------------- diff --git a/Documentation/admin-guide/hw-vuln/mds.rst b/Documentation/admin-guide/hw-vuln/mds.rst new file mode 100644 index 000000000000..1de29d28903d --- /dev/null +++ b/Documentation/admin-guide/hw-vuln/mds.rst @@ -0,0 +1,307 @@ +MDS - Microarchitectural Data Sampling +====================================== + +Microarchitectural Data Sampling is a hardware vulnerability which allows +unprivileged speculative access to data which is available in various CPU +internal buffers. + +Affected processors +------------------- + +This vulnerability affects a wide range of Intel processors. The +vulnerability is not present on: + + - Processors from AMD, Centaur and other non Intel vendors + + - Older processor models, where the CPU family is < 6 + + - Some Atoms (Bonnell, Saltwell, Goldmont, GoldmontPlus) + + - Intel processors which have the ARCH_CAP_MDS_NO bit set in the + IA32_ARCH_CAPABILITIES MSR. + +Whether a processor is affected or not can be read out from the MDS +vulnerability file in sysfs. See :ref:`mds_sys_info`. + +Not all processors are affected by all variants of MDS, but the mitigation +is identical for all of them so the kernel treats them as a single +vulnerability. + +Related CVEs +------------ + +The following CVE entries are related to the MDS vulnerability: + + ============== ===== ============================================== + CVE-2018-12126 MSBDS Microarchitectural Store Buffer Data Sampling + CVE-2018-12130 MFBDS Microarchitectural Fill Buffer Data Sampling + CVE-2018-12127 MLPDS Microarchitectural Load Port Data Sampling + ============== ===== ============================================== + +Problem +------- + +When performing store, load, L1 refill operations, processors write data +into temporary microarchitectural structures (buffers). The data in the +buffer can be forwarded to load operations as an optimization. + +Under certain conditions, usually a fault/assist caused by a load +operation, data unrelated to the load memory address can be speculatively +forwarded from the buffers. Because the load operation causes a fault or +assist and its result will be discarded, the forwarded data will not cause +incorrect program execution or state changes. But a malicious operation +may be able to forward this speculative data to a disclosure gadget which +allows in turn to infer the value via a cache side channel attack. + +Because the buffers are potentially shared between Hyper-Threads cross +Hyper-Thread attacks are possible. + +Deeper technical information is available in the MDS specific x86 +architecture section: :ref:`Documentation/x86/mds.rst `. + + +Attack scenarios +---------------- + +Attacks against the MDS vulnerabilities can be mounted from malicious non +priviledged user space applications running on hosts or guest. Malicious +guest OSes can obviously mount attacks as well. + +Contrary to other speculation based vulnerabilities the MDS vulnerability +does not allow the attacker to control the memory target address. As a +consequence the attacks are purely sampling based, but as demonstrated with +the TLBleed attack samples can be postprocessed successfully. + +Web-Browsers +^^^^^^^^^^^^ + + It's unclear whether attacks through Web-Browsers are possible at + all. The exploitation through Java-Script is considered very unlikely, + but other widely used web technologies like Webassembly could possibly be + abused. + + +.. _mds_sys_info: + +MDS system information +----------------------- + +The Linux kernel provides a sysfs interface to enumerate the current MDS +status of the system: whether the system is vulnerable, and which +mitigations are active. The relevant sysfs file is: + +/sys/devices/system/cpu/vulnerabilities/mds + +The possible values in this file are: + + ========================================= ================================= + 'Not affected' The processor is not vulnerable + + 'Vulnerable' The processor is vulnerable, + but no mitigation enabled + + 'Vulnerable: Clear CPU buffers attempted' The processor is vulnerable but + microcode is not updated. + The mitigation is enabled on a + best effort basis. + See :ref:`vmwerv` + + 'Mitigation: CPU buffer clear' The processor is vulnerable and the + CPU buffer clearing mitigation is + enabled. + ========================================= ================================= + +If the processor is vulnerable then the following information is appended +to the above information: + + ======================== ============================================ + 'SMT vulnerable' SMT is enabled + 'SMT mitigated' SMT is enabled and mitigated + 'SMT disabled' SMT is disabled + 'SMT Host state unknown' Kernel runs in a VM, Host SMT state unknown + ======================== ============================================ + +.. _vmwerv: + +Best effort mitigation mode +^^^^^^^^^^^^^^^^^^^^^^^^^^^ + + If the processor is vulnerable, but the availability of the microcode based + mitigation mechanism is not advertised via CPUID the kernel selects a best + effort mitigation mode. This mode invokes the mitigation instructions + without a guarantee that they clear the CPU buffers. + + This is done to address virtualization scenarios where the host has the + microcode update applied, but the hypervisor is not yet updated to expose + the CPUID to the guest. If the host has updated microcode the protection + takes effect otherwise a few cpu cycles are wasted pointlessly. + + The state in the mds sysfs file reflects this situation accordingly. + + +Mitigation mechanism +------------------------- + +The kernel detects the affected CPUs and the presence of the microcode +which is required. + +If a CPU is affected and the microcode is available, then the kernel +enables the mitigation by default. The mitigation can be controlled at boot +time via a kernel command line option. See +:ref:`mds_mitigation_control_command_line`. + +.. _cpu_buffer_clear: + +CPU buffer clearing +^^^^^^^^^^^^^^^^^^^ + + The mitigation for MDS clears the affected CPU buffers on return to user + space and when entering a guest. + + If SMT is enabled it also clears the buffers on idle entry when the CPU + is only affected by MSBDS and not any other MDS variant, because the + other variants cannot be protected against cross Hyper-Thread attacks. + + For CPUs which are only affected by MSBDS the user space, guest and idle + transition mitigations are sufficient and SMT is not affected. + +.. _virt_mechanism: + +Virtualization mitigation +^^^^^^^^^^^^^^^^^^^^^^^^^ + + The protection for host to guest transition depends on the L1TF + vulnerability of the CPU: + + - CPU is affected by L1TF: + + If the L1D flush mitigation is enabled and up to date microcode is + available, the L1D flush mitigation is automatically protecting the + guest transition. + + If the L1D flush mitigation is disabled then the MDS mitigation is + invoked explicit when the host MDS mitigation is enabled. + + For details on L1TF and virtualization see: + :ref:`Documentation/admin-guide/hw-vuln//l1tf.rst `. + + - CPU is not affected by L1TF: + + CPU buffers are flushed before entering the guest when the host MDS + mitigation is enabled. + + The resulting MDS protection matrix for the host to guest transition: + + ============ ===== ============= ============ ================= + L1TF MDS VMX-L1FLUSH Host MDS MDS-State + + Don't care No Don't care N/A Not affected + + Yes Yes Disabled Off Vulnerable + + Yes Yes Disabled Full Mitigated + + Yes Yes Enabled Don't care Mitigated + + No Yes N/A Off Vulnerable + + No Yes N/A Full Mitigated + ============ ===== ============= ============ ================= + + This only covers the host to guest transition, i.e. prevents leakage from + host to guest, but does not protect the guest internally. Guests need to + have their own protections. + +.. _xeon_phi: + +XEON PHI specific considerations +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + + The XEON PHI processor family is affected by MSBDS which can be exploited + cross Hyper-Threads when entering idle states. Some XEON PHI variants allow + to use MWAIT in user space (Ring 3) which opens an potential attack vector + for malicious user space. The exposure can be disabled on the kernel + command line with the 'ring3mwait=disable' command line option. + + XEON PHI is not affected by the other MDS variants and MSBDS is mitigated + before the CPU enters a idle state. As XEON PHI is not affected by L1TF + either disabling SMT is not required for full protection. + +.. _mds_smt_control: + +SMT control +^^^^^^^^^^^ + + All MDS variants except MSBDS can be attacked cross Hyper-Threads. That + means on CPUs which are affected by MFBDS or MLPDS it is necessary to + disable SMT for full protection. These are most of the affected CPUs; the + exception is XEON PHI, see :ref:`xeon_phi`. + + Disabling SMT can have a significant performance impact, but the impact + depends on the type of workloads. + + See the relevant chapter in the L1TF mitigation documentation for details: + :ref:`Documentation/admin-guide/hw-vuln/l1tf.rst `. + + +.. _mds_mitigation_control_command_line: + +Mitigation control on the kernel command line +--------------------------------------------- + +The kernel command line allows to control the MDS mitigations at boot +time with the option "mds=". The valid arguments for this option are: + + ============ ============================================================= + full If the CPU is vulnerable, enable all available mitigations + for the MDS vulnerability, CPU buffer clearing on exit to + userspace and when entering a VM. Idle transitions are + protected as well if SMT is enabled. + + It does not automatically disable SMT. + + off Disables MDS mitigations completely. + + ============ ============================================================= + +Not specifying this option is equivalent to "mds=full". + + +Mitigation selection guide +-------------------------- + +1. Trusted userspace +^^^^^^^^^^^^^^^^^^^^ + + If all userspace applications are from a trusted source and do not + execute untrusted code which is supplied externally, then the mitigation + can be disabled. + + +2. Virtualization with trusted guests +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + + The same considerations as above versus trusted user space apply. + +3. Virtualization with untrusted guests +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + + The protection depends on the state of the L1TF mitigations. + See :ref:`virt_mechanism`. + + If the MDS mitigation is enabled and SMT is disabled, guest to host and + guest to guest attacks are prevented. + +.. _mds_default_mitigations: + +Default mitigations +------------------- + + The kernel default mitigations for vulnerable processors are: + + - Enable CPU buffer clearing + + The kernel does not by default enforce the disabling of SMT, which leaves + SMT systems vulnerable when running untrusted code. The same rationale as + for L1TF applies. + See :ref:`Documentation/admin-guide/hw-vuln//l1tf.rst `. diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt index 9afcb240a673..7325319c2c23 100644 --- a/Documentation/admin-guide/kernel-parameters.txt +++ b/Documentation/admin-guide/kernel-parameters.txt @@ -2378,6 +2378,8 @@ Not specifying this option is equivalent to mds=full. + For details see: Documentation/admin-guide/hw-vuln/mds.rst + mem=nn[KMG] [KNL,BOOT] Force usage of a specific amount of memory Amount of memory to be used when the kernel is not able to see the whole system memory or for test. -- cgit v1.2.3 From fa225400758dfc7ccddebf4d990f991a435f7921 Mon Sep 17 00:00:00 2001 From: Luca Ceresoli Date: Thu, 7 Mar 2019 22:44:56 +0100 Subject: ASoC: axi-i2s: make both "rx" and "tx" optional Both the capture and playback channels are optional in the axi_i2s IP block. Document how to tell the driver which channels are instantiated. Signed-off-by: Luca Ceresoli Signed-off-by: Mark Brown --- Documentation/devicetree/bindings/sound/adi,axi-i2s.txt | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/sound/adi,axi-i2s.txt b/Documentation/devicetree/bindings/sound/adi,axi-i2s.txt index 4248b662deff..229ad1392cdc 100644 --- a/Documentation/devicetree/bindings/sound/adi,axi-i2s.txt +++ b/Documentation/devicetree/bindings/sound/adi,axi-i2s.txt @@ -1,5 +1,8 @@ ADI AXI-I2S controller +The core can be generated with transmit (playback), only receive +(capture) or both directions enabled. + Required properties: - compatible : Must be "adi,axi-i2s-1.00.a" - reg : Must contain I2S core's registers location and length @@ -9,8 +12,8 @@ Required properties: - clock-names : "axi" for the clock to the AXI interface, "ref" for the sample rate reference clock. - dmas: Pairs of phandle and specifier for the DMA channels that are used by - the core. The core expects two dma channels, one for transmit and one for - receive. + the core. The core expects two dma channels if both transmit and receive are + enabled, one channel otherwise. - dma-names : "tx" for the transmit channel, "rx" for the receive channel. For more details on the 'dma', 'dma-names', 'clock' and 'clock-names' properties -- cgit v1.2.3 From 876d8a25bdd5a2f5bd18a86e05eaca13d6964c50 Mon Sep 17 00:00:00 2001 From: Jagan Teki Date: Wed, 6 Mar 2019 22:31:09 +0530 Subject: dt-bindings: Add vendor prefix for oceanic Add oceanic vendor prefix. Oceanic Systems (UK) Ltd design and manufacture world-class marine systems for control and monitoring vessels. Signed-off-by: Jagan Teki Signed-off-by: Maxime Ripard --- Documentation/devicetree/bindings/vendor-prefixes.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/vendor-prefixes.txt b/Documentation/devicetree/bindings/vendor-prefixes.txt index 8162b0eb4b50..208889476a38 100644 --- a/Documentation/devicetree/bindings/vendor-prefixes.txt +++ b/Documentation/devicetree/bindings/vendor-prefixes.txt @@ -287,6 +287,7 @@ nuvoton Nuvoton Technology Corporation nvd New Vision Display nvidia NVIDIA nxp NXP Semiconductors +oceanic Oceanic Systems (UK) Ltd. okaya Okaya Electric America, Inc. oki Oki Electric Industry Co., Ltd. olimex OLIMEX Ltd. -- cgit v1.2.3 From 08b64bd2c681ab8bd67fbf1d34d092d1bb72ede4 Mon Sep 17 00:00:00 2001 From: Alexis Ballier Date: Fri, 22 Feb 2019 19:44:19 +0100 Subject: arm64: dts: rockchip: Add support for the Orange Pi RK3399 board. This adds basic support for the Orange Pi RK3399 board. What works: - SD card / emmc. - Debug UART - Ethernet - USB: Type C, internal USB3 for SATA, 4 USB 2.0 ports - Sensors: All of them but the Hall sensor. - Buttons - Wifi, Bluetooth - HDMI out Signed-off-by: Alexis Ballier Reviewed-by: Rob Herring Signed-off-by: Heiko Stuebner --- .../devicetree/bindings/arm/rockchip.yaml | 5 + arch/arm64/boot/dts/rockchip/Makefile | 1 + arch/arm64/boot/dts/rockchip/rk3399-orangepi.dts | 771 +++++++++++++++++++++ 3 files changed, 777 insertions(+) create mode 100644 arch/arm64/boot/dts/rockchip/rk3399-orangepi.dts (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/rockchip.yaml b/Documentation/devicetree/bindings/arm/rockchip.yaml index 061a03edf9c8..64b74b12dfea 100644 --- a/Documentation/devicetree/bindings/arm/rockchip.yaml +++ b/Documentation/devicetree/bindings/arm/rockchip.yaml @@ -308,6 +308,11 @@ properties: - const: netxeon,r89 - const: rockchip,rk3288 + - description: Orange Pi RK3399 board + items: + - const: rockchip,rk3399-orangepi + - const: rockchip,rk3399 + - description: Phytec phyCORE-RK3288 Rapid Development Kit items: - const: phytec,rk3288-pcm-947 diff --git a/arch/arm64/boot/dts/rockchip/Makefile b/arch/arm64/boot/dts/rockchip/Makefile index 1b28fa72ea0b..25454e2cf2de 100644 --- a/arch/arm64/boot/dts/rockchip/Makefile +++ b/arch/arm64/boot/dts/rockchip/Makefile @@ -18,6 +18,7 @@ dtb-$(CONFIG_ARCH_ROCKCHIP) += rk3399-gru-scarlet-inx.dtb dtb-$(CONFIG_ARCH_ROCKCHIP) += rk3399-gru-scarlet-kd.dtb dtb-$(CONFIG_ARCH_ROCKCHIP) += rk3399-nanopc-t4.dtb dtb-$(CONFIG_ARCH_ROCKCHIP) += rk3399-nanopi-m4.dtb +dtb-$(CONFIG_ARCH_ROCKCHIP) += rk3399-orangepi.dtb dtb-$(CONFIG_ARCH_ROCKCHIP) += rk3399-puma-haikou.dtb dtb-$(CONFIG_ARCH_ROCKCHIP) += rk3399-roc-pc.dtb dtb-$(CONFIG_ARCH_ROCKCHIP) += rk3399-rock-pi-4.dtb diff --git a/arch/arm64/boot/dts/rockchip/rk3399-orangepi.dts b/arch/arm64/boot/dts/rockchip/rk3399-orangepi.dts new file mode 100644 index 000000000000..cf37b96a6b77 --- /dev/null +++ b/arch/arm64/boot/dts/rockchip/rk3399-orangepi.dts @@ -0,0 +1,771 @@ +// SPDX-License-Identifier: (GPL-2.0+ OR MIT) +/* + * Copyright (c) 2017 Fuzhou Rockchip Electronics Co., Ltd. + */ + +/dts-v1/; + +#include "dt-bindings/pwm/pwm.h" +#include "dt-bindings/input/input.h" +#include "rk3399.dtsi" +#include "rk3399-opp.dtsi" + +/ { + model = "Orange Pi RK3399 Board"; + compatible = "rockchip,rk3399-orangepi", "rockchip,rk3399"; + + chosen { + stdout-path = "serial2:1500000n8"; + }; + + clkin_gmac: external-gmac-clock { + compatible = "fixed-clock"; + clock-frequency = <125000000>; + clock-output-names = "clkin_gmac"; + #clock-cells = <0>; + }; + + adc-keys { + compatible = "adc-keys"; + io-channels = <&saradc 1>; + io-channel-names = "buttons"; + keyup-threshold-microvolt = <1800000>; + poll-interval = <100>; + + button-up { + label = "Volume Up"; + linux,code = ; + press-threshold-microvolt = <100000>; + }; + + button-down { + label = "Volume Down"; + linux,code = ; + press-threshold-microvolt = <300000>; + }; + + back { + label = "Back"; + linux,code = ; + press-threshold-microvolt = <985000>; + }; + + menu { + label = "Menu"; + linux,code = ; + press-threshold-microvolt = <1314000>; + }; + }; + + dc_12v: dc-12v { + compatible = "regulator-fixed"; + regulator-name = "dc_12v"; + regulator-always-on; + regulator-boot-on; + regulator-min-microvolt = <12000000>; + regulator-max-microvolt = <12000000>; + }; + + keys: gpio-keys { + compatible = "gpio-keys"; + autorepeat; + + power { + debounce-interval = <100>; + gpios = <&gpio0 RK_PA5 GPIO_ACTIVE_LOW>; + label = "GPIO Power"; + linux,code = ; + linux,input-type = <1>; + pinctrl-names = "default"; + pinctrl-0 = <&pwr_btn>; + wakeup-source; + }; + }; + + sdio_pwrseq: sdio-pwrseq { + compatible = "mmc-pwrseq-simple"; + clocks = <&rk808 1>; + clock-names = "ext_clock"; + pinctrl-names = "default"; + pinctrl-0 = <&wifi_reg_on_h>; + reset-gpios = <&gpio0 RK_PB2 GPIO_ACTIVE_LOW>; + }; + + /* switched by pmic_sleep */ + vcc1v8_s3: vcca1v8_s3: vcc1v8-s3 { + compatible = "regulator-fixed"; + regulator-name = "vcc1v8_s3"; + regulator-always-on; + regulator-boot-on; + regulator-min-microvolt = <1800000>; + regulator-max-microvolt = <1800000>; + vin-supply = <&vcc_1v8>; + }; + + vcc3v0_sd: vcc3v0-sd { + compatible = "regulator-fixed"; + enable-active-high; + gpio = <&gpio0 RK_PA1 GPIO_ACTIVE_HIGH>; + pinctrl-names = "default"; + pinctrl-0 = <&sdmmc0_pwr_h>; + regulator-boot-on; + regulator-max-microvolt = <3000000>; + regulator-min-microvolt = <3000000>; + regulator-name = "vcc3v0_sd"; + vin-supply = <&vcc3v3_sys>; + }; + + vcc3v3_sys: vcc3v3-sys { + compatible = "regulator-fixed"; + regulator-name = "vcc3v3_sys"; + regulator-always-on; + regulator-boot-on; + regulator-min-microvolt = <3300000>; + regulator-max-microvolt = <3300000>; + vin-supply = <&vcc_sys>; + }; + + vcc5v0_host: vcc5v0-host-regulator { + compatible = "regulator-fixed"; + enable-active-high; + gpio = <&gpio4 RK_PD1 GPIO_ACTIVE_HIGH>; + pinctrl-names = "default"; + pinctrl-0 = <&vcc5v0_host_en>; + regulator-name = "vcc5v0_host"; + regulator-always-on; + vin-supply = <&vcc_sys>; + }; + + vcc5v0_typec0: vcc5v0-typec0-regulator { + compatible = "regulator-fixed"; + enable-active-high; + gpio = <&gpio1 RK_PA3 GPIO_ACTIVE_HIGH>; + pinctrl-names = "default"; + pinctrl-0 = <&vcc5v0_typec0_en>; + regulator-name = "vcc5v0_typec0"; + vin-supply = <&vcc_sys>; + }; + + vcc_sys: vcc-sys { + compatible = "regulator-fixed"; + regulator-name = "vcc_sys"; + regulator-always-on; + regulator-boot-on; + regulator-min-microvolt = <5000000>; + regulator-max-microvolt = <5000000>; + vin-supply = <&dc_12v>; + }; + + vdd_log: vdd-log { + compatible = "pwm-regulator"; + pwms = <&pwm2 0 25000 1>; + regulator-name = "vdd_log"; + regulator-always-on; + regulator-boot-on; + regulator-min-microvolt = <800000>; + regulator-max-microvolt = <1400000>; + vin-supply = <&vcc_sys>; + }; +}; + +&cpu_l0 { + cpu-supply = <&vdd_cpu_l>; +}; + +&cpu_l1 { + cpu-supply = <&vdd_cpu_l>; +}; + +&cpu_l2 { + cpu-supply = <&vdd_cpu_l>; +}; + +&cpu_l3 { + cpu-supply = <&vdd_cpu_l>; +}; + +&cpu_b0 { + cpu-supply = <&vdd_cpu_b>; +}; + +&cpu_b1 { + cpu-supply = <&vdd_cpu_b>; +}; + +&emmc_phy { + status = "okay"; +}; + +&gmac { + assigned-clocks = <&cru SCLK_RMII_SRC>; + assigned-clock-parents = <&clkin_gmac>; + clock_in_out = "input"; + phy-supply = <&vcc3v3_s3>; + phy-mode = "rgmii"; + pinctrl-names = "default"; + pinctrl-0 = <&rgmii_pins>; + snps,reset-gpio = <&gpio3 RK_PB7 GPIO_ACTIVE_LOW>; + snps,reset-active-low; + snps,reset-delays-us = <0 10000 50000>; + tx_delay = <0x28>; + rx_delay = <0x11>; + status = "okay"; +}; + +&gpu { + mali-supply = <&vdd_gpu>; + status = "okay"; +}; + +&hdmi { + ddc-i2c-bus = <&i2c3>; + status = "okay"; +}; + +&hdmi_sound { + status = "okay"; +}; + +&i2c0 { + clock-frequency = <400000>; + i2c-scl-rising-time-ns = <168>; + i2c-scl-falling-time-ns = <4>; + status = "okay"; + + rk808: pmic@1b { + compatible = "rockchip,rk808"; + reg = <0x1b>; + interrupt-parent = <&gpio1>; + interrupts = <21 IRQ_TYPE_LEVEL_LOW>; + #clock-cells = <1>; + clock-output-names = "rtc_clko_soc", "rtc_clko_wifi"; + pinctrl-names = "default"; + pinctrl-0 = <&pmic_int_l>; + rockchip,system-power-controller; + wakeup-source; + + vcc1-supply = <&vcc3v3_sys>; + vcc2-supply = <&vcc3v3_sys>; + vcc3-supply = <&vcc3v3_sys>; + vcc4-supply = <&vcc3v3_sys>; + vcc6-supply = <&vcc3v3_sys>; + vcc7-supply = <&vcc3v3_sys>; + vcc8-supply = <&vcc3v3_sys>; + vcc9-supply = <&vcc3v3_sys>; + vcc10-supply = <&vcc3v3_sys>; + vcc11-supply = <&vcc3v3_sys>; + vcc12-supply = <&vcc3v3_sys>; + vddio-supply = <&vcc_3v0>; + + regulators { + vdd_center: DCDC_REG1 { + regulator-name = "vdd_center"; + regulator-always-on; + regulator-boot-on; + regulator-min-microvolt = <700000>; + regulator-max-microvolt = <1500000>; + regulator-ramp-delay = <6001>; + regulator-state-mem { + regulator-off-in-suspend; + }; + }; + + vdd_cpu_l: DCDC_REG2 { + regulator-name = "vdd_cpu_l"; + regulator-always-on; + regulator-boot-on; + regulator-min-microvolt = <700000>; + regulator-max-microvolt = <1500000>; + regulator-ramp-delay = <6001>; + regulator-state-mem { + regulator-off-in-suspend; + }; + }; + + vcc_ddr: DCDC_REG3 { + regulator-name = "vcc_ddr"; + regulator-always-on; + regulator-boot-on; + regulator-state-mem { + regulator-on-in-suspend; + }; + }; + + vcc_1v8: DCDC_REG4 { + regulator-name = "vcc_1v8"; + regulator-always-on; + regulator-boot-on; + regulator-min-microvolt = <1800000>; + regulator-max-microvolt = <3300000>; + regulator-state-mem { + regulator-on-in-suspend; + regulator-suspend-microvolt = <1800000>; + }; + }; + + vcc1v8_dvp: LDO_REG1 { + regulator-name = "vcc1v8_dvp"; + regulator-always-on; + regulator-boot-on; + regulator-min-microvolt = <1800000>; + regulator-max-microvolt = <3400000>; + regulator-state-mem { + regulator-off-in-suspend; + }; + }; + + vcc3v0_tp: LDO_REG2 { + regulator-name = "vcc3v0_tp"; + regulator-always-on; + regulator-boot-on; + regulator-min-microvolt = <1800000>; + regulator-max-microvolt = <3400000>; + regulator-state-mem { + regulator-off-in-suspend; + }; + }; + + vcc1v8_pmupll: LDO_REG3 { + regulator-name = "vcc1v8_pmupll"; + regulator-always-on; + regulator-boot-on; + regulator-min-microvolt = <800000>; + regulator-max-microvolt = <2500000>; + regulator-state-mem { + regulator-on-in-suspend; + regulator-suspend-microvolt = <1800000>; + }; + }; + + vcc_sdio: LDO_REG4 { + regulator-name = "vcc_sdio"; + regulator-always-on; + regulator-boot-on; + regulator-min-microvolt = <1800000>; + regulator-max-microvolt = <3400000>; + regulator-state-mem { + regulator-on-in-suspend; + regulator-suspend-microvolt = <3000000>; + }; + }; + + vcca3v0_codec: LDO_REG5 { + regulator-name = "vcca3v0_codec"; + regulator-always-on; + regulator-boot-on; + regulator-min-microvolt = <1800000>; + regulator-max-microvolt = <3400000>; + regulator-state-mem { + regulator-off-in-suspend; + }; + }; + + vcc_1v5: LDO_REG6 { + regulator-name = "vcc_1v5"; + regulator-always-on; + regulator-boot-on; + regulator-min-microvolt = <800000>; + regulator-max-microvolt = <2500000>; + regulator-state-mem { + regulator-on-in-suspend; + regulator-suspend-microvolt = <1500000>; + }; + }; + + vcca1v8_codec: LDO_REG7 { + regulator-name = "vcca1v8_codec"; + regulator-always-on; + regulator-boot-on; + regulator-min-microvolt = <800000>; + regulator-max-microvolt = <2500000>; + regulator-state-mem { + regulator-off-in-suspend; + }; + }; + + vcc_3v0: LDO_REG8 { + regulator-name = "vcc_3v0"; + regulator-always-on; + regulator-boot-on; + regulator-min-microvolt = <1800000>; + regulator-max-microvolt = <3400000>; + regulator-state-mem { + regulator-on-in-suspend; + regulator-suspend-microvolt = <3000000>; + }; + }; + + vcc3v3_s3: SWITCH_REG1 { + regulator-name = "vcc3v3_s3"; + regulator-always-on; + regulator-boot-on; + regulator-state-mem { + regulator-off-in-suspend; + }; + }; + + vcc3v3_s0: SWITCH_REG2 { + regulator-name = "vcc3v3_s0"; + regulator-always-on; + regulator-boot-on; + regulator-state-mem { + regulator-off-in-suspend; + }; + }; + }; + }; + + vdd_cpu_b: regulator@40 { + compatible = "silergy,syr827"; + reg = <0x40>; + fcs,suspend-voltage-selector = <1>; + regulator-name = "vdd_cpu_b"; + regulator-min-microvolt = <712500>; + regulator-max-microvolt = <1500000>; + regulator-ramp-delay = <1000>; + regulator-always-on; + regulator-boot-on; + vin-supply = <&vcc3v3_sys>; + + regulator-state-mem { + regulator-off-in-suspend; + }; + }; + + vdd_gpu: regulator@41 { + compatible = "silergy,syr828"; + reg = <0x41>; + fcs,suspend-voltage-selector = <1>; + regulator-name = "vdd_gpu"; + regulator-min-microvolt = <712500>; + regulator-max-microvolt = <1500000>; + regulator-ramp-delay = <1000>; + regulator-always-on; + regulator-boot-on; + vin-supply = <&vcc3v3_sys>; + + regulator-state-mem { + regulator-off-in-suspend; + }; + }; +}; + +&i2c1 { + i2c-scl-rising-time-ns = <450>; + i2c-scl-falling-time-ns = <15>; + status = "okay"; +}; + +&i2c3 { + i2c-scl-rising-time-ns = <450>; + i2c-scl-falling-time-ns = <15>; + status = "okay"; +}; + +&i2c4 { + clock-frequency = <400000>; + i2c-scl-rising-time-ns = <450>; + i2c-scl-falling-time-ns = <15>; + status = "okay"; + + ak09911@c { + compatible = "asahi-kasei,ak09911"; + reg = <0x0c>; + vdd-supply = <&vcc3v3_s3>; + }; + + mpu6500@68 { + compatible = "invensense,mpu6500"; + reg = <0x68>; + interrupt-parent = <&gpio1>; + interrupts = ; + pinctrl-names = "default"; + pinctrl-0 = <&gsensor_int_l>; + vddio-supply = <&vcc3v3_s3>; + }; + + lsm6ds3@6a { + compatible = "st,lsm6ds3"; + reg = <0x6a>; + interrupt-parent = <&gpio1>; + interrupts = ; + pinctrl-names = "default"; + pinctrl-0 = <&gyr_int_l>; + vdd-supply = <&vcc3v3_s3>; + vddio-supply = <&vcc3v3_s3>; + }; + + cm32181@10 { + compatible = "capella,cm32181"; + reg = <0x10>; + interrupt-parent = <&gpio4>; + interrupts = ; + pinctrl-names = "default"; + pinctrl-0 = <&light_int_l>; + vdd-supply = <&vcc3v3_s3>; + }; +}; + +&io_domains { + status = "okay"; + bt656-supply = <&vcc_3v0>; + audio-supply = <&vcca1v8_codec>; + sdmmc-supply = <&vcc_sdio>; + gpio1830-supply = <&vcc_3v0>; +}; + +&pmu_io_domains { + status = "okay"; + pmu1830-supply = <&vcc_3v0>; +}; + +&pinctrl { + buttons { + pwr_btn: pwr-btn { + rockchip,pins = <0 RK_PA5 RK_FUNC_GPIO &pcfg_pull_up>; + }; + }; + + pmic { + pmic_int_l: pmic-int-l { + rockchip,pins = + <1 RK_PC5 RK_FUNC_GPIO &pcfg_pull_up>; + }; + }; + + sd { + sdmmc0_pwr_h: sdmmc0-pwr-h { + rockchip,pins = + ; + }; + }; + + usb2 { + vcc5v0_host_en: vcc5v0-host-en { + rockchip,pins = + <4 RK_PD1 RK_FUNC_GPIO &pcfg_pull_none>; + }; + + vcc5v0_typec0_en: vcc5v0-typec0-en { + rockchip,pins = + <1 RK_PA3 RK_FUNC_GPIO &pcfg_pull_none>; + }; + }; + + sdio-pwrseq { + wifi_reg_on_h: wifi-reg-on-h { + rockchip,pins = <0 RK_PB2 RK_FUNC_GPIO &pcfg_pull_none>; + }; + }; + + wifi { + wifi_host_wake_l: wifi-host-wake-l { + rockchip,pins = <0 RK_PA3 RK_FUNC_GPIO &pcfg_pull_none>; + }; + }; + + bluetooth { + bt_reg_on_h: bt-enable-h { + rockchip,pins = <0 RK_PB1 RK_FUNC_GPIO &pcfg_pull_none>; + }; + + bt_host_wake_l: bt-host-wake-l { + rockchip,pins = <0 RK_PA4 RK_FUNC_GPIO &pcfg_pull_none>; + }; + + bt_wake_l: bt-wake-l { + rockchip,pins = <2 RK_PD2 RK_FUNC_GPIO &pcfg_pull_none>; + }; + }; + + mpu6500 { + gsensor_int_l: gsensor-int-l { + rockchip,pins = <1 RK_PC6 RK_FUNC_GPIO &pcfg_pull_none>; + }; + }; + + lsm6ds3 { + gyr_int_l: gyr-int-l { + rockchip,pins = <1 RK_PD0 RK_FUNC_GPIO &pcfg_pull_none>; + }; + }; + + cm32181 { + light_int_l: light-int-l { + rockchip,pins = <4 RK_PD0 RK_FUNC_GPIO &pcfg_pull_none>; + }; + }; +}; + +&pwm0 { + status = "okay"; +}; + +&pwm2 { + status = "okay"; +}; + +&saradc { + vref-supply = <&vcca1v8_s3>; + status = "okay"; +}; + +&sdhci { + bus-width = <8>; + mmc-hs400-1_8v; + mmc-hs400-enhanced-strobe; + non-removable; + status = "okay"; +}; + +&sdio0 { + bus-width = <4>; + cap-sd-highspeed; + cap-sdio-irq; + clock-frequency = <50000000>; + disable-wp; + keep-power-in-suspend; + max-frequency = <50000000>; + mmc-pwrseq = <&sdio_pwrseq>; + non-removable; + pinctrl-names = "default"; + pinctrl-0 = <&sdio0_bus4 &sdio0_cmd &sdio0_clk>; + sd-uhs-sdr104; + status = "okay"; + + brcmf: wifi@1 { + compatible = "brcm,bcm4329-fmac"; + interrupt-parent = <&gpio0>; + interrupts = ; + interrupt-names = "host-wake"; + pinctrl-names = "default"; + pinctrl-0 = <&wifi_host_wake_l>; + }; +}; + +&sdmmc { + bus-width = <4>; + cap-mmc-highspeed; + cap-sd-highspeed; + cd-gpios = <&gpio0 RK_PA7 GPIO_ACTIVE_LOW>; + clock-frequency = <150000000>; + disable-wp; + max-frequency = <150000000>; + pinctrl-names = "default"; + pinctrl-0 = <&sdmmc_clk &sdmmc_cmd &sdmmc_cd &sdmmc_bus4>; + vmmc-supply = <&vcc3v0_sd>; + vqmmc-supply = <&vcc_sdio>; + status = "okay"; +}; + +&tcphy0 { + status = "okay"; +}; + +&tcphy1 { + status = "okay"; +}; + +&tsadc { + rockchip,hw-tshut-mode = <1>; + rockchip,hw-tshut-polarity = <1>; + status = "okay"; +}; + +&u2phy0 { + status = "okay"; + + u2phy0_otg: otg-port { + phy-supply = <&vcc5v0_typec0>; + status = "okay"; + }; + + u2phy0_host: host-port { + phy-supply = <&vcc5v0_host>; + status = "okay"; + }; +}; + +&u2phy1 { + status = "okay"; + + u2phy1_otg: otg-port { + status = "okay"; + }; + + u2phy1_host: host-port { + phy-supply = <&vcc5v0_host>; + status = "okay"; + }; +}; + +&uart0 { + pinctrl-names = "default"; + pinctrl-0 = <&uart0_xfer &uart0_cts &uart0_rts>; + status = "okay"; + + bluetooth { + compatible = "brcm,bcm43438-bt"; + clocks = <&rk808 1>; + clock-names = "ext_clock"; + device-wakeup-gpios = <&gpio2 RK_PD2 GPIO_ACTIVE_HIGH>; + host-wakeup-gpios = <&gpio0 RK_PA4 GPIO_ACTIVE_HIGH>; + shutdown-gpios = <&gpio0 RK_PB1 GPIO_ACTIVE_HIGH>; + pinctrl-names = "default"; + pinctrl-0 = <&bt_host_wake_l &bt_wake_l &bt_reg_on_h>; + }; +}; + +&uart2 { + status = "okay"; +}; + +&usb_host0_ehci { + status = "okay"; +}; + +&usb_host0_ohci { + status = "okay"; +}; + +&usb_host1_ehci { + status = "okay"; +}; + +&usb_host1_ohci { + status = "okay"; +}; + +&usbdrd3_0 { + status = "okay"; +}; + +&usbdrd_dwc3_0 { + status = "okay"; + dr_mode = "otg"; +}; + +&usbdrd3_1 { + status = "okay"; +}; + +&usbdrd_dwc3_1 { + status = "okay"; + dr_mode = "host"; +}; + +&vopb { + status = "okay"; +}; + +&vopb_mmu { + status = "okay"; +}; + +&vopl { + status = "okay"; +}; + +&vopl_mmu { + status = "okay"; +}; -- cgit v1.2.3 From 092470b537f19788d957aed12d835a179b606014 Mon Sep 17 00:00:00 2001 From: Jagan Teki Date: Fri, 8 Mar 2019 23:42:02 +0530 Subject: arm64: dts: rockchip: Add Nanopi NEO4 initial support FriendlyElec NanoPi NEO4 is known to be a revision 4 based NanoPi4 series of boards. Most of know peripherals are shared between Nanopi M4 vs NEO4, except - 1GB DDR3 - USB Host ports - Missing DSI port - USB 2.0 Host with USB2PHY0 (no USB2PH1) Add support for it, by reusing existing rk3399-nanopi4.dtsi Signed-off-by: Jagan Teki Signed-off-by: Akash Gajjar Reviewed-by: Rob Herring Signed-off-by: Heiko Stuebner --- .../devicetree/bindings/arm/rockchip.yaml | 1 + arch/arm64/boot/dts/rockchip/Makefile | 1 + .../arm64/boot/dts/rockchip/rk3399-nanopi-neo4.dts | 50 ++++++++++++++++++++++ 3 files changed, 52 insertions(+) create mode 100644 arch/arm64/boot/dts/rockchip/rk3399-nanopi-neo4.dts (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/rockchip.yaml b/Documentation/devicetree/bindings/arm/rockchip.yaml index 64b74b12dfea..0161b4a66586 100644 --- a/Documentation/devicetree/bindings/arm/rockchip.yaml +++ b/Documentation/devicetree/bindings/arm/rockchip.yaml @@ -97,6 +97,7 @@ properties: - enum: - friendlyarm,nanopc-t4 - friendlyarm,nanopi-m4 + - friendlyarm,nanopi-neo4 - const: rockchip,rk3399 - description: GeekBuying GeekBox diff --git a/arch/arm64/boot/dts/rockchip/Makefile b/arch/arm64/boot/dts/rockchip/Makefile index 25454e2cf2de..5f2687acbf94 100644 --- a/arch/arm64/boot/dts/rockchip/Makefile +++ b/arch/arm64/boot/dts/rockchip/Makefile @@ -18,6 +18,7 @@ dtb-$(CONFIG_ARCH_ROCKCHIP) += rk3399-gru-scarlet-inx.dtb dtb-$(CONFIG_ARCH_ROCKCHIP) += rk3399-gru-scarlet-kd.dtb dtb-$(CONFIG_ARCH_ROCKCHIP) += rk3399-nanopc-t4.dtb dtb-$(CONFIG_ARCH_ROCKCHIP) += rk3399-nanopi-m4.dtb +dtb-$(CONFIG_ARCH_ROCKCHIP) += rk3399-nanopi-neo4.dtb dtb-$(CONFIG_ARCH_ROCKCHIP) += rk3399-orangepi.dtb dtb-$(CONFIG_ARCH_ROCKCHIP) += rk3399-puma-haikou.dtb dtb-$(CONFIG_ARCH_ROCKCHIP) += rk3399-roc-pc.dtb diff --git a/arch/arm64/boot/dts/rockchip/rk3399-nanopi-neo4.dts b/arch/arm64/boot/dts/rockchip/rk3399-nanopi-neo4.dts new file mode 100644 index 000000000000..195410b089b9 --- /dev/null +++ b/arch/arm64/boot/dts/rockchip/rk3399-nanopi-neo4.dts @@ -0,0 +1,50 @@ +// SPDX-License-Identifier: (GPL-2.0+ OR MIT) +/* + * Copyright (C) 2019 Amarula Solutions B.V. + * Author: Jagan Teki + */ + +/dts-v1/; + +#include "rk3399-nanopi4.dtsi" + +/ { + model = "FriendlyARM NanoPi NEO4"; + compatible = "friendlyarm,nanopi-neo4", "rockchip,rk3399"; + + vdd_5v: vdd-5v { + compatible = "regulator-fixed"; + regulator-name = "vdd_5v"; + regulator-always-on; + regulator-boot-on; + }; + + vcc5v0_core: vcc5v0-core { + compatible = "regulator-fixed"; + regulator-name = "vcc5v0_core"; + regulator-always-on; + regulator-boot-on; + vin-supply = <&vdd_5v>; + }; + + vcc5v0_usb1: vcc5v0-usb1 { + compatible = "regulator-fixed"; + regulator-name = "vcc5v0_usb1"; + regulator-always-on; + regulator-boot-on; + vin-supply = <&vcc5v0_sys>; + }; +}; + +&vcc3v3_sys { + vin-supply = <&vcc5v0_core>; +}; + +&u2phy0_host { + phy-supply = <&vcc5v0_usb1>; +}; + +&vbus_typec { + regulator-always-on; + vin-supply = <&vdd_5v>; +}; -- cgit v1.2.3 From 295768f6207e412e145487c87993481774c55411 Mon Sep 17 00:00:00 2001 From: Biju Das Date: Wed, 16 Jan 2019 18:37:44 +0000 Subject: dt-bindings: Add vendor prefix for Silicon Linux. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Add Silicon Linux to the list of devicetree vendor prefixes. Website: http://www.si-linux.co.jp Signed-off-by: Biju Das Signed-off-by: Fabrizio Castro Reviewed-by: Chris Paterson Reviewed-by: Andreas Färber Reviewed-by: Rob Herring Signed-off-by: Simon Horman --- Documentation/devicetree/bindings/vendor-prefixes.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/vendor-prefixes.txt b/Documentation/devicetree/bindings/vendor-prefixes.txt index 8162b0eb4b50..6bca0c96c3b4 100644 --- a/Documentation/devicetree/bindings/vendor-prefixes.txt +++ b/Documentation/devicetree/bindings/vendor-prefixes.txt @@ -361,6 +361,7 @@ sgx SGX Sensortech sharp Sharp Corporation shimafuji Shimafuji Electric, Inc. si-en Si-En Technology Ltd. +si-linux Silicon Linux Corporation sifive SiFive, Inc. sigma Sigma Designs, Inc. sii Seiko Instruments, Inc. -- cgit v1.2.3 From 14c747506ae65005ab024f2247e68b8e045f210a Mon Sep 17 00:00:00 2001 From: Kuninori Morimoto Date: Mon, 18 Mar 2019 14:11:27 +0900 Subject: ASoC: rsnd: add missing reg/reg-name at Document reg is missing "Audio DMAC peri peri" part, and reg-name itself is missing at Document. This patch add these. Reported-by: Geert Uytterhoeven Signed-off-by: Kuninori Morimoto Reviewed-by: Simon Horman Signed-off-by: Mark Brown --- Documentation/devicetree/bindings/sound/renesas,rsnd.txt | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/sound/renesas,rsnd.txt b/Documentation/devicetree/bindings/sound/renesas,rsnd.txt index 648d43e1b1e9..c58af457a831 100644 --- a/Documentation/devicetree/bindings/sound/renesas,rsnd.txt +++ b/Documentation/devicetree/bindings/sound/renesas,rsnd.txt @@ -282,7 +282,10 @@ Required properties: - reg : Should contain the register physical address. required register is SRU/ADG/SSI if generation1 - SRU/ADG/SSIU/SSI if generation2 + SRU/ADG/SSIU/SSI/AUDIO-DMAC-periperi if generation2/generation3 +- reg-names : Should contain the register names. + scu/adg/ssi if generation1 + scu/adg/ssiu/ssi/audmapp if generation2/generation3 - rcar_sound,ssi : Should contain SSI feature. The number of SSI subnode should be same as HW. see below for detail. -- cgit v1.2.3 From c4bce31c4982ddb866b6b6d0f7ca1cf039a3aded Mon Sep 17 00:00:00 2001 From: Kuninori Morimoto Date: Mon, 18 Mar 2019 14:11:34 +0900 Subject: ASoC: rsnd: explain extended Audio DMAC peri peri address If SoC has extended Audio DMAC peri peri address, DT needs to select it. Otherwise, it can select normal Audio DMAC peri peri address. Extended Audio DMAC peri peri address can use BUSIF4-7, normal address can't. Reported-by: Jiada Wang Signed-off-by: Kuninori Morimoto Reviewed-by: Geert Uytterhoeven Reviewed-by: Simon Horman Signed-off-by: Mark Brown --- Documentation/devicetree/bindings/sound/renesas,rsnd.txt | 2 ++ 1 file changed, 2 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/sound/renesas,rsnd.txt b/Documentation/devicetree/bindings/sound/renesas,rsnd.txt index c58af457a831..b34afa66fb00 100644 --- a/Documentation/devicetree/bindings/sound/renesas,rsnd.txt +++ b/Documentation/devicetree/bindings/sound/renesas,rsnd.txt @@ -283,6 +283,8 @@ Required properties: required register is SRU/ADG/SSI if generation1 SRU/ADG/SSIU/SSI/AUDIO-DMAC-periperi if generation2/generation3 + Select extended AUDIO-DMAC-periperi address if SoC has it, + otherwise select normal AUDIO-DMAC-periperi address. - reg-names : Should contain the register names. scu/adg/ssi if generation1 scu/adg/ssiu/ssi/audmapp if generation2/generation3 -- cgit v1.2.3 From 2944d29d7c89573f9aa47083d105ff0243d5a125 Mon Sep 17 00:00:00 2001 From: Mylène Josserand Date: Mon, 18 Mar 2019 11:39:38 +0100 Subject: ASoC: simple-amplifier: Make gpio property optional MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Some amplifier may not have a GPIO to control the power, but instead simply rely on the regulator to power up and down the amplifier. In order to support those setups, let's make the GPIO optional. Signed-off-by: Mylène Josserand Signed-off-by: Maxime Ripard Signed-off-by: Mark Brown --- Documentation/devicetree/bindings/sound/simple-amplifier.txt | 2 +- sound/soc/codecs/simple-amplifier.c | 3 ++- 2 files changed, 3 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/sound/simple-amplifier.txt b/Documentation/devicetree/bindings/sound/simple-amplifier.txt index 7182ac4f1e65..b1b097cc9b68 100644 --- a/Documentation/devicetree/bindings/sound/simple-amplifier.txt +++ b/Documentation/devicetree/bindings/sound/simple-amplifier.txt @@ -2,9 +2,9 @@ Simple Amplifier Audio Driver Required properties: - compatible : "dioo,dio2125" or "simple-audio-amplifier" -- enable-gpios : the gpio connected to the enable pin of the simple amplifier Optional properties: +- enable-gpios : the gpio connected to the enable pin of the simple amplifier - VCC-supply : power supply for the device, as covered in Documentation/devicetree/bindings/regulator/regulator.txt diff --git a/sound/soc/codecs/simple-amplifier.c b/sound/soc/codecs/simple-amplifier.c index c07e8a80b4b7..351aa55c384e 100644 --- a/sound/soc/codecs/simple-amplifier.c +++ b/sound/soc/codecs/simple-amplifier.c @@ -89,7 +89,8 @@ static int simple_amp_probe(struct platform_device *pdev) return -ENOMEM; platform_set_drvdata(pdev, priv); - priv->gpiod_enable = devm_gpiod_get(dev, "enable", GPIOD_OUT_LOW); + priv->gpiod_enable = devm_gpiod_get_optional(dev, "enable", + GPIOD_OUT_LOW); if (IS_ERR(priv->gpiod_enable)) { err = PTR_ERR(priv->gpiod_enable); if (err != -EPROBE_DEFER) -- cgit v1.2.3 From 8a68a509ae6b5d7d18c6bfc88553ca7761029ada Mon Sep 17 00:00:00 2001 From: Hans de Goede Date: Tue, 5 Mar 2019 12:38:59 +0100 Subject: ASoC: rt5651: Add support for active-high jack detect Some boards use a jack-receptacle with a switch which reports the jack-inserted status as active-high, rather then the standard active-low reporting most jacks use. This commit adds support for it. This is activated by a boolean "realtek,jack-detect-not-inverted" device-property. The not-inverted in the device-property name, rather then active-high, was chosen to keep the device-property naming consistent with the rt5640 codec driver. Signed-off-by: Hans de Goede Signed-off-by: Mark Brown --- Documentation/devicetree/bindings/sound/rt5651.txt | 5 +++ sound/soc/codecs/rt5651.c | 47 ++++++++++++++++++---- sound/soc/codecs/rt5651.h | 1 + 3 files changed, 46 insertions(+), 7 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/sound/rt5651.txt b/Documentation/devicetree/bindings/sound/rt5651.txt index a41199a5cd79..56e736a1cba9 100644 --- a/Documentation/devicetree/bindings/sound/rt5651.txt +++ b/Documentation/devicetree/bindings/sound/rt5651.txt @@ -22,6 +22,11 @@ Optional properties: 2: Use JD1_2 pin for jack-detect 3: Use JD2 pin for jack-detect +- realtek,jack-detect-not-inverted + bool. Normal jack-detect switches give an inverted (active-low) signal, + set this bool in the rare case you've a jack-detect switch which is not + inverted. + - realtek,over-current-threshold-microamp u32, micbias over-current detection threshold in µA, valid values are 600, 1500 and 2000µA. diff --git a/sound/soc/codecs/rt5651.c b/sound/soc/codecs/rt5651.c index 29b2d60076b0..cb8252ff31cb 100644 --- a/sound/soc/codecs/rt5651.c +++ b/sound/soc/codecs/rt5651.c @@ -1645,7 +1645,10 @@ static bool rt5651_jack_inserted(struct snd_soc_component *component) break; } - return val == 0; + if (rt5651->jd_active_high) + return val != 0; + else + return val == 0; } /* Jack detect and button-press timings */ @@ -1868,20 +1871,47 @@ static void rt5651_enable_jack_detect(struct snd_soc_component *component, case RT5651_JD1_1: snd_soc_component_update_bits(component, RT5651_JD_CTRL2, RT5651_JD_TRG_SEL_MASK, RT5651_JD_TRG_SEL_JD1_1); - snd_soc_component_update_bits(component, RT5651_IRQ_CTRL1, - RT5651_JD1_1_IRQ_EN, RT5651_JD1_1_IRQ_EN); + /* active-low is normal, set inv flag for active-high */ + if (rt5651->jd_active_high) + snd_soc_component_update_bits(component, + RT5651_IRQ_CTRL1, + RT5651_JD1_1_IRQ_EN | RT5651_JD1_1_INV, + RT5651_JD1_1_IRQ_EN | RT5651_JD1_1_INV); + else + snd_soc_component_update_bits(component, + RT5651_IRQ_CTRL1, + RT5651_JD1_1_IRQ_EN | RT5651_JD1_1_INV, + RT5651_JD1_1_IRQ_EN); break; case RT5651_JD1_2: snd_soc_component_update_bits(component, RT5651_JD_CTRL2, RT5651_JD_TRG_SEL_MASK, RT5651_JD_TRG_SEL_JD1_2); - snd_soc_component_update_bits(component, RT5651_IRQ_CTRL1, - RT5651_JD1_2_IRQ_EN, RT5651_JD1_2_IRQ_EN); + /* active-low is normal, set inv flag for active-high */ + if (rt5651->jd_active_high) + snd_soc_component_update_bits(component, + RT5651_IRQ_CTRL1, + RT5651_JD1_2_IRQ_EN | RT5651_JD1_2_INV, + RT5651_JD1_2_IRQ_EN | RT5651_JD1_2_INV); + else + snd_soc_component_update_bits(component, + RT5651_IRQ_CTRL1, + RT5651_JD1_2_IRQ_EN | RT5651_JD1_2_INV, + RT5651_JD1_2_IRQ_EN); break; case RT5651_JD2: snd_soc_component_update_bits(component, RT5651_JD_CTRL2, RT5651_JD_TRG_SEL_MASK, RT5651_JD_TRG_SEL_JD2); - snd_soc_component_update_bits(component, RT5651_IRQ_CTRL1, - RT5651_JD2_IRQ_EN, RT5651_JD2_IRQ_EN); + /* active-low is normal, set inv flag for active-high */ + if (rt5651->jd_active_high) + snd_soc_component_update_bits(component, + RT5651_IRQ_CTRL1, + RT5651_JD2_IRQ_EN | RT5651_JD2_INV, + RT5651_JD2_IRQ_EN | RT5651_JD2_INV); + else + snd_soc_component_update_bits(component, + RT5651_IRQ_CTRL1, + RT5651_JD2_IRQ_EN | RT5651_JD2_INV, + RT5651_JD2_IRQ_EN); break; default: dev_err(component->dev, "Currently only JD1_1 / JD1_2 / JD2 are supported\n"); @@ -1986,6 +2016,9 @@ static void rt5651_apply_properties(struct snd_soc_component *component) "realtek,jack-detect-source", &val) == 0) rt5651->jd_src = val; + if (device_property_read_bool(component->dev, "realtek,jack-detect-not-inverted")) + rt5651->jd_active_high = true; + /* * Testing on various boards has shown that good defaults for the OVCD * threshold and scale-factor are 2000µA and 0.75. For an effective diff --git a/sound/soc/codecs/rt5651.h b/sound/soc/codecs/rt5651.h index 41fcb8b5eb40..05b0f6f8b95d 100644 --- a/sound/soc/codecs/rt5651.h +++ b/sound/soc/codecs/rt5651.h @@ -2083,6 +2083,7 @@ struct rt5651_priv { int release_count; int poll_count; unsigned int jd_src; + bool jd_active_high; unsigned int ovcd_th; unsigned int ovcd_sf; -- cgit v1.2.3 From addb32866d99068307f8eddb282ebb325d18446f Mon Sep 17 00:00:00 2001 From: Clark Wang Date: Wed, 6 Mar 2019 06:30:36 +0000 Subject: doc: lpspi: Document DT bindings for LPSPI clocks Add introductions of clocks and clock-names strings. Signed-off-by: Clark Wang Signed-off-by: Mark Brown --- Documentation/devicetree/bindings/spi/spi-fsl-lpspi.txt | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/spi/spi-fsl-lpspi.txt b/Documentation/devicetree/bindings/spi/spi-fsl-lpspi.txt index 6cc3c6fe25a3..e71b81a41ac0 100644 --- a/Documentation/devicetree/bindings/spi/spi-fsl-lpspi.txt +++ b/Documentation/devicetree/bindings/spi/spi-fsl-lpspi.txt @@ -7,7 +7,11 @@ Required properties: - reg : address and length of the lpspi master registers - interrupt-parent : core interrupt controller - interrupts : lpspi interrupt -- clocks : lpspi clock specifier +- clocks : lpspi clock specifier. Its number and order need to correspond to the + value in clock-names. +- clock-names : Corresponding to per clock and ipg clock in "clocks" + respectively. In i.MX7ULP, it only has per clk, so use CLK_DUMMY + to fill the "ipg" blank. - spi-slave : spi slave mode support. In slave mode, add this attribute without value. In master mode, remove it. @@ -18,6 +22,8 @@ lpspi2: lpspi@40290000 { reg = <0x40290000 0x10000>; interrupt-parent = <&intc>; interrupts = ; - clocks = <&clks IMX7ULP_CLK_LPSPI2>; + clocks = <&clks IMX7ULP_CLK_LPSPI2>, + <&clks IMX7ULP_CLK_DUMMY>; + clock-names = "per", "ipg"; spi-slave; }; -- cgit v1.2.3 From 31a2d5113e53a308a2b7a124f97db984d223c06f Mon Sep 17 00:00:00 2001 From: Jolly Shah Date: Wed, 27 Feb 2019 12:51:09 -0800 Subject: include: dt-binding: clock: Rename zynqmp header file Rename file name of ZynqMP clk dt-bindings to align with file name of reset and power dt-bindings. Signed-off-by: Rajan Vaja Signed-off-by: Jolly Shah Signed-off-by: Michal Simek --- .../firmware/xilinx/xlnx,zynqmp-firmware.txt | 2 +- include/dt-bindings/clock/xlnx,zynqmp-clk.h | 116 ------------------- include/dt-bindings/clock/xlnx-zynqmp-clk.h | 126 +++++++++++++++++++++ 3 files changed, 127 insertions(+), 117 deletions(-) delete mode 100644 include/dt-bindings/clock/xlnx,zynqmp-clk.h create mode 100644 include/dt-bindings/clock/xlnx-zynqmp-clk.h (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/firmware/xilinx/xlnx,zynqmp-firmware.txt b/Documentation/devicetree/bindings/firmware/xilinx/xlnx,zynqmp-firmware.txt index 614bac55df86..45d259cfc0b2 100644 --- a/Documentation/devicetree/bindings/firmware/xilinx/xlnx,zynqmp-firmware.txt +++ b/Documentation/devicetree/bindings/firmware/xilinx/xlnx,zynqmp-firmware.txt @@ -62,7 +62,7 @@ order to provide an optional (E)MIO clock source: Output clocks are registered based on clock information received from firmware. Output clocks indexes are mentioned in -include/dt-bindings/clock/xlnx,zynqmp-clk.h. +include/dt-bindings/clock/xlnx-zynqmp-clk.h. ------- Example diff --git a/include/dt-bindings/clock/xlnx,zynqmp-clk.h b/include/dt-bindings/clock/xlnx,zynqmp-clk.h deleted file mode 100644 index 4aebe6e2049e..000000000000 --- a/include/dt-bindings/clock/xlnx,zynqmp-clk.h +++ /dev/null @@ -1,116 +0,0 @@ -/* SPDX-License-Identifier: GPL-2.0 */ -/* - * Xilinx Zynq MPSoC Firmware layer - * - * Copyright (C) 2014-2018 Xilinx, Inc. - * - */ - -#ifndef _DT_BINDINGS_CLK_ZYNQMP_H -#define _DT_BINDINGS_CLK_ZYNQMP_H - -#define IOPLL 0 -#define RPLL 1 -#define APLL 2 -#define DPLL 3 -#define VPLL 4 -#define IOPLL_TO_FPD 5 -#define RPLL_TO_FPD 6 -#define APLL_TO_LPD 7 -#define DPLL_TO_LPD 8 -#define VPLL_TO_LPD 9 -#define ACPU 10 -#define ACPU_HALF 11 -#define DBF_FPD 12 -#define DBF_LPD 13 -#define DBG_TRACE 14 -#define DBG_TSTMP 15 -#define DP_VIDEO_REF 16 -#define DP_AUDIO_REF 17 -#define DP_STC_REF 18 -#define GDMA_REF 19 -#define DPDMA_REF 20 -#define DDR_REF 21 -#define SATA_REF 22 -#define PCIE_REF 23 -#define GPU_REF 24 -#define GPU_PP0_REF 25 -#define GPU_PP1_REF 26 -#define TOPSW_MAIN 27 -#define TOPSW_LSBUS 28 -#define GTGREF0_REF 29 -#define LPD_SWITCH 30 -#define LPD_LSBUS 31 -#define USB0_BUS_REF 32 -#define USB1_BUS_REF 33 -#define USB3_DUAL_REF 34 -#define USB0 35 -#define USB1 36 -#define CPU_R5 37 -#define CPU_R5_CORE 38 -#define CSU_SPB 39 -#define CSU_PLL 40 -#define PCAP 41 -#define IOU_SWITCH 42 -#define GEM_TSU_REF 43 -#define GEM_TSU 44 -#define GEM0_REF 45 -#define GEM1_REF 46 -#define GEM2_REF 47 -#define GEM3_REF 48 -#define GEM0_TX 49 -#define GEM1_TX 50 -#define GEM2_TX 51 -#define GEM3_TX 52 -#define QSPI_REF 53 -#define SDIO0_REF 54 -#define SDIO1_REF 55 -#define UART0_REF 56 -#define UART1_REF 57 -#define SPI0_REF 58 -#define SPI1_REF 59 -#define NAND_REF 60 -#define I2C0_REF 61 -#define I2C1_REF 62 -#define CAN0_REF 63 -#define CAN1_REF 64 -#define CAN0 65 -#define CAN1 66 -#define DLL_REF 67 -#define ADMA_REF 68 -#define TIMESTAMP_REF 69 -#define AMS_REF 70 -#define PL0_REF 71 -#define PL1_REF 72 -#define PL2_REF 73 -#define PL3_REF 74 -#define WDT 75 -#define IOPLL_INT 76 -#define IOPLL_PRE_SRC 77 -#define IOPLL_HALF 78 -#define IOPLL_INT_MUX 79 -#define IOPLL_POST_SRC 80 -#define RPLL_INT 81 -#define RPLL_PRE_SRC 82 -#define RPLL_HALF 83 -#define RPLL_INT_MUX 84 -#define RPLL_POST_SRC 85 -#define APLL_INT 86 -#define APLL_PRE_SRC 87 -#define APLL_HALF 88 -#define APLL_INT_MUX 89 -#define APLL_POST_SRC 90 -#define DPLL_INT 91 -#define DPLL_PRE_SRC 92 -#define DPLL_HALF 93 -#define DPLL_INT_MUX 94 -#define DPLL_POST_SRC 95 -#define VPLL_INT 96 -#define VPLL_PRE_SRC 97 -#define VPLL_HALF 98 -#define VPLL_INT_MUX 99 -#define VPLL_POST_SRC 100 -#define CAN0_MIO 101 -#define CAN1_MIO 102 - -#endif diff --git a/include/dt-bindings/clock/xlnx-zynqmp-clk.h b/include/dt-bindings/clock/xlnx-zynqmp-clk.h new file mode 100644 index 000000000000..cdc4c0b9a374 --- /dev/null +++ b/include/dt-bindings/clock/xlnx-zynqmp-clk.h @@ -0,0 +1,126 @@ +/* SPDX-License-Identifier: GPL-2.0 */ +/* + * Xilinx Zynq MPSoC Firmware layer + * + * Copyright (C) 2014-2018 Xilinx, Inc. + * + */ + +#ifndef _DT_BINDINGS_CLK_ZYNQMP_H +#define _DT_BINDINGS_CLK_ZYNQMP_H + +#define IOPLL 0 +#define RPLL 1 +#define APLL 2 +#define DPLL 3 +#define VPLL 4 +#define IOPLL_TO_FPD 5 +#define RPLL_TO_FPD 6 +#define APLL_TO_LPD 7 +#define DPLL_TO_LPD 8 +#define VPLL_TO_LPD 9 +#define ACPU 10 +#define ACPU_HALF 11 +#define DBF_FPD 12 +#define DBF_LPD 13 +#define DBG_TRACE 14 +#define DBG_TSTMP 15 +#define DP_VIDEO_REF 16 +#define DP_AUDIO_REF 17 +#define DP_STC_REF 18 +#define GDMA_REF 19 +#define DPDMA_REF 20 +#define DDR_REF 21 +#define SATA_REF 22 +#define PCIE_REF 23 +#define GPU_REF 24 +#define GPU_PP0_REF 25 +#define GPU_PP1_REF 26 +#define TOPSW_MAIN 27 +#define TOPSW_LSBUS 28 +#define GTGREF0_REF 29 +#define LPD_SWITCH 30 +#define LPD_LSBUS 31 +#define USB0_BUS_REF 32 +#define USB1_BUS_REF 33 +#define USB3_DUAL_REF 34 +#define USB0 35 +#define USB1 36 +#define CPU_R5 37 +#define CPU_R5_CORE 38 +#define CSU_SPB 39 +#define CSU_PLL 40 +#define PCAP 41 +#define IOU_SWITCH 42 +#define GEM_TSU_REF 43 +#define GEM_TSU 44 +#define GEM0_TX 45 +#define GEM1_TX 46 +#define GEM2_TX 47 +#define GEM3_TX 48 +#define GEM0_RX 49 +#define GEM1_RX 50 +#define GEM2_RX 51 +#define GEM3_RX 52 +#define QSPI_REF 53 +#define SDIO0_REF 54 +#define SDIO1_REF 55 +#define UART0_REF 56 +#define UART1_REF 57 +#define SPI0_REF 58 +#define SPI1_REF 59 +#define NAND_REF 60 +#define I2C0_REF 61 +#define I2C1_REF 62 +#define CAN0_REF 63 +#define CAN1_REF 64 +#define CAN0 65 +#define CAN1 66 +#define DLL_REF 67 +#define ADMA_REF 68 +#define TIMESTAMP_REF 69 +#define AMS_REF 70 +#define PL0_REF 71 +#define PL1_REF 72 +#define PL2_REF 73 +#define PL3_REF 74 +#define WDT 75 +#define IOPLL_INT 76 +#define IOPLL_PRE_SRC 77 +#define IOPLL_HALF 78 +#define IOPLL_INT_MUX 79 +#define IOPLL_POST_SRC 80 +#define RPLL_INT 81 +#define RPLL_PRE_SRC 82 +#define RPLL_HALF 83 +#define RPLL_INT_MUX 84 +#define RPLL_POST_SRC 85 +#define APLL_INT 86 +#define APLL_PRE_SRC 87 +#define APLL_HALF 88 +#define APLL_INT_MUX 89 +#define APLL_POST_SRC 90 +#define DPLL_INT 91 +#define DPLL_PRE_SRC 92 +#define DPLL_HALF 93 +#define DPLL_INT_MUX 94 +#define DPLL_POST_SRC 95 +#define VPLL_INT 96 +#define VPLL_PRE_SRC 97 +#define VPLL_HALF 98 +#define VPLL_INT_MUX 99 +#define VPLL_POST_SRC 100 +#define CAN0_MIO 101 +#define CAN1_MIO 102 +#define ACPU_FULL 103 +#define GEM0_REF 104 +#define GEM1_REF 105 +#define GEM2_REF 106 +#define GEM3_REF 107 +#define GEM0_REF_UNG 108 +#define GEM1_REF_UNG 109 +#define GEM2_REF_UNG 110 +#define GEM3_REF_UNG 111 +#define LPD_WDT 112 + +#endif -- cgit v1.2.3 From 437541e74c68c179837b13c59308f1a5c931db33 Mon Sep 17 00:00:00 2001 From: Rajan Vaja Date: Wed, 27 Feb 2019 12:51:10 -0800 Subject: dt-bindings: xilinx: Separate clock binding from firmware doc Clock description is part of firmware doc. Move clock description in separate doc. Signed-off-by: Rajan Vaja Signed-off-by: Jolly Shah Signed-off-by: Michal Simek --- .../devicetree/bindings/clock/xlnx,zynqmp-clk.txt | 63 ++++++++++++++++++++++ .../firmware/xilinx/xlnx,zynqmp-firmware.txt | 54 +------------------ 2 files changed, 64 insertions(+), 53 deletions(-) create mode 100644 Documentation/devicetree/bindings/clock/xlnx,zynqmp-clk.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/clock/xlnx,zynqmp-clk.txt b/Documentation/devicetree/bindings/clock/xlnx,zynqmp-clk.txt new file mode 100644 index 000000000000..391ee1a60bed --- /dev/null +++ b/Documentation/devicetree/bindings/clock/xlnx,zynqmp-clk.txt @@ -0,0 +1,63 @@ +-------------------------------------------------------------------------- +Device Tree Clock bindings for the Zynq Ultrascale+ MPSoC controlled using +Zynq MPSoC firmware interface +-------------------------------------------------------------------------- +The clock controller is a h/w block of Zynq Ultrascale+ MPSoC clock +tree. It reads required input clock frequencies from the devicetree and acts +as clock provider for all clock consumers of PS clocks. + +See clock_bindings.txt for more information on the generic clock bindings. + +Required properties: + - #clock-cells: Must be 1 + - compatible: Must contain: "xlnx,zynqmp-clk" + - clocks: List of clock specifiers which are external input + clocks to the given clock controller. Please refer + the next section to find the input clocks for a + given controller. + - clock-names: List of clock names which are exteral input clocks + to the given clock controller. Please refer to the + clock bindings for more details. + +Input clocks for zynqmp Ultrascale+ clock controller: + +The Zynq UltraScale+ MPSoC has one primary and four alternative reference clock +inputs. These required clock inputs are: + - pss_ref_clk (PS reference clock) + - video_clk (reference clock for video system ) + - pss_alt_ref_clk (alternative PS reference clock) + - aux_ref_clk + - gt_crx_ref_clk (transceiver reference clock) + +The following strings are optional parameters to the 'clock-names' property in +order to provide an optional (E)MIO clock source: + - swdt0_ext_clk + - swdt1_ext_clk + - gem0_emio_clk + - gem1_emio_clk + - gem2_emio_clk + - gem3_emio_clk + - mio_clk_XX # with XX = 00..77 + - mio_clk_50_or_51 #for the mux clock to gem tsu from 50 or 51 + + +Output clocks are registered based on clock information received +from firmware. Output clocks indexes are mentioned in +include/dt-bindings/clock/xlnx-zynqmp-clk.h. + +------- +Example +------- + +firmware { + zynqmp_firmware: zynqmp-firmware { + compatible = "xlnx,zynqmp-firmware"; + method = "smc"; + zynqmp_clk: clock-controller { + #clock-cells = <1>; + compatible = "xlnx,zynqmp-clk"; + clocks = <&pss_ref_clk>, <&video_clk>, <&pss_alt_ref_clk>, <&aux_ref_clk>, <>_crx_ref_clk>; + clock-names = "pss_ref_clk", "video_clk", "pss_alt_ref_clk","aux_ref_clk", "gt_crx_ref_clk"; + }; + }; +}; diff --git a/Documentation/devicetree/bindings/firmware/xilinx/xlnx,zynqmp-firmware.txt b/Documentation/devicetree/bindings/firmware/xilinx/xlnx,zynqmp-firmware.txt index 45d259cfc0b2..a4fe136be2ba 100644 --- a/Documentation/devicetree/bindings/firmware/xilinx/xlnx,zynqmp-firmware.txt +++ b/Documentation/devicetree/bindings/firmware/xilinx/xlnx,zynqmp-firmware.txt @@ -17,53 +17,6 @@ Required properties: - "smc" : SMC #0, following the SMCCC - "hvc" : HVC #0, following the SMCCC --------------------------------------------------------------------------- -Device Tree Clock bindings for the Zynq Ultrascale+ MPSoC controlled using -Zynq MPSoC firmware interface --------------------------------------------------------------------------- -The clock controller is a h/w block of Zynq Ultrascale+ MPSoC clock -tree. It reads required input clock frequencies from the devicetree and acts -as clock provider for all clock consumers of PS clocks. - -See clock_bindings.txt for more information on the generic clock bindings. - -Required properties: - - #clock-cells: Must be 1 - - compatible: Must contain: "xlnx,zynqmp-clk" - - clocks: List of clock specifiers which are external input - clocks to the given clock controller. Please refer - the next section to find the input clocks for a - given controller. - - clock-names: List of clock names which are exteral input clocks - to the given clock controller. Please refer to the - clock bindings for more details. - -Input clocks for zynqmp Ultrascale+ clock controller: - -The Zynq UltraScale+ MPSoC has one primary and four alternative reference clock -inputs. These required clock inputs are: - - pss_ref_clk (PS reference clock) - - video_clk (reference clock for video system ) - - pss_alt_ref_clk (alternative PS reference clock) - - aux_ref_clk - - gt_crx_ref_clk (transceiver reference clock) - -The following strings are optional parameters to the 'clock-names' property in -order to provide an optional (E)MIO clock source: - - swdt0_ext_clk - - swdt1_ext_clk - - gem0_emio_clk - - gem1_emio_clk - - gem2_emio_clk - - gem3_emio_clk - - mio_clk_XX # with XX = 00..77 - - mio_clk_50_or_51 #for the mux clock to gem tsu from 50 or 51 - - -Output clocks are registered based on clock information received -from firmware. Output clocks indexes are mentioned in -include/dt-bindings/clock/xlnx-zynqmp-clk.h. - ------- Example ------- @@ -72,11 +25,6 @@ firmware { zynqmp_firmware: zynqmp-firmware { compatible = "xlnx,zynqmp-firmware"; method = "smc"; - zynqmp_clk: clock-controller { - #clock-cells = <1>; - compatible = "xlnx,zynqmp-clk"; - clocks = <&pss_ref_clk>, <&video_clk>, <&pss_alt_ref_clk>, <&aux_ref_clk>, <>_crx_ref_clk>; - clock-names = "pss_ref_clk", "video_clk", "pss_alt_ref_clk","aux_ref_clk", "gt_crx_ref_clk"; - }; + ... }; }; -- cgit v1.2.3 From 3d0313786470acb414b7d5fdd2202f061acffb02 Mon Sep 17 00:00:00 2001 From: Rajan Vaja Date: Mon, 4 Mar 2019 15:18:08 -0800 Subject: drivers: Defer probe if firmware is not ready Driver needs ZynqMP firmware interface to call EEMI APIs. In case firmware is not ready, dependent drivers should wait until the firmware is ready. Signed-off-by: Rajan Vaja Signed-off-by: Jolly Shah Signed-off-by: Michal Simek --- Documentation/xilinx/eemi.txt | 4 ++-- drivers/clk/zynqmp/clkc.c | 4 ++-- drivers/firmware/xilinx/zynqmp-debug.c | 3 --- drivers/firmware/xilinx/zynqmp.c | 11 ++++++++++- drivers/nvmem/zynqmp_nvmem.c | 10 +++++++--- drivers/reset/reset-zynqmp.c | 8 ++++---- drivers/soc/xilinx/zynqmp_pm_domains.c | 18 ++++++++++-------- drivers/soc/xilinx/zynqmp_power.c | 10 ++++++---- drivers/spi/spi-zynqmp-gqspi.c | 5 +++++ include/linux/firmware/xlnx-zynqmp.h | 2 +- 10 files changed, 47 insertions(+), 28 deletions(-) (limited to 'Documentation') diff --git a/Documentation/xilinx/eemi.txt b/Documentation/xilinx/eemi.txt index 0ab686c173be..5f39b4ffdcd4 100644 --- a/Documentation/xilinx/eemi.txt +++ b/Documentation/xilinx/eemi.txt @@ -41,8 +41,8 @@ Example of EEMI ops usage: int ret; eemi_ops = zynqmp_pm_get_eemi_ops(); - if (!eemi_ops) - return -ENXIO; + if (IS_ERR(eemi_ops)) + return PTR_ERR(eemi_ops); ret = eemi_ops->query_data(qdata, ret_payload); diff --git a/drivers/clk/zynqmp/clkc.c b/drivers/clk/zynqmp/clkc.c index b0908ec62f73..2b1d43457f09 100644 --- a/drivers/clk/zynqmp/clkc.c +++ b/drivers/clk/zynqmp/clkc.c @@ -695,8 +695,8 @@ static int zynqmp_clock_probe(struct platform_device *pdev) struct device *dev = &pdev->dev; eemi_ops = zynqmp_pm_get_eemi_ops(); - if (!eemi_ops) - return -ENXIO; + if (IS_ERR(eemi_ops)) + return PTR_ERR(eemi_ops); ret = zynqmp_clk_setup(dev->of_node); diff --git a/drivers/firmware/xilinx/zynqmp-debug.c b/drivers/firmware/xilinx/zynqmp-debug.c index 90b66cdbfd58..c6d0724da4db 100644 --- a/drivers/firmware/xilinx/zynqmp-debug.c +++ b/drivers/firmware/xilinx/zynqmp-debug.c @@ -90,9 +90,6 @@ static int process_api_request(u32 pm_id, u64 *pm_api_arg, u32 *pm_api_ret) int ret; struct zynqmp_pm_query_data qdata = {0}; - if (!eemi_ops) - return -ENXIO; - switch (pm_id) { case PM_GET_API_VERSION: ret = eemi_ops->get_api_version(&pm_api_version); diff --git a/drivers/firmware/xilinx/zynqmp.c b/drivers/firmware/xilinx/zynqmp.c index 98f936125643..87a1d636c0dc 100644 --- a/drivers/firmware/xilinx/zynqmp.c +++ b/drivers/firmware/xilinx/zynqmp.c @@ -24,6 +24,8 @@ #include #include "zynqmp-debug.h" +static const struct zynqmp_eemi_ops *eemi_ops_tbl; + static const struct mfd_cell firmware_devs[] = { { .name = "zynqmp_power_controller", @@ -649,7 +651,11 @@ static const struct zynqmp_eemi_ops eemi_ops = { */ const struct zynqmp_eemi_ops *zynqmp_pm_get_eemi_ops(void) { - return &eemi_ops; + if (eemi_ops_tbl) + return eemi_ops_tbl; + else + return ERR_PTR(-EPROBE_DEFER); + } EXPORT_SYMBOL_GPL(zynqmp_pm_get_eemi_ops); @@ -694,6 +700,9 @@ static int zynqmp_firmware_probe(struct platform_device *pdev) pr_info("%s Trustzone version v%d.%d\n", __func__, pm_tz_version >> 16, pm_tz_version & 0xFFFF); + /* Assign eemi_ops_table */ + eemi_ops_tbl = &eemi_ops; + zynqmp_pm_api_debugfs_init(); ret = mfd_add_devices(&pdev->dev, PLATFORM_DEVID_NONE, firmware_devs, diff --git a/drivers/nvmem/zynqmp_nvmem.c b/drivers/nvmem/zynqmp_nvmem.c index 490c8fcaec80..5893543918c8 100644 --- a/drivers/nvmem/zynqmp_nvmem.c +++ b/drivers/nvmem/zynqmp_nvmem.c @@ -16,6 +16,8 @@ struct zynqmp_nvmem_data { struct nvmem_device *nvmem; }; +static const struct zynqmp_eemi_ops *eemi_ops; + static int zynqmp_nvmem_read(void *context, unsigned int offset, void *val, size_t bytes) { @@ -23,9 +25,7 @@ static int zynqmp_nvmem_read(void *context, unsigned int offset, int idcode, version; struct zynqmp_nvmem_data *priv = context; - const struct zynqmp_eemi_ops *eemi_ops = zynqmp_pm_get_eemi_ops(); - - if (!eemi_ops || !eemi_ops->get_chipid) + if (!eemi_ops->get_chipid) return -ENXIO; ret = eemi_ops->get_chipid(&idcode, &version); @@ -61,6 +61,10 @@ static int zynqmp_nvmem_probe(struct platform_device *pdev) if (!priv) return -ENOMEM; + eemi_ops = zynqmp_pm_get_eemi_ops(); + if (IS_ERR(eemi_ops)) + return PTR_ERR(eemi_ops); + priv->dev = dev; econfig.dev = dev; econfig.reg_read = zynqmp_nvmem_read; diff --git a/drivers/reset/reset-zynqmp.c b/drivers/reset/reset-zynqmp.c index 2ef1f13aa47b..99e75d92dada 100644 --- a/drivers/reset/reset-zynqmp.c +++ b/drivers/reset/reset-zynqmp.c @@ -79,11 +79,11 @@ static int zynqmp_reset_probe(struct platform_device *pdev) if (!priv) return -ENOMEM; - platform_set_drvdata(pdev, priv); - priv->eemi_ops = zynqmp_pm_get_eemi_ops(); - if (!priv->eemi_ops) - return -ENXIO; + if (IS_ERR(priv->eemi_ops)) + return PTR_ERR(priv->eemi_ops); + + platform_set_drvdata(pdev, priv); priv->rcdev.ops = &zynqmp_reset_ops; priv->rcdev.owner = THIS_MODULE; diff --git a/drivers/soc/xilinx/zynqmp_pm_domains.c b/drivers/soc/xilinx/zynqmp_pm_domains.c index 354d256e6e00..600f57cf0c2e 100644 --- a/drivers/soc/xilinx/zynqmp_pm_domains.c +++ b/drivers/soc/xilinx/zynqmp_pm_domains.c @@ -23,6 +23,8 @@ /* Flag stating if PM nodes mapped to the PM domain has been requested */ #define ZYNQMP_PM_DOMAIN_REQUESTED BIT(0) +static const struct zynqmp_eemi_ops *eemi_ops; + /** * struct zynqmp_pm_domain - Wrapper around struct generic_pm_domain * @gpd: Generic power domain @@ -71,9 +73,8 @@ static int zynqmp_gpd_power_on(struct generic_pm_domain *domain) { int ret; struct zynqmp_pm_domain *pd; - const struct zynqmp_eemi_ops *eemi_ops = zynqmp_pm_get_eemi_ops(); - if (!eemi_ops || !eemi_ops->set_requirement) + if (!eemi_ops->set_requirement) return -ENXIO; pd = container_of(domain, struct zynqmp_pm_domain, gpd); @@ -107,9 +108,8 @@ static int zynqmp_gpd_power_off(struct generic_pm_domain *domain) struct zynqmp_pm_domain *pd; u32 capabilities = 0; bool may_wakeup; - const struct zynqmp_eemi_ops *eemi_ops = zynqmp_pm_get_eemi_ops(); - if (!eemi_ops || !eemi_ops->set_requirement) + if (!eemi_ops->set_requirement) return -ENXIO; pd = container_of(domain, struct zynqmp_pm_domain, gpd); @@ -160,9 +160,8 @@ static int zynqmp_gpd_attach_dev(struct generic_pm_domain *domain, { int ret; struct zynqmp_pm_domain *pd; - const struct zynqmp_eemi_ops *eemi_ops = zynqmp_pm_get_eemi_ops(); - if (!eemi_ops || !eemi_ops->request_node) + if (!eemi_ops->request_node) return -ENXIO; pd = container_of(domain, struct zynqmp_pm_domain, gpd); @@ -197,9 +196,8 @@ static void zynqmp_gpd_detach_dev(struct generic_pm_domain *domain, { int ret; struct zynqmp_pm_domain *pd; - const struct zynqmp_eemi_ops *eemi_ops = zynqmp_pm_get_eemi_ops(); - if (!eemi_ops || !eemi_ops->release_node) + if (!eemi_ops->release_node) return; pd = container_of(domain, struct zynqmp_pm_domain, gpd); @@ -266,6 +264,10 @@ static int zynqmp_gpd_probe(struct platform_device *pdev) struct zynqmp_pm_domain *pd; struct device *dev = &pdev->dev; + eemi_ops = zynqmp_pm_get_eemi_ops(); + if (IS_ERR(eemi_ops)) + return PTR_ERR(eemi_ops); + pd = devm_kcalloc(dev, ZYNQMP_NUM_DOMAINS, sizeof(*pd), GFP_KERNEL); if (!pd) return -ENOMEM; diff --git a/drivers/soc/xilinx/zynqmp_power.c b/drivers/soc/xilinx/zynqmp_power.c index 771cb59b9d22..1b9d14411a15 100644 --- a/drivers/soc/xilinx/zynqmp_power.c +++ b/drivers/soc/xilinx/zynqmp_power.c @@ -31,6 +31,7 @@ static const char *const suspend_modes[] = { }; static enum pm_suspend_mode suspend_mode = PM_SUSPEND_MODE_STD; +static const struct zynqmp_eemi_ops *eemi_ops; enum pm_api_cb_id { PM_INIT_SUSPEND_CB = 30, @@ -92,9 +93,8 @@ static ssize_t suspend_mode_store(struct device *dev, const char *buf, size_t count) { int md, ret = -EINVAL; - const struct zynqmp_eemi_ops *eemi_ops = zynqmp_pm_get_eemi_ops(); - if (!eemi_ops || !eemi_ops->set_suspend_mode) + if (!eemi_ops->set_suspend_mode) return ret; for (md = PM_SUSPEND_MODE_FIRST; md < ARRAY_SIZE(suspend_modes); md++) @@ -120,9 +120,11 @@ static int zynqmp_pm_probe(struct platform_device *pdev) int ret, irq; u32 pm_api_version; - const struct zynqmp_eemi_ops *eemi_ops = zynqmp_pm_get_eemi_ops(); + eemi_ops = zynqmp_pm_get_eemi_ops(); + if (IS_ERR(eemi_ops)) + return PTR_ERR(eemi_ops); - if (!eemi_ops || !eemi_ops->get_api_version || !eemi_ops->init_finalize) + if (!eemi_ops->get_api_version || !eemi_ops->init_finalize) return -ENXIO; eemi_ops->init_finalize(); diff --git a/drivers/spi/spi-zynqmp-gqspi.c b/drivers/spi/spi-zynqmp-gqspi.c index 9f83e1b17aa1..d07b6f940f9f 100644 --- a/drivers/spi/spi-zynqmp-gqspi.c +++ b/drivers/spi/spi-zynqmp-gqspi.c @@ -138,6 +138,7 @@ #define SPI_AUTOSUSPEND_TIMEOUT 3000 enum mode_type {GQSPI_MODE_IO, GQSPI_MODE_DMA}; +static const struct zynqmp_eemi_ops *eemi_ops; /** * struct zynqmp_qspi - Defines qspi driver instance @@ -1021,6 +1022,10 @@ static int zynqmp_qspi_probe(struct platform_device *pdev) struct resource *res; struct device *dev = &pdev->dev; + eemi_ops = zynqmp_pm_get_eemi_ops(); + if (IS_ERR(eemi_ops)) + return PTR_ERR(eemi_ops); + master = spi_alloc_master(&pdev->dev, sizeof(*xqspi)); if (!master) return -ENOMEM; diff --git a/include/linux/firmware/xlnx-zynqmp.h b/include/linux/firmware/xlnx-zynqmp.h index 642dab10f65d..3533ee557043 100644 --- a/include/linux/firmware/xlnx-zynqmp.h +++ b/include/linux/firmware/xlnx-zynqmp.h @@ -293,7 +293,7 @@ const struct zynqmp_eemi_ops *zynqmp_pm_get_eemi_ops(void); #else static inline struct zynqmp_eemi_ops *zynqmp_pm_get_eemi_ops(void) { - return NULL; + return ERR_PTR(-ENODEV); } #endif -- cgit v1.2.3 From 69b921acae8a5b7feef03921d9b42c3634f3b9d1 Mon Sep 17 00:00:00 2001 From: Rasmus Villemoes Date: Wed, 6 Mar 2019 10:32:05 +0000 Subject: spi: spi-fsl-spi: support use of the SPISEL_BOOT signal on MPC8309 The MPC8309 has a dedicated signal, SPISEL_BOOT, usually used as chip select for the flash device from which the bootloader is loaded. It is not an ordinary gpio, but is simply controlled via the SPI_CS register in the system configuration. To allow accessing such a spi slave, we need to teach fsl_spi_cs_control() how to control the SPISEL_BOOT signal. To distinguish the gpio-controlled slaves, continue to have those use chip_select values of 0..ngpios-1, and use chip_select == ngpios for the boot flash. I'm not too happy with all the ifdeffery, but it seems to be necessary for guarding the sysdev/fsl_soc.h and use of get_immrbase() (spi-fsl-lib.c already contains similar ifdeffery). Googling suggests that the MPC8306 is similar, with the SPI_CS register at the same offset. Signed-off-by: Rasmus Villemoes Signed-off-by: Mark Brown --- Documentation/devicetree/bindings/spi/fsl-spi.txt | 4 +++ drivers/spi/spi-fsl-lib.h | 2 ++ drivers/spi/spi-fsl-spi.c | 40 ++++++++++++++++++++--- 3 files changed, 41 insertions(+), 5 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/spi/fsl-spi.txt b/Documentation/devicetree/bindings/spi/fsl-spi.txt index 8854004a1d3a..411375eac54d 100644 --- a/Documentation/devicetree/bindings/spi/fsl-spi.txt +++ b/Documentation/devicetree/bindings/spi/fsl-spi.txt @@ -18,6 +18,10 @@ Optional properties: - gpios : specifies the gpio pins to be used for chipselects. The gpios will be referred to as reg = in the SPI child nodes. If unspecified, a single SPI device without a chip select can be used. +- fsl,spisel_boot : for the MPC8306 and MPC8309, specifies that the + SPISEL_BOOT signal is used as chip select for a slave device. Use + reg = in the corresponding child node, i.e. 0 if + the gpios property is not present. Example: spi@4c0 { diff --git a/drivers/spi/spi-fsl-lib.h b/drivers/spi/spi-fsl-lib.h index f303f306b38e..483734bc1b1e 100644 --- a/drivers/spi/spi-fsl-lib.h +++ b/drivers/spi/spi-fsl-lib.h @@ -95,8 +95,10 @@ static inline u32 mpc8xxx_spi_read_reg(__be32 __iomem *reg) struct mpc8xxx_spi_probe_info { struct fsl_spi_platform_data pdata; + int ngpios; int *gpios; bool *alow_flags; + __be32 __iomem *immr_spi_cs; }; extern u32 mpc8xxx_spi_tx_buf_u8(struct mpc8xxx_spi *mpc8xxx_spi); diff --git a/drivers/spi/spi-fsl-spi.c b/drivers/spi/spi-fsl-spi.c index 8f2e97857e8b..3d7b50c65f36 100644 --- a/drivers/spi/spi-fsl-spi.c +++ b/drivers/spi/spi-fsl-spi.c @@ -39,6 +39,14 @@ #include #include +#ifdef CONFIG_FSL_SOC +#include +#endif + +/* Specific to the MPC8306/MPC8309 */ +#define IMMR_SPI_CS_OFFSET 0x14c +#define SPI_BOOT_SEL_BIT 0x80000000 + #include "spi-fsl-lib.h" #include "spi-fsl-cpm.h" #include "spi-fsl-spi.h" @@ -701,10 +709,17 @@ static void fsl_spi_cs_control(struct spi_device *spi, bool on) struct fsl_spi_platform_data *pdata = dev_get_platdata(dev); struct mpc8xxx_spi_probe_info *pinfo = to_of_pinfo(pdata); u16 cs = spi->chip_select; - int gpio = pinfo->gpios[cs]; - bool alow = pinfo->alow_flags[cs]; - gpio_set_value(gpio, on ^ alow); + if (cs < pinfo->ngpios) { + int gpio = pinfo->gpios[cs]; + bool alow = pinfo->alow_flags[cs]; + + gpio_set_value(gpio, on ^ alow); + } else { + if (WARN_ON_ONCE(cs > pinfo->ngpios || !pinfo->immr_spi_cs)) + return; + iowrite32be(on ? SPI_BOOT_SEL_BIT : 0, pinfo->immr_spi_cs); + } } static int of_fsl_spi_get_chipselects(struct device *dev) @@ -712,12 +727,15 @@ static int of_fsl_spi_get_chipselects(struct device *dev) struct device_node *np = dev->of_node; struct fsl_spi_platform_data *pdata = dev_get_platdata(dev); struct mpc8xxx_spi_probe_info *pinfo = to_of_pinfo(pdata); + bool spisel_boot = IS_ENABLED(CONFIG_FSL_SOC) && + of_property_read_bool(np, "fsl,spisel_boot"); int ngpios; int i = 0; int ret; ngpios = of_gpio_count(np); - if (ngpios <= 0) { + ngpios = max(ngpios, 0); + if (ngpios == 0 && !spisel_boot) { /* * SPI w/o chip-select line. One SPI device is still permitted * though. @@ -726,6 +744,7 @@ static int of_fsl_spi_get_chipselects(struct device *dev) return 0; } + pinfo->ngpios = ngpios; pinfo->gpios = kmalloc_array(ngpios, sizeof(*pinfo->gpios), GFP_KERNEL); if (!pinfo->gpios) @@ -769,7 +788,18 @@ static int of_fsl_spi_get_chipselects(struct device *dev) } } - pdata->max_chipselect = ngpios; +#if IS_ENABLED(CONFIG_FSL_SOC) + if (spisel_boot) { + pinfo->immr_spi_cs = ioremap(get_immrbase() + IMMR_SPI_CS_OFFSET, 4); + if (!pinfo->immr_spi_cs) { + ret = -ENOMEM; + i = ngpios - 1; + goto err_loop; + } + } +#endif + + pdata->max_chipselect = ngpios + spisel_boot; pdata->cs_control = fsl_spi_cs_control; return 0; -- cgit v1.2.3 From 6917de8a6c4d05737dded7053a66be3c7e6779c2 Mon Sep 17 00:00:00 2001 From: Neil Armstrong Date: Tue, 12 Feb 2019 15:02:58 +0100 Subject: vendor-prefixes: Add prefix for Shenzhen SEI Robotics Co., Ltd Add vendor prefix for the Shenzhen SEI Robotics Co., Ltd, a chinese ODM specialized in Android TV HDMI Stick, OTT Box, Hybrid STB, Smart Home Gateway & more. Signed-off-by: Neil Armstrong Signed-off-by: Kevin Hilman --- Documentation/devicetree/bindings/vendor-prefixes.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/vendor-prefixes.txt b/Documentation/devicetree/bindings/vendor-prefixes.txt index 8162b0eb4b50..bb6f6e8a2eee 100644 --- a/Documentation/devicetree/bindings/vendor-prefixes.txt +++ b/Documentation/devicetree/bindings/vendor-prefixes.txt @@ -353,6 +353,7 @@ sandisk Sandisk Corporation sbs Smart Battery System schindler Schindler seagate Seagate Technology PLC +seirobotics Shenzhen SEI Robotics Co., Ltd semtech Semtech Corporation sensirion Sensirion AG sff Small Form Factor Committee -- cgit v1.2.3 From b7be144932a8376fbb886115ce908a1a1818940b Mon Sep 17 00:00:00 2001 From: Neil Armstrong Date: Tue, 12 Feb 2019 15:02:59 +0100 Subject: arm64: dts: Add SEI Robotics SEI510 Board The SEI Robotics SEI510 Board is based on the Amlogic G12A S905X2 and has the following features : - Amlogic G12A S905X2 SoC - 10/100 Ethernet - USB2 + USB3 ports - Micro SDCard Port - Audio + CVBS AV Jack port - HDMI 2.1 + CEC Port - ADC Touch Button - Far-Field Microphone Array + Mono HP - IR Sensor - IR Emmiter LED Array - RGB Led Signed-off-by: Neil Armstrong [khilman: sorted Makefile entry alphabetcially] Signed-off-by: Kevin Hilman --- Documentation/devicetree/bindings/arm/amlogic.txt | 1 + arch/arm64/boot/dts/amlogic/Makefile | 1 + arch/arm64/boot/dts/amlogic/meson-g12a-sei510.dts | 38 +++++++++++++++++++++++ 3 files changed, 40 insertions(+) create mode 100644 arch/arm64/boot/dts/amlogic/meson-g12a-sei510.dts (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/amlogic.txt b/Documentation/devicetree/bindings/arm/amlogic.txt index 7f40cb5f490b..061f7b98a07f 100644 --- a/Documentation/devicetree/bindings/arm/amlogic.txt +++ b/Documentation/devicetree/bindings/arm/amlogic.txt @@ -110,6 +110,7 @@ Board compatible values (alphabetically, grouped by SoC): - "amlogic,u200" (Meson g12a s905d2) - "amediatech,x96-max" (Meson g12a s905x2) + - "seirobotics,sei510" (Meson g12a s905x2) Amlogic Meson Firmware registers Interface ------------------------------------------ diff --git a/arch/arm64/boot/dts/amlogic/Makefile b/arch/arm64/boot/dts/amlogic/Makefile index 0821fed4c074..e129c03ced14 100644 --- a/arch/arm64/boot/dts/amlogic/Makefile +++ b/arch/arm64/boot/dts/amlogic/Makefile @@ -1,5 +1,6 @@ # SPDX-License-Identifier: GPL-2.0 dtb-$(CONFIG_ARCH_MESON) += meson-axg-s400.dtb +dtb-$(CONFIG_ARCH_MESON) += meson-g12a-sei510.dtb dtb-$(CONFIG_ARCH_MESON) += meson-g12a-u200.dtb dtb-$(CONFIG_ARCH_MESON) += meson-g12a-x96-max.dtb dtb-$(CONFIG_ARCH_MESON) += meson-gxbb-nanopi-k2.dtb diff --git a/arch/arm64/boot/dts/amlogic/meson-g12a-sei510.dts b/arch/arm64/boot/dts/amlogic/meson-g12a-sei510.dts new file mode 100644 index 000000000000..6a7c3241862a --- /dev/null +++ b/arch/arm64/boot/dts/amlogic/meson-g12a-sei510.dts @@ -0,0 +1,38 @@ +// SPDX-License-Identifier: (GPL-2.0+ OR MIT) +/* + * Copyright (c) 2019 BayLibre SAS. All rights reserved. + */ + +/dts-v1/; + +#include "meson-g12a.dtsi" + +/ { + compatible = "seirobotics,sei510", "amlogic,g12a"; + model = "SEI Robotics SEI510"; + + aliases { + serial0 = &uart_AO; + }; + + chosen { + stdout-path = "serial0:115200n8"; + }; + + memory@0 { + device_type = "memory"; + reg = <0x0 0x0 0x0 0x40000000>; + }; + + reserved-memory { + /* TEE Reserved Memory */ + bl32_reserved: bl32@5000000 { + reg = <0x0 0x05300000 0x0 0x2000000>; + no-map; + }; + }; +}; + +&uart_AO { + status = "okay"; +}; -- cgit v1.2.3 From 487ecc460732cab178897e81a7f5ef6183eff143 Mon Sep 17 00:00:00 2001 From: SeongJae Park Date: Fri, 25 Jan 2019 06:55:47 +0900 Subject: sched/Documentation/kokr: Update Korean translation to update wake_up() & co. memory-barrier guarantees Translate this commit to Korean: 7696f9910a9a ("sched/Documentation: Update wake_up() & co. memory-barrier guarantees") Signed-off-by: SeongJae Park Reviewed-by: Yunjae Lee Signed-off-by: Paul E. McKenney --- .../translations/ko_KR/memory-barriers.txt | 43 +++++++++++++--------- 1 file changed, 26 insertions(+), 17 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/ko_KR/memory-barriers.txt b/Documentation/translations/ko_KR/memory-barriers.txt index 7f01fb1c1084..4a6cf4d58cbf 100644 --- a/Documentation/translations/ko_KR/memory-barriers.txt +++ b/Documentation/translations/ko_KR/memory-barriers.txt @@ -2146,33 +2146,40 @@ set_current_state() 는 다음의 것들로 감싸질 수도 있습니다: event_indicated = 1; wake_up_process(event_daemon); -wake_up() 류에 의해 쓰기 메모리 배리어가 내포됩니다. 만약 그것들이 뭔가를 -깨운다면요. 이 배리어는 태스크 상태가 지워지기 전에 수행되므로, 이벤트를 -알리기 위한 STORE 와 태스크 상태를 TASK_RUNNING 으로 설정하는 STORE 사이에 -위치하게 됩니다. +wake_up() 이 무언가를 깨우게 되면, 이 함수는 범용 메모리 배리어를 수행합니다. +이 함수가 아무것도 깨우지 않는다면 메모리 배리어는 수행될 수도, 수행되지 않을 +수도 있습니다; 이 경우에 메모리 배리어를 수행할 거라 오해해선 안됩니다. 이 +배리어는 태스크 상태가 접근되기 전에 수행되는데, 자세히 말하면 이 이벤트를 +알리기 위한 STORE 와 TASK_RUNNING 으로 상태를 쓰는 STORE 사이에 수행됩니다: - CPU 1 CPU 2 + CPU 1 (Sleeper) CPU 2 (Waker) =============================== =============================== set_current_state(); STORE event_indicated smp_store_mb(); wake_up(); - STORE current->state <쓰기 배리어> - <범용 배리어> STORE current->state - LOAD event_indicated + STORE current->state ... + <범용 배리어> <범용 배리어> + LOAD event_indicated if ((LOAD task->state) & TASK_NORMAL) + STORE task->state -한번더 말합니다만, 이 쓰기 메모리 배리어는 이 코드가 정말로 뭔가를 깨울 때에만 -실행됩니다. 이걸 설명하기 위해, X 와 Y 는 모두 0 으로 초기화 되어 있다는 가정 -하에 아래의 이벤트 시퀀스를 생각해 봅시다: +여기서 "task" 는 깨어나지는 쓰레드이고 CPU 1 의 "current" 와 같습니다. + +반복하지만, wake_up() 이 무언가를 정말 깨운다면 범용 메모리 배리어가 수행될 +것이 보장되지만, 그렇지 않다면 그런 보장이 없습니다. 이걸 이해하기 위해, X 와 +Y 는 모두 0 으로 초기화 되어 있다는 가정 하에 아래의 이벤트 시퀀스를 생각해 +봅시다: CPU 1 CPU 2 =============================== =============================== - X = 1; STORE event_indicated + X = 1; Y = 1; smp_mb(); wake_up(); - Y = 1; wait_event(wq, Y == 1); - wake_up(); load from Y sees 1, no memory barrier - load from X might see 0 + LOAD Y LOAD X + +정말로 깨우기가 행해졌다면, 두 로드 중 (최소한) 하나는 1 을 보게 됩니다. +반면에, 실제 깨우기가 행해지지 않았다면, 두 로드 모두 0을 볼 수도 있습니다. -위 예제에서의 경우와 달리 깨우기가 정말로 행해졌다면, CPU 2 의 X 로드는 1 을 -본다고 보장될 수 있을 겁니다. +wake_up_process() 는 항상 범용 메모리 배리어를 수행합니다. 이 배리어 역시 +태스크 상태가 접근되기 전에 수행됩니다. 특히, 앞의 예제 코드에서 wake_up() 이 +wake_up_process() 로 대체된다면 두 로드 중 하나는 1을 볼 것이 보장됩니다. 사용 가능한 깨우기류 함수들로 다음과 같은 것들이 있습니다: @@ -2192,6 +2199,8 @@ wake_up() 류에 의해 쓰기 메모리 배리어가 내포됩니다. 만약 wake_up_poll(); wake_up_process(); +메모리 순서규칙 관점에서, 이 함수들은 모두 wake_up() 과 같거나 보다 강한 순서 +보장을 제공합니다. [!] 잠재우는 코드와 깨우는 코드에 내포되는 메모리 배리어들은 깨우기 전에 이루어진 스토어를 잠재우는 코드가 set_current_state() 를 호출한 후에 행하는 -- cgit v1.2.3 From db467147f131b8ab799066b9779addb8603d3baf Mon Sep 17 00:00:00 2001 From: SeongJae Park Date: Fri, 25 Jan 2019 06:55:48 +0900 Subject: locking/memory-barriers/kokr: Update Korean translation to replace smp_cond_acquire() with smp_cond_load_acquire() Transalte this commit to Korean: 2f359c7ea554 ("locking/memory-barriers: Replace smp_cond_acquire() with smp_cond_load_acquire()") Signed-off-by: SeongJae Park Reviewed-by: Yunjae Lee Signed-off-by: Paul E. McKenney --- Documentation/translations/ko_KR/memory-barriers.txt | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/ko_KR/memory-barriers.txt b/Documentation/translations/ko_KR/memory-barriers.txt index 4a6cf4d58cbf..db0b9d8619f1 100644 --- a/Documentation/translations/ko_KR/memory-barriers.txt +++ b/Documentation/translations/ko_KR/memory-barriers.txt @@ -493,10 +493,8 @@ CPU 에게 기대할 수 있는 최소한의 보장사항 몇가지가 있습니 이 타입의 오퍼레이션은 단방향의 투과성 배리어처럼 동작합니다. ACQUIRE 오퍼레이션 뒤의 모든 메모리 오퍼레이션들이 ACQUIRE 오퍼레이션 후에 일어난 것으로 시스템의 나머지 컴포넌트들에 보이게 될 것이 보장됩니다. - LOCK 오퍼레이션과 smp_load_acquire(), smp_cond_acquire() 오퍼레이션도 - ACQUIRE 오퍼레이션에 포함됩니다. smp_cond_acquire() 오퍼레이션은 컨트롤 - 의존성과 smp_rmb() 를 사용해서 ACQUIRE 의 의미적 요구사항(semantic)을 - 충족시킵니다. + LOCK 오퍼레이션과 smp_load_acquire(), smp_cond_load_acquire() 오퍼레이션도 + ACQUIRE 오퍼레이션에 포함됩니다. ACQUIRE 오퍼레이션 앞의 메모리 오퍼레이션들은 ACQUIRE 오퍼레이션 완료 후에 수행된 것처럼 보일 수 있습니다. -- cgit v1.2.3 From f1887143f5984f23d2360f2efed6ef481bb41117 Mon Sep 17 00:00:00 2001 From: Peter Zijlstra Date: Mon, 11 Feb 2019 18:09:43 +0100 Subject: Documentation/atomic_t: Clarify signed vs unsigned Clarify the whole signed vs unsigned issue for atomic_t. There has been enough confusion on this topic to warrant a few explicit words I feel. Signed-off-by: Peter Zijlstra (Intel) Acked-by: Will Deacon Acked-by: Boqun Feng Signed-off-by: Paul E. McKenney --- Documentation/atomic_t.txt | 17 +++++++++++++++++ 1 file changed, 17 insertions(+) (limited to 'Documentation') diff --git a/Documentation/atomic_t.txt b/Documentation/atomic_t.txt index 913396ac5824..dca3fb0554db 100644 --- a/Documentation/atomic_t.txt +++ b/Documentation/atomic_t.txt @@ -56,6 +56,23 @@ Barriers: smp_mb__{before,after}_atomic() +TYPES (signed vs unsigned) +----- + +While atomic_t, atomic_long_t and atomic64_t use int, long and s64 +respectively (for hysterical raisins), the kernel uses -fno-strict-overflow +(which implies -fwrapv) and defines signed overflow to behave like +2s-complement. + +Therefore, an explicitly unsigned variant of the atomic ops is strictly +unnecessary and we can simply cast, there is no UB. + +There was a bug in UBSAN prior to GCC-8 that would generate UB warnings for +signed types. + +With this we also conform to the C/C++ _Atomic behaviour and things like +P1236R1. + SEMANTICS --------- -- cgit v1.2.3 From 01196f96bf2ce78538249a8c987ecee65b40df5d Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:31 +0800 Subject: docs/zh_CN: add disclaimer file This a disclaimer file which will be included in Chinese files as header. To reduce the same common contents copy. Part of contents quoted from Federico Vaga's file: Documentation/translations/it_IT/disclaimer-ita.rst. Thanks a lot! Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Li Zefan Cc: Shawn Guo Cc: Fengguang Wu Cc: Coly Li Cc: Federico Vaga Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/disclaimer-zh_CN.rst | 9 +++++++++ 1 file changed, 9 insertions(+) create mode 100644 Documentation/translations/zh_CN/disclaimer-zh_CN.rst (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/disclaimer-zh_CN.rst b/Documentation/translations/zh_CN/disclaimer-zh_CN.rst new file mode 100644 index 000000000000..5934369b2606 --- /dev/null +++ b/Documentation/translations/zh_CN/disclaimer-zh_CN.rst @@ -0,0 +1,9 @@ +:orphan: + +.. warning:: + 此文件的目的是为让中文读者更容易阅读和理解,而不是作为一个分支。 因此,如果 + 您对此文件有任何意见或更新,请先尝试更新原始英文文件。 + +.. note:: + 如果您发现本文档与原始文件有任何不同或者有翻译问题,请联系该文件的维护者, + 或者请求时奎亮的帮助:。 -- cgit v1.2.3 From aa3b3690504d8dde55539b406a3fbbdc3fe228d2 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:32 +0800 Subject: docs/zh_CN: move process related docs into process dir Much process documents spread here isn't neat. It's good to put them together in their directory: process So create 'process' directory and move docs: email-clients stable_kernel_rules stable_api_nosense submittingpatches submittingdrivers HOWTO volatile-considered-harmful there. Signed-off-by: Alex Shi Cc: Li Zefan Cc: Shawn Guo Cc: Fengguang Wu Cc: Harry Wei Cc: Jonathan Corbet Cc: Coly Li Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/HOWTO | 525 ----------- Documentation/translations/zh_CN/SubmittingDrivers | 164 ---- Documentation/translations/zh_CN/SubmittingPatches | 412 --------- Documentation/translations/zh_CN/coding-style.rst | 967 --------------------- Documentation/translations/zh_CN/email-clients.txt | 210 ----- Documentation/translations/zh_CN/magic-number.txt | 153 ---- Documentation/translations/zh_CN/process/HOWTO | 525 +++++++++++ .../translations/zh_CN/process/SubmittingDrivers | 164 ++++ .../translations/zh_CN/process/SubmittingPatches | 412 +++++++++ .../translations/zh_CN/process/coding-style.rst | 967 +++++++++++++++++++++ .../translations/zh_CN/process/email-clients.txt | 210 +++++ .../translations/zh_CN/process/magic-number.txt | 153 ++++ .../zh_CN/process/stable_api_nonsense.txt | 157 ++++ .../zh_CN/process/stable_kernel_rules.txt | 66 ++ .../zh_CN/process/volatile-considered-harmful.txt | 113 +++ .../translations/zh_CN/stable_api_nonsense.txt | 157 ---- .../translations/zh_CN/stable_kernel_rules.txt | 66 -- .../zh_CN/volatile-considered-harmful.txt | 113 --- 18 files changed, 2767 insertions(+), 2767 deletions(-) delete mode 100644 Documentation/translations/zh_CN/HOWTO delete mode 100644 Documentation/translations/zh_CN/SubmittingDrivers delete mode 100644 Documentation/translations/zh_CN/SubmittingPatches delete mode 100644 Documentation/translations/zh_CN/coding-style.rst delete mode 100644 Documentation/translations/zh_CN/email-clients.txt delete mode 100644 Documentation/translations/zh_CN/magic-number.txt create mode 100644 Documentation/translations/zh_CN/process/HOWTO create mode 100644 Documentation/translations/zh_CN/process/SubmittingDrivers create mode 100644 Documentation/translations/zh_CN/process/SubmittingPatches create mode 100644 Documentation/translations/zh_CN/process/coding-style.rst create mode 100644 Documentation/translations/zh_CN/process/email-clients.txt create mode 100644 Documentation/translations/zh_CN/process/magic-number.txt create mode 100644 Documentation/translations/zh_CN/process/stable_api_nonsense.txt create mode 100644 Documentation/translations/zh_CN/process/stable_kernel_rules.txt create mode 100644 Documentation/translations/zh_CN/process/volatile-considered-harmful.txt delete mode 100644 Documentation/translations/zh_CN/stable_api_nonsense.txt delete mode 100644 Documentation/translations/zh_CN/stable_kernel_rules.txt delete mode 100644 Documentation/translations/zh_CN/volatile-considered-harmful.txt (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/HOWTO b/Documentation/translations/zh_CN/HOWTO deleted file mode 100644 index 7a00a8a4eb15..000000000000 --- a/Documentation/translations/zh_CN/HOWTO +++ /dev/null @@ -1,525 +0,0 @@ -Chinese translated version of Documentation/process/howto.rst - -If you have any comment or update to the content, please contact the -original document maintainer directly. However, if you have a problem -communicating in English you can also ask the Chinese maintainer for -help. Contact the Chinese maintainer if this translation is outdated -or if there is a problem with the translation. - -Maintainer: Greg Kroah-Hartman -Chinese maintainer: Li Yang ---------------------------------------------------------------------- -Documentation/process/howto.rst 的中文翻译 - -如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 -交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者。 - -英文版维护者: Greg Kroah-Hartman -中文版维护者: 李阳 Li Yang -中文版翻译者: 李阳 Li Yang -中文版校译者: 钟宇 TripleX Chung - 陈琦 Maggie Chen - 王聪 Wang Cong - -以下为正文 ---------------------------------------------------------------------- - -如何参与Linux内核开发 ---------------------- - -这是一篇将如何参与Linux内核开发的相关问题一网打尽的终极秘笈。它将指导你 -成为一名Linux内核开发者,并且学会如何同Linux内核开发社区合作。它尽可能不 -包括任何关于内核编程的技术细节,但会给你指引一条获得这些知识的正确途径。 - -如果这篇文章中的任何内容不再适用,请给文末列出的文件维护者发送补丁。 - - -入门 ----- - -你想了解如何成为一名Linux内核开发者?或者老板吩咐你“给这个设备写个Linux -驱动程序”?这篇文章的目的就是教会你达成这些目标的全部诀窍,它将描述你需 -要经过的流程以及给出如何同内核社区合作的一些提示。它还将试图解释内核社区 -为何这样运作。 - -Linux内核大部分是由C语言写成的,一些体系结构相关的代码用到了汇编语言。要 -参与内核开发,你必须精通C语言。除非你想为某个架构开发底层代码,否则你并 -不需要了解(任何体系结构的)汇编语言。下面列举的书籍虽然不能替代扎实的C -语言教育和多年的开发经验,但如果需要的话,做为参考还是不错的: - - "The C Programming Language" by Kernighan and Ritchie [Prentice Hall] - 《C程序设计语言(第2版·新版)》(徐宝文 李志 译)[机械工业出版社] - - "Practical C Programming" by Steve Oualline [O'Reilly] - 《实用C语言编程(第三版)》(郭大海 译)[中国电力出版社] - - "C: A Reference Manual" by Harbison and Steele [Prentice Hall] - 《C语言参考手册(原书第5版)》(邱仲潘 等译)[机械工业出版社] - -Linux内核使用GNU C和GNU工具链开发。虽然它遵循ISO C89标准,但也用到了一些 -标准中没有定义的扩展。内核是自给自足的C环境,不依赖于标准C库的支持,所以 -并不支持C标准中的部分定义。比如long long类型的大数除法和浮点运算就不允许 -使用。有时候确实很难弄清楚内核对工具链的要求和它所使用的扩展,不幸的是目 -前还没有明确的参考资料可以解释它们。请查阅gcc信息页(使用“info gcc”命令 -显示)获得一些这方面信息。 - -请记住你是在学习怎么和已经存在的开发社区打交道。它由一群形形色色的人组成, -他们对代码、风格和过程有着很高的标准。这些标准是在长期实践中总结出来的, -适应于地理上分散的大型开发团队。它们已经被很好得整理成档,建议你在开发 -之前尽可能多的学习这些标准,而不要期望别人来适应你或者你公司的行为方式。 - - -法律问题 --------- - -Linux内核源代码都是在GPL(通用公共许可证)的保护下发布的。要了解这种许可 -的细节请查看源代码主目录下的COPYING文件。如果你对它还有更深入问题请联系 -律师,而不要在Linux内核邮件组上提问。因为邮件组里的人并不是律师,不要期 -望他们的话有法律效力。 - -对于GPL的常见问题和解答,请访问以下链接: - http://www.gnu.org/licenses/gpl-faq.html - - -文档 ----- - -Linux内核代码中包含有大量的文档。这些文档对于学习如何与内核社区互动有着 -不可估量的价值。当一个新的功能被加入内核,最好把解释如何使用这个功能的文 -档也放进内核。当内核的改动导致面向用户空间的接口发生变化时,最好将相关信 -息或手册页(manpages)的补丁发到mtk.manpages@gmail.com,以向手册页(manpages) -的维护者解释这些变化。 - -以下是内核代码中需要阅读的文档: - README - 文件简要介绍了Linux内核的背景,并且描述了如何配置和编译内核。内核的 - 新用户应该从这里开始。 - - Documentation/process/changes.rst - 文件给出了用来编译和使用内核所需要的最小软件包列表。 - - Documentation/process/coding-style.rst - 描述Linux内核的代码风格和理由。所有新代码需要遵守这篇文档中定义的规 - 范。大多数维护者只会接收符合规定的补丁,很多人也只会帮忙检查符合风格 - 的代码。 - - Documentation/process/submitting-patches.rst - Documentation/process/submitting-drivers.rst - 这两份文档明确描述如何创建和发送补丁,其中包括(但不仅限于): - - 邮件内容 - - 邮件格式 - - 选择收件人 - 遵守这些规定并不能保证提交成功(因为所有补丁需要通过严格的内容和风格 - 审查),但是忽视他们几乎就意味着失败。 - - 其他关于如何正确地生成补丁的优秀文档包括: - "The Perfect Patch" - http://www.ozlabs.org/~akpm/stuff/tpp.txt - "Linux kernel patch submission format" - http://linux.yyz.us/patch-format.html - - Documentation/process/stable-api-nonsense.rst - 论证内核为什么特意不包括稳定的内核内部API,也就是说不包括像这样的特 - 性: - - 子系统中间层(为了兼容性?) - - 在不同操作系统间易于移植的驱动程序 - - 减缓(甚至阻止)内核代码的快速变化 - 这篇文档对于理解Linux的开发哲学至关重要。对于将开发平台从其他操作系 - 统转移到Linux的人来说也很重要。 - - Documentation/admin-guide/security-bugs.rst - 如果你认为自己发现了Linux内核的安全性问题,请根据这篇文档中的步骤来 - 提醒其他内核开发者并帮助解决这个问题。 - - Documentation/process/management-style.rst - 描述内核维护者的工作方法及其共有特点。这对于刚刚接触内核开发(或者对 - 它感到好奇)的人来说很重要,因为它解释了很多对于内核维护者独特行为的 - 普遍误解与迷惑。 - - Documentation/process/stable-kernel-rules.rst - 解释了稳定版内核发布的规则,以及如何将改动放入这些版本的步骤。 - - Documentation/process/kernel-docs.rst - 有助于内核开发的外部文档列表。如果你在内核自带的文档中没有找到你想找 - 的内容,可以查看这些文档。 - - Documentation/process/applying-patches.rst - 关于补丁是什么以及如何将它打在不同内核开发分支上的好介绍 - -内核还拥有大量从代码自动生成的文档。它包含内核内部API的全面介绍以及如何 -妥善处理加锁的规则。生成的文档会放在 Documentation/DocBook/目录下。在内 -核源码的主目录中使用以下不同命令将会分别生成PDF、Postscript、HTML和手册 -页等不同格式的文档: - make pdfdocs - make htmldocs - - -如何成为内核开发者 ------------------- -如果你对Linux内核开发一无所知,你应该访问“Linux内核新手”计划: - http://kernelnewbies.org -它拥有一个可以问各种最基本的内核开发问题的邮件列表(在提问之前一定要记得 -查找已往的邮件,确认是否有人已经回答过相同的问题)。它还拥有一个可以获得 -实时反馈的IRC聊天频道,以及大量对于学习Linux内核开发相当有帮助的文档。 - -网站简要介绍了源代码组织结构、子系统划分以及目前正在进行的项目(包括内核 -中的和单独维护的)。它还提供了一些基本的帮助信息,比如如何编译内核和打补 -丁。 - -如果你想加入内核开发社区并协助完成一些任务,却找不到从哪里开始,可以访问 -“Linux内核房管员”计划: - http://kernelnewbies.org/KernelJanitors -这是极佳的起点。它提供一个相对简单的任务列表,列出内核代码中需要被重新 -整理或者改正的地方。通过和负责这个计划的开发者们一同工作,你会学到将补丁 -集成进内核的基本原理。如果还没有决定下一步要做什么的话,你还可能会得到方 -向性的指点。 - -如果你已经有一些现成的代码想要放到内核中,但是需要一些帮助来使它们拥有正 -确的格式。请访问“内核导师”计划。这个计划就是用来帮助你完成这个目标的。它 -是一个邮件列表,地址如下: - http://selenic.com/mailman/listinfo/kernel-mentors - -在真正动手修改内核代码之前,理解要修改的代码如何运作是必需的。要达到这个 -目的,没什么办法比直接读代码更有效了(大多数花招都会有相应的注释),而且 -一些特制的工具还可以提供帮助。例如,“Linux代码交叉引用”项目就是一个值得 -特别推荐的帮助工具,它将源代码显示在有编目和索引的网页上。其中一个更新及 -时的内核源码库,可以通过以下地址访问: - http://sosdg.org/~coywolf/lxr/ - - -开发流程 --------- - -目前Linux内核开发流程包括几个“主内核分支”和很多子系统相关的内核分支。这 -些分支包括: - - 2.6.x主内核源码树 - - 2.6.x.y -stable内核源码树 - - 2.6.x -mm内核补丁集 - - 子系统相关的内核源码树和补丁集 - - -2.6.x内核主源码树 ------------------ -2.6.x内核是由Linus Torvalds(Linux的创造者)亲自维护的。你可以在 -kernel.org网站的pub/linux/kernel/v2.6/目录下找到它。它的开发遵循以下步 -骤: - - 每当一个新版本的内核被发布,为期两周的集成窗口将被打开。在这段时间里 - 维护者可以向Linus提交大段的修改,通常这些修改已经被放到-mm内核中几个 - 星期了。提交大量修改的首选方式是使用git工具(内核的代码版本管理工具 - ,更多的信息可以在http://git-scm.com/获取),不过使用普通补丁也是可以 - 的。 - - 两个星期以后-rc1版本内核发布。之后只有不包含可能影响整个内核稳定性的 - 新功能的补丁才可能被接受。请注意一个全新的驱动程序(或者文件系统)有 - 可能在-rc1后被接受是因为这样的修改完全独立,不会影响其他的代码,所以 - 没有造成内核退步的风险。在-rc1以后也可以用git向Linus提交补丁,不过所 - 有的补丁需要同时被发送到相应的公众邮件列表以征询意见。 - - 当Linus认为当前的git源码树已经达到一个合理健全的状态足以发布供人测试 - 时,一个新的-rc版本就会被发布。计划是每周都发布新的-rc版本。 - - 这个过程一直持续下去直到内核被认为达到足够稳定的状态,持续时间大概是 - 6个星期。 - -关于内核发布,值得一提的是Andrew Morton在linux-kernel邮件列表中如是说: - “没有人知道新内核何时会被发布,因为发布是根据已知bug的情况来决定 - 的,而不是根据一个事先制定好的时间表。” - - -2.6.x.y -stable(稳定版)内核源码树 ------------------------------------ -由4个数字组成的内核版本号说明此内核是-stable版本。它们包含基于2.6.x版本 -内核的相对较小且至关重要的修补,这些修补针对安全性问题或者严重的内核退步。 - -这种版本的内核适用于那些期望获得最新的稳定版内核并且不想参与测试开发版或 -者实验版的用户。 - -如果没有2.6.x.y版本内核存在,那么最新的2.6.x版本内核就相当于是当前的稳定 -版内核。 - -2.6.x.y版本由“稳定版”小组(邮件地址)维护,一般隔周发 -布新版本。 - -内核源码中的Documentation/process/stable-kernel-rules.rst文件具体描述了可被稳定 -版内核接受的修改类型以及发布的流程。 - - -2.6.x -mm补丁集 ---------------- -这是由Andrew Morton维护的试验性内核补丁集。Andrew将所有子系统的内核源码 -和补丁拼凑到一起,并且加入了大量从linux-kernel邮件列表中采集的补丁。这个 -源码树是新功能和补丁的试炼场。当补丁在-mm补丁集里证明了其价值以后Andrew -或者相应子系统的维护者会将补丁发给Linus以便集成进主内核源码树。 - -在将所有新补丁发给Linus以集成到主内核源码树之前,我们非常鼓励先把这些补 -丁放在-mm版内核源码树中进行测试。 - -这些内核版本不适合在需要稳定运行的系统上运行,因为运行它们比运行任何其他 -内核分支都更具有风险。 - -如果你想为内核开发进程提供帮助,请尝试并使用这些内核版本,并在 -linux-kernel邮件列表中提供反馈,告诉大家你遇到了问题还是一切正常。 - -通常-mm版补丁集不光包括这些额外的试验性补丁,还包括发布时-git版主源码树 -中的改动。 - --mm版内核没有固定的发布周期,但是通常在每两个-rc版内核发布之间都会有若干 -个-mm版内核发布(一般是1至3个)。 - - -子系统相关内核源码树和补丁集 ----------------------------- -相当一部分内核子系统开发者会公开他们自己的开发源码树,以便其他人能了解内 -核的不同领域正在发生的事情。如上所述,这些源码树会被集成到-mm版本内核中。 - -下面是目前可用的一些内核源码树的列表: - 通过git管理的源码树: - - Kbuild开发源码树, Sam Ravnborg - git.kernel.org:/pub/scm/linux/kernel/git/sam/kbuild.git - - - ACPI开发源码树, Len Brown - git.kernel.org:/pub/scm/linux/kernel/git/lenb/linux-acpi-2.6.git - - - 块设备开发源码树, Jens Axboe - git.kernel.org:/pub/scm/linux/kernel/git/axboe/linux-2.6-block.git - - - DRM开发源码树, Dave Airlie - git.kernel.org:/pub/scm/linux/kernel/git/airlied/drm-2.6.git - - - ia64开发源码树, Tony Luck - git.kernel.org:/pub/scm/linux/kernel/git/aegl/linux-2.6.git - - - ieee1394开发源码树, Jody McIntyre - git.kernel.org:/pub/scm/linux/kernel/git/scjody/ieee1394.git - - - infiniband开发源码树, Roland Dreier - git.kernel.org:/pub/scm/linux/kernel/git/roland/infiniband.git - - - libata开发源码树, Jeff Garzik - git.kernel.org:/pub/scm/linux/kernel/git/jgarzik/libata-dev.git - - - 网络驱动程序开发源码树, Jeff Garzik - git.kernel.org:/pub/scm/linux/kernel/git/jgarzik/netdev-2.6.git - - - pcmcia开发源码树, Dominik Brodowski - git.kernel.org:/pub/scm/linux/kernel/git/brodo/pcmcia-2.6.git - - - SCSI开发源码树, James Bottomley - git.kernel.org:/pub/scm/linux/kernel/git/jejb/scsi-misc-2.6.git - - 使用quilt管理的补丁集: - - USB, PCI, 驱动程序核心和I2C, Greg Kroah-Hartman - kernel.org/pub/linux/kernel/people/gregkh/gregkh-2.6/ - - x86-64, 部分i386, Andi Kleen - ftp.firstfloor.org:/pub/ak/x86_64/quilt/ - - 其他内核源码树可以在http://git.kernel.org的列表中和MAINTAINERS文件里 - 找到。 - -报告bug -------- - -bugzilla.kernel.org是Linux内核开发者们用来跟踪内核Bug的网站。我们鼓励用 -户在这个工具中报告找到的所有bug。如何使用内核bugzilla的细节请访问: - http://test.kernel.org/bugzilla/faq.html - -内核源码主目录中的admin-guide/reporting-bugs.rst文件里有一个很好的模板。它指导用户如何报 -告可能的内核bug以及需要提供哪些信息来帮助内核开发者们找到问题的根源。 - - -利用bug报告 ------------ - -练习内核开发技能的最好办法就是修改其他人报告的bug。你不光可以帮助内核变 -得更加稳定,还可以学会如何解决实际问题从而提高自己的技能,并且让其他开发 -者感受到你的存在。修改bug是赢得其他开发者赞誉的最好办法,因为并不是很多 -人都喜欢浪费时间去修改别人报告的bug。 - -要尝试修改已知的bug,请访问http://bugzilla.kernel.org网址。如果你想获得 -最新bug的通知,可以订阅bugme-new邮件列表(只有新的bug报告会被寄到这里) -或者订阅bugme-janitor邮件列表(所有bugzilla的变动都会被寄到这里)。 - - https://lists.linux-foundation.org/mailman/listinfo/bugme-new - https://lists.linux-foundation.org/mailman/listinfo/bugme-janitors - - -邮件列表 --------- - -正如上面的文档所描述,大多数的骨干内核开发者都加入了Linux Kernel邮件列 -表。如何订阅和退订列表的细节可以在这里找到: - http://vger.kernel.org/vger-lists.html#linux-kernel -网上很多地方都有这个邮件列表的存档(archive)。可以使用搜索引擎来找到这些 -存档。比如: - http://dir.gmane.org/gmane.linux.kernel -在发信之前,我们强烈建议你先在存档中搜索你想要讨论的问题。很多已经被详细 -讨论过的问题只在邮件列表的存档中可以找到。 - -大多数内核子系统也有自己独立的邮件列表来协调各自的开发工作。从 -MAINTAINERS文件中可以找到不同话题对应的邮件列表。 - -很多邮件列表架设在kernel.org服务器上。这些列表的信息可以在这里找到: - http://vger.kernel.org/vger-lists.html - -在使用这些邮件列表时,请记住保持良好的行为习惯。下面的链接提供了与这些列 -表(或任何其它邮件列表)交流的一些简单规则,虽然内容有点滥竽充数。 - http://www.albion.com/netiquette/ - -当有很多人回复你的邮件时,邮件的抄送列表会变得很长。请不要将任何人从抄送 -列表中删除,除非你有足够的理由这么做。也不要只回复到邮件列表。请习惯于同 -一封邮件接收两次(一封来自发送者一封来自邮件列表),而不要试图通过添加一 -些奇特的邮件头来解决这个问题,人们不会喜欢的。 - -记住保留你所回复内容的上下文和源头。在你回复邮件的顶部保留“某某某说到……” -这几行。将你的评论加在被引用的段落之间而不要放在邮件的顶部。 - -如果你在邮件中附带补丁,请确认它们是可以直接阅读的纯文本(如 -Documentation/process/submitting-patches.rst文档中所述)。内核开发者们不希望遇到附件 -或者被压缩了的补丁。只有这样才能保证他们可以直接评论你的每行代码。请确保 -你使用的邮件发送程序不会修改空格和制表符。一个防范性的测试方法是先将邮件 -发送给自己,然后自己尝试是否可以顺利地打上收到的补丁。如果测试不成功,请 -调整或者更换你的邮件发送程序直到它正确工作为止。 - -总而言之,请尊重其他的邮件列表订阅者。 - - -同内核社区合作 ----------------- - -内核社区的目标就是提供尽善尽美的内核。所以当你提交补丁期望被接受进内核的 -时候,它的技术价值以及其他方面都将被评审。那么你可能会得到什么呢? - - 批评 - - 评论 - - 要求修改 - - 要求证明修改的必要性 - - 沉默 - -要记住,这些是把补丁放进内核的正常情况。你必须学会听取对补丁的批评和评论, -从技术层面评估它们,然后要么重写你的补丁要么简明扼要地论证修改是不必要 -的。如果你发的邮件没有得到任何回应,请过几天后再试一次,因为有时信件会湮 -没在茫茫信海中。 - -你不应该做的事情: - - 期望自己的补丁不受任何质疑就直接被接受 - - 翻脸 - - 忽略别人的评论 - - 没有按照别人的要求做任何修改就重新提交 - -在一个努力追寻最好技术方案的社区里,对于一个补丁有多少好处总会有不同的见 -解。你必须要抱着合作的态度,愿意改变自己的观点来适应内核的风格。或者至少 -愿意去证明你的想法是有价值的。记住,犯错误是允许的,只要你愿意朝着正确的 -方案去努力。 - -如果你的第一个补丁换来的是一堆修改建议,这是很正常的。这并不代表你的补丁 -不会被接受,也不意味着有人和你作对。你只需要改正所有提出的问题然后重新发 -送你的补丁。 - -内核社区和公司文化的差异 ------------------------- - -内核社区的工作模式同大多数传统公司开发队伍的工作模式并不相同。下面这些例 -子,可以帮助你避免某些可能发生问题: - 用这些话介绍你的修改提案会有好处: - - 它同时解决了多个问题 - - 它删除了2000行代码 - - 这是补丁,它已经解释了我想要说明的 - - 我在5种不同的体系结构上测试过它…… - - 这是一系列小补丁用来…… - - 这个修改提高了普通机器的性能…… - - 应该避免如下的说法: - - 我们在AIX/ptx/Solaris就是这么做的,所以这么做肯定是好的…… - - 我做这行已经20年了,所以…… - - 为了我们公司赚钱考虑必须这么做 - - 这是我们的企业产品线所需要的 - - 这里是描述我观点的1000页设计文档 - - 这是一个5000行的补丁用来…… - - 我重写了现在乱七八糟的代码,这就是…… - - 我被规定了最后期限,所以这个补丁需要立刻被接受 - -另外一个内核社区与大部分传统公司的软件开发队伍不同的地方是无法面对面地交 -流。使用电子邮件和IRC聊天工具做为主要沟通工具的一个好处是性别和种族歧视 -将会更少。Linux内核的工作环境更能接受妇女和少数族群,因为每个人在别人眼 -里只是一个邮件地址。国际化也帮助了公平的实现,因为你无法通过姓名来判断人 -的性别。男人有可能叫李丽,女人也有可能叫王刚。大多数在Linux内核上工作过 -并表达过看法的女性对在linux上工作的经历都给出了正面的评价。 - -对于一些不习惯使用英语的人来说,语言可能是一个引起问题的障碍。在邮件列表 -中要正确地表达想法必需良好地掌握语言,所以建议你在发送邮件之前最好检查一 -下英文写得是否正确。 - - -拆分修改 --------- - -Linux内核社区并不喜欢一下接收大段的代码。修改需要被恰当地介绍、讨论并且 -拆分成独立的小段。这几乎完全和公司中的习惯背道而驰。你的想法应该在开发最 -开始的阶段就让大家知道,这样你就可以及时获得对你正在进行的开发的反馈。这 -样也会让社区觉得你是在和他们协作,而不是仅仅把他们当作倾销新功能的对象。 -无论如何,你不要一次性地向邮件列表发送50封信,你的补丁序列应该永远用不到 -这么多。 - -将补丁拆开的原因如下: - -1) 小的补丁更有可能被接受,因为它们不需要太多的时间和精力去验证其正确性。 - 一个5行的补丁,可能在维护者看了一眼以后就会被接受。而500行的补丁则 - 需要数个小时来审查其正确性(所需时间随补丁大小增加大约呈指数级增长)。 - - 当出了问题的时候,小的补丁也会让调试变得非常容易。一个一个补丁地回溯 - 将会比仔细剖析一个被打上的大补丁(这个补丁破坏了其他东西)容易得多。 - -2)不光发送小的补丁很重要,在提交之前重新编排、化简(或者仅仅重新排列) - 补丁也是很重要的。 - -这里有内核开发者Al Viro打的一个比方: - “想象一个老师正在给学生批改数学作业。老师并不希望看到学生为了得 - 到正确解法所进行的尝试和产生的错误。他希望看到的是最干净最优雅的 - 解答。好学生了解这点,绝不会把最终解决之前的中间方案提交上去。” - - 内核开发也是这样。维护者和评审者不希望看到一个人在解决问题时的思 - 考过程。他们只希望看到简单和优雅的解决方案。 - -直接给出一流的解决方案,和社区一起协作讨论尚未完成的工作,这两者之间似乎 -很难找到一个平衡点。所以最好尽早开始收集有利于你进行改进的反馈;同时也要 -保证修改分成很多小块,这样在整个项目都准备好被包含进内核之前,其中的一部 -分可能会先被接收。 - -必须了解这样做是不可接受的:试图将未完成的工作提交进内核,然后再找时间修 -复。 - - -证明修改的必要性 ----------------- -除了将补丁拆成小块,很重要的一点是让Linux社区了解他们为什么需要这样修改。 -你必须证明新功能是有人需要的并且是有用的。 - - -记录修改 --------- - -当你发送补丁的时候,需要特别留意邮件正文的内容。因为这里的信息将会做为补 -丁的修改记录(ChangeLog),会被一直保留以备大家查阅。它需要完全地描述补丁, -包括: - - 为什么需要这个修改 - - 补丁的总体设计 - - 实现细节 - - 测试结果 - -想了解它具体应该看起来像什么,请查阅以下文档中的“ChangeLog”章节: - “The Perfect Patch” - http://www.ozlabs.org/~akpm/stuff/tpp.txt - - -这些事情有时候做起来很难。要在任何方面都做到完美可能需要好几年时间。这是 -一个持续提高的过程,它需要大量的耐心和决心。只要不放弃,你一定可以做到。 -很多人已经做到了,而他们都曾经和现在的你站在同样的起点上。 - - ---------------- -感谢Paolo Ciarrocchi允许“开发流程”部分基于他所写的文章 -(http://www.kerneltravel.net/newbie/2.6-development_process),感谢Randy -Dunlap和Gerrit Huizenga完善了应该说和不该说的列表。感谢Pat Mochel, Hanna -Linder, Randy Dunlap, Kay Sievers, Vojtech Pavlik, Jan Kara, Josh Boyer, -Kees Cook, Andrew Morton, Andi Kleen, Vadim Lobanov, Jesper Juhl, Adrian -Bunk, Keri Harris, Frans Pop, David A. Wheeler, Junio Hamano, Michael -Kerrisk和Alex Shepard的评审、建议和贡献。没有他们的帮助,这篇文档是不可 -能完成的。 - - - -英文版维护者: Greg Kroah-Hartman diff --git a/Documentation/translations/zh_CN/SubmittingDrivers b/Documentation/translations/zh_CN/SubmittingDrivers deleted file mode 100644 index 15e73562f710..000000000000 --- a/Documentation/translations/zh_CN/SubmittingDrivers +++ /dev/null @@ -1,164 +0,0 @@ -Chinese translated version of Documentation/process/submitting-drivers.rst - -If you have any comment or update to the content, please contact the -original document maintainer directly. However, if you have a problem -communicating in English you can also ask the Chinese maintainer for -help. Contact the Chinese maintainer if this translation is outdated -or if there is a problem with the translation. - -Chinese maintainer: Li Yang ---------------------------------------------------------------------- -Documentation/process/submitting-drivers.rst 的中文翻译 - -如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 -交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者。 - -中文版维护者: 李阳 Li Yang -中文版翻译者: 李阳 Li Yang -中文版校译者: 陈琦 Maggie Chen - 王聪 Wang Cong - 张巍 Zhang Wei - -以下为正文 ---------------------------------------------------------------------- - -如何向 Linux 内核提交驱动程序 ------------------------------ - -这篇文档将会解释如何向不同的内核源码树提交设备驱动程序。请注意,如果你感 -兴趣的是显卡驱动程序,你也许应该访问 XFree86 项目(http://www.xfree86.org/) -和/或 X.org 项目 (http://x.org)。 - -另请参阅 Documentation/process/submitting-patches.rst 文档。 - - -分配设备号 ----------- - -块设备和字符设备的主设备号与从设备号是由 Linux 命名编号分配权威 LANANA( -现在是 Torben Mathiasen)负责分配。申请的网址是 http://www.lanana.org/。 -即使不准备提交到主流内核的设备驱动也需要在这里分配设备号。有关详细信息, -请参阅 Documentation/admin-guide/devices.rst。 - -如果你使用的不是已经分配的设备号,那么当你提交设备驱动的时候,它将会被强 -制分配一个新的设备号,即便这个设备号和你之前发给客户的截然不同。 - -设备驱动的提交对象 ------------------- - -Linux 2.0: - 此内核源码树不接受新的驱动程序。 - -Linux 2.2: - 此内核源码树不接受新的驱动程序。 - -Linux 2.4: - 如果所属的代码领域在内核的 MAINTAINERS 文件中列有一个总维护者, - 那么请将驱动程序提交给他。如果此维护者没有回应或者你找不到恰当的 - 维护者,那么请联系 Willy Tarreau 。 - -Linux 2.6: - 除了遵循和 2.4 版内核同样的规则外,你还需要在 linux-kernel 邮件 - 列表上跟踪最新的 API 变化。向 Linux 2.6 内核提交驱动的顶级联系人 - 是 Andrew Morton 。 - -决定设备驱动能否被接受的条件 ----------------------------- - -许可: 代码必须使用 GNU 通用公开许可证 (GPL) 提交给 Linux,但是 - 我们并不要求 GPL 是唯一的许可。你或许会希望同时使用多种 - 许可证发布,如果希望驱动程序可以被其他开源社区(比如BSD) - 使用。请参考 include/linux/module.h 文件中所列出的可被 - 接受共存的许可。 - -版权: 版权所有者必须同意使用 GPL 许可。最好提交者和版权所有者 - 是相同个人或实体。否则,必需列出授权使用 GPL 的版权所有 - 人或实体,以备验证之需。 - -接口: 如果你的驱动程序使用现成的接口并且和其他同类的驱动程序行 - 为相似,而不是去发明无谓的新接口,那么它将会更容易被接受。 - 如果你需要一个 Linux 和 NT 的通用驱动接口,那么请在用 - 户空间实现它。 - -代码: 请使用 Documentation/process/coding-style.rst 中所描述的 Linux 代码风 - 格。如果你的某些代码段(例如那些与 Windows 驱动程序包共 - 享的代码段)需要使用其他格式,而你却只希望维护一份代码, - 那么请将它们很好地区分出来,并且注明原因。 - -可移植性: 请注意,指针并不永远是 32 位的,不是所有的计算机都使用小 - 尾模式 (little endian) 存储数据,不是所有的人都拥有浮点 - 单元,不要随便在你的驱动程序里嵌入 x86 汇编指令。只能在 - x86 上运行的驱动程序一般是不受欢迎的。虽然你可能只有 x86 - 硬件,很难测试驱动程序在其他平台上是否可用,但是确保代码 - 可以被轻松地移植却是很简单的。 - -清晰度: 做到所有人都能修补这个驱动程序将会很有好处,因为这样你将 - 会直接收到修复的补丁而不是 bug 报告。如果你提交一个试图 - 隐藏硬件工作机理的驱动程序,那么它将会被扔进废纸篓。 - -电源管理: 因为 Linux 正在被很多移动设备和桌面系统使用,所以你的驱 - 动程序也很有可能被使用在这些设备上。它应该支持最基本的电 - 源管理,即在需要的情况下实现系统级休眠和唤醒要用到的 - .suspend 和 .resume 函数。你应该检查你的驱动程序是否能正 - 确地处理休眠与唤醒,如果实在无法确认,请至少把 .suspend - 函数定义成返回 -ENOSYS(功能未实现)错误。你还应该尝试确 - 保你的驱动在什么都不干的情况下将耗电降到最低。要获得驱动 - 程序测试的指导,请参阅 - Documentation/power/drivers-testing.txt。有关驱动程序电 - 源管理问题相对全面的概述,请参阅 - Documentation/driver-api/pm/devices.rst。 - -管理: 如果一个驱动程序的作者还在进行有效的维护,那么通常除了那 - 些明显正确且不需要任何检查的补丁以外,其他所有的补丁都会 - 被转发给作者。如果你希望成为驱动程序的联系人和更新者,最 - 好在代码注释中写明并且在 MAINTAINERS 文件中加入这个驱动 - 程序的条目。 - -不影响设备驱动能否被接受的条件 ------------------------------- - -供应商: 由硬件供应商来维护驱动程序通常是一件好事。不过,如果源码 - 树里已经有其他人提供了可稳定工作的驱动程序,那么请不要期 - 望“我是供应商”会成为内核改用你的驱动程序的理由。理想的情 - 况是:供应商与现有驱动程序的作者合作,构建一个统一完美的 - 驱动程序。 - -作者: 驱动程序是由大的 Linux 公司研发还是由你个人编写,并不影 - 响其是否能被内核接受。没有人对内核源码树享有特权。只要你 - 充分了解内核社区,你就会发现这一点。 - - -资源列表 --------- - -Linux 内核主源码树: - ftp.??.kernel.org:/pub/linux/kernel/... - ?? == 你的国家代码,例如 "cn"、"us"、"uk"、"fr" 等等 - -Linux 内核邮件列表: - linux-kernel@vger.kernel.org - [可通过向majordomo@vger.kernel.org发邮件来订阅] - -Linux 设备驱动程序,第三版(探讨 2.6.10 版内核): - http://lwn.net/Kernel/LDD3/ (免费版) - -LWN.net: - 每周内核开发活动摘要 - http://lwn.net/ - 2.6 版中 API 的变更: - http://lwn.net/Articles/2.6-kernel-api/ - 将旧版内核的驱动程序移植到 2.6 版: - http://lwn.net/Articles/driver-porting/ - -内核新手(KernelNewbies): - 为新的内核开发者提供文档和帮助 - http://kernelnewbies.org/ - -Linux USB项目: - http://www.linux-usb.org/ - -写内核驱动的“不要”(Arjan van de Ven著): - http://www.fenrus.org/how-to-not-write-a-device-driver-paper.pdf - -内核清洁工 (Kernel Janitor): - http://kernelnewbies.org/KernelJanitors diff --git a/Documentation/translations/zh_CN/SubmittingPatches b/Documentation/translations/zh_CN/SubmittingPatches deleted file mode 100644 index e9098da8f1a4..000000000000 --- a/Documentation/translations/zh_CN/SubmittingPatches +++ /dev/null @@ -1,412 +0,0 @@ -Chinese translated version of Documentation/process/submitting-patches.rst - -If you have any comment or update to the content, please contact the -original document maintainer directly. However, if you have a problem -communicating in English you can also ask the Chinese maintainer for -help. Contact the Chinese maintainer if this translation is outdated -or if there is a problem with the translation. - -Chinese maintainer: TripleX Chung ---------------------------------------------------------------------- -Documentation/process/submitting-patches.rst 的中文翻译 - -如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 -交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者。 - -中文版维护者: 钟宇 TripleX Chung -中文版翻译者: 钟宇 TripleX Chung -中文版校译者: 李阳 Li Yang - 王聪 Wang Cong - -以下为正文 ---------------------------------------------------------------------- - - 如何让你的改动进入内核 - 或者 - 获得亲爱的 Linus Torvalds 的关注和处理 ----------------------------------- - -对于想要将改动提交到 Linux 内核的个人或者公司来说,如果不熟悉“规矩”, -提交的流程会让人畏惧。本文档收集了一系列建议,这些建议可以大大的提高你 -的改动被接受的机会。 -阅读 Documentation/process/submit-checklist.rst 来获得在提交代码前需要检查的项目的列 -表。如果你在提交一个驱动程序,那么同时阅读一下 -Documentation/process/submitting-drivers.rst 。 - - --------------------------- -第一节 - 创建并发送你的改动 --------------------------- - -1) "diff -up" ------------ - -使用 "diff -up" 或者 "diff -uprN" 来创建补丁。 - -所有内核的改动,都是以补丁的形式呈现的,补丁由 diff(1) 生成。创建补丁的 -时候,要确认它是以 "unified diff" 格式创建的,这种格式由 diff(1) 的 '-u' -参数生成。而且,请使用 '-p' 参数,那样会显示每个改动所在的C函数,使得 -产生的补丁容易读得多。补丁应该基于内核源代码树的根目录,而不是里边的任 -何子目录。 -为一个单独的文件创建补丁,一般来说这样做就够了: - - SRCTREE= linux-2.6 - MYFILE= drivers/net/mydriver.c - - cd $SRCTREE - cp $MYFILE $MYFILE.orig - vi $MYFILE # make your change - cd .. - diff -up $SRCTREE/$MYFILE{.orig,} > /tmp/patch - -为多个文件创建补丁,你可以解开一个没有修改过的内核源代码树,然后和你自 -己的代码树之间做 diff 。例如: - - MYSRC= /devel/linux-2.6 - - tar xvfz linux-2.6.12.tar.gz - mv linux-2.6.12 linux-2.6.12-vanilla - diff -uprN -X linux-2.6.12-vanilla/Documentation/dontdiff \ - linux-2.6.12-vanilla $MYSRC > /tmp/patch - -"dontdiff" 是内核在编译的时候产生的文件的列表,列表中的文件在 diff(1) -产生的补丁里会被跳过。"dontdiff" 文件被包含在2.6.12和之后版本的内核源代 -码树中。对于更早的内核版本,你可以从 - 获取它。 -确定你的补丁里没有包含任何不属于这次补丁提交的额外文件。记得在用diff(1) -生成补丁之后,审阅一次补丁,以确保准确。 -如果你的改动很散乱,你应该研究一下如何将补丁分割成独立的部分,将改动分 -割成一系列合乎逻辑的步骤。这样更容易让其他内核开发者审核,如果你想你的 -补丁被接受,这是很重要的。下面这些脚本能够帮助你做这件事情: -Quilt: -http://savannah.nongnu.org/projects/quilt - -2)描述你的改动。 -描述你的改动包含的技术细节。 - -要多具体就写多具体。最糟糕的描述可能是像下面这些语句:“更新了某驱动程 -序”,“修正了某驱动程序的bug”,或者“这个补丁包含了某子系统的修改,请 -使用。” - -如果你的描述开始变长,这表示你也许需要拆分你的补丁了,请看第3小节, -继续。 - -3)拆分你的改动 - -将改动拆分,逻辑类似的放到同一个补丁文件里。 - -例如,如果你的改动里同时有bug修正和性能优化,那么把这些改动拆分到两个或 -者更多的补丁文件中。如果你的改动包含对API的修改,并且修改了驱动程序来适 -应这些新的API,那么把这些修改分成两个补丁。 - -另一方面,如果你将一个单独的改动做成多个补丁文件,那么将它们合并成一个 -单独的补丁文件。这样一个逻辑上单独的改动只被包含在一个补丁文件里。 - -如果有一个补丁依赖另外一个补丁来完成它的改动,那没问题。简单的在你的补 -丁描述里指出“这个补丁依赖某补丁”就好了。 - -如果你不能将补丁浓缩成更少的文件,那么每次大约发送出15个,然后等待审查 -和整合。 - -4)选择 e-mail 的收件人 - -看一遍 MAINTAINERS 文件和源代码,看看你所的改动所在的内核子系统有没有指 -定的维护者。如果有,给他们发e-mail。 - -如果没有找到维护者,或者维护者没有反馈,将你的补丁发送到内核开发者主邮 -件列表 linux-kernel@vger.kernel.org。大部分的内核开发者都跟踪这个邮件列 -表,可以评价你的改动。 - -每次不要发送超过15个补丁到 vger 邮件列表!!! - -Linus Torvalds 是决定改动能否进入 Linux 内核的最终裁决者。他的 e-mail -地址是 。他收到的 e-mail 很多,所以一般 -的说,最好别给他发 e-mail。 - -那些修正bug,“显而易见”的修改或者是类似的只需要很少讨论的补丁可以直接 -发送或者CC给Linus。那些需要讨论或者没有很清楚的好处的补丁,一般先发送到 -linux-kernel邮件列表。只有当补丁被讨论得差不多了,才提交给Linus。 - -5)选择CC( e-mail 抄送)列表 - -除非你有理由不这样做,否则CC linux-kernel@vger.kernel.org。 - -除了 Linus 之外,其他内核开发者也需要注意到你的改动,这样他们才能评论你 -的改动并提供代码审查和建议。linux-kernel 是 Linux 内核开发者主邮件列表 -。其它的邮件列表为特定的子系统提供服务,比如 USB,framebuffer 设备,虚 -拟文件系统,SCSI 子系统,等等。查看 MAINTAINERS 文件来获得和你的改动有 -关的邮件列表。 - -Majordomo lists of VGER.KERNEL.ORG at: - - -如果改动影响了用户空间和内核之间的接口,请给 MAN-PAGES 的维护者(列在 -MAINTAINERS 文件里的)发送一个手册页(man-pages)补丁,或者至少通知一下改 -变,让一些信息有途径进入手册页。 - -即使在第四步的时候,维护者没有作出回应,也要确认在修改他们的代码的时候 -,一直将维护者拷贝到CC列表中。 - -对于小的补丁,你也许会CC到 Adrian Bunk 管理的搜集琐碎补丁的邮件列表 -(Trivial Patch Monkey)trivial@kernel.org,那里专门收集琐碎的补丁。下面这样 -的补丁会被看作“琐碎的”补丁: - 文档的拼写修正。 - 修正会影响到 grep(1) 的拼写。 - 警告信息修正(频繁的打印无用的警告是不好的。) - 编译错误修正(代码逻辑的确是对的,只是编译有问题。) - 运行时修正(只要真的修正了错误。) - 移除使用了被废弃的函数/宏的代码(例如 check_region。) - 联系方式和文档修正。 - 用可移植的代码替换不可移植的代码(即使在体系结构相关的代码中,既然有 - 人拷贝,只要它是琐碎的) - 任何文件的作者/维护者对该文件的改动(例如 patch monkey 在重传模式下) - -EMAIL: trivial@kernel.org - -(译注,关于“琐碎补丁”的一些说明:因为原文的这一部分写得比较简单,所以不得不 -违例写一下译注。"trivial"这个英文单词的本意是“琐碎的,不重要的。”但是在这里 -有稍微有一些变化,例如对一些明显的NULL指针的修正,属于运行时修正,会被归类 -到琐碎补丁里。虽然NULL指针的修正很重要,但是这样的修正往往很小而且很容易得到 -检验,所以也被归入琐碎补丁。琐碎补丁更精确的归类应该是 -“simple, localized & easy to verify”,也就是说简单的,局部的和易于检验的。 -trivial@kernel.org邮件列表的目的是针对这样的补丁,为提交者提供一个中心,来 -降低提交的门槛。) - -6)没有 MIME 编码,没有链接,没有压缩,没有附件,只有纯文本。 - -Linus 和其他的内核开发者需要阅读和评论你提交的改动。对于内核开发者来说 -,可以“引用”你的改动很重要,使用一般的 e-mail 工具,他们就可以在你的 -代码的任何位置添加评论。 - -因为这个原因,所有的提交的补丁都是 e-mail 中“内嵌”的。 -警告:如果你使用剪切-粘贴你的补丁,小心你的编辑器的自动换行功能破坏你的 -补丁。 - -不要将补丁作为 MIME 编码的附件,不管是否压缩。很多流行的 e-mail 软件不 -是任何时候都将 MIME 编码的附件当作纯文本发送的,这会使得别人无法在你的 -代码中加评论。另外,MIME 编码的附件会让 Linus 多花一点时间来处理,这就 -降低了你的改动被接受的可能性。 - -警告:一些邮件软件,比如 Mozilla 会将你的信息以如下格式发送: ----- 邮件头 ---- -Content-Type: text/plain; charset=us-ascii; format=flowed ----- 邮件头 ---- -问题在于 “format=flowed” 会让接收端的某些邮件软件将邮件中的制表符替换 -成空格以及做一些类似的替换。这样,你发送的时候看起来没问题的补丁就被破 -坏了。 - -要修正这个问题,只需要将你的 mozilla 的 defaults/pref/mailnews.js 文件 -里的 -pref("mailnews.send_plaintext_flowed", false); // RFC 2646======= -修改成 -pref("mailnews.display.disable_format_flowed_support", true); -就可以了。 - -7) e-mail 的大小 - -给 Linus 发送补丁的时候,永远按照第6小节说的做。 - -大的改动对邮件列表不合适,对某些维护者也不合适。如果你的补丁,在不压缩 -的情况下,超过了40kB,那么你最好将补丁放在一个能通过 internet 访问的服 -务器上,然后用指向你的补丁的 URL 替代。 - -8) 指出你的内核版本 - -在标题和在补丁的描述中,指出补丁对应的内核的版本,是很重要的。 - -如果补丁不能干净的在最新版本的内核上打上,Linus 是不会接受它的。 - -9) 不要气馁,继续提交。 - -当你提交了改动以后,耐心地等待。如果 Linus 喜欢你的改动并且同意它,那么 -它将在下一个内核发布版本中出现。 - -然而,如果你的改动没有出现在下一个版本的内核中,可能有若干原因。减少那 -些原因,修正错误,重新提交更新后的改动,是你自己的工作。 - -Linus不给出任何评论就“丢弃”你的补丁是常见的事情。在系统中这样的事情很 -平常。如果他没有接受你的补丁,也许是由于以下原因: -* 你的补丁不能在最新版本的内核上干净的打上。 -* 你的补丁在 linux-kernel 邮件列表中没有得到充分的讨论。 -* 风格问题(参照第2小节) -* 邮件格式问题(重读本节) -* 你的改动有技术问题。 -* 他收到了成吨的 e-mail,而你的在混乱中丢失了。 -* 你让人为难。 - -有疑问的时候,在 linux-kernel 邮件列表上请求评论。 - -10) 在标题上加上 PATCH 的字样 - -Linus 和 linux-kernel 邮件列表的 e-mail 流量都很高,一个通常的约定是标 -题行以 [PATCH] 开头。这样可以让 Linus 和其他内核开发人员可以从 e-mail -的讨论中很轻易的将补丁分辨出来。 - -11)为你的工作签名 - -为了加强对谁做了何事的追踪,尤其是对那些透过好几层的维护者的补丁,我们 -建议在发送出去的补丁上加一个 “sign-off” 的过程。 - -"sign-off" 是在补丁的注释的最后的简单的一行文字,认证你编写了它或者其他 -人有权力将它作为开放源代码的补丁传递。规则很简单:如果你能认证如下信息 -: - 开发者来源证书 1.1 - 对于本项目的贡献,我认证如下信息: - (a)这些贡献是完全或者部分的由我创建,我有权利以文件中指出 - 的开放源代码许可证提交它;或者 - (b)这些贡献基于以前的工作,据我所知,这些以前的工作受恰当的开放 - 源代码许可证保护,而且,根据许可证,我有权提交修改后的贡献, - 无论是完全还是部分由我创造,这些贡献都使用同一个开放源代码许可证 - (除非我被允许用其它的许可证),正如文件中指出的;或者 - (c)这些贡献由认证(a),(b)或者(c)的人直接提供给我,而 - 且我没有修改它。 - (d)我理解并同意这个项目和贡献是公开的,贡献的记录(包括我 - 一起提交的个人记录,包括 sign-off )被永久维护并且可以和这个项目 - 或者开放源代码的许可证同步地再发行。 - 那么加入这样一行: - Signed-off-by: Random J Developer - -使用你的真名(抱歉,不能使用假名或者匿名。) - -有人在最后加上标签。现在这些东西会被忽略,但是你可以这样做,来标记公司 -内部的过程,或者只是指出关于 sign-off 的一些特殊细节。 - -12)标准补丁格式 - -标准的补丁,标题行是: - Subject: [PATCH 001/123] 子系统:一句话概述 - -标准补丁的信体存在如下部分: - - - 一个 "from" 行指出补丁作者。 - - - 一个空行 - - - 说明的主体,这些说明文字会被拷贝到描述该补丁的永久改动记录里。 - - - 一个由"---"构成的标记行 - - - 不合适放到改动记录里的额外的注解。 - - - 补丁本身(diff 输出) - -标题行的格式,使得对标题行按字母序排序非常的容易 - 很多 e-mail 客户端都 -可以支持 - 因为序列号是用零填充的,所以按数字排序和按字母排序是一样的。 - -e-mail 标题中的“子系统”标识哪个内核子系统将被打补丁。 - -e-mail 标题中的“一句话概述”扼要的描述 e-mail 中的补丁。“一句话概述” -不应该是一个文件名。对于一个补丁系列(“补丁系列”指一系列的多个相关补 -丁),不要对每个补丁都使用同样的“一句话概述”。 - -记住 e-mail 的“一句话概述”会成为该补丁的全局唯一标识。它会蔓延到 git -的改动记录里。然后“一句话概述”会被用在开发者的讨论里,用来指代这个补 -丁。用户将希望通过 google 来搜索"一句话概述"来找到那些讨论这个补丁的文 -章。 - -一些标题的例子: - - Subject: [patch 2/5] ext2: improve scalability of bitmap searching - Subject: [PATCHv2 001/207] x86: fix eflags tracking - -"from" 行是信体里的最上面一行,具有如下格式: - From: Original Author - -"from" 行指明在永久改动日志里,谁会被确认为作者。如果没有 "from" 行,那 -么邮件头里的 "From: " 行会被用来决定改动日志中的作者。 - -说明的主题将会被提交到永久的源代码改动日志里,因此对那些早已经不记得和 -这个补丁相关的讨论细节的有能力的读者来说,是有意义的。 - -"---" 标记行对于补丁处理工具要找到哪里是改动日志信息的结束,是不可缺少 -的。 - -对于 "---" 标记之后的额外注解,一个好的用途就是用来写 diffstat,用来显 -示修改了什么文件和每个文件都增加和删除了多少行。diffstat 对于比较大的补 -丁特别有用。其余那些只是和时刻或者开发者相关的注解,不合适放到永久的改 -动日志里的,也应该放这里。 -使用 diffstat的选项 "-p 1 -w 70" 这样文件名就会从内核源代码树的目录开始 -,不会占用太宽的空间(很容易适合80列的宽度,也许会有一些缩进。) - -在后面的参考资料中能看到适当的补丁格式的更多细节。 - -------------------------------- -第二节 提示,建议和诀窍 -------------------------------- - -本节包含很多和提交到内核的代码有关的通常的"规则"。事情永远有例外...但是 -你必须真的有好的理由这样做。你可以把本节叫做Linus的计算机科学入门课。 - -1) 读 Document/process/coding-style.rst - -Nuff 说过,如果你的代码和这个偏离太多,那么它有可能会被拒绝,没有更多的 -审查,没有更多的评价。 - -2) #ifdef 是丑陋的 -混杂了 ifdef 的代码难以阅读和维护。别这样做。作为替代,将你的 ifdef 放 -在头文件里,有条件地定义 "static inline" 函数,或者宏,在代码里用这些东 -西。让编译器把那些"空操作"优化掉。 - -一个简单的例子,不好的代码: - - dev = alloc_etherdev (sizeof(struct funky_private)); - if (!dev) - return -ENODEV; - #ifdef CONFIG_NET_FUNKINESS - init_funky_net(dev); - #endif - -清理后的例子: - -(头文件里) - #ifndef CONFIG_NET_FUNKINESS - static inline void init_funky_net (struct net_device *d) {} - #endif - -(代码文件里) - dev = alloc_etherdev (sizeof(struct funky_private)); - if (!dev) - return -ENODEV; - init_funky_net(dev); - -3) 'static inline' 比宏好 - -Static inline 函数相比宏来说,是好得多的选择。Static inline 函数提供了 -类型安全,没有长度限制,没有格式限制,在 gcc 下开销和宏一样小。 - -宏只在 static inline 函数不是最优的时候[在 fast paths 里有很少的独立的 -案例],或者不可能用 static inline 函数的时候[例如字符串分配]。 -应该用 'static inline' 而不是 'static __inline__', 'extern inline' 和 -'extern __inline__' 。 - -4) 不要过度设计 - -不要试图预计模糊的未来事情,这些事情也许有用也许没有用:"让事情尽可能的 -简单,而不是更简单"。 - ----------------- -第三节 参考文献 ----------------- - -Andrew Morton, "The perfect patch" (tpp). - - -Jeff Garzik, "Linux kernel patch submission format". - - -Greg Kroah-Hartman, "How to piss off a kernel subsystem maintainer". - - - - - -NO!!!! No more huge patch bombs to linux-kernel@vger.kernel.org people! - - -Kernel Documentation/process/coding-style.rst: - - -Linus Torvalds's mail on the canonical patch format: - --- diff --git a/Documentation/translations/zh_CN/coding-style.rst b/Documentation/translations/zh_CN/coding-style.rst deleted file mode 100644 index 3cb09803e084..000000000000 --- a/Documentation/translations/zh_CN/coding-style.rst +++ /dev/null @@ -1,967 +0,0 @@ -Chinese translated version of Documentation/process/coding-style.rst - -If you have any comment or update to the content, please post to LKML directly. -However, if you have problem communicating in English you can also ask the -Chinese maintainer for help. Contact the Chinese maintainer, if this -translation is outdated or there is problem with translation. - -Chinese maintainer: Zhang Le - ---------------------------------------------------------------------- - -Documentation/process/coding-style.rst 的中文翻译 - -如果想评论或更新本文的内容,请直接发信到LKML。如果你使用英文交流有困难的话, -也可以向中文版维护者求助。如果本翻译更新不及时或者翻译存在问题,请联系中文版 -维护者:: - - 中文版维护者: 张乐 Zhang Le - 中文版翻译者: 张乐 Zhang Le - 中文版校译者: 王聪 Wang Cong - wheelz - 管旭东 Xudong Guan - Li Zefan - Wang Chen - -以下为正文 - ---------------------------------------------------------------------- - -Linux 内核代码风格 -========================= - -这是一个简短的文档,描述了 linux 内核的首选代码风格。代码风格是因人而异的, -而且我不愿意把自己的观点强加给任何人,但这就像我去做任何事情都必须遵循的原则 -那样,我也希望在绝大多数事上保持这种的态度。请 (在写代码时) 至少考虑一下这里 -的代码风格。 - -首先,我建议你打印一份 GNU 代码规范,然后不要读。烧了它,这是一个具有重大象征 -性意义的动作。 - -不管怎样,现在我们开始: - - -1) 缩进 --------------- - -制表符是 8 个字符,所以缩进也是 8 个字符。有些异端运动试图将缩进变为 4 (甚至 -2!) 字符深,这几乎相当于尝试将圆周率的值定义为 3。 - -理由:缩进的全部意义就在于清楚的定义一个控制块起止于何处。尤其是当你盯着你的 -屏幕连续看了 20 小时之后,你将会发现大一点的缩进会使你更容易分辨缩进。 - -现在,有些人会抱怨 8 个字符的缩进会使代码向右边移动的太远,在 80 个字符的终端 -屏幕上就很难读这样的代码。这个问题的答案是,如果你需要 3 级以上的缩进,不管用 -何种方式你的代码已经有问题了,应该修正你的程序。 - -简而言之,8 个字符的缩进可以让代码更容易阅读,还有一个好处是当你的函数嵌套太 -深的时候可以给你警告。留心这个警告。 - -在 switch 语句中消除多级缩进的首选的方式是让 ``switch`` 和从属于它的 ``case`` -标签对齐于同一列,而不要 ``两次缩进`` ``case`` 标签。比如: - -.. code-block:: c - - switch (suffix) { - case 'G': - case 'g': - mem <<= 30; - break; - case 'M': - case 'm': - mem <<= 20; - break; - case 'K': - case 'k': - mem <<= 10; - /* fall through */ - default: - break; - } - -不要把多个语句放在一行里,除非你有什么东西要隐藏: - -.. code-block:: c - - if (condition) do_this; - do_something_everytime; - -也不要在一行里放多个赋值语句。内核代码风格超级简单。就是避免可能导致别人误读 -的表达式。 - -除了注释、文档和 Kconfig 之外,不要使用空格来缩进,前面的例子是例外,是有意为 -之。 - -选用一个好的编辑器,不要在行尾留空格。 - - -2) 把长的行和字符串打散 ------------------------------- - -代码风格的意义就在于使用平常使用的工具来维持代码的可读性和可维护性。 - -每一行的长度的限制是 80 列,我们强烈建议您遵守这个惯例。 - -长于 80 列的语句要打散成有意义的片段。除非超过 80 列能显著增加可读性,并且不 -会隐藏信息。子片段要明显短于母片段,并明显靠右。这同样适用于有着很长参数列表 -的函数头。然而,绝对不要打散对用户可见的字符串,例如 printk 信息,因为这样就 -很难对它们 grep。 - - -3) 大括号和空格的放置 ------------------------------- - -C 语言风格中另外一个常见问题是大括号的放置。和缩进大小不同,选择或弃用某种放 -置策略并没有多少技术上的原因,不过首选的方式,就像 Kernighan 和 Ritchie 展示 -给我们的,是把起始大括号放在行尾,而把结束大括号放在行首,所以: - -.. code-block:: c - - if (x is true) { - we do y - } - -这适用于所有的非函数语句块 (if, switch, for, while, do)。比如: - -.. code-block:: c - - switch (action) { - case KOBJ_ADD: - return "add"; - case KOBJ_REMOVE: - return "remove"; - case KOBJ_CHANGE: - return "change"; - default: - return NULL; - } - -不过,有一个例外,那就是函数:函数的起始大括号放置于下一行的开头,所以: - -.. code-block:: c - - int function(int x) - { - body of function - } - -全世界的异端可能会抱怨这个不一致性是... 呃... 不一致的,不过所有思维健全的人 -都知道 (a) K&R 是 **正确的** 并且 (b) K&R 是正确的。此外,不管怎样函数都是特 -殊的 (C 函数是不能嵌套的)。 - -注意结束大括号独自占据一行,除非它后面跟着同一个语句的剩余部分,也就是 do 语 -句中的 "while" 或者 if 语句中的 "else",像这样: - -.. code-block:: c - - do { - body of do-loop - } while (condition); - -和 - -.. code-block:: c - - if (x == y) { - .. - } else if (x > y) { - ... - } else { - .... - } - -理由:K&R。 - -也请注意这种大括号的放置方式也能使空 (或者差不多空的) 行的数量最小化,同时不 -失可读性。因此,由于你的屏幕上的新行是不可再生资源 (想想 25 行的终端屏幕),你 -将会有更多的空行来放置注释。 - -当只有一个单独的语句的时候,不用加不必要的大括号。 - -.. code-block:: c - - if (condition) - action(); - -和 - -.. code-block:: c - - if (condition) - do_this(); - else - do_that(); - -这并不适用于只有一个条件分支是单语句的情况;这时所有分支都要使用大括号: - -.. code-block:: c - - if (condition) { - do_this(); - do_that(); - } else { - otherwise(); - } - -3.1) 空格 -******************** - -Linux 内核的空格使用方式 (主要) 取决于它是用于函数还是关键字。(大多数) 关键字 -后要加一个空格。值得注意的例外是 sizeof, typeof, alignof 和 __attribute__,这 -些关键字某些程度上看起来更像函数 (它们在 Linux 里也常常伴随小括号而使用,尽管 -在 C 里这样的小括号不是必需的,就像 ``struct fileinfo info;`` 声明过后的 -``sizeof info``)。 - -所以在这些关键字之后放一个空格:: - - if, switch, case, for, do, while - -但是不要在 sizeof, typeof, alignof 或者 __attribute__ 这些关键字之后放空格。 -例如, - -.. code-block:: c - - s = sizeof(struct file); - -不要在小括号里的表达式两侧加空格。这是一个 **反例** : - -.. code-block:: c - - s = sizeof( struct file ); - -当声明指针类型或者返回指针类型的函数时, ``*`` 的首选使用方式是使之靠近变量名 -或者函数名,而不是靠近类型名。例子: - -.. code-block:: c - - char *linux_banner; - unsigned long long memparse(char *ptr, char **retptr); - char *match_strdup(substring_t *s); - -在大多数二元和三元操作符两侧使用一个空格,例如下面所有这些操作符:: - - = + - < > * / % | & ^ <= >= == != ? : - -但是一元操作符后不要加空格:: - - & * + - ~ ! sizeof typeof alignof __attribute__ defined - -后缀自加和自减一元操作符前不加空格:: - - ++ -- - -前缀自加和自减一元操作符后不加空格:: - - ++ -- - -``.`` 和 ``->`` 结构体成员操作符前后不加空格。 - -不要在行尾留空白。有些可以自动缩进的编辑器会在新行的行首加入适量的空白,然后 -你就可以直接在那一行输入代码。不过假如你最后没有在那一行输入代码,有些编辑器 -就不会移除已经加入的空白,就像你故意留下一个只有空白的行。包含行尾空白的行就 -这样产生了。 - -当 git 发现补丁包含了行尾空白的时候会警告你,并且可以应你的要求去掉行尾空白; -不过如果你是正在打一系列补丁,这样做会导致后面的补丁失败,因为你改变了补丁的 -上下文。 - - -4) 命名 ------------------------------- - -C 是一个简朴的语言,你的命名也应该这样。和 Modula-2 和 Pascal 程序员不同, -C 程序员不使用类似 ThisVariableIsATemporaryCounter 这样华丽的名字。C 程序员会 -称那个变量为 ``tmp`` ,这样写起来会更容易,而且至少不会令其难于理解。 - -不过,虽然混用大小写的名字是不提倡使用的,但是全局变量还是需要一个具描述性的 -名字。称一个全局函数为 ``foo`` 是一个难以饶恕的错误。 - -全局变量 (只有当你 **真正** 需要它们的时候再用它) 需要有一个具描述性的名字,就 -像全局函数。如果你有一个可以计算活动用户数量的函数,你应该叫它 -``count_active_users()`` 或者类似的名字,你不应该叫它 ``cntuser()`` 。 - -在函数名中包含函数类型 (所谓的匈牙利命名法) 是脑子出了问题——编译器知道那些类 -型而且能够检查那些类型,这样做只能把程序员弄糊涂了。难怪微软总是制造出有问题 -的程序。 - -本地变量名应该简短,而且能够表达相关的含义。如果你有一些随机的整数型的循环计 -数器,它应该被称为 ``i`` 。叫它 ``loop_counter`` 并无益处,如果它没有被误解的 -可能的话。类似的, ``tmp`` 可以用来称呼任意类型的临时变量。 - -如果你怕混淆了你的本地变量名,你就遇到另一个问题了,叫做函数增长荷尔蒙失衡综 -合症。请看第六章 (函数)。 - - -5) Typedef ------------ - -不要使用类似 ``vps_t`` 之类的东西。 - -对结构体和指针使用 typedef 是一个 **错误** 。当你在代码里看到: - -.. code-block:: c - - vps_t a; - -这代表什么意思呢? - -相反,如果是这样 - -.. code-block:: c - - struct virtual_container *a; - -你就知道 ``a`` 是什么了。 - -很多人认为 typedef ``能提高可读性`` 。实际不是这样的。它们只在下列情况下有用: - - (a) 完全不透明的对象 (这种情况下要主动使用 typedef 来 **隐藏** 这个对象实际上 - 是什么)。 - - 例如: ``pte_t`` 等不透明对象,你只能用合适的访问函数来访问它们。 - - .. note:: - - 不透明性和 "访问函数" 本身是不好的。我们使用 pte_t 等类型的原因在于真 - 的是完全没有任何共用的可访问信息。 - - (b) 清楚的整数类型,如此,这层抽象就可以 **帮助** 消除到底是 ``int`` 还是 - ``long`` 的混淆。 - - u8/u16/u32 是完全没有问题的 typedef,不过它们更符合类别 (d) 而不是这里。 - - .. note:: - - 要这样做,必须事出有因。如果某个变量是 ``unsigned long`` ,那么没有必要 - - typedef unsigned long myflags_t; - - 不过如果有一个明确的原因,比如它在某种情况下可能会是一个 ``unsigned int`` - 而在其他情况下可能为 ``unsigned long`` ,那么就不要犹豫,请务必使用 - typedef。 - - (c) 当你使用 sparse 按字面的创建一个 **新** 类型来做类型检查的时候。 - - (d) 和标准 C99 类型相同的类型,在某些例外的情况下。 - - 虽然让眼睛和脑筋来适应新的标准类型比如 ``uint32_t`` 不需要花很多时间,可 - 是有些人仍然拒绝使用它们。 - - 因此,Linux 特有的等同于标准类型的 ``u8/u16/u32/u64`` 类型和它们的有符号 - 类型是被允许的——尽管在你自己的新代码中,它们不是强制要求要使用的。 - - 当编辑已经使用了某个类型集的已有代码时,你应该遵循那些代码中已经做出的选 - 择。 - - (e) 可以在用户空间安全使用的类型。 - - 在某些用户空间可见的结构体里,我们不能要求 C99 类型而且不能用上面提到的 - ``u32`` 类型。因此,我们在与用户空间共享的所有结构体中使用 __u32 和类似 - 的类型。 - -可能还有其他的情况,不过基本的规则是 **永远不要** 使用 typedef,除非你可以明 -确的应用上述某个规则中的一个。 - -总的来说,如果一个指针或者一个结构体里的元素可以合理的被直接访问到,那么它们 -就不应该是一个 typedef。 - - -6) 函数 ------------------------------- - -函数应该简短而漂亮,并且只完成一件事情。函数应该可以一屏或者两屏显示完 (我们 -都知道 ISO/ANSI 屏幕大小是 80x24),只做一件事情,而且把它做好。 - -一个函数的最大长度是和该函数的复杂度和缩进级数成反比的。所以,如果你有一个理 -论上很简单的只有一个很长 (但是简单) 的 case 语句的函数,而且你需要在每个 case -里做很多很小的事情,这样的函数尽管很长,但也是可以的。 - -不过,如果你有一个复杂的函数,而且你怀疑一个天分不是很高的高中一年级学生可能 -甚至搞不清楚这个函数的目的,你应该严格遵守前面提到的长度限制。使用辅助函数, -并为之取个具描述性的名字 (如果你觉得它们的性能很重要的话,可以让编译器内联它 -们,这样的效果往往会比你写一个复杂函数的效果要好。) - -函数的另外一个衡量标准是本地变量的数量。此数量不应超过 5-10 个,否则你的函数 -就有问题了。重新考虑一下你的函数,把它分拆成更小的函数。人的大脑一般可以轻松 -的同时跟踪 7 个不同的事物,如果再增多的话,就会糊涂了。即便你聪颖过人,你也可 -能会记不清你 2 个星期前做过的事情。 - -在源文件里,使用空行隔开不同的函数。如果该函数需要被导出,它的 **EXPORT** 宏 -应该紧贴在它的结束大括号之下。比如: - -.. code-block:: c - - int system_is_up(void) - { - return system_state == SYSTEM_RUNNING; - } - EXPORT_SYMBOL(system_is_up); - -在函数原型中,包含函数名和它们的数据类型。虽然 C 语言里没有这样的要求,在 -Linux 里这是提倡的做法,因为这样可以很简单的给读者提供更多的有价值的信息。 - - -7) 集中的函数退出途径 ------------------------------- - -虽然被某些人声称已经过时,但是 goto 语句的等价物还是经常被编译器所使用,具体 -形式是无条件跳转指令。 - -当一个函数从多个位置退出,并且需要做一些类似清理的常见操作时,goto 语句就很方 -便了。如果并不需要清理操作,那么直接 return 即可。 - -选择一个能够说明 goto 行为或它为何存在的标签名。如果 goto 要释放 ``buffer``, -一个不错的名字可以是 ``out_free_buffer:`` 。别去使用像 ``err1:`` 和 ``err2:`` -这样的GW_BASIC 名称,因为一旦你添加或删除了 (函数的) 退出路径,你就必须对它们 -重新编号,这样会难以去检验正确性。 - -使用 goto 的理由是: - -- 无条件语句容易理解和跟踪 -- 嵌套程度减小 -- 可以避免由于修改时忘记更新个别的退出点而导致错误 -- 让编译器省去删除冗余代码的工作 ;) - -.. code-block:: c - - int fun(int a) - { - int result = 0; - char *buffer; - - buffer = kmalloc(SIZE, GFP_KERNEL); - if (!buffer) - return -ENOMEM; - - if (condition1) { - while (loop1) { - ... - } - result = 1; - goto out_free_buffer; - } - ... - out_free_buffer: - kfree(buffer); - return result; - } - -一个需要注意的常见错误是 ``一个 err 错误`` ,就像这样: - -.. code-block:: c - - err: - kfree(foo->bar); - kfree(foo); - return ret; - -这段代码的错误是,在某些退出路径上 ``foo`` 是 NULL。通常情况下,通过把它分离 -成两个错误标签 ``err_free_bar:`` 和 ``err_free_foo:`` 来修复这个错误: - -.. code-block:: c - - err_free_bar: - kfree(foo->bar); - err_free_foo: - kfree(foo); - return ret; - -理想情况下,你应该模拟错误来测试所有退出路径。 - - -8) 注释 ------------------------------- - -注释是好的,不过有过度注释的危险。永远不要在注释里解释你的代码是如何运作的: -更好的做法是让别人一看你的代码就可以明白,解释写的很差的代码是浪费时间。 - -一般的,你想要你的注释告诉别人你的代码做了什么,而不是怎么做的。也请你不要把 -注释放在一个函数体内部:如果函数复杂到你需要独立的注释其中的一部分,你很可能 -需要回到第六章看一看。你可以做一些小注释来注明或警告某些很聪明 (或者槽糕) 的 -做法,但不要加太多。你应该做的,是把注释放在函数的头部,告诉人们它做了什么, -也可以加上它做这些事情的原因。 - -当注释内核 API 函数时,请使用 kernel-doc 格式。请看 -Documentation/doc-guide/ 和 scripts/kernel-doc 以获得详细信息。 - -长 (多行) 注释的首选风格是: - -.. code-block:: c - - /* - * This is the preferred style for multi-line - * comments in the Linux kernel source code. - * Please use it consistently. - * - * Description: A column of asterisks on the left side, - * with beginning and ending almost-blank lines. - */ - -对于在 net/ 和 drivers/net/ 的文件,首选的长 (多行) 注释风格有些不同。 - -.. code-block:: c - - /* The preferred comment style for files in net/ and drivers/net - * looks like this. - * - * It is nearly the same as the generally preferred comment style, - * but there is no initial almost-blank line. - */ - -注释数据也是很重要的,不管是基本类型还是衍生类型。为了方便实现这一点,每一行 -应只声明一个数据 (不要使用逗号来一次声明多个数据)。这样你就有空间来为每个数据 -写一段小注释来解释它们的用途了。 - - -9) 你已经把事情弄糟了 ------------------------------- - -这没什么,我们都是这样。可能你的使用了很长时间 Unix 的朋友已经告诉你 -``GNU emacs`` 能自动帮你格式化 C 源代码,而且你也注意到了,确实是这样,不过它 -所使用的默认值和我们想要的相去甚远 (实际上,甚至比随机打的还要差——无数个猴子 -在 GNU emacs 里打字永远不会创造出一个好程序) (译注:Infinite Monkey Theorem) - -所以你要么放弃 GNU emacs,要么改变它让它使用更合理的设定。要采用后一个方案, -你可以把下面这段粘贴到你的 .emacs 文件里。 - -.. code-block:: none - - (defun c-lineup-arglist-tabs-only (ignored) - "Line up argument lists by tabs, not spaces" - (let* ((anchor (c-langelem-pos c-syntactic-element)) - (column (c-langelem-2nd-pos c-syntactic-element)) - (offset (- (1+ column) anchor)) - (steps (floor offset c-basic-offset))) - (* (max steps 1) - c-basic-offset))) - - (dir-locals-set-class-variables - 'linux-kernel - '((c-mode . ( - (c-basic-offset . 8) - (c-label-minimum-indentation . 0) - (c-offsets-alist . ( - (arglist-close . c-lineup-arglist-tabs-only) - (arglist-cont-nonempty . - (c-lineup-gcc-asm-reg c-lineup-arglist-tabs-only)) - (arglist-intro . +) - (brace-list-intro . +) - (c . c-lineup-C-comments) - (case-label . 0) - (comment-intro . c-lineup-comment) - (cpp-define-intro . +) - (cpp-macro . -1000) - (cpp-macro-cont . +) - (defun-block-intro . +) - (else-clause . 0) - (func-decl-cont . +) - (inclass . +) - (inher-cont . c-lineup-multi-inher) - (knr-argdecl-intro . 0) - (label . -1000) - (statement . 0) - (statement-block-intro . +) - (statement-case-intro . +) - (statement-cont . +) - (substatement . +) - )) - (indent-tabs-mode . t) - (show-trailing-whitespace . t) - )))) - - (dir-locals-set-directory-class - (expand-file-name "~/src/linux-trees") - 'linux-kernel) - -这会让 emacs 在 ``~/src/linux-trees`` 下的 C 源文件获得更好的内核代码风格。 - -不过就算你尝试让 emacs 正确的格式化代码失败了,也并不意味着你失去了一切:还可 -以用 ``indent`` 。 - -不过,GNU indent 也有和 GNU emacs 一样有问题的设定,所以你需要给它一些命令选 -项。不过,这还不算太糟糕,因为就算是 GNU indent 的作者也认同 K&R 的权威性 -(GNU 的人并不是坏人,他们只是在这个问题上被严重的误导了),所以你只要给 indent -指定选项 ``-kr -i8`` (代表 ``K&R,8 字符缩进``),或使用 ``scripts/Lindent`` -这样就可以以最时髦的方式缩进源代码。 - -``indent`` 有很多选项,特别是重新格式化注释的时候,你可能需要看一下它的手册。 -不过记住: ``indent`` 不能修正坏的编程习惯。 - - -10) Kconfig 配置文件 ------------------------------- - -对于遍布源码树的所有 Kconfig* 配置文件来说,它们缩进方式有所不同。紧挨着 -``config`` 定义的行,用一个制表符缩进,然而 help 信息的缩进则额外增加 2 个空 -格。举个例子:: - - config AUDIT - bool "Auditing support" - depends on NET - help - Enable auditing infrastructure that can be used with another - kernel subsystem, such as SELinux (which requires this for - logging of avc messages output). Does not do system-call - auditing without CONFIG_AUDITSYSCALL. - -而那些危险的功能 (比如某些文件系统的写支持) 应该在它们的提示字符串里显著的声 -明这一点:: - - config ADFS_FS_RW - bool "ADFS write support (DANGEROUS)" - depends on ADFS_FS - ... - -要查看配置文件的完整文档,请看 Documentation/kbuild/kconfig-language.txt。 - - -11) 数据结构 ------------------------------- - -如果一个数据结构,在创建和销毁它的单线执行环境之外可见,那么它必须要有一个引 -用计数器。内核里没有垃圾收集 (并且内核之外的垃圾收集慢且效率低下),这意味着你 -绝对需要记录你对这种数据结构的使用情况。 - -引用计数意味着你能够避免上锁,并且允许多个用户并行访问这个数据结构——而不需要 -担心这个数据结构仅仅因为暂时不被使用就消失了,那些用户可能不过是沉睡了一阵或 -者做了一些其他事情而已。 - -注意上锁 **不能** 取代引用计数。上锁是为了保持数据结构的一致性,而引用计数是一 -个内存管理技巧。通常二者都需要,不要把两个搞混了。 - -很多数据结构实际上有 2 级引用计数,它们通常有不同 ``类`` 的用户。子类计数器统 -计子类用户的数量,每当子类计数器减至零时,全局计数器减一。 - -这种 ``多级引用计数`` 的例子可以在内存管理 (``struct mm_struct``: mm_users 和 -mm_count),和文件系统 (``struct super_block``: s_count 和 s_active) 中找到。 - -记住:如果另一个执行线索可以找到你的数据结构,但这个数据结构没有引用计数器, -这里几乎肯定是一个 bug。 - - -12) 宏,枚举和RTL ------------------------------- - -用于定义常量的宏的名字及枚举里的标签需要大写。 - -.. code-block:: c - - #define CONSTANT 0x12345 - -在定义几个相关的常量时,最好用枚举。 - -宏的名字请用大写字母,不过形如函数的宏的名字可以用小写字母。 - -一般的,如果能写成内联函数就不要写成像函数的宏。 - -含有多个语句的宏应该被包含在一个 do-while 代码块里: - -.. code-block:: c - - #define macrofun(a, b, c) \ - do { \ - if (a == 5) \ - do_this(b, c); \ - } while (0) - -使用宏的时候应避免的事情: - -1) 影响控制流程的宏: - -.. code-block:: c - - #define FOO(x) \ - do { \ - if (blah(x) < 0) \ - return -EBUGGERED; \ - } while (0) - -**非常** 不好。它看起来像一个函数,不过却能导致 ``调用`` 它的函数退出;不要打 -乱读者大脑里的语法分析器。 - -2) 依赖于一个固定名字的本地变量的宏: - -.. code-block:: c - - #define FOO(val) bar(index, val) - -可能看起来像是个不错的东西,不过它非常容易把读代码的人搞糊涂,而且容易导致看起 -来不相关的改动带来错误。 - -3) 作为左值的带参数的宏: FOO(x) = y;如果有人把 FOO 变成一个内联函数的话,这 - 种用法就会出错了。 - -4) 忘记了优先级:使用表达式定义常量的宏必须将表达式置于一对小括号之内。带参数 - 的宏也要注意此类问题。 - -.. code-block:: c - - #define CONSTANT 0x4000 - #define CONSTEXP (CONSTANT | 3) - -5) 在宏里定义类似函数的本地变量时命名冲突: - -.. code-block:: c - - #define FOO(x) \ - ({ \ - typeof(x) ret; \ - ret = calc_ret(x); \ - (ret); \ - }) - -ret 是本地变量的通用名字 - __foo_ret 更不容易与一个已存在的变量冲突。 - -cpp 手册对宏的讲解很详细。gcc internals 手册也详细讲解了 RTL,内核里的汇编语 -言经常用到它。 - - -13) 打印内核消息 ------------------------------- - -内核开发者应该是受过良好教育的。请一定注意内核信息的拼写,以给人以好的印象。 -不要用不规范的单词比如 ``dont``,而要用 ``do not`` 或者 ``don't`` 。保证这些信 -息简单明了,无歧义。 - -内核信息不必以英文句号结束。 - -在小括号里打印数字 (%d) 没有任何价值,应该避免这样做。 - - 里有一些驱动模型诊断宏,你应该使用它们,以确保信息对应于正确 -的设备和驱动,并且被标记了正确的消息级别。这些宏有:dev_err(), dev_warn(), -dev_info() 等等。对于那些不和某个特定设备相关连的信息, 定义 -了 pr_notice(), pr_info(), pr_warn(), pr_err() 和其他。 - -写出好的调试信息可以是一个很大的挑战;一旦你写出后,这些信息在远程除错时能提 -供极大的帮助。然而打印调试信息的处理方式同打印非调试信息不同。其他 pr_XXX() -函数能无条件地打印,pr_debug() 却不;默认情况下它不会被编译,除非定义了 DEBUG -或设定了 CONFIG_DYNAMIC_DEBUG。实际这同样是为了 dev_dbg(),一个相关约定是在一 -个已经开启了 DEBUG 时,使用 VERBOSE_DEBUG 来添加 dev_vdbg()。 - -许多子系统拥有 Kconfig 调试选项来开启 -DDEBUG 在对应的 Makefile 里面;在其他 -情况下,特殊文件使用 #define DEBUG。当一条调试信息需要被无条件打印时,例如, -如果已经包含一个调试相关的 #ifdef 条件,printk(KERN_DEBUG ...) 就可被使用。 - - -14) 分配内存 ------------------------------- - -内核提供了下面的一般用途的内存分配函数: -kmalloc(), kzalloc(), kmalloc_array(), kcalloc(), vmalloc() 和 vzalloc()。 -请参考 API 文档以获取有关它们的详细信息。 - -传递结构体大小的首选形式是这样的: - -.. code-block:: c - - p = kmalloc(sizeof(*p), ...); - -另外一种传递方式中,sizeof 的操作数是结构体的名字,这样会降低可读性,并且可能 -会引入 bug。有可能指针变量类型被改变时,而对应的传递给内存分配函数的 sizeof -的结果不变。 - -强制转换一个 void 指针返回值是多余的。C 语言本身保证了从 void 指针到其他任何 -指针类型的转换是没有问题的。 - -分配一个数组的首选形式是这样的: - -.. code-block:: c - - p = kmalloc_array(n, sizeof(...), ...); - -分配一个零长数组的首选形式是这样的: - -.. code-block:: c - - p = kcalloc(n, sizeof(...), ...); - -两种形式检查分配大小 n * sizeof(...) 的溢出,如果溢出返回 NULL。 - - -15) 内联弊病 ------------------------------- - -有一个常见的误解是 ``内联`` 是 gcc 提供的可以让代码运行更快的一个选项。虽然使 -用内联函数有时候是恰当的 (比如作为一种替代宏的方式,请看第十二章),不过很多情 -况下不是这样。inline 的过度使用会使内核变大,从而使整个系统运行速度变慢。 -因为体积大内核会占用更多的指令高速缓存,而且会导致 pagecache 的可用内存减少。 -想象一下,一次 pagecache 未命中就会导致一次磁盘寻址,将耗时 5 毫秒。5 毫秒的 -时间内 CPU 能执行很多很多指令。 - -一个基本的原则是如果一个函数有 3 行以上,就不要把它变成内联函数。这个原则的一 -个例外是,如果你知道某个参数是一个编译时常量,而且因为这个常量你确定编译器在 -编译时能优化掉你的函数的大部分代码,那仍然可以给它加上 inline 关键字。 -kmalloc() 内联函数就是一个很好的例子。 - -人们经常主张给 static 的而且只用了一次的函数加上 inline,如此不会有任何损失, -因为没有什么好权衡的。虽然从技术上说这是正确的,但是实际上这种情况下即使不加 -inline gcc 也可以自动使其内联。而且其他用户可能会要求移除 inline,由此而来的 -争论会抵消 inline 自身的潜在价值,得不偿失。 - - -16) 函数返回值及命名 ------------------------------- - -函数可以返回多种不同类型的值,最常见的一种是表明函数执行成功或者失败的值。这样 -的一个值可以表示为一个错误代码整数 (-Exxx=失败,0=成功) 或者一个 ``成功`` -布尔值 (0=失败,非0=成功)。 - -混合使用这两种表达方式是难于发现的 bug 的来源。如果 C 语言本身严格区分整形和 -布尔型变量,那么编译器就能够帮我们发现这些错误... 不过 C 语言不区分。为了避免 -产生这种 bug,请遵循下面的惯例:: - - 如果函数的名字是一个动作或者强制性的命令,那么这个函数应该返回错误代 - 码整数。如果是一个判断,那么函数应该返回一个 "成功" 布尔值。 - -比如, ``add work`` 是一个命令,所以 add_work() 在成功时返回 0,在失败时返回 --EBUSY。类似的,因为 ``PCI device present`` 是一个判断,所以 pci_dev_present() -在成功找到一个匹配的设备时应该返回 1,如果找不到时应该返回 0。 - -所有 EXPORTed 函数都必须遵守这个惯例,所有的公共函数也都应该如此。私有 -(static) 函数不需要如此,但是我们也推荐这样做。 - -返回值是实际计算结果而不是计算是否成功的标志的函数不受此惯例的限制。一般的, -他们通过返回一些正常值范围之外的结果来表示出错。典型的例子是返回指针的函数, -他们使用 NULL 或者 ERR_PTR 机制来报告错误。 - - -17) 不要重新发明内核宏 ------------------------------- - -头文件 include/linux/kernel.h 包含了一些宏,你应该使用它们,而不要自己写一些 -它们的变种。比如,如果你需要计算一个数组的长度,使用这个宏 - -.. code-block:: c - - #define ARRAY_SIZE(x) (sizeof(x) / sizeof((x)[0])) - -类似的,如果你要计算某结构体成员的大小,使用 - -.. code-block:: c - - #define FIELD_SIZEOF(t, f) (sizeof(((t*)0)->f)) - -还有可以做严格的类型检查的 min() 和 max() 宏,如果你需要可以使用它们。你可以 -自己看看那个头文件里还定义了什么你可以拿来用的东西,如果有定义的话,你就不应 -在你的代码里自己重新定义。 - - -18) 编辑器模式行和其他需要罗嗦的事情 --------------------------------------------------- - -有一些编辑器可以解释嵌入在源文件里的由一些特殊标记标明的配置信息。比如,emacs -能够解释被标记成这样的行: - -.. code-block:: c - - -*- mode: c -*- - -或者这样的: - -.. code-block:: c - - /* - Local Variables: - compile-command: "gcc -DMAGIC_DEBUG_FLAG foo.c" - End: - */ - -Vim 能够解释这样的标记: - -.. code-block:: c - - /* vim:set sw=8 noet */ - -不要在源代码中包含任何这样的内容。每个人都有他自己的编辑器配置,你的源文件不 -应该覆盖别人的配置。这包括有关缩进和模式配置的标记。人们可以使用他们自己定制 -的模式,或者使用其他可以产生正确的缩进的巧妙方法。 - - -19) 内联汇编 ------------------------------- - -在特定架构的代码中,你可能需要内联汇编与 CPU 和平台相关功能连接。需要这么做时 -就不要犹豫。然而,当 C 可以完成工作时,不要平白无故地使用内联汇编。在可能的情 -况下,你可以并且应该用 C 和硬件沟通。 - -请考虑去写捆绑通用位元 (wrap common bits) 的内联汇编的简单辅助函数,别去重复 -地写下只有细微差异内联汇编。记住内联汇编可以使用 C 参数。 - -大型,有一定复杂度的汇编函数应该放在 .S 文件内,用相应的 C 原型定义在 C 头文 -件中。汇编函数的 C 原型应该使用 ``asmlinkage`` 。 - -你可能需要把汇编语句标记为 volatile,用来阻止 GCC 在没发现任何副作用后就把它 -移除了。你不必总是这样做,尽管,这不必要的举动会限制优化。 - -在写一个包含多条指令的单个内联汇编语句时,把每条指令用引号分割而且各占一行, -除了最后一条指令外,在每个指令结尾加上 \n\t,让汇编输出时可以正确地缩进下一条 -指令: - -.. code-block:: c - - asm ("magic %reg1, #42\n\t" - "more_magic %reg2, %reg3" - : /* outputs */ : /* inputs */ : /* clobbers */); - - -20) 条件编译 ------------------------------- - -只要可能,就不要在 .c 文件里面使用预处理条件 (#if, #ifdef);这样做让代码更难 -阅读并且更难去跟踪逻辑。替代方案是,在头文件中用预处理条件提供给那些 .c 文件 -使用,再给 #else 提供一个空桩 (no-op stub) 版本,然后在 .c 文件内无条件地调用 -那些 (定义在头文件内的) 函数。这样做,编译器会避免为桩函数 (stub) 的调用生成 -任何代码,产生的结果是相同的,但逻辑将更加清晰。 - -最好倾向于编译整个函数,而不是函数的一部分或表达式的一部分。与其放一个 ifdef -在表达式内,不如分解出部分或全部表达式,放进一个单独的辅助函数,并应用预处理 -条件到这个辅助函数内。 - -如果你有一个在特定配置中,可能变成未使用的函数或变量,编译器会警告它定义了但 -未使用,把它标记为 __maybe_unused 而不是将它包含在一个预处理条件中。(然而,如 -果一个函数或变量总是未使用,就直接删除它。) - -在代码中,尽可能地使用 IS_ENABLED 宏来转化某个 Kconfig 标记为 C 的布尔 -表达式,并在一般的 C 条件中使用它: - -.. code-block:: c - - if (IS_ENABLED(CONFIG_SOMETHING)) { - ... - } - -编译器会做常量折叠,然后就像使用 #ifdef 那样去包含或排除代码块,所以这不会带 -来任何运行时开销。然而,这种方法依旧允许 C 编译器查看块内的代码,并检查它的正 -确性 (语法,类型,符号引用,等等)。因此,如果条件不满足,代码块内的引用符号就 -不存在时,你还是必须去用 #ifdef。 - -在任何有意义的 #if 或 #ifdef 块的末尾 (超过几行的),在 #endif 同一行的后面写下 -注解,注释这个条件表达式。例如: - -.. code-block:: c - - #ifdef CONFIG_SOMETHING - ... - #endif /* CONFIG_SOMETHING */ - - -附录 I) 参考 -------------------- - -The C Programming Language, 第二版 -作者:Brian W. Kernighan 和 Denni M. Ritchie. -Prentice Hall, Inc., 1988. -ISBN 0-13-110362-8 (软皮), 0-13-110370-9 (硬皮). - -The Practice of Programming -作者:Brian W. Kernighan 和 Rob Pike. -Addison-Wesley, Inc., 1999. -ISBN 0-201-61586-X. - -GNU 手册 - 遵循 K&R 标准和此文本 - cpp, gcc, gcc internals and indent, -都可以从 http://www.gnu.org/manual/ 找到 - -WG14 是 C 语言的国际标准化工作组,URL: http://www.open-std.org/JTC1/SC22/WG14/ - -Kernel process/coding-style.rst,作者 greg@kroah.com 发表于 OLS 2002: -http://www.kroah.com/linux/talks/ols_2002_kernel_codingstyle_talk/html/ diff --git a/Documentation/translations/zh_CN/email-clients.txt b/Documentation/translations/zh_CN/email-clients.txt deleted file mode 100644 index ec31d97e8d0e..000000000000 --- a/Documentation/translations/zh_CN/email-clients.txt +++ /dev/null @@ -1,210 +0,0 @@ -Chinese translated version of Documentation/process/email-clients.rst - -If you have any comment or update to the content, please contact the -original document maintainer directly. However, if you have a problem -communicating in English you can also ask the Chinese maintainer for -help. Contact the Chinese maintainer if this translation is outdated -or if there is a problem with the translation. - -Chinese maintainer: Harry Wei ---------------------------------------------------------------------- -Documentation/process/email-clients.rst 的中文翻译 - -如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 -交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者。 - -中文版维护者: 贾威威 Harry Wei -中文版翻译者: 贾威威 Harry Wei -中文版校译者: Yinglin Luan - Xiaochen Wang - yaxinsn - -以下为正文 ---------------------------------------------------------------------- - -Linux邮件客户端配置信息 -====================================================================== - -普通配置 ----------------------------------------------------------------------- -Linux内核补丁是通过邮件被提交的,最好把补丁作为邮件体的内嵌文本。有些维护者 -接收附件,但是附件的内容格式应该是"text/plain"。然而,附件一般是不赞成的, -因为这会使补丁的引用部分在评论过程中变的很困难。 - -用来发送Linux内核补丁的邮件客户端在发送补丁时应该处于文本的原始状态。例如, -他们不能改变或者删除制表符或者空格,甚至是在每一行的开头或者结尾。 - -不要通过"format=flowed"模式发送补丁。这样会引起不可预期以及有害的断行。 - -不要让你的邮件客户端进行自动换行。这样也会破坏你的补丁。 - -邮件客户端不能改变文本的字符集编码方式。要发送的补丁只能是ASCII或者UTF-8编码方式, -如果你使用UTF-8编码方式发送邮件,那么你将会避免一些可能发生的字符集问题。 - -邮件客户端应该形成并且保持 References: 或者 In-Reply-To: 标题,那么 -邮件话题就不会中断。 - -复制粘帖(或者剪贴粘帖)通常不能用于补丁,因为制表符会转换为空格。使用xclipboard, xclip -或者xcutsel也许可以,但是最好测试一下或者避免使用复制粘帖。 - -不要在使用PGP/GPG署名的邮件中包含补丁。这样会使得很多脚本不能读取和适用于你的补丁。 -(这个问题应该是可以修复的) - -在给内核邮件列表发送补丁之前,给自己发送一个补丁是个不错的主意,保存接收到的 -邮件,将补丁用'patch'命令打上,如果成功了,再给内核邮件列表发送。 - - -一些邮件客户端提示 ----------------------------------------------------------------------- -这里给出一些详细的MUA配置提示,可以用于给Linux内核发送补丁。这些并不意味是 -所有的软件包配置总结。 - -说明: -TUI = 以文本为基础的用户接口 -GUI = 图形界面用户接口 - -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -Alpine (TUI) - -配置选项: -在"Sending Preferences"部分: - -- "Do Not Send Flowed Text"必须开启 -- "Strip Whitespace Before Sending"必须关闭 - -当写邮件时,光标应该放在补丁会出现的地方,然后按下CTRL-R组合键,使指定的 -补丁文件嵌入到邮件中。 - -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -Evolution (GUI) - -一些开发者成功的使用它发送补丁 - -当选择邮件选项:Preformat - 从Format->Heading->Preformatted (Ctrl-7)或者工具栏 - -然后使用: - Insert->Text File... (Alt-n x)插入补丁文件。 - -你还可以"diff -Nru old.c new.c | xclip",选择Preformat,然后使用中间键进行粘帖。 - -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -Kmail (GUI) - -一些开发者成功的使用它发送补丁。 - -默认设置不为HTML格式是合适的;不要启用它。 - -当书写一封邮件的时候,在选项下面不要选择自动换行。唯一的缺点就是你在邮件中输入的任何文本 -都不会被自动换行,因此你必须在发送补丁之前手动换行。最简单的方法就是启用自动换行来书写邮件, -然后把它保存为草稿。一旦你在草稿中再次打开它,它已经全部自动换行了,那么你的邮件虽然没有 -选择自动换行,但是还不会失去已有的自动换行。 - -在邮件的底部,插入补丁之前,放上常用的补丁定界符:三个连字号(---)。 - -然后在"Message"菜单条目,选择插入文件,接着选取你的补丁文件。还有一个额外的选项,你可以 -通过它配置你的邮件建立工具栏菜单,还可以带上"insert file"图标。 - -你可以安全地通过GPG标记附件,但是内嵌补丁最好不要使用GPG标记它们。作为内嵌文本的签发补丁, -当从GPG中提取7位编码时会使他们变的更加复杂。 - -如果你非要以附件的形式发送补丁,那么就右键点击附件,然后选中属性,突出"Suggest automatic -display",这样内嵌附件更容易让读者看到。 - -当你要保存将要发送的内嵌文本补丁,你可以从消息列表窗格选择包含补丁的邮件,然后右击选择 -"save as"。你可以使用一个没有更改的包含补丁的邮件,如果它是以正确的形式组成。当你正真在它 -自己的窗口之下察看,那时没有选项可以保存邮件--已经有一个这样的bug被汇报到了kmail的bugzilla -并且希望这将会被处理。邮件是以只针对某个用户可读写的权限被保存的,所以如果你想把邮件复制到其他地方, -你不得不把他们的权限改为组或者整体可读。 - -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -Lotus Notes (GUI) - -不要使用它。 - -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -Mutt (TUI) - -很多Linux开发人员使用mutt客户端,所以证明它肯定工作的非常漂亮。 - -Mutt不自带编辑器,所以不管你使用什么编辑器都不应该带有自动断行。大多数编辑器都带有 -一个"insert file"选项,它可以通过不改变文件内容的方式插入文件。 - -'vim'作为mutt的编辑器: - set editor="vi" - - 如果使用xclip,敲入以下命令 - :set paste - 按中键之前或者shift-insert或者使用 - :r filename - -如果想要把补丁作为内嵌文本。 -(a)ttach工作的很好,不带有"set paste"。 - -配置选项: -它应该以默认设置的形式工作。 -然而,把"send_charset"设置为"us-ascii::utf-8"也是一个不错的主意。 - -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -Pine (TUI) - -Pine过去有一些空格删减问题,但是这些现在应该都被修复了。 - -如果可以,请使用alpine(pine的继承者) - -配置选项: -- 最近的版本需要消除流程文本 -- "no-strip-whitespace-before-send"选项也是需要的。 - - -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -Sylpheed (GUI) - -- 内嵌文本可以很好的工作(或者使用附件)。 -- 允许使用外部的编辑器。 -- 对于目录较多时非常慢。 -- 如果通过non-SSL连接,无法使用TLS SMTP授权。 -- 在组成窗口中有一个很有用的ruler bar。 -- 给地址本中添加地址就不会正确的了解显示名。 - -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -Thunderbird (GUI) - -默认情况下,thunderbird很容易损坏文本,但是还有一些方法可以强制它变得更好。 - -- 在用户帐号设置里,组成和寻址,不要选择"Compose messages in HTML format"。 - -- 编辑你的Thunderbird配置设置来使它不要拆行使用:user_pref("mailnews.wraplength", 0); - -- 编辑你的Thunderbird配置设置,使它不要使用"format=flowed"格式:user_pref("mailnews. - send_plaintext_flowed", false); - -- 你需要使Thunderbird变为预先格式方式: - 如果默认情况下你书写的是HTML格式,那不是很难。仅仅从标题栏的下拉框中选择"Preformat"格式。 - 如果默认情况下你书写的是文本格式,你不得把它改为HTML格式(仅仅作为一次性的)来书写新的消息, - 然后强制使它回到文本格式,否则它就会拆行。要实现它,在写信的图标上使用shift键来使它变为HTML - 格式,然后标题栏的下拉框中选择"Preformat"格式。 - -- 允许使用外部的编辑器: - 针对Thunderbird打补丁最简单的方法就是使用一个"external editor"扩展,然后使用你最喜欢的 - $EDITOR来读取或者合并补丁到文本中。要实现它,可以下载并且安装这个扩展,然后添加一个使用它的 - 按键View->Toolbars->Customize...最后当你书写信息的时候仅仅点击它就可以了。 - -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -TkRat (GUI) - -可以使用它。使用"Insert file..."或者外部的编辑器。 - -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -Gmail (Web GUI) - -不要使用它发送补丁。 - -Gmail网页客户端自动地把制表符转换为空格。 - -虽然制表符转换为空格问题可以被外部编辑器解决,同时它还会使用回车换行把每行拆分为78个字符。 - -另一个问题是Gmail还会把任何不是ASCII的字符的信息改为base64编码。它把东西变的像欧洲人的名字。 - - ### diff --git a/Documentation/translations/zh_CN/magic-number.txt b/Documentation/translations/zh_CN/magic-number.txt deleted file mode 100644 index 7159cec04090..000000000000 --- a/Documentation/translations/zh_CN/magic-number.txt +++ /dev/null @@ -1,153 +0,0 @@ -Chinese translated version of Documentation/process/magic-number.rst - -If you have any comment or update to the content, please post to LKML directly. -However, if you have problem communicating in English you can also ask the -Chinese maintainer for help. Contact the Chinese maintainer, if this -translation is outdated or there is problem with translation. - -Chinese maintainer: Jia Wei Wei ---------------------------------------------------------------------- -Documentation/process/magic-number.rst的中文翻译 - -如果想评论或更新本文的内容,请直接发信到LKML。如果你使用英文交流有困难的话,也可 -以向中文版维护者求助。如果本翻译更新不及时或者翻译存在问题,请联系中文版维护者。 - -中文版维护者: 贾威威 Jia Wei Wei -中文版翻译者: 贾威威 Jia Wei Wei -中文版校译者: 贾威威 Jia Wei Wei - -以下为正文 ---------------------------------------------------------------------- -这个文件是有关当前使用的魔术值注册表。当你给一个结构添加了一个魔术值,你也应该把这个魔术值添加到这个文件,因为我们最好把用于各种结构的魔术值统一起来。 - -使用魔术值来保护内核数据结构是一个非常好的主意。这就允许你在运行期检查(a)一个结构是否已经被攻击,或者(b)你已经给一个例行程序通过了一个错误的结构。后一种情况特别地有用---特别是当你通过一个空指针指向结构体的时候。tty源码,例如,经常通过特定驱动使用这种方法并且反复地排列特定方面的结构。 - -使用魔术值的方法是在结构的开始处声明的,如下: - -struct tty_ldisc { - int magic; - ... -}; - -当你以后给内核添加增强功能的时候,请遵守这条规则!这样就会节省数不清的调试时间,特别是一些古怪的情况,例如,数组超出范围并且重新写了超出部分。遵守这个规则,‪这些情况可以被快速地,安全地避免。 - - Theodore Ts'o - 31 Mar 94 - -给当前的Linux 2.1.55添加魔术表。 - - Michael Chastain - - 22 Sep 1997 - -现在应该最新的Linux 2.1.112.因为在特性冻结期间,不能在2.2.x前改变任何东西。这些条目被数域所排序。 - - Krzysztof G.Baranowski - - 29 Jul 1998 - -更新魔术表到Linux 2.5.45。刚好越过特性冻结,但是有可能还会有一些新的魔术值在2.6.x之前融入到内核中。 - - Petr Baudis - - 03 Nov 2002 - -更新魔术表到Linux 2.5.74。 - - Fabian Frederick - - 09 Jul 2003 - -魔术名 地址 结构 所在文件 -=========================================================================== -PG_MAGIC 'P' pg_{read,write}_hdr include/linux/pg.h -CMAGIC 0x0111 user include/linux/a.out.h -MKISS_DRIVER_MAGIC 0x04bf mkiss_channel drivers/net/mkiss.h -HDLC_MAGIC 0x239e n_hdlc drivers/char/n_hdlc.c -APM_BIOS_MAGIC 0x4101 apm_user arch/x86/kernel/apm_32.c -CYCLADES_MAGIC 0x4359 cyclades_port include/linux/cyclades.h -DB_MAGIC 0x4442 fc_info drivers/net/iph5526_novram.c -DL_MAGIC 0x444d fc_info drivers/net/iph5526_novram.c -FASYNC_MAGIC 0x4601 fasync_struct include/linux/fs.h -FF_MAGIC 0x4646 fc_info drivers/net/iph5526_novram.c -ISICOM_MAGIC 0x4d54 isi_port include/linux/isicom.h -PTY_MAGIC 0x5001 drivers/char/pty.c -PPP_MAGIC 0x5002 ppp include/linux/if_pppvar.h -SERIAL_MAGIC 0x5301 async_struct include/linux/serial.h -SSTATE_MAGIC 0x5302 serial_state include/linux/serial.h -SLIP_MAGIC 0x5302 slip drivers/net/slip.h -STRIP_MAGIC 0x5303 strip drivers/net/strip.c -X25_ASY_MAGIC 0x5303 x25_asy drivers/net/x25_asy.h -SIXPACK_MAGIC 0x5304 sixpack drivers/net/hamradio/6pack.h -AX25_MAGIC 0x5316 ax_disp drivers/net/mkiss.h -TTY_MAGIC 0x5401 tty_struct include/linux/tty.h -MGSL_MAGIC 0x5401 mgsl_info drivers/char/synclink.c -TTY_DRIVER_MAGIC 0x5402 tty_driver include/linux/tty_driver.h -MGSLPC_MAGIC 0x5402 mgslpc_info drivers/char/pcmcia/synclink_cs.c -TTY_LDISC_MAGIC 0x5403 tty_ldisc include/linux/tty_ldisc.h -USB_SERIAL_MAGIC 0x6702 usb_serial drivers/usb/serial/usb-serial.h -FULL_DUPLEX_MAGIC 0x6969 drivers/net/ethernet/dec/tulip/de2104x.c -USB_BLUETOOTH_MAGIC 0x6d02 usb_bluetooth drivers/usb/class/bluetty.c -RFCOMM_TTY_MAGIC 0x6d02 net/bluetooth/rfcomm/tty.c -USB_SERIAL_PORT_MAGIC 0x7301 usb_serial_port drivers/usb/serial/usb-serial.h -CG_MAGIC 0x00090255 ufs_cylinder_group include/linux/ufs_fs.h -RPORT_MAGIC 0x00525001 r_port drivers/char/rocket_int.h -LSEMAGIC 0x05091998 lse drivers/fc4/fc.c -GDTIOCTL_MAGIC 0x06030f07 gdth_iowr_str drivers/scsi/gdth_ioctl.h -RIEBL_MAGIC 0x09051990 drivers/net/atarilance.c -NBD_REQUEST_MAGIC 0x12560953 nbd_request include/linux/nbd.h -RED_MAGIC2 0x170fc2a5 (any) mm/slab.c -BAYCOM_MAGIC 0x19730510 baycom_state drivers/net/baycom_epp.c -ISDN_X25IFACE_MAGIC 0x1e75a2b9 isdn_x25iface_proto_data - drivers/isdn/isdn_x25iface.h -ECP_MAGIC 0x21504345 cdkecpsig include/linux/cdk.h -LSOMAGIC 0x27091997 lso drivers/fc4/fc.c -LSMAGIC 0x2a3b4d2a ls drivers/fc4/fc.c -WANPIPE_MAGIC 0x414C4453 sdla_{dump,exec} include/linux/wanpipe.h -CS_CARD_MAGIC 0x43525553 cs_card sound/oss/cs46xx.c -LABELCL_MAGIC 0x4857434c labelcl_info_s include/asm/ia64/sn/labelcl.h -ISDN_ASYNC_MAGIC 0x49344C01 modem_info include/linux/isdn.h -CTC_ASYNC_MAGIC 0x49344C01 ctc_tty_info drivers/s390/net/ctctty.c -ISDN_NET_MAGIC 0x49344C02 isdn_net_local_s drivers/isdn/i4l/isdn_net_lib.h -SAVEKMSG_MAGIC2 0x4B4D5347 savekmsg arch/*/amiga/config.c -CS_STATE_MAGIC 0x4c4f4749 cs_state sound/oss/cs46xx.c -SLAB_C_MAGIC 0x4f17a36d kmem_cache mm/slab.c -COW_MAGIC 0x4f4f4f4d cow_header_v1 arch/um/drivers/ubd_user.c -I810_CARD_MAGIC 0x5072696E i810_card sound/oss/i810_audio.c -TRIDENT_CARD_MAGIC 0x5072696E trident_card sound/oss/trident.c -ROUTER_MAGIC 0x524d4157 wan_device [in wanrouter.h pre 3.9] -SAVEKMSG_MAGIC1 0x53415645 savekmsg arch/*/amiga/config.c -GDA_MAGIC 0x58464552 gda arch/mips/include/asm/sn/gda.h -RED_MAGIC1 0x5a2cf071 (any) mm/slab.c -EEPROM_MAGIC_VALUE 0x5ab478d2 lanai_dev drivers/atm/lanai.c -HDLCDRV_MAGIC 0x5ac6e778 hdlcdrv_state include/linux/hdlcdrv.h -PCXX_MAGIC 0x5c6df104 channel drivers/char/pcxx.h -KV_MAGIC 0x5f4b565f kernel_vars_s arch/mips/include/asm/sn/klkernvars.h -I810_STATE_MAGIC 0x63657373 i810_state sound/oss/i810_audio.c -TRIDENT_STATE_MAGIC 0x63657373 trient_state sound/oss/trident.c -M3_CARD_MAGIC 0x646e6f50 m3_card sound/oss/maestro3.c -FW_HEADER_MAGIC 0x65726F66 fw_header drivers/atm/fore200e.h -SLOT_MAGIC 0x67267321 slot drivers/hotplug/cpqphp.h -SLOT_MAGIC 0x67267322 slot drivers/hotplug/acpiphp.h -LO_MAGIC 0x68797548 nbd_device include/linux/nbd.h -OPROFILE_MAGIC 0x6f70726f super_block drivers/oprofile/oprofilefs.h -M3_STATE_MAGIC 0x734d724d m3_state sound/oss/maestro3.c -VMALLOC_MAGIC 0x87654320 snd_alloc_track sound/core/memory.c -KMALLOC_MAGIC 0x87654321 snd_alloc_track sound/core/memory.c -PWC_MAGIC 0x89DC10AB pwc_device drivers/usb/media/pwc.h -NBD_REPLY_MAGIC 0x96744668 nbd_reply include/linux/nbd.h -ENI155_MAGIC 0xa54b872d midway_eprom drivers/atm/eni.h -CODA_MAGIC 0xC0DAC0DA coda_file_info include/linux/coda_fs_i.h -DPMEM_MAGIC 0xc0ffee11 gdt_pci_sram drivers/scsi/gdth.h -YAM_MAGIC 0xF10A7654 yam_port drivers/net/hamradio/yam.c -CCB_MAGIC 0xf2691ad2 ccb drivers/scsi/ncr53c8xx.c -QUEUE_MAGIC_FREE 0xf7e1c9a3 queue_entry drivers/scsi/arm/queue.c -QUEUE_MAGIC_USED 0xf7e1cc33 queue_entry drivers/scsi/arm/queue.c -HTB_CMAGIC 0xFEFAFEF1 htb_class net/sched/sch_htb.c -NMI_MAGIC 0x48414d4d455201 nmi_s arch/mips/include/asm/sn/nmi.h - -请注意,在声音记忆管理中仍然有一些特殊的为每个驱动定义的魔术值。查看include/sound/sndmagic.h来获取他们完整的列表信息。很多OSS声音驱动拥有自己从声卡PCI ID构建的魔术值-他们也没有被列在这里。 - -IrDA子系统也使用了大量的自己的魔术值,查看include/net/irda/irda.h来获取他们完整的信息。 - -HFS是另外一个比较大的使用魔术值的文件系统-你可以在fs/hfs/hfs.h中找到他们。 diff --git a/Documentation/translations/zh_CN/process/HOWTO b/Documentation/translations/zh_CN/process/HOWTO new file mode 100644 index 000000000000..7a00a8a4eb15 --- /dev/null +++ b/Documentation/translations/zh_CN/process/HOWTO @@ -0,0 +1,525 @@ +Chinese translated version of Documentation/process/howto.rst + +If you have any comment or update to the content, please contact the +original document maintainer directly. However, if you have a problem +communicating in English you can also ask the Chinese maintainer for +help. Contact the Chinese maintainer if this translation is outdated +or if there is a problem with the translation. + +Maintainer: Greg Kroah-Hartman +Chinese maintainer: Li Yang +--------------------------------------------------------------------- +Documentation/process/howto.rst 的中文翻译 + +如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 +交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 +译存在问题,请联系中文版维护者。 + +英文版维护者: Greg Kroah-Hartman +中文版维护者: 李阳 Li Yang +中文版翻译者: 李阳 Li Yang +中文版校译者: 钟宇 TripleX Chung + 陈琦 Maggie Chen + 王聪 Wang Cong + +以下为正文 +--------------------------------------------------------------------- + +如何参与Linux内核开发 +--------------------- + +这是一篇将如何参与Linux内核开发的相关问题一网打尽的终极秘笈。它将指导你 +成为一名Linux内核开发者,并且学会如何同Linux内核开发社区合作。它尽可能不 +包括任何关于内核编程的技术细节,但会给你指引一条获得这些知识的正确途径。 + +如果这篇文章中的任何内容不再适用,请给文末列出的文件维护者发送补丁。 + + +入门 +---- + +你想了解如何成为一名Linux内核开发者?或者老板吩咐你“给这个设备写个Linux +驱动程序”?这篇文章的目的就是教会你达成这些目标的全部诀窍,它将描述你需 +要经过的流程以及给出如何同内核社区合作的一些提示。它还将试图解释内核社区 +为何这样运作。 + +Linux内核大部分是由C语言写成的,一些体系结构相关的代码用到了汇编语言。要 +参与内核开发,你必须精通C语言。除非你想为某个架构开发底层代码,否则你并 +不需要了解(任何体系结构的)汇编语言。下面列举的书籍虽然不能替代扎实的C +语言教育和多年的开发经验,但如果需要的话,做为参考还是不错的: + - "The C Programming Language" by Kernighan and Ritchie [Prentice Hall] + 《C程序设计语言(第2版·新版)》(徐宝文 李志 译)[机械工业出版社] + - "Practical C Programming" by Steve Oualline [O'Reilly] + 《实用C语言编程(第三版)》(郭大海 译)[中国电力出版社] + - "C: A Reference Manual" by Harbison and Steele [Prentice Hall] + 《C语言参考手册(原书第5版)》(邱仲潘 等译)[机械工业出版社] + +Linux内核使用GNU C和GNU工具链开发。虽然它遵循ISO C89标准,但也用到了一些 +标准中没有定义的扩展。内核是自给自足的C环境,不依赖于标准C库的支持,所以 +并不支持C标准中的部分定义。比如long long类型的大数除法和浮点运算就不允许 +使用。有时候确实很难弄清楚内核对工具链的要求和它所使用的扩展,不幸的是目 +前还没有明确的参考资料可以解释它们。请查阅gcc信息页(使用“info gcc”命令 +显示)获得一些这方面信息。 + +请记住你是在学习怎么和已经存在的开发社区打交道。它由一群形形色色的人组成, +他们对代码、风格和过程有着很高的标准。这些标准是在长期实践中总结出来的, +适应于地理上分散的大型开发团队。它们已经被很好得整理成档,建议你在开发 +之前尽可能多的学习这些标准,而不要期望别人来适应你或者你公司的行为方式。 + + +法律问题 +-------- + +Linux内核源代码都是在GPL(通用公共许可证)的保护下发布的。要了解这种许可 +的细节请查看源代码主目录下的COPYING文件。如果你对它还有更深入问题请联系 +律师,而不要在Linux内核邮件组上提问。因为邮件组里的人并不是律师,不要期 +望他们的话有法律效力。 + +对于GPL的常见问题和解答,请访问以下链接: + http://www.gnu.org/licenses/gpl-faq.html + + +文档 +---- + +Linux内核代码中包含有大量的文档。这些文档对于学习如何与内核社区互动有着 +不可估量的价值。当一个新的功能被加入内核,最好把解释如何使用这个功能的文 +档也放进内核。当内核的改动导致面向用户空间的接口发生变化时,最好将相关信 +息或手册页(manpages)的补丁发到mtk.manpages@gmail.com,以向手册页(manpages) +的维护者解释这些变化。 + +以下是内核代码中需要阅读的文档: + README + 文件简要介绍了Linux内核的背景,并且描述了如何配置和编译内核。内核的 + 新用户应该从这里开始。 + + Documentation/process/changes.rst + 文件给出了用来编译和使用内核所需要的最小软件包列表。 + + Documentation/process/coding-style.rst + 描述Linux内核的代码风格和理由。所有新代码需要遵守这篇文档中定义的规 + 范。大多数维护者只会接收符合规定的补丁,很多人也只会帮忙检查符合风格 + 的代码。 + + Documentation/process/submitting-patches.rst + Documentation/process/submitting-drivers.rst + 这两份文档明确描述如何创建和发送补丁,其中包括(但不仅限于): + - 邮件内容 + - 邮件格式 + - 选择收件人 + 遵守这些规定并不能保证提交成功(因为所有补丁需要通过严格的内容和风格 + 审查),但是忽视他们几乎就意味着失败。 + + 其他关于如何正确地生成补丁的优秀文档包括: + "The Perfect Patch" + http://www.ozlabs.org/~akpm/stuff/tpp.txt + "Linux kernel patch submission format" + http://linux.yyz.us/patch-format.html + + Documentation/process/stable-api-nonsense.rst + 论证内核为什么特意不包括稳定的内核内部API,也就是说不包括像这样的特 + 性: + - 子系统中间层(为了兼容性?) + - 在不同操作系统间易于移植的驱动程序 + - 减缓(甚至阻止)内核代码的快速变化 + 这篇文档对于理解Linux的开发哲学至关重要。对于将开发平台从其他操作系 + 统转移到Linux的人来说也很重要。 + + Documentation/admin-guide/security-bugs.rst + 如果你认为自己发现了Linux内核的安全性问题,请根据这篇文档中的步骤来 + 提醒其他内核开发者并帮助解决这个问题。 + + Documentation/process/management-style.rst + 描述内核维护者的工作方法及其共有特点。这对于刚刚接触内核开发(或者对 + 它感到好奇)的人来说很重要,因为它解释了很多对于内核维护者独特行为的 + 普遍误解与迷惑。 + + Documentation/process/stable-kernel-rules.rst + 解释了稳定版内核发布的规则,以及如何将改动放入这些版本的步骤。 + + Documentation/process/kernel-docs.rst + 有助于内核开发的外部文档列表。如果你在内核自带的文档中没有找到你想找 + 的内容,可以查看这些文档。 + + Documentation/process/applying-patches.rst + 关于补丁是什么以及如何将它打在不同内核开发分支上的好介绍 + +内核还拥有大量从代码自动生成的文档。它包含内核内部API的全面介绍以及如何 +妥善处理加锁的规则。生成的文档会放在 Documentation/DocBook/目录下。在内 +核源码的主目录中使用以下不同命令将会分别生成PDF、Postscript、HTML和手册 +页等不同格式的文档: + make pdfdocs + make htmldocs + + +如何成为内核开发者 +------------------ +如果你对Linux内核开发一无所知,你应该访问“Linux内核新手”计划: + http://kernelnewbies.org +它拥有一个可以问各种最基本的内核开发问题的邮件列表(在提问之前一定要记得 +查找已往的邮件,确认是否有人已经回答过相同的问题)。它还拥有一个可以获得 +实时反馈的IRC聊天频道,以及大量对于学习Linux内核开发相当有帮助的文档。 + +网站简要介绍了源代码组织结构、子系统划分以及目前正在进行的项目(包括内核 +中的和单独维护的)。它还提供了一些基本的帮助信息,比如如何编译内核和打补 +丁。 + +如果你想加入内核开发社区并协助完成一些任务,却找不到从哪里开始,可以访问 +“Linux内核房管员”计划: + http://kernelnewbies.org/KernelJanitors +这是极佳的起点。它提供一个相对简单的任务列表,列出内核代码中需要被重新 +整理或者改正的地方。通过和负责这个计划的开发者们一同工作,你会学到将补丁 +集成进内核的基本原理。如果还没有决定下一步要做什么的话,你还可能会得到方 +向性的指点。 + +如果你已经有一些现成的代码想要放到内核中,但是需要一些帮助来使它们拥有正 +确的格式。请访问“内核导师”计划。这个计划就是用来帮助你完成这个目标的。它 +是一个邮件列表,地址如下: + http://selenic.com/mailman/listinfo/kernel-mentors + +在真正动手修改内核代码之前,理解要修改的代码如何运作是必需的。要达到这个 +目的,没什么办法比直接读代码更有效了(大多数花招都会有相应的注释),而且 +一些特制的工具还可以提供帮助。例如,“Linux代码交叉引用”项目就是一个值得 +特别推荐的帮助工具,它将源代码显示在有编目和索引的网页上。其中一个更新及 +时的内核源码库,可以通过以下地址访问: + http://sosdg.org/~coywolf/lxr/ + + +开发流程 +-------- + +目前Linux内核开发流程包括几个“主内核分支”和很多子系统相关的内核分支。这 +些分支包括: + - 2.6.x主内核源码树 + - 2.6.x.y -stable内核源码树 + - 2.6.x -mm内核补丁集 + - 子系统相关的内核源码树和补丁集 + + +2.6.x内核主源码树 +----------------- +2.6.x内核是由Linus Torvalds(Linux的创造者)亲自维护的。你可以在 +kernel.org网站的pub/linux/kernel/v2.6/目录下找到它。它的开发遵循以下步 +骤: + - 每当一个新版本的内核被发布,为期两周的集成窗口将被打开。在这段时间里 + 维护者可以向Linus提交大段的修改,通常这些修改已经被放到-mm内核中几个 + 星期了。提交大量修改的首选方式是使用git工具(内核的代码版本管理工具 + ,更多的信息可以在http://git-scm.com/获取),不过使用普通补丁也是可以 + 的。 + - 两个星期以后-rc1版本内核发布。之后只有不包含可能影响整个内核稳定性的 + 新功能的补丁才可能被接受。请注意一个全新的驱动程序(或者文件系统)有 + 可能在-rc1后被接受是因为这样的修改完全独立,不会影响其他的代码,所以 + 没有造成内核退步的风险。在-rc1以后也可以用git向Linus提交补丁,不过所 + 有的补丁需要同时被发送到相应的公众邮件列表以征询意见。 + - 当Linus认为当前的git源码树已经达到一个合理健全的状态足以发布供人测试 + 时,一个新的-rc版本就会被发布。计划是每周都发布新的-rc版本。 + - 这个过程一直持续下去直到内核被认为达到足够稳定的状态,持续时间大概是 + 6个星期。 + +关于内核发布,值得一提的是Andrew Morton在linux-kernel邮件列表中如是说: + “没有人知道新内核何时会被发布,因为发布是根据已知bug的情况来决定 + 的,而不是根据一个事先制定好的时间表。” + + +2.6.x.y -stable(稳定版)内核源码树 +----------------------------------- +由4个数字组成的内核版本号说明此内核是-stable版本。它们包含基于2.6.x版本 +内核的相对较小且至关重要的修补,这些修补针对安全性问题或者严重的内核退步。 + +这种版本的内核适用于那些期望获得最新的稳定版内核并且不想参与测试开发版或 +者实验版的用户。 + +如果没有2.6.x.y版本内核存在,那么最新的2.6.x版本内核就相当于是当前的稳定 +版内核。 + +2.6.x.y版本由“稳定版”小组(邮件地址)维护,一般隔周发 +布新版本。 + +内核源码中的Documentation/process/stable-kernel-rules.rst文件具体描述了可被稳定 +版内核接受的修改类型以及发布的流程。 + + +2.6.x -mm补丁集 +--------------- +这是由Andrew Morton维护的试验性内核补丁集。Andrew将所有子系统的内核源码 +和补丁拼凑到一起,并且加入了大量从linux-kernel邮件列表中采集的补丁。这个 +源码树是新功能和补丁的试炼场。当补丁在-mm补丁集里证明了其价值以后Andrew +或者相应子系统的维护者会将补丁发给Linus以便集成进主内核源码树。 + +在将所有新补丁发给Linus以集成到主内核源码树之前,我们非常鼓励先把这些补 +丁放在-mm版内核源码树中进行测试。 + +这些内核版本不适合在需要稳定运行的系统上运行,因为运行它们比运行任何其他 +内核分支都更具有风险。 + +如果你想为内核开发进程提供帮助,请尝试并使用这些内核版本,并在 +linux-kernel邮件列表中提供反馈,告诉大家你遇到了问题还是一切正常。 + +通常-mm版补丁集不光包括这些额外的试验性补丁,还包括发布时-git版主源码树 +中的改动。 + +-mm版内核没有固定的发布周期,但是通常在每两个-rc版内核发布之间都会有若干 +个-mm版内核发布(一般是1至3个)。 + + +子系统相关内核源码树和补丁集 +---------------------------- +相当一部分内核子系统开发者会公开他们自己的开发源码树,以便其他人能了解内 +核的不同领域正在发生的事情。如上所述,这些源码树会被集成到-mm版本内核中。 + +下面是目前可用的一些内核源码树的列表: + 通过git管理的源码树: + - Kbuild开发源码树, Sam Ravnborg + git.kernel.org:/pub/scm/linux/kernel/git/sam/kbuild.git + + - ACPI开发源码树, Len Brown + git.kernel.org:/pub/scm/linux/kernel/git/lenb/linux-acpi-2.6.git + + - 块设备开发源码树, Jens Axboe + git.kernel.org:/pub/scm/linux/kernel/git/axboe/linux-2.6-block.git + + - DRM开发源码树, Dave Airlie + git.kernel.org:/pub/scm/linux/kernel/git/airlied/drm-2.6.git + + - ia64开发源码树, Tony Luck + git.kernel.org:/pub/scm/linux/kernel/git/aegl/linux-2.6.git + + - ieee1394开发源码树, Jody McIntyre + git.kernel.org:/pub/scm/linux/kernel/git/scjody/ieee1394.git + + - infiniband开发源码树, Roland Dreier + git.kernel.org:/pub/scm/linux/kernel/git/roland/infiniband.git + + - libata开发源码树, Jeff Garzik + git.kernel.org:/pub/scm/linux/kernel/git/jgarzik/libata-dev.git + + - 网络驱动程序开发源码树, Jeff Garzik + git.kernel.org:/pub/scm/linux/kernel/git/jgarzik/netdev-2.6.git + + - pcmcia开发源码树, Dominik Brodowski + git.kernel.org:/pub/scm/linux/kernel/git/brodo/pcmcia-2.6.git + + - SCSI开发源码树, James Bottomley + git.kernel.org:/pub/scm/linux/kernel/git/jejb/scsi-misc-2.6.git + + 使用quilt管理的补丁集: + - USB, PCI, 驱动程序核心和I2C, Greg Kroah-Hartman + kernel.org/pub/linux/kernel/people/gregkh/gregkh-2.6/ + - x86-64, 部分i386, Andi Kleen + ftp.firstfloor.org:/pub/ak/x86_64/quilt/ + + 其他内核源码树可以在http://git.kernel.org的列表中和MAINTAINERS文件里 + 找到。 + +报告bug +------- + +bugzilla.kernel.org是Linux内核开发者们用来跟踪内核Bug的网站。我们鼓励用 +户在这个工具中报告找到的所有bug。如何使用内核bugzilla的细节请访问: + http://test.kernel.org/bugzilla/faq.html + +内核源码主目录中的admin-guide/reporting-bugs.rst文件里有一个很好的模板。它指导用户如何报 +告可能的内核bug以及需要提供哪些信息来帮助内核开发者们找到问题的根源。 + + +利用bug报告 +----------- + +练习内核开发技能的最好办法就是修改其他人报告的bug。你不光可以帮助内核变 +得更加稳定,还可以学会如何解决实际问题从而提高自己的技能,并且让其他开发 +者感受到你的存在。修改bug是赢得其他开发者赞誉的最好办法,因为并不是很多 +人都喜欢浪费时间去修改别人报告的bug。 + +要尝试修改已知的bug,请访问http://bugzilla.kernel.org网址。如果你想获得 +最新bug的通知,可以订阅bugme-new邮件列表(只有新的bug报告会被寄到这里) +或者订阅bugme-janitor邮件列表(所有bugzilla的变动都会被寄到这里)。 + + https://lists.linux-foundation.org/mailman/listinfo/bugme-new + https://lists.linux-foundation.org/mailman/listinfo/bugme-janitors + + +邮件列表 +-------- + +正如上面的文档所描述,大多数的骨干内核开发者都加入了Linux Kernel邮件列 +表。如何订阅和退订列表的细节可以在这里找到: + http://vger.kernel.org/vger-lists.html#linux-kernel +网上很多地方都有这个邮件列表的存档(archive)。可以使用搜索引擎来找到这些 +存档。比如: + http://dir.gmane.org/gmane.linux.kernel +在发信之前,我们强烈建议你先在存档中搜索你想要讨论的问题。很多已经被详细 +讨论过的问题只在邮件列表的存档中可以找到。 + +大多数内核子系统也有自己独立的邮件列表来协调各自的开发工作。从 +MAINTAINERS文件中可以找到不同话题对应的邮件列表。 + +很多邮件列表架设在kernel.org服务器上。这些列表的信息可以在这里找到: + http://vger.kernel.org/vger-lists.html + +在使用这些邮件列表时,请记住保持良好的行为习惯。下面的链接提供了与这些列 +表(或任何其它邮件列表)交流的一些简单规则,虽然内容有点滥竽充数。 + http://www.albion.com/netiquette/ + +当有很多人回复你的邮件时,邮件的抄送列表会变得很长。请不要将任何人从抄送 +列表中删除,除非你有足够的理由这么做。也不要只回复到邮件列表。请习惯于同 +一封邮件接收两次(一封来自发送者一封来自邮件列表),而不要试图通过添加一 +些奇特的邮件头来解决这个问题,人们不会喜欢的。 + +记住保留你所回复内容的上下文和源头。在你回复邮件的顶部保留“某某某说到……” +这几行。将你的评论加在被引用的段落之间而不要放在邮件的顶部。 + +如果你在邮件中附带补丁,请确认它们是可以直接阅读的纯文本(如 +Documentation/process/submitting-patches.rst文档中所述)。内核开发者们不希望遇到附件 +或者被压缩了的补丁。只有这样才能保证他们可以直接评论你的每行代码。请确保 +你使用的邮件发送程序不会修改空格和制表符。一个防范性的测试方法是先将邮件 +发送给自己,然后自己尝试是否可以顺利地打上收到的补丁。如果测试不成功,请 +调整或者更换你的邮件发送程序直到它正确工作为止。 + +总而言之,请尊重其他的邮件列表订阅者。 + + +同内核社区合作 +---------------- + +内核社区的目标就是提供尽善尽美的内核。所以当你提交补丁期望被接受进内核的 +时候,它的技术价值以及其他方面都将被评审。那么你可能会得到什么呢? + - 批评 + - 评论 + - 要求修改 + - 要求证明修改的必要性 + - 沉默 + +要记住,这些是把补丁放进内核的正常情况。你必须学会听取对补丁的批评和评论, +从技术层面评估它们,然后要么重写你的补丁要么简明扼要地论证修改是不必要 +的。如果你发的邮件没有得到任何回应,请过几天后再试一次,因为有时信件会湮 +没在茫茫信海中。 + +你不应该做的事情: + - 期望自己的补丁不受任何质疑就直接被接受 + - 翻脸 + - 忽略别人的评论 + - 没有按照别人的要求做任何修改就重新提交 + +在一个努力追寻最好技术方案的社区里,对于一个补丁有多少好处总会有不同的见 +解。你必须要抱着合作的态度,愿意改变自己的观点来适应内核的风格。或者至少 +愿意去证明你的想法是有价值的。记住,犯错误是允许的,只要你愿意朝着正确的 +方案去努力。 + +如果你的第一个补丁换来的是一堆修改建议,这是很正常的。这并不代表你的补丁 +不会被接受,也不意味着有人和你作对。你只需要改正所有提出的问题然后重新发 +送你的补丁。 + +内核社区和公司文化的差异 +------------------------ + +内核社区的工作模式同大多数传统公司开发队伍的工作模式并不相同。下面这些例 +子,可以帮助你避免某些可能发生问题: + 用这些话介绍你的修改提案会有好处: + - 它同时解决了多个问题 + - 它删除了2000行代码 + - 这是补丁,它已经解释了我想要说明的 + - 我在5种不同的体系结构上测试过它…… + - 这是一系列小补丁用来…… + - 这个修改提高了普通机器的性能…… + + 应该避免如下的说法: + - 我们在AIX/ptx/Solaris就是这么做的,所以这么做肯定是好的…… + - 我做这行已经20年了,所以…… + - 为了我们公司赚钱考虑必须这么做 + - 这是我们的企业产品线所需要的 + - 这里是描述我观点的1000页设计文档 + - 这是一个5000行的补丁用来…… + - 我重写了现在乱七八糟的代码,这就是…… + - 我被规定了最后期限,所以这个补丁需要立刻被接受 + +另外一个内核社区与大部分传统公司的软件开发队伍不同的地方是无法面对面地交 +流。使用电子邮件和IRC聊天工具做为主要沟通工具的一个好处是性别和种族歧视 +将会更少。Linux内核的工作环境更能接受妇女和少数族群,因为每个人在别人眼 +里只是一个邮件地址。国际化也帮助了公平的实现,因为你无法通过姓名来判断人 +的性别。男人有可能叫李丽,女人也有可能叫王刚。大多数在Linux内核上工作过 +并表达过看法的女性对在linux上工作的经历都给出了正面的评价。 + +对于一些不习惯使用英语的人来说,语言可能是一个引起问题的障碍。在邮件列表 +中要正确地表达想法必需良好地掌握语言,所以建议你在发送邮件之前最好检查一 +下英文写得是否正确。 + + +拆分修改 +-------- + +Linux内核社区并不喜欢一下接收大段的代码。修改需要被恰当地介绍、讨论并且 +拆分成独立的小段。这几乎完全和公司中的习惯背道而驰。你的想法应该在开发最 +开始的阶段就让大家知道,这样你就可以及时获得对你正在进行的开发的反馈。这 +样也会让社区觉得你是在和他们协作,而不是仅仅把他们当作倾销新功能的对象。 +无论如何,你不要一次性地向邮件列表发送50封信,你的补丁序列应该永远用不到 +这么多。 + +将补丁拆开的原因如下: + +1) 小的补丁更有可能被接受,因为它们不需要太多的时间和精力去验证其正确性。 + 一个5行的补丁,可能在维护者看了一眼以后就会被接受。而500行的补丁则 + 需要数个小时来审查其正确性(所需时间随补丁大小增加大约呈指数级增长)。 + + 当出了问题的时候,小的补丁也会让调试变得非常容易。一个一个补丁地回溯 + 将会比仔细剖析一个被打上的大补丁(这个补丁破坏了其他东西)容易得多。 + +2)不光发送小的补丁很重要,在提交之前重新编排、化简(或者仅仅重新排列) + 补丁也是很重要的。 + +这里有内核开发者Al Viro打的一个比方: + “想象一个老师正在给学生批改数学作业。老师并不希望看到学生为了得 + 到正确解法所进行的尝试和产生的错误。他希望看到的是最干净最优雅的 + 解答。好学生了解这点,绝不会把最终解决之前的中间方案提交上去。” + + 内核开发也是这样。维护者和评审者不希望看到一个人在解决问题时的思 + 考过程。他们只希望看到简单和优雅的解决方案。 + +直接给出一流的解决方案,和社区一起协作讨论尚未完成的工作,这两者之间似乎 +很难找到一个平衡点。所以最好尽早开始收集有利于你进行改进的反馈;同时也要 +保证修改分成很多小块,这样在整个项目都准备好被包含进内核之前,其中的一部 +分可能会先被接收。 + +必须了解这样做是不可接受的:试图将未完成的工作提交进内核,然后再找时间修 +复。 + + +证明修改的必要性 +---------------- +除了将补丁拆成小块,很重要的一点是让Linux社区了解他们为什么需要这样修改。 +你必须证明新功能是有人需要的并且是有用的。 + + +记录修改 +-------- + +当你发送补丁的时候,需要特别留意邮件正文的内容。因为这里的信息将会做为补 +丁的修改记录(ChangeLog),会被一直保留以备大家查阅。它需要完全地描述补丁, +包括: + - 为什么需要这个修改 + - 补丁的总体设计 + - 实现细节 + - 测试结果 + +想了解它具体应该看起来像什么,请查阅以下文档中的“ChangeLog”章节: + “The Perfect Patch” + http://www.ozlabs.org/~akpm/stuff/tpp.txt + + +这些事情有时候做起来很难。要在任何方面都做到完美可能需要好几年时间。这是 +一个持续提高的过程,它需要大量的耐心和决心。只要不放弃,你一定可以做到。 +很多人已经做到了,而他们都曾经和现在的你站在同样的起点上。 + + +--------------- +感谢Paolo Ciarrocchi允许“开发流程”部分基于他所写的文章 +(http://www.kerneltravel.net/newbie/2.6-development_process),感谢Randy +Dunlap和Gerrit Huizenga完善了应该说和不该说的列表。感谢Pat Mochel, Hanna +Linder, Randy Dunlap, Kay Sievers, Vojtech Pavlik, Jan Kara, Josh Boyer, +Kees Cook, Andrew Morton, Andi Kleen, Vadim Lobanov, Jesper Juhl, Adrian +Bunk, Keri Harris, Frans Pop, David A. Wheeler, Junio Hamano, Michael +Kerrisk和Alex Shepard的评审、建议和贡献。没有他们的帮助,这篇文档是不可 +能完成的。 + + + +英文版维护者: Greg Kroah-Hartman diff --git a/Documentation/translations/zh_CN/process/SubmittingDrivers b/Documentation/translations/zh_CN/process/SubmittingDrivers new file mode 100644 index 000000000000..15e73562f710 --- /dev/null +++ b/Documentation/translations/zh_CN/process/SubmittingDrivers @@ -0,0 +1,164 @@ +Chinese translated version of Documentation/process/submitting-drivers.rst + +If you have any comment or update to the content, please contact the +original document maintainer directly. However, if you have a problem +communicating in English you can also ask the Chinese maintainer for +help. Contact the Chinese maintainer if this translation is outdated +or if there is a problem with the translation. + +Chinese maintainer: Li Yang +--------------------------------------------------------------------- +Documentation/process/submitting-drivers.rst 的中文翻译 + +如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 +交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 +译存在问题,请联系中文版维护者。 + +中文版维护者: 李阳 Li Yang +中文版翻译者: 李阳 Li Yang +中文版校译者: 陈琦 Maggie Chen + 王聪 Wang Cong + 张巍 Zhang Wei + +以下为正文 +--------------------------------------------------------------------- + +如何向 Linux 内核提交驱动程序 +----------------------------- + +这篇文档将会解释如何向不同的内核源码树提交设备驱动程序。请注意,如果你感 +兴趣的是显卡驱动程序,你也许应该访问 XFree86 项目(http://www.xfree86.org/) +和/或 X.org 项目 (http://x.org)。 + +另请参阅 Documentation/process/submitting-patches.rst 文档。 + + +分配设备号 +---------- + +块设备和字符设备的主设备号与从设备号是由 Linux 命名编号分配权威 LANANA( +现在是 Torben Mathiasen)负责分配。申请的网址是 http://www.lanana.org/。 +即使不准备提交到主流内核的设备驱动也需要在这里分配设备号。有关详细信息, +请参阅 Documentation/admin-guide/devices.rst。 + +如果你使用的不是已经分配的设备号,那么当你提交设备驱动的时候,它将会被强 +制分配一个新的设备号,即便这个设备号和你之前发给客户的截然不同。 + +设备驱动的提交对象 +------------------ + +Linux 2.0: + 此内核源码树不接受新的驱动程序。 + +Linux 2.2: + 此内核源码树不接受新的驱动程序。 + +Linux 2.4: + 如果所属的代码领域在内核的 MAINTAINERS 文件中列有一个总维护者, + 那么请将驱动程序提交给他。如果此维护者没有回应或者你找不到恰当的 + 维护者,那么请联系 Willy Tarreau 。 + +Linux 2.6: + 除了遵循和 2.4 版内核同样的规则外,你还需要在 linux-kernel 邮件 + 列表上跟踪最新的 API 变化。向 Linux 2.6 内核提交驱动的顶级联系人 + 是 Andrew Morton 。 + +决定设备驱动能否被接受的条件 +---------------------------- + +许可: 代码必须使用 GNU 通用公开许可证 (GPL) 提交给 Linux,但是 + 我们并不要求 GPL 是唯一的许可。你或许会希望同时使用多种 + 许可证发布,如果希望驱动程序可以被其他开源社区(比如BSD) + 使用。请参考 include/linux/module.h 文件中所列出的可被 + 接受共存的许可。 + +版权: 版权所有者必须同意使用 GPL 许可。最好提交者和版权所有者 + 是相同个人或实体。否则,必需列出授权使用 GPL 的版权所有 + 人或实体,以备验证之需。 + +接口: 如果你的驱动程序使用现成的接口并且和其他同类的驱动程序行 + 为相似,而不是去发明无谓的新接口,那么它将会更容易被接受。 + 如果你需要一个 Linux 和 NT 的通用驱动接口,那么请在用 + 户空间实现它。 + +代码: 请使用 Documentation/process/coding-style.rst 中所描述的 Linux 代码风 + 格。如果你的某些代码段(例如那些与 Windows 驱动程序包共 + 享的代码段)需要使用其他格式,而你却只希望维护一份代码, + 那么请将它们很好地区分出来,并且注明原因。 + +可移植性: 请注意,指针并不永远是 32 位的,不是所有的计算机都使用小 + 尾模式 (little endian) 存储数据,不是所有的人都拥有浮点 + 单元,不要随便在你的驱动程序里嵌入 x86 汇编指令。只能在 + x86 上运行的驱动程序一般是不受欢迎的。虽然你可能只有 x86 + 硬件,很难测试驱动程序在其他平台上是否可用,但是确保代码 + 可以被轻松地移植却是很简单的。 + +清晰度: 做到所有人都能修补这个驱动程序将会很有好处,因为这样你将 + 会直接收到修复的补丁而不是 bug 报告。如果你提交一个试图 + 隐藏硬件工作机理的驱动程序,那么它将会被扔进废纸篓。 + +电源管理: 因为 Linux 正在被很多移动设备和桌面系统使用,所以你的驱 + 动程序也很有可能被使用在这些设备上。它应该支持最基本的电 + 源管理,即在需要的情况下实现系统级休眠和唤醒要用到的 + .suspend 和 .resume 函数。你应该检查你的驱动程序是否能正 + 确地处理休眠与唤醒,如果实在无法确认,请至少把 .suspend + 函数定义成返回 -ENOSYS(功能未实现)错误。你还应该尝试确 + 保你的驱动在什么都不干的情况下将耗电降到最低。要获得驱动 + 程序测试的指导,请参阅 + Documentation/power/drivers-testing.txt。有关驱动程序电 + 源管理问题相对全面的概述,请参阅 + Documentation/driver-api/pm/devices.rst。 + +管理: 如果一个驱动程序的作者还在进行有效的维护,那么通常除了那 + 些明显正确且不需要任何检查的补丁以外,其他所有的补丁都会 + 被转发给作者。如果你希望成为驱动程序的联系人和更新者,最 + 好在代码注释中写明并且在 MAINTAINERS 文件中加入这个驱动 + 程序的条目。 + +不影响设备驱动能否被接受的条件 +------------------------------ + +供应商: 由硬件供应商来维护驱动程序通常是一件好事。不过,如果源码 + 树里已经有其他人提供了可稳定工作的驱动程序,那么请不要期 + 望“我是供应商”会成为内核改用你的驱动程序的理由。理想的情 + 况是:供应商与现有驱动程序的作者合作,构建一个统一完美的 + 驱动程序。 + +作者: 驱动程序是由大的 Linux 公司研发还是由你个人编写,并不影 + 响其是否能被内核接受。没有人对内核源码树享有特权。只要你 + 充分了解内核社区,你就会发现这一点。 + + +资源列表 +-------- + +Linux 内核主源码树: + ftp.??.kernel.org:/pub/linux/kernel/... + ?? == 你的国家代码,例如 "cn"、"us"、"uk"、"fr" 等等 + +Linux 内核邮件列表: + linux-kernel@vger.kernel.org + [可通过向majordomo@vger.kernel.org发邮件来订阅] + +Linux 设备驱动程序,第三版(探讨 2.6.10 版内核): + http://lwn.net/Kernel/LDD3/ (免费版) + +LWN.net: + 每周内核开发活动摘要 - http://lwn.net/ + 2.6 版中 API 的变更: + http://lwn.net/Articles/2.6-kernel-api/ + 将旧版内核的驱动程序移植到 2.6 版: + http://lwn.net/Articles/driver-porting/ + +内核新手(KernelNewbies): + 为新的内核开发者提供文档和帮助 + http://kernelnewbies.org/ + +Linux USB项目: + http://www.linux-usb.org/ + +写内核驱动的“不要”(Arjan van de Ven著): + http://www.fenrus.org/how-to-not-write-a-device-driver-paper.pdf + +内核清洁工 (Kernel Janitor): + http://kernelnewbies.org/KernelJanitors diff --git a/Documentation/translations/zh_CN/process/SubmittingPatches b/Documentation/translations/zh_CN/process/SubmittingPatches new file mode 100644 index 000000000000..e9098da8f1a4 --- /dev/null +++ b/Documentation/translations/zh_CN/process/SubmittingPatches @@ -0,0 +1,412 @@ +Chinese translated version of Documentation/process/submitting-patches.rst + +If you have any comment or update to the content, please contact the +original document maintainer directly. However, if you have a problem +communicating in English you can also ask the Chinese maintainer for +help. Contact the Chinese maintainer if this translation is outdated +or if there is a problem with the translation. + +Chinese maintainer: TripleX Chung +--------------------------------------------------------------------- +Documentation/process/submitting-patches.rst 的中文翻译 + +如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 +交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 +译存在问题,请联系中文版维护者。 + +中文版维护者: 钟宇 TripleX Chung +中文版翻译者: 钟宇 TripleX Chung +中文版校译者: 李阳 Li Yang + 王聪 Wang Cong + +以下为正文 +--------------------------------------------------------------------- + + 如何让你的改动进入内核 + 或者 + 获得亲爱的 Linus Torvalds 的关注和处理 +---------------------------------- + +对于想要将改动提交到 Linux 内核的个人或者公司来说,如果不熟悉“规矩”, +提交的流程会让人畏惧。本文档收集了一系列建议,这些建议可以大大的提高你 +的改动被接受的机会。 +阅读 Documentation/process/submit-checklist.rst 来获得在提交代码前需要检查的项目的列 +表。如果你在提交一个驱动程序,那么同时阅读一下 +Documentation/process/submitting-drivers.rst 。 + + +-------------------------- +第一节 - 创建并发送你的改动 +-------------------------- + +1) "diff -up" +----------- + +使用 "diff -up" 或者 "diff -uprN" 来创建补丁。 + +所有内核的改动,都是以补丁的形式呈现的,补丁由 diff(1) 生成。创建补丁的 +时候,要确认它是以 "unified diff" 格式创建的,这种格式由 diff(1) 的 '-u' +参数生成。而且,请使用 '-p' 参数,那样会显示每个改动所在的C函数,使得 +产生的补丁容易读得多。补丁应该基于内核源代码树的根目录,而不是里边的任 +何子目录。 +为一个单独的文件创建补丁,一般来说这样做就够了: + + SRCTREE= linux-2.6 + MYFILE= drivers/net/mydriver.c + + cd $SRCTREE + cp $MYFILE $MYFILE.orig + vi $MYFILE # make your change + cd .. + diff -up $SRCTREE/$MYFILE{.orig,} > /tmp/patch + +为多个文件创建补丁,你可以解开一个没有修改过的内核源代码树,然后和你自 +己的代码树之间做 diff 。例如: + + MYSRC= /devel/linux-2.6 + + tar xvfz linux-2.6.12.tar.gz + mv linux-2.6.12 linux-2.6.12-vanilla + diff -uprN -X linux-2.6.12-vanilla/Documentation/dontdiff \ + linux-2.6.12-vanilla $MYSRC > /tmp/patch + +"dontdiff" 是内核在编译的时候产生的文件的列表,列表中的文件在 diff(1) +产生的补丁里会被跳过。"dontdiff" 文件被包含在2.6.12和之后版本的内核源代 +码树中。对于更早的内核版本,你可以从 + 获取它。 +确定你的补丁里没有包含任何不属于这次补丁提交的额外文件。记得在用diff(1) +生成补丁之后,审阅一次补丁,以确保准确。 +如果你的改动很散乱,你应该研究一下如何将补丁分割成独立的部分,将改动分 +割成一系列合乎逻辑的步骤。这样更容易让其他内核开发者审核,如果你想你的 +补丁被接受,这是很重要的。下面这些脚本能够帮助你做这件事情: +Quilt: +http://savannah.nongnu.org/projects/quilt + +2)描述你的改动。 +描述你的改动包含的技术细节。 + +要多具体就写多具体。最糟糕的描述可能是像下面这些语句:“更新了某驱动程 +序”,“修正了某驱动程序的bug”,或者“这个补丁包含了某子系统的修改,请 +使用。” + +如果你的描述开始变长,这表示你也许需要拆分你的补丁了,请看第3小节, +继续。 + +3)拆分你的改动 + +将改动拆分,逻辑类似的放到同一个补丁文件里。 + +例如,如果你的改动里同时有bug修正和性能优化,那么把这些改动拆分到两个或 +者更多的补丁文件中。如果你的改动包含对API的修改,并且修改了驱动程序来适 +应这些新的API,那么把这些修改分成两个补丁。 + +另一方面,如果你将一个单独的改动做成多个补丁文件,那么将它们合并成一个 +单独的补丁文件。这样一个逻辑上单独的改动只被包含在一个补丁文件里。 + +如果有一个补丁依赖另外一个补丁来完成它的改动,那没问题。简单的在你的补 +丁描述里指出“这个补丁依赖某补丁”就好了。 + +如果你不能将补丁浓缩成更少的文件,那么每次大约发送出15个,然后等待审查 +和整合。 + +4)选择 e-mail 的收件人 + +看一遍 MAINTAINERS 文件和源代码,看看你所的改动所在的内核子系统有没有指 +定的维护者。如果有,给他们发e-mail。 + +如果没有找到维护者,或者维护者没有反馈,将你的补丁发送到内核开发者主邮 +件列表 linux-kernel@vger.kernel.org。大部分的内核开发者都跟踪这个邮件列 +表,可以评价你的改动。 + +每次不要发送超过15个补丁到 vger 邮件列表!!! + +Linus Torvalds 是决定改动能否进入 Linux 内核的最终裁决者。他的 e-mail +地址是 。他收到的 e-mail 很多,所以一般 +的说,最好别给他发 e-mail。 + +那些修正bug,“显而易见”的修改或者是类似的只需要很少讨论的补丁可以直接 +发送或者CC给Linus。那些需要讨论或者没有很清楚的好处的补丁,一般先发送到 +linux-kernel邮件列表。只有当补丁被讨论得差不多了,才提交给Linus。 + +5)选择CC( e-mail 抄送)列表 + +除非你有理由不这样做,否则CC linux-kernel@vger.kernel.org。 + +除了 Linus 之外,其他内核开发者也需要注意到你的改动,这样他们才能评论你 +的改动并提供代码审查和建议。linux-kernel 是 Linux 内核开发者主邮件列表 +。其它的邮件列表为特定的子系统提供服务,比如 USB,framebuffer 设备,虚 +拟文件系统,SCSI 子系统,等等。查看 MAINTAINERS 文件来获得和你的改动有 +关的邮件列表。 + +Majordomo lists of VGER.KERNEL.ORG at: + + +如果改动影响了用户空间和内核之间的接口,请给 MAN-PAGES 的维护者(列在 +MAINTAINERS 文件里的)发送一个手册页(man-pages)补丁,或者至少通知一下改 +变,让一些信息有途径进入手册页。 + +即使在第四步的时候,维护者没有作出回应,也要确认在修改他们的代码的时候 +,一直将维护者拷贝到CC列表中。 + +对于小的补丁,你也许会CC到 Adrian Bunk 管理的搜集琐碎补丁的邮件列表 +(Trivial Patch Monkey)trivial@kernel.org,那里专门收集琐碎的补丁。下面这样 +的补丁会被看作“琐碎的”补丁: + 文档的拼写修正。 + 修正会影响到 grep(1) 的拼写。 + 警告信息修正(频繁的打印无用的警告是不好的。) + 编译错误修正(代码逻辑的确是对的,只是编译有问题。) + 运行时修正(只要真的修正了错误。) + 移除使用了被废弃的函数/宏的代码(例如 check_region。) + 联系方式和文档修正。 + 用可移植的代码替换不可移植的代码(即使在体系结构相关的代码中,既然有 + 人拷贝,只要它是琐碎的) + 任何文件的作者/维护者对该文件的改动(例如 patch monkey 在重传模式下) + +EMAIL: trivial@kernel.org + +(译注,关于“琐碎补丁”的一些说明:因为原文的这一部分写得比较简单,所以不得不 +违例写一下译注。"trivial"这个英文单词的本意是“琐碎的,不重要的。”但是在这里 +有稍微有一些变化,例如对一些明显的NULL指针的修正,属于运行时修正,会被归类 +到琐碎补丁里。虽然NULL指针的修正很重要,但是这样的修正往往很小而且很容易得到 +检验,所以也被归入琐碎补丁。琐碎补丁更精确的归类应该是 +“simple, localized & easy to verify”,也就是说简单的,局部的和易于检验的。 +trivial@kernel.org邮件列表的目的是针对这样的补丁,为提交者提供一个中心,来 +降低提交的门槛。) + +6)没有 MIME 编码,没有链接,没有压缩,没有附件,只有纯文本。 + +Linus 和其他的内核开发者需要阅读和评论你提交的改动。对于内核开发者来说 +,可以“引用”你的改动很重要,使用一般的 e-mail 工具,他们就可以在你的 +代码的任何位置添加评论。 + +因为这个原因,所有的提交的补丁都是 e-mail 中“内嵌”的。 +警告:如果你使用剪切-粘贴你的补丁,小心你的编辑器的自动换行功能破坏你的 +补丁。 + +不要将补丁作为 MIME 编码的附件,不管是否压缩。很多流行的 e-mail 软件不 +是任何时候都将 MIME 编码的附件当作纯文本发送的,这会使得别人无法在你的 +代码中加评论。另外,MIME 编码的附件会让 Linus 多花一点时间来处理,这就 +降低了你的改动被接受的可能性。 + +警告:一些邮件软件,比如 Mozilla 会将你的信息以如下格式发送: +---- 邮件头 ---- +Content-Type: text/plain; charset=us-ascii; format=flowed +---- 邮件头 ---- +问题在于 “format=flowed” 会让接收端的某些邮件软件将邮件中的制表符替换 +成空格以及做一些类似的替换。这样,你发送的时候看起来没问题的补丁就被破 +坏了。 + +要修正这个问题,只需要将你的 mozilla 的 defaults/pref/mailnews.js 文件 +里的 +pref("mailnews.send_plaintext_flowed", false); // RFC 2646======= +修改成 +pref("mailnews.display.disable_format_flowed_support", true); +就可以了。 + +7) e-mail 的大小 + +给 Linus 发送补丁的时候,永远按照第6小节说的做。 + +大的改动对邮件列表不合适,对某些维护者也不合适。如果你的补丁,在不压缩 +的情况下,超过了40kB,那么你最好将补丁放在一个能通过 internet 访问的服 +务器上,然后用指向你的补丁的 URL 替代。 + +8) 指出你的内核版本 + +在标题和在补丁的描述中,指出补丁对应的内核的版本,是很重要的。 + +如果补丁不能干净的在最新版本的内核上打上,Linus 是不会接受它的。 + +9) 不要气馁,继续提交。 + +当你提交了改动以后,耐心地等待。如果 Linus 喜欢你的改动并且同意它,那么 +它将在下一个内核发布版本中出现。 + +然而,如果你的改动没有出现在下一个版本的内核中,可能有若干原因。减少那 +些原因,修正错误,重新提交更新后的改动,是你自己的工作。 + +Linus不给出任何评论就“丢弃”你的补丁是常见的事情。在系统中这样的事情很 +平常。如果他没有接受你的补丁,也许是由于以下原因: +* 你的补丁不能在最新版本的内核上干净的打上。 +* 你的补丁在 linux-kernel 邮件列表中没有得到充分的讨论。 +* 风格问题(参照第2小节) +* 邮件格式问题(重读本节) +* 你的改动有技术问题。 +* 他收到了成吨的 e-mail,而你的在混乱中丢失了。 +* 你让人为难。 + +有疑问的时候,在 linux-kernel 邮件列表上请求评论。 + +10) 在标题上加上 PATCH 的字样 + +Linus 和 linux-kernel 邮件列表的 e-mail 流量都很高,一个通常的约定是标 +题行以 [PATCH] 开头。这样可以让 Linus 和其他内核开发人员可以从 e-mail +的讨论中很轻易的将补丁分辨出来。 + +11)为你的工作签名 + +为了加强对谁做了何事的追踪,尤其是对那些透过好几层的维护者的补丁,我们 +建议在发送出去的补丁上加一个 “sign-off” 的过程。 + +"sign-off" 是在补丁的注释的最后的简单的一行文字,认证你编写了它或者其他 +人有权力将它作为开放源代码的补丁传递。规则很简单:如果你能认证如下信息 +: + 开发者来源证书 1.1 + 对于本项目的贡献,我认证如下信息: + (a)这些贡献是完全或者部分的由我创建,我有权利以文件中指出 + 的开放源代码许可证提交它;或者 + (b)这些贡献基于以前的工作,据我所知,这些以前的工作受恰当的开放 + 源代码许可证保护,而且,根据许可证,我有权提交修改后的贡献, + 无论是完全还是部分由我创造,这些贡献都使用同一个开放源代码许可证 + (除非我被允许用其它的许可证),正如文件中指出的;或者 + (c)这些贡献由认证(a),(b)或者(c)的人直接提供给我,而 + 且我没有修改它。 + (d)我理解并同意这个项目和贡献是公开的,贡献的记录(包括我 + 一起提交的个人记录,包括 sign-off )被永久维护并且可以和这个项目 + 或者开放源代码的许可证同步地再发行。 + 那么加入这样一行: + Signed-off-by: Random J Developer + +使用你的真名(抱歉,不能使用假名或者匿名。) + +有人在最后加上标签。现在这些东西会被忽略,但是你可以这样做,来标记公司 +内部的过程,或者只是指出关于 sign-off 的一些特殊细节。 + +12)标准补丁格式 + +标准的补丁,标题行是: + Subject: [PATCH 001/123] 子系统:一句话概述 + +标准补丁的信体存在如下部分: + + - 一个 "from" 行指出补丁作者。 + + - 一个空行 + + - 说明的主体,这些说明文字会被拷贝到描述该补丁的永久改动记录里。 + + - 一个由"---"构成的标记行 + + - 不合适放到改动记录里的额外的注解。 + + - 补丁本身(diff 输出) + +标题行的格式,使得对标题行按字母序排序非常的容易 - 很多 e-mail 客户端都 +可以支持 - 因为序列号是用零填充的,所以按数字排序和按字母排序是一样的。 + +e-mail 标题中的“子系统”标识哪个内核子系统将被打补丁。 + +e-mail 标题中的“一句话概述”扼要的描述 e-mail 中的补丁。“一句话概述” +不应该是一个文件名。对于一个补丁系列(“补丁系列”指一系列的多个相关补 +丁),不要对每个补丁都使用同样的“一句话概述”。 + +记住 e-mail 的“一句话概述”会成为该补丁的全局唯一标识。它会蔓延到 git +的改动记录里。然后“一句话概述”会被用在开发者的讨论里,用来指代这个补 +丁。用户将希望通过 google 来搜索"一句话概述"来找到那些讨论这个补丁的文 +章。 + +一些标题的例子: + + Subject: [patch 2/5] ext2: improve scalability of bitmap searching + Subject: [PATCHv2 001/207] x86: fix eflags tracking + +"from" 行是信体里的最上面一行,具有如下格式: + From: Original Author + +"from" 行指明在永久改动日志里,谁会被确认为作者。如果没有 "from" 行,那 +么邮件头里的 "From: " 行会被用来决定改动日志中的作者。 + +说明的主题将会被提交到永久的源代码改动日志里,因此对那些早已经不记得和 +这个补丁相关的讨论细节的有能力的读者来说,是有意义的。 + +"---" 标记行对于补丁处理工具要找到哪里是改动日志信息的结束,是不可缺少 +的。 + +对于 "---" 标记之后的额外注解,一个好的用途就是用来写 diffstat,用来显 +示修改了什么文件和每个文件都增加和删除了多少行。diffstat 对于比较大的补 +丁特别有用。其余那些只是和时刻或者开发者相关的注解,不合适放到永久的改 +动日志里的,也应该放这里。 +使用 diffstat的选项 "-p 1 -w 70" 这样文件名就会从内核源代码树的目录开始 +,不会占用太宽的空间(很容易适合80列的宽度,也许会有一些缩进。) + +在后面的参考资料中能看到适当的补丁格式的更多细节。 + +------------------------------- +第二节 提示,建议和诀窍 +------------------------------- + +本节包含很多和提交到内核的代码有关的通常的"规则"。事情永远有例外...但是 +你必须真的有好的理由这样做。你可以把本节叫做Linus的计算机科学入门课。 + +1) 读 Document/process/coding-style.rst + +Nuff 说过,如果你的代码和这个偏离太多,那么它有可能会被拒绝,没有更多的 +审查,没有更多的评价。 + +2) #ifdef 是丑陋的 +混杂了 ifdef 的代码难以阅读和维护。别这样做。作为替代,将你的 ifdef 放 +在头文件里,有条件地定义 "static inline" 函数,或者宏,在代码里用这些东 +西。让编译器把那些"空操作"优化掉。 + +一个简单的例子,不好的代码: + + dev = alloc_etherdev (sizeof(struct funky_private)); + if (!dev) + return -ENODEV; + #ifdef CONFIG_NET_FUNKINESS + init_funky_net(dev); + #endif + +清理后的例子: + +(头文件里) + #ifndef CONFIG_NET_FUNKINESS + static inline void init_funky_net (struct net_device *d) {} + #endif + +(代码文件里) + dev = alloc_etherdev (sizeof(struct funky_private)); + if (!dev) + return -ENODEV; + init_funky_net(dev); + +3) 'static inline' 比宏好 + +Static inline 函数相比宏来说,是好得多的选择。Static inline 函数提供了 +类型安全,没有长度限制,没有格式限制,在 gcc 下开销和宏一样小。 + +宏只在 static inline 函数不是最优的时候[在 fast paths 里有很少的独立的 +案例],或者不可能用 static inline 函数的时候[例如字符串分配]。 +应该用 'static inline' 而不是 'static __inline__', 'extern inline' 和 +'extern __inline__' 。 + +4) 不要过度设计 + +不要试图预计模糊的未来事情,这些事情也许有用也许没有用:"让事情尽可能的 +简单,而不是更简单"。 + +---------------- +第三节 参考文献 +---------------- + +Andrew Morton, "The perfect patch" (tpp). + + +Jeff Garzik, "Linux kernel patch submission format". + + +Greg Kroah-Hartman, "How to piss off a kernel subsystem maintainer". + + + + + +NO!!!! No more huge patch bombs to linux-kernel@vger.kernel.org people! + + +Kernel Documentation/process/coding-style.rst: + + +Linus Torvalds's mail on the canonical patch format: + +-- diff --git a/Documentation/translations/zh_CN/process/coding-style.rst b/Documentation/translations/zh_CN/process/coding-style.rst new file mode 100644 index 000000000000..3cb09803e084 --- /dev/null +++ b/Documentation/translations/zh_CN/process/coding-style.rst @@ -0,0 +1,967 @@ +Chinese translated version of Documentation/process/coding-style.rst + +If you have any comment or update to the content, please post to LKML directly. +However, if you have problem communicating in English you can also ask the +Chinese maintainer for help. Contact the Chinese maintainer, if this +translation is outdated or there is problem with translation. + +Chinese maintainer: Zhang Le + +--------------------------------------------------------------------- + +Documentation/process/coding-style.rst 的中文翻译 + +如果想评论或更新本文的内容,请直接发信到LKML。如果你使用英文交流有困难的话, +也可以向中文版维护者求助。如果本翻译更新不及时或者翻译存在问题,请联系中文版 +维护者:: + + 中文版维护者: 张乐 Zhang Le + 中文版翻译者: 张乐 Zhang Le + 中文版校译者: 王聪 Wang Cong + wheelz + 管旭东 Xudong Guan + Li Zefan + Wang Chen + +以下为正文 + +--------------------------------------------------------------------- + +Linux 内核代码风格 +========================= + +这是一个简短的文档,描述了 linux 内核的首选代码风格。代码风格是因人而异的, +而且我不愿意把自己的观点强加给任何人,但这就像我去做任何事情都必须遵循的原则 +那样,我也希望在绝大多数事上保持这种的态度。请 (在写代码时) 至少考虑一下这里 +的代码风格。 + +首先,我建议你打印一份 GNU 代码规范,然后不要读。烧了它,这是一个具有重大象征 +性意义的动作。 + +不管怎样,现在我们开始: + + +1) 缩进 +-------------- + +制表符是 8 个字符,所以缩进也是 8 个字符。有些异端运动试图将缩进变为 4 (甚至 +2!) 字符深,这几乎相当于尝试将圆周率的值定义为 3。 + +理由:缩进的全部意义就在于清楚的定义一个控制块起止于何处。尤其是当你盯着你的 +屏幕连续看了 20 小时之后,你将会发现大一点的缩进会使你更容易分辨缩进。 + +现在,有些人会抱怨 8 个字符的缩进会使代码向右边移动的太远,在 80 个字符的终端 +屏幕上就很难读这样的代码。这个问题的答案是,如果你需要 3 级以上的缩进,不管用 +何种方式你的代码已经有问题了,应该修正你的程序。 + +简而言之,8 个字符的缩进可以让代码更容易阅读,还有一个好处是当你的函数嵌套太 +深的时候可以给你警告。留心这个警告。 + +在 switch 语句中消除多级缩进的首选的方式是让 ``switch`` 和从属于它的 ``case`` +标签对齐于同一列,而不要 ``两次缩进`` ``case`` 标签。比如: + +.. code-block:: c + + switch (suffix) { + case 'G': + case 'g': + mem <<= 30; + break; + case 'M': + case 'm': + mem <<= 20; + break; + case 'K': + case 'k': + mem <<= 10; + /* fall through */ + default: + break; + } + +不要把多个语句放在一行里,除非你有什么东西要隐藏: + +.. code-block:: c + + if (condition) do_this; + do_something_everytime; + +也不要在一行里放多个赋值语句。内核代码风格超级简单。就是避免可能导致别人误读 +的表达式。 + +除了注释、文档和 Kconfig 之外,不要使用空格来缩进,前面的例子是例外,是有意为 +之。 + +选用一个好的编辑器,不要在行尾留空格。 + + +2) 把长的行和字符串打散 +------------------------------ + +代码风格的意义就在于使用平常使用的工具来维持代码的可读性和可维护性。 + +每一行的长度的限制是 80 列,我们强烈建议您遵守这个惯例。 + +长于 80 列的语句要打散成有意义的片段。除非超过 80 列能显著增加可读性,并且不 +会隐藏信息。子片段要明显短于母片段,并明显靠右。这同样适用于有着很长参数列表 +的函数头。然而,绝对不要打散对用户可见的字符串,例如 printk 信息,因为这样就 +很难对它们 grep。 + + +3) 大括号和空格的放置 +------------------------------ + +C 语言风格中另外一个常见问题是大括号的放置。和缩进大小不同,选择或弃用某种放 +置策略并没有多少技术上的原因,不过首选的方式,就像 Kernighan 和 Ritchie 展示 +给我们的,是把起始大括号放在行尾,而把结束大括号放在行首,所以: + +.. code-block:: c + + if (x is true) { + we do y + } + +这适用于所有的非函数语句块 (if, switch, for, while, do)。比如: + +.. code-block:: c + + switch (action) { + case KOBJ_ADD: + return "add"; + case KOBJ_REMOVE: + return "remove"; + case KOBJ_CHANGE: + return "change"; + default: + return NULL; + } + +不过,有一个例外,那就是函数:函数的起始大括号放置于下一行的开头,所以: + +.. code-block:: c + + int function(int x) + { + body of function + } + +全世界的异端可能会抱怨这个不一致性是... 呃... 不一致的,不过所有思维健全的人 +都知道 (a) K&R 是 **正确的** 并且 (b) K&R 是正确的。此外,不管怎样函数都是特 +殊的 (C 函数是不能嵌套的)。 + +注意结束大括号独自占据一行,除非它后面跟着同一个语句的剩余部分,也就是 do 语 +句中的 "while" 或者 if 语句中的 "else",像这样: + +.. code-block:: c + + do { + body of do-loop + } while (condition); + +和 + +.. code-block:: c + + if (x == y) { + .. + } else if (x > y) { + ... + } else { + .... + } + +理由:K&R。 + +也请注意这种大括号的放置方式也能使空 (或者差不多空的) 行的数量最小化,同时不 +失可读性。因此,由于你的屏幕上的新行是不可再生资源 (想想 25 行的终端屏幕),你 +将会有更多的空行来放置注释。 + +当只有一个单独的语句的时候,不用加不必要的大括号。 + +.. code-block:: c + + if (condition) + action(); + +和 + +.. code-block:: c + + if (condition) + do_this(); + else + do_that(); + +这并不适用于只有一个条件分支是单语句的情况;这时所有分支都要使用大括号: + +.. code-block:: c + + if (condition) { + do_this(); + do_that(); + } else { + otherwise(); + } + +3.1) 空格 +******************** + +Linux 内核的空格使用方式 (主要) 取决于它是用于函数还是关键字。(大多数) 关键字 +后要加一个空格。值得注意的例外是 sizeof, typeof, alignof 和 __attribute__,这 +些关键字某些程度上看起来更像函数 (它们在 Linux 里也常常伴随小括号而使用,尽管 +在 C 里这样的小括号不是必需的,就像 ``struct fileinfo info;`` 声明过后的 +``sizeof info``)。 + +所以在这些关键字之后放一个空格:: + + if, switch, case, for, do, while + +但是不要在 sizeof, typeof, alignof 或者 __attribute__ 这些关键字之后放空格。 +例如, + +.. code-block:: c + + s = sizeof(struct file); + +不要在小括号里的表达式两侧加空格。这是一个 **反例** : + +.. code-block:: c + + s = sizeof( struct file ); + +当声明指针类型或者返回指针类型的函数时, ``*`` 的首选使用方式是使之靠近变量名 +或者函数名,而不是靠近类型名。例子: + +.. code-block:: c + + char *linux_banner; + unsigned long long memparse(char *ptr, char **retptr); + char *match_strdup(substring_t *s); + +在大多数二元和三元操作符两侧使用一个空格,例如下面所有这些操作符:: + + = + - < > * / % | & ^ <= >= == != ? : + +但是一元操作符后不要加空格:: + + & * + - ~ ! sizeof typeof alignof __attribute__ defined + +后缀自加和自减一元操作符前不加空格:: + + ++ -- + +前缀自加和自减一元操作符后不加空格:: + + ++ -- + +``.`` 和 ``->`` 结构体成员操作符前后不加空格。 + +不要在行尾留空白。有些可以自动缩进的编辑器会在新行的行首加入适量的空白,然后 +你就可以直接在那一行输入代码。不过假如你最后没有在那一行输入代码,有些编辑器 +就不会移除已经加入的空白,就像你故意留下一个只有空白的行。包含行尾空白的行就 +这样产生了。 + +当 git 发现补丁包含了行尾空白的时候会警告你,并且可以应你的要求去掉行尾空白; +不过如果你是正在打一系列补丁,这样做会导致后面的补丁失败,因为你改变了补丁的 +上下文。 + + +4) 命名 +------------------------------ + +C 是一个简朴的语言,你的命名也应该这样。和 Modula-2 和 Pascal 程序员不同, +C 程序员不使用类似 ThisVariableIsATemporaryCounter 这样华丽的名字。C 程序员会 +称那个变量为 ``tmp`` ,这样写起来会更容易,而且至少不会令其难于理解。 + +不过,虽然混用大小写的名字是不提倡使用的,但是全局变量还是需要一个具描述性的 +名字。称一个全局函数为 ``foo`` 是一个难以饶恕的错误。 + +全局变量 (只有当你 **真正** 需要它们的时候再用它) 需要有一个具描述性的名字,就 +像全局函数。如果你有一个可以计算活动用户数量的函数,你应该叫它 +``count_active_users()`` 或者类似的名字,你不应该叫它 ``cntuser()`` 。 + +在函数名中包含函数类型 (所谓的匈牙利命名法) 是脑子出了问题——编译器知道那些类 +型而且能够检查那些类型,这样做只能把程序员弄糊涂了。难怪微软总是制造出有问题 +的程序。 + +本地变量名应该简短,而且能够表达相关的含义。如果你有一些随机的整数型的循环计 +数器,它应该被称为 ``i`` 。叫它 ``loop_counter`` 并无益处,如果它没有被误解的 +可能的话。类似的, ``tmp`` 可以用来称呼任意类型的临时变量。 + +如果你怕混淆了你的本地变量名,你就遇到另一个问题了,叫做函数增长荷尔蒙失衡综 +合症。请看第六章 (函数)。 + + +5) Typedef +----------- + +不要使用类似 ``vps_t`` 之类的东西。 + +对结构体和指针使用 typedef 是一个 **错误** 。当你在代码里看到: + +.. code-block:: c + + vps_t a; + +这代表什么意思呢? + +相反,如果是这样 + +.. code-block:: c + + struct virtual_container *a; + +你就知道 ``a`` 是什么了。 + +很多人认为 typedef ``能提高可读性`` 。实际不是这样的。它们只在下列情况下有用: + + (a) 完全不透明的对象 (这种情况下要主动使用 typedef 来 **隐藏** 这个对象实际上 + 是什么)。 + + 例如: ``pte_t`` 等不透明对象,你只能用合适的访问函数来访问它们。 + + .. note:: + + 不透明性和 "访问函数" 本身是不好的。我们使用 pte_t 等类型的原因在于真 + 的是完全没有任何共用的可访问信息。 + + (b) 清楚的整数类型,如此,这层抽象就可以 **帮助** 消除到底是 ``int`` 还是 + ``long`` 的混淆。 + + u8/u16/u32 是完全没有问题的 typedef,不过它们更符合类别 (d) 而不是这里。 + + .. note:: + + 要这样做,必须事出有因。如果某个变量是 ``unsigned long`` ,那么没有必要 + + typedef unsigned long myflags_t; + + 不过如果有一个明确的原因,比如它在某种情况下可能会是一个 ``unsigned int`` + 而在其他情况下可能为 ``unsigned long`` ,那么就不要犹豫,请务必使用 + typedef。 + + (c) 当你使用 sparse 按字面的创建一个 **新** 类型来做类型检查的时候。 + + (d) 和标准 C99 类型相同的类型,在某些例外的情况下。 + + 虽然让眼睛和脑筋来适应新的标准类型比如 ``uint32_t`` 不需要花很多时间,可 + 是有些人仍然拒绝使用它们。 + + 因此,Linux 特有的等同于标准类型的 ``u8/u16/u32/u64`` 类型和它们的有符号 + 类型是被允许的——尽管在你自己的新代码中,它们不是强制要求要使用的。 + + 当编辑已经使用了某个类型集的已有代码时,你应该遵循那些代码中已经做出的选 + 择。 + + (e) 可以在用户空间安全使用的类型。 + + 在某些用户空间可见的结构体里,我们不能要求 C99 类型而且不能用上面提到的 + ``u32`` 类型。因此,我们在与用户空间共享的所有结构体中使用 __u32 和类似 + 的类型。 + +可能还有其他的情况,不过基本的规则是 **永远不要** 使用 typedef,除非你可以明 +确的应用上述某个规则中的一个。 + +总的来说,如果一个指针或者一个结构体里的元素可以合理的被直接访问到,那么它们 +就不应该是一个 typedef。 + + +6) 函数 +------------------------------ + +函数应该简短而漂亮,并且只完成一件事情。函数应该可以一屏或者两屏显示完 (我们 +都知道 ISO/ANSI 屏幕大小是 80x24),只做一件事情,而且把它做好。 + +一个函数的最大长度是和该函数的复杂度和缩进级数成反比的。所以,如果你有一个理 +论上很简单的只有一个很长 (但是简单) 的 case 语句的函数,而且你需要在每个 case +里做很多很小的事情,这样的函数尽管很长,但也是可以的。 + +不过,如果你有一个复杂的函数,而且你怀疑一个天分不是很高的高中一年级学生可能 +甚至搞不清楚这个函数的目的,你应该严格遵守前面提到的长度限制。使用辅助函数, +并为之取个具描述性的名字 (如果你觉得它们的性能很重要的话,可以让编译器内联它 +们,这样的效果往往会比你写一个复杂函数的效果要好。) + +函数的另外一个衡量标准是本地变量的数量。此数量不应超过 5-10 个,否则你的函数 +就有问题了。重新考虑一下你的函数,把它分拆成更小的函数。人的大脑一般可以轻松 +的同时跟踪 7 个不同的事物,如果再增多的话,就会糊涂了。即便你聪颖过人,你也可 +能会记不清你 2 个星期前做过的事情。 + +在源文件里,使用空行隔开不同的函数。如果该函数需要被导出,它的 **EXPORT** 宏 +应该紧贴在它的结束大括号之下。比如: + +.. code-block:: c + + int system_is_up(void) + { + return system_state == SYSTEM_RUNNING; + } + EXPORT_SYMBOL(system_is_up); + +在函数原型中,包含函数名和它们的数据类型。虽然 C 语言里没有这样的要求,在 +Linux 里这是提倡的做法,因为这样可以很简单的给读者提供更多的有价值的信息。 + + +7) 集中的函数退出途径 +------------------------------ + +虽然被某些人声称已经过时,但是 goto 语句的等价物还是经常被编译器所使用,具体 +形式是无条件跳转指令。 + +当一个函数从多个位置退出,并且需要做一些类似清理的常见操作时,goto 语句就很方 +便了。如果并不需要清理操作,那么直接 return 即可。 + +选择一个能够说明 goto 行为或它为何存在的标签名。如果 goto 要释放 ``buffer``, +一个不错的名字可以是 ``out_free_buffer:`` 。别去使用像 ``err1:`` 和 ``err2:`` +这样的GW_BASIC 名称,因为一旦你添加或删除了 (函数的) 退出路径,你就必须对它们 +重新编号,这样会难以去检验正确性。 + +使用 goto 的理由是: + +- 无条件语句容易理解和跟踪 +- 嵌套程度减小 +- 可以避免由于修改时忘记更新个别的退出点而导致错误 +- 让编译器省去删除冗余代码的工作 ;) + +.. code-block:: c + + int fun(int a) + { + int result = 0; + char *buffer; + + buffer = kmalloc(SIZE, GFP_KERNEL); + if (!buffer) + return -ENOMEM; + + if (condition1) { + while (loop1) { + ... + } + result = 1; + goto out_free_buffer; + } + ... + out_free_buffer: + kfree(buffer); + return result; + } + +一个需要注意的常见错误是 ``一个 err 错误`` ,就像这样: + +.. code-block:: c + + err: + kfree(foo->bar); + kfree(foo); + return ret; + +这段代码的错误是,在某些退出路径上 ``foo`` 是 NULL。通常情况下,通过把它分离 +成两个错误标签 ``err_free_bar:`` 和 ``err_free_foo:`` 来修复这个错误: + +.. code-block:: c + + err_free_bar: + kfree(foo->bar); + err_free_foo: + kfree(foo); + return ret; + +理想情况下,你应该模拟错误来测试所有退出路径。 + + +8) 注释 +------------------------------ + +注释是好的,不过有过度注释的危险。永远不要在注释里解释你的代码是如何运作的: +更好的做法是让别人一看你的代码就可以明白,解释写的很差的代码是浪费时间。 + +一般的,你想要你的注释告诉别人你的代码做了什么,而不是怎么做的。也请你不要把 +注释放在一个函数体内部:如果函数复杂到你需要独立的注释其中的一部分,你很可能 +需要回到第六章看一看。你可以做一些小注释来注明或警告某些很聪明 (或者槽糕) 的 +做法,但不要加太多。你应该做的,是把注释放在函数的头部,告诉人们它做了什么, +也可以加上它做这些事情的原因。 + +当注释内核 API 函数时,请使用 kernel-doc 格式。请看 +Documentation/doc-guide/ 和 scripts/kernel-doc 以获得详细信息。 + +长 (多行) 注释的首选风格是: + +.. code-block:: c + + /* + * This is the preferred style for multi-line + * comments in the Linux kernel source code. + * Please use it consistently. + * + * Description: A column of asterisks on the left side, + * with beginning and ending almost-blank lines. + */ + +对于在 net/ 和 drivers/net/ 的文件,首选的长 (多行) 注释风格有些不同。 + +.. code-block:: c + + /* The preferred comment style for files in net/ and drivers/net + * looks like this. + * + * It is nearly the same as the generally preferred comment style, + * but there is no initial almost-blank line. + */ + +注释数据也是很重要的,不管是基本类型还是衍生类型。为了方便实现这一点,每一行 +应只声明一个数据 (不要使用逗号来一次声明多个数据)。这样你就有空间来为每个数据 +写一段小注释来解释它们的用途了。 + + +9) 你已经把事情弄糟了 +------------------------------ + +这没什么,我们都是这样。可能你的使用了很长时间 Unix 的朋友已经告诉你 +``GNU emacs`` 能自动帮你格式化 C 源代码,而且你也注意到了,确实是这样,不过它 +所使用的默认值和我们想要的相去甚远 (实际上,甚至比随机打的还要差——无数个猴子 +在 GNU emacs 里打字永远不会创造出一个好程序) (译注:Infinite Monkey Theorem) + +所以你要么放弃 GNU emacs,要么改变它让它使用更合理的设定。要采用后一个方案, +你可以把下面这段粘贴到你的 .emacs 文件里。 + +.. code-block:: none + + (defun c-lineup-arglist-tabs-only (ignored) + "Line up argument lists by tabs, not spaces" + (let* ((anchor (c-langelem-pos c-syntactic-element)) + (column (c-langelem-2nd-pos c-syntactic-element)) + (offset (- (1+ column) anchor)) + (steps (floor offset c-basic-offset))) + (* (max steps 1) + c-basic-offset))) + + (dir-locals-set-class-variables + 'linux-kernel + '((c-mode . ( + (c-basic-offset . 8) + (c-label-minimum-indentation . 0) + (c-offsets-alist . ( + (arglist-close . c-lineup-arglist-tabs-only) + (arglist-cont-nonempty . + (c-lineup-gcc-asm-reg c-lineup-arglist-tabs-only)) + (arglist-intro . +) + (brace-list-intro . +) + (c . c-lineup-C-comments) + (case-label . 0) + (comment-intro . c-lineup-comment) + (cpp-define-intro . +) + (cpp-macro . -1000) + (cpp-macro-cont . +) + (defun-block-intro . +) + (else-clause . 0) + (func-decl-cont . +) + (inclass . +) + (inher-cont . c-lineup-multi-inher) + (knr-argdecl-intro . 0) + (label . -1000) + (statement . 0) + (statement-block-intro . +) + (statement-case-intro . +) + (statement-cont . +) + (substatement . +) + )) + (indent-tabs-mode . t) + (show-trailing-whitespace . t) + )))) + + (dir-locals-set-directory-class + (expand-file-name "~/src/linux-trees") + 'linux-kernel) + +这会让 emacs 在 ``~/src/linux-trees`` 下的 C 源文件获得更好的内核代码风格。 + +不过就算你尝试让 emacs 正确的格式化代码失败了,也并不意味着你失去了一切:还可 +以用 ``indent`` 。 + +不过,GNU indent 也有和 GNU emacs 一样有问题的设定,所以你需要给它一些命令选 +项。不过,这还不算太糟糕,因为就算是 GNU indent 的作者也认同 K&R 的权威性 +(GNU 的人并不是坏人,他们只是在这个问题上被严重的误导了),所以你只要给 indent +指定选项 ``-kr -i8`` (代表 ``K&R,8 字符缩进``),或使用 ``scripts/Lindent`` +这样就可以以最时髦的方式缩进源代码。 + +``indent`` 有很多选项,特别是重新格式化注释的时候,你可能需要看一下它的手册。 +不过记住: ``indent`` 不能修正坏的编程习惯。 + + +10) Kconfig 配置文件 +------------------------------ + +对于遍布源码树的所有 Kconfig* 配置文件来说,它们缩进方式有所不同。紧挨着 +``config`` 定义的行,用一个制表符缩进,然而 help 信息的缩进则额外增加 2 个空 +格。举个例子:: + + config AUDIT + bool "Auditing support" + depends on NET + help + Enable auditing infrastructure that can be used with another + kernel subsystem, such as SELinux (which requires this for + logging of avc messages output). Does not do system-call + auditing without CONFIG_AUDITSYSCALL. + +而那些危险的功能 (比如某些文件系统的写支持) 应该在它们的提示字符串里显著的声 +明这一点:: + + config ADFS_FS_RW + bool "ADFS write support (DANGEROUS)" + depends on ADFS_FS + ... + +要查看配置文件的完整文档,请看 Documentation/kbuild/kconfig-language.txt。 + + +11) 数据结构 +------------------------------ + +如果一个数据结构,在创建和销毁它的单线执行环境之外可见,那么它必须要有一个引 +用计数器。内核里没有垃圾收集 (并且内核之外的垃圾收集慢且效率低下),这意味着你 +绝对需要记录你对这种数据结构的使用情况。 + +引用计数意味着你能够避免上锁,并且允许多个用户并行访问这个数据结构——而不需要 +担心这个数据结构仅仅因为暂时不被使用就消失了,那些用户可能不过是沉睡了一阵或 +者做了一些其他事情而已。 + +注意上锁 **不能** 取代引用计数。上锁是为了保持数据结构的一致性,而引用计数是一 +个内存管理技巧。通常二者都需要,不要把两个搞混了。 + +很多数据结构实际上有 2 级引用计数,它们通常有不同 ``类`` 的用户。子类计数器统 +计子类用户的数量,每当子类计数器减至零时,全局计数器减一。 + +这种 ``多级引用计数`` 的例子可以在内存管理 (``struct mm_struct``: mm_users 和 +mm_count),和文件系统 (``struct super_block``: s_count 和 s_active) 中找到。 + +记住:如果另一个执行线索可以找到你的数据结构,但这个数据结构没有引用计数器, +这里几乎肯定是一个 bug。 + + +12) 宏,枚举和RTL +------------------------------ + +用于定义常量的宏的名字及枚举里的标签需要大写。 + +.. code-block:: c + + #define CONSTANT 0x12345 + +在定义几个相关的常量时,最好用枚举。 + +宏的名字请用大写字母,不过形如函数的宏的名字可以用小写字母。 + +一般的,如果能写成内联函数就不要写成像函数的宏。 + +含有多个语句的宏应该被包含在一个 do-while 代码块里: + +.. code-block:: c + + #define macrofun(a, b, c) \ + do { \ + if (a == 5) \ + do_this(b, c); \ + } while (0) + +使用宏的时候应避免的事情: + +1) 影响控制流程的宏: + +.. code-block:: c + + #define FOO(x) \ + do { \ + if (blah(x) < 0) \ + return -EBUGGERED; \ + } while (0) + +**非常** 不好。它看起来像一个函数,不过却能导致 ``调用`` 它的函数退出;不要打 +乱读者大脑里的语法分析器。 + +2) 依赖于一个固定名字的本地变量的宏: + +.. code-block:: c + + #define FOO(val) bar(index, val) + +可能看起来像是个不错的东西,不过它非常容易把读代码的人搞糊涂,而且容易导致看起 +来不相关的改动带来错误。 + +3) 作为左值的带参数的宏: FOO(x) = y;如果有人把 FOO 变成一个内联函数的话,这 + 种用法就会出错了。 + +4) 忘记了优先级:使用表达式定义常量的宏必须将表达式置于一对小括号之内。带参数 + 的宏也要注意此类问题。 + +.. code-block:: c + + #define CONSTANT 0x4000 + #define CONSTEXP (CONSTANT | 3) + +5) 在宏里定义类似函数的本地变量时命名冲突: + +.. code-block:: c + + #define FOO(x) \ + ({ \ + typeof(x) ret; \ + ret = calc_ret(x); \ + (ret); \ + }) + +ret 是本地变量的通用名字 - __foo_ret 更不容易与一个已存在的变量冲突。 + +cpp 手册对宏的讲解很详细。gcc internals 手册也详细讲解了 RTL,内核里的汇编语 +言经常用到它。 + + +13) 打印内核消息 +------------------------------ + +内核开发者应该是受过良好教育的。请一定注意内核信息的拼写,以给人以好的印象。 +不要用不规范的单词比如 ``dont``,而要用 ``do not`` 或者 ``don't`` 。保证这些信 +息简单明了,无歧义。 + +内核信息不必以英文句号结束。 + +在小括号里打印数字 (%d) 没有任何价值,应该避免这样做。 + + 里有一些驱动模型诊断宏,你应该使用它们,以确保信息对应于正确 +的设备和驱动,并且被标记了正确的消息级别。这些宏有:dev_err(), dev_warn(), +dev_info() 等等。对于那些不和某个特定设备相关连的信息, 定义 +了 pr_notice(), pr_info(), pr_warn(), pr_err() 和其他。 + +写出好的调试信息可以是一个很大的挑战;一旦你写出后,这些信息在远程除错时能提 +供极大的帮助。然而打印调试信息的处理方式同打印非调试信息不同。其他 pr_XXX() +函数能无条件地打印,pr_debug() 却不;默认情况下它不会被编译,除非定义了 DEBUG +或设定了 CONFIG_DYNAMIC_DEBUG。实际这同样是为了 dev_dbg(),一个相关约定是在一 +个已经开启了 DEBUG 时,使用 VERBOSE_DEBUG 来添加 dev_vdbg()。 + +许多子系统拥有 Kconfig 调试选项来开启 -DDEBUG 在对应的 Makefile 里面;在其他 +情况下,特殊文件使用 #define DEBUG。当一条调试信息需要被无条件打印时,例如, +如果已经包含一个调试相关的 #ifdef 条件,printk(KERN_DEBUG ...) 就可被使用。 + + +14) 分配内存 +------------------------------ + +内核提供了下面的一般用途的内存分配函数: +kmalloc(), kzalloc(), kmalloc_array(), kcalloc(), vmalloc() 和 vzalloc()。 +请参考 API 文档以获取有关它们的详细信息。 + +传递结构体大小的首选形式是这样的: + +.. code-block:: c + + p = kmalloc(sizeof(*p), ...); + +另外一种传递方式中,sizeof 的操作数是结构体的名字,这样会降低可读性,并且可能 +会引入 bug。有可能指针变量类型被改变时,而对应的传递给内存分配函数的 sizeof +的结果不变。 + +强制转换一个 void 指针返回值是多余的。C 语言本身保证了从 void 指针到其他任何 +指针类型的转换是没有问题的。 + +分配一个数组的首选形式是这样的: + +.. code-block:: c + + p = kmalloc_array(n, sizeof(...), ...); + +分配一个零长数组的首选形式是这样的: + +.. code-block:: c + + p = kcalloc(n, sizeof(...), ...); + +两种形式检查分配大小 n * sizeof(...) 的溢出,如果溢出返回 NULL。 + + +15) 内联弊病 +------------------------------ + +有一个常见的误解是 ``内联`` 是 gcc 提供的可以让代码运行更快的一个选项。虽然使 +用内联函数有时候是恰当的 (比如作为一种替代宏的方式,请看第十二章),不过很多情 +况下不是这样。inline 的过度使用会使内核变大,从而使整个系统运行速度变慢。 +因为体积大内核会占用更多的指令高速缓存,而且会导致 pagecache 的可用内存减少。 +想象一下,一次 pagecache 未命中就会导致一次磁盘寻址,将耗时 5 毫秒。5 毫秒的 +时间内 CPU 能执行很多很多指令。 + +一个基本的原则是如果一个函数有 3 行以上,就不要把它变成内联函数。这个原则的一 +个例外是,如果你知道某个参数是一个编译时常量,而且因为这个常量你确定编译器在 +编译时能优化掉你的函数的大部分代码,那仍然可以给它加上 inline 关键字。 +kmalloc() 内联函数就是一个很好的例子。 + +人们经常主张给 static 的而且只用了一次的函数加上 inline,如此不会有任何损失, +因为没有什么好权衡的。虽然从技术上说这是正确的,但是实际上这种情况下即使不加 +inline gcc 也可以自动使其内联。而且其他用户可能会要求移除 inline,由此而来的 +争论会抵消 inline 自身的潜在价值,得不偿失。 + + +16) 函数返回值及命名 +------------------------------ + +函数可以返回多种不同类型的值,最常见的一种是表明函数执行成功或者失败的值。这样 +的一个值可以表示为一个错误代码整数 (-Exxx=失败,0=成功) 或者一个 ``成功`` +布尔值 (0=失败,非0=成功)。 + +混合使用这两种表达方式是难于发现的 bug 的来源。如果 C 语言本身严格区分整形和 +布尔型变量,那么编译器就能够帮我们发现这些错误... 不过 C 语言不区分。为了避免 +产生这种 bug,请遵循下面的惯例:: + + 如果函数的名字是一个动作或者强制性的命令,那么这个函数应该返回错误代 + 码整数。如果是一个判断,那么函数应该返回一个 "成功" 布尔值。 + +比如, ``add work`` 是一个命令,所以 add_work() 在成功时返回 0,在失败时返回 +-EBUSY。类似的,因为 ``PCI device present`` 是一个判断,所以 pci_dev_present() +在成功找到一个匹配的设备时应该返回 1,如果找不到时应该返回 0。 + +所有 EXPORTed 函数都必须遵守这个惯例,所有的公共函数也都应该如此。私有 +(static) 函数不需要如此,但是我们也推荐这样做。 + +返回值是实际计算结果而不是计算是否成功的标志的函数不受此惯例的限制。一般的, +他们通过返回一些正常值范围之外的结果来表示出错。典型的例子是返回指针的函数, +他们使用 NULL 或者 ERR_PTR 机制来报告错误。 + + +17) 不要重新发明内核宏 +------------------------------ + +头文件 include/linux/kernel.h 包含了一些宏,你应该使用它们,而不要自己写一些 +它们的变种。比如,如果你需要计算一个数组的长度,使用这个宏 + +.. code-block:: c + + #define ARRAY_SIZE(x) (sizeof(x) / sizeof((x)[0])) + +类似的,如果你要计算某结构体成员的大小,使用 + +.. code-block:: c + + #define FIELD_SIZEOF(t, f) (sizeof(((t*)0)->f)) + +还有可以做严格的类型检查的 min() 和 max() 宏,如果你需要可以使用它们。你可以 +自己看看那个头文件里还定义了什么你可以拿来用的东西,如果有定义的话,你就不应 +在你的代码里自己重新定义。 + + +18) 编辑器模式行和其他需要罗嗦的事情 +-------------------------------------------------- + +有一些编辑器可以解释嵌入在源文件里的由一些特殊标记标明的配置信息。比如,emacs +能够解释被标记成这样的行: + +.. code-block:: c + + -*- mode: c -*- + +或者这样的: + +.. code-block:: c + + /* + Local Variables: + compile-command: "gcc -DMAGIC_DEBUG_FLAG foo.c" + End: + */ + +Vim 能够解释这样的标记: + +.. code-block:: c + + /* vim:set sw=8 noet */ + +不要在源代码中包含任何这样的内容。每个人都有他自己的编辑器配置,你的源文件不 +应该覆盖别人的配置。这包括有关缩进和模式配置的标记。人们可以使用他们自己定制 +的模式,或者使用其他可以产生正确的缩进的巧妙方法。 + + +19) 内联汇编 +------------------------------ + +在特定架构的代码中,你可能需要内联汇编与 CPU 和平台相关功能连接。需要这么做时 +就不要犹豫。然而,当 C 可以完成工作时,不要平白无故地使用内联汇编。在可能的情 +况下,你可以并且应该用 C 和硬件沟通。 + +请考虑去写捆绑通用位元 (wrap common bits) 的内联汇编的简单辅助函数,别去重复 +地写下只有细微差异内联汇编。记住内联汇编可以使用 C 参数。 + +大型,有一定复杂度的汇编函数应该放在 .S 文件内,用相应的 C 原型定义在 C 头文 +件中。汇编函数的 C 原型应该使用 ``asmlinkage`` 。 + +你可能需要把汇编语句标记为 volatile,用来阻止 GCC 在没发现任何副作用后就把它 +移除了。你不必总是这样做,尽管,这不必要的举动会限制优化。 + +在写一个包含多条指令的单个内联汇编语句时,把每条指令用引号分割而且各占一行, +除了最后一条指令外,在每个指令结尾加上 \n\t,让汇编输出时可以正确地缩进下一条 +指令: + +.. code-block:: c + + asm ("magic %reg1, #42\n\t" + "more_magic %reg2, %reg3" + : /* outputs */ : /* inputs */ : /* clobbers */); + + +20) 条件编译 +------------------------------ + +只要可能,就不要在 .c 文件里面使用预处理条件 (#if, #ifdef);这样做让代码更难 +阅读并且更难去跟踪逻辑。替代方案是,在头文件中用预处理条件提供给那些 .c 文件 +使用,再给 #else 提供一个空桩 (no-op stub) 版本,然后在 .c 文件内无条件地调用 +那些 (定义在头文件内的) 函数。这样做,编译器会避免为桩函数 (stub) 的调用生成 +任何代码,产生的结果是相同的,但逻辑将更加清晰。 + +最好倾向于编译整个函数,而不是函数的一部分或表达式的一部分。与其放一个 ifdef +在表达式内,不如分解出部分或全部表达式,放进一个单独的辅助函数,并应用预处理 +条件到这个辅助函数内。 + +如果你有一个在特定配置中,可能变成未使用的函数或变量,编译器会警告它定义了但 +未使用,把它标记为 __maybe_unused 而不是将它包含在一个预处理条件中。(然而,如 +果一个函数或变量总是未使用,就直接删除它。) + +在代码中,尽可能地使用 IS_ENABLED 宏来转化某个 Kconfig 标记为 C 的布尔 +表达式,并在一般的 C 条件中使用它: + +.. code-block:: c + + if (IS_ENABLED(CONFIG_SOMETHING)) { + ... + } + +编译器会做常量折叠,然后就像使用 #ifdef 那样去包含或排除代码块,所以这不会带 +来任何运行时开销。然而,这种方法依旧允许 C 编译器查看块内的代码,并检查它的正 +确性 (语法,类型,符号引用,等等)。因此,如果条件不满足,代码块内的引用符号就 +不存在时,你还是必须去用 #ifdef。 + +在任何有意义的 #if 或 #ifdef 块的末尾 (超过几行的),在 #endif 同一行的后面写下 +注解,注释这个条件表达式。例如: + +.. code-block:: c + + #ifdef CONFIG_SOMETHING + ... + #endif /* CONFIG_SOMETHING */ + + +附录 I) 参考 +------------------- + +The C Programming Language, 第二版 +作者:Brian W. Kernighan 和 Denni M. Ritchie. +Prentice Hall, Inc., 1988. +ISBN 0-13-110362-8 (软皮), 0-13-110370-9 (硬皮). + +The Practice of Programming +作者:Brian W. Kernighan 和 Rob Pike. +Addison-Wesley, Inc., 1999. +ISBN 0-201-61586-X. + +GNU 手册 - 遵循 K&R 标准和此文本 - cpp, gcc, gcc internals and indent, +都可以从 http://www.gnu.org/manual/ 找到 + +WG14 是 C 语言的国际标准化工作组,URL: http://www.open-std.org/JTC1/SC22/WG14/ + +Kernel process/coding-style.rst,作者 greg@kroah.com 发表于 OLS 2002: +http://www.kroah.com/linux/talks/ols_2002_kernel_codingstyle_talk/html/ diff --git a/Documentation/translations/zh_CN/process/email-clients.txt b/Documentation/translations/zh_CN/process/email-clients.txt new file mode 100644 index 000000000000..ec31d97e8d0e --- /dev/null +++ b/Documentation/translations/zh_CN/process/email-clients.txt @@ -0,0 +1,210 @@ +Chinese translated version of Documentation/process/email-clients.rst + +If you have any comment or update to the content, please contact the +original document maintainer directly. However, if you have a problem +communicating in English you can also ask the Chinese maintainer for +help. Contact the Chinese maintainer if this translation is outdated +or if there is a problem with the translation. + +Chinese maintainer: Harry Wei +--------------------------------------------------------------------- +Documentation/process/email-clients.rst 的中文翻译 + +如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 +交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 +译存在问题,请联系中文版维护者。 + +中文版维护者: 贾威威 Harry Wei +中文版翻译者: 贾威威 Harry Wei +中文版校译者: Yinglin Luan + Xiaochen Wang + yaxinsn + +以下为正文 +--------------------------------------------------------------------- + +Linux邮件客户端配置信息 +====================================================================== + +普通配置 +---------------------------------------------------------------------- +Linux内核补丁是通过邮件被提交的,最好把补丁作为邮件体的内嵌文本。有些维护者 +接收附件,但是附件的内容格式应该是"text/plain"。然而,附件一般是不赞成的, +因为这会使补丁的引用部分在评论过程中变的很困难。 + +用来发送Linux内核补丁的邮件客户端在发送补丁时应该处于文本的原始状态。例如, +他们不能改变或者删除制表符或者空格,甚至是在每一行的开头或者结尾。 + +不要通过"format=flowed"模式发送补丁。这样会引起不可预期以及有害的断行。 + +不要让你的邮件客户端进行自动换行。这样也会破坏你的补丁。 + +邮件客户端不能改变文本的字符集编码方式。要发送的补丁只能是ASCII或者UTF-8编码方式, +如果你使用UTF-8编码方式发送邮件,那么你将会避免一些可能发生的字符集问题。 + +邮件客户端应该形成并且保持 References: 或者 In-Reply-To: 标题,那么 +邮件话题就不会中断。 + +复制粘帖(或者剪贴粘帖)通常不能用于补丁,因为制表符会转换为空格。使用xclipboard, xclip +或者xcutsel也许可以,但是最好测试一下或者避免使用复制粘帖。 + +不要在使用PGP/GPG署名的邮件中包含补丁。这样会使得很多脚本不能读取和适用于你的补丁。 +(这个问题应该是可以修复的) + +在给内核邮件列表发送补丁之前,给自己发送一个补丁是个不错的主意,保存接收到的 +邮件,将补丁用'patch'命令打上,如果成功了,再给内核邮件列表发送。 + + +一些邮件客户端提示 +---------------------------------------------------------------------- +这里给出一些详细的MUA配置提示,可以用于给Linux内核发送补丁。这些并不意味是 +所有的软件包配置总结。 + +说明: +TUI = 以文本为基础的用户接口 +GUI = 图形界面用户接口 + +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +Alpine (TUI) + +配置选项: +在"Sending Preferences"部分: + +- "Do Not Send Flowed Text"必须开启 +- "Strip Whitespace Before Sending"必须关闭 + +当写邮件时,光标应该放在补丁会出现的地方,然后按下CTRL-R组合键,使指定的 +补丁文件嵌入到邮件中。 + +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +Evolution (GUI) + +一些开发者成功的使用它发送补丁 + +当选择邮件选项:Preformat + 从Format->Heading->Preformatted (Ctrl-7)或者工具栏 + +然后使用: + Insert->Text File... (Alt-n x)插入补丁文件。 + +你还可以"diff -Nru old.c new.c | xclip",选择Preformat,然后使用中间键进行粘帖。 + +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +Kmail (GUI) + +一些开发者成功的使用它发送补丁。 + +默认设置不为HTML格式是合适的;不要启用它。 + +当书写一封邮件的时候,在选项下面不要选择自动换行。唯一的缺点就是你在邮件中输入的任何文本 +都不会被自动换行,因此你必须在发送补丁之前手动换行。最简单的方法就是启用自动换行来书写邮件, +然后把它保存为草稿。一旦你在草稿中再次打开它,它已经全部自动换行了,那么你的邮件虽然没有 +选择自动换行,但是还不会失去已有的自动换行。 + +在邮件的底部,插入补丁之前,放上常用的补丁定界符:三个连字号(---)。 + +然后在"Message"菜单条目,选择插入文件,接着选取你的补丁文件。还有一个额外的选项,你可以 +通过它配置你的邮件建立工具栏菜单,还可以带上"insert file"图标。 + +你可以安全地通过GPG标记附件,但是内嵌补丁最好不要使用GPG标记它们。作为内嵌文本的签发补丁, +当从GPG中提取7位编码时会使他们变的更加复杂。 + +如果你非要以附件的形式发送补丁,那么就右键点击附件,然后选中属性,突出"Suggest automatic +display",这样内嵌附件更容易让读者看到。 + +当你要保存将要发送的内嵌文本补丁,你可以从消息列表窗格选择包含补丁的邮件,然后右击选择 +"save as"。你可以使用一个没有更改的包含补丁的邮件,如果它是以正确的形式组成。当你正真在它 +自己的窗口之下察看,那时没有选项可以保存邮件--已经有一个这样的bug被汇报到了kmail的bugzilla +并且希望这将会被处理。邮件是以只针对某个用户可读写的权限被保存的,所以如果你想把邮件复制到其他地方, +你不得不把他们的权限改为组或者整体可读。 + +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +Lotus Notes (GUI) + +不要使用它。 + +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +Mutt (TUI) + +很多Linux开发人员使用mutt客户端,所以证明它肯定工作的非常漂亮。 + +Mutt不自带编辑器,所以不管你使用什么编辑器都不应该带有自动断行。大多数编辑器都带有 +一个"insert file"选项,它可以通过不改变文件内容的方式插入文件。 + +'vim'作为mutt的编辑器: + set editor="vi" + + 如果使用xclip,敲入以下命令 + :set paste + 按中键之前或者shift-insert或者使用 + :r filename + +如果想要把补丁作为内嵌文本。 +(a)ttach工作的很好,不带有"set paste"。 + +配置选项: +它应该以默认设置的形式工作。 +然而,把"send_charset"设置为"us-ascii::utf-8"也是一个不错的主意。 + +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +Pine (TUI) + +Pine过去有一些空格删减问题,但是这些现在应该都被修复了。 + +如果可以,请使用alpine(pine的继承者) + +配置选项: +- 最近的版本需要消除流程文本 +- "no-strip-whitespace-before-send"选项也是需要的。 + + +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +Sylpheed (GUI) + +- 内嵌文本可以很好的工作(或者使用附件)。 +- 允许使用外部的编辑器。 +- 对于目录较多时非常慢。 +- 如果通过non-SSL连接,无法使用TLS SMTP授权。 +- 在组成窗口中有一个很有用的ruler bar。 +- 给地址本中添加地址就不会正确的了解显示名。 + +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +Thunderbird (GUI) + +默认情况下,thunderbird很容易损坏文本,但是还有一些方法可以强制它变得更好。 + +- 在用户帐号设置里,组成和寻址,不要选择"Compose messages in HTML format"。 + +- 编辑你的Thunderbird配置设置来使它不要拆行使用:user_pref("mailnews.wraplength", 0); + +- 编辑你的Thunderbird配置设置,使它不要使用"format=flowed"格式:user_pref("mailnews. + send_plaintext_flowed", false); + +- 你需要使Thunderbird变为预先格式方式: + 如果默认情况下你书写的是HTML格式,那不是很难。仅仅从标题栏的下拉框中选择"Preformat"格式。 + 如果默认情况下你书写的是文本格式,你不得把它改为HTML格式(仅仅作为一次性的)来书写新的消息, + 然后强制使它回到文本格式,否则它就会拆行。要实现它,在写信的图标上使用shift键来使它变为HTML + 格式,然后标题栏的下拉框中选择"Preformat"格式。 + +- 允许使用外部的编辑器: + 针对Thunderbird打补丁最简单的方法就是使用一个"external editor"扩展,然后使用你最喜欢的 + $EDITOR来读取或者合并补丁到文本中。要实现它,可以下载并且安装这个扩展,然后添加一个使用它的 + 按键View->Toolbars->Customize...最后当你书写信息的时候仅仅点击它就可以了。 + +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +TkRat (GUI) + +可以使用它。使用"Insert file..."或者外部的编辑器。 + +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +Gmail (Web GUI) + +不要使用它发送补丁。 + +Gmail网页客户端自动地把制表符转换为空格。 + +虽然制表符转换为空格问题可以被外部编辑器解决,同时它还会使用回车换行把每行拆分为78个字符。 + +另一个问题是Gmail还会把任何不是ASCII的字符的信息改为base64编码。它把东西变的像欧洲人的名字。 + + ### diff --git a/Documentation/translations/zh_CN/process/magic-number.txt b/Documentation/translations/zh_CN/process/magic-number.txt new file mode 100644 index 000000000000..7159cec04090 --- /dev/null +++ b/Documentation/translations/zh_CN/process/magic-number.txt @@ -0,0 +1,153 @@ +Chinese translated version of Documentation/process/magic-number.rst + +If you have any comment or update to the content, please post to LKML directly. +However, if you have problem communicating in English you can also ask the +Chinese maintainer for help. Contact the Chinese maintainer, if this +translation is outdated or there is problem with translation. + +Chinese maintainer: Jia Wei Wei +--------------------------------------------------------------------- +Documentation/process/magic-number.rst的中文翻译 + +如果想评论或更新本文的内容,请直接发信到LKML。如果你使用英文交流有困难的话,也可 +以向中文版维护者求助。如果本翻译更新不及时或者翻译存在问题,请联系中文版维护者。 + +中文版维护者: 贾威威 Jia Wei Wei +中文版翻译者: 贾威威 Jia Wei Wei +中文版校译者: 贾威威 Jia Wei Wei + +以下为正文 +--------------------------------------------------------------------- +这个文件是有关当前使用的魔术值注册表。当你给一个结构添加了一个魔术值,你也应该把这个魔术值添加到这个文件,因为我们最好把用于各种结构的魔术值统一起来。 + +使用魔术值来保护内核数据结构是一个非常好的主意。这就允许你在运行期检查(a)一个结构是否已经被攻击,或者(b)你已经给一个例行程序通过了一个错误的结构。后一种情况特别地有用---特别是当你通过一个空指针指向结构体的时候。tty源码,例如,经常通过特定驱动使用这种方法并且反复地排列特定方面的结构。 + +使用魔术值的方法是在结构的开始处声明的,如下: + +struct tty_ldisc { + int magic; + ... +}; + +当你以后给内核添加增强功能的时候,请遵守这条规则!这样就会节省数不清的调试时间,特别是一些古怪的情况,例如,数组超出范围并且重新写了超出部分。遵守这个规则,‪这些情况可以被快速地,安全地避免。 + + Theodore Ts'o + 31 Mar 94 + +给当前的Linux 2.1.55添加魔术表。 + + Michael Chastain + + 22 Sep 1997 + +现在应该最新的Linux 2.1.112.因为在特性冻结期间,不能在2.2.x前改变任何东西。这些条目被数域所排序。 + + Krzysztof G.Baranowski + + 29 Jul 1998 + +更新魔术表到Linux 2.5.45。刚好越过特性冻结,但是有可能还会有一些新的魔术值在2.6.x之前融入到内核中。 + + Petr Baudis + + 03 Nov 2002 + +更新魔术表到Linux 2.5.74。 + + Fabian Frederick + + 09 Jul 2003 + +魔术名 地址 结构 所在文件 +=========================================================================== +PG_MAGIC 'P' pg_{read,write}_hdr include/linux/pg.h +CMAGIC 0x0111 user include/linux/a.out.h +MKISS_DRIVER_MAGIC 0x04bf mkiss_channel drivers/net/mkiss.h +HDLC_MAGIC 0x239e n_hdlc drivers/char/n_hdlc.c +APM_BIOS_MAGIC 0x4101 apm_user arch/x86/kernel/apm_32.c +CYCLADES_MAGIC 0x4359 cyclades_port include/linux/cyclades.h +DB_MAGIC 0x4442 fc_info drivers/net/iph5526_novram.c +DL_MAGIC 0x444d fc_info drivers/net/iph5526_novram.c +FASYNC_MAGIC 0x4601 fasync_struct include/linux/fs.h +FF_MAGIC 0x4646 fc_info drivers/net/iph5526_novram.c +ISICOM_MAGIC 0x4d54 isi_port include/linux/isicom.h +PTY_MAGIC 0x5001 drivers/char/pty.c +PPP_MAGIC 0x5002 ppp include/linux/if_pppvar.h +SERIAL_MAGIC 0x5301 async_struct include/linux/serial.h +SSTATE_MAGIC 0x5302 serial_state include/linux/serial.h +SLIP_MAGIC 0x5302 slip drivers/net/slip.h +STRIP_MAGIC 0x5303 strip drivers/net/strip.c +X25_ASY_MAGIC 0x5303 x25_asy drivers/net/x25_asy.h +SIXPACK_MAGIC 0x5304 sixpack drivers/net/hamradio/6pack.h +AX25_MAGIC 0x5316 ax_disp drivers/net/mkiss.h +TTY_MAGIC 0x5401 tty_struct include/linux/tty.h +MGSL_MAGIC 0x5401 mgsl_info drivers/char/synclink.c +TTY_DRIVER_MAGIC 0x5402 tty_driver include/linux/tty_driver.h +MGSLPC_MAGIC 0x5402 mgslpc_info drivers/char/pcmcia/synclink_cs.c +TTY_LDISC_MAGIC 0x5403 tty_ldisc include/linux/tty_ldisc.h +USB_SERIAL_MAGIC 0x6702 usb_serial drivers/usb/serial/usb-serial.h +FULL_DUPLEX_MAGIC 0x6969 drivers/net/ethernet/dec/tulip/de2104x.c +USB_BLUETOOTH_MAGIC 0x6d02 usb_bluetooth drivers/usb/class/bluetty.c +RFCOMM_TTY_MAGIC 0x6d02 net/bluetooth/rfcomm/tty.c +USB_SERIAL_PORT_MAGIC 0x7301 usb_serial_port drivers/usb/serial/usb-serial.h +CG_MAGIC 0x00090255 ufs_cylinder_group include/linux/ufs_fs.h +RPORT_MAGIC 0x00525001 r_port drivers/char/rocket_int.h +LSEMAGIC 0x05091998 lse drivers/fc4/fc.c +GDTIOCTL_MAGIC 0x06030f07 gdth_iowr_str drivers/scsi/gdth_ioctl.h +RIEBL_MAGIC 0x09051990 drivers/net/atarilance.c +NBD_REQUEST_MAGIC 0x12560953 nbd_request include/linux/nbd.h +RED_MAGIC2 0x170fc2a5 (any) mm/slab.c +BAYCOM_MAGIC 0x19730510 baycom_state drivers/net/baycom_epp.c +ISDN_X25IFACE_MAGIC 0x1e75a2b9 isdn_x25iface_proto_data + drivers/isdn/isdn_x25iface.h +ECP_MAGIC 0x21504345 cdkecpsig include/linux/cdk.h +LSOMAGIC 0x27091997 lso drivers/fc4/fc.c +LSMAGIC 0x2a3b4d2a ls drivers/fc4/fc.c +WANPIPE_MAGIC 0x414C4453 sdla_{dump,exec} include/linux/wanpipe.h +CS_CARD_MAGIC 0x43525553 cs_card sound/oss/cs46xx.c +LABELCL_MAGIC 0x4857434c labelcl_info_s include/asm/ia64/sn/labelcl.h +ISDN_ASYNC_MAGIC 0x49344C01 modem_info include/linux/isdn.h +CTC_ASYNC_MAGIC 0x49344C01 ctc_tty_info drivers/s390/net/ctctty.c +ISDN_NET_MAGIC 0x49344C02 isdn_net_local_s drivers/isdn/i4l/isdn_net_lib.h +SAVEKMSG_MAGIC2 0x4B4D5347 savekmsg arch/*/amiga/config.c +CS_STATE_MAGIC 0x4c4f4749 cs_state sound/oss/cs46xx.c +SLAB_C_MAGIC 0x4f17a36d kmem_cache mm/slab.c +COW_MAGIC 0x4f4f4f4d cow_header_v1 arch/um/drivers/ubd_user.c +I810_CARD_MAGIC 0x5072696E i810_card sound/oss/i810_audio.c +TRIDENT_CARD_MAGIC 0x5072696E trident_card sound/oss/trident.c +ROUTER_MAGIC 0x524d4157 wan_device [in wanrouter.h pre 3.9] +SAVEKMSG_MAGIC1 0x53415645 savekmsg arch/*/amiga/config.c +GDA_MAGIC 0x58464552 gda arch/mips/include/asm/sn/gda.h +RED_MAGIC1 0x5a2cf071 (any) mm/slab.c +EEPROM_MAGIC_VALUE 0x5ab478d2 lanai_dev drivers/atm/lanai.c +HDLCDRV_MAGIC 0x5ac6e778 hdlcdrv_state include/linux/hdlcdrv.h +PCXX_MAGIC 0x5c6df104 channel drivers/char/pcxx.h +KV_MAGIC 0x5f4b565f kernel_vars_s arch/mips/include/asm/sn/klkernvars.h +I810_STATE_MAGIC 0x63657373 i810_state sound/oss/i810_audio.c +TRIDENT_STATE_MAGIC 0x63657373 trient_state sound/oss/trident.c +M3_CARD_MAGIC 0x646e6f50 m3_card sound/oss/maestro3.c +FW_HEADER_MAGIC 0x65726F66 fw_header drivers/atm/fore200e.h +SLOT_MAGIC 0x67267321 slot drivers/hotplug/cpqphp.h +SLOT_MAGIC 0x67267322 slot drivers/hotplug/acpiphp.h +LO_MAGIC 0x68797548 nbd_device include/linux/nbd.h +OPROFILE_MAGIC 0x6f70726f super_block drivers/oprofile/oprofilefs.h +M3_STATE_MAGIC 0x734d724d m3_state sound/oss/maestro3.c +VMALLOC_MAGIC 0x87654320 snd_alloc_track sound/core/memory.c +KMALLOC_MAGIC 0x87654321 snd_alloc_track sound/core/memory.c +PWC_MAGIC 0x89DC10AB pwc_device drivers/usb/media/pwc.h +NBD_REPLY_MAGIC 0x96744668 nbd_reply include/linux/nbd.h +ENI155_MAGIC 0xa54b872d midway_eprom drivers/atm/eni.h +CODA_MAGIC 0xC0DAC0DA coda_file_info include/linux/coda_fs_i.h +DPMEM_MAGIC 0xc0ffee11 gdt_pci_sram drivers/scsi/gdth.h +YAM_MAGIC 0xF10A7654 yam_port drivers/net/hamradio/yam.c +CCB_MAGIC 0xf2691ad2 ccb drivers/scsi/ncr53c8xx.c +QUEUE_MAGIC_FREE 0xf7e1c9a3 queue_entry drivers/scsi/arm/queue.c +QUEUE_MAGIC_USED 0xf7e1cc33 queue_entry drivers/scsi/arm/queue.c +HTB_CMAGIC 0xFEFAFEF1 htb_class net/sched/sch_htb.c +NMI_MAGIC 0x48414d4d455201 nmi_s arch/mips/include/asm/sn/nmi.h + +请注意,在声音记忆管理中仍然有一些特殊的为每个驱动定义的魔术值。查看include/sound/sndmagic.h来获取他们完整的列表信息。很多OSS声音驱动拥有自己从声卡PCI ID构建的魔术值-他们也没有被列在这里。 + +IrDA子系统也使用了大量的自己的魔术值,查看include/net/irda/irda.h来获取他们完整的信息。 + +HFS是另外一个比较大的使用魔术值的文件系统-你可以在fs/hfs/hfs.h中找到他们。 diff --git a/Documentation/translations/zh_CN/process/stable_api_nonsense.txt b/Documentation/translations/zh_CN/process/stable_api_nonsense.txt new file mode 100644 index 000000000000..a2b27fab382c --- /dev/null +++ b/Documentation/translations/zh_CN/process/stable_api_nonsense.txt @@ -0,0 +1,157 @@ +Chinese translated version of Documentation/process/stable-api-nonsense.rst + +If you have any comment or update to the content, please contact the +original document maintainer directly. However, if you have problem +communicating in English you can also ask the Chinese maintainer for help. +Contact the Chinese maintainer, if this translation is outdated or there +is problem with translation. + +Maintainer: Greg Kroah-Hartman +Chinese maintainer: TripleX Chung +--------------------------------------------------------------------- +Documentation/process/stable-api-nonsense.rst 的中文翻译 + +如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 +交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 +译存在问题,请联系中文版维护者。 + +英文版维护者: Greg Kroah-Hartman +中文版维护者: 钟宇 TripleX Chung +中文版翻译者: 钟宇 TripleX Chung +中文版校译者: 李阳 Li Yang +以下为正文 +--------------------------------------------------------------------- + +写作本文档的目的,是为了解释为什么Linux既没有二进制内核接口,也没有稳定 +的内核接口。这里所说的内核接口,是指内核里的接口,而不是内核和用户空间 +的接口。内核到用户空间的接口,是提供给应用程序使用的系统调用,系统调用 +在历史上几乎没有过变化,将来也不会有变化。我有一些老应用程序是在0.9版本 +或者更早版本的内核上编译的,在使用2.6版本内核的Linux发布上依然用得很好 +。用户和应用程序作者可以将这个接口看成是稳定的。 + + +执行纲要 +-------- + +你也许以为自己想要稳定的内核接口,但是你不清楚你要的实际上不是它。你需 +要的其实是稳定的驱动程序,而你只有将驱动程序放到公版内核的源代码树里, +才有可能达到这个目的。而且这样做还有很多其它好处,正是因为这些好处使得 +Linux能成为强壮,稳定,成熟的操作系统,这也是你最开始选择Linux的原因。 + + +入门 +----- + +只有那些写驱动程序的“怪人”才会担心内核接口的改变,对广大用户来说,既 +看不到内核接口,也不需要去关心它。 + +首先,我不打算讨论关于任何非GPL许可的内核驱动的法律问题,这些非GPL许可 +的驱动程序包括不公开源代码,隐藏源代码,二进制或者是用源代码包装,或者 +是其它任何形式的不能以GPL许可公开源代码的驱动程序。如果有法律问题,请咨 +询律师,我只是一个程序员,所以我只打算探讨技术问题(不是小看法律问题, +法律问题很实际,并且需要一直关注)。 + +既然只谈技术问题,我们就有了下面两个主题:二进制内核接口和稳定的内核源 +代码接口。这两个问题是互相关联的,让我们先解决掉二进制接口的问题。 + + +二进制内核接口 +-------------- +假如我们有一个稳定的内核源代码接口,那么自然而然的,我们就拥有了稳定的 +二进制接口,是这样的吗?错。让我们看看关于Linux内核的几点事实: + - 取决于所用的C编译器的版本,不同的内核数据结构里的结构体的对齐方 +式会有差别,代码中不同函数的表现形式也不一样(函数是不是被inline编译取 +决于编译器行为)。不同的函数的表现形式并不重要,但是数据结构内部的对齐 +方式很关键。 + - 取决于内核的配置选项,不同的选项会让内核的很多东西发生改变: + - 同一个结构体可能包含不同的成员变量 + - 有的函数可能根本不会被实现(比如编译的时候没有选择SMP支持 +,一些锁函数就会被定义成空函数)。 + - 内核使用的内存会以不同的方式对齐,这取决于不同的内核配置选 +项。 + - Linux可以在很多的不同体系结构的处理器上运行。在某个体系结构上编 +译好的二进制驱动程序,不可能在另外一个体系结构上正确的运行。 + +对于一个特定的内核,满足这些条件并不难,使用同一个C编译器和同样的内核配 +置选项来编译驱动程序模块就可以了。这对于给一个特定Linux发布的特定版本提 +供驱动程序,是完全可以满足需求的。但是如果你要给不同发布的不同版本都发 +布一个驱动程序,就需要在每个发布上用不同的内核设置参数都编译一次内核, +这简直跟噩梦一样。而且还要注意到,每个Linux发布还提供不同的Linux内核, +这些内核都针对不同的硬件类型进行了优化(有很多种不同的处理器,还有不同 +的内核设置选项)。所以每发布一次驱动程序,都需要提供很多不同版本的内核 +模块。 + +相信我,如果你真的要采取这种发布方式,一定会慢慢疯掉,我很久以前就有过 +深刻的教训... + + +稳定的内核源代码接口 +-------------------- + +如果有人不将他的内核驱动程序,放入公版内核的源代码树,而又想让驱动程序 +一直保持在最新的内核中可用,那么这个话题将会变得没完没了。 + 内核开发是持续而且快节奏的,从来都不会慢下来。内核开发人员在当前接口中 +找到bug,或者找到更好的实现方式。一旦发现这些,他们就很快会去修改当前的 +接口。修改接口意味着,函数名可能会改变,结构体可能被扩充或者删减,函数 +的参数也可能发生改变。一旦接口被修改,内核中使用这些接口的地方需要同时 +修正,这样才能保证所有的东西继续工作。 + +举一个例子,内核的USB驱动程序接口在USB子系统的整个生命周期中,至少经历 +了三次重写。这些重写解决以下问题: + - 把数据流从同步模式改成非同步模式,这个改动减少了一些驱动程序的 +复杂度,提高了所有USB驱动程序的吞吐率,这样几乎所有的USB设备都能以最大 +速率工作了。 + - 修改了USB核心代码中为USB驱动分配数据包内存的方式,所有的驱动都 +需要提供更多的参数给USB核心,以修正了很多已经被记录在案的死锁。 + +这和一些封闭源代码的操作系统形成鲜明的对比,在那些操作系统上,不得不额 +外的维护旧的USB接口。这导致了一个可能性,新的开发者依然会不小心使用旧的 +接口,以不恰当的方式编写代码,进而影响到操作系统的稳定性。 + 在上面的例子中,所有的开发者都同意这些重要的改动,在这样的情况下修改代 +价很低。如果Linux保持一个稳定的内核源代码接口,那么就得创建一个新的接口 +;旧的,有问题的接口必须一直维护,给Linux USB开发者带来额外的工作。既然 +所有的Linux USB驱动的作者都是利用自己的时间工作,那么要求他们去做毫无意 +义的免费额外工作,是不可能的。 + 安全问题对Linux来说十分重要。一个安全问题被发现,就会在短时间内得到修 +正。在很多情况下,这将导致Linux内核中的一些接口被重写,以从根本上避免安 +全问题。一旦接口被重写,所有使用这些接口的驱动程序,必须同时得到修正, +以确定安全问题已经得到修复并且不可能在未来还有同样的安全问题。如果内核 +内部接口不允许改变,那么就不可能修复这样的安全问题,也不可能确认这样的 +安全问题以后不会发生。 +开发者一直在清理内核接口。如果一个接口没有人在使用了,它就会被删除。这 +样可以确保内核尽可能的小,而且所有潜在的接口都会得到尽可能完整的测试 +(没有人使用的接口是不可能得到良好的测试的)。 + + +要做什么 +------- + +如果你写了一个Linux内核驱动,但是它还不在Linux源代码树里,作为一个开发 +者,你应该怎么做?为每个发布的每个版本提供一个二进制驱动,那简直是一个 +噩梦,要跟上永远处于变化之中的内核接口,也是一件辛苦活。 +很简单,让你的驱动进入内核源代码树(要记得我们在谈论的是以GPL许可发行 +的驱动,如果你的代码不符合GPL,那么祝你好运,你只能自己解决这个问题了, +你这个吸血鬼<把Andrew和Linus对吸血鬼的定义链接到这里>)。当你的代码加入 +公版内核源代码树之后,如果一个内核接口改变,你的驱动会直接被修改接口的 +那个人修改。保证你的驱动永远都可以编译通过,并且一直工作,你几乎不需要 +做什么事情。 + +把驱动放到内核源代码树里会有很多的好处: + - 驱动的质量会提升,而维护成本(对原始作者来说)会下降。 + - 其他人会给驱动添加新特性。 + - 其他人会找到驱动中的bug并修复。 + - 其他人会在驱动中找到性能优化的机会。 + - 当外部的接口的改变需要修改驱动程序的时候,其他人会修改驱动程序 +。 + - 不需要联系任何发行商,这个驱动会自动的随着所有的Linux发布一起发 +布。 + +和别的操作系统相比,Linux为更多不同的设备提供现成的驱动,而且能在更多不 +同体系结构的处理器上支持这些设备。这个经过考验的开发模式,必然是错不了 +的 :) + +------------- +感谢 Randy Dunlap, Andrew Morton, David Brownell, Hanna Linder, +Robert Love, and Nishanth Aravamudan 对于本文档早期版本的评审和建议。 + +英文版维护者: Greg Kroah-Hartman diff --git a/Documentation/translations/zh_CN/process/stable_kernel_rules.txt b/Documentation/translations/zh_CN/process/stable_kernel_rules.txt new file mode 100644 index 000000000000..db4ba5a0c39a --- /dev/null +++ b/Documentation/translations/zh_CN/process/stable_kernel_rules.txt @@ -0,0 +1,66 @@ +Chinese translated version of Documentation/process/stable-kernel-rules.rst + +If you have any comment or update to the content, please contact the +original document maintainer directly. However, if you have a problem +communicating in English you can also ask the Chinese maintainer for +help. Contact the Chinese maintainer if this translation is outdated +or if there is a problem with the translation. + +Chinese maintainer: TripleX Chung +--------------------------------------------------------------------- +Documentation/process/stable-kernel-rules.rst 的中文翻译 + +如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 +交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 +译存在问题,请联系中文版维护者。 + + +中文版维护者: 钟宇 TripleX Chung +中文版翻译者: 钟宇 TripleX Chung +中文版校译者: 李阳 Li Yang + Kangkai Yin + +以下为正文 +--------------------------------------------------------------------- + +关于Linux 2.6稳定版发布,所有你想知道的事情。 + +关于哪些类型的补丁可以被接收进入稳定版代码树,哪些不可以的规则: + + - 必须是显而易见的正确,并且经过测试的。 + - 连同上下文,不能大于100行。 + - 必须只修正一件事情。 + - 必须修正了一个给大家带来麻烦的真正的bug(不是“这也许是一个问题...” + 那样的东西)。 + - 必须修正带来如下后果的问题:编译错误(对被标记为CONFIG_BROKEN的例外), + 内核崩溃,挂起,数据损坏,真正的安全问题,或者一些类似“哦,这不 + 好”的问题。简短的说,就是一些致命的问题。 + - 没有“理论上的竞争条件”,除非能给出竞争条件如何被利用的解释。 + - 不能存在任何的“琐碎的”修正(拼写修正,去掉多余空格之类的)。 + - 必须被相关子系统的维护者接受。 + - 必须遵循Documentation/process/submitting-patches.rst里的规则。 + +向稳定版代码树提交补丁的过程: + + - 在确认了补丁符合以上的规则后,将补丁发送到stable@vger.kernel.org。 + - 如果补丁被接受到队列里,发送者会收到一个ACK回复,如果没有被接受,收 + 到的是NAK回复。回复需要几天的时间,这取决于开发者的时间安排。 + - 被接受的补丁会被加到稳定版本队列里,等待其他开发者的审查。 + - 安全方面的补丁不要发到这个列表,应该发送到security@kernel.org。 + +审查周期: + + - 当稳定版的维护者决定开始一个审查周期,补丁将被发送到审查委员会,以 + 及被补丁影响的领域的维护者(除非提交者就是该领域的维护者)并且抄送 + 到linux-kernel邮件列表。 + - 审查委员会有48小时的时间,用来决定给该补丁回复ACK还是NAK。 + - 如果委员会中有成员拒绝这个补丁,或者linux-kernel列表上有人反对这个 + 补丁,并提出维护者和审查委员会之前没有意识到的问题,补丁会从队列中 + 丢弃。 + - 在审查周期结束的时候,那些得到ACK回应的补丁将会被加入到最新的稳定版 + 发布中,一个新的稳定版发布就此产生。 + - 安全性补丁将从内核安全小组那里直接接收到稳定版代码树中,而不是通过 + 通常的审查周期。请联系内核安全小组以获得关于这个过程的更多细节。 + +审查委员会: + - 由一些自愿承担这项任务的内核开发者,和几个非志愿的组成。 diff --git a/Documentation/translations/zh_CN/process/volatile-considered-harmful.txt b/Documentation/translations/zh_CN/process/volatile-considered-harmful.txt new file mode 100644 index 000000000000..475125967197 --- /dev/null +++ b/Documentation/translations/zh_CN/process/volatile-considered-harmful.txt @@ -0,0 +1,113 @@ +Chinese translated version of Documentation/process/volatile-considered-harmful.rst + +If you have any comment or update to the content, please contact the +original document maintainer directly. However, if you have a problem +communicating in English you can also ask the Chinese maintainer for +help. Contact the Chinese maintainer if this translation is outdated +or if there is a problem with the translation. + +Maintainer: Jonathan Corbet +Chinese maintainer: Bryan Wu +--------------------------------------------------------------------- +Documentation/process/volatile-considered-harmful.rst 的中文翻译 + +如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 +交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 +译存在问题,请联系中文版维护者。 + +英文版维护者: Jonathan Corbet +中文版维护者: 伍鹏 Bryan Wu +中文版翻译者: 伍鹏 Bryan Wu +中文版校译者: 张汉辉 Eugene Teo + 杨瑞 Dave Young +以下为正文 +--------------------------------------------------------------------- + +为什么不应该使用“volatile”类型 +------------------------------ + +C程序员通常认为volatile表示某个变量可以在当前执行的线程之外被改变;因此,在内核 +中用到共享数据结构时,常常会有C程序员喜欢使用volatile这类变量。换句话说,他们经 +常会把volatile类型看成某种简易的原子变量,当然它们不是。在内核中使用volatile几 +乎总是错误的;本文档将解释为什么这样。 + +理解volatile的关键是知道它的目的是用来消除优化,实际上很少有人真正需要这样的应 +用。在内核中,程序员必须防止意外的并发访问破坏共享的数据结构,这其实是一个完全 +不同的任务。用来防止意外并发访问的保护措施,可以更加高效的避免大多数优化相关的 +问题。 + +像volatile一样,内核提供了很多原语来保证并发访问时的数据安全(自旋锁, 互斥量,内 +存屏障等等),同样可以防止意外的优化。如果可以正确使用这些内核原语,那么就没有 +必要再使用volatile。如果仍然必须使用volatile,那么几乎可以肯定在代码的某处有一 +个bug。在正确设计的内核代码中,volatile能带来的仅仅是使事情变慢。 + +思考一下这段典型的内核代码: + + spin_lock(&the_lock); + do_something_on(&shared_data); + do_something_else_with(&shared_data); + spin_unlock(&the_lock); + +如果所有的代码都遵循加锁规则,当持有the_lock的时候,不可能意外的改变shared_data的 +值。任何可能访问该数据的其他代码都会在这个锁上等待。自旋锁原语跟内存屏障一样—— 它 +们显式的用来书写成这样 —— 意味着数据访问不会跨越它们而被优化。所以本来编译器认为 +它知道在shared_data里面将有什么,但是因为spin_lock()调用跟内存屏障一样,会强制编 +译器忘记它所知道的一切。那么在访问这些数据时不会有优化的问题。 + +如果shared_data被声名为volatile,锁操作将仍然是必须的。就算我们知道没有其他人正在 +使用它,编译器也将被阻止优化对临界区内shared_data的访问。在锁有效的同时, +shared_data不是volatile的。在处理共享数据的时候,适当的锁操作可以不再需要 +volatile —— 并且是有潜在危害的。 + +volatile的存储类型最初是为那些内存映射的I/O寄存器而定义。在内核里,寄存器访问也应 +该被锁保护,但是人们也不希望编译器“优化”临界区内的寄存器访问。内核里I/O的内存访问 +是通过访问函数完成的;不赞成通过指针对I/O内存的直接访问,并且不是在所有体系架构上 +都能工作。那些访问函数正是为了防止意外优化而写的,因此,再说一次,volatile类型不 +是必需的。 + +另一种引起用户可能使用volatile的情况是当处理器正忙着等待一个变量的值。正确执行一 +个忙等待的方法是: + + while (my_variable != what_i_want) + cpu_relax(); + +cpu_relax()调用会降低CPU的能量消耗或者让位于超线程双处理器;它也作为内存屏障一样出 +现,所以,再一次,volatile不是必需的。当然,忙等待一开始就是一种反常规的做法。 + +在内核中,一些稀少的情况下volatile仍然是有意义的: + + - 在一些体系架构的系统上,允许直接的I/0内存访问,那么前面提到的访问函数可以使用 + volatile。基本上,每一个访问函数调用它自己都是一个小的临界区域并且保证了按照 + 程序员期望的那样发生访问操作。 + + - 某些会改变内存的内联汇编代码虽然没有什么其他明显的附作用,但是有被GCC删除的可 + 能性。在汇编声明中加上volatile关键字可以防止这种删除操作。 + + - Jiffies变量是一种特殊情况,虽然每次引用它的时候都可以有不同的值,但读jiffies + 变量时不需要任何特殊的加锁保护。所以jiffies变量可以使用volatile,但是不赞成 + 其他跟jiffies相同类型变量使用volatile。Jiffies被认为是一种“愚蠢的遗留物" + (Linus的话)因为解决这个问题比保持现状要麻烦的多。 + + - 由于某些I/0设备可能会修改连续一致的内存,所以有时,指向连续一致内存的数据结构 + 的指针需要正确的使用volatile。网络适配器使用的环状缓存区正是这类情形的一个例 + 子,其中适配器用改变指针来表示哪些描述符已经处理过了。 + +对于大多代码,上述几种可以使用volatile的情况都不适用。所以,使用volatile是一种 +bug并且需要对这样的代码额外仔细检查。那些试图使用volatile的开发人员需要退一步想想 +他们真正想实现的是什么。 + +非常欢迎删除volatile变量的补丁 - 只要证明这些补丁完整的考虑了并发问题。 + +注释 +---- + +[1] http://lwn.net/Articles/233481/ +[2] http://lwn.net/Articles/233482/ + +致谢 +---- + +最初由Randy Dunlap推动并作初步研究 +由Jonathan Corbet撰写 +参考Satyam Sharma,Johannes Stezenbach,Jesper Juhl,Heikki Orsila, +H. Peter Anvin,Philipp Hahn和Stefan Richter的意见改善了本档。 diff --git a/Documentation/translations/zh_CN/stable_api_nonsense.txt b/Documentation/translations/zh_CN/stable_api_nonsense.txt deleted file mode 100644 index a2b27fab382c..000000000000 --- a/Documentation/translations/zh_CN/stable_api_nonsense.txt +++ /dev/null @@ -1,157 +0,0 @@ -Chinese translated version of Documentation/process/stable-api-nonsense.rst - -If you have any comment or update to the content, please contact the -original document maintainer directly. However, if you have problem -communicating in English you can also ask the Chinese maintainer for help. -Contact the Chinese maintainer, if this translation is outdated or there -is problem with translation. - -Maintainer: Greg Kroah-Hartman -Chinese maintainer: TripleX Chung ---------------------------------------------------------------------- -Documentation/process/stable-api-nonsense.rst 的中文翻译 - -如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 -交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者。 - -英文版维护者: Greg Kroah-Hartman -中文版维护者: 钟宇 TripleX Chung -中文版翻译者: 钟宇 TripleX Chung -中文版校译者: 李阳 Li Yang -以下为正文 ---------------------------------------------------------------------- - -写作本文档的目的,是为了解释为什么Linux既没有二进制内核接口,也没有稳定 -的内核接口。这里所说的内核接口,是指内核里的接口,而不是内核和用户空间 -的接口。内核到用户空间的接口,是提供给应用程序使用的系统调用,系统调用 -在历史上几乎没有过变化,将来也不会有变化。我有一些老应用程序是在0.9版本 -或者更早版本的内核上编译的,在使用2.6版本内核的Linux发布上依然用得很好 -。用户和应用程序作者可以将这个接口看成是稳定的。 - - -执行纲要 --------- - -你也许以为自己想要稳定的内核接口,但是你不清楚你要的实际上不是它。你需 -要的其实是稳定的驱动程序,而你只有将驱动程序放到公版内核的源代码树里, -才有可能达到这个目的。而且这样做还有很多其它好处,正是因为这些好处使得 -Linux能成为强壮,稳定,成熟的操作系统,这也是你最开始选择Linux的原因。 - - -入门 ------ - -只有那些写驱动程序的“怪人”才会担心内核接口的改变,对广大用户来说,既 -看不到内核接口,也不需要去关心它。 - -首先,我不打算讨论关于任何非GPL许可的内核驱动的法律问题,这些非GPL许可 -的驱动程序包括不公开源代码,隐藏源代码,二进制或者是用源代码包装,或者 -是其它任何形式的不能以GPL许可公开源代码的驱动程序。如果有法律问题,请咨 -询律师,我只是一个程序员,所以我只打算探讨技术问题(不是小看法律问题, -法律问题很实际,并且需要一直关注)。 - -既然只谈技术问题,我们就有了下面两个主题:二进制内核接口和稳定的内核源 -代码接口。这两个问题是互相关联的,让我们先解决掉二进制接口的问题。 - - -二进制内核接口 --------------- -假如我们有一个稳定的内核源代码接口,那么自然而然的,我们就拥有了稳定的 -二进制接口,是这样的吗?错。让我们看看关于Linux内核的几点事实: - - 取决于所用的C编译器的版本,不同的内核数据结构里的结构体的对齐方 -式会有差别,代码中不同函数的表现形式也不一样(函数是不是被inline编译取 -决于编译器行为)。不同的函数的表现形式并不重要,但是数据结构内部的对齐 -方式很关键。 - - 取决于内核的配置选项,不同的选项会让内核的很多东西发生改变: - - 同一个结构体可能包含不同的成员变量 - - 有的函数可能根本不会被实现(比如编译的时候没有选择SMP支持 -,一些锁函数就会被定义成空函数)。 - - 内核使用的内存会以不同的方式对齐,这取决于不同的内核配置选 -项。 - - Linux可以在很多的不同体系结构的处理器上运行。在某个体系结构上编 -译好的二进制驱动程序,不可能在另外一个体系结构上正确的运行。 - -对于一个特定的内核,满足这些条件并不难,使用同一个C编译器和同样的内核配 -置选项来编译驱动程序模块就可以了。这对于给一个特定Linux发布的特定版本提 -供驱动程序,是完全可以满足需求的。但是如果你要给不同发布的不同版本都发 -布一个驱动程序,就需要在每个发布上用不同的内核设置参数都编译一次内核, -这简直跟噩梦一样。而且还要注意到,每个Linux发布还提供不同的Linux内核, -这些内核都针对不同的硬件类型进行了优化(有很多种不同的处理器,还有不同 -的内核设置选项)。所以每发布一次驱动程序,都需要提供很多不同版本的内核 -模块。 - -相信我,如果你真的要采取这种发布方式,一定会慢慢疯掉,我很久以前就有过 -深刻的教训... - - -稳定的内核源代码接口 --------------------- - -如果有人不将他的内核驱动程序,放入公版内核的源代码树,而又想让驱动程序 -一直保持在最新的内核中可用,那么这个话题将会变得没完没了。 - 内核开发是持续而且快节奏的,从来都不会慢下来。内核开发人员在当前接口中 -找到bug,或者找到更好的实现方式。一旦发现这些,他们就很快会去修改当前的 -接口。修改接口意味着,函数名可能会改变,结构体可能被扩充或者删减,函数 -的参数也可能发生改变。一旦接口被修改,内核中使用这些接口的地方需要同时 -修正,这样才能保证所有的东西继续工作。 - -举一个例子,内核的USB驱动程序接口在USB子系统的整个生命周期中,至少经历 -了三次重写。这些重写解决以下问题: - - 把数据流从同步模式改成非同步模式,这个改动减少了一些驱动程序的 -复杂度,提高了所有USB驱动程序的吞吐率,这样几乎所有的USB设备都能以最大 -速率工作了。 - - 修改了USB核心代码中为USB驱动分配数据包内存的方式,所有的驱动都 -需要提供更多的参数给USB核心,以修正了很多已经被记录在案的死锁。 - -这和一些封闭源代码的操作系统形成鲜明的对比,在那些操作系统上,不得不额 -外的维护旧的USB接口。这导致了一个可能性,新的开发者依然会不小心使用旧的 -接口,以不恰当的方式编写代码,进而影响到操作系统的稳定性。 - 在上面的例子中,所有的开发者都同意这些重要的改动,在这样的情况下修改代 -价很低。如果Linux保持一个稳定的内核源代码接口,那么就得创建一个新的接口 -;旧的,有问题的接口必须一直维护,给Linux USB开发者带来额外的工作。既然 -所有的Linux USB驱动的作者都是利用自己的时间工作,那么要求他们去做毫无意 -义的免费额外工作,是不可能的。 - 安全问题对Linux来说十分重要。一个安全问题被发现,就会在短时间内得到修 -正。在很多情况下,这将导致Linux内核中的一些接口被重写,以从根本上避免安 -全问题。一旦接口被重写,所有使用这些接口的驱动程序,必须同时得到修正, -以确定安全问题已经得到修复并且不可能在未来还有同样的安全问题。如果内核 -内部接口不允许改变,那么就不可能修复这样的安全问题,也不可能确认这样的 -安全问题以后不会发生。 -开发者一直在清理内核接口。如果一个接口没有人在使用了,它就会被删除。这 -样可以确保内核尽可能的小,而且所有潜在的接口都会得到尽可能完整的测试 -(没有人使用的接口是不可能得到良好的测试的)。 - - -要做什么 -------- - -如果你写了一个Linux内核驱动,但是它还不在Linux源代码树里,作为一个开发 -者,你应该怎么做?为每个发布的每个版本提供一个二进制驱动,那简直是一个 -噩梦,要跟上永远处于变化之中的内核接口,也是一件辛苦活。 -很简单,让你的驱动进入内核源代码树(要记得我们在谈论的是以GPL许可发行 -的驱动,如果你的代码不符合GPL,那么祝你好运,你只能自己解决这个问题了, -你这个吸血鬼<把Andrew和Linus对吸血鬼的定义链接到这里>)。当你的代码加入 -公版内核源代码树之后,如果一个内核接口改变,你的驱动会直接被修改接口的 -那个人修改。保证你的驱动永远都可以编译通过,并且一直工作,你几乎不需要 -做什么事情。 - -把驱动放到内核源代码树里会有很多的好处: - - 驱动的质量会提升,而维护成本(对原始作者来说)会下降。 - - 其他人会给驱动添加新特性。 - - 其他人会找到驱动中的bug并修复。 - - 其他人会在驱动中找到性能优化的机会。 - - 当外部的接口的改变需要修改驱动程序的时候,其他人会修改驱动程序 -。 - - 不需要联系任何发行商,这个驱动会自动的随着所有的Linux发布一起发 -布。 - -和别的操作系统相比,Linux为更多不同的设备提供现成的驱动,而且能在更多不 -同体系结构的处理器上支持这些设备。这个经过考验的开发模式,必然是错不了 -的 :) - -------------- -感谢 Randy Dunlap, Andrew Morton, David Brownell, Hanna Linder, -Robert Love, and Nishanth Aravamudan 对于本文档早期版本的评审和建议。 - -英文版维护者: Greg Kroah-Hartman diff --git a/Documentation/translations/zh_CN/stable_kernel_rules.txt b/Documentation/translations/zh_CN/stable_kernel_rules.txt deleted file mode 100644 index db4ba5a0c39a..000000000000 --- a/Documentation/translations/zh_CN/stable_kernel_rules.txt +++ /dev/null @@ -1,66 +0,0 @@ -Chinese translated version of Documentation/process/stable-kernel-rules.rst - -If you have any comment or update to the content, please contact the -original document maintainer directly. However, if you have a problem -communicating in English you can also ask the Chinese maintainer for -help. Contact the Chinese maintainer if this translation is outdated -or if there is a problem with the translation. - -Chinese maintainer: TripleX Chung ---------------------------------------------------------------------- -Documentation/process/stable-kernel-rules.rst 的中文翻译 - -如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 -交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者。 - - -中文版维护者: 钟宇 TripleX Chung -中文版翻译者: 钟宇 TripleX Chung -中文版校译者: 李阳 Li Yang - Kangkai Yin - -以下为正文 ---------------------------------------------------------------------- - -关于Linux 2.6稳定版发布,所有你想知道的事情。 - -关于哪些类型的补丁可以被接收进入稳定版代码树,哪些不可以的规则: - - - 必须是显而易见的正确,并且经过测试的。 - - 连同上下文,不能大于100行。 - - 必须只修正一件事情。 - - 必须修正了一个给大家带来麻烦的真正的bug(不是“这也许是一个问题...” - 那样的东西)。 - - 必须修正带来如下后果的问题:编译错误(对被标记为CONFIG_BROKEN的例外), - 内核崩溃,挂起,数据损坏,真正的安全问题,或者一些类似“哦,这不 - 好”的问题。简短的说,就是一些致命的问题。 - - 没有“理论上的竞争条件”,除非能给出竞争条件如何被利用的解释。 - - 不能存在任何的“琐碎的”修正(拼写修正,去掉多余空格之类的)。 - - 必须被相关子系统的维护者接受。 - - 必须遵循Documentation/process/submitting-patches.rst里的规则。 - -向稳定版代码树提交补丁的过程: - - - 在确认了补丁符合以上的规则后,将补丁发送到stable@vger.kernel.org。 - - 如果补丁被接受到队列里,发送者会收到一个ACK回复,如果没有被接受,收 - 到的是NAK回复。回复需要几天的时间,这取决于开发者的时间安排。 - - 被接受的补丁会被加到稳定版本队列里,等待其他开发者的审查。 - - 安全方面的补丁不要发到这个列表,应该发送到security@kernel.org。 - -审查周期: - - - 当稳定版的维护者决定开始一个审查周期,补丁将被发送到审查委员会,以 - 及被补丁影响的领域的维护者(除非提交者就是该领域的维护者)并且抄送 - 到linux-kernel邮件列表。 - - 审查委员会有48小时的时间,用来决定给该补丁回复ACK还是NAK。 - - 如果委员会中有成员拒绝这个补丁,或者linux-kernel列表上有人反对这个 - 补丁,并提出维护者和审查委员会之前没有意识到的问题,补丁会从队列中 - 丢弃。 - - 在审查周期结束的时候,那些得到ACK回应的补丁将会被加入到最新的稳定版 - 发布中,一个新的稳定版发布就此产生。 - - 安全性补丁将从内核安全小组那里直接接收到稳定版代码树中,而不是通过 - 通常的审查周期。请联系内核安全小组以获得关于这个过程的更多细节。 - -审查委员会: - - 由一些自愿承担这项任务的内核开发者,和几个非志愿的组成。 diff --git a/Documentation/translations/zh_CN/volatile-considered-harmful.txt b/Documentation/translations/zh_CN/volatile-considered-harmful.txt deleted file mode 100644 index 475125967197..000000000000 --- a/Documentation/translations/zh_CN/volatile-considered-harmful.txt +++ /dev/null @@ -1,113 +0,0 @@ -Chinese translated version of Documentation/process/volatile-considered-harmful.rst - -If you have any comment or update to the content, please contact the -original document maintainer directly. However, if you have a problem -communicating in English you can also ask the Chinese maintainer for -help. Contact the Chinese maintainer if this translation is outdated -or if there is a problem with the translation. - -Maintainer: Jonathan Corbet -Chinese maintainer: Bryan Wu ---------------------------------------------------------------------- -Documentation/process/volatile-considered-harmful.rst 的中文翻译 - -如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 -交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者。 - -英文版维护者: Jonathan Corbet -中文版维护者: 伍鹏 Bryan Wu -中文版翻译者: 伍鹏 Bryan Wu -中文版校译者: 张汉辉 Eugene Teo - 杨瑞 Dave Young -以下为正文 ---------------------------------------------------------------------- - -为什么不应该使用“volatile”类型 ------------------------------- - -C程序员通常认为volatile表示某个变量可以在当前执行的线程之外被改变;因此,在内核 -中用到共享数据结构时,常常会有C程序员喜欢使用volatile这类变量。换句话说,他们经 -常会把volatile类型看成某种简易的原子变量,当然它们不是。在内核中使用volatile几 -乎总是错误的;本文档将解释为什么这样。 - -理解volatile的关键是知道它的目的是用来消除优化,实际上很少有人真正需要这样的应 -用。在内核中,程序员必须防止意外的并发访问破坏共享的数据结构,这其实是一个完全 -不同的任务。用来防止意外并发访问的保护措施,可以更加高效的避免大多数优化相关的 -问题。 - -像volatile一样,内核提供了很多原语来保证并发访问时的数据安全(自旋锁, 互斥量,内 -存屏障等等),同样可以防止意外的优化。如果可以正确使用这些内核原语,那么就没有 -必要再使用volatile。如果仍然必须使用volatile,那么几乎可以肯定在代码的某处有一 -个bug。在正确设计的内核代码中,volatile能带来的仅仅是使事情变慢。 - -思考一下这段典型的内核代码: - - spin_lock(&the_lock); - do_something_on(&shared_data); - do_something_else_with(&shared_data); - spin_unlock(&the_lock); - -如果所有的代码都遵循加锁规则,当持有the_lock的时候,不可能意外的改变shared_data的 -值。任何可能访问该数据的其他代码都会在这个锁上等待。自旋锁原语跟内存屏障一样—— 它 -们显式的用来书写成这样 —— 意味着数据访问不会跨越它们而被优化。所以本来编译器认为 -它知道在shared_data里面将有什么,但是因为spin_lock()调用跟内存屏障一样,会强制编 -译器忘记它所知道的一切。那么在访问这些数据时不会有优化的问题。 - -如果shared_data被声名为volatile,锁操作将仍然是必须的。就算我们知道没有其他人正在 -使用它,编译器也将被阻止优化对临界区内shared_data的访问。在锁有效的同时, -shared_data不是volatile的。在处理共享数据的时候,适当的锁操作可以不再需要 -volatile —— 并且是有潜在危害的。 - -volatile的存储类型最初是为那些内存映射的I/O寄存器而定义。在内核里,寄存器访问也应 -该被锁保护,但是人们也不希望编译器“优化”临界区内的寄存器访问。内核里I/O的内存访问 -是通过访问函数完成的;不赞成通过指针对I/O内存的直接访问,并且不是在所有体系架构上 -都能工作。那些访问函数正是为了防止意外优化而写的,因此,再说一次,volatile类型不 -是必需的。 - -另一种引起用户可能使用volatile的情况是当处理器正忙着等待一个变量的值。正确执行一 -个忙等待的方法是: - - while (my_variable != what_i_want) - cpu_relax(); - -cpu_relax()调用会降低CPU的能量消耗或者让位于超线程双处理器;它也作为内存屏障一样出 -现,所以,再一次,volatile不是必需的。当然,忙等待一开始就是一种反常规的做法。 - -在内核中,一些稀少的情况下volatile仍然是有意义的: - - - 在一些体系架构的系统上,允许直接的I/0内存访问,那么前面提到的访问函数可以使用 - volatile。基本上,每一个访问函数调用它自己都是一个小的临界区域并且保证了按照 - 程序员期望的那样发生访问操作。 - - - 某些会改变内存的内联汇编代码虽然没有什么其他明显的附作用,但是有被GCC删除的可 - 能性。在汇编声明中加上volatile关键字可以防止这种删除操作。 - - - Jiffies变量是一种特殊情况,虽然每次引用它的时候都可以有不同的值,但读jiffies - 变量时不需要任何特殊的加锁保护。所以jiffies变量可以使用volatile,但是不赞成 - 其他跟jiffies相同类型变量使用volatile。Jiffies被认为是一种“愚蠢的遗留物" - (Linus的话)因为解决这个问题比保持现状要麻烦的多。 - - - 由于某些I/0设备可能会修改连续一致的内存,所以有时,指向连续一致内存的数据结构 - 的指针需要正确的使用volatile。网络适配器使用的环状缓存区正是这类情形的一个例 - 子,其中适配器用改变指针来表示哪些描述符已经处理过了。 - -对于大多代码,上述几种可以使用volatile的情况都不适用。所以,使用volatile是一种 -bug并且需要对这样的代码额外仔细检查。那些试图使用volatile的开发人员需要退一步想想 -他们真正想实现的是什么。 - -非常欢迎删除volatile变量的补丁 - 只要证明这些补丁完整的考虑了并发问题。 - -注释 ----- - -[1] http://lwn.net/Articles/233481/ -[2] http://lwn.net/Articles/233482/ - -致谢 ----- - -最初由Randy Dunlap推动并作初步研究 -由Jonathan Corbet撰写 -参考Satyam Sharma,Johannes Stezenbach,Jesper Juhl,Heikki Orsila, -H. Peter Anvin,Philipp Hahn和Stefan Richter的意见改善了本档。 -- cgit v1.2.3 From 744da9033b3a59be21f135a10b8150e9a0352198 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:33 +0800 Subject: docs/zh_CN: change Chinese index to know process dir And add some description translation in index file. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Li Zefan Cc: Shawn Guo Cc: Fengguang Wu Cc: Coly Li Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/index.rst | 17 +++++++++++++---- 1 file changed, 13 insertions(+), 4 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/index.rst b/Documentation/translations/zh_CN/index.rst index 75956d669962..d3165535ec9e 100644 --- a/Documentation/translations/zh_CN/index.rst +++ b/Documentation/translations/zh_CN/index.rst @@ -3,10 +3,19 @@ \renewcommand\thesection* \renewcommand\thesubsection* -Chinese translations -==================== +中文翻译 +======== + +这些手册包含有关如何开发内核的整体信息。内核社区非常庞大,一年下来有数千名开发 +人员做出贡献。 与任何大型社区一样,知道如何完成任务将使得更改合并的过程变得更 +加容易。 .. toctree:: - :maxdepth: 1 + :maxdepth: 2 + + process/index + +目录和表格 +---------- - coding-style +* :ref:`genindex` -- cgit v1.2.3 From 653f10690164d2ab7d3b328a54d53140a8f3d035 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:34 +0800 Subject: docs/zh_CN: add index file into process dir Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Li Zefan Cc: Shawn Guo Cc: Fengguang Wu Cc: Coly Li Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/index.rst | 53 ++++++++++++++++++++++ 1 file changed, 53 insertions(+) create mode 100644 Documentation/translations/zh_CN/process/index.rst (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/index.rst b/Documentation/translations/zh_CN/process/index.rst new file mode 100644 index 000000000000..03939e1a7b92 --- /dev/null +++ b/Documentation/translations/zh_CN/process/index.rst @@ -0,0 +1,53 @@ +.. raw:: latex + + \renewcommand\thesection* + \renewcommand\thesubsection* + +.. include:: ../disclaimer-zh_CN.rst + +:Original: :ref:`Documentation/process/index.rst ` +:Translator: Alex Shi + +.. _cn_process_index: + +与Linux 内核社区一起工作 +======================== + +那么你想成为Linux内核开发人员? 欢迎! 不但从技术意义上讲有很多关于内核的知识 +需要学,而且了解我们社区的工作方式也很重要。 阅读这些文章可以让您以更轻松地, +麻烦最少的方式将更改合并到内核。 + +以下是每位开发人员应阅读的基本指南。 + +.. toctree:: + :maxdepth: 1 + + howto + submitting-patches + coding-style + email-clients + +其它大多数开发人员感兴趣的社区指南: + + +.. toctree:: + :maxdepth: 1 + + submitting-drivers + stable-api-nonsense + stable-kernel-rules + +这些是一些总体技术指南,由于缺乏更好的地方,现在已经放在这里 + +.. toctree:: + :maxdepth: 1 + + magic-number + volatile-considered-harmful + +.. only:: subproject and html + + 目录 + ==== + + * :ref:`genindex` -- cgit v1.2.3 From 32946a03984d466c80345167bd53fe1e3195ce8f Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:35 +0800 Subject: docs/zh_CN: rename HOWTO into process directory Make it available in htmldocs Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Li Yang Cc: Li Zefan Cc: Shawn Guo Cc: Fengguang Wu Cc: Coly Li Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/HOWTO | 525 --------------------- Documentation/translations/zh_CN/process/howto.rst | 525 +++++++++++++++++++++ 2 files changed, 525 insertions(+), 525 deletions(-) delete mode 100644 Documentation/translations/zh_CN/process/HOWTO create mode 100644 Documentation/translations/zh_CN/process/howto.rst (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/HOWTO b/Documentation/translations/zh_CN/process/HOWTO deleted file mode 100644 index 7a00a8a4eb15..000000000000 --- a/Documentation/translations/zh_CN/process/HOWTO +++ /dev/null @@ -1,525 +0,0 @@ -Chinese translated version of Documentation/process/howto.rst - -If you have any comment or update to the content, please contact the -original document maintainer directly. However, if you have a problem -communicating in English you can also ask the Chinese maintainer for -help. Contact the Chinese maintainer if this translation is outdated -or if there is a problem with the translation. - -Maintainer: Greg Kroah-Hartman -Chinese maintainer: Li Yang ---------------------------------------------------------------------- -Documentation/process/howto.rst 的中文翻译 - -如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 -交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者。 - -英文版维护者: Greg Kroah-Hartman -中文版维护者: 李阳 Li Yang -中文版翻译者: 李阳 Li Yang -中文版校译者: 钟宇 TripleX Chung - 陈琦 Maggie Chen - 王聪 Wang Cong - -以下为正文 ---------------------------------------------------------------------- - -如何参与Linux内核开发 ---------------------- - -这是一篇将如何参与Linux内核开发的相关问题一网打尽的终极秘笈。它将指导你 -成为一名Linux内核开发者,并且学会如何同Linux内核开发社区合作。它尽可能不 -包括任何关于内核编程的技术细节,但会给你指引一条获得这些知识的正确途径。 - -如果这篇文章中的任何内容不再适用,请给文末列出的文件维护者发送补丁。 - - -入门 ----- - -你想了解如何成为一名Linux内核开发者?或者老板吩咐你“给这个设备写个Linux -驱动程序”?这篇文章的目的就是教会你达成这些目标的全部诀窍,它将描述你需 -要经过的流程以及给出如何同内核社区合作的一些提示。它还将试图解释内核社区 -为何这样运作。 - -Linux内核大部分是由C语言写成的,一些体系结构相关的代码用到了汇编语言。要 -参与内核开发,你必须精通C语言。除非你想为某个架构开发底层代码,否则你并 -不需要了解(任何体系结构的)汇编语言。下面列举的书籍虽然不能替代扎实的C -语言教育和多年的开发经验,但如果需要的话,做为参考还是不错的: - - "The C Programming Language" by Kernighan and Ritchie [Prentice Hall] - 《C程序设计语言(第2版·新版)》(徐宝文 李志 译)[机械工业出版社] - - "Practical C Programming" by Steve Oualline [O'Reilly] - 《实用C语言编程(第三版)》(郭大海 译)[中国电力出版社] - - "C: A Reference Manual" by Harbison and Steele [Prentice Hall] - 《C语言参考手册(原书第5版)》(邱仲潘 等译)[机械工业出版社] - -Linux内核使用GNU C和GNU工具链开发。虽然它遵循ISO C89标准,但也用到了一些 -标准中没有定义的扩展。内核是自给自足的C环境,不依赖于标准C库的支持,所以 -并不支持C标准中的部分定义。比如long long类型的大数除法和浮点运算就不允许 -使用。有时候确实很难弄清楚内核对工具链的要求和它所使用的扩展,不幸的是目 -前还没有明确的参考资料可以解释它们。请查阅gcc信息页(使用“info gcc”命令 -显示)获得一些这方面信息。 - -请记住你是在学习怎么和已经存在的开发社区打交道。它由一群形形色色的人组成, -他们对代码、风格和过程有着很高的标准。这些标准是在长期实践中总结出来的, -适应于地理上分散的大型开发团队。它们已经被很好得整理成档,建议你在开发 -之前尽可能多的学习这些标准,而不要期望别人来适应你或者你公司的行为方式。 - - -法律问题 --------- - -Linux内核源代码都是在GPL(通用公共许可证)的保护下发布的。要了解这种许可 -的细节请查看源代码主目录下的COPYING文件。如果你对它还有更深入问题请联系 -律师,而不要在Linux内核邮件组上提问。因为邮件组里的人并不是律师,不要期 -望他们的话有法律效力。 - -对于GPL的常见问题和解答,请访问以下链接: - http://www.gnu.org/licenses/gpl-faq.html - - -文档 ----- - -Linux内核代码中包含有大量的文档。这些文档对于学习如何与内核社区互动有着 -不可估量的价值。当一个新的功能被加入内核,最好把解释如何使用这个功能的文 -档也放进内核。当内核的改动导致面向用户空间的接口发生变化时,最好将相关信 -息或手册页(manpages)的补丁发到mtk.manpages@gmail.com,以向手册页(manpages) -的维护者解释这些变化。 - -以下是内核代码中需要阅读的文档: - README - 文件简要介绍了Linux内核的背景,并且描述了如何配置和编译内核。内核的 - 新用户应该从这里开始。 - - Documentation/process/changes.rst - 文件给出了用来编译和使用内核所需要的最小软件包列表。 - - Documentation/process/coding-style.rst - 描述Linux内核的代码风格和理由。所有新代码需要遵守这篇文档中定义的规 - 范。大多数维护者只会接收符合规定的补丁,很多人也只会帮忙检查符合风格 - 的代码。 - - Documentation/process/submitting-patches.rst - Documentation/process/submitting-drivers.rst - 这两份文档明确描述如何创建和发送补丁,其中包括(但不仅限于): - - 邮件内容 - - 邮件格式 - - 选择收件人 - 遵守这些规定并不能保证提交成功(因为所有补丁需要通过严格的内容和风格 - 审查),但是忽视他们几乎就意味着失败。 - - 其他关于如何正确地生成补丁的优秀文档包括: - "The Perfect Patch" - http://www.ozlabs.org/~akpm/stuff/tpp.txt - "Linux kernel patch submission format" - http://linux.yyz.us/patch-format.html - - Documentation/process/stable-api-nonsense.rst - 论证内核为什么特意不包括稳定的内核内部API,也就是说不包括像这样的特 - 性: - - 子系统中间层(为了兼容性?) - - 在不同操作系统间易于移植的驱动程序 - - 减缓(甚至阻止)内核代码的快速变化 - 这篇文档对于理解Linux的开发哲学至关重要。对于将开发平台从其他操作系 - 统转移到Linux的人来说也很重要。 - - Documentation/admin-guide/security-bugs.rst - 如果你认为自己发现了Linux内核的安全性问题,请根据这篇文档中的步骤来 - 提醒其他内核开发者并帮助解决这个问题。 - - Documentation/process/management-style.rst - 描述内核维护者的工作方法及其共有特点。这对于刚刚接触内核开发(或者对 - 它感到好奇)的人来说很重要,因为它解释了很多对于内核维护者独特行为的 - 普遍误解与迷惑。 - - Documentation/process/stable-kernel-rules.rst - 解释了稳定版内核发布的规则,以及如何将改动放入这些版本的步骤。 - - Documentation/process/kernel-docs.rst - 有助于内核开发的外部文档列表。如果你在内核自带的文档中没有找到你想找 - 的内容,可以查看这些文档。 - - Documentation/process/applying-patches.rst - 关于补丁是什么以及如何将它打在不同内核开发分支上的好介绍 - -内核还拥有大量从代码自动生成的文档。它包含内核内部API的全面介绍以及如何 -妥善处理加锁的规则。生成的文档会放在 Documentation/DocBook/目录下。在内 -核源码的主目录中使用以下不同命令将会分别生成PDF、Postscript、HTML和手册 -页等不同格式的文档: - make pdfdocs - make htmldocs - - -如何成为内核开发者 ------------------- -如果你对Linux内核开发一无所知,你应该访问“Linux内核新手”计划: - http://kernelnewbies.org -它拥有一个可以问各种最基本的内核开发问题的邮件列表(在提问之前一定要记得 -查找已往的邮件,确认是否有人已经回答过相同的问题)。它还拥有一个可以获得 -实时反馈的IRC聊天频道,以及大量对于学习Linux内核开发相当有帮助的文档。 - -网站简要介绍了源代码组织结构、子系统划分以及目前正在进行的项目(包括内核 -中的和单独维护的)。它还提供了一些基本的帮助信息,比如如何编译内核和打补 -丁。 - -如果你想加入内核开发社区并协助完成一些任务,却找不到从哪里开始,可以访问 -“Linux内核房管员”计划: - http://kernelnewbies.org/KernelJanitors -这是极佳的起点。它提供一个相对简单的任务列表,列出内核代码中需要被重新 -整理或者改正的地方。通过和负责这个计划的开发者们一同工作,你会学到将补丁 -集成进内核的基本原理。如果还没有决定下一步要做什么的话,你还可能会得到方 -向性的指点。 - -如果你已经有一些现成的代码想要放到内核中,但是需要一些帮助来使它们拥有正 -确的格式。请访问“内核导师”计划。这个计划就是用来帮助你完成这个目标的。它 -是一个邮件列表,地址如下: - http://selenic.com/mailman/listinfo/kernel-mentors - -在真正动手修改内核代码之前,理解要修改的代码如何运作是必需的。要达到这个 -目的,没什么办法比直接读代码更有效了(大多数花招都会有相应的注释),而且 -一些特制的工具还可以提供帮助。例如,“Linux代码交叉引用”项目就是一个值得 -特别推荐的帮助工具,它将源代码显示在有编目和索引的网页上。其中一个更新及 -时的内核源码库,可以通过以下地址访问: - http://sosdg.org/~coywolf/lxr/ - - -开发流程 --------- - -目前Linux内核开发流程包括几个“主内核分支”和很多子系统相关的内核分支。这 -些分支包括: - - 2.6.x主内核源码树 - - 2.6.x.y -stable内核源码树 - - 2.6.x -mm内核补丁集 - - 子系统相关的内核源码树和补丁集 - - -2.6.x内核主源码树 ------------------ -2.6.x内核是由Linus Torvalds(Linux的创造者)亲自维护的。你可以在 -kernel.org网站的pub/linux/kernel/v2.6/目录下找到它。它的开发遵循以下步 -骤: - - 每当一个新版本的内核被发布,为期两周的集成窗口将被打开。在这段时间里 - 维护者可以向Linus提交大段的修改,通常这些修改已经被放到-mm内核中几个 - 星期了。提交大量修改的首选方式是使用git工具(内核的代码版本管理工具 - ,更多的信息可以在http://git-scm.com/获取),不过使用普通补丁也是可以 - 的。 - - 两个星期以后-rc1版本内核发布。之后只有不包含可能影响整个内核稳定性的 - 新功能的补丁才可能被接受。请注意一个全新的驱动程序(或者文件系统)有 - 可能在-rc1后被接受是因为这样的修改完全独立,不会影响其他的代码,所以 - 没有造成内核退步的风险。在-rc1以后也可以用git向Linus提交补丁,不过所 - 有的补丁需要同时被发送到相应的公众邮件列表以征询意见。 - - 当Linus认为当前的git源码树已经达到一个合理健全的状态足以发布供人测试 - 时,一个新的-rc版本就会被发布。计划是每周都发布新的-rc版本。 - - 这个过程一直持续下去直到内核被认为达到足够稳定的状态,持续时间大概是 - 6个星期。 - -关于内核发布,值得一提的是Andrew Morton在linux-kernel邮件列表中如是说: - “没有人知道新内核何时会被发布,因为发布是根据已知bug的情况来决定 - 的,而不是根据一个事先制定好的时间表。” - - -2.6.x.y -stable(稳定版)内核源码树 ------------------------------------ -由4个数字组成的内核版本号说明此内核是-stable版本。它们包含基于2.6.x版本 -内核的相对较小且至关重要的修补,这些修补针对安全性问题或者严重的内核退步。 - -这种版本的内核适用于那些期望获得最新的稳定版内核并且不想参与测试开发版或 -者实验版的用户。 - -如果没有2.6.x.y版本内核存在,那么最新的2.6.x版本内核就相当于是当前的稳定 -版内核。 - -2.6.x.y版本由“稳定版”小组(邮件地址)维护,一般隔周发 -布新版本。 - -内核源码中的Documentation/process/stable-kernel-rules.rst文件具体描述了可被稳定 -版内核接受的修改类型以及发布的流程。 - - -2.6.x -mm补丁集 ---------------- -这是由Andrew Morton维护的试验性内核补丁集。Andrew将所有子系统的内核源码 -和补丁拼凑到一起,并且加入了大量从linux-kernel邮件列表中采集的补丁。这个 -源码树是新功能和补丁的试炼场。当补丁在-mm补丁集里证明了其价值以后Andrew -或者相应子系统的维护者会将补丁发给Linus以便集成进主内核源码树。 - -在将所有新补丁发给Linus以集成到主内核源码树之前,我们非常鼓励先把这些补 -丁放在-mm版内核源码树中进行测试。 - -这些内核版本不适合在需要稳定运行的系统上运行,因为运行它们比运行任何其他 -内核分支都更具有风险。 - -如果你想为内核开发进程提供帮助,请尝试并使用这些内核版本,并在 -linux-kernel邮件列表中提供反馈,告诉大家你遇到了问题还是一切正常。 - -通常-mm版补丁集不光包括这些额外的试验性补丁,还包括发布时-git版主源码树 -中的改动。 - --mm版内核没有固定的发布周期,但是通常在每两个-rc版内核发布之间都会有若干 -个-mm版内核发布(一般是1至3个)。 - - -子系统相关内核源码树和补丁集 ----------------------------- -相当一部分内核子系统开发者会公开他们自己的开发源码树,以便其他人能了解内 -核的不同领域正在发生的事情。如上所述,这些源码树会被集成到-mm版本内核中。 - -下面是目前可用的一些内核源码树的列表: - 通过git管理的源码树: - - Kbuild开发源码树, Sam Ravnborg - git.kernel.org:/pub/scm/linux/kernel/git/sam/kbuild.git - - - ACPI开发源码树, Len Brown - git.kernel.org:/pub/scm/linux/kernel/git/lenb/linux-acpi-2.6.git - - - 块设备开发源码树, Jens Axboe - git.kernel.org:/pub/scm/linux/kernel/git/axboe/linux-2.6-block.git - - - DRM开发源码树, Dave Airlie - git.kernel.org:/pub/scm/linux/kernel/git/airlied/drm-2.6.git - - - ia64开发源码树, Tony Luck - git.kernel.org:/pub/scm/linux/kernel/git/aegl/linux-2.6.git - - - ieee1394开发源码树, Jody McIntyre - git.kernel.org:/pub/scm/linux/kernel/git/scjody/ieee1394.git - - - infiniband开发源码树, Roland Dreier - git.kernel.org:/pub/scm/linux/kernel/git/roland/infiniband.git - - - libata开发源码树, Jeff Garzik - git.kernel.org:/pub/scm/linux/kernel/git/jgarzik/libata-dev.git - - - 网络驱动程序开发源码树, Jeff Garzik - git.kernel.org:/pub/scm/linux/kernel/git/jgarzik/netdev-2.6.git - - - pcmcia开发源码树, Dominik Brodowski - git.kernel.org:/pub/scm/linux/kernel/git/brodo/pcmcia-2.6.git - - - SCSI开发源码树, James Bottomley - git.kernel.org:/pub/scm/linux/kernel/git/jejb/scsi-misc-2.6.git - - 使用quilt管理的补丁集: - - USB, PCI, 驱动程序核心和I2C, Greg Kroah-Hartman - kernel.org/pub/linux/kernel/people/gregkh/gregkh-2.6/ - - x86-64, 部分i386, Andi Kleen - ftp.firstfloor.org:/pub/ak/x86_64/quilt/ - - 其他内核源码树可以在http://git.kernel.org的列表中和MAINTAINERS文件里 - 找到。 - -报告bug -------- - -bugzilla.kernel.org是Linux内核开发者们用来跟踪内核Bug的网站。我们鼓励用 -户在这个工具中报告找到的所有bug。如何使用内核bugzilla的细节请访问: - http://test.kernel.org/bugzilla/faq.html - -内核源码主目录中的admin-guide/reporting-bugs.rst文件里有一个很好的模板。它指导用户如何报 -告可能的内核bug以及需要提供哪些信息来帮助内核开发者们找到问题的根源。 - - -利用bug报告 ------------ - -练习内核开发技能的最好办法就是修改其他人报告的bug。你不光可以帮助内核变 -得更加稳定,还可以学会如何解决实际问题从而提高自己的技能,并且让其他开发 -者感受到你的存在。修改bug是赢得其他开发者赞誉的最好办法,因为并不是很多 -人都喜欢浪费时间去修改别人报告的bug。 - -要尝试修改已知的bug,请访问http://bugzilla.kernel.org网址。如果你想获得 -最新bug的通知,可以订阅bugme-new邮件列表(只有新的bug报告会被寄到这里) -或者订阅bugme-janitor邮件列表(所有bugzilla的变动都会被寄到这里)。 - - https://lists.linux-foundation.org/mailman/listinfo/bugme-new - https://lists.linux-foundation.org/mailman/listinfo/bugme-janitors - - -邮件列表 --------- - -正如上面的文档所描述,大多数的骨干内核开发者都加入了Linux Kernel邮件列 -表。如何订阅和退订列表的细节可以在这里找到: - http://vger.kernel.org/vger-lists.html#linux-kernel -网上很多地方都有这个邮件列表的存档(archive)。可以使用搜索引擎来找到这些 -存档。比如: - http://dir.gmane.org/gmane.linux.kernel -在发信之前,我们强烈建议你先在存档中搜索你想要讨论的问题。很多已经被详细 -讨论过的问题只在邮件列表的存档中可以找到。 - -大多数内核子系统也有自己独立的邮件列表来协调各自的开发工作。从 -MAINTAINERS文件中可以找到不同话题对应的邮件列表。 - -很多邮件列表架设在kernel.org服务器上。这些列表的信息可以在这里找到: - http://vger.kernel.org/vger-lists.html - -在使用这些邮件列表时,请记住保持良好的行为习惯。下面的链接提供了与这些列 -表(或任何其它邮件列表)交流的一些简单规则,虽然内容有点滥竽充数。 - http://www.albion.com/netiquette/ - -当有很多人回复你的邮件时,邮件的抄送列表会变得很长。请不要将任何人从抄送 -列表中删除,除非你有足够的理由这么做。也不要只回复到邮件列表。请习惯于同 -一封邮件接收两次(一封来自发送者一封来自邮件列表),而不要试图通过添加一 -些奇特的邮件头来解决这个问题,人们不会喜欢的。 - -记住保留你所回复内容的上下文和源头。在你回复邮件的顶部保留“某某某说到……” -这几行。将你的评论加在被引用的段落之间而不要放在邮件的顶部。 - -如果你在邮件中附带补丁,请确认它们是可以直接阅读的纯文本(如 -Documentation/process/submitting-patches.rst文档中所述)。内核开发者们不希望遇到附件 -或者被压缩了的补丁。只有这样才能保证他们可以直接评论你的每行代码。请确保 -你使用的邮件发送程序不会修改空格和制表符。一个防范性的测试方法是先将邮件 -发送给自己,然后自己尝试是否可以顺利地打上收到的补丁。如果测试不成功,请 -调整或者更换你的邮件发送程序直到它正确工作为止。 - -总而言之,请尊重其他的邮件列表订阅者。 - - -同内核社区合作 ----------------- - -内核社区的目标就是提供尽善尽美的内核。所以当你提交补丁期望被接受进内核的 -时候,它的技术价值以及其他方面都将被评审。那么你可能会得到什么呢? - - 批评 - - 评论 - - 要求修改 - - 要求证明修改的必要性 - - 沉默 - -要记住,这些是把补丁放进内核的正常情况。你必须学会听取对补丁的批评和评论, -从技术层面评估它们,然后要么重写你的补丁要么简明扼要地论证修改是不必要 -的。如果你发的邮件没有得到任何回应,请过几天后再试一次,因为有时信件会湮 -没在茫茫信海中。 - -你不应该做的事情: - - 期望自己的补丁不受任何质疑就直接被接受 - - 翻脸 - - 忽略别人的评论 - - 没有按照别人的要求做任何修改就重新提交 - -在一个努力追寻最好技术方案的社区里,对于一个补丁有多少好处总会有不同的见 -解。你必须要抱着合作的态度,愿意改变自己的观点来适应内核的风格。或者至少 -愿意去证明你的想法是有价值的。记住,犯错误是允许的,只要你愿意朝着正确的 -方案去努力。 - -如果你的第一个补丁换来的是一堆修改建议,这是很正常的。这并不代表你的补丁 -不会被接受,也不意味着有人和你作对。你只需要改正所有提出的问题然后重新发 -送你的补丁。 - -内核社区和公司文化的差异 ------------------------- - -内核社区的工作模式同大多数传统公司开发队伍的工作模式并不相同。下面这些例 -子,可以帮助你避免某些可能发生问题: - 用这些话介绍你的修改提案会有好处: - - 它同时解决了多个问题 - - 它删除了2000行代码 - - 这是补丁,它已经解释了我想要说明的 - - 我在5种不同的体系结构上测试过它…… - - 这是一系列小补丁用来…… - - 这个修改提高了普通机器的性能…… - - 应该避免如下的说法: - - 我们在AIX/ptx/Solaris就是这么做的,所以这么做肯定是好的…… - - 我做这行已经20年了,所以…… - - 为了我们公司赚钱考虑必须这么做 - - 这是我们的企业产品线所需要的 - - 这里是描述我观点的1000页设计文档 - - 这是一个5000行的补丁用来…… - - 我重写了现在乱七八糟的代码,这就是…… - - 我被规定了最后期限,所以这个补丁需要立刻被接受 - -另外一个内核社区与大部分传统公司的软件开发队伍不同的地方是无法面对面地交 -流。使用电子邮件和IRC聊天工具做为主要沟通工具的一个好处是性别和种族歧视 -将会更少。Linux内核的工作环境更能接受妇女和少数族群,因为每个人在别人眼 -里只是一个邮件地址。国际化也帮助了公平的实现,因为你无法通过姓名来判断人 -的性别。男人有可能叫李丽,女人也有可能叫王刚。大多数在Linux内核上工作过 -并表达过看法的女性对在linux上工作的经历都给出了正面的评价。 - -对于一些不习惯使用英语的人来说,语言可能是一个引起问题的障碍。在邮件列表 -中要正确地表达想法必需良好地掌握语言,所以建议你在发送邮件之前最好检查一 -下英文写得是否正确。 - - -拆分修改 --------- - -Linux内核社区并不喜欢一下接收大段的代码。修改需要被恰当地介绍、讨论并且 -拆分成独立的小段。这几乎完全和公司中的习惯背道而驰。你的想法应该在开发最 -开始的阶段就让大家知道,这样你就可以及时获得对你正在进行的开发的反馈。这 -样也会让社区觉得你是在和他们协作,而不是仅仅把他们当作倾销新功能的对象。 -无论如何,你不要一次性地向邮件列表发送50封信,你的补丁序列应该永远用不到 -这么多。 - -将补丁拆开的原因如下: - -1) 小的补丁更有可能被接受,因为它们不需要太多的时间和精力去验证其正确性。 - 一个5行的补丁,可能在维护者看了一眼以后就会被接受。而500行的补丁则 - 需要数个小时来审查其正确性(所需时间随补丁大小增加大约呈指数级增长)。 - - 当出了问题的时候,小的补丁也会让调试变得非常容易。一个一个补丁地回溯 - 将会比仔细剖析一个被打上的大补丁(这个补丁破坏了其他东西)容易得多。 - -2)不光发送小的补丁很重要,在提交之前重新编排、化简(或者仅仅重新排列) - 补丁也是很重要的。 - -这里有内核开发者Al Viro打的一个比方: - “想象一个老师正在给学生批改数学作业。老师并不希望看到学生为了得 - 到正确解法所进行的尝试和产生的错误。他希望看到的是最干净最优雅的 - 解答。好学生了解这点,绝不会把最终解决之前的中间方案提交上去。” - - 内核开发也是这样。维护者和评审者不希望看到一个人在解决问题时的思 - 考过程。他们只希望看到简单和优雅的解决方案。 - -直接给出一流的解决方案,和社区一起协作讨论尚未完成的工作,这两者之间似乎 -很难找到一个平衡点。所以最好尽早开始收集有利于你进行改进的反馈;同时也要 -保证修改分成很多小块,这样在整个项目都准备好被包含进内核之前,其中的一部 -分可能会先被接收。 - -必须了解这样做是不可接受的:试图将未完成的工作提交进内核,然后再找时间修 -复。 - - -证明修改的必要性 ----------------- -除了将补丁拆成小块,很重要的一点是让Linux社区了解他们为什么需要这样修改。 -你必须证明新功能是有人需要的并且是有用的。 - - -记录修改 --------- - -当你发送补丁的时候,需要特别留意邮件正文的内容。因为这里的信息将会做为补 -丁的修改记录(ChangeLog),会被一直保留以备大家查阅。它需要完全地描述补丁, -包括: - - 为什么需要这个修改 - - 补丁的总体设计 - - 实现细节 - - 测试结果 - -想了解它具体应该看起来像什么,请查阅以下文档中的“ChangeLog”章节: - “The Perfect Patch” - http://www.ozlabs.org/~akpm/stuff/tpp.txt - - -这些事情有时候做起来很难。要在任何方面都做到完美可能需要好几年时间。这是 -一个持续提高的过程,它需要大量的耐心和决心。只要不放弃,你一定可以做到。 -很多人已经做到了,而他们都曾经和现在的你站在同样的起点上。 - - ---------------- -感谢Paolo Ciarrocchi允许“开发流程”部分基于他所写的文章 -(http://www.kerneltravel.net/newbie/2.6-development_process),感谢Randy -Dunlap和Gerrit Huizenga完善了应该说和不该说的列表。感谢Pat Mochel, Hanna -Linder, Randy Dunlap, Kay Sievers, Vojtech Pavlik, Jan Kara, Josh Boyer, -Kees Cook, Andrew Morton, Andi Kleen, Vadim Lobanov, Jesper Juhl, Adrian -Bunk, Keri Harris, Frans Pop, David A. Wheeler, Junio Hamano, Michael -Kerrisk和Alex Shepard的评审、建议和贡献。没有他们的帮助,这篇文档是不可 -能完成的。 - - - -英文版维护者: Greg Kroah-Hartman diff --git a/Documentation/translations/zh_CN/process/howto.rst b/Documentation/translations/zh_CN/process/howto.rst new file mode 100644 index 000000000000..7a00a8a4eb15 --- /dev/null +++ b/Documentation/translations/zh_CN/process/howto.rst @@ -0,0 +1,525 @@ +Chinese translated version of Documentation/process/howto.rst + +If you have any comment or update to the content, please contact the +original document maintainer directly. However, if you have a problem +communicating in English you can also ask the Chinese maintainer for +help. Contact the Chinese maintainer if this translation is outdated +or if there is a problem with the translation. + +Maintainer: Greg Kroah-Hartman +Chinese maintainer: Li Yang +--------------------------------------------------------------------- +Documentation/process/howto.rst 的中文翻译 + +如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 +交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 +译存在问题,请联系中文版维护者。 + +英文版维护者: Greg Kroah-Hartman +中文版维护者: 李阳 Li Yang +中文版翻译者: 李阳 Li Yang +中文版校译者: 钟宇 TripleX Chung + 陈琦 Maggie Chen + 王聪 Wang Cong + +以下为正文 +--------------------------------------------------------------------- + +如何参与Linux内核开发 +--------------------- + +这是一篇将如何参与Linux内核开发的相关问题一网打尽的终极秘笈。它将指导你 +成为一名Linux内核开发者,并且学会如何同Linux内核开发社区合作。它尽可能不 +包括任何关于内核编程的技术细节,但会给你指引一条获得这些知识的正确途径。 + +如果这篇文章中的任何内容不再适用,请给文末列出的文件维护者发送补丁。 + + +入门 +---- + +你想了解如何成为一名Linux内核开发者?或者老板吩咐你“给这个设备写个Linux +驱动程序”?这篇文章的目的就是教会你达成这些目标的全部诀窍,它将描述你需 +要经过的流程以及给出如何同内核社区合作的一些提示。它还将试图解释内核社区 +为何这样运作。 + +Linux内核大部分是由C语言写成的,一些体系结构相关的代码用到了汇编语言。要 +参与内核开发,你必须精通C语言。除非你想为某个架构开发底层代码,否则你并 +不需要了解(任何体系结构的)汇编语言。下面列举的书籍虽然不能替代扎实的C +语言教育和多年的开发经验,但如果需要的话,做为参考还是不错的: + - "The C Programming Language" by Kernighan and Ritchie [Prentice Hall] + 《C程序设计语言(第2版·新版)》(徐宝文 李志 译)[机械工业出版社] + - "Practical C Programming" by Steve Oualline [O'Reilly] + 《实用C语言编程(第三版)》(郭大海 译)[中国电力出版社] + - "C: A Reference Manual" by Harbison and Steele [Prentice Hall] + 《C语言参考手册(原书第5版)》(邱仲潘 等译)[机械工业出版社] + +Linux内核使用GNU C和GNU工具链开发。虽然它遵循ISO C89标准,但也用到了一些 +标准中没有定义的扩展。内核是自给自足的C环境,不依赖于标准C库的支持,所以 +并不支持C标准中的部分定义。比如long long类型的大数除法和浮点运算就不允许 +使用。有时候确实很难弄清楚内核对工具链的要求和它所使用的扩展,不幸的是目 +前还没有明确的参考资料可以解释它们。请查阅gcc信息页(使用“info gcc”命令 +显示)获得一些这方面信息。 + +请记住你是在学习怎么和已经存在的开发社区打交道。它由一群形形色色的人组成, +他们对代码、风格和过程有着很高的标准。这些标准是在长期实践中总结出来的, +适应于地理上分散的大型开发团队。它们已经被很好得整理成档,建议你在开发 +之前尽可能多的学习这些标准,而不要期望别人来适应你或者你公司的行为方式。 + + +法律问题 +-------- + +Linux内核源代码都是在GPL(通用公共许可证)的保护下发布的。要了解这种许可 +的细节请查看源代码主目录下的COPYING文件。如果你对它还有更深入问题请联系 +律师,而不要在Linux内核邮件组上提问。因为邮件组里的人并不是律师,不要期 +望他们的话有法律效力。 + +对于GPL的常见问题和解答,请访问以下链接: + http://www.gnu.org/licenses/gpl-faq.html + + +文档 +---- + +Linux内核代码中包含有大量的文档。这些文档对于学习如何与内核社区互动有着 +不可估量的价值。当一个新的功能被加入内核,最好把解释如何使用这个功能的文 +档也放进内核。当内核的改动导致面向用户空间的接口发生变化时,最好将相关信 +息或手册页(manpages)的补丁发到mtk.manpages@gmail.com,以向手册页(manpages) +的维护者解释这些变化。 + +以下是内核代码中需要阅读的文档: + README + 文件简要介绍了Linux内核的背景,并且描述了如何配置和编译内核。内核的 + 新用户应该从这里开始。 + + Documentation/process/changes.rst + 文件给出了用来编译和使用内核所需要的最小软件包列表。 + + Documentation/process/coding-style.rst + 描述Linux内核的代码风格和理由。所有新代码需要遵守这篇文档中定义的规 + 范。大多数维护者只会接收符合规定的补丁,很多人也只会帮忙检查符合风格 + 的代码。 + + Documentation/process/submitting-patches.rst + Documentation/process/submitting-drivers.rst + 这两份文档明确描述如何创建和发送补丁,其中包括(但不仅限于): + - 邮件内容 + - 邮件格式 + - 选择收件人 + 遵守这些规定并不能保证提交成功(因为所有补丁需要通过严格的内容和风格 + 审查),但是忽视他们几乎就意味着失败。 + + 其他关于如何正确地生成补丁的优秀文档包括: + "The Perfect Patch" + http://www.ozlabs.org/~akpm/stuff/tpp.txt + "Linux kernel patch submission format" + http://linux.yyz.us/patch-format.html + + Documentation/process/stable-api-nonsense.rst + 论证内核为什么特意不包括稳定的内核内部API,也就是说不包括像这样的特 + 性: + - 子系统中间层(为了兼容性?) + - 在不同操作系统间易于移植的驱动程序 + - 减缓(甚至阻止)内核代码的快速变化 + 这篇文档对于理解Linux的开发哲学至关重要。对于将开发平台从其他操作系 + 统转移到Linux的人来说也很重要。 + + Documentation/admin-guide/security-bugs.rst + 如果你认为自己发现了Linux内核的安全性问题,请根据这篇文档中的步骤来 + 提醒其他内核开发者并帮助解决这个问题。 + + Documentation/process/management-style.rst + 描述内核维护者的工作方法及其共有特点。这对于刚刚接触内核开发(或者对 + 它感到好奇)的人来说很重要,因为它解释了很多对于内核维护者独特行为的 + 普遍误解与迷惑。 + + Documentation/process/stable-kernel-rules.rst + 解释了稳定版内核发布的规则,以及如何将改动放入这些版本的步骤。 + + Documentation/process/kernel-docs.rst + 有助于内核开发的外部文档列表。如果你在内核自带的文档中没有找到你想找 + 的内容,可以查看这些文档。 + + Documentation/process/applying-patches.rst + 关于补丁是什么以及如何将它打在不同内核开发分支上的好介绍 + +内核还拥有大量从代码自动生成的文档。它包含内核内部API的全面介绍以及如何 +妥善处理加锁的规则。生成的文档会放在 Documentation/DocBook/目录下。在内 +核源码的主目录中使用以下不同命令将会分别生成PDF、Postscript、HTML和手册 +页等不同格式的文档: + make pdfdocs + make htmldocs + + +如何成为内核开发者 +------------------ +如果你对Linux内核开发一无所知,你应该访问“Linux内核新手”计划: + http://kernelnewbies.org +它拥有一个可以问各种最基本的内核开发问题的邮件列表(在提问之前一定要记得 +查找已往的邮件,确认是否有人已经回答过相同的问题)。它还拥有一个可以获得 +实时反馈的IRC聊天频道,以及大量对于学习Linux内核开发相当有帮助的文档。 + +网站简要介绍了源代码组织结构、子系统划分以及目前正在进行的项目(包括内核 +中的和单独维护的)。它还提供了一些基本的帮助信息,比如如何编译内核和打补 +丁。 + +如果你想加入内核开发社区并协助完成一些任务,却找不到从哪里开始,可以访问 +“Linux内核房管员”计划: + http://kernelnewbies.org/KernelJanitors +这是极佳的起点。它提供一个相对简单的任务列表,列出内核代码中需要被重新 +整理或者改正的地方。通过和负责这个计划的开发者们一同工作,你会学到将补丁 +集成进内核的基本原理。如果还没有决定下一步要做什么的话,你还可能会得到方 +向性的指点。 + +如果你已经有一些现成的代码想要放到内核中,但是需要一些帮助来使它们拥有正 +确的格式。请访问“内核导师”计划。这个计划就是用来帮助你完成这个目标的。它 +是一个邮件列表,地址如下: + http://selenic.com/mailman/listinfo/kernel-mentors + +在真正动手修改内核代码之前,理解要修改的代码如何运作是必需的。要达到这个 +目的,没什么办法比直接读代码更有效了(大多数花招都会有相应的注释),而且 +一些特制的工具还可以提供帮助。例如,“Linux代码交叉引用”项目就是一个值得 +特别推荐的帮助工具,它将源代码显示在有编目和索引的网页上。其中一个更新及 +时的内核源码库,可以通过以下地址访问: + http://sosdg.org/~coywolf/lxr/ + + +开发流程 +-------- + +目前Linux内核开发流程包括几个“主内核分支”和很多子系统相关的内核分支。这 +些分支包括: + - 2.6.x主内核源码树 + - 2.6.x.y -stable内核源码树 + - 2.6.x -mm内核补丁集 + - 子系统相关的内核源码树和补丁集 + + +2.6.x内核主源码树 +----------------- +2.6.x内核是由Linus Torvalds(Linux的创造者)亲自维护的。你可以在 +kernel.org网站的pub/linux/kernel/v2.6/目录下找到它。它的开发遵循以下步 +骤: + - 每当一个新版本的内核被发布,为期两周的集成窗口将被打开。在这段时间里 + 维护者可以向Linus提交大段的修改,通常这些修改已经被放到-mm内核中几个 + 星期了。提交大量修改的首选方式是使用git工具(内核的代码版本管理工具 + ,更多的信息可以在http://git-scm.com/获取),不过使用普通补丁也是可以 + 的。 + - 两个星期以后-rc1版本内核发布。之后只有不包含可能影响整个内核稳定性的 + 新功能的补丁才可能被接受。请注意一个全新的驱动程序(或者文件系统)有 + 可能在-rc1后被接受是因为这样的修改完全独立,不会影响其他的代码,所以 + 没有造成内核退步的风险。在-rc1以后也可以用git向Linus提交补丁,不过所 + 有的补丁需要同时被发送到相应的公众邮件列表以征询意见。 + - 当Linus认为当前的git源码树已经达到一个合理健全的状态足以发布供人测试 + 时,一个新的-rc版本就会被发布。计划是每周都发布新的-rc版本。 + - 这个过程一直持续下去直到内核被认为达到足够稳定的状态,持续时间大概是 + 6个星期。 + +关于内核发布,值得一提的是Andrew Morton在linux-kernel邮件列表中如是说: + “没有人知道新内核何时会被发布,因为发布是根据已知bug的情况来决定 + 的,而不是根据一个事先制定好的时间表。” + + +2.6.x.y -stable(稳定版)内核源码树 +----------------------------------- +由4个数字组成的内核版本号说明此内核是-stable版本。它们包含基于2.6.x版本 +内核的相对较小且至关重要的修补,这些修补针对安全性问题或者严重的内核退步。 + +这种版本的内核适用于那些期望获得最新的稳定版内核并且不想参与测试开发版或 +者实验版的用户。 + +如果没有2.6.x.y版本内核存在,那么最新的2.6.x版本内核就相当于是当前的稳定 +版内核。 + +2.6.x.y版本由“稳定版”小组(邮件地址)维护,一般隔周发 +布新版本。 + +内核源码中的Documentation/process/stable-kernel-rules.rst文件具体描述了可被稳定 +版内核接受的修改类型以及发布的流程。 + + +2.6.x -mm补丁集 +--------------- +这是由Andrew Morton维护的试验性内核补丁集。Andrew将所有子系统的内核源码 +和补丁拼凑到一起,并且加入了大量从linux-kernel邮件列表中采集的补丁。这个 +源码树是新功能和补丁的试炼场。当补丁在-mm补丁集里证明了其价值以后Andrew +或者相应子系统的维护者会将补丁发给Linus以便集成进主内核源码树。 + +在将所有新补丁发给Linus以集成到主内核源码树之前,我们非常鼓励先把这些补 +丁放在-mm版内核源码树中进行测试。 + +这些内核版本不适合在需要稳定运行的系统上运行,因为运行它们比运行任何其他 +内核分支都更具有风险。 + +如果你想为内核开发进程提供帮助,请尝试并使用这些内核版本,并在 +linux-kernel邮件列表中提供反馈,告诉大家你遇到了问题还是一切正常。 + +通常-mm版补丁集不光包括这些额外的试验性补丁,还包括发布时-git版主源码树 +中的改动。 + +-mm版内核没有固定的发布周期,但是通常在每两个-rc版内核发布之间都会有若干 +个-mm版内核发布(一般是1至3个)。 + + +子系统相关内核源码树和补丁集 +---------------------------- +相当一部分内核子系统开发者会公开他们自己的开发源码树,以便其他人能了解内 +核的不同领域正在发生的事情。如上所述,这些源码树会被集成到-mm版本内核中。 + +下面是目前可用的一些内核源码树的列表: + 通过git管理的源码树: + - Kbuild开发源码树, Sam Ravnborg + git.kernel.org:/pub/scm/linux/kernel/git/sam/kbuild.git + + - ACPI开发源码树, Len Brown + git.kernel.org:/pub/scm/linux/kernel/git/lenb/linux-acpi-2.6.git + + - 块设备开发源码树, Jens Axboe + git.kernel.org:/pub/scm/linux/kernel/git/axboe/linux-2.6-block.git + + - DRM开发源码树, Dave Airlie + git.kernel.org:/pub/scm/linux/kernel/git/airlied/drm-2.6.git + + - ia64开发源码树, Tony Luck + git.kernel.org:/pub/scm/linux/kernel/git/aegl/linux-2.6.git + + - ieee1394开发源码树, Jody McIntyre + git.kernel.org:/pub/scm/linux/kernel/git/scjody/ieee1394.git + + - infiniband开发源码树, Roland Dreier + git.kernel.org:/pub/scm/linux/kernel/git/roland/infiniband.git + + - libata开发源码树, Jeff Garzik + git.kernel.org:/pub/scm/linux/kernel/git/jgarzik/libata-dev.git + + - 网络驱动程序开发源码树, Jeff Garzik + git.kernel.org:/pub/scm/linux/kernel/git/jgarzik/netdev-2.6.git + + - pcmcia开发源码树, Dominik Brodowski + git.kernel.org:/pub/scm/linux/kernel/git/brodo/pcmcia-2.6.git + + - SCSI开发源码树, James Bottomley + git.kernel.org:/pub/scm/linux/kernel/git/jejb/scsi-misc-2.6.git + + 使用quilt管理的补丁集: + - USB, PCI, 驱动程序核心和I2C, Greg Kroah-Hartman + kernel.org/pub/linux/kernel/people/gregkh/gregkh-2.6/ + - x86-64, 部分i386, Andi Kleen + ftp.firstfloor.org:/pub/ak/x86_64/quilt/ + + 其他内核源码树可以在http://git.kernel.org的列表中和MAINTAINERS文件里 + 找到。 + +报告bug +------- + +bugzilla.kernel.org是Linux内核开发者们用来跟踪内核Bug的网站。我们鼓励用 +户在这个工具中报告找到的所有bug。如何使用内核bugzilla的细节请访问: + http://test.kernel.org/bugzilla/faq.html + +内核源码主目录中的admin-guide/reporting-bugs.rst文件里有一个很好的模板。它指导用户如何报 +告可能的内核bug以及需要提供哪些信息来帮助内核开发者们找到问题的根源。 + + +利用bug报告 +----------- + +练习内核开发技能的最好办法就是修改其他人报告的bug。你不光可以帮助内核变 +得更加稳定,还可以学会如何解决实际问题从而提高自己的技能,并且让其他开发 +者感受到你的存在。修改bug是赢得其他开发者赞誉的最好办法,因为并不是很多 +人都喜欢浪费时间去修改别人报告的bug。 + +要尝试修改已知的bug,请访问http://bugzilla.kernel.org网址。如果你想获得 +最新bug的通知,可以订阅bugme-new邮件列表(只有新的bug报告会被寄到这里) +或者订阅bugme-janitor邮件列表(所有bugzilla的变动都会被寄到这里)。 + + https://lists.linux-foundation.org/mailman/listinfo/bugme-new + https://lists.linux-foundation.org/mailman/listinfo/bugme-janitors + + +邮件列表 +-------- + +正如上面的文档所描述,大多数的骨干内核开发者都加入了Linux Kernel邮件列 +表。如何订阅和退订列表的细节可以在这里找到: + http://vger.kernel.org/vger-lists.html#linux-kernel +网上很多地方都有这个邮件列表的存档(archive)。可以使用搜索引擎来找到这些 +存档。比如: + http://dir.gmane.org/gmane.linux.kernel +在发信之前,我们强烈建议你先在存档中搜索你想要讨论的问题。很多已经被详细 +讨论过的问题只在邮件列表的存档中可以找到。 + +大多数内核子系统也有自己独立的邮件列表来协调各自的开发工作。从 +MAINTAINERS文件中可以找到不同话题对应的邮件列表。 + +很多邮件列表架设在kernel.org服务器上。这些列表的信息可以在这里找到: + http://vger.kernel.org/vger-lists.html + +在使用这些邮件列表时,请记住保持良好的行为习惯。下面的链接提供了与这些列 +表(或任何其它邮件列表)交流的一些简单规则,虽然内容有点滥竽充数。 + http://www.albion.com/netiquette/ + +当有很多人回复你的邮件时,邮件的抄送列表会变得很长。请不要将任何人从抄送 +列表中删除,除非你有足够的理由这么做。也不要只回复到邮件列表。请习惯于同 +一封邮件接收两次(一封来自发送者一封来自邮件列表),而不要试图通过添加一 +些奇特的邮件头来解决这个问题,人们不会喜欢的。 + +记住保留你所回复内容的上下文和源头。在你回复邮件的顶部保留“某某某说到……” +这几行。将你的评论加在被引用的段落之间而不要放在邮件的顶部。 + +如果你在邮件中附带补丁,请确认它们是可以直接阅读的纯文本(如 +Documentation/process/submitting-patches.rst文档中所述)。内核开发者们不希望遇到附件 +或者被压缩了的补丁。只有这样才能保证他们可以直接评论你的每行代码。请确保 +你使用的邮件发送程序不会修改空格和制表符。一个防范性的测试方法是先将邮件 +发送给自己,然后自己尝试是否可以顺利地打上收到的补丁。如果测试不成功,请 +调整或者更换你的邮件发送程序直到它正确工作为止。 + +总而言之,请尊重其他的邮件列表订阅者。 + + +同内核社区合作 +---------------- + +内核社区的目标就是提供尽善尽美的内核。所以当你提交补丁期望被接受进内核的 +时候,它的技术价值以及其他方面都将被评审。那么你可能会得到什么呢? + - 批评 + - 评论 + - 要求修改 + - 要求证明修改的必要性 + - 沉默 + +要记住,这些是把补丁放进内核的正常情况。你必须学会听取对补丁的批评和评论, +从技术层面评估它们,然后要么重写你的补丁要么简明扼要地论证修改是不必要 +的。如果你发的邮件没有得到任何回应,请过几天后再试一次,因为有时信件会湮 +没在茫茫信海中。 + +你不应该做的事情: + - 期望自己的补丁不受任何质疑就直接被接受 + - 翻脸 + - 忽略别人的评论 + - 没有按照别人的要求做任何修改就重新提交 + +在一个努力追寻最好技术方案的社区里,对于一个补丁有多少好处总会有不同的见 +解。你必须要抱着合作的态度,愿意改变自己的观点来适应内核的风格。或者至少 +愿意去证明你的想法是有价值的。记住,犯错误是允许的,只要你愿意朝着正确的 +方案去努力。 + +如果你的第一个补丁换来的是一堆修改建议,这是很正常的。这并不代表你的补丁 +不会被接受,也不意味着有人和你作对。你只需要改正所有提出的问题然后重新发 +送你的补丁。 + +内核社区和公司文化的差异 +------------------------ + +内核社区的工作模式同大多数传统公司开发队伍的工作模式并不相同。下面这些例 +子,可以帮助你避免某些可能发生问题: + 用这些话介绍你的修改提案会有好处: + - 它同时解决了多个问题 + - 它删除了2000行代码 + - 这是补丁,它已经解释了我想要说明的 + - 我在5种不同的体系结构上测试过它…… + - 这是一系列小补丁用来…… + - 这个修改提高了普通机器的性能…… + + 应该避免如下的说法: + - 我们在AIX/ptx/Solaris就是这么做的,所以这么做肯定是好的…… + - 我做这行已经20年了,所以…… + - 为了我们公司赚钱考虑必须这么做 + - 这是我们的企业产品线所需要的 + - 这里是描述我观点的1000页设计文档 + - 这是一个5000行的补丁用来…… + - 我重写了现在乱七八糟的代码,这就是…… + - 我被规定了最后期限,所以这个补丁需要立刻被接受 + +另外一个内核社区与大部分传统公司的软件开发队伍不同的地方是无法面对面地交 +流。使用电子邮件和IRC聊天工具做为主要沟通工具的一个好处是性别和种族歧视 +将会更少。Linux内核的工作环境更能接受妇女和少数族群,因为每个人在别人眼 +里只是一个邮件地址。国际化也帮助了公平的实现,因为你无法通过姓名来判断人 +的性别。男人有可能叫李丽,女人也有可能叫王刚。大多数在Linux内核上工作过 +并表达过看法的女性对在linux上工作的经历都给出了正面的评价。 + +对于一些不习惯使用英语的人来说,语言可能是一个引起问题的障碍。在邮件列表 +中要正确地表达想法必需良好地掌握语言,所以建议你在发送邮件之前最好检查一 +下英文写得是否正确。 + + +拆分修改 +-------- + +Linux内核社区并不喜欢一下接收大段的代码。修改需要被恰当地介绍、讨论并且 +拆分成独立的小段。这几乎完全和公司中的习惯背道而驰。你的想法应该在开发最 +开始的阶段就让大家知道,这样你就可以及时获得对你正在进行的开发的反馈。这 +样也会让社区觉得你是在和他们协作,而不是仅仅把他们当作倾销新功能的对象。 +无论如何,你不要一次性地向邮件列表发送50封信,你的补丁序列应该永远用不到 +这么多。 + +将补丁拆开的原因如下: + +1) 小的补丁更有可能被接受,因为它们不需要太多的时间和精力去验证其正确性。 + 一个5行的补丁,可能在维护者看了一眼以后就会被接受。而500行的补丁则 + 需要数个小时来审查其正确性(所需时间随补丁大小增加大约呈指数级增长)。 + + 当出了问题的时候,小的补丁也会让调试变得非常容易。一个一个补丁地回溯 + 将会比仔细剖析一个被打上的大补丁(这个补丁破坏了其他东西)容易得多。 + +2)不光发送小的补丁很重要,在提交之前重新编排、化简(或者仅仅重新排列) + 补丁也是很重要的。 + +这里有内核开发者Al Viro打的一个比方: + “想象一个老师正在给学生批改数学作业。老师并不希望看到学生为了得 + 到正确解法所进行的尝试和产生的错误。他希望看到的是最干净最优雅的 + 解答。好学生了解这点,绝不会把最终解决之前的中间方案提交上去。” + + 内核开发也是这样。维护者和评审者不希望看到一个人在解决问题时的思 + 考过程。他们只希望看到简单和优雅的解决方案。 + +直接给出一流的解决方案,和社区一起协作讨论尚未完成的工作,这两者之间似乎 +很难找到一个平衡点。所以最好尽早开始收集有利于你进行改进的反馈;同时也要 +保证修改分成很多小块,这样在整个项目都准备好被包含进内核之前,其中的一部 +分可能会先被接收。 + +必须了解这样做是不可接受的:试图将未完成的工作提交进内核,然后再找时间修 +复。 + + +证明修改的必要性 +---------------- +除了将补丁拆成小块,很重要的一点是让Linux社区了解他们为什么需要这样修改。 +你必须证明新功能是有人需要的并且是有用的。 + + +记录修改 +-------- + +当你发送补丁的时候,需要特别留意邮件正文的内容。因为这里的信息将会做为补 +丁的修改记录(ChangeLog),会被一直保留以备大家查阅。它需要完全地描述补丁, +包括: + - 为什么需要这个修改 + - 补丁的总体设计 + - 实现细节 + - 测试结果 + +想了解它具体应该看起来像什么,请查阅以下文档中的“ChangeLog”章节: + “The Perfect Patch” + http://www.ozlabs.org/~akpm/stuff/tpp.txt + + +这些事情有时候做起来很难。要在任何方面都做到完美可能需要好几年时间。这是 +一个持续提高的过程,它需要大量的耐心和决心。只要不放弃,你一定可以做到。 +很多人已经做到了,而他们都曾经和现在的你站在同样的起点上。 + + +--------------- +感谢Paolo Ciarrocchi允许“开发流程”部分基于他所写的文章 +(http://www.kerneltravel.net/newbie/2.6-development_process),感谢Randy +Dunlap和Gerrit Huizenga完善了应该说和不该说的列表。感谢Pat Mochel, Hanna +Linder, Randy Dunlap, Kay Sievers, Vojtech Pavlik, Jan Kara, Josh Boyer, +Kees Cook, Andrew Morton, Andi Kleen, Vadim Lobanov, Jesper Juhl, Adrian +Bunk, Keri Harris, Frans Pop, David A. Wheeler, Junio Hamano, Michael +Kerrisk和Alex Shepard的评审、建议和贡献。没有他们的帮助,这篇文档是不可 +能完成的。 + + + +英文版维护者: Greg Kroah-Hartman -- cgit v1.2.3 From 6014f056ac551322f4e83007ad2de53247a9823a Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:36 +0800 Subject: docs/zh_CN: howto format changes also with few contents changes Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Li Yang Cc: Li Zefan Cc: Shawn Guo Cc: Fengguang Wu Cc: Coly Li Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/howto.rst | 37 +++++++++------------- 1 file changed, 15 insertions(+), 22 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/howto.rst b/Documentation/translations/zh_CN/process/howto.rst index 7a00a8a4eb15..f25a74fb90da 100644 --- a/Documentation/translations/zh_CN/process/howto.rst +++ b/Documentation/translations/zh_CN/process/howto.rst @@ -1,32 +1,23 @@ -Chinese translated version of Documentation/process/howto.rst +.. _cn_process_howto: -If you have any comment or update to the content, please contact the -original document maintainer directly. However, if you have a problem -communicating in English you can also ask the Chinese maintainer for -help. Contact the Chinese maintainer if this translation is outdated -or if there is a problem with the translation. +.. include:: ../disclaimer-zh_CN.rst -Maintainer: Greg Kroah-Hartman -Chinese maintainer: Li Yang ---------------------------------------------------------------------- -Documentation/process/howto.rst 的中文翻译 +:Original: :ref:`Documentation/process/howto.rst ` 如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者。 +译存在问题,请联系中文版维护者:: -英文版维护者: Greg Kroah-Hartman -中文版维护者: 李阳 Li Yang -中文版翻译者: 李阳 Li Yang -中文版校译者: 钟宇 TripleX Chung - 陈琦 Maggie Chen - 王聪 Wang Cong - -以下为正文 ---------------------------------------------------------------------- + 英文版维护者: Greg Kroah-Hartman + 中文版维护者: 李阳 Li Yang + 中文版翻译者: 李阳 Li Yang + 中文版校译者: + 钟宇 TripleX Chung + 陈琦 Maggie Chen + 王聪 Wang Cong 如何参与Linux内核开发 ---------------------- +===================== 这是一篇将如何参与Linux内核开发的相关问题一网打尽的终极秘笈。它将指导你 成为一名Linux内核开发者,并且学会如何同Linux内核开发社区合作。它尽可能不 @@ -114,6 +105,7 @@ Linux内核代码中包含有大量的文档。这些文档对于学习如何与 "The Perfect Patch" http://www.ozlabs.org/~akpm/stuff/tpp.txt "Linux kernel patch submission format" + http://linux.yyz.us/patch-format.html Documentation/process/stable-api-nonsense.rst @@ -510,7 +502,8 @@ Linux内核社区并不喜欢一下接收大段的代码。修改需要被恰当 很多人已经做到了,而他们都曾经和现在的你站在同样的起点上。 ---------------- +感谢 +---- 感谢Paolo Ciarrocchi允许“开发流程”部分基于他所写的文章 (http://www.kerneltravel.net/newbie/2.6-development_process),感谢Randy Dunlap和Gerrit Huizenga完善了应该说和不该说的列表。感谢Pat Mochel, Hanna -- cgit v1.2.3 From 001ef4e0fc96fb7a0c99036e98e8f25f51df84b3 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:37 +0800 Subject: docs/zh_CN: rename SubmittingPatches for html links renamed: Documentation/translations/zh_CN/process/SubmittingPatches -> Documentation/translations/zh_CN/process/submitting-patches.rst For htmldoc links. And will change the doc format to rst. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: TripleX Chung Cc: Li Zefan Cc: Shawn Guo Cc: Fengguang Wu Cc: Coly Li Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- .../translations/zh_CN/process/SubmittingPatches | 412 --------------------- .../zh_CN/process/submitting-patches.rst | 412 +++++++++++++++++++++ 2 files changed, 412 insertions(+), 412 deletions(-) delete mode 100644 Documentation/translations/zh_CN/process/SubmittingPatches create mode 100644 Documentation/translations/zh_CN/process/submitting-patches.rst (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/SubmittingPatches b/Documentation/translations/zh_CN/process/SubmittingPatches deleted file mode 100644 index e9098da8f1a4..000000000000 --- a/Documentation/translations/zh_CN/process/SubmittingPatches +++ /dev/null @@ -1,412 +0,0 @@ -Chinese translated version of Documentation/process/submitting-patches.rst - -If you have any comment or update to the content, please contact the -original document maintainer directly. However, if you have a problem -communicating in English you can also ask the Chinese maintainer for -help. Contact the Chinese maintainer if this translation is outdated -or if there is a problem with the translation. - -Chinese maintainer: TripleX Chung ---------------------------------------------------------------------- -Documentation/process/submitting-patches.rst 的中文翻译 - -如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 -交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者。 - -中文版维护者: 钟宇 TripleX Chung -中文版翻译者: 钟宇 TripleX Chung -中文版校译者: 李阳 Li Yang - 王聪 Wang Cong - -以下为正文 ---------------------------------------------------------------------- - - 如何让你的改动进入内核 - 或者 - 获得亲爱的 Linus Torvalds 的关注和处理 ----------------------------------- - -对于想要将改动提交到 Linux 内核的个人或者公司来说,如果不熟悉“规矩”, -提交的流程会让人畏惧。本文档收集了一系列建议,这些建议可以大大的提高你 -的改动被接受的机会。 -阅读 Documentation/process/submit-checklist.rst 来获得在提交代码前需要检查的项目的列 -表。如果你在提交一个驱动程序,那么同时阅读一下 -Documentation/process/submitting-drivers.rst 。 - - --------------------------- -第一节 - 创建并发送你的改动 --------------------------- - -1) "diff -up" ------------ - -使用 "diff -up" 或者 "diff -uprN" 来创建补丁。 - -所有内核的改动,都是以补丁的形式呈现的,补丁由 diff(1) 生成。创建补丁的 -时候,要确认它是以 "unified diff" 格式创建的,这种格式由 diff(1) 的 '-u' -参数生成。而且,请使用 '-p' 参数,那样会显示每个改动所在的C函数,使得 -产生的补丁容易读得多。补丁应该基于内核源代码树的根目录,而不是里边的任 -何子目录。 -为一个单独的文件创建补丁,一般来说这样做就够了: - - SRCTREE= linux-2.6 - MYFILE= drivers/net/mydriver.c - - cd $SRCTREE - cp $MYFILE $MYFILE.orig - vi $MYFILE # make your change - cd .. - diff -up $SRCTREE/$MYFILE{.orig,} > /tmp/patch - -为多个文件创建补丁,你可以解开一个没有修改过的内核源代码树,然后和你自 -己的代码树之间做 diff 。例如: - - MYSRC= /devel/linux-2.6 - - tar xvfz linux-2.6.12.tar.gz - mv linux-2.6.12 linux-2.6.12-vanilla - diff -uprN -X linux-2.6.12-vanilla/Documentation/dontdiff \ - linux-2.6.12-vanilla $MYSRC > /tmp/patch - -"dontdiff" 是内核在编译的时候产生的文件的列表,列表中的文件在 diff(1) -产生的补丁里会被跳过。"dontdiff" 文件被包含在2.6.12和之后版本的内核源代 -码树中。对于更早的内核版本,你可以从 - 获取它。 -确定你的补丁里没有包含任何不属于这次补丁提交的额外文件。记得在用diff(1) -生成补丁之后,审阅一次补丁,以确保准确。 -如果你的改动很散乱,你应该研究一下如何将补丁分割成独立的部分,将改动分 -割成一系列合乎逻辑的步骤。这样更容易让其他内核开发者审核,如果你想你的 -补丁被接受,这是很重要的。下面这些脚本能够帮助你做这件事情: -Quilt: -http://savannah.nongnu.org/projects/quilt - -2)描述你的改动。 -描述你的改动包含的技术细节。 - -要多具体就写多具体。最糟糕的描述可能是像下面这些语句:“更新了某驱动程 -序”,“修正了某驱动程序的bug”,或者“这个补丁包含了某子系统的修改,请 -使用。” - -如果你的描述开始变长,这表示你也许需要拆分你的补丁了,请看第3小节, -继续。 - -3)拆分你的改动 - -将改动拆分,逻辑类似的放到同一个补丁文件里。 - -例如,如果你的改动里同时有bug修正和性能优化,那么把这些改动拆分到两个或 -者更多的补丁文件中。如果你的改动包含对API的修改,并且修改了驱动程序来适 -应这些新的API,那么把这些修改分成两个补丁。 - -另一方面,如果你将一个单独的改动做成多个补丁文件,那么将它们合并成一个 -单独的补丁文件。这样一个逻辑上单独的改动只被包含在一个补丁文件里。 - -如果有一个补丁依赖另外一个补丁来完成它的改动,那没问题。简单的在你的补 -丁描述里指出“这个补丁依赖某补丁”就好了。 - -如果你不能将补丁浓缩成更少的文件,那么每次大约发送出15个,然后等待审查 -和整合。 - -4)选择 e-mail 的收件人 - -看一遍 MAINTAINERS 文件和源代码,看看你所的改动所在的内核子系统有没有指 -定的维护者。如果有,给他们发e-mail。 - -如果没有找到维护者,或者维护者没有反馈,将你的补丁发送到内核开发者主邮 -件列表 linux-kernel@vger.kernel.org。大部分的内核开发者都跟踪这个邮件列 -表,可以评价你的改动。 - -每次不要发送超过15个补丁到 vger 邮件列表!!! - -Linus Torvalds 是决定改动能否进入 Linux 内核的最终裁决者。他的 e-mail -地址是 。他收到的 e-mail 很多,所以一般 -的说,最好别给他发 e-mail。 - -那些修正bug,“显而易见”的修改或者是类似的只需要很少讨论的补丁可以直接 -发送或者CC给Linus。那些需要讨论或者没有很清楚的好处的补丁,一般先发送到 -linux-kernel邮件列表。只有当补丁被讨论得差不多了,才提交给Linus。 - -5)选择CC( e-mail 抄送)列表 - -除非你有理由不这样做,否则CC linux-kernel@vger.kernel.org。 - -除了 Linus 之外,其他内核开发者也需要注意到你的改动,这样他们才能评论你 -的改动并提供代码审查和建议。linux-kernel 是 Linux 内核开发者主邮件列表 -。其它的邮件列表为特定的子系统提供服务,比如 USB,framebuffer 设备,虚 -拟文件系统,SCSI 子系统,等等。查看 MAINTAINERS 文件来获得和你的改动有 -关的邮件列表。 - -Majordomo lists of VGER.KERNEL.ORG at: - - -如果改动影响了用户空间和内核之间的接口,请给 MAN-PAGES 的维护者(列在 -MAINTAINERS 文件里的)发送一个手册页(man-pages)补丁,或者至少通知一下改 -变,让一些信息有途径进入手册页。 - -即使在第四步的时候,维护者没有作出回应,也要确认在修改他们的代码的时候 -,一直将维护者拷贝到CC列表中。 - -对于小的补丁,你也许会CC到 Adrian Bunk 管理的搜集琐碎补丁的邮件列表 -(Trivial Patch Monkey)trivial@kernel.org,那里专门收集琐碎的补丁。下面这样 -的补丁会被看作“琐碎的”补丁: - 文档的拼写修正。 - 修正会影响到 grep(1) 的拼写。 - 警告信息修正(频繁的打印无用的警告是不好的。) - 编译错误修正(代码逻辑的确是对的,只是编译有问题。) - 运行时修正(只要真的修正了错误。) - 移除使用了被废弃的函数/宏的代码(例如 check_region。) - 联系方式和文档修正。 - 用可移植的代码替换不可移植的代码(即使在体系结构相关的代码中,既然有 - 人拷贝,只要它是琐碎的) - 任何文件的作者/维护者对该文件的改动(例如 patch monkey 在重传模式下) - -EMAIL: trivial@kernel.org - -(译注,关于“琐碎补丁”的一些说明:因为原文的这一部分写得比较简单,所以不得不 -违例写一下译注。"trivial"这个英文单词的本意是“琐碎的,不重要的。”但是在这里 -有稍微有一些变化,例如对一些明显的NULL指针的修正,属于运行时修正,会被归类 -到琐碎补丁里。虽然NULL指针的修正很重要,但是这样的修正往往很小而且很容易得到 -检验,所以也被归入琐碎补丁。琐碎补丁更精确的归类应该是 -“simple, localized & easy to verify”,也就是说简单的,局部的和易于检验的。 -trivial@kernel.org邮件列表的目的是针对这样的补丁,为提交者提供一个中心,来 -降低提交的门槛。) - -6)没有 MIME 编码,没有链接,没有压缩,没有附件,只有纯文本。 - -Linus 和其他的内核开发者需要阅读和评论你提交的改动。对于内核开发者来说 -,可以“引用”你的改动很重要,使用一般的 e-mail 工具,他们就可以在你的 -代码的任何位置添加评论。 - -因为这个原因,所有的提交的补丁都是 e-mail 中“内嵌”的。 -警告:如果你使用剪切-粘贴你的补丁,小心你的编辑器的自动换行功能破坏你的 -补丁。 - -不要将补丁作为 MIME 编码的附件,不管是否压缩。很多流行的 e-mail 软件不 -是任何时候都将 MIME 编码的附件当作纯文本发送的,这会使得别人无法在你的 -代码中加评论。另外,MIME 编码的附件会让 Linus 多花一点时间来处理,这就 -降低了你的改动被接受的可能性。 - -警告:一些邮件软件,比如 Mozilla 会将你的信息以如下格式发送: ----- 邮件头 ---- -Content-Type: text/plain; charset=us-ascii; format=flowed ----- 邮件头 ---- -问题在于 “format=flowed” 会让接收端的某些邮件软件将邮件中的制表符替换 -成空格以及做一些类似的替换。这样,你发送的时候看起来没问题的补丁就被破 -坏了。 - -要修正这个问题,只需要将你的 mozilla 的 defaults/pref/mailnews.js 文件 -里的 -pref("mailnews.send_plaintext_flowed", false); // RFC 2646======= -修改成 -pref("mailnews.display.disable_format_flowed_support", true); -就可以了。 - -7) e-mail 的大小 - -给 Linus 发送补丁的时候,永远按照第6小节说的做。 - -大的改动对邮件列表不合适,对某些维护者也不合适。如果你的补丁,在不压缩 -的情况下,超过了40kB,那么你最好将补丁放在一个能通过 internet 访问的服 -务器上,然后用指向你的补丁的 URL 替代。 - -8) 指出你的内核版本 - -在标题和在补丁的描述中,指出补丁对应的内核的版本,是很重要的。 - -如果补丁不能干净的在最新版本的内核上打上,Linus 是不会接受它的。 - -9) 不要气馁,继续提交。 - -当你提交了改动以后,耐心地等待。如果 Linus 喜欢你的改动并且同意它,那么 -它将在下一个内核发布版本中出现。 - -然而,如果你的改动没有出现在下一个版本的内核中,可能有若干原因。减少那 -些原因,修正错误,重新提交更新后的改动,是你自己的工作。 - -Linus不给出任何评论就“丢弃”你的补丁是常见的事情。在系统中这样的事情很 -平常。如果他没有接受你的补丁,也许是由于以下原因: -* 你的补丁不能在最新版本的内核上干净的打上。 -* 你的补丁在 linux-kernel 邮件列表中没有得到充分的讨论。 -* 风格问题(参照第2小节) -* 邮件格式问题(重读本节) -* 你的改动有技术问题。 -* 他收到了成吨的 e-mail,而你的在混乱中丢失了。 -* 你让人为难。 - -有疑问的时候,在 linux-kernel 邮件列表上请求评论。 - -10) 在标题上加上 PATCH 的字样 - -Linus 和 linux-kernel 邮件列表的 e-mail 流量都很高,一个通常的约定是标 -题行以 [PATCH] 开头。这样可以让 Linus 和其他内核开发人员可以从 e-mail -的讨论中很轻易的将补丁分辨出来。 - -11)为你的工作签名 - -为了加强对谁做了何事的追踪,尤其是对那些透过好几层的维护者的补丁,我们 -建议在发送出去的补丁上加一个 “sign-off” 的过程。 - -"sign-off" 是在补丁的注释的最后的简单的一行文字,认证你编写了它或者其他 -人有权力将它作为开放源代码的补丁传递。规则很简单:如果你能认证如下信息 -: - 开发者来源证书 1.1 - 对于本项目的贡献,我认证如下信息: - (a)这些贡献是完全或者部分的由我创建,我有权利以文件中指出 - 的开放源代码许可证提交它;或者 - (b)这些贡献基于以前的工作,据我所知,这些以前的工作受恰当的开放 - 源代码许可证保护,而且,根据许可证,我有权提交修改后的贡献, - 无论是完全还是部分由我创造,这些贡献都使用同一个开放源代码许可证 - (除非我被允许用其它的许可证),正如文件中指出的;或者 - (c)这些贡献由认证(a),(b)或者(c)的人直接提供给我,而 - 且我没有修改它。 - (d)我理解并同意这个项目和贡献是公开的,贡献的记录(包括我 - 一起提交的个人记录,包括 sign-off )被永久维护并且可以和这个项目 - 或者开放源代码的许可证同步地再发行。 - 那么加入这样一行: - Signed-off-by: Random J Developer - -使用你的真名(抱歉,不能使用假名或者匿名。) - -有人在最后加上标签。现在这些东西会被忽略,但是你可以这样做,来标记公司 -内部的过程,或者只是指出关于 sign-off 的一些特殊细节。 - -12)标准补丁格式 - -标准的补丁,标题行是: - Subject: [PATCH 001/123] 子系统:一句话概述 - -标准补丁的信体存在如下部分: - - - 一个 "from" 行指出补丁作者。 - - - 一个空行 - - - 说明的主体,这些说明文字会被拷贝到描述该补丁的永久改动记录里。 - - - 一个由"---"构成的标记行 - - - 不合适放到改动记录里的额外的注解。 - - - 补丁本身(diff 输出) - -标题行的格式,使得对标题行按字母序排序非常的容易 - 很多 e-mail 客户端都 -可以支持 - 因为序列号是用零填充的,所以按数字排序和按字母排序是一样的。 - -e-mail 标题中的“子系统”标识哪个内核子系统将被打补丁。 - -e-mail 标题中的“一句话概述”扼要的描述 e-mail 中的补丁。“一句话概述” -不应该是一个文件名。对于一个补丁系列(“补丁系列”指一系列的多个相关补 -丁),不要对每个补丁都使用同样的“一句话概述”。 - -记住 e-mail 的“一句话概述”会成为该补丁的全局唯一标识。它会蔓延到 git -的改动记录里。然后“一句话概述”会被用在开发者的讨论里,用来指代这个补 -丁。用户将希望通过 google 来搜索"一句话概述"来找到那些讨论这个补丁的文 -章。 - -一些标题的例子: - - Subject: [patch 2/5] ext2: improve scalability of bitmap searching - Subject: [PATCHv2 001/207] x86: fix eflags tracking - -"from" 行是信体里的最上面一行,具有如下格式: - From: Original Author - -"from" 行指明在永久改动日志里,谁会被确认为作者。如果没有 "from" 行,那 -么邮件头里的 "From: " 行会被用来决定改动日志中的作者。 - -说明的主题将会被提交到永久的源代码改动日志里,因此对那些早已经不记得和 -这个补丁相关的讨论细节的有能力的读者来说,是有意义的。 - -"---" 标记行对于补丁处理工具要找到哪里是改动日志信息的结束,是不可缺少 -的。 - -对于 "---" 标记之后的额外注解,一个好的用途就是用来写 diffstat,用来显 -示修改了什么文件和每个文件都增加和删除了多少行。diffstat 对于比较大的补 -丁特别有用。其余那些只是和时刻或者开发者相关的注解,不合适放到永久的改 -动日志里的,也应该放这里。 -使用 diffstat的选项 "-p 1 -w 70" 这样文件名就会从内核源代码树的目录开始 -,不会占用太宽的空间(很容易适合80列的宽度,也许会有一些缩进。) - -在后面的参考资料中能看到适当的补丁格式的更多细节。 - -------------------------------- -第二节 提示,建议和诀窍 -------------------------------- - -本节包含很多和提交到内核的代码有关的通常的"规则"。事情永远有例外...但是 -你必须真的有好的理由这样做。你可以把本节叫做Linus的计算机科学入门课。 - -1) 读 Document/process/coding-style.rst - -Nuff 说过,如果你的代码和这个偏离太多,那么它有可能会被拒绝,没有更多的 -审查,没有更多的评价。 - -2) #ifdef 是丑陋的 -混杂了 ifdef 的代码难以阅读和维护。别这样做。作为替代,将你的 ifdef 放 -在头文件里,有条件地定义 "static inline" 函数,或者宏,在代码里用这些东 -西。让编译器把那些"空操作"优化掉。 - -一个简单的例子,不好的代码: - - dev = alloc_etherdev (sizeof(struct funky_private)); - if (!dev) - return -ENODEV; - #ifdef CONFIG_NET_FUNKINESS - init_funky_net(dev); - #endif - -清理后的例子: - -(头文件里) - #ifndef CONFIG_NET_FUNKINESS - static inline void init_funky_net (struct net_device *d) {} - #endif - -(代码文件里) - dev = alloc_etherdev (sizeof(struct funky_private)); - if (!dev) - return -ENODEV; - init_funky_net(dev); - -3) 'static inline' 比宏好 - -Static inline 函数相比宏来说,是好得多的选择。Static inline 函数提供了 -类型安全,没有长度限制,没有格式限制,在 gcc 下开销和宏一样小。 - -宏只在 static inline 函数不是最优的时候[在 fast paths 里有很少的独立的 -案例],或者不可能用 static inline 函数的时候[例如字符串分配]。 -应该用 'static inline' 而不是 'static __inline__', 'extern inline' 和 -'extern __inline__' 。 - -4) 不要过度设计 - -不要试图预计模糊的未来事情,这些事情也许有用也许没有用:"让事情尽可能的 -简单,而不是更简单"。 - ----------------- -第三节 参考文献 ----------------- - -Andrew Morton, "The perfect patch" (tpp). - - -Jeff Garzik, "Linux kernel patch submission format". - - -Greg Kroah-Hartman, "How to piss off a kernel subsystem maintainer". - - - - - -NO!!!! No more huge patch bombs to linux-kernel@vger.kernel.org people! - - -Kernel Documentation/process/coding-style.rst: - - -Linus Torvalds's mail on the canonical patch format: - --- diff --git a/Documentation/translations/zh_CN/process/submitting-patches.rst b/Documentation/translations/zh_CN/process/submitting-patches.rst new file mode 100644 index 000000000000..e9098da8f1a4 --- /dev/null +++ b/Documentation/translations/zh_CN/process/submitting-patches.rst @@ -0,0 +1,412 @@ +Chinese translated version of Documentation/process/submitting-patches.rst + +If you have any comment or update to the content, please contact the +original document maintainer directly. However, if you have a problem +communicating in English you can also ask the Chinese maintainer for +help. Contact the Chinese maintainer if this translation is outdated +or if there is a problem with the translation. + +Chinese maintainer: TripleX Chung +--------------------------------------------------------------------- +Documentation/process/submitting-patches.rst 的中文翻译 + +如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 +交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 +译存在问题,请联系中文版维护者。 + +中文版维护者: 钟宇 TripleX Chung +中文版翻译者: 钟宇 TripleX Chung +中文版校译者: 李阳 Li Yang + 王聪 Wang Cong + +以下为正文 +--------------------------------------------------------------------- + + 如何让你的改动进入内核 + 或者 + 获得亲爱的 Linus Torvalds 的关注和处理 +---------------------------------- + +对于想要将改动提交到 Linux 内核的个人或者公司来说,如果不熟悉“规矩”, +提交的流程会让人畏惧。本文档收集了一系列建议,这些建议可以大大的提高你 +的改动被接受的机会。 +阅读 Documentation/process/submit-checklist.rst 来获得在提交代码前需要检查的项目的列 +表。如果你在提交一个驱动程序,那么同时阅读一下 +Documentation/process/submitting-drivers.rst 。 + + +-------------------------- +第一节 - 创建并发送你的改动 +-------------------------- + +1) "diff -up" +----------- + +使用 "diff -up" 或者 "diff -uprN" 来创建补丁。 + +所有内核的改动,都是以补丁的形式呈现的,补丁由 diff(1) 生成。创建补丁的 +时候,要确认它是以 "unified diff" 格式创建的,这种格式由 diff(1) 的 '-u' +参数生成。而且,请使用 '-p' 参数,那样会显示每个改动所在的C函数,使得 +产生的补丁容易读得多。补丁应该基于内核源代码树的根目录,而不是里边的任 +何子目录。 +为一个单独的文件创建补丁,一般来说这样做就够了: + + SRCTREE= linux-2.6 + MYFILE= drivers/net/mydriver.c + + cd $SRCTREE + cp $MYFILE $MYFILE.orig + vi $MYFILE # make your change + cd .. + diff -up $SRCTREE/$MYFILE{.orig,} > /tmp/patch + +为多个文件创建补丁,你可以解开一个没有修改过的内核源代码树,然后和你自 +己的代码树之间做 diff 。例如: + + MYSRC= /devel/linux-2.6 + + tar xvfz linux-2.6.12.tar.gz + mv linux-2.6.12 linux-2.6.12-vanilla + diff -uprN -X linux-2.6.12-vanilla/Documentation/dontdiff \ + linux-2.6.12-vanilla $MYSRC > /tmp/patch + +"dontdiff" 是内核在编译的时候产生的文件的列表,列表中的文件在 diff(1) +产生的补丁里会被跳过。"dontdiff" 文件被包含在2.6.12和之后版本的内核源代 +码树中。对于更早的内核版本,你可以从 + 获取它。 +确定你的补丁里没有包含任何不属于这次补丁提交的额外文件。记得在用diff(1) +生成补丁之后,审阅一次补丁,以确保准确。 +如果你的改动很散乱,你应该研究一下如何将补丁分割成独立的部分,将改动分 +割成一系列合乎逻辑的步骤。这样更容易让其他内核开发者审核,如果你想你的 +补丁被接受,这是很重要的。下面这些脚本能够帮助你做这件事情: +Quilt: +http://savannah.nongnu.org/projects/quilt + +2)描述你的改动。 +描述你的改动包含的技术细节。 + +要多具体就写多具体。最糟糕的描述可能是像下面这些语句:“更新了某驱动程 +序”,“修正了某驱动程序的bug”,或者“这个补丁包含了某子系统的修改,请 +使用。” + +如果你的描述开始变长,这表示你也许需要拆分你的补丁了,请看第3小节, +继续。 + +3)拆分你的改动 + +将改动拆分,逻辑类似的放到同一个补丁文件里。 + +例如,如果你的改动里同时有bug修正和性能优化,那么把这些改动拆分到两个或 +者更多的补丁文件中。如果你的改动包含对API的修改,并且修改了驱动程序来适 +应这些新的API,那么把这些修改分成两个补丁。 + +另一方面,如果你将一个单独的改动做成多个补丁文件,那么将它们合并成一个 +单独的补丁文件。这样一个逻辑上单独的改动只被包含在一个补丁文件里。 + +如果有一个补丁依赖另外一个补丁来完成它的改动,那没问题。简单的在你的补 +丁描述里指出“这个补丁依赖某补丁”就好了。 + +如果你不能将补丁浓缩成更少的文件,那么每次大约发送出15个,然后等待审查 +和整合。 + +4)选择 e-mail 的收件人 + +看一遍 MAINTAINERS 文件和源代码,看看你所的改动所在的内核子系统有没有指 +定的维护者。如果有,给他们发e-mail。 + +如果没有找到维护者,或者维护者没有反馈,将你的补丁发送到内核开发者主邮 +件列表 linux-kernel@vger.kernel.org。大部分的内核开发者都跟踪这个邮件列 +表,可以评价你的改动。 + +每次不要发送超过15个补丁到 vger 邮件列表!!! + +Linus Torvalds 是决定改动能否进入 Linux 内核的最终裁决者。他的 e-mail +地址是 。他收到的 e-mail 很多,所以一般 +的说,最好别给他发 e-mail。 + +那些修正bug,“显而易见”的修改或者是类似的只需要很少讨论的补丁可以直接 +发送或者CC给Linus。那些需要讨论或者没有很清楚的好处的补丁,一般先发送到 +linux-kernel邮件列表。只有当补丁被讨论得差不多了,才提交给Linus。 + +5)选择CC( e-mail 抄送)列表 + +除非你有理由不这样做,否则CC linux-kernel@vger.kernel.org。 + +除了 Linus 之外,其他内核开发者也需要注意到你的改动,这样他们才能评论你 +的改动并提供代码审查和建议。linux-kernel 是 Linux 内核开发者主邮件列表 +。其它的邮件列表为特定的子系统提供服务,比如 USB,framebuffer 设备,虚 +拟文件系统,SCSI 子系统,等等。查看 MAINTAINERS 文件来获得和你的改动有 +关的邮件列表。 + +Majordomo lists of VGER.KERNEL.ORG at: + + +如果改动影响了用户空间和内核之间的接口,请给 MAN-PAGES 的维护者(列在 +MAINTAINERS 文件里的)发送一个手册页(man-pages)补丁,或者至少通知一下改 +变,让一些信息有途径进入手册页。 + +即使在第四步的时候,维护者没有作出回应,也要确认在修改他们的代码的时候 +,一直将维护者拷贝到CC列表中。 + +对于小的补丁,你也许会CC到 Adrian Bunk 管理的搜集琐碎补丁的邮件列表 +(Trivial Patch Monkey)trivial@kernel.org,那里专门收集琐碎的补丁。下面这样 +的补丁会被看作“琐碎的”补丁: + 文档的拼写修正。 + 修正会影响到 grep(1) 的拼写。 + 警告信息修正(频繁的打印无用的警告是不好的。) + 编译错误修正(代码逻辑的确是对的,只是编译有问题。) + 运行时修正(只要真的修正了错误。) + 移除使用了被废弃的函数/宏的代码(例如 check_region。) + 联系方式和文档修正。 + 用可移植的代码替换不可移植的代码(即使在体系结构相关的代码中,既然有 + 人拷贝,只要它是琐碎的) + 任何文件的作者/维护者对该文件的改动(例如 patch monkey 在重传模式下) + +EMAIL: trivial@kernel.org + +(译注,关于“琐碎补丁”的一些说明:因为原文的这一部分写得比较简单,所以不得不 +违例写一下译注。"trivial"这个英文单词的本意是“琐碎的,不重要的。”但是在这里 +有稍微有一些变化,例如对一些明显的NULL指针的修正,属于运行时修正,会被归类 +到琐碎补丁里。虽然NULL指针的修正很重要,但是这样的修正往往很小而且很容易得到 +检验,所以也被归入琐碎补丁。琐碎补丁更精确的归类应该是 +“simple, localized & easy to verify”,也就是说简单的,局部的和易于检验的。 +trivial@kernel.org邮件列表的目的是针对这样的补丁,为提交者提供一个中心,来 +降低提交的门槛。) + +6)没有 MIME 编码,没有链接,没有压缩,没有附件,只有纯文本。 + +Linus 和其他的内核开发者需要阅读和评论你提交的改动。对于内核开发者来说 +,可以“引用”你的改动很重要,使用一般的 e-mail 工具,他们就可以在你的 +代码的任何位置添加评论。 + +因为这个原因,所有的提交的补丁都是 e-mail 中“内嵌”的。 +警告:如果你使用剪切-粘贴你的补丁,小心你的编辑器的自动换行功能破坏你的 +补丁。 + +不要将补丁作为 MIME 编码的附件,不管是否压缩。很多流行的 e-mail 软件不 +是任何时候都将 MIME 编码的附件当作纯文本发送的,这会使得别人无法在你的 +代码中加评论。另外,MIME 编码的附件会让 Linus 多花一点时间来处理,这就 +降低了你的改动被接受的可能性。 + +警告:一些邮件软件,比如 Mozilla 会将你的信息以如下格式发送: +---- 邮件头 ---- +Content-Type: text/plain; charset=us-ascii; format=flowed +---- 邮件头 ---- +问题在于 “format=flowed” 会让接收端的某些邮件软件将邮件中的制表符替换 +成空格以及做一些类似的替换。这样,你发送的时候看起来没问题的补丁就被破 +坏了。 + +要修正这个问题,只需要将你的 mozilla 的 defaults/pref/mailnews.js 文件 +里的 +pref("mailnews.send_plaintext_flowed", false); // RFC 2646======= +修改成 +pref("mailnews.display.disable_format_flowed_support", true); +就可以了。 + +7) e-mail 的大小 + +给 Linus 发送补丁的时候,永远按照第6小节说的做。 + +大的改动对邮件列表不合适,对某些维护者也不合适。如果你的补丁,在不压缩 +的情况下,超过了40kB,那么你最好将补丁放在一个能通过 internet 访问的服 +务器上,然后用指向你的补丁的 URL 替代。 + +8) 指出你的内核版本 + +在标题和在补丁的描述中,指出补丁对应的内核的版本,是很重要的。 + +如果补丁不能干净的在最新版本的内核上打上,Linus 是不会接受它的。 + +9) 不要气馁,继续提交。 + +当你提交了改动以后,耐心地等待。如果 Linus 喜欢你的改动并且同意它,那么 +它将在下一个内核发布版本中出现。 + +然而,如果你的改动没有出现在下一个版本的内核中,可能有若干原因。减少那 +些原因,修正错误,重新提交更新后的改动,是你自己的工作。 + +Linus不给出任何评论就“丢弃”你的补丁是常见的事情。在系统中这样的事情很 +平常。如果他没有接受你的补丁,也许是由于以下原因: +* 你的补丁不能在最新版本的内核上干净的打上。 +* 你的补丁在 linux-kernel 邮件列表中没有得到充分的讨论。 +* 风格问题(参照第2小节) +* 邮件格式问题(重读本节) +* 你的改动有技术问题。 +* 他收到了成吨的 e-mail,而你的在混乱中丢失了。 +* 你让人为难。 + +有疑问的时候,在 linux-kernel 邮件列表上请求评论。 + +10) 在标题上加上 PATCH 的字样 + +Linus 和 linux-kernel 邮件列表的 e-mail 流量都很高,一个通常的约定是标 +题行以 [PATCH] 开头。这样可以让 Linus 和其他内核开发人员可以从 e-mail +的讨论中很轻易的将补丁分辨出来。 + +11)为你的工作签名 + +为了加强对谁做了何事的追踪,尤其是对那些透过好几层的维护者的补丁,我们 +建议在发送出去的补丁上加一个 “sign-off” 的过程。 + +"sign-off" 是在补丁的注释的最后的简单的一行文字,认证你编写了它或者其他 +人有权力将它作为开放源代码的补丁传递。规则很简单:如果你能认证如下信息 +: + 开发者来源证书 1.1 + 对于本项目的贡献,我认证如下信息: + (a)这些贡献是完全或者部分的由我创建,我有权利以文件中指出 + 的开放源代码许可证提交它;或者 + (b)这些贡献基于以前的工作,据我所知,这些以前的工作受恰当的开放 + 源代码许可证保护,而且,根据许可证,我有权提交修改后的贡献, + 无论是完全还是部分由我创造,这些贡献都使用同一个开放源代码许可证 + (除非我被允许用其它的许可证),正如文件中指出的;或者 + (c)这些贡献由认证(a),(b)或者(c)的人直接提供给我,而 + 且我没有修改它。 + (d)我理解并同意这个项目和贡献是公开的,贡献的记录(包括我 + 一起提交的个人记录,包括 sign-off )被永久维护并且可以和这个项目 + 或者开放源代码的许可证同步地再发行。 + 那么加入这样一行: + Signed-off-by: Random J Developer + +使用你的真名(抱歉,不能使用假名或者匿名。) + +有人在最后加上标签。现在这些东西会被忽略,但是你可以这样做,来标记公司 +内部的过程,或者只是指出关于 sign-off 的一些特殊细节。 + +12)标准补丁格式 + +标准的补丁,标题行是: + Subject: [PATCH 001/123] 子系统:一句话概述 + +标准补丁的信体存在如下部分: + + - 一个 "from" 行指出补丁作者。 + + - 一个空行 + + - 说明的主体,这些说明文字会被拷贝到描述该补丁的永久改动记录里。 + + - 一个由"---"构成的标记行 + + - 不合适放到改动记录里的额外的注解。 + + - 补丁本身(diff 输出) + +标题行的格式,使得对标题行按字母序排序非常的容易 - 很多 e-mail 客户端都 +可以支持 - 因为序列号是用零填充的,所以按数字排序和按字母排序是一样的。 + +e-mail 标题中的“子系统”标识哪个内核子系统将被打补丁。 + +e-mail 标题中的“一句话概述”扼要的描述 e-mail 中的补丁。“一句话概述” +不应该是一个文件名。对于一个补丁系列(“补丁系列”指一系列的多个相关补 +丁),不要对每个补丁都使用同样的“一句话概述”。 + +记住 e-mail 的“一句话概述”会成为该补丁的全局唯一标识。它会蔓延到 git +的改动记录里。然后“一句话概述”会被用在开发者的讨论里,用来指代这个补 +丁。用户将希望通过 google 来搜索"一句话概述"来找到那些讨论这个补丁的文 +章。 + +一些标题的例子: + + Subject: [patch 2/5] ext2: improve scalability of bitmap searching + Subject: [PATCHv2 001/207] x86: fix eflags tracking + +"from" 行是信体里的最上面一行,具有如下格式: + From: Original Author + +"from" 行指明在永久改动日志里,谁会被确认为作者。如果没有 "from" 行,那 +么邮件头里的 "From: " 行会被用来决定改动日志中的作者。 + +说明的主题将会被提交到永久的源代码改动日志里,因此对那些早已经不记得和 +这个补丁相关的讨论细节的有能力的读者来说,是有意义的。 + +"---" 标记行对于补丁处理工具要找到哪里是改动日志信息的结束,是不可缺少 +的。 + +对于 "---" 标记之后的额外注解,一个好的用途就是用来写 diffstat,用来显 +示修改了什么文件和每个文件都增加和删除了多少行。diffstat 对于比较大的补 +丁特别有用。其余那些只是和时刻或者开发者相关的注解,不合适放到永久的改 +动日志里的,也应该放这里。 +使用 diffstat的选项 "-p 1 -w 70" 这样文件名就会从内核源代码树的目录开始 +,不会占用太宽的空间(很容易适合80列的宽度,也许会有一些缩进。) + +在后面的参考资料中能看到适当的补丁格式的更多细节。 + +------------------------------- +第二节 提示,建议和诀窍 +------------------------------- + +本节包含很多和提交到内核的代码有关的通常的"规则"。事情永远有例外...但是 +你必须真的有好的理由这样做。你可以把本节叫做Linus的计算机科学入门课。 + +1) 读 Document/process/coding-style.rst + +Nuff 说过,如果你的代码和这个偏离太多,那么它有可能会被拒绝,没有更多的 +审查,没有更多的评价。 + +2) #ifdef 是丑陋的 +混杂了 ifdef 的代码难以阅读和维护。别这样做。作为替代,将你的 ifdef 放 +在头文件里,有条件地定义 "static inline" 函数,或者宏,在代码里用这些东 +西。让编译器把那些"空操作"优化掉。 + +一个简单的例子,不好的代码: + + dev = alloc_etherdev (sizeof(struct funky_private)); + if (!dev) + return -ENODEV; + #ifdef CONFIG_NET_FUNKINESS + init_funky_net(dev); + #endif + +清理后的例子: + +(头文件里) + #ifndef CONFIG_NET_FUNKINESS + static inline void init_funky_net (struct net_device *d) {} + #endif + +(代码文件里) + dev = alloc_etherdev (sizeof(struct funky_private)); + if (!dev) + return -ENODEV; + init_funky_net(dev); + +3) 'static inline' 比宏好 + +Static inline 函数相比宏来说,是好得多的选择。Static inline 函数提供了 +类型安全,没有长度限制,没有格式限制,在 gcc 下开销和宏一样小。 + +宏只在 static inline 函数不是最优的时候[在 fast paths 里有很少的独立的 +案例],或者不可能用 static inline 函数的时候[例如字符串分配]。 +应该用 'static inline' 而不是 'static __inline__', 'extern inline' 和 +'extern __inline__' 。 + +4) 不要过度设计 + +不要试图预计模糊的未来事情,这些事情也许有用也许没有用:"让事情尽可能的 +简单,而不是更简单"。 + +---------------- +第三节 参考文献 +---------------- + +Andrew Morton, "The perfect patch" (tpp). + + +Jeff Garzik, "Linux kernel patch submission format". + + +Greg Kroah-Hartman, "How to piss off a kernel subsystem maintainer". + + + + + +NO!!!! No more huge patch bombs to linux-kernel@vger.kernel.org people! + + +Kernel Documentation/process/coding-style.rst: + + +Linus Torvalds's mail on the canonical patch format: + +-- -- cgit v1.2.3 From 6bd77522580df45de15342c6424f442877b031be Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:38 +0800 Subject: docs/zh_CN: format the submitting-patches doc to rst And remove Enghlish explainations in the docs, which it isn't necessary in Chinese doc. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: TripleX Chung Cc: Li Zefan Cc: Shawn Guo Cc: Fengguang Wu Cc: Coly Li Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- .../zh_CN/process/submitting-patches.rst | 36 ++++++++-------------- 1 file changed, 13 insertions(+), 23 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/submitting-patches.rst b/Documentation/translations/zh_CN/process/submitting-patches.rst index e9098da8f1a4..2a2989733c8d 100644 --- a/Documentation/translations/zh_CN/process/submitting-patches.rst +++ b/Documentation/translations/zh_CN/process/submitting-patches.rst @@ -1,31 +1,21 @@ -Chinese translated version of Documentation/process/submitting-patches.rst +.. _cn_process_submittingpatches: -If you have any comment or update to the content, please contact the -original document maintainer directly. However, if you have a problem -communicating in English you can also ask the Chinese maintainer for -help. Contact the Chinese maintainer if this translation is outdated -or if there is a problem with the translation. +.. include:: ../disclaimer-zh_CN.rst -Chinese maintainer: TripleX Chung ---------------------------------------------------------------------- -Documentation/process/submitting-patches.rst 的中文翻译 +:Original: :ref:`Documentation/process/submitting-patches.rst ` 如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者。 +译存在问题,请联系中文版维护者:: -中文版维护者: 钟宇 TripleX Chung -中文版翻译者: 钟宇 TripleX Chung -中文版校译者: 李阳 Li Yang - 王聪 Wang Cong + 中文版维护者: 钟宇 TripleX Chung + 中文版翻译者: 钟宇 TripleX Chung + 中文版校译者: 李阳 Li Yang + 王聪 Wang Cong -以下为正文 ---------------------------------------------------------------------- - 如何让你的改动进入内核 - 或者 - 获得亲爱的 Linus Torvalds 的关注和处理 ----------------------------------- +如何让你的改动进入内核 +====================== 对于想要将改动提交到 Linux 内核的个人或者公司来说,如果不熟悉“规矩”, 提交的流程会让人畏惧。本文档收集了一系列建议,这些建议可以大大的提高你 @@ -35,12 +25,12 @@ Documentation/process/submitting-patches.rst 的中文翻译 Documentation/process/submitting-drivers.rst 。 --------------------------- +--------------------------- 第一节 - 创建并发送你的改动 --------------------------- +--------------------------- 1) "diff -up" ------------ +------------- 使用 "diff -up" 或者 "diff -uprN" 来创建补丁。 -- cgit v1.2.3 From d7fb7ad29dbaf96da6adbefcf3a63984a9b2a3a4 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:39 +0800 Subject: docs/zh_CN: rename stable_kernel_rules doc This patch renamed stable_kernel_rules.txt to stable-kernel-rules.rst Make it available in htmldocs making. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: TripleX Chung Cc: Li Zefan Cc: Shawn Guo Cc: Fengguang Wu Cc: Coly Li Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- .../zh_CN/process/stable-kernel-rules.rst | 66 ++++++++++++++++++++++ .../zh_CN/process/stable_kernel_rules.txt | 66 ---------------------- 2 files changed, 66 insertions(+), 66 deletions(-) create mode 100644 Documentation/translations/zh_CN/process/stable-kernel-rules.rst delete mode 100644 Documentation/translations/zh_CN/process/stable_kernel_rules.txt (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/stable-kernel-rules.rst b/Documentation/translations/zh_CN/process/stable-kernel-rules.rst new file mode 100644 index 000000000000..db4ba5a0c39a --- /dev/null +++ b/Documentation/translations/zh_CN/process/stable-kernel-rules.rst @@ -0,0 +1,66 @@ +Chinese translated version of Documentation/process/stable-kernel-rules.rst + +If you have any comment or update to the content, please contact the +original document maintainer directly. However, if you have a problem +communicating in English you can also ask the Chinese maintainer for +help. Contact the Chinese maintainer if this translation is outdated +or if there is a problem with the translation. + +Chinese maintainer: TripleX Chung +--------------------------------------------------------------------- +Documentation/process/stable-kernel-rules.rst 的中文翻译 + +如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 +交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 +译存在问题,请联系中文版维护者。 + + +中文版维护者: 钟宇 TripleX Chung +中文版翻译者: 钟宇 TripleX Chung +中文版校译者: 李阳 Li Yang + Kangkai Yin + +以下为正文 +--------------------------------------------------------------------- + +关于Linux 2.6稳定版发布,所有你想知道的事情。 + +关于哪些类型的补丁可以被接收进入稳定版代码树,哪些不可以的规则: + + - 必须是显而易见的正确,并且经过测试的。 + - 连同上下文,不能大于100行。 + - 必须只修正一件事情。 + - 必须修正了一个给大家带来麻烦的真正的bug(不是“这也许是一个问题...” + 那样的东西)。 + - 必须修正带来如下后果的问题:编译错误(对被标记为CONFIG_BROKEN的例外), + 内核崩溃,挂起,数据损坏,真正的安全问题,或者一些类似“哦,这不 + 好”的问题。简短的说,就是一些致命的问题。 + - 没有“理论上的竞争条件”,除非能给出竞争条件如何被利用的解释。 + - 不能存在任何的“琐碎的”修正(拼写修正,去掉多余空格之类的)。 + - 必须被相关子系统的维护者接受。 + - 必须遵循Documentation/process/submitting-patches.rst里的规则。 + +向稳定版代码树提交补丁的过程: + + - 在确认了补丁符合以上的规则后,将补丁发送到stable@vger.kernel.org。 + - 如果补丁被接受到队列里,发送者会收到一个ACK回复,如果没有被接受,收 + 到的是NAK回复。回复需要几天的时间,这取决于开发者的时间安排。 + - 被接受的补丁会被加到稳定版本队列里,等待其他开发者的审查。 + - 安全方面的补丁不要发到这个列表,应该发送到security@kernel.org。 + +审查周期: + + - 当稳定版的维护者决定开始一个审查周期,补丁将被发送到审查委员会,以 + 及被补丁影响的领域的维护者(除非提交者就是该领域的维护者)并且抄送 + 到linux-kernel邮件列表。 + - 审查委员会有48小时的时间,用来决定给该补丁回复ACK还是NAK。 + - 如果委员会中有成员拒绝这个补丁,或者linux-kernel列表上有人反对这个 + 补丁,并提出维护者和审查委员会之前没有意识到的问题,补丁会从队列中 + 丢弃。 + - 在审查周期结束的时候,那些得到ACK回应的补丁将会被加入到最新的稳定版 + 发布中,一个新的稳定版发布就此产生。 + - 安全性补丁将从内核安全小组那里直接接收到稳定版代码树中,而不是通过 + 通常的审查周期。请联系内核安全小组以获得关于这个过程的更多细节。 + +审查委员会: + - 由一些自愿承担这项任务的内核开发者,和几个非志愿的组成。 diff --git a/Documentation/translations/zh_CN/process/stable_kernel_rules.txt b/Documentation/translations/zh_CN/process/stable_kernel_rules.txt deleted file mode 100644 index db4ba5a0c39a..000000000000 --- a/Documentation/translations/zh_CN/process/stable_kernel_rules.txt +++ /dev/null @@ -1,66 +0,0 @@ -Chinese translated version of Documentation/process/stable-kernel-rules.rst - -If you have any comment or update to the content, please contact the -original document maintainer directly. However, if you have a problem -communicating in English you can also ask the Chinese maintainer for -help. Contact the Chinese maintainer if this translation is outdated -or if there is a problem with the translation. - -Chinese maintainer: TripleX Chung ---------------------------------------------------------------------- -Documentation/process/stable-kernel-rules.rst 的中文翻译 - -如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 -交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者。 - - -中文版维护者: 钟宇 TripleX Chung -中文版翻译者: 钟宇 TripleX Chung -中文版校译者: 李阳 Li Yang - Kangkai Yin - -以下为正文 ---------------------------------------------------------------------- - -关于Linux 2.6稳定版发布,所有你想知道的事情。 - -关于哪些类型的补丁可以被接收进入稳定版代码树,哪些不可以的规则: - - - 必须是显而易见的正确,并且经过测试的。 - - 连同上下文,不能大于100行。 - - 必须只修正一件事情。 - - 必须修正了一个给大家带来麻烦的真正的bug(不是“这也许是一个问题...” - 那样的东西)。 - - 必须修正带来如下后果的问题:编译错误(对被标记为CONFIG_BROKEN的例外), - 内核崩溃,挂起,数据损坏,真正的安全问题,或者一些类似“哦,这不 - 好”的问题。简短的说,就是一些致命的问题。 - - 没有“理论上的竞争条件”,除非能给出竞争条件如何被利用的解释。 - - 不能存在任何的“琐碎的”修正(拼写修正,去掉多余空格之类的)。 - - 必须被相关子系统的维护者接受。 - - 必须遵循Documentation/process/submitting-patches.rst里的规则。 - -向稳定版代码树提交补丁的过程: - - - 在确认了补丁符合以上的规则后,将补丁发送到stable@vger.kernel.org。 - - 如果补丁被接受到队列里,发送者会收到一个ACK回复,如果没有被接受,收 - 到的是NAK回复。回复需要几天的时间,这取决于开发者的时间安排。 - - 被接受的补丁会被加到稳定版本队列里,等待其他开发者的审查。 - - 安全方面的补丁不要发到这个列表,应该发送到security@kernel.org。 - -审查周期: - - - 当稳定版的维护者决定开始一个审查周期,补丁将被发送到审查委员会,以 - 及被补丁影响的领域的维护者(除非提交者就是该领域的维护者)并且抄送 - 到linux-kernel邮件列表。 - - 审查委员会有48小时的时间,用来决定给该补丁回复ACK还是NAK。 - - 如果委员会中有成员拒绝这个补丁,或者linux-kernel列表上有人反对这个 - 补丁,并提出维护者和审查委员会之前没有意识到的问题,补丁会从队列中 - 丢弃。 - - 在审查周期结束的时候,那些得到ACK回应的补丁将会被加入到最新的稳定版 - 发布中,一个新的稳定版发布就此产生。 - - 安全性补丁将从内核安全小组那里直接接收到稳定版代码树中,而不是通过 - 通常的审查周期。请联系内核安全小组以获得关于这个过程的更多细节。 - -审查委员会: - - 由一些自愿承担这项任务的内核开发者,和几个非志愿的组成。 -- cgit v1.2.3 From d6bf62e30d4d60e41093e8067e2107ffeb7145dd Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:40 +0800 Subject: docs/zh_CN: rst format change for stable-kernel-rules to Make it readble with rst format. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: TripleX Chung Cc: Li Zefan Cc: Shawn Guo Cc: Fengguang Wu Cc: Coly Li Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- .../zh_CN/process/stable-kernel-rules.rst | 32 ++++++++++------------ 1 file changed, 15 insertions(+), 17 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/stable-kernel-rules.rst b/Documentation/translations/zh_CN/process/stable-kernel-rules.rst index db4ba5a0c39a..425d06f99ac2 100644 --- a/Documentation/translations/zh_CN/process/stable-kernel-rules.rst +++ b/Documentation/translations/zh_CN/process/stable-kernel-rules.rst @@ -1,31 +1,26 @@ -Chinese translated version of Documentation/process/stable-kernel-rules.rst +.. _cn_stable_kernel_rules: -If you have any comment or update to the content, please contact the -original document maintainer directly. However, if you have a problem -communicating in English you can also ask the Chinese maintainer for -help. Contact the Chinese maintainer if this translation is outdated -or if there is a problem with the translation. +.. include:: ../disclaimer-zh_CN.rst -Chinese maintainer: TripleX Chung ---------------------------------------------------------------------- -Documentation/process/stable-kernel-rules.rst 的中文翻译 +:Original: :ref:`Documentation/process/stable-kernel-rules.rst ` 如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者。 +译存在问题,请联系中文版维护者:: + 中文版维护者: 钟宇 TripleX Chung + 中文版翻译者: 钟宇 TripleX Chung + 中文版校译者: + - 李阳 Li Yang + - Kangkai Yin -中文版维护者: 钟宇 TripleX Chung -中文版翻译者: 钟宇 TripleX Chung -中文版校译者: 李阳 Li Yang - Kangkai Yin - -以下为正文 ---------------------------------------------------------------------- +所有你想知道的事情 - 关于linux稳定版发布 +======================================== 关于Linux 2.6稳定版发布,所有你想知道的事情。 关于哪些类型的补丁可以被接收进入稳定版代码树,哪些不可以的规则: +---------------------------------------------------------------- - 必须是显而易见的正确,并且经过测试的。 - 连同上下文,不能大于100行。 @@ -41,6 +36,7 @@ Documentation/process/stable-kernel-rules.rst 的中文翻译 - 必须遵循Documentation/process/submitting-patches.rst里的规则。 向稳定版代码树提交补丁的过程: +------------------------------ - 在确认了补丁符合以上的规则后,将补丁发送到stable@vger.kernel.org。 - 如果补丁被接受到队列里,发送者会收到一个ACK回复,如果没有被接受,收 @@ -49,6 +45,7 @@ Documentation/process/stable-kernel-rules.rst 的中文翻译 - 安全方面的补丁不要发到这个列表,应该发送到security@kernel.org。 审查周期: +---------- - 当稳定版的维护者决定开始一个审查周期,补丁将被发送到审查委员会,以 及被补丁影响的领域的维护者(除非提交者就是该领域的维护者)并且抄送 @@ -63,4 +60,5 @@ Documentation/process/stable-kernel-rules.rst 的中文翻译 通常的审查周期。请联系内核安全小组以获得关于这个过程的更多细节。 审查委员会: +------------ - 由一些自愿承担这项任务的内核开发者,和几个非志愿的组成。 -- cgit v1.2.3 From 9d47f5148c6580020c32d415f68b29575d193119 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:41 +0800 Subject: docs/zh_CN: rename email-clients.txt as email-clients.rst Make it available for html etc docs. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Li Zefan Cc: Shawn Guo Cc: Fengguang Wu Cc: Coly Li Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- .../translations/zh_CN/process/email-clients.rst | 210 +++++++++++++++++++++ .../translations/zh_CN/process/email-clients.txt | 210 --------------------- 2 files changed, 210 insertions(+), 210 deletions(-) create mode 100644 Documentation/translations/zh_CN/process/email-clients.rst delete mode 100644 Documentation/translations/zh_CN/process/email-clients.txt (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/email-clients.rst b/Documentation/translations/zh_CN/process/email-clients.rst new file mode 100644 index 000000000000..ec31d97e8d0e --- /dev/null +++ b/Documentation/translations/zh_CN/process/email-clients.rst @@ -0,0 +1,210 @@ +Chinese translated version of Documentation/process/email-clients.rst + +If you have any comment or update to the content, please contact the +original document maintainer directly. However, if you have a problem +communicating in English you can also ask the Chinese maintainer for +help. Contact the Chinese maintainer if this translation is outdated +or if there is a problem with the translation. + +Chinese maintainer: Harry Wei +--------------------------------------------------------------------- +Documentation/process/email-clients.rst 的中文翻译 + +如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 +交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 +译存在问题,请联系中文版维护者。 + +中文版维护者: 贾威威 Harry Wei +中文版翻译者: 贾威威 Harry Wei +中文版校译者: Yinglin Luan + Xiaochen Wang + yaxinsn + +以下为正文 +--------------------------------------------------------------------- + +Linux邮件客户端配置信息 +====================================================================== + +普通配置 +---------------------------------------------------------------------- +Linux内核补丁是通过邮件被提交的,最好把补丁作为邮件体的内嵌文本。有些维护者 +接收附件,但是附件的内容格式应该是"text/plain"。然而,附件一般是不赞成的, +因为这会使补丁的引用部分在评论过程中变的很困难。 + +用来发送Linux内核补丁的邮件客户端在发送补丁时应该处于文本的原始状态。例如, +他们不能改变或者删除制表符或者空格,甚至是在每一行的开头或者结尾。 + +不要通过"format=flowed"模式发送补丁。这样会引起不可预期以及有害的断行。 + +不要让你的邮件客户端进行自动换行。这样也会破坏你的补丁。 + +邮件客户端不能改变文本的字符集编码方式。要发送的补丁只能是ASCII或者UTF-8编码方式, +如果你使用UTF-8编码方式发送邮件,那么你将会避免一些可能发生的字符集问题。 + +邮件客户端应该形成并且保持 References: 或者 In-Reply-To: 标题,那么 +邮件话题就不会中断。 + +复制粘帖(或者剪贴粘帖)通常不能用于补丁,因为制表符会转换为空格。使用xclipboard, xclip +或者xcutsel也许可以,但是最好测试一下或者避免使用复制粘帖。 + +不要在使用PGP/GPG署名的邮件中包含补丁。这样会使得很多脚本不能读取和适用于你的补丁。 +(这个问题应该是可以修复的) + +在给内核邮件列表发送补丁之前,给自己发送一个补丁是个不错的主意,保存接收到的 +邮件,将补丁用'patch'命令打上,如果成功了,再给内核邮件列表发送。 + + +一些邮件客户端提示 +---------------------------------------------------------------------- +这里给出一些详细的MUA配置提示,可以用于给Linux内核发送补丁。这些并不意味是 +所有的软件包配置总结。 + +说明: +TUI = 以文本为基础的用户接口 +GUI = 图形界面用户接口 + +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +Alpine (TUI) + +配置选项: +在"Sending Preferences"部分: + +- "Do Not Send Flowed Text"必须开启 +- "Strip Whitespace Before Sending"必须关闭 + +当写邮件时,光标应该放在补丁会出现的地方,然后按下CTRL-R组合键,使指定的 +补丁文件嵌入到邮件中。 + +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +Evolution (GUI) + +一些开发者成功的使用它发送补丁 + +当选择邮件选项:Preformat + 从Format->Heading->Preformatted (Ctrl-7)或者工具栏 + +然后使用: + Insert->Text File... (Alt-n x)插入补丁文件。 + +你还可以"diff -Nru old.c new.c | xclip",选择Preformat,然后使用中间键进行粘帖。 + +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +Kmail (GUI) + +一些开发者成功的使用它发送补丁。 + +默认设置不为HTML格式是合适的;不要启用它。 + +当书写一封邮件的时候,在选项下面不要选择自动换行。唯一的缺点就是你在邮件中输入的任何文本 +都不会被自动换行,因此你必须在发送补丁之前手动换行。最简单的方法就是启用自动换行来书写邮件, +然后把它保存为草稿。一旦你在草稿中再次打开它,它已经全部自动换行了,那么你的邮件虽然没有 +选择自动换行,但是还不会失去已有的自动换行。 + +在邮件的底部,插入补丁之前,放上常用的补丁定界符:三个连字号(---)。 + +然后在"Message"菜单条目,选择插入文件,接着选取你的补丁文件。还有一个额外的选项,你可以 +通过它配置你的邮件建立工具栏菜单,还可以带上"insert file"图标。 + +你可以安全地通过GPG标记附件,但是内嵌补丁最好不要使用GPG标记它们。作为内嵌文本的签发补丁, +当从GPG中提取7位编码时会使他们变的更加复杂。 + +如果你非要以附件的形式发送补丁,那么就右键点击附件,然后选中属性,突出"Suggest automatic +display",这样内嵌附件更容易让读者看到。 + +当你要保存将要发送的内嵌文本补丁,你可以从消息列表窗格选择包含补丁的邮件,然后右击选择 +"save as"。你可以使用一个没有更改的包含补丁的邮件,如果它是以正确的形式组成。当你正真在它 +自己的窗口之下察看,那时没有选项可以保存邮件--已经有一个这样的bug被汇报到了kmail的bugzilla +并且希望这将会被处理。邮件是以只针对某个用户可读写的权限被保存的,所以如果你想把邮件复制到其他地方, +你不得不把他们的权限改为组或者整体可读。 + +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +Lotus Notes (GUI) + +不要使用它。 + +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +Mutt (TUI) + +很多Linux开发人员使用mutt客户端,所以证明它肯定工作的非常漂亮。 + +Mutt不自带编辑器,所以不管你使用什么编辑器都不应该带有自动断行。大多数编辑器都带有 +一个"insert file"选项,它可以通过不改变文件内容的方式插入文件。 + +'vim'作为mutt的编辑器: + set editor="vi" + + 如果使用xclip,敲入以下命令 + :set paste + 按中键之前或者shift-insert或者使用 + :r filename + +如果想要把补丁作为内嵌文本。 +(a)ttach工作的很好,不带有"set paste"。 + +配置选项: +它应该以默认设置的形式工作。 +然而,把"send_charset"设置为"us-ascii::utf-8"也是一个不错的主意。 + +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +Pine (TUI) + +Pine过去有一些空格删减问题,但是这些现在应该都被修复了。 + +如果可以,请使用alpine(pine的继承者) + +配置选项: +- 最近的版本需要消除流程文本 +- "no-strip-whitespace-before-send"选项也是需要的。 + + +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +Sylpheed (GUI) + +- 内嵌文本可以很好的工作(或者使用附件)。 +- 允许使用外部的编辑器。 +- 对于目录较多时非常慢。 +- 如果通过non-SSL连接,无法使用TLS SMTP授权。 +- 在组成窗口中有一个很有用的ruler bar。 +- 给地址本中添加地址就不会正确的了解显示名。 + +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +Thunderbird (GUI) + +默认情况下,thunderbird很容易损坏文本,但是还有一些方法可以强制它变得更好。 + +- 在用户帐号设置里,组成和寻址,不要选择"Compose messages in HTML format"。 + +- 编辑你的Thunderbird配置设置来使它不要拆行使用:user_pref("mailnews.wraplength", 0); + +- 编辑你的Thunderbird配置设置,使它不要使用"format=flowed"格式:user_pref("mailnews. + send_plaintext_flowed", false); + +- 你需要使Thunderbird变为预先格式方式: + 如果默认情况下你书写的是HTML格式,那不是很难。仅仅从标题栏的下拉框中选择"Preformat"格式。 + 如果默认情况下你书写的是文本格式,你不得把它改为HTML格式(仅仅作为一次性的)来书写新的消息, + 然后强制使它回到文本格式,否则它就会拆行。要实现它,在写信的图标上使用shift键来使它变为HTML + 格式,然后标题栏的下拉框中选择"Preformat"格式。 + +- 允许使用外部的编辑器: + 针对Thunderbird打补丁最简单的方法就是使用一个"external editor"扩展,然后使用你最喜欢的 + $EDITOR来读取或者合并补丁到文本中。要实现它,可以下载并且安装这个扩展,然后添加一个使用它的 + 按键View->Toolbars->Customize...最后当你书写信息的时候仅仅点击它就可以了。 + +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +TkRat (GUI) + +可以使用它。使用"Insert file..."或者外部的编辑器。 + +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +Gmail (Web GUI) + +不要使用它发送补丁。 + +Gmail网页客户端自动地把制表符转换为空格。 + +虽然制表符转换为空格问题可以被外部编辑器解决,同时它还会使用回车换行把每行拆分为78个字符。 + +另一个问题是Gmail还会把任何不是ASCII的字符的信息改为base64编码。它把东西变的像欧洲人的名字。 + + ### diff --git a/Documentation/translations/zh_CN/process/email-clients.txt b/Documentation/translations/zh_CN/process/email-clients.txt deleted file mode 100644 index ec31d97e8d0e..000000000000 --- a/Documentation/translations/zh_CN/process/email-clients.txt +++ /dev/null @@ -1,210 +0,0 @@ -Chinese translated version of Documentation/process/email-clients.rst - -If you have any comment or update to the content, please contact the -original document maintainer directly. However, if you have a problem -communicating in English you can also ask the Chinese maintainer for -help. Contact the Chinese maintainer if this translation is outdated -or if there is a problem with the translation. - -Chinese maintainer: Harry Wei ---------------------------------------------------------------------- -Documentation/process/email-clients.rst 的中文翻译 - -如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 -交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者。 - -中文版维护者: 贾威威 Harry Wei -中文版翻译者: 贾威威 Harry Wei -中文版校译者: Yinglin Luan - Xiaochen Wang - yaxinsn - -以下为正文 ---------------------------------------------------------------------- - -Linux邮件客户端配置信息 -====================================================================== - -普通配置 ----------------------------------------------------------------------- -Linux内核补丁是通过邮件被提交的,最好把补丁作为邮件体的内嵌文本。有些维护者 -接收附件,但是附件的内容格式应该是"text/plain"。然而,附件一般是不赞成的, -因为这会使补丁的引用部分在评论过程中变的很困难。 - -用来发送Linux内核补丁的邮件客户端在发送补丁时应该处于文本的原始状态。例如, -他们不能改变或者删除制表符或者空格,甚至是在每一行的开头或者结尾。 - -不要通过"format=flowed"模式发送补丁。这样会引起不可预期以及有害的断行。 - -不要让你的邮件客户端进行自动换行。这样也会破坏你的补丁。 - -邮件客户端不能改变文本的字符集编码方式。要发送的补丁只能是ASCII或者UTF-8编码方式, -如果你使用UTF-8编码方式发送邮件,那么你将会避免一些可能发生的字符集问题。 - -邮件客户端应该形成并且保持 References: 或者 In-Reply-To: 标题,那么 -邮件话题就不会中断。 - -复制粘帖(或者剪贴粘帖)通常不能用于补丁,因为制表符会转换为空格。使用xclipboard, xclip -或者xcutsel也许可以,但是最好测试一下或者避免使用复制粘帖。 - -不要在使用PGP/GPG署名的邮件中包含补丁。这样会使得很多脚本不能读取和适用于你的补丁。 -(这个问题应该是可以修复的) - -在给内核邮件列表发送补丁之前,给自己发送一个补丁是个不错的主意,保存接收到的 -邮件,将补丁用'patch'命令打上,如果成功了,再给内核邮件列表发送。 - - -一些邮件客户端提示 ----------------------------------------------------------------------- -这里给出一些详细的MUA配置提示,可以用于给Linux内核发送补丁。这些并不意味是 -所有的软件包配置总结。 - -说明: -TUI = 以文本为基础的用户接口 -GUI = 图形界面用户接口 - -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -Alpine (TUI) - -配置选项: -在"Sending Preferences"部分: - -- "Do Not Send Flowed Text"必须开启 -- "Strip Whitespace Before Sending"必须关闭 - -当写邮件时,光标应该放在补丁会出现的地方,然后按下CTRL-R组合键,使指定的 -补丁文件嵌入到邮件中。 - -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -Evolution (GUI) - -一些开发者成功的使用它发送补丁 - -当选择邮件选项:Preformat - 从Format->Heading->Preformatted (Ctrl-7)或者工具栏 - -然后使用: - Insert->Text File... (Alt-n x)插入补丁文件。 - -你还可以"diff -Nru old.c new.c | xclip",选择Preformat,然后使用中间键进行粘帖。 - -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -Kmail (GUI) - -一些开发者成功的使用它发送补丁。 - -默认设置不为HTML格式是合适的;不要启用它。 - -当书写一封邮件的时候,在选项下面不要选择自动换行。唯一的缺点就是你在邮件中输入的任何文本 -都不会被自动换行,因此你必须在发送补丁之前手动换行。最简单的方法就是启用自动换行来书写邮件, -然后把它保存为草稿。一旦你在草稿中再次打开它,它已经全部自动换行了,那么你的邮件虽然没有 -选择自动换行,但是还不会失去已有的自动换行。 - -在邮件的底部,插入补丁之前,放上常用的补丁定界符:三个连字号(---)。 - -然后在"Message"菜单条目,选择插入文件,接着选取你的补丁文件。还有一个额外的选项,你可以 -通过它配置你的邮件建立工具栏菜单,还可以带上"insert file"图标。 - -你可以安全地通过GPG标记附件,但是内嵌补丁最好不要使用GPG标记它们。作为内嵌文本的签发补丁, -当从GPG中提取7位编码时会使他们变的更加复杂。 - -如果你非要以附件的形式发送补丁,那么就右键点击附件,然后选中属性,突出"Suggest automatic -display",这样内嵌附件更容易让读者看到。 - -当你要保存将要发送的内嵌文本补丁,你可以从消息列表窗格选择包含补丁的邮件,然后右击选择 -"save as"。你可以使用一个没有更改的包含补丁的邮件,如果它是以正确的形式组成。当你正真在它 -自己的窗口之下察看,那时没有选项可以保存邮件--已经有一个这样的bug被汇报到了kmail的bugzilla -并且希望这将会被处理。邮件是以只针对某个用户可读写的权限被保存的,所以如果你想把邮件复制到其他地方, -你不得不把他们的权限改为组或者整体可读。 - -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -Lotus Notes (GUI) - -不要使用它。 - -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -Mutt (TUI) - -很多Linux开发人员使用mutt客户端,所以证明它肯定工作的非常漂亮。 - -Mutt不自带编辑器,所以不管你使用什么编辑器都不应该带有自动断行。大多数编辑器都带有 -一个"insert file"选项,它可以通过不改变文件内容的方式插入文件。 - -'vim'作为mutt的编辑器: - set editor="vi" - - 如果使用xclip,敲入以下命令 - :set paste - 按中键之前或者shift-insert或者使用 - :r filename - -如果想要把补丁作为内嵌文本。 -(a)ttach工作的很好,不带有"set paste"。 - -配置选项: -它应该以默认设置的形式工作。 -然而,把"send_charset"设置为"us-ascii::utf-8"也是一个不错的主意。 - -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -Pine (TUI) - -Pine过去有一些空格删减问题,但是这些现在应该都被修复了。 - -如果可以,请使用alpine(pine的继承者) - -配置选项: -- 最近的版本需要消除流程文本 -- "no-strip-whitespace-before-send"选项也是需要的。 - - -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -Sylpheed (GUI) - -- 内嵌文本可以很好的工作(或者使用附件)。 -- 允许使用外部的编辑器。 -- 对于目录较多时非常慢。 -- 如果通过non-SSL连接,无法使用TLS SMTP授权。 -- 在组成窗口中有一个很有用的ruler bar。 -- 给地址本中添加地址就不会正确的了解显示名。 - -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -Thunderbird (GUI) - -默认情况下,thunderbird很容易损坏文本,但是还有一些方法可以强制它变得更好。 - -- 在用户帐号设置里,组成和寻址,不要选择"Compose messages in HTML format"。 - -- 编辑你的Thunderbird配置设置来使它不要拆行使用:user_pref("mailnews.wraplength", 0); - -- 编辑你的Thunderbird配置设置,使它不要使用"format=flowed"格式:user_pref("mailnews. - send_plaintext_flowed", false); - -- 你需要使Thunderbird变为预先格式方式: - 如果默认情况下你书写的是HTML格式,那不是很难。仅仅从标题栏的下拉框中选择"Preformat"格式。 - 如果默认情况下你书写的是文本格式,你不得把它改为HTML格式(仅仅作为一次性的)来书写新的消息, - 然后强制使它回到文本格式,否则它就会拆行。要实现它,在写信的图标上使用shift键来使它变为HTML - 格式,然后标题栏的下拉框中选择"Preformat"格式。 - -- 允许使用外部的编辑器: - 针对Thunderbird打补丁最简单的方法就是使用一个"external editor"扩展,然后使用你最喜欢的 - $EDITOR来读取或者合并补丁到文本中。要实现它,可以下载并且安装这个扩展,然后添加一个使用它的 - 按键View->Toolbars->Customize...最后当你书写信息的时候仅仅点击它就可以了。 - -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -TkRat (GUI) - -可以使用它。使用"Insert file..."或者外部的编辑器。 - -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -Gmail (Web GUI) - -不要使用它发送补丁。 - -Gmail网页客户端自动地把制表符转换为空格。 - -虽然制表符转换为空格问题可以被外部编辑器解决,同时它还会使用回车换行把每行拆分为78个字符。 - -另一个问题是Gmail还会把任何不是ASCII的字符的信息改为base64编码。它把东西变的像欧洲人的名字。 - - ### -- cgit v1.2.3 From 8bfb5561e1dd2303d871153a22905af0d395e9a4 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:42 +0800 Subject: docs/zh_CN: do rst format for email-clients.rst Make it readble as rst format. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Li Zefan Cc: Shawn Guo Cc: Fengguang Wu Cc: Coly Li Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- .../translations/zh_CN/process/email-clients.rst | 53 +++++++++------------- 1 file changed, 22 insertions(+), 31 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/email-clients.rst b/Documentation/translations/zh_CN/process/email-clients.rst index ec31d97e8d0e..e8641a5899e4 100644 --- a/Documentation/translations/zh_CN/process/email-clients.rst +++ b/Documentation/translations/zh_CN/process/email-clients.rst @@ -1,33 +1,24 @@ -Chinese translated version of Documentation/process/email-clients.rst +.. _cn_email_clients: -If you have any comment or update to the content, please contact the -original document maintainer directly. However, if you have a problem -communicating in English you can also ask the Chinese maintainer for -help. Contact the Chinese maintainer if this translation is outdated -or if there is a problem with the translation. +.. include:: ../disclaimer-zh_CN.rst -Chinese maintainer: Harry Wei ---------------------------------------------------------------------- -Documentation/process/email-clients.rst 的中文翻译 +:Original: :ref:`Documentation/process/email-clients.rst ` 如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者。 +译存在问题,请联系中文版维护者:: -中文版维护者: 贾威威 Harry Wei -中文版翻译者: 贾威威 Harry Wei -中文版校译者: Yinglin Luan - Xiaochen Wang - yaxinsn - -以下为正文 ---------------------------------------------------------------------- + 中文版维护者: 贾威威 Harry Wei + 中文版翻译者: 贾威威 Harry Wei + 中文版校译者: Yinglin Luan + Xiaochen Wang + yaxinsn Linux邮件客户端配置信息 -====================================================================== +======================= 普通配置 ----------------------------------------------------------------------- +-------- Linux内核补丁是通过邮件被提交的,最好把补丁作为邮件体的内嵌文本。有些维护者 接收附件,但是附件的内容格式应该是"text/plain"。然而,附件一般是不赞成的, 因为这会使补丁的引用部分在评论过程中变的很困难。 @@ -56,7 +47,7 @@ Linux内核补丁是通过邮件被提交的,最好把补丁作为邮件体的 一些邮件客户端提示 ----------------------------------------------------------------------- +------------------ 这里给出一些详细的MUA配置提示,可以用于给Linux内核发送补丁。这些并不意味是 所有的软件包配置总结。 @@ -64,8 +55,8 @@ Linux内核补丁是通过邮件被提交的,最好把补丁作为邮件体的 TUI = 以文本为基础的用户接口 GUI = 图形界面用户接口 -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ Alpine (TUI) +~~~~~~~~~~~~ 配置选项: 在"Sending Preferences"部分: @@ -76,8 +67,8 @@ Alpine (TUI) 当写邮件时,光标应该放在补丁会出现的地方,然后按下CTRL-R组合键,使指定的 补丁文件嵌入到邮件中。 -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ Evolution (GUI) +~~~~~~~~~~~~~~~ 一些开发者成功的使用它发送补丁 @@ -89,8 +80,8 @@ Evolution (GUI) 你还可以"diff -Nru old.c new.c | xclip",选择Preformat,然后使用中间键进行粘帖。 -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ Kmail (GUI) +~~~~~~~~~~~ 一些开发者成功的使用它发送补丁。 @@ -118,13 +109,13 @@ display",这样内嵌附件更容易让读者看到。 并且希望这将会被处理。邮件是以只针对某个用户可读写的权限被保存的,所以如果你想把邮件复制到其他地方, 你不得不把他们的权限改为组或者整体可读。 -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ Lotus Notes (GUI) +~~~~~~~~~~~~~~~~~ 不要使用它。 -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ Mutt (TUI) +~~~~~~~~~~ 很多Linux开发人员使用mutt客户端,所以证明它肯定工作的非常漂亮。 @@ -146,8 +137,8 @@ Mutt不自带编辑器,所以不管你使用什么编辑器都不应该带有 它应该以默认设置的形式工作。 然而,把"send_charset"设置为"us-ascii::utf-8"也是一个不错的主意。 -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ Pine (TUI) +~~~~~~~~~~ Pine过去有一些空格删减问题,但是这些现在应该都被修复了。 @@ -158,8 +149,8 @@ Pine过去有一些空格删减问题,但是这些现在应该都被修复了 - "no-strip-whitespace-before-send"选项也是需要的。 -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ Sylpheed (GUI) +~~~~~~~~~~~~~~ - 内嵌文本可以很好的工作(或者使用附件)。 - 允许使用外部的编辑器。 @@ -168,8 +159,8 @@ Sylpheed (GUI) - 在组成窗口中有一个很有用的ruler bar。 - 给地址本中添加地址就不会正确的了解显示名。 -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ Thunderbird (GUI) +~~~~~~~~~~~~~~~~~ 默认情况下,thunderbird很容易损坏文本,但是还有一些方法可以强制它变得更好。 @@ -191,13 +182,13 @@ Thunderbird (GUI) $EDITOR来读取或者合并补丁到文本中。要实现它,可以下载并且安装这个扩展,然后添加一个使用它的 按键View->Toolbars->Customize...最后当你书写信息的时候仅仅点击它就可以了。 -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ TkRat (GUI) +~~~~~~~~~~~ 可以使用它。使用"Insert file..."或者外部的编辑器。 -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ Gmail (Web GUI) +~~~~~~~~~~~~~~~ 不要使用它发送补丁。 -- cgit v1.2.3 From bc31de5664c13481e4725c8ca9ad4655a06d65ed Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:43 +0800 Subject: docs/zh_CN: rename volatile-consider-harmful doc Make it available for html etc docs making. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Bryan Wu Cc: Li Zefan Cc: Shawn Guo Cc: Fengguang Wu Cc: Coly Li Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- .../zh_CN/process/volatile-considered-harmful.rst | 113 +++++++++++++++++++++ .../zh_CN/process/volatile-considered-harmful.txt | 113 --------------------- 2 files changed, 113 insertions(+), 113 deletions(-) create mode 100644 Documentation/translations/zh_CN/process/volatile-considered-harmful.rst delete mode 100644 Documentation/translations/zh_CN/process/volatile-considered-harmful.txt (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/volatile-considered-harmful.rst b/Documentation/translations/zh_CN/process/volatile-considered-harmful.rst new file mode 100644 index 000000000000..475125967197 --- /dev/null +++ b/Documentation/translations/zh_CN/process/volatile-considered-harmful.rst @@ -0,0 +1,113 @@ +Chinese translated version of Documentation/process/volatile-considered-harmful.rst + +If you have any comment or update to the content, please contact the +original document maintainer directly. However, if you have a problem +communicating in English you can also ask the Chinese maintainer for +help. Contact the Chinese maintainer if this translation is outdated +or if there is a problem with the translation. + +Maintainer: Jonathan Corbet +Chinese maintainer: Bryan Wu +--------------------------------------------------------------------- +Documentation/process/volatile-considered-harmful.rst 的中文翻译 + +如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 +交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 +译存在问题,请联系中文版维护者。 + +英文版维护者: Jonathan Corbet +中文版维护者: 伍鹏 Bryan Wu +中文版翻译者: 伍鹏 Bryan Wu +中文版校译者: 张汉辉 Eugene Teo + 杨瑞 Dave Young +以下为正文 +--------------------------------------------------------------------- + +为什么不应该使用“volatile”类型 +------------------------------ + +C程序员通常认为volatile表示某个变量可以在当前执行的线程之外被改变;因此,在内核 +中用到共享数据结构时,常常会有C程序员喜欢使用volatile这类变量。换句话说,他们经 +常会把volatile类型看成某种简易的原子变量,当然它们不是。在内核中使用volatile几 +乎总是错误的;本文档将解释为什么这样。 + +理解volatile的关键是知道它的目的是用来消除优化,实际上很少有人真正需要这样的应 +用。在内核中,程序员必须防止意外的并发访问破坏共享的数据结构,这其实是一个完全 +不同的任务。用来防止意外并发访问的保护措施,可以更加高效的避免大多数优化相关的 +问题。 + +像volatile一样,内核提供了很多原语来保证并发访问时的数据安全(自旋锁, 互斥量,内 +存屏障等等),同样可以防止意外的优化。如果可以正确使用这些内核原语,那么就没有 +必要再使用volatile。如果仍然必须使用volatile,那么几乎可以肯定在代码的某处有一 +个bug。在正确设计的内核代码中,volatile能带来的仅仅是使事情变慢。 + +思考一下这段典型的内核代码: + + spin_lock(&the_lock); + do_something_on(&shared_data); + do_something_else_with(&shared_data); + spin_unlock(&the_lock); + +如果所有的代码都遵循加锁规则,当持有the_lock的时候,不可能意外的改变shared_data的 +值。任何可能访问该数据的其他代码都会在这个锁上等待。自旋锁原语跟内存屏障一样—— 它 +们显式的用来书写成这样 —— 意味着数据访问不会跨越它们而被优化。所以本来编译器认为 +它知道在shared_data里面将有什么,但是因为spin_lock()调用跟内存屏障一样,会强制编 +译器忘记它所知道的一切。那么在访问这些数据时不会有优化的问题。 + +如果shared_data被声名为volatile,锁操作将仍然是必须的。就算我们知道没有其他人正在 +使用它,编译器也将被阻止优化对临界区内shared_data的访问。在锁有效的同时, +shared_data不是volatile的。在处理共享数据的时候,适当的锁操作可以不再需要 +volatile —— 并且是有潜在危害的。 + +volatile的存储类型最初是为那些内存映射的I/O寄存器而定义。在内核里,寄存器访问也应 +该被锁保护,但是人们也不希望编译器“优化”临界区内的寄存器访问。内核里I/O的内存访问 +是通过访问函数完成的;不赞成通过指针对I/O内存的直接访问,并且不是在所有体系架构上 +都能工作。那些访问函数正是为了防止意外优化而写的,因此,再说一次,volatile类型不 +是必需的。 + +另一种引起用户可能使用volatile的情况是当处理器正忙着等待一个变量的值。正确执行一 +个忙等待的方法是: + + while (my_variable != what_i_want) + cpu_relax(); + +cpu_relax()调用会降低CPU的能量消耗或者让位于超线程双处理器;它也作为内存屏障一样出 +现,所以,再一次,volatile不是必需的。当然,忙等待一开始就是一种反常规的做法。 + +在内核中,一些稀少的情况下volatile仍然是有意义的: + + - 在一些体系架构的系统上,允许直接的I/0内存访问,那么前面提到的访问函数可以使用 + volatile。基本上,每一个访问函数调用它自己都是一个小的临界区域并且保证了按照 + 程序员期望的那样发生访问操作。 + + - 某些会改变内存的内联汇编代码虽然没有什么其他明显的附作用,但是有被GCC删除的可 + 能性。在汇编声明中加上volatile关键字可以防止这种删除操作。 + + - Jiffies变量是一种特殊情况,虽然每次引用它的时候都可以有不同的值,但读jiffies + 变量时不需要任何特殊的加锁保护。所以jiffies变量可以使用volatile,但是不赞成 + 其他跟jiffies相同类型变量使用volatile。Jiffies被认为是一种“愚蠢的遗留物" + (Linus的话)因为解决这个问题比保持现状要麻烦的多。 + + - 由于某些I/0设备可能会修改连续一致的内存,所以有时,指向连续一致内存的数据结构 + 的指针需要正确的使用volatile。网络适配器使用的环状缓存区正是这类情形的一个例 + 子,其中适配器用改变指针来表示哪些描述符已经处理过了。 + +对于大多代码,上述几种可以使用volatile的情况都不适用。所以,使用volatile是一种 +bug并且需要对这样的代码额外仔细检查。那些试图使用volatile的开发人员需要退一步想想 +他们真正想实现的是什么。 + +非常欢迎删除volatile变量的补丁 - 只要证明这些补丁完整的考虑了并发问题。 + +注释 +---- + +[1] http://lwn.net/Articles/233481/ +[2] http://lwn.net/Articles/233482/ + +致谢 +---- + +最初由Randy Dunlap推动并作初步研究 +由Jonathan Corbet撰写 +参考Satyam Sharma,Johannes Stezenbach,Jesper Juhl,Heikki Orsila, +H. Peter Anvin,Philipp Hahn和Stefan Richter的意见改善了本档。 diff --git a/Documentation/translations/zh_CN/process/volatile-considered-harmful.txt b/Documentation/translations/zh_CN/process/volatile-considered-harmful.txt deleted file mode 100644 index 475125967197..000000000000 --- a/Documentation/translations/zh_CN/process/volatile-considered-harmful.txt +++ /dev/null @@ -1,113 +0,0 @@ -Chinese translated version of Documentation/process/volatile-considered-harmful.rst - -If you have any comment or update to the content, please contact the -original document maintainer directly. However, if you have a problem -communicating in English you can also ask the Chinese maintainer for -help. Contact the Chinese maintainer if this translation is outdated -or if there is a problem with the translation. - -Maintainer: Jonathan Corbet -Chinese maintainer: Bryan Wu ---------------------------------------------------------------------- -Documentation/process/volatile-considered-harmful.rst 的中文翻译 - -如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 -交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者。 - -英文版维护者: Jonathan Corbet -中文版维护者: 伍鹏 Bryan Wu -中文版翻译者: 伍鹏 Bryan Wu -中文版校译者: 张汉辉 Eugene Teo - 杨瑞 Dave Young -以下为正文 ---------------------------------------------------------------------- - -为什么不应该使用“volatile”类型 ------------------------------- - -C程序员通常认为volatile表示某个变量可以在当前执行的线程之外被改变;因此,在内核 -中用到共享数据结构时,常常会有C程序员喜欢使用volatile这类变量。换句话说,他们经 -常会把volatile类型看成某种简易的原子变量,当然它们不是。在内核中使用volatile几 -乎总是错误的;本文档将解释为什么这样。 - -理解volatile的关键是知道它的目的是用来消除优化,实际上很少有人真正需要这样的应 -用。在内核中,程序员必须防止意外的并发访问破坏共享的数据结构,这其实是一个完全 -不同的任务。用来防止意外并发访问的保护措施,可以更加高效的避免大多数优化相关的 -问题。 - -像volatile一样,内核提供了很多原语来保证并发访问时的数据安全(自旋锁, 互斥量,内 -存屏障等等),同样可以防止意外的优化。如果可以正确使用这些内核原语,那么就没有 -必要再使用volatile。如果仍然必须使用volatile,那么几乎可以肯定在代码的某处有一 -个bug。在正确设计的内核代码中,volatile能带来的仅仅是使事情变慢。 - -思考一下这段典型的内核代码: - - spin_lock(&the_lock); - do_something_on(&shared_data); - do_something_else_with(&shared_data); - spin_unlock(&the_lock); - -如果所有的代码都遵循加锁规则,当持有the_lock的时候,不可能意外的改变shared_data的 -值。任何可能访问该数据的其他代码都会在这个锁上等待。自旋锁原语跟内存屏障一样—— 它 -们显式的用来书写成这样 —— 意味着数据访问不会跨越它们而被优化。所以本来编译器认为 -它知道在shared_data里面将有什么,但是因为spin_lock()调用跟内存屏障一样,会强制编 -译器忘记它所知道的一切。那么在访问这些数据时不会有优化的问题。 - -如果shared_data被声名为volatile,锁操作将仍然是必须的。就算我们知道没有其他人正在 -使用它,编译器也将被阻止优化对临界区内shared_data的访问。在锁有效的同时, -shared_data不是volatile的。在处理共享数据的时候,适当的锁操作可以不再需要 -volatile —— 并且是有潜在危害的。 - -volatile的存储类型最初是为那些内存映射的I/O寄存器而定义。在内核里,寄存器访问也应 -该被锁保护,但是人们也不希望编译器“优化”临界区内的寄存器访问。内核里I/O的内存访问 -是通过访问函数完成的;不赞成通过指针对I/O内存的直接访问,并且不是在所有体系架构上 -都能工作。那些访问函数正是为了防止意外优化而写的,因此,再说一次,volatile类型不 -是必需的。 - -另一种引起用户可能使用volatile的情况是当处理器正忙着等待一个变量的值。正确执行一 -个忙等待的方法是: - - while (my_variable != what_i_want) - cpu_relax(); - -cpu_relax()调用会降低CPU的能量消耗或者让位于超线程双处理器;它也作为内存屏障一样出 -现,所以,再一次,volatile不是必需的。当然,忙等待一开始就是一种反常规的做法。 - -在内核中,一些稀少的情况下volatile仍然是有意义的: - - - 在一些体系架构的系统上,允许直接的I/0内存访问,那么前面提到的访问函数可以使用 - volatile。基本上,每一个访问函数调用它自己都是一个小的临界区域并且保证了按照 - 程序员期望的那样发生访问操作。 - - - 某些会改变内存的内联汇编代码虽然没有什么其他明显的附作用,但是有被GCC删除的可 - 能性。在汇编声明中加上volatile关键字可以防止这种删除操作。 - - - Jiffies变量是一种特殊情况,虽然每次引用它的时候都可以有不同的值,但读jiffies - 变量时不需要任何特殊的加锁保护。所以jiffies变量可以使用volatile,但是不赞成 - 其他跟jiffies相同类型变量使用volatile。Jiffies被认为是一种“愚蠢的遗留物" - (Linus的话)因为解决这个问题比保持现状要麻烦的多。 - - - 由于某些I/0设备可能会修改连续一致的内存,所以有时,指向连续一致内存的数据结构 - 的指针需要正确的使用volatile。网络适配器使用的环状缓存区正是这类情形的一个例 - 子,其中适配器用改变指针来表示哪些描述符已经处理过了。 - -对于大多代码,上述几种可以使用volatile的情况都不适用。所以,使用volatile是一种 -bug并且需要对这样的代码额外仔细检查。那些试图使用volatile的开发人员需要退一步想想 -他们真正想实现的是什么。 - -非常欢迎删除volatile变量的补丁 - 只要证明这些补丁完整的考虑了并发问题。 - -注释 ----- - -[1] http://lwn.net/Articles/233481/ -[2] http://lwn.net/Articles/233482/ - -致谢 ----- - -最初由Randy Dunlap推动并作初步研究 -由Jonathan Corbet撰写 -参考Satyam Sharma,Johannes Stezenbach,Jesper Juhl,Heikki Orsila, -H. Peter Anvin,Philipp Hahn和Stefan Richter的意见改善了本档。 -- cgit v1.2.3 From 7712cfd6597ab952a700dee6cca5a3c3a319b2d0 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:44 +0800 Subject: docs/zh_CN: volatile doc format changes make it readble as rst format for html etc doc making. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Bryan Wu Cc: Li Zefan Cc: Shawn Guo Cc: Fengguang Wu Cc: Coly Li Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- .../zh_CN/process/volatile-considered-harmful.rst | 35 +++++++++------------- 1 file changed, 14 insertions(+), 21 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/volatile-considered-harmful.rst b/Documentation/translations/zh_CN/process/volatile-considered-harmful.rst index 475125967197..48b32ce58ef1 100644 --- a/Documentation/translations/zh_CN/process/volatile-considered-harmful.rst +++ b/Documentation/translations/zh_CN/process/volatile-considered-harmful.rst @@ -1,30 +1,23 @@ -Chinese translated version of Documentation/process/volatile-considered-harmful.rst +.. _cn_volatile_considered_harmful: -If you have any comment or update to the content, please contact the -original document maintainer directly. However, if you have a problem -communicating in English you can also ask the Chinese maintainer for -help. Contact the Chinese maintainer if this translation is outdated -or if there is a problem with the translation. +.. include:: ../disclaimer-zh_CN.rst -Maintainer: Jonathan Corbet -Chinese maintainer: Bryan Wu ---------------------------------------------------------------------- -Documentation/process/volatile-considered-harmful.rst 的中文翻译 +:Original: :ref:`Documentation/process/volatile-considered-harmful.rst + ` 如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者。 +译存在问题,请联系中文版维护者:: -英文版维护者: Jonathan Corbet -中文版维护者: 伍鹏 Bryan Wu -中文版翻译者: 伍鹏 Bryan Wu -中文版校译者: 张汉辉 Eugene Teo - 杨瑞 Dave Young -以下为正文 ---------------------------------------------------------------------- + 英文版维护者: Jonathan Corbet + 中文版维护者: 伍鹏 Bryan Wu + 中文版翻译者: 伍鹏 Bryan Wu + 中文版校译者: 张汉辉 Eugene Teo + 杨瑞 Dave Young + 时奎亮 Alex Shi 为什么不应该使用“volatile”类型 ------------------------------- +============================== C程序员通常认为volatile表示某个变量可以在当前执行的线程之外被改变;因此,在内核 中用到共享数据结构时,常常会有C程序员喜欢使用volatile这类变量。换句话说,他们经 @@ -41,7 +34,7 @@ C程序员通常认为volatile表示某个变量可以在当前执行的线程 必要再使用volatile。如果仍然必须使用volatile,那么几乎可以肯定在代码的某处有一 个bug。在正确设计的内核代码中,volatile能带来的仅仅是使事情变慢。 -思考一下这段典型的内核代码: +思考一下这段典型的内核代码:: spin_lock(&the_lock); do_something_on(&shared_data); @@ -66,7 +59,7 @@ volatile的存储类型最初是为那些内存映射的I/O寄存器而定义。 是必需的。 另一种引起用户可能使用volatile的情况是当处理器正忙着等待一个变量的值。正确执行一 -个忙等待的方法是: +个忙等待的方法是:: while (my_variable != what_i_want) cpu_relax(); -- cgit v1.2.3 From 701a4ebd627c17c3c3857e83ba9a5c8e93b5f98d Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:45 +0800 Subject: docs/zh_CN: rename SubmittingDrivers Rename the file to make it available in html etc docs making. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Li Yang Cc: Li Zefan Cc: Shawn Guo Cc: Fengguang Wu Cc: Coly Li Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- .../translations/zh_CN/process/SubmittingDrivers | 164 --------------------- .../zh_CN/process/submitting-drivers.rst | 164 +++++++++++++++++++++ 2 files changed, 164 insertions(+), 164 deletions(-) delete mode 100644 Documentation/translations/zh_CN/process/SubmittingDrivers create mode 100644 Documentation/translations/zh_CN/process/submitting-drivers.rst (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/SubmittingDrivers b/Documentation/translations/zh_CN/process/SubmittingDrivers deleted file mode 100644 index 15e73562f710..000000000000 --- a/Documentation/translations/zh_CN/process/SubmittingDrivers +++ /dev/null @@ -1,164 +0,0 @@ -Chinese translated version of Documentation/process/submitting-drivers.rst - -If you have any comment or update to the content, please contact the -original document maintainer directly. However, if you have a problem -communicating in English you can also ask the Chinese maintainer for -help. Contact the Chinese maintainer if this translation is outdated -or if there is a problem with the translation. - -Chinese maintainer: Li Yang ---------------------------------------------------------------------- -Documentation/process/submitting-drivers.rst 的中文翻译 - -如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 -交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者。 - -中文版维护者: 李阳 Li Yang -中文版翻译者: 李阳 Li Yang -中文版校译者: 陈琦 Maggie Chen - 王聪 Wang Cong - 张巍 Zhang Wei - -以下为正文 ---------------------------------------------------------------------- - -如何向 Linux 内核提交驱动程序 ------------------------------ - -这篇文档将会解释如何向不同的内核源码树提交设备驱动程序。请注意,如果你感 -兴趣的是显卡驱动程序,你也许应该访问 XFree86 项目(http://www.xfree86.org/) -和/或 X.org 项目 (http://x.org)。 - -另请参阅 Documentation/process/submitting-patches.rst 文档。 - - -分配设备号 ----------- - -块设备和字符设备的主设备号与从设备号是由 Linux 命名编号分配权威 LANANA( -现在是 Torben Mathiasen)负责分配。申请的网址是 http://www.lanana.org/。 -即使不准备提交到主流内核的设备驱动也需要在这里分配设备号。有关详细信息, -请参阅 Documentation/admin-guide/devices.rst。 - -如果你使用的不是已经分配的设备号,那么当你提交设备驱动的时候,它将会被强 -制分配一个新的设备号,即便这个设备号和你之前发给客户的截然不同。 - -设备驱动的提交对象 ------------------- - -Linux 2.0: - 此内核源码树不接受新的驱动程序。 - -Linux 2.2: - 此内核源码树不接受新的驱动程序。 - -Linux 2.4: - 如果所属的代码领域在内核的 MAINTAINERS 文件中列有一个总维护者, - 那么请将驱动程序提交给他。如果此维护者没有回应或者你找不到恰当的 - 维护者,那么请联系 Willy Tarreau 。 - -Linux 2.6: - 除了遵循和 2.4 版内核同样的规则外,你还需要在 linux-kernel 邮件 - 列表上跟踪最新的 API 变化。向 Linux 2.6 内核提交驱动的顶级联系人 - 是 Andrew Morton 。 - -决定设备驱动能否被接受的条件 ----------------------------- - -许可: 代码必须使用 GNU 通用公开许可证 (GPL) 提交给 Linux,但是 - 我们并不要求 GPL 是唯一的许可。你或许会希望同时使用多种 - 许可证发布,如果希望驱动程序可以被其他开源社区(比如BSD) - 使用。请参考 include/linux/module.h 文件中所列出的可被 - 接受共存的许可。 - -版权: 版权所有者必须同意使用 GPL 许可。最好提交者和版权所有者 - 是相同个人或实体。否则,必需列出授权使用 GPL 的版权所有 - 人或实体,以备验证之需。 - -接口: 如果你的驱动程序使用现成的接口并且和其他同类的驱动程序行 - 为相似,而不是去发明无谓的新接口,那么它将会更容易被接受。 - 如果你需要一个 Linux 和 NT 的通用驱动接口,那么请在用 - 户空间实现它。 - -代码: 请使用 Documentation/process/coding-style.rst 中所描述的 Linux 代码风 - 格。如果你的某些代码段(例如那些与 Windows 驱动程序包共 - 享的代码段)需要使用其他格式,而你却只希望维护一份代码, - 那么请将它们很好地区分出来,并且注明原因。 - -可移植性: 请注意,指针并不永远是 32 位的,不是所有的计算机都使用小 - 尾模式 (little endian) 存储数据,不是所有的人都拥有浮点 - 单元,不要随便在你的驱动程序里嵌入 x86 汇编指令。只能在 - x86 上运行的驱动程序一般是不受欢迎的。虽然你可能只有 x86 - 硬件,很难测试驱动程序在其他平台上是否可用,但是确保代码 - 可以被轻松地移植却是很简单的。 - -清晰度: 做到所有人都能修补这个驱动程序将会很有好处,因为这样你将 - 会直接收到修复的补丁而不是 bug 报告。如果你提交一个试图 - 隐藏硬件工作机理的驱动程序,那么它将会被扔进废纸篓。 - -电源管理: 因为 Linux 正在被很多移动设备和桌面系统使用,所以你的驱 - 动程序也很有可能被使用在这些设备上。它应该支持最基本的电 - 源管理,即在需要的情况下实现系统级休眠和唤醒要用到的 - .suspend 和 .resume 函数。你应该检查你的驱动程序是否能正 - 确地处理休眠与唤醒,如果实在无法确认,请至少把 .suspend - 函数定义成返回 -ENOSYS(功能未实现)错误。你还应该尝试确 - 保你的驱动在什么都不干的情况下将耗电降到最低。要获得驱动 - 程序测试的指导,请参阅 - Documentation/power/drivers-testing.txt。有关驱动程序电 - 源管理问题相对全面的概述,请参阅 - Documentation/driver-api/pm/devices.rst。 - -管理: 如果一个驱动程序的作者还在进行有效的维护,那么通常除了那 - 些明显正确且不需要任何检查的补丁以外,其他所有的补丁都会 - 被转发给作者。如果你希望成为驱动程序的联系人和更新者,最 - 好在代码注释中写明并且在 MAINTAINERS 文件中加入这个驱动 - 程序的条目。 - -不影响设备驱动能否被接受的条件 ------------------------------- - -供应商: 由硬件供应商来维护驱动程序通常是一件好事。不过,如果源码 - 树里已经有其他人提供了可稳定工作的驱动程序,那么请不要期 - 望“我是供应商”会成为内核改用你的驱动程序的理由。理想的情 - 况是:供应商与现有驱动程序的作者合作,构建一个统一完美的 - 驱动程序。 - -作者: 驱动程序是由大的 Linux 公司研发还是由你个人编写,并不影 - 响其是否能被内核接受。没有人对内核源码树享有特权。只要你 - 充分了解内核社区,你就会发现这一点。 - - -资源列表 --------- - -Linux 内核主源码树: - ftp.??.kernel.org:/pub/linux/kernel/... - ?? == 你的国家代码,例如 "cn"、"us"、"uk"、"fr" 等等 - -Linux 内核邮件列表: - linux-kernel@vger.kernel.org - [可通过向majordomo@vger.kernel.org发邮件来订阅] - -Linux 设备驱动程序,第三版(探讨 2.6.10 版内核): - http://lwn.net/Kernel/LDD3/ (免费版) - -LWN.net: - 每周内核开发活动摘要 - http://lwn.net/ - 2.6 版中 API 的变更: - http://lwn.net/Articles/2.6-kernel-api/ - 将旧版内核的驱动程序移植到 2.6 版: - http://lwn.net/Articles/driver-porting/ - -内核新手(KernelNewbies): - 为新的内核开发者提供文档和帮助 - http://kernelnewbies.org/ - -Linux USB项目: - http://www.linux-usb.org/ - -写内核驱动的“不要”(Arjan van de Ven著): - http://www.fenrus.org/how-to-not-write-a-device-driver-paper.pdf - -内核清洁工 (Kernel Janitor): - http://kernelnewbies.org/KernelJanitors diff --git a/Documentation/translations/zh_CN/process/submitting-drivers.rst b/Documentation/translations/zh_CN/process/submitting-drivers.rst new file mode 100644 index 000000000000..15e73562f710 --- /dev/null +++ b/Documentation/translations/zh_CN/process/submitting-drivers.rst @@ -0,0 +1,164 @@ +Chinese translated version of Documentation/process/submitting-drivers.rst + +If you have any comment or update to the content, please contact the +original document maintainer directly. However, if you have a problem +communicating in English you can also ask the Chinese maintainer for +help. Contact the Chinese maintainer if this translation is outdated +or if there is a problem with the translation. + +Chinese maintainer: Li Yang +--------------------------------------------------------------------- +Documentation/process/submitting-drivers.rst 的中文翻译 + +如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 +交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 +译存在问题,请联系中文版维护者。 + +中文版维护者: 李阳 Li Yang +中文版翻译者: 李阳 Li Yang +中文版校译者: 陈琦 Maggie Chen + 王聪 Wang Cong + 张巍 Zhang Wei + +以下为正文 +--------------------------------------------------------------------- + +如何向 Linux 内核提交驱动程序 +----------------------------- + +这篇文档将会解释如何向不同的内核源码树提交设备驱动程序。请注意,如果你感 +兴趣的是显卡驱动程序,你也许应该访问 XFree86 项目(http://www.xfree86.org/) +和/或 X.org 项目 (http://x.org)。 + +另请参阅 Documentation/process/submitting-patches.rst 文档。 + + +分配设备号 +---------- + +块设备和字符设备的主设备号与从设备号是由 Linux 命名编号分配权威 LANANA( +现在是 Torben Mathiasen)负责分配。申请的网址是 http://www.lanana.org/。 +即使不准备提交到主流内核的设备驱动也需要在这里分配设备号。有关详细信息, +请参阅 Documentation/admin-guide/devices.rst。 + +如果你使用的不是已经分配的设备号,那么当你提交设备驱动的时候,它将会被强 +制分配一个新的设备号,即便这个设备号和你之前发给客户的截然不同。 + +设备驱动的提交对象 +------------------ + +Linux 2.0: + 此内核源码树不接受新的驱动程序。 + +Linux 2.2: + 此内核源码树不接受新的驱动程序。 + +Linux 2.4: + 如果所属的代码领域在内核的 MAINTAINERS 文件中列有一个总维护者, + 那么请将驱动程序提交给他。如果此维护者没有回应或者你找不到恰当的 + 维护者,那么请联系 Willy Tarreau 。 + +Linux 2.6: + 除了遵循和 2.4 版内核同样的规则外,你还需要在 linux-kernel 邮件 + 列表上跟踪最新的 API 变化。向 Linux 2.6 内核提交驱动的顶级联系人 + 是 Andrew Morton 。 + +决定设备驱动能否被接受的条件 +---------------------------- + +许可: 代码必须使用 GNU 通用公开许可证 (GPL) 提交给 Linux,但是 + 我们并不要求 GPL 是唯一的许可。你或许会希望同时使用多种 + 许可证发布,如果希望驱动程序可以被其他开源社区(比如BSD) + 使用。请参考 include/linux/module.h 文件中所列出的可被 + 接受共存的许可。 + +版权: 版权所有者必须同意使用 GPL 许可。最好提交者和版权所有者 + 是相同个人或实体。否则,必需列出授权使用 GPL 的版权所有 + 人或实体,以备验证之需。 + +接口: 如果你的驱动程序使用现成的接口并且和其他同类的驱动程序行 + 为相似,而不是去发明无谓的新接口,那么它将会更容易被接受。 + 如果你需要一个 Linux 和 NT 的通用驱动接口,那么请在用 + 户空间实现它。 + +代码: 请使用 Documentation/process/coding-style.rst 中所描述的 Linux 代码风 + 格。如果你的某些代码段(例如那些与 Windows 驱动程序包共 + 享的代码段)需要使用其他格式,而你却只希望维护一份代码, + 那么请将它们很好地区分出来,并且注明原因。 + +可移植性: 请注意,指针并不永远是 32 位的,不是所有的计算机都使用小 + 尾模式 (little endian) 存储数据,不是所有的人都拥有浮点 + 单元,不要随便在你的驱动程序里嵌入 x86 汇编指令。只能在 + x86 上运行的驱动程序一般是不受欢迎的。虽然你可能只有 x86 + 硬件,很难测试驱动程序在其他平台上是否可用,但是确保代码 + 可以被轻松地移植却是很简单的。 + +清晰度: 做到所有人都能修补这个驱动程序将会很有好处,因为这样你将 + 会直接收到修复的补丁而不是 bug 报告。如果你提交一个试图 + 隐藏硬件工作机理的驱动程序,那么它将会被扔进废纸篓。 + +电源管理: 因为 Linux 正在被很多移动设备和桌面系统使用,所以你的驱 + 动程序也很有可能被使用在这些设备上。它应该支持最基本的电 + 源管理,即在需要的情况下实现系统级休眠和唤醒要用到的 + .suspend 和 .resume 函数。你应该检查你的驱动程序是否能正 + 确地处理休眠与唤醒,如果实在无法确认,请至少把 .suspend + 函数定义成返回 -ENOSYS(功能未实现)错误。你还应该尝试确 + 保你的驱动在什么都不干的情况下将耗电降到最低。要获得驱动 + 程序测试的指导,请参阅 + Documentation/power/drivers-testing.txt。有关驱动程序电 + 源管理问题相对全面的概述,请参阅 + Documentation/driver-api/pm/devices.rst。 + +管理: 如果一个驱动程序的作者还在进行有效的维护,那么通常除了那 + 些明显正确且不需要任何检查的补丁以外,其他所有的补丁都会 + 被转发给作者。如果你希望成为驱动程序的联系人和更新者,最 + 好在代码注释中写明并且在 MAINTAINERS 文件中加入这个驱动 + 程序的条目。 + +不影响设备驱动能否被接受的条件 +------------------------------ + +供应商: 由硬件供应商来维护驱动程序通常是一件好事。不过,如果源码 + 树里已经有其他人提供了可稳定工作的驱动程序,那么请不要期 + 望“我是供应商”会成为内核改用你的驱动程序的理由。理想的情 + 况是:供应商与现有驱动程序的作者合作,构建一个统一完美的 + 驱动程序。 + +作者: 驱动程序是由大的 Linux 公司研发还是由你个人编写,并不影 + 响其是否能被内核接受。没有人对内核源码树享有特权。只要你 + 充分了解内核社区,你就会发现这一点。 + + +资源列表 +-------- + +Linux 内核主源码树: + ftp.??.kernel.org:/pub/linux/kernel/... + ?? == 你的国家代码,例如 "cn"、"us"、"uk"、"fr" 等等 + +Linux 内核邮件列表: + linux-kernel@vger.kernel.org + [可通过向majordomo@vger.kernel.org发邮件来订阅] + +Linux 设备驱动程序,第三版(探讨 2.6.10 版内核): + http://lwn.net/Kernel/LDD3/ (免费版) + +LWN.net: + 每周内核开发活动摘要 - http://lwn.net/ + 2.6 版中 API 的变更: + http://lwn.net/Articles/2.6-kernel-api/ + 将旧版内核的驱动程序移植到 2.6 版: + http://lwn.net/Articles/driver-porting/ + +内核新手(KernelNewbies): + 为新的内核开发者提供文档和帮助 + http://kernelnewbies.org/ + +Linux USB项目: + http://www.linux-usb.org/ + +写内核驱动的“不要”(Arjan van de Ven著): + http://www.fenrus.org/how-to-not-write-a-device-driver-paper.pdf + +内核清洁工 (Kernel Janitor): + http://kernelnewbies.org/KernelJanitors -- cgit v1.2.3 From eb6adf7da473fe0db11571652e6da7012b94bdfd Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:46 +0800 Subject: docs/zh_CN: format submitting drivers as rst to Make it readble for html etc docs making. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Li Yang Cc: Li Zefan Cc: Shawn Guo Cc: Fengguang Wu Cc: Coly Li Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- .../zh_CN/process/submitting-drivers.rst | 30 ++++++++-------------- 1 file changed, 11 insertions(+), 19 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/submitting-drivers.rst b/Documentation/translations/zh_CN/process/submitting-drivers.rst index 15e73562f710..c90ab5ae233d 100644 --- a/Documentation/translations/zh_CN/process/submitting-drivers.rst +++ b/Documentation/translations/zh_CN/process/submitting-drivers.rst @@ -1,30 +1,22 @@ -Chinese translated version of Documentation/process/submitting-drivers.rst +.. _cn_submittingdrivers: -If you have any comment or update to the content, please contact the -original document maintainer directly. However, if you have a problem -communicating in English you can also ask the Chinese maintainer for -help. Contact the Chinese maintainer if this translation is outdated -or if there is a problem with the translation. +.. include:: ../disclaimer-zh_CN.rst -Chinese maintainer: Li Yang ---------------------------------------------------------------------- -Documentation/process/submitting-drivers.rst 的中文翻译 +:Original: :ref:`Documentation/process/submitting-drivers.rst + ` 如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者。 +译存在问题,请联系中文版维护者:: -中文版维护者: 李阳 Li Yang -中文版翻译者: 李阳 Li Yang -中文版校译者: 陈琦 Maggie Chen - 王聪 Wang Cong - 张巍 Zhang Wei - -以下为正文 ---------------------------------------------------------------------- + 中文版维护者: 李阳 Li Yang + 中文版翻译者: 李阳 Li Yang + 中文版校译者: 陈琦 Maggie Chen + 王聪 Wang Cong + 张巍 Zhang Wei 如何向 Linux 内核提交驱动程序 ------------------------------ +============================= 这篇文档将会解释如何向不同的内核源码树提交设备驱动程序。请注意,如果你感 兴趣的是显卡驱动程序,你也许应该访问 XFree86 项目(http://www.xfree86.org/) -- cgit v1.2.3 From 95dcdb6e125f237417df4618676871dbb02b380e Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:47 +0800 Subject: docs/zh_CN: rename magic-numbers as rst doc to Make it available in html etc doc making Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Jia Wei Wei Cc: Li Zefan Cc: Shawn Guo Cc: Fengguang Wu Cc: Coly Li Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- .../translations/zh_CN/process/magic-number.rst | 153 +++++++++++++++++++++ .../translations/zh_CN/process/magic-number.txt | 153 --------------------- 2 files changed, 153 insertions(+), 153 deletions(-) create mode 100644 Documentation/translations/zh_CN/process/magic-number.rst delete mode 100644 Documentation/translations/zh_CN/process/magic-number.txt (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/magic-number.rst b/Documentation/translations/zh_CN/process/magic-number.rst new file mode 100644 index 000000000000..7159cec04090 --- /dev/null +++ b/Documentation/translations/zh_CN/process/magic-number.rst @@ -0,0 +1,153 @@ +Chinese translated version of Documentation/process/magic-number.rst + +If you have any comment or update to the content, please post to LKML directly. +However, if you have problem communicating in English you can also ask the +Chinese maintainer for help. Contact the Chinese maintainer, if this +translation is outdated or there is problem with translation. + +Chinese maintainer: Jia Wei Wei +--------------------------------------------------------------------- +Documentation/process/magic-number.rst的中文翻译 + +如果想评论或更新本文的内容,请直接发信到LKML。如果你使用英文交流有困难的话,也可 +以向中文版维护者求助。如果本翻译更新不及时或者翻译存在问题,请联系中文版维护者。 + +中文版维护者: 贾威威 Jia Wei Wei +中文版翻译者: 贾威威 Jia Wei Wei +中文版校译者: 贾威威 Jia Wei Wei + +以下为正文 +--------------------------------------------------------------------- +这个文件是有关当前使用的魔术值注册表。当你给一个结构添加了一个魔术值,你也应该把这个魔术值添加到这个文件,因为我们最好把用于各种结构的魔术值统一起来。 + +使用魔术值来保护内核数据结构是一个非常好的主意。这就允许你在运行期检查(a)一个结构是否已经被攻击,或者(b)你已经给一个例行程序通过了一个错误的结构。后一种情况特别地有用---特别是当你通过一个空指针指向结构体的时候。tty源码,例如,经常通过特定驱动使用这种方法并且反复地排列特定方面的结构。 + +使用魔术值的方法是在结构的开始处声明的,如下: + +struct tty_ldisc { + int magic; + ... +}; + +当你以后给内核添加增强功能的时候,请遵守这条规则!这样就会节省数不清的调试时间,特别是一些古怪的情况,例如,数组超出范围并且重新写了超出部分。遵守这个规则,‪这些情况可以被快速地,安全地避免。 + + Theodore Ts'o + 31 Mar 94 + +给当前的Linux 2.1.55添加魔术表。 + + Michael Chastain + + 22 Sep 1997 + +现在应该最新的Linux 2.1.112.因为在特性冻结期间,不能在2.2.x前改变任何东西。这些条目被数域所排序。 + + Krzysztof G.Baranowski + + 29 Jul 1998 + +更新魔术表到Linux 2.5.45。刚好越过特性冻结,但是有可能还会有一些新的魔术值在2.6.x之前融入到内核中。 + + Petr Baudis + + 03 Nov 2002 + +更新魔术表到Linux 2.5.74。 + + Fabian Frederick + + 09 Jul 2003 + +魔术名 地址 结构 所在文件 +=========================================================================== +PG_MAGIC 'P' pg_{read,write}_hdr include/linux/pg.h +CMAGIC 0x0111 user include/linux/a.out.h +MKISS_DRIVER_MAGIC 0x04bf mkiss_channel drivers/net/mkiss.h +HDLC_MAGIC 0x239e n_hdlc drivers/char/n_hdlc.c +APM_BIOS_MAGIC 0x4101 apm_user arch/x86/kernel/apm_32.c +CYCLADES_MAGIC 0x4359 cyclades_port include/linux/cyclades.h +DB_MAGIC 0x4442 fc_info drivers/net/iph5526_novram.c +DL_MAGIC 0x444d fc_info drivers/net/iph5526_novram.c +FASYNC_MAGIC 0x4601 fasync_struct include/linux/fs.h +FF_MAGIC 0x4646 fc_info drivers/net/iph5526_novram.c +ISICOM_MAGIC 0x4d54 isi_port include/linux/isicom.h +PTY_MAGIC 0x5001 drivers/char/pty.c +PPP_MAGIC 0x5002 ppp include/linux/if_pppvar.h +SERIAL_MAGIC 0x5301 async_struct include/linux/serial.h +SSTATE_MAGIC 0x5302 serial_state include/linux/serial.h +SLIP_MAGIC 0x5302 slip drivers/net/slip.h +STRIP_MAGIC 0x5303 strip drivers/net/strip.c +X25_ASY_MAGIC 0x5303 x25_asy drivers/net/x25_asy.h +SIXPACK_MAGIC 0x5304 sixpack drivers/net/hamradio/6pack.h +AX25_MAGIC 0x5316 ax_disp drivers/net/mkiss.h +TTY_MAGIC 0x5401 tty_struct include/linux/tty.h +MGSL_MAGIC 0x5401 mgsl_info drivers/char/synclink.c +TTY_DRIVER_MAGIC 0x5402 tty_driver include/linux/tty_driver.h +MGSLPC_MAGIC 0x5402 mgslpc_info drivers/char/pcmcia/synclink_cs.c +TTY_LDISC_MAGIC 0x5403 tty_ldisc include/linux/tty_ldisc.h +USB_SERIAL_MAGIC 0x6702 usb_serial drivers/usb/serial/usb-serial.h +FULL_DUPLEX_MAGIC 0x6969 drivers/net/ethernet/dec/tulip/de2104x.c +USB_BLUETOOTH_MAGIC 0x6d02 usb_bluetooth drivers/usb/class/bluetty.c +RFCOMM_TTY_MAGIC 0x6d02 net/bluetooth/rfcomm/tty.c +USB_SERIAL_PORT_MAGIC 0x7301 usb_serial_port drivers/usb/serial/usb-serial.h +CG_MAGIC 0x00090255 ufs_cylinder_group include/linux/ufs_fs.h +RPORT_MAGIC 0x00525001 r_port drivers/char/rocket_int.h +LSEMAGIC 0x05091998 lse drivers/fc4/fc.c +GDTIOCTL_MAGIC 0x06030f07 gdth_iowr_str drivers/scsi/gdth_ioctl.h +RIEBL_MAGIC 0x09051990 drivers/net/atarilance.c +NBD_REQUEST_MAGIC 0x12560953 nbd_request include/linux/nbd.h +RED_MAGIC2 0x170fc2a5 (any) mm/slab.c +BAYCOM_MAGIC 0x19730510 baycom_state drivers/net/baycom_epp.c +ISDN_X25IFACE_MAGIC 0x1e75a2b9 isdn_x25iface_proto_data + drivers/isdn/isdn_x25iface.h +ECP_MAGIC 0x21504345 cdkecpsig include/linux/cdk.h +LSOMAGIC 0x27091997 lso drivers/fc4/fc.c +LSMAGIC 0x2a3b4d2a ls drivers/fc4/fc.c +WANPIPE_MAGIC 0x414C4453 sdla_{dump,exec} include/linux/wanpipe.h +CS_CARD_MAGIC 0x43525553 cs_card sound/oss/cs46xx.c +LABELCL_MAGIC 0x4857434c labelcl_info_s include/asm/ia64/sn/labelcl.h +ISDN_ASYNC_MAGIC 0x49344C01 modem_info include/linux/isdn.h +CTC_ASYNC_MAGIC 0x49344C01 ctc_tty_info drivers/s390/net/ctctty.c +ISDN_NET_MAGIC 0x49344C02 isdn_net_local_s drivers/isdn/i4l/isdn_net_lib.h +SAVEKMSG_MAGIC2 0x4B4D5347 savekmsg arch/*/amiga/config.c +CS_STATE_MAGIC 0x4c4f4749 cs_state sound/oss/cs46xx.c +SLAB_C_MAGIC 0x4f17a36d kmem_cache mm/slab.c +COW_MAGIC 0x4f4f4f4d cow_header_v1 arch/um/drivers/ubd_user.c +I810_CARD_MAGIC 0x5072696E i810_card sound/oss/i810_audio.c +TRIDENT_CARD_MAGIC 0x5072696E trident_card sound/oss/trident.c +ROUTER_MAGIC 0x524d4157 wan_device [in wanrouter.h pre 3.9] +SAVEKMSG_MAGIC1 0x53415645 savekmsg arch/*/amiga/config.c +GDA_MAGIC 0x58464552 gda arch/mips/include/asm/sn/gda.h +RED_MAGIC1 0x5a2cf071 (any) mm/slab.c +EEPROM_MAGIC_VALUE 0x5ab478d2 lanai_dev drivers/atm/lanai.c +HDLCDRV_MAGIC 0x5ac6e778 hdlcdrv_state include/linux/hdlcdrv.h +PCXX_MAGIC 0x5c6df104 channel drivers/char/pcxx.h +KV_MAGIC 0x5f4b565f kernel_vars_s arch/mips/include/asm/sn/klkernvars.h +I810_STATE_MAGIC 0x63657373 i810_state sound/oss/i810_audio.c +TRIDENT_STATE_MAGIC 0x63657373 trient_state sound/oss/trident.c +M3_CARD_MAGIC 0x646e6f50 m3_card sound/oss/maestro3.c +FW_HEADER_MAGIC 0x65726F66 fw_header drivers/atm/fore200e.h +SLOT_MAGIC 0x67267321 slot drivers/hotplug/cpqphp.h +SLOT_MAGIC 0x67267322 slot drivers/hotplug/acpiphp.h +LO_MAGIC 0x68797548 nbd_device include/linux/nbd.h +OPROFILE_MAGIC 0x6f70726f super_block drivers/oprofile/oprofilefs.h +M3_STATE_MAGIC 0x734d724d m3_state sound/oss/maestro3.c +VMALLOC_MAGIC 0x87654320 snd_alloc_track sound/core/memory.c +KMALLOC_MAGIC 0x87654321 snd_alloc_track sound/core/memory.c +PWC_MAGIC 0x89DC10AB pwc_device drivers/usb/media/pwc.h +NBD_REPLY_MAGIC 0x96744668 nbd_reply include/linux/nbd.h +ENI155_MAGIC 0xa54b872d midway_eprom drivers/atm/eni.h +CODA_MAGIC 0xC0DAC0DA coda_file_info include/linux/coda_fs_i.h +DPMEM_MAGIC 0xc0ffee11 gdt_pci_sram drivers/scsi/gdth.h +YAM_MAGIC 0xF10A7654 yam_port drivers/net/hamradio/yam.c +CCB_MAGIC 0xf2691ad2 ccb drivers/scsi/ncr53c8xx.c +QUEUE_MAGIC_FREE 0xf7e1c9a3 queue_entry drivers/scsi/arm/queue.c +QUEUE_MAGIC_USED 0xf7e1cc33 queue_entry drivers/scsi/arm/queue.c +HTB_CMAGIC 0xFEFAFEF1 htb_class net/sched/sch_htb.c +NMI_MAGIC 0x48414d4d455201 nmi_s arch/mips/include/asm/sn/nmi.h + +请注意,在声音记忆管理中仍然有一些特殊的为每个驱动定义的魔术值。查看include/sound/sndmagic.h来获取他们完整的列表信息。很多OSS声音驱动拥有自己从声卡PCI ID构建的魔术值-他们也没有被列在这里。 + +IrDA子系统也使用了大量的自己的魔术值,查看include/net/irda/irda.h来获取他们完整的信息。 + +HFS是另外一个比较大的使用魔术值的文件系统-你可以在fs/hfs/hfs.h中找到他们。 diff --git a/Documentation/translations/zh_CN/process/magic-number.txt b/Documentation/translations/zh_CN/process/magic-number.txt deleted file mode 100644 index 7159cec04090..000000000000 --- a/Documentation/translations/zh_CN/process/magic-number.txt +++ /dev/null @@ -1,153 +0,0 @@ -Chinese translated version of Documentation/process/magic-number.rst - -If you have any comment or update to the content, please post to LKML directly. -However, if you have problem communicating in English you can also ask the -Chinese maintainer for help. Contact the Chinese maintainer, if this -translation is outdated or there is problem with translation. - -Chinese maintainer: Jia Wei Wei ---------------------------------------------------------------------- -Documentation/process/magic-number.rst的中文翻译 - -如果想评论或更新本文的内容,请直接发信到LKML。如果你使用英文交流有困难的话,也可 -以向中文版维护者求助。如果本翻译更新不及时或者翻译存在问题,请联系中文版维护者。 - -中文版维护者: 贾威威 Jia Wei Wei -中文版翻译者: 贾威威 Jia Wei Wei -中文版校译者: 贾威威 Jia Wei Wei - -以下为正文 ---------------------------------------------------------------------- -这个文件是有关当前使用的魔术值注册表。当你给一个结构添加了一个魔术值,你也应该把这个魔术值添加到这个文件,因为我们最好把用于各种结构的魔术值统一起来。 - -使用魔术值来保护内核数据结构是一个非常好的主意。这就允许你在运行期检查(a)一个结构是否已经被攻击,或者(b)你已经给一个例行程序通过了一个错误的结构。后一种情况特别地有用---特别是当你通过一个空指针指向结构体的时候。tty源码,例如,经常通过特定驱动使用这种方法并且反复地排列特定方面的结构。 - -使用魔术值的方法是在结构的开始处声明的,如下: - -struct tty_ldisc { - int magic; - ... -}; - -当你以后给内核添加增强功能的时候,请遵守这条规则!这样就会节省数不清的调试时间,特别是一些古怪的情况,例如,数组超出范围并且重新写了超出部分。遵守这个规则,‪这些情况可以被快速地,安全地避免。 - - Theodore Ts'o - 31 Mar 94 - -给当前的Linux 2.1.55添加魔术表。 - - Michael Chastain - - 22 Sep 1997 - -现在应该最新的Linux 2.1.112.因为在特性冻结期间,不能在2.2.x前改变任何东西。这些条目被数域所排序。 - - Krzysztof G.Baranowski - - 29 Jul 1998 - -更新魔术表到Linux 2.5.45。刚好越过特性冻结,但是有可能还会有一些新的魔术值在2.6.x之前融入到内核中。 - - Petr Baudis - - 03 Nov 2002 - -更新魔术表到Linux 2.5.74。 - - Fabian Frederick - - 09 Jul 2003 - -魔术名 地址 结构 所在文件 -=========================================================================== -PG_MAGIC 'P' pg_{read,write}_hdr include/linux/pg.h -CMAGIC 0x0111 user include/linux/a.out.h -MKISS_DRIVER_MAGIC 0x04bf mkiss_channel drivers/net/mkiss.h -HDLC_MAGIC 0x239e n_hdlc drivers/char/n_hdlc.c -APM_BIOS_MAGIC 0x4101 apm_user arch/x86/kernel/apm_32.c -CYCLADES_MAGIC 0x4359 cyclades_port include/linux/cyclades.h -DB_MAGIC 0x4442 fc_info drivers/net/iph5526_novram.c -DL_MAGIC 0x444d fc_info drivers/net/iph5526_novram.c -FASYNC_MAGIC 0x4601 fasync_struct include/linux/fs.h -FF_MAGIC 0x4646 fc_info drivers/net/iph5526_novram.c -ISICOM_MAGIC 0x4d54 isi_port include/linux/isicom.h -PTY_MAGIC 0x5001 drivers/char/pty.c -PPP_MAGIC 0x5002 ppp include/linux/if_pppvar.h -SERIAL_MAGIC 0x5301 async_struct include/linux/serial.h -SSTATE_MAGIC 0x5302 serial_state include/linux/serial.h -SLIP_MAGIC 0x5302 slip drivers/net/slip.h -STRIP_MAGIC 0x5303 strip drivers/net/strip.c -X25_ASY_MAGIC 0x5303 x25_asy drivers/net/x25_asy.h -SIXPACK_MAGIC 0x5304 sixpack drivers/net/hamradio/6pack.h -AX25_MAGIC 0x5316 ax_disp drivers/net/mkiss.h -TTY_MAGIC 0x5401 tty_struct include/linux/tty.h -MGSL_MAGIC 0x5401 mgsl_info drivers/char/synclink.c -TTY_DRIVER_MAGIC 0x5402 tty_driver include/linux/tty_driver.h -MGSLPC_MAGIC 0x5402 mgslpc_info drivers/char/pcmcia/synclink_cs.c -TTY_LDISC_MAGIC 0x5403 tty_ldisc include/linux/tty_ldisc.h -USB_SERIAL_MAGIC 0x6702 usb_serial drivers/usb/serial/usb-serial.h -FULL_DUPLEX_MAGIC 0x6969 drivers/net/ethernet/dec/tulip/de2104x.c -USB_BLUETOOTH_MAGIC 0x6d02 usb_bluetooth drivers/usb/class/bluetty.c -RFCOMM_TTY_MAGIC 0x6d02 net/bluetooth/rfcomm/tty.c -USB_SERIAL_PORT_MAGIC 0x7301 usb_serial_port drivers/usb/serial/usb-serial.h -CG_MAGIC 0x00090255 ufs_cylinder_group include/linux/ufs_fs.h -RPORT_MAGIC 0x00525001 r_port drivers/char/rocket_int.h -LSEMAGIC 0x05091998 lse drivers/fc4/fc.c -GDTIOCTL_MAGIC 0x06030f07 gdth_iowr_str drivers/scsi/gdth_ioctl.h -RIEBL_MAGIC 0x09051990 drivers/net/atarilance.c -NBD_REQUEST_MAGIC 0x12560953 nbd_request include/linux/nbd.h -RED_MAGIC2 0x170fc2a5 (any) mm/slab.c -BAYCOM_MAGIC 0x19730510 baycom_state drivers/net/baycom_epp.c -ISDN_X25IFACE_MAGIC 0x1e75a2b9 isdn_x25iface_proto_data - drivers/isdn/isdn_x25iface.h -ECP_MAGIC 0x21504345 cdkecpsig include/linux/cdk.h -LSOMAGIC 0x27091997 lso drivers/fc4/fc.c -LSMAGIC 0x2a3b4d2a ls drivers/fc4/fc.c -WANPIPE_MAGIC 0x414C4453 sdla_{dump,exec} include/linux/wanpipe.h -CS_CARD_MAGIC 0x43525553 cs_card sound/oss/cs46xx.c -LABELCL_MAGIC 0x4857434c labelcl_info_s include/asm/ia64/sn/labelcl.h -ISDN_ASYNC_MAGIC 0x49344C01 modem_info include/linux/isdn.h -CTC_ASYNC_MAGIC 0x49344C01 ctc_tty_info drivers/s390/net/ctctty.c -ISDN_NET_MAGIC 0x49344C02 isdn_net_local_s drivers/isdn/i4l/isdn_net_lib.h -SAVEKMSG_MAGIC2 0x4B4D5347 savekmsg arch/*/amiga/config.c -CS_STATE_MAGIC 0x4c4f4749 cs_state sound/oss/cs46xx.c -SLAB_C_MAGIC 0x4f17a36d kmem_cache mm/slab.c -COW_MAGIC 0x4f4f4f4d cow_header_v1 arch/um/drivers/ubd_user.c -I810_CARD_MAGIC 0x5072696E i810_card sound/oss/i810_audio.c -TRIDENT_CARD_MAGIC 0x5072696E trident_card sound/oss/trident.c -ROUTER_MAGIC 0x524d4157 wan_device [in wanrouter.h pre 3.9] -SAVEKMSG_MAGIC1 0x53415645 savekmsg arch/*/amiga/config.c -GDA_MAGIC 0x58464552 gda arch/mips/include/asm/sn/gda.h -RED_MAGIC1 0x5a2cf071 (any) mm/slab.c -EEPROM_MAGIC_VALUE 0x5ab478d2 lanai_dev drivers/atm/lanai.c -HDLCDRV_MAGIC 0x5ac6e778 hdlcdrv_state include/linux/hdlcdrv.h -PCXX_MAGIC 0x5c6df104 channel drivers/char/pcxx.h -KV_MAGIC 0x5f4b565f kernel_vars_s arch/mips/include/asm/sn/klkernvars.h -I810_STATE_MAGIC 0x63657373 i810_state sound/oss/i810_audio.c -TRIDENT_STATE_MAGIC 0x63657373 trient_state sound/oss/trident.c -M3_CARD_MAGIC 0x646e6f50 m3_card sound/oss/maestro3.c -FW_HEADER_MAGIC 0x65726F66 fw_header drivers/atm/fore200e.h -SLOT_MAGIC 0x67267321 slot drivers/hotplug/cpqphp.h -SLOT_MAGIC 0x67267322 slot drivers/hotplug/acpiphp.h -LO_MAGIC 0x68797548 nbd_device include/linux/nbd.h -OPROFILE_MAGIC 0x6f70726f super_block drivers/oprofile/oprofilefs.h -M3_STATE_MAGIC 0x734d724d m3_state sound/oss/maestro3.c -VMALLOC_MAGIC 0x87654320 snd_alloc_track sound/core/memory.c -KMALLOC_MAGIC 0x87654321 snd_alloc_track sound/core/memory.c -PWC_MAGIC 0x89DC10AB pwc_device drivers/usb/media/pwc.h -NBD_REPLY_MAGIC 0x96744668 nbd_reply include/linux/nbd.h -ENI155_MAGIC 0xa54b872d midway_eprom drivers/atm/eni.h -CODA_MAGIC 0xC0DAC0DA coda_file_info include/linux/coda_fs_i.h -DPMEM_MAGIC 0xc0ffee11 gdt_pci_sram drivers/scsi/gdth.h -YAM_MAGIC 0xF10A7654 yam_port drivers/net/hamradio/yam.c -CCB_MAGIC 0xf2691ad2 ccb drivers/scsi/ncr53c8xx.c -QUEUE_MAGIC_FREE 0xf7e1c9a3 queue_entry drivers/scsi/arm/queue.c -QUEUE_MAGIC_USED 0xf7e1cc33 queue_entry drivers/scsi/arm/queue.c -HTB_CMAGIC 0xFEFAFEF1 htb_class net/sched/sch_htb.c -NMI_MAGIC 0x48414d4d455201 nmi_s arch/mips/include/asm/sn/nmi.h - -请注意,在声音记忆管理中仍然有一些特殊的为每个驱动定义的魔术值。查看include/sound/sndmagic.h来获取他们完整的列表信息。很多OSS声音驱动拥有自己从声卡PCI ID构建的魔术值-他们也没有被列在这里。 - -IrDA子系统也使用了大量的自己的魔术值,查看include/net/irda/irda.h来获取他们完整的信息。 - -HFS是另外一个比较大的使用魔术值的文件系统-你可以在fs/hfs/hfs.h中找到他们。 -- cgit v1.2.3 From 4cc4e49a416459c08da456ef7802fb090d2404ae Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:48 +0800 Subject: docs/zh_CN: format the magic-number doc as rst to Make it readble in html etc doc making. And fix the wrong translation for 'number' in form. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Jia Wei Wei Cc: Li Zefan Cc: Shawn Guo Cc: Fengguang Wu Cc: Coly Li Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- .../translations/zh_CN/process/magic-number.rst | 210 ++++++++++----------- 1 file changed, 104 insertions(+), 106 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/magic-number.rst b/Documentation/translations/zh_CN/process/magic-number.rst index 7159cec04090..15c592518194 100644 --- a/Documentation/translations/zh_CN/process/magic-number.rst +++ b/Documentation/translations/zh_CN/process/magic-number.rst @@ -1,33 +1,29 @@ -Chinese translated version of Documentation/process/magic-number.rst +.. _cn_magicnumbers: -If you have any comment or update to the content, please post to LKML directly. -However, if you have problem communicating in English you can also ask the -Chinese maintainer for help. Contact the Chinese maintainer, if this -translation is outdated or there is problem with translation. +.. include:: ../disclaimer-zh_CN.rst -Chinese maintainer: Jia Wei Wei ---------------------------------------------------------------------- -Documentation/process/magic-number.rst的中文翻译 +:Original: :ref:`Documentation/process/magic-number.rst ` 如果想评论或更新本文的内容,请直接发信到LKML。如果你使用英文交流有困难的话,也可 -以向中文版维护者求助。如果本翻译更新不及时或者翻译存在问题,请联系中文版维护者。 +以向中文版维护者求助。如果本翻译更新不及时或者翻译存在问题,请联系中文版维护者:: -中文版维护者: 贾威威 Jia Wei Wei -中文版翻译者: 贾威威 Jia Wei Wei -中文版校译者: 贾威威 Jia Wei Wei + 中文版维护者: 贾威威 Jia Wei Wei + 中文版翻译者: 贾威威 Jia Wei Wei + 中文版校译者: 贾威威 Jia Wei Wei + +Linux 魔术数 +============ -以下为正文 ---------------------------------------------------------------------- 这个文件是有关当前使用的魔术值注册表。当你给一个结构添加了一个魔术值,你也应该把这个魔术值添加到这个文件,因为我们最好把用于各种结构的魔术值统一起来。 使用魔术值来保护内核数据结构是一个非常好的主意。这就允许你在运行期检查(a)一个结构是否已经被攻击,或者(b)你已经给一个例行程序通过了一个错误的结构。后一种情况特别地有用---特别是当你通过一个空指针指向结构体的时候。tty源码,例如,经常通过特定驱动使用这种方法并且反复地排列特定方面的结构。 -使用魔术值的方法是在结构的开始处声明的,如下: +使用魔术值的方法是在结构的开始处声明的,如下:: -struct tty_ldisc { - int magic; - ... -}; + struct tty_ldisc { + int magic; + ... + }; 当你以后给内核添加增强功能的时候,请遵守这条规则!这样就会节省数不清的调试时间,特别是一些古怪的情况,例如,数组超出范围并且重新写了超出部分。遵守这个规则,‪这些情况可以被快速地,安全地避免。 @@ -58,93 +54,95 @@ struct tty_ldisc { 09 Jul 2003 -魔术名 地址 结构 所在文件 -=========================================================================== -PG_MAGIC 'P' pg_{read,write}_hdr include/linux/pg.h -CMAGIC 0x0111 user include/linux/a.out.h -MKISS_DRIVER_MAGIC 0x04bf mkiss_channel drivers/net/mkiss.h -HDLC_MAGIC 0x239e n_hdlc drivers/char/n_hdlc.c -APM_BIOS_MAGIC 0x4101 apm_user arch/x86/kernel/apm_32.c -CYCLADES_MAGIC 0x4359 cyclades_port include/linux/cyclades.h -DB_MAGIC 0x4442 fc_info drivers/net/iph5526_novram.c -DL_MAGIC 0x444d fc_info drivers/net/iph5526_novram.c -FASYNC_MAGIC 0x4601 fasync_struct include/linux/fs.h -FF_MAGIC 0x4646 fc_info drivers/net/iph5526_novram.c -ISICOM_MAGIC 0x4d54 isi_port include/linux/isicom.h -PTY_MAGIC 0x5001 drivers/char/pty.c -PPP_MAGIC 0x5002 ppp include/linux/if_pppvar.h -SERIAL_MAGIC 0x5301 async_struct include/linux/serial.h -SSTATE_MAGIC 0x5302 serial_state include/linux/serial.h -SLIP_MAGIC 0x5302 slip drivers/net/slip.h -STRIP_MAGIC 0x5303 strip drivers/net/strip.c -X25_ASY_MAGIC 0x5303 x25_asy drivers/net/x25_asy.h -SIXPACK_MAGIC 0x5304 sixpack drivers/net/hamradio/6pack.h -AX25_MAGIC 0x5316 ax_disp drivers/net/mkiss.h -TTY_MAGIC 0x5401 tty_struct include/linux/tty.h -MGSL_MAGIC 0x5401 mgsl_info drivers/char/synclink.c -TTY_DRIVER_MAGIC 0x5402 tty_driver include/linux/tty_driver.h -MGSLPC_MAGIC 0x5402 mgslpc_info drivers/char/pcmcia/synclink_cs.c -TTY_LDISC_MAGIC 0x5403 tty_ldisc include/linux/tty_ldisc.h -USB_SERIAL_MAGIC 0x6702 usb_serial drivers/usb/serial/usb-serial.h -FULL_DUPLEX_MAGIC 0x6969 drivers/net/ethernet/dec/tulip/de2104x.c -USB_BLUETOOTH_MAGIC 0x6d02 usb_bluetooth drivers/usb/class/bluetty.c -RFCOMM_TTY_MAGIC 0x6d02 net/bluetooth/rfcomm/tty.c -USB_SERIAL_PORT_MAGIC 0x7301 usb_serial_port drivers/usb/serial/usb-serial.h -CG_MAGIC 0x00090255 ufs_cylinder_group include/linux/ufs_fs.h -RPORT_MAGIC 0x00525001 r_port drivers/char/rocket_int.h -LSEMAGIC 0x05091998 lse drivers/fc4/fc.c -GDTIOCTL_MAGIC 0x06030f07 gdth_iowr_str drivers/scsi/gdth_ioctl.h -RIEBL_MAGIC 0x09051990 drivers/net/atarilance.c -NBD_REQUEST_MAGIC 0x12560953 nbd_request include/linux/nbd.h -RED_MAGIC2 0x170fc2a5 (any) mm/slab.c -BAYCOM_MAGIC 0x19730510 baycom_state drivers/net/baycom_epp.c -ISDN_X25IFACE_MAGIC 0x1e75a2b9 isdn_x25iface_proto_data - drivers/isdn/isdn_x25iface.h -ECP_MAGIC 0x21504345 cdkecpsig include/linux/cdk.h -LSOMAGIC 0x27091997 lso drivers/fc4/fc.c -LSMAGIC 0x2a3b4d2a ls drivers/fc4/fc.c -WANPIPE_MAGIC 0x414C4453 sdla_{dump,exec} include/linux/wanpipe.h -CS_CARD_MAGIC 0x43525553 cs_card sound/oss/cs46xx.c -LABELCL_MAGIC 0x4857434c labelcl_info_s include/asm/ia64/sn/labelcl.h -ISDN_ASYNC_MAGIC 0x49344C01 modem_info include/linux/isdn.h -CTC_ASYNC_MAGIC 0x49344C01 ctc_tty_info drivers/s390/net/ctctty.c -ISDN_NET_MAGIC 0x49344C02 isdn_net_local_s drivers/isdn/i4l/isdn_net_lib.h -SAVEKMSG_MAGIC2 0x4B4D5347 savekmsg arch/*/amiga/config.c -CS_STATE_MAGIC 0x4c4f4749 cs_state sound/oss/cs46xx.c -SLAB_C_MAGIC 0x4f17a36d kmem_cache mm/slab.c -COW_MAGIC 0x4f4f4f4d cow_header_v1 arch/um/drivers/ubd_user.c -I810_CARD_MAGIC 0x5072696E i810_card sound/oss/i810_audio.c -TRIDENT_CARD_MAGIC 0x5072696E trident_card sound/oss/trident.c -ROUTER_MAGIC 0x524d4157 wan_device [in wanrouter.h pre 3.9] -SAVEKMSG_MAGIC1 0x53415645 savekmsg arch/*/amiga/config.c -GDA_MAGIC 0x58464552 gda arch/mips/include/asm/sn/gda.h -RED_MAGIC1 0x5a2cf071 (any) mm/slab.c -EEPROM_MAGIC_VALUE 0x5ab478d2 lanai_dev drivers/atm/lanai.c -HDLCDRV_MAGIC 0x5ac6e778 hdlcdrv_state include/linux/hdlcdrv.h -PCXX_MAGIC 0x5c6df104 channel drivers/char/pcxx.h -KV_MAGIC 0x5f4b565f kernel_vars_s arch/mips/include/asm/sn/klkernvars.h -I810_STATE_MAGIC 0x63657373 i810_state sound/oss/i810_audio.c -TRIDENT_STATE_MAGIC 0x63657373 trient_state sound/oss/trident.c -M3_CARD_MAGIC 0x646e6f50 m3_card sound/oss/maestro3.c -FW_HEADER_MAGIC 0x65726F66 fw_header drivers/atm/fore200e.h -SLOT_MAGIC 0x67267321 slot drivers/hotplug/cpqphp.h -SLOT_MAGIC 0x67267322 slot drivers/hotplug/acpiphp.h -LO_MAGIC 0x68797548 nbd_device include/linux/nbd.h -OPROFILE_MAGIC 0x6f70726f super_block drivers/oprofile/oprofilefs.h -M3_STATE_MAGIC 0x734d724d m3_state sound/oss/maestro3.c -VMALLOC_MAGIC 0x87654320 snd_alloc_track sound/core/memory.c -KMALLOC_MAGIC 0x87654321 snd_alloc_track sound/core/memory.c -PWC_MAGIC 0x89DC10AB pwc_device drivers/usb/media/pwc.h -NBD_REPLY_MAGIC 0x96744668 nbd_reply include/linux/nbd.h -ENI155_MAGIC 0xa54b872d midway_eprom drivers/atm/eni.h -CODA_MAGIC 0xC0DAC0DA coda_file_info include/linux/coda_fs_i.h -DPMEM_MAGIC 0xc0ffee11 gdt_pci_sram drivers/scsi/gdth.h -YAM_MAGIC 0xF10A7654 yam_port drivers/net/hamradio/yam.c -CCB_MAGIC 0xf2691ad2 ccb drivers/scsi/ncr53c8xx.c -QUEUE_MAGIC_FREE 0xf7e1c9a3 queue_entry drivers/scsi/arm/queue.c -QUEUE_MAGIC_USED 0xf7e1cc33 queue_entry drivers/scsi/arm/queue.c -HTB_CMAGIC 0xFEFAFEF1 htb_class net/sched/sch_htb.c -NMI_MAGIC 0x48414d4d455201 nmi_s arch/mips/include/asm/sn/nmi.h +===================== ================ ======================== ========================================== +魔术数名 数字 结构 文件 +===================== ================ ======================== ========================================== +PG_MAGIC 'P' pg_{read,write}_hdr ``include/linux/pg.h`` +CMAGIC 0x0111 user ``include/linux/a.out.h`` +MKISS_DRIVER_MAGIC 0x04bf mkiss_channel ``drivers/net/mkiss.h`` +HDLC_MAGIC 0x239e n_hdlc ``drivers/char/n_hdlc.c`` +APM_BIOS_MAGIC 0x4101 apm_user ``arch/x86/kernel/apm_32.c`` +CYCLADES_MAGIC 0x4359 cyclades_port ``include/linux/cyclades.h`` +DB_MAGIC 0x4442 fc_info ``drivers/net/iph5526_novram.c`` +DL_MAGIC 0x444d fc_info ``drivers/net/iph5526_novram.c`` +FASYNC_MAGIC 0x4601 fasync_struct ``include/linux/fs.h`` +FF_MAGIC 0x4646 fc_info ``drivers/net/iph5526_novram.c`` +ISICOM_MAGIC 0x4d54 isi_port ``include/linux/isicom.h`` +PTY_MAGIC 0x5001 ``drivers/char/pty.c`` +PPP_MAGIC 0x5002 ppp ``include/linux/if_pppvar.h`` +SERIAL_MAGIC 0x5301 async_struct ``include/linux/serial.h`` +SSTATE_MAGIC 0x5302 serial_state ``include/linux/serial.h`` +SLIP_MAGIC 0x5302 slip ``drivers/net/slip.h`` +STRIP_MAGIC 0x5303 strip ``drivers/net/strip.c`` +X25_ASY_MAGIC 0x5303 x25_asy ``drivers/net/x25_asy.h`` +SIXPACK_MAGIC 0x5304 sixpack ``drivers/net/hamradio/6pack.h`` +AX25_MAGIC 0x5316 ax_disp ``drivers/net/mkiss.h`` +TTY_MAGIC 0x5401 tty_struct ``include/linux/tty.h`` +MGSL_MAGIC 0x5401 mgsl_info ``drivers/char/synclink.c`` +TTY_DRIVER_MAGIC 0x5402 tty_driver ``include/linux/tty_driver.h`` +MGSLPC_MAGIC 0x5402 mgslpc_info ``drivers/char/pcmcia/synclink_cs.c`` +TTY_LDISC_MAGIC 0x5403 tty_ldisc ``include/linux/tty_ldisc.h`` +USB_SERIAL_MAGIC 0x6702 usb_serial ``drivers/usb/serial/usb-serial.h`` +FULL_DUPLEX_MAGIC 0x6969 ``drivers/net/ethernet/dec/tulip/de2104x.c`` +USB_BLUETOOTH_MAGIC 0x6d02 usb_bluetooth ``drivers/usb/class/bluetty.c`` +RFCOMM_TTY_MAGIC 0x6d02 ``net/bluetooth/rfcomm/tty.c`` +USB_SERIAL_PORT_MAGIC 0x7301 usb_serial_port ``drivers/usb/serial/usb-serial.h`` +CG_MAGIC 0x00090255 ufs_cylinder_group ``include/linux/ufs_fs.h`` +RPORT_MAGIC 0x00525001 r_port ``drivers/char/rocket_int.h`` +LSEMAGIC 0x05091998 lse ``drivers/fc4/fc.c`` +GDTIOCTL_MAGIC 0x06030f07 gdth_iowr_str ``drivers/scsi/gdth_ioctl.h`` +RIEBL_MAGIC 0x09051990 ``drivers/net/atarilance.c`` +NBD_REQUEST_MAGIC 0x12560953 nbd_request ``include/linux/nbd.h`` +RED_MAGIC2 0x170fc2a5 (any) ``mm/slab.c`` +BAYCOM_MAGIC 0x19730510 baycom_state ``drivers/net/baycom_epp.c`` +ISDN_X25IFACE_MAGIC 0x1e75a2b9 isdn_x25iface_proto_data ``drivers/isdn/isdn_x25iface.h`` +ECP_MAGIC 0x21504345 cdkecpsig ``include/linux/cdk.h`` +LSOMAGIC 0x27091997 lso ``drivers/fc4/fc.c`` +LSMAGIC 0x2a3b4d2a ls ``drivers/fc4/fc.c`` +WANPIPE_MAGIC 0x414C4453 sdla_{dump,exec} ``include/linux/wanpipe.h`` +CS_CARD_MAGIC 0x43525553 cs_card ``sound/oss/cs46xx.c`` +LABELCL_MAGIC 0x4857434c labelcl_info_s ``include/asm/ia64/sn/labelcl.h`` +ISDN_ASYNC_MAGIC 0x49344C01 modem_info ``include/linux/isdn.h`` +CTC_ASYNC_MAGIC 0x49344C01 ctc_tty_info ``drivers/s390/net/ctctty.c`` +ISDN_NET_MAGIC 0x49344C02 isdn_net_local_s ``drivers/isdn/i4l/isdn_net_lib.h`` +SAVEKMSG_MAGIC2 0x4B4D5347 savekmsg ``arch/*/amiga/config.c`` +CS_STATE_MAGIC 0x4c4f4749 cs_state ``sound/oss/cs46xx.c`` +SLAB_C_MAGIC 0x4f17a36d kmem_cache ``mm/slab.c`` +COW_MAGIC 0x4f4f4f4d cow_header_v1 ``arch/um/drivers/ubd_user.c`` +I810_CARD_MAGIC 0x5072696E i810_card ``sound/oss/i810_audio.c`` +TRIDENT_CARD_MAGIC 0x5072696E trident_card ``sound/oss/trident.c`` +ROUTER_MAGIC 0x524d4157 wan_device [in ``wanrouter.h`` pre 3.9] +SAVEKMSG_MAGIC1 0x53415645 savekmsg ``arch/*/amiga/config.c`` +GDA_MAGIC 0x58464552 gda ``arch/mips/include/asm/sn/gda.h`` +RED_MAGIC1 0x5a2cf071 (any) ``mm/slab.c`` +EEPROM_MAGIC_VALUE 0x5ab478d2 lanai_dev ``drivers/atm/lanai.c`` +HDLCDRV_MAGIC 0x5ac6e778 hdlcdrv_state ``include/linux/hdlcdrv.h`` +PCXX_MAGIC 0x5c6df104 channel ``drivers/char/pcxx.h`` +KV_MAGIC 0x5f4b565f kernel_vars_s ``arch/mips/include/asm/sn/klkernvars.h`` +I810_STATE_MAGIC 0x63657373 i810_state ``sound/oss/i810_audio.c`` +TRIDENT_STATE_MAGIC 0x63657373 trient_state ``sound/oss/trident.c`` +M3_CARD_MAGIC 0x646e6f50 m3_card ``sound/oss/maestro3.c`` +FW_HEADER_MAGIC 0x65726F66 fw_header ``drivers/atm/fore200e.h`` +SLOT_MAGIC 0x67267321 slot ``drivers/hotplug/cpqphp.h`` +SLOT_MAGIC 0x67267322 slot ``drivers/hotplug/acpiphp.h`` +LO_MAGIC 0x68797548 nbd_device ``include/linux/nbd.h`` +OPROFILE_MAGIC 0x6f70726f super_block ``drivers/oprofile/oprofilefs.h`` +M3_STATE_MAGIC 0x734d724d m3_state ``sound/oss/maestro3.c`` +VMALLOC_MAGIC 0x87654320 snd_alloc_track ``sound/core/memory.c`` +KMALLOC_MAGIC 0x87654321 snd_alloc_track ``sound/core/memory.c`` +PWC_MAGIC 0x89DC10AB pwc_device ``drivers/usb/media/pwc.h`` +NBD_REPLY_MAGIC 0x96744668 nbd_reply ``include/linux/nbd.h`` +ENI155_MAGIC 0xa54b872d midway_eprom ``drivers/atm/eni.h`` +CODA_MAGIC 0xC0DAC0DA coda_file_info ``fs/coda/coda_fs_i.h`` +DPMEM_MAGIC 0xc0ffee11 gdt_pci_sram ``drivers/scsi/gdth.h`` +YAM_MAGIC 0xF10A7654 yam_port ``drivers/net/hamradio/yam.c`` +CCB_MAGIC 0xf2691ad2 ccb ``drivers/scsi/ncr53c8xx.c`` +QUEUE_MAGIC_FREE 0xf7e1c9a3 queue_entry ``drivers/scsi/arm/queue.c`` +QUEUE_MAGIC_USED 0xf7e1cc33 queue_entry ``drivers/scsi/arm/queue.c`` +HTB_CMAGIC 0xFEFAFEF1 htb_class ``net/sched/sch_htb.c`` +NMI_MAGIC 0x48414d4d455201 nmi_s ``arch/mips/include/asm/sn/nmi.h`` +===================== ================ ======================== ========================================== + 请注意,在声音记忆管理中仍然有一些特殊的为每个驱动定义的魔术值。查看include/sound/sndmagic.h来获取他们完整的列表信息。很多OSS声音驱动拥有自己从声卡PCI ID构建的魔术值-他们也没有被列在这里。 -- cgit v1.2.3 From 2f3dea95661c24e352e3265a85c0c22d9bda92c7 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:49 +0800 Subject: docs/zh_CN: rename stable_api_nonsense.txt as stable-api-nonsense.rst make it available in html etc doc making Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: TripleX Chung Cc: Li Zefan Cc: Shawn Guo Cc: Fengguang Wu Cc: Coly Li Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- .../zh_CN/process/stable-api-nonsense.rst | 157 +++++++++++++++++++++ .../zh_CN/process/stable_api_nonsense.txt | 157 --------------------- 2 files changed, 157 insertions(+), 157 deletions(-) create mode 100644 Documentation/translations/zh_CN/process/stable-api-nonsense.rst delete mode 100644 Documentation/translations/zh_CN/process/stable_api_nonsense.txt (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/stable-api-nonsense.rst b/Documentation/translations/zh_CN/process/stable-api-nonsense.rst new file mode 100644 index 000000000000..a2b27fab382c --- /dev/null +++ b/Documentation/translations/zh_CN/process/stable-api-nonsense.rst @@ -0,0 +1,157 @@ +Chinese translated version of Documentation/process/stable-api-nonsense.rst + +If you have any comment or update to the content, please contact the +original document maintainer directly. However, if you have problem +communicating in English you can also ask the Chinese maintainer for help. +Contact the Chinese maintainer, if this translation is outdated or there +is problem with translation. + +Maintainer: Greg Kroah-Hartman +Chinese maintainer: TripleX Chung +--------------------------------------------------------------------- +Documentation/process/stable-api-nonsense.rst 的中文翻译 + +如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 +交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 +译存在问题,请联系中文版维护者。 + +英文版维护者: Greg Kroah-Hartman +中文版维护者: 钟宇 TripleX Chung +中文版翻译者: 钟宇 TripleX Chung +中文版校译者: 李阳 Li Yang +以下为正文 +--------------------------------------------------------------------- + +写作本文档的目的,是为了解释为什么Linux既没有二进制内核接口,也没有稳定 +的内核接口。这里所说的内核接口,是指内核里的接口,而不是内核和用户空间 +的接口。内核到用户空间的接口,是提供给应用程序使用的系统调用,系统调用 +在历史上几乎没有过变化,将来也不会有变化。我有一些老应用程序是在0.9版本 +或者更早版本的内核上编译的,在使用2.6版本内核的Linux发布上依然用得很好 +。用户和应用程序作者可以将这个接口看成是稳定的。 + + +执行纲要 +-------- + +你也许以为自己想要稳定的内核接口,但是你不清楚你要的实际上不是它。你需 +要的其实是稳定的驱动程序,而你只有将驱动程序放到公版内核的源代码树里, +才有可能达到这个目的。而且这样做还有很多其它好处,正是因为这些好处使得 +Linux能成为强壮,稳定,成熟的操作系统,这也是你最开始选择Linux的原因。 + + +入门 +----- + +只有那些写驱动程序的“怪人”才会担心内核接口的改变,对广大用户来说,既 +看不到内核接口,也不需要去关心它。 + +首先,我不打算讨论关于任何非GPL许可的内核驱动的法律问题,这些非GPL许可 +的驱动程序包括不公开源代码,隐藏源代码,二进制或者是用源代码包装,或者 +是其它任何形式的不能以GPL许可公开源代码的驱动程序。如果有法律问题,请咨 +询律师,我只是一个程序员,所以我只打算探讨技术问题(不是小看法律问题, +法律问题很实际,并且需要一直关注)。 + +既然只谈技术问题,我们就有了下面两个主题:二进制内核接口和稳定的内核源 +代码接口。这两个问题是互相关联的,让我们先解决掉二进制接口的问题。 + + +二进制内核接口 +-------------- +假如我们有一个稳定的内核源代码接口,那么自然而然的,我们就拥有了稳定的 +二进制接口,是这样的吗?错。让我们看看关于Linux内核的几点事实: + - 取决于所用的C编译器的版本,不同的内核数据结构里的结构体的对齐方 +式会有差别,代码中不同函数的表现形式也不一样(函数是不是被inline编译取 +决于编译器行为)。不同的函数的表现形式并不重要,但是数据结构内部的对齐 +方式很关键。 + - 取决于内核的配置选项,不同的选项会让内核的很多东西发生改变: + - 同一个结构体可能包含不同的成员变量 + - 有的函数可能根本不会被实现(比如编译的时候没有选择SMP支持 +,一些锁函数就会被定义成空函数)。 + - 内核使用的内存会以不同的方式对齐,这取决于不同的内核配置选 +项。 + - Linux可以在很多的不同体系结构的处理器上运行。在某个体系结构上编 +译好的二进制驱动程序,不可能在另外一个体系结构上正确的运行。 + +对于一个特定的内核,满足这些条件并不难,使用同一个C编译器和同样的内核配 +置选项来编译驱动程序模块就可以了。这对于给一个特定Linux发布的特定版本提 +供驱动程序,是完全可以满足需求的。但是如果你要给不同发布的不同版本都发 +布一个驱动程序,就需要在每个发布上用不同的内核设置参数都编译一次内核, +这简直跟噩梦一样。而且还要注意到,每个Linux发布还提供不同的Linux内核, +这些内核都针对不同的硬件类型进行了优化(有很多种不同的处理器,还有不同 +的内核设置选项)。所以每发布一次驱动程序,都需要提供很多不同版本的内核 +模块。 + +相信我,如果你真的要采取这种发布方式,一定会慢慢疯掉,我很久以前就有过 +深刻的教训... + + +稳定的内核源代码接口 +-------------------- + +如果有人不将他的内核驱动程序,放入公版内核的源代码树,而又想让驱动程序 +一直保持在最新的内核中可用,那么这个话题将会变得没完没了。 + 内核开发是持续而且快节奏的,从来都不会慢下来。内核开发人员在当前接口中 +找到bug,或者找到更好的实现方式。一旦发现这些,他们就很快会去修改当前的 +接口。修改接口意味着,函数名可能会改变,结构体可能被扩充或者删减,函数 +的参数也可能发生改变。一旦接口被修改,内核中使用这些接口的地方需要同时 +修正,这样才能保证所有的东西继续工作。 + +举一个例子,内核的USB驱动程序接口在USB子系统的整个生命周期中,至少经历 +了三次重写。这些重写解决以下问题: + - 把数据流从同步模式改成非同步模式,这个改动减少了一些驱动程序的 +复杂度,提高了所有USB驱动程序的吞吐率,这样几乎所有的USB设备都能以最大 +速率工作了。 + - 修改了USB核心代码中为USB驱动分配数据包内存的方式,所有的驱动都 +需要提供更多的参数给USB核心,以修正了很多已经被记录在案的死锁。 + +这和一些封闭源代码的操作系统形成鲜明的对比,在那些操作系统上,不得不额 +外的维护旧的USB接口。这导致了一个可能性,新的开发者依然会不小心使用旧的 +接口,以不恰当的方式编写代码,进而影响到操作系统的稳定性。 + 在上面的例子中,所有的开发者都同意这些重要的改动,在这样的情况下修改代 +价很低。如果Linux保持一个稳定的内核源代码接口,那么就得创建一个新的接口 +;旧的,有问题的接口必须一直维护,给Linux USB开发者带来额外的工作。既然 +所有的Linux USB驱动的作者都是利用自己的时间工作,那么要求他们去做毫无意 +义的免费额外工作,是不可能的。 + 安全问题对Linux来说十分重要。一个安全问题被发现,就会在短时间内得到修 +正。在很多情况下,这将导致Linux内核中的一些接口被重写,以从根本上避免安 +全问题。一旦接口被重写,所有使用这些接口的驱动程序,必须同时得到修正, +以确定安全问题已经得到修复并且不可能在未来还有同样的安全问题。如果内核 +内部接口不允许改变,那么就不可能修复这样的安全问题,也不可能确认这样的 +安全问题以后不会发生。 +开发者一直在清理内核接口。如果一个接口没有人在使用了,它就会被删除。这 +样可以确保内核尽可能的小,而且所有潜在的接口都会得到尽可能完整的测试 +(没有人使用的接口是不可能得到良好的测试的)。 + + +要做什么 +------- + +如果你写了一个Linux内核驱动,但是它还不在Linux源代码树里,作为一个开发 +者,你应该怎么做?为每个发布的每个版本提供一个二进制驱动,那简直是一个 +噩梦,要跟上永远处于变化之中的内核接口,也是一件辛苦活。 +很简单,让你的驱动进入内核源代码树(要记得我们在谈论的是以GPL许可发行 +的驱动,如果你的代码不符合GPL,那么祝你好运,你只能自己解决这个问题了, +你这个吸血鬼<把Andrew和Linus对吸血鬼的定义链接到这里>)。当你的代码加入 +公版内核源代码树之后,如果一个内核接口改变,你的驱动会直接被修改接口的 +那个人修改。保证你的驱动永远都可以编译通过,并且一直工作,你几乎不需要 +做什么事情。 + +把驱动放到内核源代码树里会有很多的好处: + - 驱动的质量会提升,而维护成本(对原始作者来说)会下降。 + - 其他人会给驱动添加新特性。 + - 其他人会找到驱动中的bug并修复。 + - 其他人会在驱动中找到性能优化的机会。 + - 当外部的接口的改变需要修改驱动程序的时候,其他人会修改驱动程序 +。 + - 不需要联系任何发行商,这个驱动会自动的随着所有的Linux发布一起发 +布。 + +和别的操作系统相比,Linux为更多不同的设备提供现成的驱动,而且能在更多不 +同体系结构的处理器上支持这些设备。这个经过考验的开发模式,必然是错不了 +的 :) + +------------- +感谢 Randy Dunlap, Andrew Morton, David Brownell, Hanna Linder, +Robert Love, and Nishanth Aravamudan 对于本文档早期版本的评审和建议。 + +英文版维护者: Greg Kroah-Hartman diff --git a/Documentation/translations/zh_CN/process/stable_api_nonsense.txt b/Documentation/translations/zh_CN/process/stable_api_nonsense.txt deleted file mode 100644 index a2b27fab382c..000000000000 --- a/Documentation/translations/zh_CN/process/stable_api_nonsense.txt +++ /dev/null @@ -1,157 +0,0 @@ -Chinese translated version of Documentation/process/stable-api-nonsense.rst - -If you have any comment or update to the content, please contact the -original document maintainer directly. However, if you have problem -communicating in English you can also ask the Chinese maintainer for help. -Contact the Chinese maintainer, if this translation is outdated or there -is problem with translation. - -Maintainer: Greg Kroah-Hartman -Chinese maintainer: TripleX Chung ---------------------------------------------------------------------- -Documentation/process/stable-api-nonsense.rst 的中文翻译 - -如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 -交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者。 - -英文版维护者: Greg Kroah-Hartman -中文版维护者: 钟宇 TripleX Chung -中文版翻译者: 钟宇 TripleX Chung -中文版校译者: 李阳 Li Yang -以下为正文 ---------------------------------------------------------------------- - -写作本文档的目的,是为了解释为什么Linux既没有二进制内核接口,也没有稳定 -的内核接口。这里所说的内核接口,是指内核里的接口,而不是内核和用户空间 -的接口。内核到用户空间的接口,是提供给应用程序使用的系统调用,系统调用 -在历史上几乎没有过变化,将来也不会有变化。我有一些老应用程序是在0.9版本 -或者更早版本的内核上编译的,在使用2.6版本内核的Linux发布上依然用得很好 -。用户和应用程序作者可以将这个接口看成是稳定的。 - - -执行纲要 --------- - -你也许以为自己想要稳定的内核接口,但是你不清楚你要的实际上不是它。你需 -要的其实是稳定的驱动程序,而你只有将驱动程序放到公版内核的源代码树里, -才有可能达到这个目的。而且这样做还有很多其它好处,正是因为这些好处使得 -Linux能成为强壮,稳定,成熟的操作系统,这也是你最开始选择Linux的原因。 - - -入门 ------ - -只有那些写驱动程序的“怪人”才会担心内核接口的改变,对广大用户来说,既 -看不到内核接口,也不需要去关心它。 - -首先,我不打算讨论关于任何非GPL许可的内核驱动的法律问题,这些非GPL许可 -的驱动程序包括不公开源代码,隐藏源代码,二进制或者是用源代码包装,或者 -是其它任何形式的不能以GPL许可公开源代码的驱动程序。如果有法律问题,请咨 -询律师,我只是一个程序员,所以我只打算探讨技术问题(不是小看法律问题, -法律问题很实际,并且需要一直关注)。 - -既然只谈技术问题,我们就有了下面两个主题:二进制内核接口和稳定的内核源 -代码接口。这两个问题是互相关联的,让我们先解决掉二进制接口的问题。 - - -二进制内核接口 --------------- -假如我们有一个稳定的内核源代码接口,那么自然而然的,我们就拥有了稳定的 -二进制接口,是这样的吗?错。让我们看看关于Linux内核的几点事实: - - 取决于所用的C编译器的版本,不同的内核数据结构里的结构体的对齐方 -式会有差别,代码中不同函数的表现形式也不一样(函数是不是被inline编译取 -决于编译器行为)。不同的函数的表现形式并不重要,但是数据结构内部的对齐 -方式很关键。 - - 取决于内核的配置选项,不同的选项会让内核的很多东西发生改变: - - 同一个结构体可能包含不同的成员变量 - - 有的函数可能根本不会被实现(比如编译的时候没有选择SMP支持 -,一些锁函数就会被定义成空函数)。 - - 内核使用的内存会以不同的方式对齐,这取决于不同的内核配置选 -项。 - - Linux可以在很多的不同体系结构的处理器上运行。在某个体系结构上编 -译好的二进制驱动程序,不可能在另外一个体系结构上正确的运行。 - -对于一个特定的内核,满足这些条件并不难,使用同一个C编译器和同样的内核配 -置选项来编译驱动程序模块就可以了。这对于给一个特定Linux发布的特定版本提 -供驱动程序,是完全可以满足需求的。但是如果你要给不同发布的不同版本都发 -布一个驱动程序,就需要在每个发布上用不同的内核设置参数都编译一次内核, -这简直跟噩梦一样。而且还要注意到,每个Linux发布还提供不同的Linux内核, -这些内核都针对不同的硬件类型进行了优化(有很多种不同的处理器,还有不同 -的内核设置选项)。所以每发布一次驱动程序,都需要提供很多不同版本的内核 -模块。 - -相信我,如果你真的要采取这种发布方式,一定会慢慢疯掉,我很久以前就有过 -深刻的教训... - - -稳定的内核源代码接口 --------------------- - -如果有人不将他的内核驱动程序,放入公版内核的源代码树,而又想让驱动程序 -一直保持在最新的内核中可用,那么这个话题将会变得没完没了。 - 内核开发是持续而且快节奏的,从来都不会慢下来。内核开发人员在当前接口中 -找到bug,或者找到更好的实现方式。一旦发现这些,他们就很快会去修改当前的 -接口。修改接口意味着,函数名可能会改变,结构体可能被扩充或者删减,函数 -的参数也可能发生改变。一旦接口被修改,内核中使用这些接口的地方需要同时 -修正,这样才能保证所有的东西继续工作。 - -举一个例子,内核的USB驱动程序接口在USB子系统的整个生命周期中,至少经历 -了三次重写。这些重写解决以下问题: - - 把数据流从同步模式改成非同步模式,这个改动减少了一些驱动程序的 -复杂度,提高了所有USB驱动程序的吞吐率,这样几乎所有的USB设备都能以最大 -速率工作了。 - - 修改了USB核心代码中为USB驱动分配数据包内存的方式,所有的驱动都 -需要提供更多的参数给USB核心,以修正了很多已经被记录在案的死锁。 - -这和一些封闭源代码的操作系统形成鲜明的对比,在那些操作系统上,不得不额 -外的维护旧的USB接口。这导致了一个可能性,新的开发者依然会不小心使用旧的 -接口,以不恰当的方式编写代码,进而影响到操作系统的稳定性。 - 在上面的例子中,所有的开发者都同意这些重要的改动,在这样的情况下修改代 -价很低。如果Linux保持一个稳定的内核源代码接口,那么就得创建一个新的接口 -;旧的,有问题的接口必须一直维护,给Linux USB开发者带来额外的工作。既然 -所有的Linux USB驱动的作者都是利用自己的时间工作,那么要求他们去做毫无意 -义的免费额外工作,是不可能的。 - 安全问题对Linux来说十分重要。一个安全问题被发现,就会在短时间内得到修 -正。在很多情况下,这将导致Linux内核中的一些接口被重写,以从根本上避免安 -全问题。一旦接口被重写,所有使用这些接口的驱动程序,必须同时得到修正, -以确定安全问题已经得到修复并且不可能在未来还有同样的安全问题。如果内核 -内部接口不允许改变,那么就不可能修复这样的安全问题,也不可能确认这样的 -安全问题以后不会发生。 -开发者一直在清理内核接口。如果一个接口没有人在使用了,它就会被删除。这 -样可以确保内核尽可能的小,而且所有潜在的接口都会得到尽可能完整的测试 -(没有人使用的接口是不可能得到良好的测试的)。 - - -要做什么 -------- - -如果你写了一个Linux内核驱动,但是它还不在Linux源代码树里,作为一个开发 -者,你应该怎么做?为每个发布的每个版本提供一个二进制驱动,那简直是一个 -噩梦,要跟上永远处于变化之中的内核接口,也是一件辛苦活。 -很简单,让你的驱动进入内核源代码树(要记得我们在谈论的是以GPL许可发行 -的驱动,如果你的代码不符合GPL,那么祝你好运,你只能自己解决这个问题了, -你这个吸血鬼<把Andrew和Linus对吸血鬼的定义链接到这里>)。当你的代码加入 -公版内核源代码树之后,如果一个内核接口改变,你的驱动会直接被修改接口的 -那个人修改。保证你的驱动永远都可以编译通过,并且一直工作,你几乎不需要 -做什么事情。 - -把驱动放到内核源代码树里会有很多的好处: - - 驱动的质量会提升,而维护成本(对原始作者来说)会下降。 - - 其他人会给驱动添加新特性。 - - 其他人会找到驱动中的bug并修复。 - - 其他人会在驱动中找到性能优化的机会。 - - 当外部的接口的改变需要修改驱动程序的时候,其他人会修改驱动程序 -。 - - 不需要联系任何发行商,这个驱动会自动的随着所有的Linux发布一起发 -布。 - -和别的操作系统相比,Linux为更多不同的设备提供现成的驱动,而且能在更多不 -同体系结构的处理器上支持这些设备。这个经过考验的开发模式,必然是错不了 -的 :) - -------------- -感谢 Randy Dunlap, Andrew Morton, David Brownell, Hanna Linder, -Robert Love, and Nishanth Aravamudan 对于本文档早期版本的评审和建议。 - -英文版维护者: Greg Kroah-Hartman -- cgit v1.2.3 From fce8cc57b37e6bb9820ea02a008c602e497f81b3 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:50 +0800 Subject: docs/zh_CN: format stable-api-nonsense to make it follow rst format and readble in html etc doc making. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: TripleX Chung Cc: Li Zefan Cc: Shawn Guo Cc: Fengguang Wu Cc: Coly Li Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- .../zh_CN/process/stable-api-nonsense.rst | 34 ++++++++++------------ 1 file changed, 15 insertions(+), 19 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/stable-api-nonsense.rst b/Documentation/translations/zh_CN/process/stable-api-nonsense.rst index a2b27fab382c..e97bcf5c44ce 100644 --- a/Documentation/translations/zh_CN/process/stable-api-nonsense.rst +++ b/Documentation/translations/zh_CN/process/stable-api-nonsense.rst @@ -1,26 +1,21 @@ -Chinese translated version of Documentation/process/stable-api-nonsense.rst +.. _cn_stable_api_nonsense: -If you have any comment or update to the content, please contact the -original document maintainer directly. However, if you have problem -communicating in English you can also ask the Chinese maintainer for help. -Contact the Chinese maintainer, if this translation is outdated or there -is problem with translation. +.. include:: ../disclaimer-zh_CN.rst -Maintainer: Greg Kroah-Hartman -Chinese maintainer: TripleX Chung ---------------------------------------------------------------------- -Documentation/process/stable-api-nonsense.rst 的中文翻译 +:Original: :ref:`Documentation/process/stable-api-nonsense.rst + ` 如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者。 +译存在问题,请联系中文版维护者:: -英文版维护者: Greg Kroah-Hartman -中文版维护者: 钟宇 TripleX Chung -中文版翻译者: 钟宇 TripleX Chung -中文版校译者: 李阳 Li Yang -以下为正文 ---------------------------------------------------------------------- + 英文版维护者: Greg Kroah-Hartman + 中文版维护者: 钟宇 TripleX Chung + 中文版翻译者: 钟宇 TripleX Chung + 中文版校译者: 李阳 Li Yang + +Linux 内核驱动接口 +================== 写作本文档的目的,是为了解释为什么Linux既没有二进制内核接口,也没有稳定 的内核接口。这里所说的内核接口,是指内核里的接口,而不是内核和用户空间 @@ -124,7 +119,7 @@ Linux能成为强壮,稳定,成熟的操作系统,这也是你最开始选 要做什么 -------- +-------- 如果你写了一个Linux内核驱动,但是它还不在Linux源代码树里,作为一个开发 者,你应该怎么做?为每个发布的每个版本提供一个二进制驱动,那简直是一个 @@ -150,7 +145,8 @@ Linux能成为强壮,稳定,成熟的操作系统,这也是你最开始选 同体系结构的处理器上支持这些设备。这个经过考验的开发模式,必然是错不了 的 :) -------------- +感谢 +---- 感谢 Randy Dunlap, Andrew Morton, David Brownell, Hanna Linder, Robert Love, and Nishanth Aravamudan 对于本文档早期版本的评审和建议。 -- cgit v1.2.3 From 707a680e5c904e87ad98a28fdfefb1467b86b1bc Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:51 +0800 Subject: docs/zh_CN: update Li Yang's email address Change leoli@freescale.com and leo@zh-kernel.org to active address: leoyang.li@nxp.com Signed-off-by: Alex Shi Cc: Li Yang Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/oops-tracing.txt | 2 +- Documentation/translations/zh_CN/process/howto.rst | 4 ++-- Documentation/translations/zh_CN/process/stable-api-nonsense.rst | 2 +- Documentation/translations/zh_CN/process/stable-kernel-rules.rst | 2 +- Documentation/translations/zh_CN/process/submitting-drivers.rst | 4 ++-- Documentation/translations/zh_CN/process/submitting-patches.rst | 2 +- Documentation/translations/zh_CN/sparse.txt | 6 +++--- 7 files changed, 11 insertions(+), 11 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/oops-tracing.txt b/Documentation/translations/zh_CN/oops-tracing.txt index a893f04dfd5d..93fa061cf9e4 100644 --- a/Documentation/translations/zh_CN/oops-tracing.txt +++ b/Documentation/translations/zh_CN/oops-tracing.txt @@ -16,7 +16,7 @@ Documentation/admin-guide/bug-hunting.rst 的中文翻译 中文版维护者: 杨瑞 Dave Young 中文版翻译者: 杨瑞 Dave Young -中文版校译者: 李阳 Li Yang +中文版校译者: 李阳 Li Yang 王聪 Wang Cong 以下为正文 diff --git a/Documentation/translations/zh_CN/process/howto.rst b/Documentation/translations/zh_CN/process/howto.rst index f25a74fb90da..4c46eb90f43f 100644 --- a/Documentation/translations/zh_CN/process/howto.rst +++ b/Documentation/translations/zh_CN/process/howto.rst @@ -9,8 +9,8 @@ 译存在问题,请联系中文版维护者:: 英文版维护者: Greg Kroah-Hartman - 中文版维护者: 李阳 Li Yang - 中文版翻译者: 李阳 Li Yang + 中文版维护者: 李阳 Li Yang + 中文版翻译者: 李阳 Li Yang 中文版校译者: 钟宇 TripleX Chung 陈琦 Maggie Chen diff --git a/Documentation/translations/zh_CN/process/stable-api-nonsense.rst b/Documentation/translations/zh_CN/process/stable-api-nonsense.rst index e97bcf5c44ce..f11829429000 100644 --- a/Documentation/translations/zh_CN/process/stable-api-nonsense.rst +++ b/Documentation/translations/zh_CN/process/stable-api-nonsense.rst @@ -12,7 +12,7 @@ 英文版维护者: Greg Kroah-Hartman 中文版维护者: 钟宇 TripleX Chung 中文版翻译者: 钟宇 TripleX Chung - 中文版校译者: 李阳 Li Yang + 中文版校译者: 李阳 Li Yang Linux 内核驱动接口 ================== diff --git a/Documentation/translations/zh_CN/process/stable-kernel-rules.rst b/Documentation/translations/zh_CN/process/stable-kernel-rules.rst index 425d06f99ac2..3d5a10dfc1ae 100644 --- a/Documentation/translations/zh_CN/process/stable-kernel-rules.rst +++ b/Documentation/translations/zh_CN/process/stable-kernel-rules.rst @@ -11,7 +11,7 @@ 中文版维护者: 钟宇 TripleX Chung 中文版翻译者: 钟宇 TripleX Chung 中文版校译者: - - 李阳 Li Yang + - 李阳 Li Yang - Kangkai Yin 所有你想知道的事情 - 关于linux稳定版发布 diff --git a/Documentation/translations/zh_CN/process/submitting-drivers.rst b/Documentation/translations/zh_CN/process/submitting-drivers.rst index c90ab5ae233d..fade72515b04 100644 --- a/Documentation/translations/zh_CN/process/submitting-drivers.rst +++ b/Documentation/translations/zh_CN/process/submitting-drivers.rst @@ -9,8 +9,8 @@ 交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 译存在问题,请联系中文版维护者:: - 中文版维护者: 李阳 Li Yang - 中文版翻译者: 李阳 Li Yang + 中文版维护者: 李阳 Li Yang + 中文版翻译者: 李阳 Li Yang 中文版校译者: 陈琦 Maggie Chen 王聪 Wang Cong 张巍 Zhang Wei diff --git a/Documentation/translations/zh_CN/process/submitting-patches.rst b/Documentation/translations/zh_CN/process/submitting-patches.rst index 2a2989733c8d..54d2d45e27df 100644 --- a/Documentation/translations/zh_CN/process/submitting-patches.rst +++ b/Documentation/translations/zh_CN/process/submitting-patches.rst @@ -10,7 +10,7 @@ 中文版维护者: 钟宇 TripleX Chung 中文版翻译者: 钟宇 TripleX Chung - 中文版校译者: 李阳 Li Yang + 中文版校译者: 李阳 Li Yang 王聪 Wang Cong diff --git a/Documentation/translations/zh_CN/sparse.txt b/Documentation/translations/zh_CN/sparse.txt index 2f728962a8e2..47fc4a06ebe8 100644 --- a/Documentation/translations/zh_CN/sparse.txt +++ b/Documentation/translations/zh_CN/sparse.txt @@ -6,7 +6,7 @@ communicating in English you can also ask the Chinese maintainer for help. Contact the Chinese maintainer if this translation is outdated or if there is a problem with the translation. -Chinese maintainer: Li Yang +Chinese maintainer: Li Yang --------------------------------------------------------------------- Documentation/dev-tools/sparse.rst 的中文翻译 @@ -14,8 +14,8 @@ Documentation/dev-tools/sparse.rst 的中文翻译 交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 译存在问题,请联系中文版维护者。 -中文版维护者: 李阳 Li Yang -中文版翻译者: 李阳 Li Yang +中文版维护者: 李阳 Li Yang +中文版翻译者: 李阳 Li Yang 以下为正文 -- cgit v1.2.3 From 89870c214360a1e42df83fa3fce71b5b661aa07c Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:53 +0800 Subject: docs/zh_CN: update Zhang Wei's email address to replace the obsolete email address with new one. Signed-off-by: Alex Shi Cc: Zhang Wei Cc: Li Yang Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/submitting-drivers.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/submitting-drivers.rst b/Documentation/translations/zh_CN/process/submitting-drivers.rst index fade72515b04..43c0e4530362 100644 --- a/Documentation/translations/zh_CN/process/submitting-drivers.rst +++ b/Documentation/translations/zh_CN/process/submitting-drivers.rst @@ -13,7 +13,7 @@ 中文版翻译者: 李阳 Li Yang 中文版校译者: 陈琦 Maggie Chen 王聪 Wang Cong - 张巍 Zhang Wei + 张巍 Zhang Wei 如何向 Linux 内核提交驱动程序 ============================= -- cgit v1.2.3 From f448a54e0e47e9578d8547c8f91ccfb7fb26be45 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:55 +0800 Subject: docs/zh_CN: update TripleX chung's email address Update the obslete email address to active one in Chineses docs. Signed-off-by: Alex Shi Cc: TripleX Chung Cc: Li Yang Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/stable-api-nonsense.rst | 4 ++-- Documentation/translations/zh_CN/process/stable-kernel-rules.rst | 4 ++-- Documentation/translations/zh_CN/process/submitting-patches.rst | 4 ++-- 3 files changed, 6 insertions(+), 6 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/stable-api-nonsense.rst b/Documentation/translations/zh_CN/process/stable-api-nonsense.rst index f11829429000..42d974e6dc35 100644 --- a/Documentation/translations/zh_CN/process/stable-api-nonsense.rst +++ b/Documentation/translations/zh_CN/process/stable-api-nonsense.rst @@ -10,8 +10,8 @@ 译存在问题,请联系中文版维护者:: 英文版维护者: Greg Kroah-Hartman - 中文版维护者: 钟宇 TripleX Chung - 中文版翻译者: 钟宇 TripleX Chung + 中文版维护者: 钟宇 TripleX Chung + 中文版翻译者: 钟宇 TripleX Chung 中文版校译者: 李阳 Li Yang Linux 内核驱动接口 diff --git a/Documentation/translations/zh_CN/process/stable-kernel-rules.rst b/Documentation/translations/zh_CN/process/stable-kernel-rules.rst index 3d5a10dfc1ae..fb048c42ae48 100644 --- a/Documentation/translations/zh_CN/process/stable-kernel-rules.rst +++ b/Documentation/translations/zh_CN/process/stable-kernel-rules.rst @@ -8,8 +8,8 @@ 交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 译存在问题,请联系中文版维护者:: - 中文版维护者: 钟宇 TripleX Chung - 中文版翻译者: 钟宇 TripleX Chung + 中文版维护者: 钟宇 TripleX Chung + 中文版翻译者: 钟宇 TripleX Chung 中文版校译者: - 李阳 Li Yang - Kangkai Yin diff --git a/Documentation/translations/zh_CN/process/submitting-patches.rst b/Documentation/translations/zh_CN/process/submitting-patches.rst index 54d2d45e27df..47cdca62cfa2 100644 --- a/Documentation/translations/zh_CN/process/submitting-patches.rst +++ b/Documentation/translations/zh_CN/process/submitting-patches.rst @@ -8,8 +8,8 @@ 交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 译存在问题,请联系中文版维护者:: - 中文版维护者: 钟宇 TripleX Chung - 中文版翻译者: 钟宇 TripleX Chung + 中文版维护者: 钟宇 TripleX Chung + 中文版翻译者: 钟宇 TripleX Chung 中文版校译者: 李阳 Li Yang 王聪 Wang Cong -- cgit v1.2.3 From 115dbd5ca563e5c1ffb79413e9fbb0babf0832f8 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:56 +0800 Subject: docs/zh_CN: fix indent issue in stable-api-nonsense file Tame the 'make htmldocs' to avoid 'ERROR: Unexpected indentation' etc errors. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Li Yang Cc: TripleX Chung Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- .../zh_CN/process/stable-api-nonsense.rst | 33 +++++++++++++--------- 1 file changed, 19 insertions(+), 14 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/stable-api-nonsense.rst b/Documentation/translations/zh_CN/process/stable-api-nonsense.rst index 42d974e6dc35..beb94200b35e 100644 --- a/Documentation/translations/zh_CN/process/stable-api-nonsense.rst +++ b/Documentation/translations/zh_CN/process/stable-api-nonsense.rst @@ -54,18 +54,22 @@ Linux能成为强壮,稳定,成熟的操作系统,这也是你最开始选 -------------- 假如我们有一个稳定的内核源代码接口,那么自然而然的,我们就拥有了稳定的 二进制接口,是这样的吗?错。让我们看看关于Linux内核的几点事实: + - 取决于所用的C编译器的版本,不同的内核数据结构里的结构体的对齐方 -式会有差别,代码中不同函数的表现形式也不一样(函数是不是被inline编译取 -决于编译器行为)。不同的函数的表现形式并不重要,但是数据结构内部的对齐 -方式很关键。 + 式会有差别,代码中不同函数的表现形式也不一样(函数是不是被inline + 编译取决于编译器行为)。不同的函数的表现形式并不重要,但是数据 + 结构内部的对齐方式很关键。 + - 取决于内核的配置选项,不同的选项会让内核的很多东西发生改变: + - 同一个结构体可能包含不同的成员变量 - 有的函数可能根本不会被实现(比如编译的时候没有选择SMP支持 -,一些锁函数就会被定义成空函数)。 + 一些锁函数就会被定义成空函数)。 - 内核使用的内存会以不同的方式对齐,这取决于不同的内核配置选 -项。 + 项。 + - Linux可以在很多的不同体系结构的处理器上运行。在某个体系结构上编 -译好的二进制驱动程序,不可能在另外一个体系结构上正确的运行。 + 译好的二进制驱动程序,不可能在另外一个体系结构上正确的运行。 对于一个特定的内核,满足这些条件并不难,使用同一个C编译器和同样的内核配 置选项来编译驱动程序模块就可以了。这对于给一个特定Linux发布的特定版本提 @@ -85,7 +89,7 @@ Linux能成为强壮,稳定,成熟的操作系统,这也是你最开始选 如果有人不将他的内核驱动程序,放入公版内核的源代码树,而又想让驱动程序 一直保持在最新的内核中可用,那么这个话题将会变得没完没了。 - 内核开发是持续而且快节奏的,从来都不会慢下来。内核开发人员在当前接口中 +内核开发是持续而且快节奏的,从来都不会慢下来。内核开发人员在当前接口中 找到bug,或者找到更好的实现方式。一旦发现这些,他们就很快会去修改当前的 接口。修改接口意味着,函数名可能会改变,结构体可能被扩充或者删减,函数 的参数也可能发生改变。一旦接口被修改,内核中使用这些接口的地方需要同时 @@ -93,21 +97,22 @@ Linux能成为强壮,稳定,成熟的操作系统,这也是你最开始选 举一个例子,内核的USB驱动程序接口在USB子系统的整个生命周期中,至少经历 了三次重写。这些重写解决以下问题: + - 把数据流从同步模式改成非同步模式,这个改动减少了一些驱动程序的 -复杂度,提高了所有USB驱动程序的吞吐率,这样几乎所有的USB设备都能以最大 -速率工作了。 + 复杂度,提高了所有USB驱动程序的吞吐率,这样几乎所有的USB设备都 + 能以最大速率工作了。 - 修改了USB核心代码中为USB驱动分配数据包内存的方式,所有的驱动都 -需要提供更多的参数给USB核心,以修正了很多已经被记录在案的死锁。 + 需要提供更多的参数给USB核心,以修正了很多已经被记录在案的死锁。 这和一些封闭源代码的操作系统形成鲜明的对比,在那些操作系统上,不得不额 外的维护旧的USB接口。这导致了一个可能性,新的开发者依然会不小心使用旧的 接口,以不恰当的方式编写代码,进而影响到操作系统的稳定性。 - 在上面的例子中,所有的开发者都同意这些重要的改动,在这样的情况下修改代 +在上面的例子中,所有的开发者都同意这些重要的改动,在这样的情况下修改代 价很低。如果Linux保持一个稳定的内核源代码接口,那么就得创建一个新的接口 ;旧的,有问题的接口必须一直维护,给Linux USB开发者带来额外的工作。既然 所有的Linux USB驱动的作者都是利用自己的时间工作,那么要求他们去做毫无意 义的免费额外工作,是不可能的。 - 安全问题对Linux来说十分重要。一个安全问题被发现,就会在短时间内得到修 +安全问题对Linux来说十分重要。一个安全问题被发现,就会在短时间内得到修 正。在很多情况下,这将导致Linux内核中的一些接口被重写,以从根本上避免安 全问题。一旦接口被重写,所有使用这些接口的驱动程序,必须同时得到修正, 以确定安全问题已经得到修复并且不可能在未来还有同样的安全问题。如果内核 @@ -132,14 +137,14 @@ Linux能成为强壮,稳定,成熟的操作系统,这也是你最开始选 做什么事情。 把驱动放到内核源代码树里会有很多的好处: + - 驱动的质量会提升,而维护成本(对原始作者来说)会下降。 - 其他人会给驱动添加新特性。 - 其他人会找到驱动中的bug并修复。 - 其他人会在驱动中找到性能优化的机会。 - 当外部的接口的改变需要修改驱动程序的时候,其他人会修改驱动程序 -。 - 不需要联系任何发行商,这个驱动会自动的随着所有的Linux发布一起发 -布。 + 布。 和别的操作系统相比,Linux为更多不同的设备提供现成的驱动,而且能在更多不 同体系结构的处理器上支持这些设备。这个经过考验的开发模式,必然是错不了 -- cgit v1.2.3 From ce8ee3a8c07f6218124aa0336bae9c669b203bd7 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:49:57 +0800 Subject: docs/zh_CN: fix indent issue in submitting-drivers Tame 'make htmldocs' w/o indent complains. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Li Yang Cc: TripleX Chung Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/submitting-drivers.rst | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/submitting-drivers.rst b/Documentation/translations/zh_CN/process/submitting-drivers.rst index 43c0e4530362..3be51d998c80 100644 --- a/Documentation/translations/zh_CN/process/submitting-drivers.rst +++ b/Documentation/translations/zh_CN/process/submitting-drivers.rst @@ -137,9 +137,13 @@ Linux 设备驱动程序,第三版(探讨 2.6.10 版内核): LWN.net: 每周内核开发活动摘要 - http://lwn.net/ + 2.6 版中 API 的变更: + http://lwn.net/Articles/2.6-kernel-api/ + 将旧版内核的驱动程序移植到 2.6 版: + http://lwn.net/Articles/driver-porting/ 内核新手(KernelNewbies): -- cgit v1.2.3 From a31ffdb3fc06006205c991a1199b175bfa358e79 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:50:00 +0800 Subject: docs/zh_CN: fix rst format issue in submitting-patch Tame 'make htmldocs' to avoid indent and code section error complains. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Li Yang Cc: TripleX Chung Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- .../zh_CN/process/submitting-patches.rst | 22 +++++++++++++--------- 1 file changed, 13 insertions(+), 9 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/submitting-patches.rst b/Documentation/translations/zh_CN/process/submitting-patches.rst index 47cdca62cfa2..66c64acf86c1 100644 --- a/Documentation/translations/zh_CN/process/submitting-patches.rst +++ b/Documentation/translations/zh_CN/process/submitting-patches.rst @@ -39,7 +39,7 @@ Documentation/process/submitting-drivers.rst 。 参数生成。而且,请使用 '-p' 参数,那样会显示每个改动所在的C函数,使得 产生的补丁容易读得多。补丁应该基于内核源代码树的根目录,而不是里边的任 何子目录。 -为一个单独的文件创建补丁,一般来说这样做就够了: +为一个单独的文件创建补丁,一般来说这样做就够了:: SRCTREE= linux-2.6 MYFILE= drivers/net/mydriver.c @@ -51,7 +51,7 @@ Documentation/process/submitting-drivers.rst 。 diff -up $SRCTREE/$MYFILE{.orig,} > /tmp/patch 为多个文件创建补丁,你可以解开一个没有修改过的内核源代码树,然后和你自 -己的代码树之间做 diff 。例如: +己的代码树之间做 diff 。例如:: MYSRC= /devel/linux-2.6 @@ -141,6 +141,7 @@ MAINTAINERS 文件里的)发送一个手册页(man-pages)补丁,或者 对于小的补丁,你也许会CC到 Adrian Bunk 管理的搜集琐碎补丁的邮件列表 (Trivial Patch Monkey)trivial@kernel.org,那里专门收集琐碎的补丁。下面这样 的补丁会被看作“琐碎的”补丁: + 文档的拼写修正。 修正会影响到 grep(1) 的拼写。 警告信息修正(频繁的打印无用的警告是不好的。) @@ -241,8 +242,10 @@ Linus 和 linux-kernel 邮件列表的 e-mail 流量都很高,一个通常的 "sign-off" 是在补丁的注释的最后的简单的一行文字,认证你编写了它或者其他 人有权力将它作为开放源代码的补丁传递。规则很简单:如果你能认证如下信息 : - 开发者来源证书 1.1 - 对于本项目的贡献,我认证如下信息: +开发者来源证书 1.1 +^^^^^^^^^^^^^^^^^^ +对于本项目的贡献,我认证如下信息: + (a)这些贡献是完全或者部分的由我创建,我有权利以文件中指出 的开放源代码许可证提交它;或者 (b)这些贡献基于以前的工作,据我所知,这些以前的工作受恰当的开放 @@ -295,7 +298,7 @@ e-mail 标题中的“一句话概述”扼要的描述 e-mail 中的补丁。 丁。用户将希望通过 google 来搜索"一句话概述"来找到那些讨论这个补丁的文 章。 -一些标题的例子: +一些标题的例子:: Subject: [patch 2/5] ext2: improve scalability of bitmap searching Subject: [PATCHv2 001/207] x86: fix eflags tracking @@ -338,7 +341,7 @@ Nuff 说过,如果你的代码和这个偏离太多,那么它有可能会被 在头文件里,有条件地定义 "static inline" 函数,或者宏,在代码里用这些东 西。让编译器把那些"空操作"优化掉。 -一个简单的例子,不好的代码: +一个简单的例子,不好的代码:: dev = alloc_etherdev (sizeof(struct funky_private)); if (!dev) @@ -349,12 +352,14 @@ Nuff 说过,如果你的代码和这个偏离太多,那么它有可能会被 清理后的例子: -(头文件里) +(头文件里):: + #ifndef CONFIG_NET_FUNKINESS static inline void init_funky_net (struct net_device *d) {} #endif -(代码文件里) +(代码文件里):: + dev = alloc_etherdev (sizeof(struct funky_private)); if (!dev) return -ENODEV; @@ -399,4 +404,3 @@ Kernel Documentation/process/coding-style.rst: Linus Torvalds's mail on the canonical patch format: --- -- cgit v1.2.3 From dcea1c73a656599783a610df910c11231997f224 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Wed, 13 Mar 2019 21:50:01 +0800 Subject: docs/zh_CN: fix rst format errors in howto.rst Tame howto.rst file to avoid "ERROR: Unexpected indentation." etc compiler errors. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Li Yang Cc: TripleX Chung Signed-off-by: Weiwei Jia Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/howto.rst | 32 ++++++++++++++++++++-- 1 file changed, 30 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/howto.rst b/Documentation/translations/zh_CN/process/howto.rst index 4c46eb90f43f..6ab167812325 100644 --- a/Documentation/translations/zh_CN/process/howto.rst +++ b/Documentation/translations/zh_CN/process/howto.rst @@ -38,6 +38,7 @@ Linux内核大部分是由C语言写成的,一些体系结构相关的代码 参与内核开发,你必须精通C语言。除非你想为某个架构开发底层代码,否则你并 不需要了解(任何体系结构的)汇编语言。下面列举的书籍虽然不能替代扎实的C 语言教育和多年的开发经验,但如果需要的话,做为参考还是不错的: + - "The C Programming Language" by Kernighan and Ritchie [Prentice Hall] 《C程序设计语言(第2版·新版)》(徐宝文 李志 译)[机械工业出版社] - "Practical C Programming" by Steve Oualline [O'Reilly] @@ -94,16 +95,20 @@ Linux内核代码中包含有大量的文档。这些文档对于学习如何与 Documentation/process/submitting-patches.rst Documentation/process/submitting-drivers.rst + 这两份文档明确描述如何创建和发送补丁,其中包括(但不仅限于): - 邮件内容 - 邮件格式 - 选择收件人 + 遵守这些规定并不能保证提交成功(因为所有补丁需要通过严格的内容和风格 审查),但是忽视他们几乎就意味着失败。 其他关于如何正确地生成补丁的优秀文档包括: "The Perfect Patch" + http://www.ozlabs.org/~akpm/stuff/tpp.txt + "Linux kernel patch submission format" http://linux.yyz.us/patch-format.html @@ -111,9 +116,11 @@ Linux内核代码中包含有大量的文档。这些文档对于学习如何与 Documentation/process/stable-api-nonsense.rst 论证内核为什么特意不包括稳定的内核内部API,也就是说不包括像这样的特 性: + - 子系统中间层(为了兼容性?) - 在不同操作系统间易于移植的驱动程序 - 减缓(甚至阻止)内核代码的快速变化 + 这篇文档对于理解Linux的开发哲学至关重要。对于将开发平台从其他操作系 统转移到Linux的人来说也很重要。 @@ -140,6 +147,7 @@ Linux内核代码中包含有大量的文档。这些文档对于学习如何与 妥善处理加锁的规则。生成的文档会放在 Documentation/DocBook/目录下。在内 核源码的主目录中使用以下不同命令将会分别生成PDF、Postscript、HTML和手册 页等不同格式的文档: + make pdfdocs make htmldocs @@ -147,7 +155,9 @@ Linux内核代码中包含有大量的文档。这些文档对于学习如何与 如何成为内核开发者 ------------------ 如果你对Linux内核开发一无所知,你应该访问“Linux内核新手”计划: + http://kernelnewbies.org + 它拥有一个可以问各种最基本的内核开发问题的邮件列表(在提问之前一定要记得 查找已往的邮件,确认是否有人已经回答过相同的问题)。它还拥有一个可以获得 实时反馈的IRC聊天频道,以及大量对于学习Linux内核开发相当有帮助的文档。 @@ -158,7 +168,9 @@ Linux内核代码中包含有大量的文档。这些文档对于学习如何与 如果你想加入内核开发社区并协助完成一些任务,却找不到从哪里开始,可以访问 “Linux内核房管员”计划: + http://kernelnewbies.org/KernelJanitors + 这是极佳的起点。它提供一个相对简单的任务列表,列出内核代码中需要被重新 整理或者改正的地方。通过和负责这个计划的开发者们一同工作,你会学到将补丁 集成进内核的基本原理。如果还没有决定下一步要做什么的话,你还可能会得到方 @@ -167,6 +179,7 @@ Linux内核代码中包含有大量的文档。这些文档对于学习如何与 如果你已经有一些现成的代码想要放到内核中,但是需要一些帮助来使它们拥有正 确的格式。请访问“内核导师”计划。这个计划就是用来帮助你完成这个目标的。它 是一个邮件列表,地址如下: + http://selenic.com/mailman/listinfo/kernel-mentors 在真正动手修改内核代码之前,理解要修改的代码如何运作是必需的。要达到这个 @@ -174,6 +187,7 @@ Linux内核代码中包含有大量的文档。这些文档对于学习如何与 一些特制的工具还可以提供帮助。例如,“Linux代码交叉引用”项目就是一个值得 特别推荐的帮助工具,它将源代码显示在有编目和索引的网页上。其中一个更新及 时的内核源码库,可以通过以下地址访问: + http://sosdg.org/~coywolf/lxr/ @@ -182,6 +196,7 @@ Linux内核代码中包含有大量的文档。这些文档对于学习如何与 目前Linux内核开发流程包括几个“主内核分支”和很多子系统相关的内核分支。这 些分支包括: + - 2.6.x主内核源码树 - 2.6.x.y -stable内核源码树 - 2.6.x -mm内核补丁集 @@ -193,6 +208,7 @@ Linux内核代码中包含有大量的文档。这些文档对于学习如何与 2.6.x内核是由Linus Torvalds(Linux的创造者)亲自维护的。你可以在 kernel.org网站的pub/linux/kernel/v2.6/目录下找到它。它的开发遵循以下步 骤: + - 每当一个新版本的内核被发布,为期两周的集成窗口将被打开。在这段时间里 维护者可以向Linus提交大段的修改,通常这些修改已经被放到-mm内核中几个 星期了。提交大量修改的首选方式是使用git工具(内核的代码版本管理工具 @@ -308,6 +324,7 @@ linux-kernel邮件列表中提供反馈,告诉大家你遇到了问题还是 bugzilla.kernel.org是Linux内核开发者们用来跟踪内核Bug的网站。我们鼓励用 户在这个工具中报告找到的所有bug。如何使用内核bugzilla的细节请访问: + http://test.kernel.org/bugzilla/faq.html 内核源码主目录中的admin-guide/reporting-bugs.rst文件里有一个很好的模板。它指导用户如何报 @@ -335,10 +352,14 @@ bugzilla.kernel.org是Linux内核开发者们用来跟踪内核Bug的网站。 正如上面的文档所描述,大多数的骨干内核开发者都加入了Linux Kernel邮件列 表。如何订阅和退订列表的细节可以在这里找到: + http://vger.kernel.org/vger-lists.html#linux-kernel + 网上很多地方都有这个邮件列表的存档(archive)。可以使用搜索引擎来找到这些 存档。比如: + http://dir.gmane.org/gmane.linux.kernel + 在发信之前,我们强烈建议你先在存档中搜索你想要讨论的问题。很多已经被详细 讨论过的问题只在邮件列表的存档中可以找到。 @@ -346,10 +367,12 @@ bugzilla.kernel.org是Linux内核开发者们用来跟踪内核Bug的网站。 MAINTAINERS文件中可以找到不同话题对应的邮件列表。 很多邮件列表架设在kernel.org服务器上。这些列表的信息可以在这里找到: + http://vger.kernel.org/vger-lists.html 在使用这些邮件列表时,请记住保持良好的行为习惯。下面的链接提供了与这些列 表(或任何其它邮件列表)交流的一些简单规则,虽然内容有点滥竽充数。 + http://www.albion.com/netiquette/ 当有很多人回复你的邮件时,邮件的抄送列表会变得很长。请不要将任何人从抄送 @@ -375,6 +398,7 @@ Documentation/process/submitting-patches.rst文档中所述)。内核开发者 内核社区的目标就是提供尽善尽美的内核。所以当你提交补丁期望被接受进内核的 时候,它的技术价值以及其他方面都将被评审。那么你可能会得到什么呢? + - 批评 - 评论 - 要求修改 @@ -387,6 +411,7 @@ Documentation/process/submitting-patches.rst文档中所述)。内核开发者 没在茫茫信海中。 你不应该做的事情: + - 期望自己的补丁不受任何质疑就直接被接受 - 翻脸 - 忽略别人的评论 @@ -406,7 +431,8 @@ Documentation/process/submitting-patches.rst文档中所述)。内核开发者 内核社区的工作模式同大多数传统公司开发队伍的工作模式并不相同。下面这些例 子,可以帮助你避免某些可能发生问题: - 用这些话介绍你的修改提案会有好处: +用这些话介绍你的修改提案会有好处: + - 它同时解决了多个问题 - 它删除了2000行代码 - 这是补丁,它已经解释了我想要说明的 @@ -414,7 +440,8 @@ Documentation/process/submitting-patches.rst文档中所述)。内核开发者 - 这是一系列小补丁用来…… - 这个修改提高了普通机器的性能…… - 应该避免如下的说法: +应该避免如下的说法: + - 我们在AIX/ptx/Solaris就是这么做的,所以这么做肯定是好的…… - 我做这行已经20年了,所以…… - 为了我们公司赚钱考虑必须这么做 @@ -487,6 +514,7 @@ Linux内核社区并不喜欢一下接收大段的代码。修改需要被恰当 当你发送补丁的时候,需要特别留意邮件正文的内容。因为这里的信息将会做为补 丁的修改记录(ChangeLog),会被一直保留以备大家查阅。它需要完全地描述补丁, 包括: + - 为什么需要这个修改 - 补丁的总体设计 - 实现细节 -- cgit v1.2.3 From 20bd1249489bcc74f275fc2f1d27cd2ceda4ee38 Mon Sep 17 00:00:00 2001 From: Federico Vaga Date: Thu, 14 Mar 2019 21:45:16 +0100 Subject: doc: add translation disclaimer Add the translation disclaimer in English as reference for other languages. Translations must include this disclaimer in their language so that readers are properly informed. This very same patch updates the Italian translation accordingly. Signed-off-by: Federico Vaga Acked-by: Alex Shi Signed-off-by: Jonathan Corbet --- Documentation/translations/index.rst | 42 ++++++++++++++++ .../translations/it_IT/disclaimer-ita.rst | 13 ++--- Documentation/translations/it_IT/index.rst | 57 +++++++++++++++------- 3 files changed, 85 insertions(+), 27 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/index.rst b/Documentation/translations/index.rst index 7f77c52d33aa..d7a38fd28b50 100644 --- a/Documentation/translations/index.rst +++ b/Documentation/translations/index.rst @@ -4,6 +4,48 @@ Translations ============ +.. _translations_disclaimer: + +Disclaimer +---------- + +Translation's purpose is to ease reading and understating in languages other +than English. Its aim is to help people who do not understand English or have +doubts about its interpretation. Additionally, some people prefer to read +documentation in their native language, but please bear in mind that the +*only* official documentation is the English one: :ref:`linux_doc`. + +It is very unlikely that an update to :ref:`linux_doc` will be propagated +immediately to all translations. Translations' maintainers - and +contributors - follow the evolution of the official documentation and they +maintain translations aligned as much as they can. For this reason there is +no guarantee that a translation is up to date. If what you read in a +translation does not sound right compared to what you read in the code, please +inform the translation maintainer and - if you can - check also the English +documentation. + +A translation is not a fork of the official documentation, therefore +translations' users should not find information that differs from the official +English documentation. Any content addition, removal or update, must be +applied to the English documents first. Afterwards and when possible, the +same change should be applied to translations. Translations' maintainers +accept only contributions that are merely translation related (e.g. new +translations, updates, fixes). + +Translations try to be as accurate as possible but it is not possible to map +one language directly to all other languages. Each language has its own +grammar and culture, so the translation of an English statement may need to be +adapted to fit a different language. For this reason, when viewing +translations, you may find slight differences that carry the same message but +in a different form. + +If you need to communicate with the Linux community but you do not feel +comfortable to write in English, you can ask to the translation's +maintainers for help. + +Translations +------------ + .. toctree:: :maxdepth: 1 diff --git a/Documentation/translations/it_IT/disclaimer-ita.rst b/Documentation/translations/it_IT/disclaimer-ita.rst index d68e52de6a5d..bfe8a384baed 100644 --- a/Documentation/translations/it_IT/disclaimer-ita.rst +++ b/Documentation/translations/it_IT/disclaimer-ita.rst @@ -1,13 +1,6 @@ :orphan: -.. note:: - This document is maintained by Federico Vaga . - If you find any difference between this document and the original file or a - problem with the translation, please contact the maintainer of this file. - Following people helped to translate or review: - Alessia Mantegazza - .. warning:: - The purpose of this file is to be easier to read and understand for Italian - speakers and is not intended as a fork. So, if you have any comments or - updates for this file please try to update the original English file first. + In caso di dubbi sulla correttezza del contenuto di questa traduzione, + l'unico riferimento valido è la documentazione ufficiale in inglese. + Per maggiori informazioni consultate le :ref:`avvertenze `. diff --git a/Documentation/translations/it_IT/index.rst b/Documentation/translations/it_IT/index.rst index ea9b2916b3e4..340d3f690dfd 100644 --- a/Documentation/translations/it_IT/index.rst +++ b/Documentation/translations/it_IT/index.rst @@ -4,26 +4,49 @@ Traduzione italiana =================== -L'obiettivo di questa traduzione è di rendere più facile la lettura e -la comprensione per chi preferisce leggere in lingua italiana. -Tenete presente che la documentazione di riferimento rimane comunque -quella in lingua inglese: :ref:`linux_doc` - -Questa traduzione cerca di essere il più fedele possibile all'originale ma -è ovvio che alcune frasi vadano trasformate: non aspettatevi una traduzione -letterale. Quando possibile, si eviteranno gli inglesismi ed al loro posto -verranno utilizzate le corrispettive parole italiane. +:manutentore: Federico Vaga -Se notate che la traduzione non è più aggiornata potete contattare -direttamente il manutentore della traduzione italiana. +.. _it_disclaimer: -Se notate che la documentazione contiene errori o dimenticanze, allora -verificate la documentazione di riferimento in lingua inglese. Se il problema -è presente anche nella documentazione di riferimento, contattate il suo -manutentore. Se avete problemi a scrivere in inglese, potete comunque -riportare il problema al manutentore della traduzione italiana. +Avvertenze +========== -Manutentore della traduzione italiana: Federico Vaga +L'obiettivo di questa traduzione è di rendere più facile la lettura e +la comprensione per chi non capisce l'inglese o ha dubbi sulla sua +interpretazione, oppure semplicemente per chi preferisce leggere in lingua +italiana. Tuttavia, tenete ben presente che l'*unica* documentazione +ufficiale è quella in lingua inglese: :ref:`linux_doc` + +La propagazione simultanea a tutte le traduzioni di una modifica in +:ref:`linux_doc` è altamente improbabile. I manutentori delle traduzioni - +e i contributori - seguono l'evolversi della documentazione ufficiale e +cercano di mantenere le rispettive traduzioni allineate nel limite del +possibile. Per questo motivo non c'è garanzia che una traduzione sia +aggiornata all'ultima modifica. Se quello che leggete in una traduzione +non corrisponde a quello che leggete nel codice, informate il manutentore +della traduzione e - se potete - verificate anche la documentazione in +inglese. + +Una traduzione non è un *fork* della documentazione ufficiale, perciò gli +utenti non vi troveranno alcuna informazione diversa rispetto alla versione +ufficiale. Ogni aggiunta, rimozione o modifica dei contenuti deve essere +fatta prima nei documenti in inglese. In seguito, e quando è possibile, la +stessa modifica dovrebbe essere applicata anche alle traduzioni. I manutentori +delle traduzioni accettano contributi che interessano prettamente l'attività +di traduzione (per esempio, nuove traduzioni, aggiornamenti, correzioni). + +Le traduzioni cercano di essere il più possibile accurate ma non è possibile +mappare direttamente una lingua in un'altra. Ogni lingua ha la sua grammatica +e una sua cultura alle spalle, quindi la traduzione di una frase in inglese +potrebbe essere modificata per adattarla all'italiano. Per questo motivo, +quando leggete questa traduzione, potreste trovare alcune differenze di forma +ma che trasmettono comunque il messaggio originale. Nonostante la grande +diffusione di inglesismi nella lingua parlata, quando possibile, questi +verranno sostituiti dalle corrispettive parole italiane + +Se avete bisogno d'aiuto per comunicare con la comunità Linux ma non vi sentite +a vostro agio nello scrivere in inglese, potete chiedere aiuto al manutentore +della traduzione. La documentazione del kernel Linux ================================== -- cgit v1.2.3 From 30cc0b6c1220d61347177560afc3c8c706c73741 Mon Sep 17 00:00:00 2001 From: Juergen Gross Date: Fri, 8 Mar 2019 12:43:10 +0100 Subject: doc: add boot protocol 2.13 description to Documentation/x86/boot.txt Documentation/x86/boot.txt is missing protocol 2.13 description. Reported-by: Ross Philipson Signed-off-by: Juergen Gross Reviewed-by: Konrad Rzeszutek Wilk Reviewed-by: H. Peter Anvin Reviewed-by: Matt Fleming Reviewed-by: Daniel Kiper Signed-off-by: Jonathan Corbet --- Documentation/x86/boot.txt | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'Documentation') diff --git a/Documentation/x86/boot.txt b/Documentation/x86/boot.txt index f4c2a97bfdbd..223e484a1304 100644 --- a/Documentation/x86/boot.txt +++ b/Documentation/x86/boot.txt @@ -61,6 +61,10 @@ Protocol 2.12: (Kernel 3.8) Added the xloadflags field and extension fields to struct boot_params for loading bzImage and ramdisk above 4G in 64bit. +Protocol 2.13: (Kernel 3.14) Support 32- and 64-bit flags being set in + xloadflags to support booting a 64-bit kernel from 32-bit + EFI + **** MEMORY LAYOUT The traditional memory map for the kernel loader, used for Image or -- cgit v1.2.3 From 6491126e1ba774622e7c69de95bdfa7127ef83f7 Mon Sep 17 00:00:00 2001 From: Jakub Wilk Date: Mon, 4 Mar 2019 21:31:51 +0100 Subject: Documentation: seccomp: fix reST markup Signed-off-by: Jakub Wilk Acked-by: Kees Cook Signed-off-by: Jonathan Corbet --- Documentation/userspace-api/seccomp_filter.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/userspace-api/seccomp_filter.rst b/Documentation/userspace-api/seccomp_filter.rst index b1b846d8a094..0f09a63ea923 100644 --- a/Documentation/userspace-api/seccomp_filter.rst +++ b/Documentation/userspace-api/seccomp_filter.rst @@ -133,7 +133,7 @@ In precedence order, they are: call. If there is no tracer present, ``-ENOSYS`` is returned to userland and the system call is not executed. - A tracer will be notified if it requests ``PTRACE_O_TRACESECCOM``P + A tracer will be notified if it requests ``PTRACE_O_TRACESECCOMP`` using ``ptrace(PTRACE_SETOPTIONS)``. The tracer will be notified of a ``PTRACE_EVENT_SECCOMP`` and the ``SECCOMP_RET_DATA`` portion of the BPF program return value will be available to the tracer -- cgit v1.2.3 From 2f1ff5899076ec8ff87e4088fb9a4f55825c66a5 Mon Sep 17 00:00:00 2001 From: Jakub Wilk Date: Mon, 4 Mar 2019 21:31:52 +0100 Subject: Documentation: seccomp: unify list indentation Use tabs to indent SECCOMP_RET_USER_NOTIF definition, for consistency with other items in this list. Signed-off-by: Jakub Wilk Acked-by: Kees Cook Signed-off-by: Jonathan Corbet --- Documentation/userspace-api/seccomp_filter.rst | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/userspace-api/seccomp_filter.rst b/Documentation/userspace-api/seccomp_filter.rst index 0f09a63ea923..bd9165241b6c 100644 --- a/Documentation/userspace-api/seccomp_filter.rst +++ b/Documentation/userspace-api/seccomp_filter.rst @@ -123,9 +123,9 @@ In precedence order, they are: to userland as the errno without executing the system call. ``SECCOMP_RET_USER_NOTIF``: - Results in a ``struct seccomp_notif`` message sent on the userspace - notification fd, if it is attached, or ``-ENOSYS`` if it is not. See below - on discussion of how to handle user notifications. + Results in a ``struct seccomp_notif`` message sent on the userspace + notification fd, if it is attached, or ``-ENOSYS`` if it is not. See + below on discussion of how to handle user notifications. ``SECCOMP_RET_TRACE``: When returned, this value will cause the kernel to attempt to -- cgit v1.2.3 From 9834857754fffde7008123503fe8f1d66f526eb5 Mon Sep 17 00:00:00 2001 From: Federico Vaga Date: Sun, 24 Feb 2019 21:05:27 +0100 Subject: doc:it_IT: translations for documents in process/ Translated documents: - stable-kernel-rules.rst - deprecated.rst - kernel-enforcement-statement.rst - license-rules.rst Added document to have valid links - netdev-FAQ.rst Modifications to main documentation - add label in deprecated.rst Signed-off-by: Federico Vaga Signed-off-by: Jonathan Corbet --- Documentation/process/deprecated.rst | 2 + Documentation/translations/it_IT/index.rst | 8 +- .../translations/it_IT/networking/netdev-FAQ.rst | 13 + .../translations/it_IT/process/deprecated.rst | 129 ++++++ .../it_IT/process/kernel-enforcement-statement.rst | 168 +++++++- .../translations/it_IT/process/license-rules.rst | 452 +++++++++++++++++++++ .../it_IT/process/stable-kernel-rules.rst | 194 ++++++++- 7 files changed, 954 insertions(+), 12 deletions(-) create mode 100644 Documentation/translations/it_IT/networking/netdev-FAQ.rst create mode 100644 Documentation/translations/it_IT/process/deprecated.rst create mode 100644 Documentation/translations/it_IT/process/license-rules.rst (limited to 'Documentation') diff --git a/Documentation/process/deprecated.rst b/Documentation/process/deprecated.rst index 0ef5a63c06ba..49e0f64a3427 100644 --- a/Documentation/process/deprecated.rst +++ b/Documentation/process/deprecated.rst @@ -1,5 +1,7 @@ .. SPDX-License-Identifier: GPL-2.0 +.. _deprecated: + ===================================================================== Deprecated Interfaces, Language Features, Attributes, and Conventions ===================================================================== diff --git a/Documentation/translations/it_IT/index.rst b/Documentation/translations/it_IT/index.rst index 340d3f690dfd..409eaac03e9f 100644 --- a/Documentation/translations/it_IT/index.rst +++ b/Documentation/translations/it_IT/index.rst @@ -70,9 +70,7 @@ I seguenti documenti descrivono la licenza usata nei sorgenti del kernel Linux (GPLv2), come licenziare i singoli file; inoltre troverete i riferimenti al testo integrale della licenza. -.. warning:: - - TODO ancora da tradurre +* :ref:`it_kernel_licensing` Documentazione per gli utenti ----------------------------- @@ -113,10 +111,6 @@ vostre modifiche molto più semplice doc-guide/index kernel-hacking/index -.. warning:: - - TODO ancora da tradurre - Documentazione della API del kernel ----------------------------------- diff --git a/Documentation/translations/it_IT/networking/netdev-FAQ.rst b/Documentation/translations/it_IT/networking/netdev-FAQ.rst new file mode 100644 index 000000000000..8489ead7cff1 --- /dev/null +++ b/Documentation/translations/it_IT/networking/netdev-FAQ.rst @@ -0,0 +1,13 @@ +.. include:: ../disclaimer-ita.rst + +:Original: :ref:`Documentation/process/stable-kernel-rules.rst ` + +.. _it_netdev-FAQ: + +========== +netdev FAQ +========== + +.. warning:: + + TODO ancora da tradurre diff --git a/Documentation/translations/it_IT/process/deprecated.rst b/Documentation/translations/it_IT/process/deprecated.rst new file mode 100644 index 000000000000..776f26732a94 --- /dev/null +++ b/Documentation/translations/it_IT/process/deprecated.rst @@ -0,0 +1,129 @@ +.. SPDX-License-Identifier: GPL-2.0 + +.. include:: ../disclaimer-ita.rst + +:Original: :ref:`Documentation/process/deprecated.rst ` +:Translator: Federico Vaga + +.. _it_deprecated: + +============================================================================== +Interfacce deprecate, caratteristiche del linguaggio, attributi, e convenzioni +============================================================================== + +In un mondo perfetto, sarebbe possibile prendere tutti gli usi di +un'interfaccia deprecata e convertirli in quella nuova, e così sarebbe +possibile rimuovere la vecchia interfaccia in un singolo ciclo di sviluppo. +Tuttavia, per via delle dimensioni del kernel, la gerarchia dei manutentori e +le tempistiche, non è sempre possibile fare questo tipo di conversione tutta +in una volta. Questo significa che nuove istanze di una vecchia interfaccia +potrebbero aggiungersi al kernel proprio quando si sta cercando di rimuoverle, +aumentando così il carico di lavoro. Al fine di istruire gli sviluppatori su +cosa è considerato deprecato (e perché), è stata create la seguente lista a cui +fare riferimento quando qualcuno propone modifiche che usano cose deprecate. + +__deprecated +------------ +Nonostante questo attributo marchi visibilmente un interfaccia come deprecata, +`non produce più alcun avviso durante la compilazione +`_ +perché uno degli obiettivi del kernel è quello di compilare senza avvisi; +inoltre, nessuno stava agendo per rimuovere queste interfacce. Nonostante l'uso +di `__deprecated` in un file d'intestazione sia opportuno per segnare una +interfaccia come 'vecchia', questa non è una soluzione completa. L'interfaccia +deve essere rimossa dal kernel, o aggiunta a questo documento per scoraggiarne +l'uso. + +Calcoli codificati negli argomenti di un allocatore +---------------------------------------------------- +Il calcolo dinamico delle dimensioni (specialmente le moltiplicazioni) non +dovrebbero essere fatto negli argomenti di funzioni di allocazione di memoria +(o simili) per via del rischio di overflow. Questo può portare a valori più +piccoli di quelli che il chiamante si aspettava. L'uso di questo modo di +allocare può portare ad un overflow della memoria di heap e altri +malfunzionamenti. (Si fa eccezione per valori numerici per i quali il +compilatore può generare avvisi circa un potenziale overflow. Tuttavia usare +i valori numerici come suggerito di seguito è innocuo). + +Per esempio, non usate ``count * size`` come argomento:: + + foo = kmalloc(count * size, GFP_KERNEL); + +Al suo posto, si dovrebbe usare l'allocatore a due argomenti:: + + foo = kmalloc_array(count, size, GFP_KERNEL); + +Se questo tipo di allocatore non è disponibile, allora dovrebbero essere usate +le funzioni del tipo *saturate-on-overflow*:: + + bar = vmalloc(array_size(count, size)); + +Un altro tipico caso da evitare è quello di calcolare la dimensione di una +struttura seguita da un vettore di altre strutture, come nel seguente caso:: + + header = kzalloc(sizeof(*header) + count * sizeof(*header->item), + GFP_KERNEL); + +Invece, usate la seguente funzione:: + + header = kzalloc(struct_size(header, item, count), GFP_KERNEL); + +Per maggiori dettagli fate riferimento a :c:func:`array_size`, +:c:func:`array3_size`, e :c:func:`struct_size`, così come la famiglia di +funzioni :c:func:`check_add_overflow` e :c:func:`check_mul_overflow`. + +simple_strtol(), simple_strtoll(), simple_strtoul(), simple_strtoull() +---------------------------------------------------------------------- +Le funzioni :c:func:`simple_strtol`, :c:func:`simple_strtoll`, +:c:func:`simple_strtoul`, e :c:func:`simple_strtoull` ignorano volutamente +i possibili overflow, e questo può portare il chiamante a generare risultati +inaspettati. Le rispettive funzioni :c:func:`kstrtol`, :c:func:`kstrtoll`, +:c:func:`kstrtoul`, e :c:func:`kstrtoull` sono da considerarsi le corrette +sostitute; tuttavia va notato che queste richiedono che la stringa sia +terminata con il carattere NUL o quello di nuova riga. + +strcpy() +-------- +La funzione :c:func:`strcpy` non fa controlli agli estremi del buffer +di destinazione. Questo può portare ad un overflow oltre i limiti del +buffer e generare svariati tipi di malfunzionamenti. Nonostante l'opzione +`CONFIG_FORTIFY_SOURCE=y` e svariate opzioni del compilatore aiutano +a ridurne il rischio, non c'è alcuna buona ragione per continuare ad usare +questa funzione. La versione sicura da usare è :c:func:`strscpy`. + +strncpy() su stringe terminate con NUL +-------------------------------------- +L'utilizzo di :c:func:`strncpy` non fornisce alcuna garanzia sul fatto che +il buffer di destinazione verrà terminato con il carattere NUL. Questo +potrebbe portare a diversi overflow di lettura o altri malfunzionamenti +causati, appunto, dalla mancanza del terminatore. Questa estende la +terminazione nel buffer di destinazione quando la stringa d'origine è più +corta; questo potrebbe portare ad una penalizzazione delle prestazioni per +chi usa solo stringe terminate. La versione sicura da usare è +:c:func:`strscpy`. (chi usa :c:func:`strscpy` e necessita di estendere la +terminazione con NUL deve aggiungere una chiamata a :c:func:`memset`) + +Se il chiamate no usa stringhe terminate con NUL, allore :c:func:`strncpy()` +può continuare ad essere usata, ma i buffer di destinazione devono essere +marchiati con l'attributo `__nonstring `_ +per evitare avvisi durante la compilazione. + +strlcpy() +--------- +La funzione :c:func:`strlcpy`, per prima cosa, legge interamente il buffer di +origine, magari leggendo più di quanto verrà effettivamente copiato. Questo +è inefficiente e può portare a overflow di lettura quando la stringa non è +terminata con NUL. La versione sicura da usare è :c:func:`strscpy`. + +Vettori a dimensione variabile (VLA) +------------------------------------ + +Usare VLA sullo stack produce codice molto peggiore rispetto a quando si usano +vettori a dimensione fissa. Questi `problemi di prestazioni `_, +tutt'altro che banali, sono già un motivo valido per eliminare i VLA; in +aggiunta sono anche un problema per la sicurezza. La crescita dinamica di un +vettore nello stack potrebbe eccedere la memoria rimanente in tale segmento. +Questo può portare a dei malfunzionamenti, potrebbe sovrascrivere +dati importanti alla fine dello stack (quando il kernel è compilato senza +`CONFIG_THREAD_INFO_IN_TASK=y`), o sovrascrivere un pezzo di memoria adiacente +allo stack (quando il kernel è compilato senza `CONFIG_VMAP_STACK=y`). diff --git a/Documentation/translations/it_IT/process/kernel-enforcement-statement.rst b/Documentation/translations/it_IT/process/kernel-enforcement-statement.rst index 4ddf5a35b270..1f62da622e26 100644 --- a/Documentation/translations/it_IT/process/kernel-enforcement-statement.rst +++ b/Documentation/translations/it_IT/process/kernel-enforcement-statement.rst @@ -1,13 +1,175 @@ .. include:: ../disclaimer-ita.rst :Original: :ref:`Documentation/process/kernel-enforcement-statement.rst ` - +:Translator: Federico Vaga .. _it_process_statement_kernel: Applicazione della licenza sul kernel Linux =========================================== -.. warning:: +Come sviluppatori del kernel Linux, abbiamo un certo interessa su come il +nostro software viene usato e su come la sua licenza viene fatta rispettare. +Il rispetto reciproco degli obblighi di condivisione della GPL-2.0 è +fondamentale per la sostenibilità di lungo periodo del nostro software e +della nostra comunità. + +Benché ognuno abbia il diritto a far rispettare il diritto d'autore per i +propri contributi alla nostra comunità, condividiamo l'interesse a far si che +ogni azione individuale nel far rispettare i propri diritti sia condotta in +modo da portare beneficio alla comunità e che non abbia, involontariamente, +impatti negativi sulla salute e la crescita del nostro ecosistema software. +Al fine di scoraggiare l'esecuzione di azioni inutili, concordiamo che è nel +migliore interesse della nostra comunità di sviluppo di impegnarci nel +rispettare i seguenti obblighi nei confronti degli utenti del kernel Linux +per conto nostro e di qualsiasi successore ai nostri interessi sul diritto +d'autore: + + Malgrado le clausole di risoluzione della licenza GPL-2.0, abbiamo + concordato che è nel migliore interesse della nostra comunità di sviluppo + adottare le seguenti disposizioni della GPL-3.0 come permessi aggiuntivi + alla nostra licenza nei confronti di qualsiasi affermazione non difensiva + di diritti sulla licenza. + + In ogni caso, se cessano tutte le violazioni di questa Licenza, allora + la tua licenza da parte di un dato detentore del copyright viene + ripristinata (a) in via cautelativa, a meno che e fino a quando il + detentore del copyright non cessa esplicitamente e definitivamente + la tua licenza, e (b) in via permanente se il detentore del copyright + non ti notifica in alcun modo la violazione entro 60 giorni dalla + cessazione della licenza. + + Inoltre, la tua licenza da parte di un dato detentore del copyright + viene ripristinata in maniera permanente se il detentore del copyright + ti notifica la violazione in maniera adeguata, se questa è la prima + volta che ricevi una notifica di violazione di questa Licenza (per + qualunque Programma) dallo stesso detentore di copyright, e se rimedi + alla violazione entro 30 giorni dalla data di ricezione della notifica + di violazione. + +Fornendo queste garanzie, abbiamo l'intenzione di incoraggiare l'uso del +software. Vogliamo che le aziende e le persone usino, modifichino e +distribuiscano a questo software. Vogliamo lavorare con gli utenti in modo +aperto e trasparente per eliminare ogni incertezza circa le nostre aspettative +sul rispetto o l'ottemperanza alla licenza che possa limitare l'uso del nostro +software. Vediamo l'azione legale come ultima spiaggia, da avviare solo quando +gli altri sforzi della comunità hanno fallito nel risolvere il problema. + +Per finire, una volta che un problema di non rispetto della licenza viene +risolto, speriamo che gli utenti si sentano i benvenuti ad aggregarsi a noi +nello sviluppo di questo progetto. Lavorando assieme, saremo più forti. + +Ad eccezione deve specificato, parliamo per noi stessi, e non per una qualsiasi +azienda per la quale lavoriamo oggi, o per cui abbiamo lavorato in passato, o +lavoreremo in futuro. + - TODO ancora da tradurre + - Laura Abbott + - Bjorn Andersson (Linaro) + - Andrea Arcangeli + - Neil Armstrong + - Jens Axboe + - Pablo Neira Ayuso + - Khalid Aziz + - Ralf Baechle + - Felipe Balbi + - Arnd Bergmann + - Ard Biesheuvel + - Tim Bird + - Paolo Bonzini + - Christian Borntraeger + - Mark Brown (Linaro) + - Paul Burton + - Javier Martinez Canillas + - Rob Clark + - Kees Cook (Google) + - Jonathan Corbet + - Dennis Dalessandro + - Vivien Didelot (Savoir-faire Linux) + - Hans de Goede + - Mel Gorman (SUSE) + - Sven Eckelmann + - Alex Elder (Linaro) + - Fabio Estevam + - Larry Finger + - Bhumika Goyal + - Andy Gross + - Juergen Gross + - Shawn Guo + - Ulf Hansson + - Stephen Hemminger (Microsoft) + - Tejun Heo + - Rob Herring + - Masami Hiramatsu + - Michal Hocko + - Simon Horman + - Johan Hovold (Hovold Consulting AB) + - Christophe JAILLET + - Olof Johansson + - Lee Jones (Linaro) + - Heiner Kallweit + - Srinivas Kandagatla + - Jan Kara + - Shuah Khan (Samsung) + - David Kershner + - Jaegeuk Kim + - Namhyung Kim + - Colin Ian King + - Jeff Kirsher + - Greg Kroah-Hartman (Linux Foundation) + - Christian König + - Vinod Koul + - Krzysztof Kozlowski + - Viresh Kumar + - Aneesh Kumar K.V + - Julia Lawall + - Doug Ledford + - Chuck Lever (Oracle) + - Daniel Lezcano + - Shaohua Li + - Xin Long + - Tony Luck + - Catalin Marinas (Arm Ltd) + - Mike Marshall + - Chris Mason + - Paul E. McKenney + - Arnaldo Carvalho de Melo + - David S. Miller + - Ingo Molnar + - Kuninori Morimoto + - Trond Myklebust + - Martin K. Petersen (Oracle) + - Borislav Petkov + - Jiri Pirko + - Josh Poimboeuf + - Sebastian Reichel (Collabora) + - Guenter Roeck + - Joerg Roedel + - Leon Romanovsky + - Steven Rostedt (VMware) + - Frank Rowand + - Ivan Safonov + - Anna Schumaker + - Jes Sorensen + - K.Y. Srinivasan + - David Sterba (SUSE) + - Heiko Stuebner + - Jiri Kosina (SUSE) + - Willy Tarreau + - Dmitry Torokhov + - Linus Torvalds + - Thierry Reding + - Rik van Riel + - Luis R. Rodriguez + - Geert Uytterhoeven (Glider bvba) + - Eduardo Valentin (Amazon.com) + - Daniel Vetter + - Linus Walleij + - Richard Weinberger + - Dan Williams + - Rafael J. Wysocki + - Arvind Yadav + - Masahiro Yamada + - Wei Yongjun + - Lv Zheng + - Marc Zyngier (Arm Ltd) diff --git a/Documentation/translations/it_IT/process/license-rules.rst b/Documentation/translations/it_IT/process/license-rules.rst new file mode 100644 index 000000000000..91a8794ffd79 --- /dev/null +++ b/Documentation/translations/it_IT/process/license-rules.rst @@ -0,0 +1,452 @@ +.. SPDX-License-Identifier: GPL-2.0 + +.. include:: ../disclaimer-ita.rst + +:Original: :ref:`Documentation/process/license-rules.rst ` +:Translator: Federico Vaga + +.. _it_kernel_licensing: + +Regole per licenziare il kernel Linux +===================================== + +Il kernel Linux viene rilasciato sotto i termini definiti dalla seconda +versione della licenza *GNU General Public License* (GPL-2.0), di cui una +copia è disponibile nel file LICENSES/preferred/GPL-2.0; a questo si +aggiunge eccezione per le chiamate di sistema come descritto in +LICENSES/exceptions/Linux-syscall-note; tutto ciò è descritto nel file COPYING. + +Questo documento fornisce una descrizione su come ogni singolo file sorgente +debba essere licenziato per far si che sia chiaro e non ambiguo. Questo non +sostituisce la licenza del kernel. + +La licenza descritta nel file COPYING si applica ai sorgenti del kernel nella +loro interezza, quindi i singoli file sorgenti possono avere diverse licenze ma +devono essere compatibili con la GPL-2.0:: + + GPL-1.0+ : GNU General Public License v1.0 o successiva + GPL-2.0+ : GNU General Public License v2.0 o successiva + LGPL-2.0 : GNU Library General Public License v2 + LGPL-2.0+ : GNU Library General Public License v2 o successiva + LGPL-2.1 : GNU Lesser General Public License v2.1 + LGPL-2.1+ : GNU Lesser General Public License v2.1 o successiva + +A parte questo, i singolo file possono essere forniti con una doppia licenza, +per esempio con una delle varianti compatibili della GPL e alternativamente con +una licenza permissiva come BSD, MIT eccetera. + +I file d'intestazione per l'API verso lo spazio utente (UAPI) descrivono +le interfacce usate dai programmi, e per questo sono un caso speciale. +Secondo le note nel file COPYING, le chiamate di sistema sono un chiaro +confine oltre il quale non si estendono i requisiti della GPL per quei +programmi che le usano per comunicare con il kernel. Dato che i file +d'intestazione UAPI devono poter essere inclusi nei sorgenti di un +qualsiasi programma eseguibile sul kernel Linux, questi meritano +un'eccezione documentata da una clausola speciale. + +Il modo più comune per indicare la licenza dei file sorgenti è quello di +aggiungere il corrispondente blocco di testo come commento in testa a detto +file. Per via della formattazione, dei refusi, eccetera, questi blocchi di +testo sono difficili da identificare dagli strumenti usati per verificare il +rispetto delle licenze. + +Un'alternativa ai blocchi di testo è data dall'uso degli identificatori +*Software Package Data Exchange* (SPDX) in ogni file sorgente. Gli +identificatori di licenza SPDX sono analizzabili dalle macchine e sono precisi +simboli stenografici che identificano la licenza sotto la quale viene +licenziato il file che lo include. Gli identificatori di licenza SPDX sono +gestiti del gruppo di lavoro SPDX presso la Linux Foundation e sono stati +concordati fra i soci nell'industria, gli sviluppatori di strumenti, e i +rispettivi gruppi legali. Per maggiori informazioni, consultate +https://spdx.org/ + +Il kernel Linux richiede un preciso identificatore SPDX in tutti i file +sorgenti. Gli identificatori validi verranno spiegati nella sezione +`Identificatori di licenza`_ e sono stati copiati dalla lista ufficiale di +licenze SPDX assieme al rispettivo testo come mostrato in +https://spdx.org/licenses/. + +Sintassi degli identificatori di licenza +---------------------------------------- + +1. Posizionamento: + + L'identificativo di licenza SPDX dev'essere posizionato come prima riga + possibile di un file che possa contenere commenti. Per la maggior parte + dei file questa è la prima riga, fanno eccezione gli script che richiedono + come prima riga '#!PATH_TO_INTERPRETER'. Per questi script l'identificativo + SPDX finisce nella seconda riga. + +| + +2. Stile: + + L'identificativo di licenza SPDX viene aggiunto sotto forma di commento. + Lo stile del commento dipende dal tipo di file:: + + sorgenti C: // SPDX-License-Identifier: + intestazioni C: /* SPDX-License-Identifier: */ + ASM: /* SPDX-License-Identifier: */ + scripts: # SPDX-License-Identifier: + .rst: .. SPDX-License-Identifier: + .dts{i}: // SPDX-License-Identifier: + + Se un particolare programma non dovesse riuscire a gestire lo stile + principale per i commenti, allora dev'essere usato il meccanismo accettato + dal programma. Questo è il motivo per cui si ha "/\* \*/" nei file + d'intestazione C. Notammo che 'ld' falliva nell'analizzare i commenti del + C++ nei file .lds che venivano prodotti. Oggi questo è stato corretto, + ma ci sono in giro ancora vecchi programmi che non sono in grado di + gestire lo stile dei commenti del C++. + +| + +3. Sintassi: + + Una può essere scritta usando l'identificatore + SPDX della licenza come indicato nella lista di licenze SPDX, oppure la + combinazione di due identificatori SPDX separati da "WITH" per i casi + eccezionali. Quando si usano più licenze l'espressione viene formata da + sottoespressioni separate dalle parole chiave "AND", "OR" e racchiuse fra + parentesi tonde "(", ")". + + Gli identificativi di licenza per licenze come la [L]GPL che si avvalgono + dell'opzione 'o successive' si formano aggiungendo alla fine il simbolo "+" + per indicare l'opzione 'o successive'.:: + + // SPDX-License-Identifier: GPL-2.0+ + // SPDX-License-Identifier: LGPL-2.1+ + + WITH dovrebbe essere usato quando sono necessarie delle modifiche alla + licenza. Per esempio, la UAPI del kernel linux usa l'espressione:: + + // SPDX-License-Identifier: GPL-2.0 WITH Linux-syscall-note + // SPDX-License-Identifier: GPL-2.0+ WITH Linux-syscall-note + + Altri esempi di usi di WITH all'interno del kernel sono:: + + // SPDX-License-Identifier: GPL-2.0 WITH mif-exception + // SPDX-License-Identifier: GPL-2.0+ WITH GCC-exception-2.0 + + Le eccezioni si possono usare solo in combinazione con identificatori di + licenza. Gli identificatori di licenza riconosciuti sono elencati nei + corrispondenti file d'eccezione. Per maggiori dettagli consultate + `Eccezioni`_ nel capitolo `Identificatori di licenza`_ + + La parola chiave OR dovrebbe essere usata solo quando si usa una doppia + licenza e solo una dev'essere scelta. Per esempio, alcuni file dtsi sono + disponibili con doppia licenza:: + + // SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause + + Esempi dal kernel di espressioni per file licenziati con doppia licenza + sono:: + + // SPDX-License-Identifier: GPL-2.0 OR MIT + // SPDX-License-Identifier: GPL-2.0 OR BSD-2-Clause + // SPDX-License-Identifier: GPL-2.0 OR Apache-2.0 + // SPDX-License-Identifier: GPL-2.0 OR MPL-1.1 + // SPDX-License-Identifier: (GPL-2.0 WITH Linux-syscall-note) OR MIT + // SPDX-License-Identifier: GPL-1.0+ OR BSD-3-Clause OR OpenSSL + + La parola chiave AND dovrebbe essere usata quando i termini di più licenze + si applicano ad un file. Per esempio, quando il codice viene preso da + un altro progetto il quale da i permessi per aggiungerlo nel kernel ma + richiede che i termini originali della licenza rimangano intatti:: + + // SPDX-License-Identifier: (GPL-2.0 WITH Linux-syscall-note) AND MIT + + Di seguito, un altro esempio dove entrambe i termini di licenza devono + essere rispettati:: + + // SPDX-License-Identifier: GPL-1.0+ AND LGPL-2.1+ + +Identificatori di licenza +------------------------- + +Le licenze attualmente in uso, così come le licenze aggiunte al kernel, possono +essere categorizzate in: + +1. _`Licenze raccomandate`: + + Ovunque possibile le licenze qui indicate dovrebbero essere usate perché + pienamente compatibili e molto usate. Queste licenze sono disponibile nei + sorgenti del kernel, nella cartella:: + + LICENSES/preferred/ + + I file in questa cartella contengono il testo completo della licenza e i + `Metatag`_. Il nome di questi file è lo stesso usato come identificatore + di licenza SPDX e che deve essere usato nei file sorgenti. + + Esempi:: + + LICENSES/preferred/GPL-2.0 + + Contiene il testo della seconda versione della licenza GPL e i metatag + necessari:: + + LICENSES/preferred/MIT + + Contiene il testo della licenza MIT e i metatag necessari. + + _`Metatag`: + + I seguenti metatag devono essere presenti in un file di licenza: + + - Valid-License-Identifier: + + Una o più righe che dichiarano quali identificatori di licenza sono validi + all'interno del progetto per far riferimento alla licenza in questione. + Solitamente, questo è un unico identificatore valido, ma per esempio le + licenze che permettono l'opzione 'o successive' hanno due identificatori + validi. + + - SPDX-URL: + + L'URL della pagina SPDX che contiene informazioni aggiuntive riguardanti + la licenza. + + - Usage-Guidance: + + Testo in formato libero per dare suggerimenti agli utenti. Il testo deve + includere degli esempi su come usare gli identificatori di licenza SPDX + in un file sorgente in conformità con le linea guida in + `Sintassi degli identificatori di licenza`_. + + - License-Text: + + Tutto il testo che compare dopo questa etichetta viene trattato + come se fosse parte del testo originale della licenza. + + Esempi:: + + Valid-License-Identifier: GPL-2.0 + Valid-License-Identifier: GPL-2.0+ + SPDX-URL: https://spdx.org/licenses/GPL-2.0.html + Usage-Guide: + To use this license in source code, put one of the following SPDX + tag/value pairs into a comment according to the placement + guidelines in the licensing rules documentation. + For 'GNU General Public License (GPL) version 2 only' use: + SPDX-License-Identifier: GPL-2.0 + For 'GNU General Public License (GPL) version 2 or any later version' use: + SPDX-License-Identifier: GPL-2.0+ + License-Text: + Full license text + + :: + + SPDX-License-Identifier: MIT + SPDX-URL: https://spdx.org/licenses/MIT.html + Usage-Guide: + To use this license in source code, put the following SPDX + tag/value pair into a comment according to the placement + guidelines in the licensing rules documentation. + SPDX-License-Identifier: MIT + License-Text: + Full license text + +| + +2. Licenze non raccomandate: + + Questo tipo di licenze dovrebbero essere usate solo per codice già esistente + o quando si prende codice da altri progetti. Le licenze sono disponibili + nei sorgenti del kernel nella cartella:: + + LICENSES/other/ + + I file in questa cartella contengono il testo completo della licenza e i + `Metatag`_. Il nome di questi file è lo stesso usato come identificatore + di licenza SPDX e che deve essere usato nei file sorgenti. + + Esempi:: + + LICENSES/other/ISC + + Contiene il testo della licenza Internet System Consortium e i suoi + metatag:: + + LICENSES/other/ZLib + + Contiene il testo della licenza ZLIB e i suoi metatag. + + Metatag: + + I metatag necessari per le 'altre' ('other') licenze sono gli stessi + di usati per le `Licenze raccomandate`_. + + Esempio del formato del file:: + + Valid-License-Identifier: ISC + SPDX-URL: https://spdx.org/licenses/ISC.html + Usage-Guide: + Usage of this license in the kernel for new code is discouraged + and it should solely be used for importing code from an already + existing project. + To use this license in source code, put the following SPDX + tag/value pair into a comment according to the placement + guidelines in the licensing rules documentation. + SPDX-License-Identifier: ISC + License-Text: + Full license text + +| + +3. _`Eccezioni`: + + Alcune licenze possono essere corrette con delle eccezioni che forniscono + diritti aggiuntivi. Queste eccezioni sono disponibili nei sorgenti del + kernel nella cartella:: + + LICENSES/exceptions/ + + I file in questa cartella contengono il testo completo dell'eccezione e i + `Metatag per le eccezioni`_. + + Esempi:: + + LICENSES/exceptions/Linux-syscall-note + + Contiene la descrizione dell'eccezione per le chiamate di sistema Linux + così come documentato nel file COPYING del kernel Linux; questo viene usato + per i file d'intestazione per la UAPI. Per esempio + /\* SPDX-License-Identifier: GPL-2.0 WITH Linux-syscall-note \*/:: + + LICENSES/exceptions/GCC-exception-2.0 + + Contiene la 'eccezione di linking' che permette di collegare qualsiasi + binario, indipendentemente dalla sua licenza, con un compilato il cui file + sorgente è marchiato con questa eccezione. Questo è necessario per creare + eseguibili dai sorgenti che non sono compatibili con la GPL. + + _`Metatag per le eccezioni`: + + Un file contenente un'eccezione deve avere i seguenti metatag: + + - SPDX-Exception-Identifier: + + Un identificatore d'eccezione che possa essere usato in combinazione con + un identificatore di licenza SPDX. + + - SPDX-URL: + + L'URL della pagina SPDX che contiene informazioni aggiuntive riguardanti + l'eccezione. + + - SPDX-Licenses: + + Una lista di licenze SPDX separate da virgola, che possono essere usate + con l'eccezione. + + - Usage-Guidance: + + Testo in formato libero per dare suggerimenti agli utenti. Il testo deve + includere degli esempi su come usare gli identificatori di licenza SPDX + in un file sorgente in conformità con le linea guida in + `Sintassi degli identificatori di licenza`_. + + - Exception-Text: + + Tutto il testo che compare dopo questa etichetta viene trattato + come se fosse parte del testo originale della licenza. + + Esempi:: + + SPDX-Exception-Identifier: Linux-syscall-note + SPDX-URL: https://spdx.org/licenses/Linux-syscall-note.html + SPDX-Licenses: GPL-2.0, GPL-2.0+, GPL-1.0+, LGPL-2.0, LGPL-2.0+, LGPL-2.1, LGPL-2.1+ + Usage-Guidance: + This exception is used together with one of the above SPDX-Licenses + to mark user-space API (uapi) header files so they can be included + into non GPL compliant user-space application code. + To use this exception add it with the keyword WITH to one of the + identifiers in the SPDX-Licenses tag: + SPDX-License-Identifier: WITH Linux-syscall-note + Exception-Text: + Full exception text + + :: + + SPDX-Exception-Identifier: GCC-exception-2.0 + SPDX-URL: https://spdx.org/licenses/GCC-exception-2.0.html + SPDX-Licenses: GPL-2.0, GPL-2.0+ + Usage-Guidance: + The "GCC Runtime Library exception 2.0" is used together with one + of the above SPDX-Licenses for code imported from the GCC runtime + library. + To use this exception add it with the keyword WITH to one of the + identifiers in the SPDX-Licenses tag: + SPDX-License-Identifier: WITH GCC-exception-2.0 + Exception-Text: + Full exception text + +Per ogni identificatore di licenza SPDX e per le eccezioni dev'esserci un file +nella sotto-cartella LICENSES. Questo è necessario per permettere agli +strumenti di effettuare verifiche (come checkpatch.pl), per avere le licenze +disponibili per la lettura e per estrarre i diritti dai sorgenti, così come +raccomandato da diverse organizzazioni FOSS, per esempio l'`iniziativa FSFE +REUSE `_. + +_`MODULE_LICENSE` +----------------- + + I moduli del kernel necessitano di un'etichetta MODULE_LICENSE(). Questa + etichetta non sostituisce le informazioni sulla licenza del codice sorgente + (SPDX-License-Identifier) né fornisce informazioni che esprimono o + determinano l'esatta licenza sotto la quale viene rilasciato. + + Il solo scopo di questa etichetta è quello di fornire sufficienti + informazioni al caricatore di moduli del kernel, o agli strumenti in spazio + utente, per capire se il modulo è libero o proprietario. + + Le stringe di licenza valide per MODULE_LICENSE() sono: + + ============================= ============================================= + "GPL" Il modulo è licenziato con la GPL versione 2. + Questo non fa distinzione fra GPL'2.0-only o + GPL-2.0-or-later. L'esatta licenza può essere + determinata solo leggendo i corrispondenti + file sorgenti. + + "GPL v2" Stesso significato di "GPL". Esiste per + motivi storici. + + "GPL and additional rights" Questa è una variante che esiste per motivi + storici che indica che i sorgenti di un + modulo sono rilasciati sotto una variante + della licenza GPL v2 e quella MIT. Per favore + non utilizzatela per codice nuovo. + + "Dual MIT/GPL" Questo è il modo corretto per esprimere il + il fatto che il modulo è rilasciato con + doppia licenza a scelta fra: una variante + della GPL v2 o la licenza MIT. + + "Dual BSD/GPL" Questo modulo è rilasciato con doppia licenza + a scelta fra: una variante della GPL v2 o la + licenza BSD. La variante esatta della licenza + BSD può essere determinata solo attraverso i + corrispondenti file sorgenti. + + "Dual MPL/GPL" Questo modulo è rilasciato con doppia licenza + a scelta fra: una variante della GPL v2 o la + Mozilla Public License (MPL). La variante + esatta della licenza MPL può essere + determinata solo attraverso i corrispondenti + file sorgenti. + + "Proprietary" Questo modulo è rilasciato con licenza + proprietaria. Questa stringa è solo per i + moduli proprietari di terze parti e non può + essere usata per quelli che risiedono nei + sorgenti del kernel. I moduli etichettati in + questo modo stanno contaminando il kernel e + gli viene assegnato un flag 'P'; quando + vengono caricati, il caricatore di moduli del + kernel si rifiuterà di collegare questi + moduli ai simboli che sono stati esportati + con EXPORT_SYMBOL_GPL(). + + ============================= ============================================= diff --git a/Documentation/translations/it_IT/process/stable-kernel-rules.rst b/Documentation/translations/it_IT/process/stable-kernel-rules.rst index 6fa5ce9c3572..48e88e5ad2c5 100644 --- a/Documentation/translations/it_IT/process/stable-kernel-rules.rst +++ b/Documentation/translations/it_IT/process/stable-kernel-rules.rst @@ -1,12 +1,202 @@ .. include:: ../disclaimer-ita.rst :Original: :ref:`Documentation/process/stable-kernel-rules.rst ` +:Translator: Federico Vaga .. _it_stable_kernel_rules: Tutto quello che volevate sapere sui rilasci -stable di Linux ============================================================== -.. warning:: +Regole sul tipo di patch che vengono o non vengono accettate nei sorgenti +"-stable": - TODO ancora da tradurre + - Ovviamente dev'essere corretta e verificata. + - Non dev'essere più grande di 100 righe, incluso il contesto. + - Deve correggere una cosa sola. + - Deve correggere un baco vero che sta disturbando gli utenti (non cose del + tipo "Questo potrebbe essere un problema ..."). + - Deve correggere un problema di compilazione (ma non per cose già segnate + con CONFIG_BROKEN), un kernel oops, un blocco, una corruzione di dati, + un vero problema di sicurezza, o problemi del tipo "oh, questo non va bene". + In pratica, qualcosa di critico. + - Problemi importanti riportati dagli utenti di una distribuzione potrebbero + essere considerati se correggono importanti problemi di prestazioni o di + interattività. Dato che questi problemi non sono così ovvi e la loro + correzione ha un'alta probabilità d'introdurre una regressione, dovrebbero + essere sottomessi solo dal manutentore della distribuzione includendo un + link, se esiste, ad un rapporto su bugzilla, e informazioni aggiuntive + sull'impatto che ha sugli utenti. + - Non deve correggere problemi relativi a una "teorica sezione critica", + a meno che non venga fornita anche una spiegazione su come questa si + possa verificare. + - Non deve includere alcuna correzione "banale" (correzioni grammaticali, + pulizia dagli spazi bianchi, eccetera). + - Deve rispettare le regole scritte in + :ref:`Documentation/translation/it_IT/process/submitting-patches.rst ` + - Questa patch o una equivalente deve esistere già nei sorgenti principali di + Linux + + +Procedura per sottomettere patch per i sorgenti -stable +------------------------------------------------------- + + - Se la patch contiene modifiche a dei file nelle cartelle net/ o drivers/net, + allora seguite le linee guida descritte in + :ref:`Documentation/translation/it_IT/networking/netdev-FAQ.rst `; + ma solo dopo aver verificato al seguente indirizzo che la patch non sia + già in coda: + https://patchwork.ozlabs.org/bundle/davem/stable/?series=&submitter=&state=*&q=&archive= + - Una patch di sicurezza non dovrebbero essere gestite (solamente) dal processo + di revisione -stable, ma dovrebbe seguire le procedure descritte in + :ref:`Documentation/translations/it_IT/admin-guide/security-bugs.rst `. + + +Per tutte le altre sottomissioni, scegliere una delle seguenti procedure +------------------------------------------------------------------------ + +.. _it_option_1: + +Opzione 1 +********* + +Per far sì che una patch venga automaticamente inclusa nei sorgenti stabili, +aggiungete l'etichetta + +.. code-block:: none + + Cc: stable@vger.kernel.org + +nell'area dedicata alla firme. Una volta che la patch è stata inclusa, verrà +applicata anche sui sorgenti stabili senza che l'autore o il manutentore +del sottosistema debba fare qualcosa. + +.. _it_option_2: + +Opzione 2 +********* + +Dopo che la patch è stata inclusa nei sorgenti Linux, inviate una mail a +stable@vger.kernel.org includendo: il titolo della patch, l'identificativo +del commit, il perché pensate che debba essere applicata, e in quale versione +del kernel la vorreste vedere. + +.. _it_option_3: + +Opzione 3 +********* + +Inviata la patch, dopo aver verificato che rispetta le regole descritte in +precedenza, a stable@vger.kernel.org. Dovete annotare nel changelog +l'identificativo del commit nei sorgenti principali, così come la versione +del kernel nel quale vorreste vedere la patch. + +L':ref:`it_option_1` è fortemente raccomandata; è il modo più facile e usato. +L':ref:`it_option_2` e l':ref:`it_option_3` sono più utili quando, al momento +dell'inclusione dei sorgenti principali, si ritiene che non debbano essere +incluse anche in quelli stabili (per esempio, perché si crede che si dovrebbero +fare più verifiche per eventuali regressioni). L':ref:`it_option_3` è +particolarmente utile se la patch ha bisogno di qualche modifica per essere +applicata ad un kernel più vecchio (per esempio, perché nel frattempo l'API è +cambiata). + +Notate che per l':ref:`it_option_3`, se la patch è diversa da quella nei +sorgenti principali (per esempio perché è stato necessario un lavoro di +adattamento) allora dev'essere ben documentata e giustificata nella descrizione +della patch. + +L'identificativo del commit nei sorgenti principali dev'essere indicato sopra +al messaggio della patch, così: + +.. code-block:: none + + commit upstream. + +In aggiunta, alcune patch inviate attraverso l':ref:`it_option_1` potrebbero +dipendere da altre che devo essere incluse. Questa situazione può essere +indicata nel seguente modo nell'area dedicata alle firme: + +.. code-block:: none + + Cc: # 3.3.x: a1f84a3: sched: Check for idle + Cc: # 3.3.x: 1b9508f: sched: Rate-limit newidle + Cc: # 3.3.x: fd21073: sched: Fix affinity logic + Cc: # 3.3.x + Signed-off-by: Ingo Molnar + +La sequenza di etichette ha il seguente significato: + +.. code-block:: none + + git cherry-pick a1f84a3 + git cherry-pick 1b9508f + git cherry-pick fd21073 + git cherry-pick + +Inoltre, alcune patch potrebbero avere dei requisiti circa la versione del +kernel. Questo può essere indicato usando il seguente formato nell'area +dedicata alle firme: + +.. code-block:: none + + Cc: # 3.3.x + +L'etichetta ha il seguente significato: + +.. code-block:: none + + git cherry-pick + +per ogni sorgente "-stable" che inizia con la versione indicata. + +Dopo la sottomissione: + + - Il mittente riceverà un ACK quando la patch è stata accettata e messa in + coda, oppure un NAK se la patch è stata rigettata. A seconda degli impegni + degli sviluppatori, questa risposta potrebbe richiedere alcuni giorni. + - Se accettata, la patch verrà aggiunta alla coda -stable per essere + revisionata dal altri sviluppatori e dal principale manutentore del + sottosistema. + + +Ciclo di una revisione +---------------------- + + - Quando i manutentori -stable decidono di fare un ciclo di revisione, le + patch vengono mandate al comitato per la revisione, ai manutentori soggetti + alle modifiche delle patch (a meno che il mittente non sia anche il + manutentore di quell'area del kernel) e in CC: alla lista di discussione + linux-kernel. + - La commissione per la revisione ha 48 ore per dare il proprio ACK o NACK + alle patch. + - Se una patch viene rigettata da un membro della commissione, o un membro + della lista linux-kernel obietta la bontà della patch, sollevando problemi + che i manutentori ed i membri non avevano compreso, allora la patch verrà + rimossa dalla coda. + - Alla fine del ciclo di revisione tutte le patch che hanno ricevuto l'ACK + verranno aggiunte per il prossimo rilascio -stable, e successivamente + questo nuovo rilascio verrà fatto. + - Le patch di sicurezza verranno accettate nei sorgenti -stable direttamente + dalla squadra per la sicurezza del kernel, e non passerà per il normale + ciclo di revisione. Contattate la suddetta squadra per maggiori dettagli + su questa procedura. + +Sorgenti +-------- + + - La coda delle patch, sia quelle già applicate che in fase di revisione, + possono essere trovate al seguente indirizzo: + + https://git.kernel.org/pub/scm/linux/kernel/git/stable/stable-queue.git + + - Il rilascio definitivo, e marchiato, di tutti i kernel stabili può essere + trovato in rami distinti per versione al seguente indirizzo: + + https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux-stable.git + + +Comitato per la revisione +------------------------- + + - Questo comitato è fatto di sviluppatori del kernel che si sono offerti + volontari per questo lavoro, e pochi altri che non sono proprio volontari. -- cgit v1.2.3 From 71c873080200912a053e1d897c5106e6b65f5309 Mon Sep 17 00:00:00 2001 From: Sakari Ailus Date: Tue, 26 Feb 2019 12:42:58 +0200 Subject: ACPI: Document how to refer to LEDs from remote nodes Document referring to LEDs from remote device nodes, such as from camera sensors. Signed-off-by: Sakari Ailus Acked-by: Rafael J. Wysocki Signed-off-by: Jacek Anaszewski --- Documentation/acpi/dsd/leds.txt | 99 +++++++++++++++++++++++++++++++++++++++++ 1 file changed, 99 insertions(+) create mode 100644 Documentation/acpi/dsd/leds.txt (limited to 'Documentation') diff --git a/Documentation/acpi/dsd/leds.txt b/Documentation/acpi/dsd/leds.txt new file mode 100644 index 000000000000..81a63af42ed2 --- /dev/null +++ b/Documentation/acpi/dsd/leds.txt @@ -0,0 +1,99 @@ +Describing and referring to LEDs in ACPI + +Individual LEDs are described by hierarchical data extension [6] nodes under the +device node, the LED driver chip. The "reg" property in the LED specific nodes +tells the numerical ID of each individual LED output to which the LEDs are +connected. [3] The hierarchical data nodes are named "led@X", where X is the +number of the LED output. + +Referring to LEDs in Device tree is documented in [4], in "flash-leds" property +documentation. In short, LEDs are directly referred to by using phandles. + +While Device tree allows referring to any node in the tree[1], in ACPI +references are limited to device nodes only [2]. For this reason using the same +mechanism on ACPI is not possible. A mechanism to refer to non-device ACPI nodes +is documented in [7]. + +ACPI allows (as does DT) using integer arguments after the reference. A +combination of the LED driver device reference and an integer argument, +referring to the "reg" property of the relevant LED, is used to identify +individual LEDs. The value of the "reg" property is a contract between the +firmware and software, it uniquely identifies the LED driver outputs. + +Under the LED driver device, The first hierarchical data extension package list +entry shall contain the string "led@" followed by the number of the LED, +followed by the referred object name. That object shall be named "LED" followed +by the number of the LED. + +An ASL example of a camera sensor device and a LED driver device for two LEDs. +Objects not relevant for LEDs or the references to them have been omitted. + + Device (LED) + { + Name (_DSD, Package () { + ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), + Package () { + Package () { "led@0", LED0 }, + Package () { "led@1", LED1 }, + } + }) + Name (LED0, Package () { + ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), + Package () { + Package () { "reg", 0 }, + Package () { "flash-max-microamp", 1000000 }, + Package () { "flash-timeout-us", 200000 }, + Package () { "led-max-microamp", 100000 }, + Package () { "label", "white:flash" }, + } + }) + Name (LED1, Package () { + ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), + Package () { + Package () { "reg", 1 }, + Package () { "led-max-microamp", 10000 }, + Package () { "label", "red:indicator" }, + } + }) + } + + Device (SEN) + { + Name (_DSD, Package () { + ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), + Package () { + Package () { + "flash-leds", + Package () { ^LED, "led@0", ^LED, "led@1" }, + } + } + }) + } + +where + + LED LED driver device + LED0 First LED + LED1 Second LED + SEN Camera sensor device (or another device the LED is + related to) + +[1] Device tree. , referenced 2019-02-21. + +[2] Advanced Configuration and Power Interface Specification. + , + referenced 2019-02-21. + +[3] Documentation/devicetree/bindings/leds/common.txt + +[4] Documentation/devicetree/bindings/media/video-interfaces.txt + +[5] Device Properties UUID For _DSD. + , + referenced 2019-02-21. + +[6] Hierarchical Data Extension UUID For _DSD. + , + referenced 2019-02-21. + +[7] Documentation/acpi/dsd/data-node-reference.txt -- cgit v1.2.3 From 29f6c4227e450cd9d20615c08478bd4d3e04a711 Mon Sep 17 00:00:00 2001 From: Biju Das Date: Fri, 1 Mar 2019 10:45:33 -0500 Subject: media: dt-bindings: media: rcar-csi2: Add r8a774a1 support MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Document RZ/G2M (R8A774A1) SoC bindings. The RZ/G2M SoC is similar to R-Car M3-W (R8A7796). Signed-off-by: Biju Das Reviewed-by: Fabrizio Castro Acked-by: Niklas Söderlund Reviewed-by: Simon Horman Reviewed-by: Rob Herring Signed-off-by: Hans Verkuil Signed-off-by: Mauro Carvalho Chehab --- Documentation/devicetree/bindings/media/renesas,rcar-csi2.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/media/renesas,rcar-csi2.txt b/Documentation/devicetree/bindings/media/renesas,rcar-csi2.txt index d63275e17afd..9932458a0a45 100644 --- a/Documentation/devicetree/bindings/media/renesas,rcar-csi2.txt +++ b/Documentation/devicetree/bindings/media/renesas,rcar-csi2.txt @@ -8,6 +8,7 @@ R-Car VIN module, which provides the video capture capabilities. Mandatory properties -------------------- - compatible: Must be one or more of the following + - "renesas,r8a774a1-csi2" for the R8A774A1 device. - "renesas,r8a774c0-csi2" for the R8A774C0 device. - "renesas,r8a7795-csi2" for the R8A7795 device. - "renesas,r8a7796-csi2" for the R8A7796 device. -- cgit v1.2.3 From b8f92200d16e68e51c55f8ea7c2e251c423aac76 Mon Sep 17 00:00:00 2001 From: Biju Das Date: Fri, 1 Mar 2019 10:45:35 -0500 Subject: media: dt-bindings: media: rcar_vin: Add r8a774a1 support MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Document RZ/G2M (R8A774A1) SoC bindings. The RZ/G2M SoC is similar to R-Car M3-W (R8A7796). Signed-off-by: Biju Das Reviewed-by: Fabrizio Castro Acked-by: Niklas Söderlund Reviewed-by: Simon Horman Reviewed-by: Rob Herring Signed-off-by: Hans Verkuil Signed-off-by: Mauro Carvalho Chehab --- Documentation/devicetree/bindings/media/rcar_vin.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/media/rcar_vin.txt b/Documentation/devicetree/bindings/media/rcar_vin.txt index 224a4615b418..aa217b096279 100644 --- a/Documentation/devicetree/bindings/media/rcar_vin.txt +++ b/Documentation/devicetree/bindings/media/rcar_vin.txt @@ -13,6 +13,7 @@ on Gen3 and RZ/G2 platforms to a CSI-2 receiver. - "renesas,vin-r8a7743" for the R8A7743 device - "renesas,vin-r8a7744" for the R8A7744 device - "renesas,vin-r8a7745" for the R8A7745 device + - "renesas,vin-r8a774a1" for the R8A774A1 device - "renesas,vin-r8a774c0" for the R8A774C0 device - "renesas,vin-r8a7778" for the R8A7778 device - "renesas,vin-r8a7779" for the R8A7779 device -- cgit v1.2.3 From dfecb7b2564dcb5fa0c36a615b0d5960eff413ac Mon Sep 17 00:00:00 2001 From: Jernej Skrabec Date: Mon, 28 Jan 2019 15:54:59 -0500 Subject: media: dt-bindings: media: cedrus: Add H6 compatible This adds a compatible for H6. H6 VPU supports 10-bit HEVC decoding and additional AFBC output format for HEVC. Signed-off-by: Jernej Skrabec Acked-by: Maxime Ripard Reviewed-by: Rob Herring Signed-off-by: Hans Verkuil Signed-off-by: Mauro Carvalho Chehab --- Documentation/devicetree/bindings/media/cedrus.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/media/cedrus.txt b/Documentation/devicetree/bindings/media/cedrus.txt index bce0705df953..20c82fb0c343 100644 --- a/Documentation/devicetree/bindings/media/cedrus.txt +++ b/Documentation/devicetree/bindings/media/cedrus.txt @@ -13,6 +13,7 @@ Required properties: - "allwinner,sun8i-h3-video-engine" - "allwinner,sun50i-a64-video-engine" - "allwinner,sun50i-h5-video-engine" + - "allwinner,sun50i-h6-video-engine" - reg : register base and length of VE; - clocks : list of clock specifiers, corresponding to entries in the clock-names property; -- cgit v1.2.3 From 55a1fa9538bf88935cadf34df997c1189735648e Mon Sep 17 00:00:00 2001 From: Stanley Chu Date: Sat, 16 Mar 2019 13:04:44 +0800 Subject: scsi: dt-bindings: phy: Add document for phy-mtk-ufs Add UFS M-PHY node document for MediaTek SoC chips. Signed-off-by: Stanley Chu Reviewed-by: Rob Herring Signed-off-by: Martin K. Petersen --- .../devicetree/bindings/phy/phy-mtk-ufs.txt | 38 ++++++++++++++++++++++ 1 file changed, 38 insertions(+) create mode 100644 Documentation/devicetree/bindings/phy/phy-mtk-ufs.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/phy/phy-mtk-ufs.txt b/Documentation/devicetree/bindings/phy/phy-mtk-ufs.txt new file mode 100644 index 000000000000..5789029a1d42 --- /dev/null +++ b/Documentation/devicetree/bindings/phy/phy-mtk-ufs.txt @@ -0,0 +1,38 @@ +MediaTek Universal Flash Storage (UFS) M-PHY binding +-------------------------------------------------------- + +UFS M-PHY nodes are defined to describe on-chip UFS M-PHY hardware macro. +Each UFS M-PHY node should have its own node. + +To bind UFS M-PHY with UFS host controller, the controller node should +contain a phandle reference to UFS M-PHY node. + +Required properties for UFS M-PHY nodes: +- compatible : Compatible list, contains the following controller: + "mediatek,mt8183-ufsphy" for ufs phy + persent on MT81xx chipsets. +- reg : Address and length of the UFS M-PHY register set. +- #phy-cells : This property shall be set to 0. +- clocks : List of phandle and clock specifier pairs. +- clock-names : List of clock input name strings sorted in the same + order as the clocks property. Following clocks are + mandatory. + "unipro": Unipro core control clock. + "mp": M-PHY core control clock. + +Example: + + ufsphy: phy@11fa0000 { + compatible = "mediatek,mt8183-ufsphy"; + reg = <0 0x11fa0000 0 0xc000>; + #phy-cells = <0>; + + clocks = <&infracfg_ao INFRACFG_AO_UNIPRO_SCK_CG>, + <&infracfg_ao INFRACFG_AO_UFS_MP_SAP_BCLK_CG>; + clock-names = "unipro", "mp"; + }; + + ufshci@11270000 { + ... + phys = <&ufsphy>; + }; -- cgit v1.2.3 From e95424f009af2b2ba6f10b30c33977f2beb9a5ae Mon Sep 17 00:00:00 2001 From: Stanley Chu Date: Sat, 16 Mar 2019 13:04:45 +0800 Subject: scsi: dt-bindings: ufs: Add document for ufs-mediatek Add UFS and UFS PHY node document for Mediatek SoC chips. Signed-off-by: Stanley Chu Reviewed-by: Rob Herring Signed-off-by: Martin K. Petersen --- .../devicetree/bindings/ufs/ufs-mediatek.txt | 40 ++++++++++++++++++++++ 1 file changed, 40 insertions(+) create mode 100644 Documentation/devicetree/bindings/ufs/ufs-mediatek.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/ufs/ufs-mediatek.txt b/Documentation/devicetree/bindings/ufs/ufs-mediatek.txt new file mode 100644 index 000000000000..e25c007b95d7 --- /dev/null +++ b/Documentation/devicetree/bindings/ufs/ufs-mediatek.txt @@ -0,0 +1,40 @@ +* Mediatek Universal Flash Storage (UFS) Host Controller + +UFS nodes are defined to describe on-chip UFS hardware macro. +Each UFS Host Controller should have its own node. + +To bind UFS PHY with UFS host controller, the controller node should +contain a phandle reference to UFS M-PHY node. + +Required properties for UFS nodes: +- compatible : Compatible list, contains the following controller: + "mediatek,mt8183-ufshci" for MediaTek UFS host controller + present on MT81xx chipsets. +- reg : Address and length of the UFS register set. +- phys : phandle to m-phy. +- clocks : List of phandle and clock specifier pairs. +- clock-names : List of clock input name strings sorted in the same + order as the clocks property. "ufs" is mandatory. + "ufs": ufshci core control clock. +- freq-table-hz : Array of operating frequencies stored in the same + order as the clocks property. If this property is not + defined or a value in the array is "0" then it is assumed + that the frequency is set by the parent clock or a + fixed rate clock source. + +Example: + + ufsphy: phy@11fa0000 { + ... + }; + + ufshci@11270000 { + compatible = "mediatek,mt8183-ufshci"; + reg = <0 0x11270000 0 0x2300>; + interrupts = ; + phys = <&ufsphy>; + + clocks = <&infracfg_ao INFRACFG_AO_UFS_CG>; + clock-names = "ufs"; + freq-table-hz = <0 0>; + }; -- cgit v1.2.3 From 03f1eccc7a69c965351e6bee41c62afa2844752f Mon Sep 17 00:00:00 2001 From: Stephen Suryaputra Date: Tue, 19 Mar 2019 12:37:12 -0400 Subject: ipv6: Add icmp_echo_ignore_multicast support for ICMPv6 IPv4 has icmp_echo_ignore_broadcast to prevent responding to broadcast pings. IPv6 needs a similar mechanism. v1->v2: - Remove NET_IPV6_ICMP_ECHO_IGNORE_MULTICAST. Signed-off-by: Stephen Suryaputra Signed-off-by: David S. Miller --- Documentation/networking/ip-sysctl.txt | 5 +++++ include/net/netns/ipv6.h | 1 + net/ipv6/af_inet6.c | 1 + net/ipv6/icmp.c | 12 ++++++++++++ 4 files changed, 19 insertions(+) (limited to 'Documentation') diff --git a/Documentation/networking/ip-sysctl.txt b/Documentation/networking/ip-sysctl.txt index acdfb5d2bcaa..55ea7def46be 100644 --- a/Documentation/networking/ip-sysctl.txt +++ b/Documentation/networking/ip-sysctl.txt @@ -1918,6 +1918,11 @@ echo_ignore_all - BOOLEAN requests sent to it over the IPv6 protocol. Default: 0 +echo_ignore_multicast - BOOLEAN + If set non-zero, then the kernel will ignore all ICMP ECHO + requests sent to it over the IPv6 protocol via multicast. + Default: 0 + xfrm6_gc_thresh - INTEGER The threshold at which we will start garbage collecting for IPv6 destination cache entries. At twice this value the system will diff --git a/include/net/netns/ipv6.h b/include/net/netns/ipv6.h index b028a1dc150d..e29aff15acc9 100644 --- a/include/net/netns/ipv6.h +++ b/include/net/netns/ipv6.h @@ -33,6 +33,7 @@ struct netns_sysctl_ipv6 { int auto_flowlabels; int icmpv6_time; int icmpv6_echo_ignore_all; + int icmpv6_echo_ignore_multicast; int anycast_src_echo_reply; int ip_nonlocal_bind; int fwmark_reflect; diff --git a/net/ipv6/af_inet6.c b/net/ipv6/af_inet6.c index 2f45d2a3e3a3..fdc117de849c 100644 --- a/net/ipv6/af_inet6.c +++ b/net/ipv6/af_inet6.c @@ -847,6 +847,7 @@ static int __net_init inet6_net_init(struct net *net) net->ipv6.sysctl.bindv6only = 0; net->ipv6.sysctl.icmpv6_time = 1*HZ; net->ipv6.sysctl.icmpv6_echo_ignore_all = 0; + net->ipv6.sysctl.icmpv6_echo_ignore_multicast = 0; net->ipv6.sysctl.flowlabel_consistency = 1; net->ipv6.sysctl.auto_flowlabels = IP6_DEFAULT_AUTO_FLOW_LABELS; net->ipv6.sysctl.idgen_retries = 3; diff --git a/net/ipv6/icmp.c b/net/ipv6/icmp.c index 802faa2fcc0e..0907bcede5e5 100644 --- a/net/ipv6/icmp.c +++ b/net/ipv6/icmp.c @@ -684,6 +684,10 @@ static void icmpv6_echo_reply(struct sk_buff *skb) struct ipcm6_cookie ipc6; u32 mark = IP6_REPLY_MARK(net, skb->mark); + if (ipv6_addr_is_multicast(&ipv6_hdr(skb)->daddr) && + net->ipv6.sysctl.icmpv6_echo_ignore_multicast) + return; + saddr = &ipv6_hdr(skb)->daddr; if (!ipv6_unicast_destination(skb) && @@ -1115,6 +1119,13 @@ static struct ctl_table ipv6_icmp_table_template[] = { .mode = 0644, .proc_handler = proc_dointvec, }, + { + .procname = "echo_ignore_multicast", + .data = &init_net.ipv6.sysctl.icmpv6_echo_ignore_multicast, + .maxlen = sizeof(int), + .mode = 0644, + .proc_handler = proc_dointvec, + }, { }, }; @@ -1129,6 +1140,7 @@ struct ctl_table * __net_init ipv6_icmp_sysctl_init(struct net *net) if (table) { table[0].data = &net->ipv6.sysctl.icmpv6_time; table[1].data = &net->ipv6.sysctl.icmpv6_echo_ignore_all; + table[2].data = &net->ipv6.sysctl.icmpv6_echo_ignore_multicast; } return table; } -- cgit v1.2.3 From 0b5173368b4c2713044ec677a3b8cae413cc8e19 Mon Sep 17 00:00:00 2001 From: Daniel Baluta Date: Tue, 19 Mar 2019 17:48:38 +0000 Subject: bindings: fsl-imx-sdma: Document fsl,imx8mq-sdma compatbile string Add imx8mq sdma support. Signed-off-by: Daniel Baluta Reviewed-by: Rob Herring Reviewed-by: Fabio Estevam Signed-off-by: Shawn Guo --- Documentation/devicetree/bindings/dma/fsl-imx-sdma.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/dma/fsl-imx-sdma.txt b/Documentation/devicetree/bindings/dma/fsl-imx-sdma.txt index 3c9a57a8443b..9d8bbac27d8b 100644 --- a/Documentation/devicetree/bindings/dma/fsl-imx-sdma.txt +++ b/Documentation/devicetree/bindings/dma/fsl-imx-sdma.txt @@ -9,6 +9,7 @@ Required properties: "fsl,imx53-sdma" "fsl,imx6q-sdma" "fsl,imx7d-sdma" + "fsl,imx8mq-sdma" The -to variants should be preferred since they allow to determine the correct ROM script addresses needed for the driver to work without additional firmware. -- cgit v1.2.3 From 20d467e1e9bdd091af56b856300545fa578e30cb Mon Sep 17 00:00:00 2001 From: Marek Vasut Date: Mon, 4 Mar 2019 13:11:39 +0100 Subject: of: Add vendor prefix for Menlo Systems GmbH Add vendor prefix for Menlo Systems GmbH, http://www.menlosystems.com/ . Signed-off-by: Marek Vasut Cc: Fabio Estevam Cc: NXP Linux Team Cc: Rob Herring Cc: Shawn Guo Cc: devicetree@vger.kernel.org Reviewed-by: Rob Herring Signed-off-by: Shawn Guo --- Documentation/devicetree/bindings/vendor-prefixes.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/vendor-prefixes.txt b/Documentation/devicetree/bindings/vendor-prefixes.txt index 8162b0eb4b50..192249f30ab9 100644 --- a/Documentation/devicetree/bindings/vendor-prefixes.txt +++ b/Documentation/devicetree/bindings/vendor-prefixes.txt @@ -244,6 +244,7 @@ melexis Melexis N.V. melfas MELFAS Inc. mellanox Mellanox Technologies memsic MEMSIC Inc. +menlo Menlo Systems GmbH merrii Merrii Technology Co., Ltd. micrel Micrel Inc. microchip Microchip Technology Inc. -- cgit v1.2.3 From b54d1ed07ad896e89b356421785ef34486f62834 Mon Sep 17 00:00:00 2001 From: Vignesh Raghavendra Date: Tue, 12 Mar 2019 14:46:28 +0530 Subject: dt-bindings: pwm: tiehrpwm: Add TI AM654 SoC specific compatible Add a new compatible string "ti,am654-ehrpwm" to support EHRPWM IP on TI AM654 SoC. Signed-off-by: Vignesh Raghavendra Signed-off-by: Thierry Reding --- Documentation/devicetree/bindings/pwm/pwm-tiehrpwm.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/pwm/pwm-tiehrpwm.txt b/Documentation/devicetree/bindings/pwm/pwm-tiehrpwm.txt index 944fe356bb45..31c4577157dd 100644 --- a/Documentation/devicetree/bindings/pwm/pwm-tiehrpwm.txt +++ b/Documentation/devicetree/bindings/pwm/pwm-tiehrpwm.txt @@ -4,6 +4,7 @@ Required properties: - compatible: Must be "ti,-ehrpwm". for am33xx - compatible = "ti,am3352-ehrpwm", "ti,am33xx-ehrpwm"; for am4372 - compatible = "ti,am4372-ehrpwm", "ti-am3352-ehrpwm", "ti,am33xx-ehrpwm"; + for am654 - compatible = "ti,am654-ehrpwm", "ti-am3352-ehrpwm"; for da850 - compatible = "ti,da850-ehrpwm", "ti-am3352-ehrpwm", "ti,am33xx-ehrpwm"; for dra746 - compatible = "ti,dra746-ehrpwm", "ti-am3352-ehrpwm"; - #pwm-cells: should be 3. See pwm.txt in this directory for a description of -- cgit v1.2.3 From bdfdf4b2ba644347d63a61da941f30aea1bd35fc Mon Sep 17 00:00:00 2001 From: Phil Edworthy Date: Thu, 28 Feb 2019 13:52:09 +0000 Subject: dt: snps,designware-i2c: Add clock bindings documentation The driver requires an undocumented clock property, so detail it. Add documentation for a separate, optional, interface clock. Signed-off-by: Phil Edworthy Signed-off-by: Gareth Williams Acked-by: Wolfram Sang Reviewed-by: Rob Herring Reviewed-by: Jarkko Nikula Signed-off-by: Wolfram Sang --- Documentation/devicetree/bindings/i2c/i2c-designware.txt | 9 +++++++++ 1 file changed, 9 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/i2c/i2c-designware.txt b/Documentation/devicetree/bindings/i2c/i2c-designware.txt index 3e4bcc2fb6f7..08be4d3846e5 100644 --- a/Documentation/devicetree/bindings/i2c/i2c-designware.txt +++ b/Documentation/devicetree/bindings/i2c/i2c-designware.txt @@ -6,12 +6,21 @@ Required properties : or "mscc,ocelot-i2c" with "snps,designware-i2c" for fallback - reg : Offset and length of the register set for the device - interrupts : where IRQ is the interrupt number. + - clocks : phandles for the clocks, see the description of clock-names below. + The phandle for the "ic_clk" clock is required. The phandle for the "pclk" + clock is optional. If a single clock is specified but no clock-name, it is + the "ic_clk" clock. If both clocks are listed, the "ic_clk" must be first. Recommended properties : - clock-frequency : desired I2C bus clock frequency in Hz. Optional properties : + + - clock-names : Contains the names of the clocks: + "ic_clk", for the core clock used to generate the external I2C clock. + "pclk", the interface clock, required for register access. + - reg : for "mscc,ocelot-i2c", a second register set to configure the SDA hold time, named ICPU_CFG:TWI_DELAY in the datasheet. -- cgit v1.2.3 From 80c94557e94f25df5df00fd94e2a58bf31230fce Mon Sep 17 00:00:00 2001 From: Marek Vasut Date: Sat, 16 Mar 2019 21:25:51 +0100 Subject: regulator: gpio: Reword the binding document Reword the binding document to make it clear how the propeties work and which properties affect which other properties. Signed-off-by: Marek Vasut Cc: Harald Geyer Cc: Kuninori Morimoto Cc: Linus Walleij Cc: Mark Brown Cc: Rob Herring Cc: linux-renesas-soc@vger.kernel.org To: devicetree@vger.kernel.org Signed-off-by: Mark Brown --- .../bindings/regulator/gpio-regulator.txt | 30 ++++++++++++++++------ 1 file changed, 22 insertions(+), 8 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/regulator/gpio-regulator.txt b/Documentation/devicetree/bindings/regulator/gpio-regulator.txt index 1f496159e2bb..dd25e73b5d79 100644 --- a/Documentation/devicetree/bindings/regulator/gpio-regulator.txt +++ b/Documentation/devicetree/bindings/regulator/gpio-regulator.txt @@ -4,16 +4,30 @@ Required properties: - compatible : Must be "regulator-gpio". - regulator-name : Defined in regulator.txt as optional, but required here. -- states : Selection of available voltages and GPIO configs. - if there are no states, then use a fixed regulator +- gpios : Array of one or more GPIO pins used to select the + regulator voltage/current listed in "states". +- states : Selection of available voltages/currents provided by + this regulator and matching GPIO configurations to + achieve them. If there are no states in the "states" + array, use a fixed regulator instead. Optional properties: -- enable-gpio : GPIO to use to enable/disable the regulator. -- gpios : GPIO group used to control voltage. -- gpios-states : gpios pin's initial states array. 0: LOW, 1: HIGH. - defualt is LOW if nothing is specified. +- enable-gpios : GPIO used to enable/disable the regulator. + Warning, the GPIO phandle flags are ignored and the + GPIO polarity is controlled solely by the presence + of "enable-active-high" DT property. This is due to + compatibility with old DTs. +- enable-active-high : Polarity of "enable-gpio" GPIO is active HIGH. + Default is active LOW. +- gpios-states : On operating systems, that don't support reading back + gpio values in output mode (most notably linux), this + array provides the state of GPIO pins set when + requesting them from the gpio controller. Systems, + that are capable of preserving state when requesting + the lines, are free to ignore this property. + 0: LOW, 1: HIGH. Default is LOW if nothing else + is specified. - startup-delay-us : Startup time in microseconds. -- enable-active-high : Polarity of GPIO is active high (default is low). - regulator-type : Specifies what is being regulated, must be either "voltage" or "current", defaults to voltage. @@ -30,7 +44,7 @@ Example: regulator-max-microvolt = <2600000>; regulator-boot-on; - enable-gpio = <&gpio0 23 0x4>; + enable-gpios = <&gpio0 23 0x4>; gpios = <&gpio0 24 0x4 &gpio0 25 0x4>; states = <1800000 0x3 -- cgit v1.2.3 From 57a9f6e7eefa697349ff4823f178fd56abe27345 Mon Sep 17 00:00:00 2001 From: Phil Edworthy Date: Tue, 19 Mar 2019 15:52:05 +0000 Subject: dt-bindings: snps,dw-apb-ssi: Add mandatory clock bindings documentation The Synopsys SSI driver uses a mandatory clock that is not documented, so detail it in the device tree bindings. Also correct the spelling of "pins" in the "Optional Properties" section for the driver. Signed-off-by: Phil Edworthy Signed-off-by: Gareth Williams Signed-off-by: Mark Brown --- Documentation/devicetree/bindings/spi/snps,dw-apb-ssi.txt | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/spi/snps,dw-apb-ssi.txt b/Documentation/devicetree/bindings/spi/snps,dw-apb-ssi.txt index 2864bc6b659c..bcd8f960afb9 100644 --- a/Documentation/devicetree/bindings/spi/snps,dw-apb-ssi.txt +++ b/Documentation/devicetree/bindings/spi/snps,dw-apb-ssi.txt @@ -8,9 +8,10 @@ Required properties: - interrupts : One interrupt, used by the controller. - #address-cells : <1>, as required by generic SPI binding. - #size-cells : <0>, also as required by generic SPI binding. +- clocks : phandle for the core clock used to generate the external SPI clock. Optional properties: -- cs-gpios : Specifies the gpio pis to be used for chipselects. +- cs-gpios : Specifies the gpio pins to be used for chipselects. - num-cs : The number of chipselects. If omitted, this will default to 4. - reg-io-width : The I/O register width (in bytes) implemented by this device. Supported values are 2 or 4 (the default). @@ -25,6 +26,7 @@ Example: interrupts = <0 154 4>; #address-cells = <1>; #size-cells = <0>; + clocks = <&spi_m_clk>; num-cs = <2>; cs-gpios = <&gpio0 13 0>, <&gpio0 14 0>; -- cgit v1.2.3 From 2f324ac7cf8c50aa079cf30445b99a1b98ea2728 Mon Sep 17 00:00:00 2001 From: Gareth Williams Date: Tue, 19 Mar 2019 15:52:06 +0000 Subject: dt-bindings: snps,dw-apb-ssi: Add optional clock bindings documentation Add documentation to the Synopsys SPI dt-bindings to support an optional interface clock that may be used for register access. Signed-off-by: Phil Edworthy Signed-off-by: Gareth Williams Signed-off-by: Mark Brown --- Documentation/devicetree/bindings/spi/snps,dw-apb-ssi.txt | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/spi/snps,dw-apb-ssi.txt b/Documentation/devicetree/bindings/spi/snps,dw-apb-ssi.txt index bcd8f960afb9..f54c8c36395e 100644 --- a/Documentation/devicetree/bindings/spi/snps,dw-apb-ssi.txt +++ b/Documentation/devicetree/bindings/spi/snps,dw-apb-ssi.txt @@ -8,9 +8,15 @@ Required properties: - interrupts : One interrupt, used by the controller. - #address-cells : <1>, as required by generic SPI binding. - #size-cells : <0>, also as required by generic SPI binding. -- clocks : phandle for the core clock used to generate the external SPI clock. +- clocks : phandles for the clocks, see the description of clock-names below. + The phandle for the "ssi_clk" is required. The phandle for the "pclk" clock + is optional. If a single clock is specified but no clock-name, it is the + "ssi_clk" clock. If both clocks are listed, the "ssi_clk" must be first. Optional properties: +- clock-names : Contains the names of the clocks: + "ssi_clk", for the core clock used to generate the external SPI clock. + "pclk", the interface clock, required for register access. - cs-gpios : Specifies the gpio pins to be used for chipselects. - num-cs : The number of chipselects. If omitted, this will default to 4. - reg-io-width : The I/O register width (in bytes) implemented by this -- cgit v1.2.3 From 0b03a5ca8b14321366eec4a903922d2b46d585ff Mon Sep 17 00:00:00 2001 From: Stephen Suryaputra Date: Wed, 20 Mar 2019 10:29:27 -0400 Subject: ipv6: Add icmp_echo_ignore_anycast for ICMPv6 In addition to icmp_echo_ignore_multicast, there is a need to also prevent responding to pings to anycast addresses for security. Signed-off-by: Stephen Suryaputra Signed-off-by: David S. Miller --- Documentation/networking/ip-sysctl.txt | 5 +++++ include/net/netns/ipv6.h | 1 + net/ipv6/af_inet6.c | 1 + net/ipv6/icmp.c | 16 ++++++++++++++-- 4 files changed, 21 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/networking/ip-sysctl.txt b/Documentation/networking/ip-sysctl.txt index 55ea7def46be..bd029fc55ccb 100644 --- a/Documentation/networking/ip-sysctl.txt +++ b/Documentation/networking/ip-sysctl.txt @@ -1923,6 +1923,11 @@ echo_ignore_multicast - BOOLEAN requests sent to it over the IPv6 protocol via multicast. Default: 0 +echo_ignore_anycast - BOOLEAN + If set non-zero, then the kernel will ignore all ICMP ECHO + requests sent to it over the IPv6 protocol destined to anycast address. + Default: 0 + xfrm6_gc_thresh - INTEGER The threshold at which we will start garbage collecting for IPv6 destination cache entries. At twice this value the system will diff --git a/include/net/netns/ipv6.h b/include/net/netns/ipv6.h index e29aff15acc9..64e29b58bb5e 100644 --- a/include/net/netns/ipv6.h +++ b/include/net/netns/ipv6.h @@ -34,6 +34,7 @@ struct netns_sysctl_ipv6 { int icmpv6_time; int icmpv6_echo_ignore_all; int icmpv6_echo_ignore_multicast; + int icmpv6_echo_ignore_anycast; int anycast_src_echo_reply; int ip_nonlocal_bind; int fwmark_reflect; diff --git a/net/ipv6/af_inet6.c b/net/ipv6/af_inet6.c index fdc117de849c..fa6b404cbd10 100644 --- a/net/ipv6/af_inet6.c +++ b/net/ipv6/af_inet6.c @@ -848,6 +848,7 @@ static int __net_init inet6_net_init(struct net *net) net->ipv6.sysctl.icmpv6_time = 1*HZ; net->ipv6.sysctl.icmpv6_echo_ignore_all = 0; net->ipv6.sysctl.icmpv6_echo_ignore_multicast = 0; + net->ipv6.sysctl.icmpv6_echo_ignore_anycast = 0; net->ipv6.sysctl.flowlabel_consistency = 1; net->ipv6.sysctl.auto_flowlabels = IP6_DEFAULT_AUTO_FLOW_LABELS; net->ipv6.sysctl.idgen_retries = 3; diff --git a/net/ipv6/icmp.c b/net/ipv6/icmp.c index 0907bcede5e5..cc14b9998941 100644 --- a/net/ipv6/icmp.c +++ b/net/ipv6/icmp.c @@ -683,6 +683,7 @@ static void icmpv6_echo_reply(struct sk_buff *skb) struct dst_entry *dst; struct ipcm6_cookie ipc6; u32 mark = IP6_REPLY_MARK(net, skb->mark); + bool acast; if (ipv6_addr_is_multicast(&ipv6_hdr(skb)->daddr) && net->ipv6.sysctl.icmpv6_echo_ignore_multicast) @@ -690,9 +691,12 @@ static void icmpv6_echo_reply(struct sk_buff *skb) saddr = &ipv6_hdr(skb)->daddr; + acast = ipv6_anycast_destination(skb_dst(skb), saddr); + if (acast && net->ipv6.sysctl.icmpv6_echo_ignore_anycast) + return; + if (!ipv6_unicast_destination(skb) && - !(net->ipv6.sysctl.anycast_src_echo_reply && - ipv6_anycast_destination(skb_dst(skb), saddr))) + !(net->ipv6.sysctl.anycast_src_echo_reply && acast)) saddr = NULL; memcpy(&tmp_hdr, icmph, sizeof(tmp_hdr)); @@ -1126,6 +1130,13 @@ static struct ctl_table ipv6_icmp_table_template[] = { .mode = 0644, .proc_handler = proc_dointvec, }, + { + .procname = "echo_ignore_anycast", + .data = &init_net.ipv6.sysctl.icmpv6_echo_ignore_anycast, + .maxlen = sizeof(int), + .mode = 0644, + .proc_handler = proc_dointvec, + }, { }, }; @@ -1141,6 +1152,7 @@ struct ctl_table * __net_init ipv6_icmp_sysctl_init(struct net *net) table[0].data = &net->ipv6.sysctl.icmpv6_time; table[1].data = &net->ipv6.sysctl.icmpv6_echo_ignore_all; table[2].data = &net->ipv6.sysctl.icmpv6_echo_ignore_multicast; + table[3].data = &net->ipv6.sysctl.icmpv6_echo_ignore_anycast; } return table; } -- cgit v1.2.3 From 46fc15487d02451448c11b83c4d086d87a6ad588 Mon Sep 17 00:00:00 2001 From: Kimberly Brown Date: Tue, 19 Mar 2019 00:04:01 -0400 Subject: Drivers: hv: vmbus: Expose monitor data only when monitor pages are used MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit There are two methods for signaling the host: the monitor page mechanism and hypercalls. The monitor page mechanism is used by performance critical channels (storage, networking, etc.) because it provides improved throughput. However, latency is increased. Monitor pages are allocated to these channels. Monitor pages are not allocated to channels that do not use the monitor page mechanism. Therefore, these channels do not have a valid monitor id or valid monitor page data. In these cases, some of the "_show" functions return incorrect data. They return an invalid monitor id and data that is beyond the bounds of the hv_monitor_page array fields. The "channel->offermsg.monitor_allocated" value can be used to determine whether monitor pages have been allocated to a channel. Add "is_visible()" callback functions for the device-level and channel-level attribute groups. These functions will hide the monitor sysfs files when the monitor mechanism is not used. Remove ".default_attributes" from "vmbus_chan_attrs" and create a channel-level attribute group. These changes allow the new "is_visible()" callback function to be applied to the channel-level attributes. Call "sysfs_create_group()" in "vmbus_add_channel_kobj()" to create the channel's sysfs files. Add a new function, “vmbus_remove_channel_attr_group()”, and call it in "free_channel()" to remove the channel's sysfs files when the channel is closed. Signed-off-by: Kimberly Brown Reviewed-by: Greg Kroah-Hartman Reviewed-by: Michael Kelley Signed-off-by: Sasha Levin --- Documentation/ABI/stable/sysfs-bus-vmbus | 12 +++-- drivers/hv/channel_mgmt.c | 1 + drivers/hv/hyperv_vmbus.h | 2 + drivers/hv/vmbus_drv.c | 77 +++++++++++++++++++++++++++++++- 4 files changed, 87 insertions(+), 5 deletions(-) (limited to 'Documentation') diff --git a/Documentation/ABI/stable/sysfs-bus-vmbus b/Documentation/ABI/stable/sysfs-bus-vmbus index 826689dcc2e6..8e8d167eca31 100644 --- a/Documentation/ABI/stable/sysfs-bus-vmbus +++ b/Documentation/ABI/stable/sysfs-bus-vmbus @@ -81,7 +81,9 @@ What: /sys/bus/vmbus/devices//channels//latency Date: September. 2017 KernelVersion: 4.14 Contact: Stephen Hemminger -Description: Channel signaling latency +Description: Channel signaling latency. This file is available only for + performance critical channels (storage, network, etc.) that use + the monitor page mechanism. Users: Debugging tools What: /sys/bus/vmbus/devices//channels//out_mask @@ -95,7 +97,9 @@ What: /sys/bus/vmbus/devices//channels//pending Date: September. 2017 KernelVersion: 4.14 Contact: Stephen Hemminger -Description: Channel interrupt pending state +Description: Channel interrupt pending state. This file is available only for + performance critical channels (storage, network, etc.) that use + the monitor page mechanism. Users: Debugging tools What: /sys/bus/vmbus/devices//channels//read_avail @@ -137,7 +141,9 @@ What: /sys/bus/vmbus/devices//channels//monitor_id Date: January. 2018 KernelVersion: 4.16 Contact: Stephen Hemminger -Description: Monitor bit associated with channel +Description: Monitor bit associated with channel. This file is available only + for performance critical channels (storage, network, etc.) that + use the monitor page mechanism. Users: Debugging tools and userspace drivers What: /sys/bus/vmbus/devices//channels//ring diff --git a/drivers/hv/channel_mgmt.c b/drivers/hv/channel_mgmt.c index 62703b354d6d..d32cac501fc7 100644 --- a/drivers/hv/channel_mgmt.c +++ b/drivers/hv/channel_mgmt.c @@ -345,6 +345,7 @@ static struct vmbus_channel *alloc_channel(void) static void free_channel(struct vmbus_channel *channel) { tasklet_kill(&channel->callback_event); + vmbus_remove_channel_attr_group(channel); kobject_put(&channel->kobj); } diff --git a/drivers/hv/hyperv_vmbus.h b/drivers/hv/hyperv_vmbus.h index cb86b133eb4d..a94aab94e0b5 100644 --- a/drivers/hv/hyperv_vmbus.h +++ b/drivers/hv/hyperv_vmbus.h @@ -321,6 +321,8 @@ void vmbus_device_unregister(struct hv_device *device_obj); int vmbus_add_channel_kobj(struct hv_device *device_obj, struct vmbus_channel *channel); +void vmbus_remove_channel_attr_group(struct vmbus_channel *channel); + struct vmbus_channel *relid2channel(u32 relid); void vmbus_free_channels(void); diff --git a/drivers/hv/vmbus_drv.c b/drivers/hv/vmbus_drv.c index 000b53e5a17a..b23aea86d029 100644 --- a/drivers/hv/vmbus_drv.c +++ b/drivers/hv/vmbus_drv.c @@ -630,7 +630,36 @@ static struct attribute *vmbus_dev_attrs[] = { &dev_attr_driver_override.attr, NULL, }; -ATTRIBUTE_GROUPS(vmbus_dev); + +/* + * Device-level attribute_group callback function. Returns the permission for + * each attribute, and returns 0 if an attribute is not visible. + */ +static umode_t vmbus_dev_attr_is_visible(struct kobject *kobj, + struct attribute *attr, int idx) +{ + struct device *dev = kobj_to_dev(kobj); + const struct hv_device *hv_dev = device_to_hv_device(dev); + + /* Hide the monitor attributes if the monitor mechanism is not used. */ + if (!hv_dev->channel->offermsg.monitor_allocated && + (attr == &dev_attr_monitor_id.attr || + attr == &dev_attr_server_monitor_pending.attr || + attr == &dev_attr_client_monitor_pending.attr || + attr == &dev_attr_server_monitor_latency.attr || + attr == &dev_attr_client_monitor_latency.attr || + attr == &dev_attr_server_monitor_conn_id.attr || + attr == &dev_attr_client_monitor_conn_id.attr)) + return 0; + + return attr->mode; +} + +static const struct attribute_group vmbus_dev_group = { + .attrs = vmbus_dev_attrs, + .is_visible = vmbus_dev_attr_is_visible +}; +__ATTRIBUTE_GROUPS(vmbus_dev); /* * vmbus_uevent - add uevent for our device @@ -1550,10 +1579,34 @@ static struct attribute *vmbus_chan_attrs[] = { NULL }; +/* + * Channel-level attribute_group callback function. Returns the permission for + * each attribute, and returns 0 if an attribute is not visible. + */ +static umode_t vmbus_chan_attr_is_visible(struct kobject *kobj, + struct attribute *attr, int idx) +{ + const struct vmbus_channel *channel = + container_of(kobj, struct vmbus_channel, kobj); + + /* Hide the monitor attributes if the monitor mechanism is not used. */ + if (!channel->offermsg.monitor_allocated && + (attr == &chan_attr_pending.attr || + attr == &chan_attr_latency.attr || + attr == &chan_attr_monitor_id.attr)) + return 0; + + return attr->mode; +} + +static struct attribute_group vmbus_chan_group = { + .attrs = vmbus_chan_attrs, + .is_visible = vmbus_chan_attr_is_visible +}; + static struct kobj_type vmbus_chan_ktype = { .sysfs_ops = &vmbus_chan_sysfs_ops, .release = vmbus_chan_release, - .default_attrs = vmbus_chan_attrs, }; /* @@ -1561,6 +1614,7 @@ static struct kobj_type vmbus_chan_ktype = { */ int vmbus_add_channel_kobj(struct hv_device *dev, struct vmbus_channel *channel) { + const struct device *device = &dev->device; struct kobject *kobj = &channel->kobj; u32 relid = channel->offermsg.child_relid; int ret; @@ -1571,11 +1625,30 @@ int vmbus_add_channel_kobj(struct hv_device *dev, struct vmbus_channel *channel) if (ret) return ret; + ret = sysfs_create_group(kobj, &vmbus_chan_group); + + if (ret) { + /* + * The calling functions' error handling paths will cleanup the + * empty channel directory. + */ + dev_err(device, "Unable to set up channel sysfs files\n"); + return ret; + } + kobject_uevent(kobj, KOBJ_ADD); return 0; } +/* + * vmbus_remove_channel_attr_group - remove the channel's attribute group + */ +void vmbus_remove_channel_attr_group(struct vmbus_channel *channel) +{ + sysfs_remove_group(&channel->kobj, &vmbus_chan_group); +} + /* * vmbus_device_create - Creates and registers a new child device * on the vmbus. -- cgit v1.2.3 From 8677858da6b9d1afc49b5ba8bfefea92e9416cd2 Mon Sep 17 00:00:00 2001 From: Anson Huang Date: Tue, 12 Mar 2019 02:24:08 +0000 Subject: dt-bindings: memory-controllers: freescale: add MMDC binding doc Freescale MMDC (Multi Mode DDR Controller) driver is supported since i.MX6Q, but not yet documented, this patch adds binding doc for MMDC module driver. Signed-off-by: Anson Huang Reviewed-by: Rob Herring Signed-off-by: Shawn Guo --- .../bindings/memory-controllers/fsl/mmdc.txt | 35 ++++++++++++++++++++++ 1 file changed, 35 insertions(+) create mode 100644 Documentation/devicetree/bindings/memory-controllers/fsl/mmdc.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/memory-controllers/fsl/mmdc.txt b/Documentation/devicetree/bindings/memory-controllers/fsl/mmdc.txt new file mode 100644 index 000000000000..bcc36c5b543c --- /dev/null +++ b/Documentation/devicetree/bindings/memory-controllers/fsl/mmdc.txt @@ -0,0 +1,35 @@ +Freescale Multi Mode DDR controller (MMDC) + +Required properties : +- compatible : should be one of following: + for i.MX6Q/i.MX6DL: + - "fsl,imx6q-mmdc"; + for i.MX6QP: + - "fsl,imx6qp-mmdc", "fsl,imx6q-mmdc"; + for i.MX6SL: + - "fsl,imx6sl-mmdc", "fsl,imx6q-mmdc"; + for i.MX6SLL: + - "fsl,imx6sll-mmdc", "fsl,imx6q-mmdc"; + for i.MX6SX: + - "fsl,imx6sx-mmdc", "fsl,imx6q-mmdc"; + for i.MX6UL/i.MX6ULL/i.MX6ULZ: + - "fsl,imx6ul-mmdc", "fsl,imx6q-mmdc"; + for i.MX7ULP: + - "fsl,imx7ulp-mmdc", "fsl,imx6q-mmdc"; +- reg : address and size of MMDC DDR controller registers + +Optional properties : +- clocks : the clock provided by the SoC to access the MMDC registers + +Example : + mmdc0: memory-controller@21b0000 { /* MMDC0 */ + compatible = "fsl,imx6q-mmdc"; + reg = <0x021b0000 0x4000>; + clocks = <&clks IMX6QDL_CLK_MMDC_P0_IPG>; + }; + + mmdc1: memory-controller@21b4000 { /* MMDC1 */ + compatible = "fsl,imx6q-mmdc"; + reg = <0x021b4000 0x4000>; + status = "disabled"; + }; -- cgit v1.2.3 From d333bad1f6f3e0df224db181c991fb8d65bbc2be Mon Sep 17 00:00:00 2001 From: Geert Uytterhoeven Date: Wed, 20 Mar 2019 11:33:51 +0100 Subject: dt-bindings: at24: add Renesas R1EX24016 Document the compatible value for the Renesas R1EX24128ASAS0A two-wire serial interface EEPROM, so it can be used in DTS files without causing checkpatch warnings. This is a 2 KiB EEPROM. The first 1 KiB can always be written, the second 1 KiB cannot be written if the write-protect line is asserted. Signed-off-by: Geert Uytterhoeven Signed-off-by: Bartosz Golaszewski --- Documentation/devicetree/bindings/eeprom/at24.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/eeprom/at24.txt b/Documentation/devicetree/bindings/eeprom/at24.txt index 0e456bbc1213..22aead844d0f 100644 --- a/Documentation/devicetree/bindings/eeprom/at24.txt +++ b/Documentation/devicetree/bindings/eeprom/at24.txt @@ -50,6 +50,7 @@ Required properties: "nxp,se97b" - the fallback is "atmel,24c02", "renesas,r1ex24002" - the fallback is "atmel,24c02" + "renesas,r1ex24016" - the fallback is "atmel,24c16" "renesas,r1ex24128" - the fallback is "atmel,24c128" "rohm,br24t01" - the fallback is "atmel,24c01" -- cgit v1.2.3 From 41d176d3ec147f499614adc773080f244d47e3cd Mon Sep 17 00:00:00 2001 From: Adam Thomson Date: Tue, 19 Mar 2019 17:49:30 +0000 Subject: ASoC: da7219: Update DAI clock binding info to cover WCLK/BCLK With the need to expose WCLK and BCLK as separate clocks, the 'clock-cells' and 'clock-output-names' descriptions need to be updated as now the codec is providing 2 clocks. The example is also updated accordingly. Signed-off-by: Adam Thomson Signed-off-by: Mark Brown --- Documentation/devicetree/bindings/sound/da7219.txt | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/sound/da7219.txt b/Documentation/devicetree/bindings/sound/da7219.txt index e9d0baeb94e2..add1caf26ac2 100644 --- a/Documentation/devicetree/bindings/sound/da7219.txt +++ b/Documentation/devicetree/bindings/sound/da7219.txt @@ -23,8 +23,8 @@ Optional properties: interrupt is to be used to wake system, otherwise "irq" should be used. - wakeup-source: Flag to indicate this device can wake system (suspend/resume). -- #clock-cells : Should be set to '<0>', only one clock source provided; -- clock-output-names : Name given for DAI clocks output; +- #clock-cells : Should be set to '<1>', two clock sources provided; +- clock-output-names : Names given for DAI clock outputs (WCLK & BCLK); - clocks : phandle and clock specifier for codec MCLK. - clock-names : Clock name string for 'clocks' attribute, should be "mclk". @@ -84,8 +84,8 @@ Example: VDDMIC-supply = <®_audio>; VDDIO-supply = <®_audio>; - #clock-cells = <0>; - clock-output-names = "dai-clks"; + #clock-cells = <1>; + clock-output-names = "dai-wclk", "dai-bclk"; clocks = <&clks 201>; clock-names = "mclk"; -- cgit v1.2.3 From 4c798984c0dcd7649a6ff8a3d64361ba896efe61 Mon Sep 17 00:00:00 2001 From: Codrin Ciubotariu Date: Tue, 5 Mar 2019 11:26:42 +0000 Subject: ASoC: mchp-i2s-mcc: dt-bindings: add DT bindings for I2S Multi-Channel Controller This patch adds DT bindings for the new Microchip I2S Multi-Channel controller embedded inside sam9x60 SoCs. Signed-off-by: Codrin Ciubotariu Signed-off-by: Mark Brown --- .../devicetree/bindings/sound/mchp-i2s-mcc.txt | 43 ++++++++++++++++++++++ 1 file changed, 43 insertions(+) create mode 100644 Documentation/devicetree/bindings/sound/mchp-i2s-mcc.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/sound/mchp-i2s-mcc.txt b/Documentation/devicetree/bindings/sound/mchp-i2s-mcc.txt new file mode 100644 index 000000000000..91ec83a6faed --- /dev/null +++ b/Documentation/devicetree/bindings/sound/mchp-i2s-mcc.txt @@ -0,0 +1,43 @@ +* Microchip I2S Multi-Channel Controller + +Required properties: +- compatible: Should be "microchip,sam9x60-i2smcc". +- reg: Should be the physical base address of the controller and the + length of memory mapped region. +- interrupts: Should contain the interrupt for the controller. +- dmas: Should be one per channel name listed in the dma-names property, + as described in atmel-dma.txt and dma.txt files. +- dma-names: Identifier string for each DMA request line in the dmas property. + Two dmas have to be defined, "tx" and "rx". +- clocks: Must contain an entry for each entry in clock-names. + Please refer to clock-bindings.txt. +- clock-names: Should be one of each entry matching the clocks phandles list: + - "pclk" (peripheral clock) Required. + - "gclk" (generated clock) Optional (1). + +Optional properties: +- pinctrl-0: Should specify pin control groups used for this controller. +- princtrl-names: Should contain only one value - "default". + + +(1) : Only the peripheral clock is required. The generated clock is optional + and should be set mostly when Master Mode is required. + +Example: + + i2s@f001c000 { + compatible = "microchip,sam9x60-i2smcc"; + reg = <0xf001c000 0x100>; + interrupts = <34 IRQ_TYPE_LEVEL_HIGH 7>; + dmas = <&dma0 + (AT91_XDMAC_DT_MEM_IF(0) | AT91_XDMAC_DT_PER_IF(1) | + AT91_XDMAC_DT_PERID(36))>, + <&dma0 + (AT91_XDMAC_DT_MEM_IF(0) | AT91_XDMAC_DT_PER_IF(1) | + AT91_XDMAC_DT_PERID(37))>; + dma-names = "tx", "rx"; + clocks = <&i2s_clk>, <&i2s_gclk>; + clock-names = "pclk", "gclk"; + pinctrl-names = "default"; + pinctrl-0 = <&pinctrl_i2s_default>; + }; -- cgit v1.2.3 From d9b27d50340c4c90637ebf24106c9064992e2f2a Mon Sep 17 00:00:00 2001 From: Charles Keepax Date: Wed, 20 Mar 2019 17:37:31 +0000 Subject: ASoC: lochnagar: Add device tree binding document Lochnagar is an evaluation and development board for Cirrus Logic Smart CODEC and Amp devices. It allows the connection of most Cirrus Logic devices on mini-cards, as well as allowing connection of various application processor systems to provide a full evaluation platform. This driver supports the board controller chip on the Lochnagar board. Signed-off-by: Charles Keepax Signed-off-by: Mark Brown --- .../devicetree/bindings/sound/cirrus,lochnagar.txt | 39 ++++++++++++++++++++++ 1 file changed, 39 insertions(+) create mode 100644 Documentation/devicetree/bindings/sound/cirrus,lochnagar.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/sound/cirrus,lochnagar.txt b/Documentation/devicetree/bindings/sound/cirrus,lochnagar.txt new file mode 100644 index 000000000000..41ae2699f07a --- /dev/null +++ b/Documentation/devicetree/bindings/sound/cirrus,lochnagar.txt @@ -0,0 +1,39 @@ +Cirrus Logic Lochnagar Audio Development Board + +Lochnagar is an evaluation and development board for Cirrus Logic +Smart CODEC and Amp devices. It allows the connection of most Cirrus +Logic devices on mini-cards, as well as allowing connection of +various application processor systems to provide a full evaluation +platform. Audio system topology, clocking and power can all be +controlled through the Lochnagar, allowing the device under test +to be used in a variety of possible use cases. + +This binding document describes the binding for the audio portion +of the driver. + +This binding must be part of the Lochnagar MFD binding: + [4] ../mfd/cirrus,lochnagar.txt + +Required properties: + + - compatible : One of the following strings: + "cirrus,lochnagar2-soundcard" + + - #sound-dai-cells : Must be set to 1. + + - clocks : Contains an entry for each entry in clock-names. + - clock-names : Must include the following clocks: + "mclk" Master clock source for the sound card, should normally + be set to LOCHNAGAR_SOUNDCARD_MCLK provided by the Lochnagar + clock driver. + +Example: + +lochnagar-sc { + compatible = "cirrus,lochnagar2-soundcard"; + + #sound-dai-cells = <1>; + + clocks = <&lochnagar_clk LOCHNAGAR_SOUNDCARD_MCLK>; + clock-names = "mclk"; +}; -- cgit v1.2.3 From 996acbfb1fe370cfaa3c7469e93fc54c634fba08 Mon Sep 17 00:00:00 2001 From: Tudor Ambarus Date: Wed, 13 Feb 2019 08:59:52 +0000 Subject: dt-bindings: memory: atmel-ebi: add sam9x60 compatible Add compatibility string for the sam9x60 EBI. Signed-off-by: Tudor Ambarus Acked-by: Alexandre Belloni Reviewed-by: Rob Herring Signed-off-by: Miquel Raynal --- Documentation/devicetree/bindings/memory-controllers/atmel,ebi.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/memory-controllers/atmel,ebi.txt b/Documentation/devicetree/bindings/memory-controllers/atmel,ebi.txt index 9bb5f57e2066..94bf7896a688 100644 --- a/Documentation/devicetree/bindings/memory-controllers/atmel,ebi.txt +++ b/Documentation/devicetree/bindings/memory-controllers/atmel,ebi.txt @@ -15,6 +15,7 @@ Required properties: "atmel,at91sam9g45-ebi" "atmel,at91sam9x5-ebi" "atmel,sama5d3-ebi" + "microchip,sam9x60-ebi" - reg: Contains offset/length value for EBI memory mapping. This property might contain several entries if the EBI -- cgit v1.2.3 From b1e8e0aa15a08a40af496b3377efa90e1750ab3d Mon Sep 17 00:00:00 2001 From: Tudor Ambarus Date: Wed, 13 Feb 2019 09:00:01 +0000 Subject: dt-bindings: mtd: atmel-nand: add sam9x60 compatible Add compatibility string for the sam9x60 nand controller. Signed-off-by: Tudor Ambarus Reviewed-by: Rob Herring Signed-off-by: Miquel Raynal --- Documentation/devicetree/bindings/mtd/atmel-nand.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mtd/atmel-nand.txt b/Documentation/devicetree/bindings/mtd/atmel-nand.txt index 9bb66e476672..68b51dc58816 100644 --- a/Documentation/devicetree/bindings/mtd/atmel-nand.txt +++ b/Documentation/devicetree/bindings/mtd/atmel-nand.txt @@ -14,6 +14,7 @@ Required properties: "atmel,at91sam9261-nand-controller" "atmel,at91sam9g45-nand-controller" "atmel,sama5d3-nand-controller" + "microchip,sam9x60-nand-controller" - ranges: empty ranges property to forward EBI ranges definitions. - #address-cells: should be set to 2. - #size-cells: should be set to 1. -- cgit v1.2.3 From a07c63d3e95de359f71e991dfdf53b47cb23c15d Mon Sep 17 00:00:00 2001 From: Paul Cercueil Date: Tue, 19 Mar 2019 15:53:51 +0100 Subject: dt-bindings: mtd: ingenic: Add compatible strings for JZ4740 and JZ4725B Add compatible strings to probe the jz4780-nand and jz4780-bch drivers from devicetree on the JZ4725B and JZ4740 SoCs from Ingenic. Signed-off-by: Paul Cercueil Reviewed-by: Rob Herring Signed-off-by: Miquel Raynal --- Documentation/devicetree/bindings/mtd/ingenic,jz4780-nand.txt | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mtd/ingenic,jz4780-nand.txt b/Documentation/devicetree/bindings/mtd/ingenic,jz4780-nand.txt index 29ea5853ca91..a5b940f18bf6 100644 --- a/Documentation/devicetree/bindings/mtd/ingenic,jz4780-nand.txt +++ b/Documentation/devicetree/bindings/mtd/ingenic,jz4780-nand.txt @@ -6,7 +6,10 @@ memory-controllers/ingenic,jz4780-nemc.txt), and thus NAND device nodes must be children of the NEMC node. Required NAND controller device properties: -- compatible: Should be set to "ingenic,jz4780-nand". +- compatible: Should be one of: + * ingenic,jz4740-nand + * ingenic,jz4725b-nand + * ingenic,jz4780-nand - reg: For each bank with a NAND chip attached, should specify a bank number, an offset of 0 and a size of 0x1000000 (i.e. the whole NEMC bank). @@ -72,7 +75,10 @@ NAND devices. The following is a description of the device properties for a BCH controller. Required BCH properties: -- compatible: Should be set to "ingenic,jz4780-bch". +- compatible: Should be one of: + * ingenic,jz4740-ecc + * ingenic,jz4725b-bch + * ingenic,jz4780-bch - reg: Should specify the BCH controller registers location and length. - clocks: Clock for the BCH controller. -- cgit v1.2.3 From 057c319a0fe697b2fc9c55015fec601123f7ac4b Mon Sep 17 00:00:00 2001 From: Paul Cercueil Date: Tue, 19 Mar 2019 15:53:52 +0100 Subject: dt-bindings: mtd: ingenic: Change 'BCH' to 'ECC' in documentation The JZ4740 ECC hardware is not BCH but Reed-Solomon, so it makes more sense to use the more generic ECC term. Signed-off-by: Paul Cercueil Reviewed-by: Rob Herring Signed-off-by: Miquel Raynal --- .../devicetree/bindings/mtd/ingenic,jz4780-nand.txt | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mtd/ingenic,jz4780-nand.txt b/Documentation/devicetree/bindings/mtd/ingenic,jz4780-nand.txt index a5b940f18bf6..5a45cc54f46d 100644 --- a/Documentation/devicetree/bindings/mtd/ingenic,jz4780-nand.txt +++ b/Documentation/devicetree/bindings/mtd/ingenic,jz4780-nand.txt @@ -1,4 +1,4 @@ -* Ingenic JZ4780 NAND/BCH +* Ingenic JZ4780 NAND/ECC This file documents the device tree bindings for NAND flash devices on the JZ4780. NAND devices are connected to the NEMC controller (described in @@ -14,10 +14,10 @@ Required NAND controller device properties: an offset of 0 and a size of 0x1000000 (i.e. the whole NEMC bank). Optional NAND controller device properties: -- ingenic,bch-controller: To make use of the hardware BCH controller, this - property must contain a phandle for the BCH controller node. The required +- ingenic,bch-controller: To make use of the hardware ECC controller, this + property must contain a phandle for the ECC controller node. The required properties for this node are described below. If this is not specified, - software BCH will be used instead. + software ECC will be used instead. Optional children nodes: - Individual NAND chips are children of the NAND controller node. @@ -70,17 +70,17 @@ nemc: nemc@13410000 { }; }; -The BCH controller is a separate SoC component used for error correction on +The ECC controller is a separate SoC component used for error correction on NAND devices. The following is a description of the device properties for a -BCH controller. +ECC controller. -Required BCH properties: +Required ECC properties: - compatible: Should be one of: * ingenic,jz4740-ecc * ingenic,jz4725b-bch * ingenic,jz4780-bch -- reg: Should specify the BCH controller registers location and length. -- clocks: Clock for the BCH controller. +- reg: Should specify the ECC controller registers location and length. +- clocks: Clock for the ECC controller. Example: -- cgit v1.2.3 From badb37f1601de0642330125928104e2d19dcc8da Mon Sep 17 00:00:00 2001 From: Paul Cercueil Date: Tue, 19 Mar 2019 15:53:53 +0100 Subject: dt-bindings: mtd: ingenic: Use standard ecc-engine property The 'ingenic,bch-controller' property is now deprecated and the 'ecc-engine' property should be used instead. Signed-off-by: Paul Cercueil Reviewed-by: Rob Herring Signed-off-by: Miquel Raynal --- Documentation/devicetree/bindings/mtd/ingenic,jz4780-nand.txt | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mtd/ingenic,jz4780-nand.txt b/Documentation/devicetree/bindings/mtd/ingenic,jz4780-nand.txt index 5a45cc54f46d..c02259353327 100644 --- a/Documentation/devicetree/bindings/mtd/ingenic,jz4780-nand.txt +++ b/Documentation/devicetree/bindings/mtd/ingenic,jz4780-nand.txt @@ -14,7 +14,7 @@ Required NAND controller device properties: an offset of 0 and a size of 0x1000000 (i.e. the whole NEMC bank). Optional NAND controller device properties: -- ingenic,bch-controller: To make use of the hardware ECC controller, this +- ecc-engine: To make use of the hardware ECC controller, this property must contain a phandle for the ECC controller node. The required properties for this node are described below. If this is not specified, software ECC will be used instead. @@ -48,7 +48,7 @@ nemc: nemc@13410000 { #address-cells = <1>; #size-cells = <0>; - ingenic,bch-controller = <&bch>; + ecc-engine = <&bch>; nand@1 { reg = <1>; -- cgit v1.2.3 From 9ab948a91b2c2abc8e82845c0e61f4b1683e3a4f Mon Sep 17 00:00:00 2001 From: David Ahern Date: Wed, 20 Mar 2019 09:18:59 -0700 Subject: ipv4: Allow amount of dirty memory from fib resizing to be controllable fib_trie implementation calls synchronize_rcu when a certain amount of pages are dirty from freed entries. The number of pages was determined experimentally in 2009 (commit c3059477fce2d). At the current setting, synchronize_rcu is called often -- 51 times in a second in one test with an average of an 8 msec delay adding a fib entry. The total impact is a lot of slow down modifying the fib. This is seen in the output of 'time' - the difference between real time and sys+user. For example, using 720,022 single path routes and 'ip -batch'[1]: $ time ./ip -batch ipv4/routes-1-hops real 0m14.214s user 0m2.513s sys 0m6.783s So roughly 35% of the actual time to install the routes is from the ip command getting scheduled out, most notably due to synchronize_rcu (this is observed using 'perf sched timehist'). This patch makes the amount of dirty memory configurable between 64k where the synchronize_rcu is called often (small, low end systems that are memory sensitive) to 64M where synchronize_rcu is called rarely during a large FIB change (for high end systems with lots of memory). The default is 512kB which corresponds to the current setting of 128 pages with a 4kB page size. As an example, at 16MB the worst interval shows 4 calls to synchronize_rcu in a second blocking for up to 30 msec in a single instance, and a total of almost 100 msec across the 4 calls in the second. The trade off is allowing FIB entries to consume more memory in a given time window but but with much better fib insertion rates (~30% increase in prefixes/sec). With this patch and net.ipv4.fib_sync_mem set to 16MB, the same batch file runs in: $ time ./ip -batch ipv4/routes-1-hops real 0m9.692s user 0m2.491s sys 0m6.769s So the dead time is reduced to about 1/2 second or <5% of the real time. [1] 'ip' modified to not request ACK messages which improves route insertion times by about 20% Signed-off-by: David Ahern Signed-off-by: David S. Miller --- Documentation/networking/ip-sysctl.txt | 5 +++++ include/net/ip.h | 4 ++++ net/ipv4/fib_trie.c | 14 ++++++++------ net/ipv4/sysctl_net_ipv4.c | 9 +++++++++ 4 files changed, 26 insertions(+), 6 deletions(-) (limited to 'Documentation') diff --git a/Documentation/networking/ip-sysctl.txt b/Documentation/networking/ip-sysctl.txt index bd029fc55ccb..5eedc6941ce5 100644 --- a/Documentation/networking/ip-sysctl.txt +++ b/Documentation/networking/ip-sysctl.txt @@ -81,6 +81,11 @@ fib_multipath_hash_policy - INTEGER 0 - Layer 3 1 - Layer 4 +fib_sync_mem - UNSIGNED INTEGER + Amount of dirty memory from fib entries that can be backlogged before + synchronize_rcu is forced. + Default: 512kB Minimum: 64kB Maximum: 64MB + ip_forward_update_priority - INTEGER Whether to update SKB priority from "TOS" field in IPv4 header after it is forwarded. The new SKB priority is mapped from TOS field value diff --git a/include/net/ip.h b/include/net/ip.h index be3cad9c2e4c..aa09ae5f01a5 100644 --- a/include/net/ip.h +++ b/include/net/ip.h @@ -38,6 +38,10 @@ #define IPV4_MAX_PMTU 65535U /* RFC 2675, Section 5.1 */ #define IPV4_MIN_MTU 68 /* RFC 791 */ +extern unsigned int sysctl_fib_sync_mem; +extern unsigned int sysctl_fib_sync_mem_min; +extern unsigned int sysctl_fib_sync_mem_max; + struct sock; struct inet_skb_parm { diff --git a/net/ipv4/fib_trie.c b/net/ipv4/fib_trie.c index a573e37e0615..1704f432de1f 100644 --- a/net/ipv4/fib_trie.c +++ b/net/ipv4/fib_trie.c @@ -183,14 +183,16 @@ struct trie { }; static struct key_vector *resize(struct trie *t, struct key_vector *tn); -static size_t tnode_free_size; +static unsigned int tnode_free_size; /* - * synchronize_rcu after call_rcu for that many pages; it should be especially - * useful before resizing the root node with PREEMPT_NONE configs; the value was - * obtained experimentally, aiming to avoid visible slowdown. + * synchronize_rcu after call_rcu for outstanding dirty memory; it should be + * especially useful before resizing the root node with PREEMPT_NONE configs; + * the value was obtained experimentally, aiming to avoid visible slowdown. */ -static const int sync_pages = 128; +unsigned int sysctl_fib_sync_mem = 512 * 1024; +unsigned int sysctl_fib_sync_mem_min = 64 * 1024; +unsigned int sysctl_fib_sync_mem_max = 64 * 1024 * 1024; static struct kmem_cache *fn_alias_kmem __ro_after_init; static struct kmem_cache *trie_leaf_kmem __ro_after_init; @@ -504,7 +506,7 @@ static void tnode_free(struct key_vector *tn) tn = container_of(head, struct tnode, rcu)->kv; } - if (tnode_free_size >= PAGE_SIZE * sync_pages) { + if (tnode_free_size >= sysctl_fib_sync_mem) { tnode_free_size = 0; synchronize_rcu(); } diff --git a/net/ipv4/sysctl_net_ipv4.c b/net/ipv4/sysctl_net_ipv4.c index ba0fc4b18465..2316c08e9591 100644 --- a/net/ipv4/sysctl_net_ipv4.c +++ b/net/ipv4/sysctl_net_ipv4.c @@ -549,6 +549,15 @@ static struct ctl_table ipv4_table[] = { .mode = 0644, .proc_handler = proc_doulongvec_minmax, }, + { + .procname = "fib_sync_mem", + .data = &sysctl_fib_sync_mem, + .maxlen = sizeof(sysctl_fib_sync_mem), + .mode = 0644, + .proc_handler = proc_douintvec_minmax, + .extra1 = &sysctl_fib_sync_mem_min, + .extra2 = &sysctl_fib_sync_mem_max, + }, { } }; -- cgit v1.2.3 From 0f0b7e1cc7abf8e1a8b301f2868379d611d05ae2 Mon Sep 17 00:00:00 2001 From: Juri Lelli Date: Thu, 7 Mar 2019 13:09:13 +0100 Subject: x86/tsc: Add option to disable tsc clocksource watchdog Clocksource watchdog has been found responsible for generating latency spikes (in the 10-20 us range) when woken up to check for TSC stability. Add an option to disable it at boot. Signed-off-by: Juri Lelli Signed-off-by: Thomas Gleixner Cc: bigeasy@linutronix.de Cc: linux-rt-users@vger.kernel.org Cc: peterz@infradead.org Cc: bristot@redhat.com Cc: williams@redhat.com Link: https://lkml.kernel.org/r/20190307120913.13168-1-juri.lelli@redhat.com --- Documentation/admin-guide/kernel-parameters.txt | 4 ++++ arch/x86/kernel/tsc.c | 5 ++++- 2 files changed, 8 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt index 2b8ee90bb644..c4d830003b21 100644 --- a/Documentation/admin-guide/kernel-parameters.txt +++ b/Documentation/admin-guide/kernel-parameters.txt @@ -4703,6 +4703,10 @@ [x86] unstable: mark the TSC clocksource as unstable, this marks the TSC unconditionally unstable at bootup and avoids any further wobbles once the TSC watchdog notices. + [x86] nowatchdog: disable clocksource watchdog. Used + in situations with strict latency requirements (where + interruptions from clocksource watchdog are not + acceptable). turbografx.map[2|3]= [HW,JOY] TurboGraFX parallel port interface diff --git a/arch/x86/kernel/tsc.c b/arch/x86/kernel/tsc.c index 3fae23834069..aab0c82e0a0d 100644 --- a/arch/x86/kernel/tsc.c +++ b/arch/x86/kernel/tsc.c @@ -283,6 +283,7 @@ int __init notsc_setup(char *str) __setup("notsc", notsc_setup); static int no_sched_irq_time; +static int no_tsc_watchdog; static int __init tsc_setup(char *str) { @@ -292,6 +293,8 @@ static int __init tsc_setup(char *str) no_sched_irq_time = 1; if (!strcmp(str, "unstable")) mark_tsc_unstable("boot parameter"); + if (!strcmp(str, "nowatchdog")) + no_tsc_watchdog = 1; return 1; } @@ -1349,7 +1352,7 @@ static int __init init_tsc_clocksource(void) if (tsc_unstable) goto unreg; - if (tsc_clocksource_reliable) + if (tsc_clocksource_reliable || no_tsc_watchdog) clocksource_tsc.flags &= ~CLOCK_SOURCE_MUST_VERIFY; if (boot_cpu_has(X86_FEATURE_NONSTOP_TSC_S3)) -- cgit v1.2.3 From 5c9f8cfe3cb67dcbf3e38a2b64c887200e363376 Mon Sep 17 00:00:00 2001 From: Geert Uytterhoeven Date: Thu, 21 Mar 2019 10:21:44 +0100 Subject: dt-bindings: gpio: pca953x: Document onnn,cat9554 The ON Semiconductor CAT9554 is a variant of the PCA953x GPIO expander, with 8 GPIOs and interrupt functionality. Signed-off-by: Geert Uytterhoeven Signed-off-by: Bartosz Golaszewski --- Documentation/devicetree/bindings/gpio/gpio-pca953x.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/gpio/gpio-pca953x.txt b/Documentation/devicetree/bindings/gpio/gpio-pca953x.txt index fb144e2b6522..8678df2a5713 100644 --- a/Documentation/devicetree/bindings/gpio/gpio-pca953x.txt +++ b/Documentation/devicetree/bindings/gpio/gpio-pca953x.txt @@ -30,6 +30,7 @@ Required properties: ti,tca6424 ti,tca9539 ti,tca9554 + onnn,cat9554 onnn,pca9654 exar,xra1202 - gpio-controller: if used as gpio expander. -- cgit v1.2.3 From 472ec0ce3ef4111c1b55e6f677599cef4b52eed1 Mon Sep 17 00:00:00 2001 From: Bich HEMON Date: Wed, 6 Mar 2019 15:11:51 +0000 Subject: dt-bindings: i2c: stm32: remove extra spaces Remove extra spaces before colons. Signed-off-by: Bich Hemon Reviewed-by: Pierre-Yves MORDRET Signed-off-by: Wolfram Sang --- .../devicetree/bindings/i2c/i2c-stm32.txt | 26 +++++++++++----------- 1 file changed, 13 insertions(+), 13 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/i2c/i2c-stm32.txt b/Documentation/devicetree/bindings/i2c/i2c-stm32.txt index 69240e189b01..7d054f1a5b2b 100644 --- a/Documentation/devicetree/bindings/i2c/i2c-stm32.txt +++ b/Documentation/devicetree/bindings/i2c/i2c-stm32.txt @@ -1,11 +1,11 @@ * I2C controller embedded in STMicroelectronics STM32 I2C platform -Required properties : -- compatible : Must be one of the following +Required properties: +- compatible: Must be one of the following - "st,stm32f4-i2c" - "st,stm32f7-i2c" -- reg : Offset and length of the register set for the device -- interrupts : Must contain the interrupt id for I2C event and then the +- reg: Offset and length of the register set for the device +- interrupts: Must contain the interrupt id for I2C event and then the interrupt id for I2C error. - resets: Must contain the phandle to the reset controller. - clocks: Must contain the input clock of the I2C instance. @@ -14,25 +14,25 @@ Required properties : - #address-cells = <1>; - #size-cells = <0>; -Optional properties : -- clock-frequency : Desired I2C bus clock frequency in Hz. If not specified, +Optional properties: +- clock-frequency: Desired I2C bus clock frequency in Hz. If not specified, the default 100 kHz frequency will be used. For STM32F4 SoC Standard-mode and Fast-mode are supported, possible values are 100000 and 400000. For STM32F7 SoC, Standard-mode, Fast-mode and Fast-mode Plus are supported, possible values are 100000, 400000 and 1000000. -- i2c-scl-rising-time-ns : Only for STM32F7, I2C SCL Rising time for the board +- i2c-scl-rising-time-ns: Only for STM32F7, I2C SCL Rising time for the board (default: 25) -- i2c-scl-falling-time-ns : Only for STM32F7, I2C SCL Falling time for the board +- i2c-scl-falling-time-ns: Only for STM32F7, I2C SCL Falling time for the board (default: 10) I2C Timings are derived from these 2 values -- st,syscfg-fmp: Only for STM32F7, use to set Fast Mode Plus bit within SYSCFG +- st,syscfg-fmp: Only for STM32F7, use to set Fast Mode Plus bit within SYSCFG whether Fast Mode Plus speed is selected by slave. - 1st cell : phandle to syscfg - 2nd cell : register offset within SYSCFG - 3rd cell : register bitmask for FMP bit + 1st cell: phandle to syscfg + 2nd cell: register offset within SYSCFG + 3rd cell: register bitmask for FMP bit -Example : +Example: i2c@40005400 { compatible = "st,stm32f4-i2c"; -- cgit v1.2.3 From 36ea73cb9a42aaf67451f6a9373777363a6ce508 Mon Sep 17 00:00:00 2001 From: Bich HEMON Date: Wed, 6 Mar 2019 15:11:51 +0000 Subject: dt-bindings: i2c: stm32: update optional properties for stm32h7/stm32mp1 Add STM32H7 and STM32MP1 in the list of compatible socs for each optional property. Signed-off-by: Bich Hemon Reviewed-by: Pierre-Yves MORDRET Signed-off-by: Wolfram Sang --- Documentation/devicetree/bindings/i2c/i2c-stm32.txt | 17 +++++++++-------- 1 file changed, 9 insertions(+), 8 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/i2c/i2c-stm32.txt b/Documentation/devicetree/bindings/i2c/i2c-stm32.txt index 7d054f1a5b2b..f334738f7a35 100644 --- a/Documentation/devicetree/bindings/i2c/i2c-stm32.txt +++ b/Documentation/devicetree/bindings/i2c/i2c-stm32.txt @@ -19,18 +19,19 @@ Optional properties: the default 100 kHz frequency will be used. For STM32F4 SoC Standard-mode and Fast-mode are supported, possible values are 100000 and 400000. - For STM32F7 SoC, Standard-mode, Fast-mode and Fast-mode Plus are supported, - possible values are 100000, 400000 and 1000000. -- i2c-scl-rising-time-ns: Only for STM32F7, I2C SCL Rising time for the board - (default: 25) -- i2c-scl-falling-time-ns: Only for STM32F7, I2C SCL Falling time for the board - (default: 10) + For STM32F7, STM32H7 and STM32MP1 SoCs, Standard-mode, Fast-mode and Fast-mode + Plus are supported, possible values are 100000, 400000 and 1000000. +- i2c-scl-rising-time-ns: I2C SCL Rising time for the board (default: 25) + For STM32F7, STM32H7 and STM32MP1 only. +- i2c-scl-falling-time-ns: I2C SCL Falling time for the board (default: 10) + For STM32F7, STM32H7 and STM32MP1 only. I2C Timings are derived from these 2 values -- st,syscfg-fmp: Only for STM32F7, use to set Fast Mode Plus bit within SYSCFG - whether Fast Mode Plus speed is selected by slave. +- st,syscfg-fmp: Use to set Fast Mode Plus bit within SYSCFG when Fast Mode + Plus speed is selected by slave. 1st cell: phandle to syscfg 2nd cell: register offset within SYSCFG 3rd cell: register bitmask for FMP bit + For STM32F7, STM32H7 and STM32MP1 only. Example: -- cgit v1.2.3 From 4c35e15a8311fbf5dd95b598a43bb28985876ee2 Mon Sep 17 00:00:00 2001 From: Sven Eckelmann Date: Sun, 3 Mar 2019 18:02:55 +0100 Subject: batman-adv: Drop documentation about debugfs files The debugfs files were marked as deprecated by commit 00caf6a2b318 ("batman-adv: Mark debugfs functionality as deprecated"). The documentation should not advertise its usage anymore and instead promote the generic netlink family and a userspace tool to access it. Signed-off-by: Sven Eckelmann Signed-off-by: Simon Wunderlich --- Documentation/networking/batman-adv.rst | 29 +++++++++-------------------- 1 file changed, 9 insertions(+), 20 deletions(-) (limited to 'Documentation') diff --git a/Documentation/networking/batman-adv.rst b/Documentation/networking/batman-adv.rst index 245fb6c0ab6f..1b9ff47c0976 100644 --- a/Documentation/networking/batman-adv.rst +++ b/Documentation/networking/batman-adv.rst @@ -74,23 +74,9 @@ All mesh wide settings can be found in batman's own interface folder:: bridge_loop_avoidance gw_sel_class network_coding distributed_arp_table hop_penalty orig_interval -There is a special folder for debugging information:: - - $ ls /sys/kernel/debug/batman_adv/bat0/ - bla_backbone_table log neighbors transtable_local - bla_claim_table mcast_flags originators - dat_cache nc socket - gateways nc_nodes transtable_global - -Some of the files contain all sort of status information regarding the mesh -network. For example, you can view the table of originators (mesh -participants) with:: - - $ cat /sys/kernel/debug/batman_adv/bat0/originators - -Other files allow to change batman's behaviour to better fit your requirements. -For instance, you can check the current originator interval (value in -milliseconds which determines how often batman sends its broadcast packets):: +Some files allow to change batman-adv's behaviour to better fit your +requirements. For instance, you can check the current originator interval (value +in milliseconds which determines how often batman sends its broadcast packets):: $ cat /sys/class/net/bat0/mesh/orig_interval 1000 @@ -103,6 +89,10 @@ In very mobile scenarios, you might want to adjust the originator interval to a lower value. This will make the mesh more responsive to topology changes, but will also increase the overhead. +Information about the current state can be accessed via the batadv generic +netlink family. batctl provides human readable version via its debug tables +subcommands. + Usage ===== @@ -147,10 +137,9 @@ batman-adv module. When building batman-adv as part of kernel, use "make menuconfig" and enable the option ``B.A.T.M.A.N. debugging`` (``CONFIG_BATMAN_ADV_DEBUG=y``). -Those additional debug messages can be accessed using a special file in -debugfs:: +Those additional debug messages can be accessed using the perf infrastructure:: - $ cat /sys/kernel/debug/batman_adv/bat0/log + $ trace-cmd stream -e batadv:batadv_dbg The additional debug output is by default disabled. It can be enabled during run time. Following log_levels are defined: -- cgit v1.2.3 From 52735a6f0bd2593d681001ded2f7fbbee168a235 Mon Sep 17 00:00:00 2001 From: Sven Eckelmann Date: Sun, 3 Mar 2019 18:02:56 +0100 Subject: batman-adv: Drop documentation about sysfs files The sysfs files will be marked as deprecated in the near future. They are already replaced by the batadv generic netlink family. The documentation should not advertise its usage anymore and instead promote the generic netlink family and a userspace tool to access it. Signed-off-by: Sven Eckelmann Signed-off-by: Simon Wunderlich --- Documentation/networking/batman-adv.rst | 91 +++++++++------------------------ 1 file changed, 24 insertions(+), 67 deletions(-) (limited to 'Documentation') diff --git a/Documentation/networking/batman-adv.rst b/Documentation/networking/batman-adv.rst index 1b9ff47c0976..18020943ba25 100644 --- a/Documentation/networking/batman-adv.rst +++ b/Documentation/networking/batman-adv.rst @@ -27,24 +27,8 @@ Load the batman-adv module into your kernel:: $ insmod batman-adv.ko The module is now waiting for activation. You must add some interfaces on which -batman can operate. After loading the module batman advanced will scan your -systems interfaces to search for compatible interfaces. Once found, it will -create subfolders in the ``/sys`` directories of each supported interface, -e.g.:: - - $ ls /sys/class/net/eth0/batman_adv/ - elp_interval iface_status mesh_iface throughput_override - -If an interface does not have the ``batman_adv`` subfolder, it probably is not -supported. Not supported interfaces are: loopback, non-ethernet and batman's -own interfaces. - -Note: After the module was loaded it will continuously watch for new -interfaces to verify the compatibility. There is no need to reload the module -if you plug your USB wifi adapter into your machine after batman advanced was -initially loaded. - -The batman-adv soft-interface can be created using the iproute2 tool ``ip``:: +batman-adv can operate. The batman-adv soft-interface can be created using the +iproute2 tool ``ip``:: $ ip link add name bat0 type batadv @@ -52,38 +36,37 @@ To activate a given interface simply attach it to the ``bat0`` interface:: $ ip link set dev eth0 master bat0 -Repeat this step for all interfaces you wish to add. Now batman starts +Repeat this step for all interfaces you wish to add. Now batman-adv starts using/broadcasting on this/these interface(s). -By reading the "iface_status" file you can check its status:: - - $ cat /sys/class/net/eth0/batman_adv/iface_status - active - To deactivate an interface you have to detach it from the "bat0" interface:: $ ip link set dev eth0 nomaster +The same can also be done using the batctl interface subcommand:: + + batctl -m bat0 interface create + batctl -m bat0 interface add -M eth0 + +To detach eth0 and destroy bat0:: -All mesh wide settings can be found in batman's own interface folder:: + batctl -m bat0 interface del -M eth0 + batctl -m bat0 interface destroy - $ ls /sys/class/net/bat0/mesh/ - aggregated_ogms fragmentation isolation_mark routing_algo - ap_isolation gw_bandwidth log_level vlan0 - bonding gw_mode multicast_mode - bridge_loop_avoidance gw_sel_class network_coding - distributed_arp_table hop_penalty orig_interval +There are additional settings for each batadv mesh interface, vlan and hardif +which can be modified using batctl. Detailed information about this can be found +in its manual. -Some files allow to change batman-adv's behaviour to better fit your -requirements. For instance, you can check the current originator interval (value -in milliseconds which determines how often batman sends its broadcast packets):: +For instance, you can check the current originator interval (value +in milliseconds which determines how often batman-adv sends its broadcast +packets):: - $ cat /sys/class/net/bat0/mesh/orig_interval + $ batctl -M bat0 orig_interval 1000 and also change its value:: - $ echo 3000 > /sys/class/net/bat0/mesh/orig_interval + $ batctl -M bat0 orig_interval 3000 In very mobile scenarios, you might want to adjust the originator interval to a lower value. This will make the mesh more responsive to topology changes, but @@ -142,37 +125,11 @@ Those additional debug messages can be accessed using the perf infrastructure:: $ trace-cmd stream -e batadv:batadv_dbg The additional debug output is by default disabled. It can be enabled during -run time. Following log_levels are defined: - -.. flat-table:: - - * - 0 - - All debug output disabled - * - 1 - - Enable messages related to routing / flooding / broadcasting - * - 2 - - Enable messages related to route added / changed / deleted - * - 4 - - Enable messages related to translation table operations - * - 8 - - Enable messages related to bridge loop avoidance - * - 16 - - Enable messages related to DAT, ARP snooping and parsing - * - 32 - - Enable messages related to network coding - * - 64 - - Enable messages related to multicast - * - 128 - - Enable messages related to throughput meter - * - 255 - - Enable all messages - -The debug output can be changed at runtime using the file -``/sys/class/net/bat0/mesh/log_level``. e.g.:: - - $ echo 6 > /sys/class/net/bat0/mesh/log_level - -will enable debug messages for when routes change. +run time:: + + $ batctl -m bat0 loglevel routes tt + +will enable debug messages for when routes and translation table entries change. Counters for different types of packets entering and leaving the batman-adv module are available through ethtool:: -- cgit v1.2.3 From 42cdd521487f6509f52096fa08590f275073e81b Mon Sep 17 00:00:00 2001 From: Sven Eckelmann Date: Sun, 3 Mar 2019 18:02:58 +0100 Subject: batman-adv: ABI: Mark sysfs files as deprecated The sysfs files are replaced by the batadv generic netlink family. The old sysfs configuration interface was frowned upon by other kernel developers. But the files cannot be removed immediately because userspace tools might still depend on it. Instead schedule for its removal in 2021. Signed-off-by: Sven Eckelmann Signed-off-by: Simon Wunderlich --- .../ABI/obsolete/sysfs-class-net-batman-adv | 32 ++++++ Documentation/ABI/obsolete/sysfs-class-net-mesh | 110 +++++++++++++++++++++ .../ABI/testing/sysfs-class-net-batman-adv | 30 ------ Documentation/ABI/testing/sysfs-class-net-mesh | 108 -------------------- MAINTAINERS | 4 +- 5 files changed, 144 insertions(+), 140 deletions(-) create mode 100644 Documentation/ABI/obsolete/sysfs-class-net-batman-adv create mode 100644 Documentation/ABI/obsolete/sysfs-class-net-mesh delete mode 100644 Documentation/ABI/testing/sysfs-class-net-batman-adv delete mode 100644 Documentation/ABI/testing/sysfs-class-net-mesh (limited to 'Documentation') diff --git a/Documentation/ABI/obsolete/sysfs-class-net-batman-adv b/Documentation/ABI/obsolete/sysfs-class-net-batman-adv new file mode 100644 index 000000000000..5bdbc8d40256 --- /dev/null +++ b/Documentation/ABI/obsolete/sysfs-class-net-batman-adv @@ -0,0 +1,32 @@ +This ABI is deprecated and will be removed after 2021. It is +replaced with the batadv generic netlink family. + +What: /sys/class/net//batman-adv/elp_interval +Date: Feb 2014 +Contact: Linus Lüssing +Description: + Defines the interval in milliseconds in which batman + emits probing packets for neighbor sensing (ELP). + +What: /sys/class/net//batman-adv/iface_status +Date: May 2010 +Contact: Marek Lindner +Description: + Indicates the status of as it is seen by batman. + +What: /sys/class/net//batman-adv/mesh_iface +Date: May 2010 +Contact: Marek Lindner +Description: + The /sys/class/net//batman-adv/mesh_iface file + displays the batman mesh interface this + currently is associated with. + +What: /sys/class/net//batman-adv/throughput_override +Date: Feb 2014 +Contact: Antonio Quartulli +description: + Defines the throughput value to be used by B.A.T.M.A.N. V + when estimating the link throughput using this interface. + If the value is set to 0 then batman-adv will try to + estimate the throughput by itself. diff --git a/Documentation/ABI/obsolete/sysfs-class-net-mesh b/Documentation/ABI/obsolete/sysfs-class-net-mesh new file mode 100644 index 000000000000..04c1a2932507 --- /dev/null +++ b/Documentation/ABI/obsolete/sysfs-class-net-mesh @@ -0,0 +1,110 @@ +This ABI is deprecated and will be removed after 2021. It is +replaced with the batadv generic netlink family. + +What: /sys/class/net//mesh/aggregated_ogms +Date: May 2010 +Contact: Marek Lindner +Description: + Indicates whether the batman protocol messages of the + mesh shall be aggregated or not. + +What: /sys/class/net//mesh//ap_isolation +Date: May 2011 +Contact: Antonio Quartulli +Description: + Indicates whether the data traffic going from a + wireless client to another wireless client will be + silently dropped. is empty when referring + to the untagged lan. + +What: /sys/class/net//mesh/bonding +Date: June 2010 +Contact: Simon Wunderlich +Description: + Indicates whether the data traffic going through the + mesh will be sent using multiple interfaces at the + same time (if available). + +What: /sys/class/net//mesh/bridge_loop_avoidance +Date: November 2011 +Contact: Simon Wunderlich +Description: + Indicates whether the bridge loop avoidance feature + is enabled. This feature detects and avoids loops + between the mesh and devices bridged with the soft + interface . + +What: /sys/class/net//mesh/fragmentation +Date: October 2010 +Contact: Andreas Langer +Description: + Indicates whether the data traffic going through the + mesh will be fragmented or silently discarded if the + packet size exceeds the outgoing interface MTU. + +What: /sys/class/net//mesh/gw_bandwidth +Date: October 2010 +Contact: Marek Lindner +Description: + Defines the bandwidth which is propagated by this + node if gw_mode was set to 'server'. + +What: /sys/class/net//mesh/gw_mode +Date: October 2010 +Contact: Marek Lindner +Description: + Defines the state of the gateway features. Can be + either 'off', 'client' or 'server'. + +What: /sys/class/net//mesh/gw_sel_class +Date: October 2010 +Contact: Marek Lindner +Description: + Defines the selection criteria this node will use + to choose a gateway if gw_mode was set to 'client'. + +What: /sys/class/net//mesh/hop_penalty +Date: Oct 2010 +Contact: Linus Lüssing +Description: + Defines the penalty which will be applied to an + originator message's tq-field on every hop. + +What: /sys/class/net//mesh/isolation_mark +Date: Nov 2013 +Contact: Antonio Quartulli +Description: + Defines the isolation mark (and its bitmask) which + is used to classify clients as "isolated" by the + Extended Isolation feature. + +What: /sys/class/net//mesh/multicast_mode +Date: Feb 2014 +Contact: Linus Lüssing +Description: + Indicates whether multicast optimizations are enabled + or disabled. If set to zero then all nodes in the + mesh are going to use classic flooding for any + multicast packet with no optimizations. + +What: /sys/class/net//mesh/network_coding +Date: Nov 2012 +Contact: Martin Hundeboll +Description: + Controls whether Network Coding (using some magic + to send fewer wifi packets but still the same + content) is enabled or not. + +What: /sys/class/net//mesh/orig_interval +Date: May 2010 +Contact: Marek Lindner +Description: + Defines the interval in milliseconds in which batman + sends its protocol messages. + +What: /sys/class/net//mesh/routing_algo +Date: Dec 2011 +Contact: Marek Lindner +Description: + Defines the routing procotol this mesh instance + uses to find the optimal paths through the mesh. diff --git a/Documentation/ABI/testing/sysfs-class-net-batman-adv b/Documentation/ABI/testing/sysfs-class-net-batman-adv deleted file mode 100644 index 898106849e27..000000000000 --- a/Documentation/ABI/testing/sysfs-class-net-batman-adv +++ /dev/null @@ -1,30 +0,0 @@ - -What: /sys/class/net//batman-adv/elp_interval -Date: Feb 2014 -Contact: Linus Lüssing -Description: - Defines the interval in milliseconds in which batman - emits probing packets for neighbor sensing (ELP). - -What: /sys/class/net//batman-adv/iface_status -Date: May 2010 -Contact: Marek Lindner -Description: - Indicates the status of as it is seen by batman. - -What: /sys/class/net//batman-adv/mesh_iface -Date: May 2010 -Contact: Marek Lindner -Description: - The /sys/class/net//batman-adv/mesh_iface file - displays the batman mesh interface this - currently is associated with. - -What: /sys/class/net//batman-adv/throughput_override -Date: Feb 2014 -Contact: Antonio Quartulli -description: - Defines the throughput value to be used by B.A.T.M.A.N. V - when estimating the link throughput using this interface. - If the value is set to 0 then batman-adv will try to - estimate the throughput by itself. diff --git a/Documentation/ABI/testing/sysfs-class-net-mesh b/Documentation/ABI/testing/sysfs-class-net-mesh deleted file mode 100644 index c2b956d44a95..000000000000 --- a/Documentation/ABI/testing/sysfs-class-net-mesh +++ /dev/null @@ -1,108 +0,0 @@ - -What: /sys/class/net//mesh/aggregated_ogms -Date: May 2010 -Contact: Marek Lindner -Description: - Indicates whether the batman protocol messages of the - mesh shall be aggregated or not. - -What: /sys/class/net//mesh//ap_isolation -Date: May 2011 -Contact: Antonio Quartulli -Description: - Indicates whether the data traffic going from a - wireless client to another wireless client will be - silently dropped. is empty when referring - to the untagged lan. - -What: /sys/class/net//mesh/bonding -Date: June 2010 -Contact: Simon Wunderlich -Description: - Indicates whether the data traffic going through the - mesh will be sent using multiple interfaces at the - same time (if available). - -What: /sys/class/net//mesh/bridge_loop_avoidance -Date: November 2011 -Contact: Simon Wunderlich -Description: - Indicates whether the bridge loop avoidance feature - is enabled. This feature detects and avoids loops - between the mesh and devices bridged with the soft - interface . - -What: /sys/class/net//mesh/fragmentation -Date: October 2010 -Contact: Andreas Langer -Description: - Indicates whether the data traffic going through the - mesh will be fragmented or silently discarded if the - packet size exceeds the outgoing interface MTU. - -What: /sys/class/net//mesh/gw_bandwidth -Date: October 2010 -Contact: Marek Lindner -Description: - Defines the bandwidth which is propagated by this - node if gw_mode was set to 'server'. - -What: /sys/class/net//mesh/gw_mode -Date: October 2010 -Contact: Marek Lindner -Description: - Defines the state of the gateway features. Can be - either 'off', 'client' or 'server'. - -What: /sys/class/net//mesh/gw_sel_class -Date: October 2010 -Contact: Marek Lindner -Description: - Defines the selection criteria this node will use - to choose a gateway if gw_mode was set to 'client'. - -What: /sys/class/net//mesh/hop_penalty -Date: Oct 2010 -Contact: Linus Lüssing -Description: - Defines the penalty which will be applied to an - originator message's tq-field on every hop. - -What: /sys/class/net//mesh/isolation_mark -Date: Nov 2013 -Contact: Antonio Quartulli -Description: - Defines the isolation mark (and its bitmask) which - is used to classify clients as "isolated" by the - Extended Isolation feature. - -What: /sys/class/net//mesh/multicast_mode -Date: Feb 2014 -Contact: Linus Lüssing -Description: - Indicates whether multicast optimizations are enabled - or disabled. If set to zero then all nodes in the - mesh are going to use classic flooding for any - multicast packet with no optimizations. - -What: /sys/class/net//mesh/network_coding -Date: Nov 2012 -Contact: Martin Hundeboll -Description: - Controls whether Network Coding (using some magic - to send fewer wifi packets but still the same - content) is enabled or not. - -What: /sys/class/net//mesh/orig_interval -Date: May 2010 -Contact: Marek Lindner -Description: - Defines the interval in milliseconds in which batman - sends its protocol messages. - -What: /sys/class/net//mesh/routing_algo -Date: Dec 2011 -Contact: Marek Lindner -Description: - Defines the routing procotol this mesh instance - uses to find the optimal paths through the mesh. diff --git a/MAINTAINERS b/MAINTAINERS index f8ff9ae52c21..fce2919582fb 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -2795,8 +2795,8 @@ L: b.a.t.m.a.n@lists.open-mesh.org (moderated for non-subscribers) W: https://www.open-mesh.org/ Q: https://patchwork.open-mesh.org/project/batman/list/ S: Maintained -F: Documentation/ABI/testing/sysfs-class-net-batman-adv -F: Documentation/ABI/testing/sysfs-class-net-mesh +F: Documentation/ABI/obsolete/sysfs-class-net-batman-adv +F: Documentation/ABI/obsolete/sysfs-class-net-mesh F: Documentation/networking/batman-adv.rst F: include/uapi/linux/batadv_packet.h F: include/uapi/linux/batman_adv.h -- cgit v1.2.3 From cbd66c626e16743b05af807ad48012c0a097b9fb Mon Sep 17 00:00:00 2001 From: Stefan Roese Date: Mon, 25 Mar 2019 09:29:25 +0100 Subject: spi: mt7621: Move SPI driver out of staging This patch moves the MT7621 SPI driver, which is used on some Ralink / MediaTek MT76xx MIPS SoC's, out of the staging directory. No changes to the source code are done in this patch. This driver version was tested successfully on an MT7688 based platform with an SPI NOR on CS0 and an SPI NAND on CS1 without any issues (so far). This patch also documents the devicetree bindings for the MT7621 SPI device driver. Signed-off-by: Stefan Roese Cc: Rob Herring Cc: Mark Brown Cc: Greg Kroah-Hartman Cc: NeilBrown Cc: Sankalp Negi Cc: Chuanhong Guo Cc: John Crispin Cc: Armando Miraglia Signed-off-by: Mark Brown --- .../devicetree/bindings/spi/spi-mt7621.txt | 26 ++ drivers/spi/Kconfig | 6 + drivers/spi/Makefile | 1 + drivers/spi/spi-mt7621.c | 421 ++++++++++++++++++++ drivers/staging/Kconfig | 2 - drivers/staging/Makefile | 1 - drivers/staging/mt7621-spi/Kconfig | 6 - drivers/staging/mt7621-spi/Makefile | 1 - drivers/staging/mt7621-spi/TODO | 5 - drivers/staging/mt7621-spi/spi-mt7621.c | 422 --------------------- 10 files changed, 454 insertions(+), 437 deletions(-) create mode 100644 Documentation/devicetree/bindings/spi/spi-mt7621.txt create mode 100644 drivers/spi/spi-mt7621.c delete mode 100644 drivers/staging/mt7621-spi/Kconfig delete mode 100644 drivers/staging/mt7621-spi/Makefile delete mode 100644 drivers/staging/mt7621-spi/TODO delete mode 100644 drivers/staging/mt7621-spi/spi-mt7621.c (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/spi/spi-mt7621.txt b/Documentation/devicetree/bindings/spi/spi-mt7621.txt new file mode 100644 index 000000000000..d5baec0fa56e --- /dev/null +++ b/Documentation/devicetree/bindings/spi/spi-mt7621.txt @@ -0,0 +1,26 @@ +Binding for MTK SPI controller (MT7621 MIPS) + +Required properties: +- compatible: Should be one of the following: + - "ralink,mt7621-spi": for mt7621/mt7628/mt7688 platforms +- #address-cells: should be 1. +- #size-cells: should be 0. +- reg: Address and length of the register set for the device +- resets: phandle to the reset controller asserting this device in + reset + See ../reset/reset.txt for details. + +Optional properties: +- cs-gpios: see spi-bus.txt. + +Example: + +- SoC Specific Portion: +spi0: spi@b00 { + compatible = "ralink,mt7621-spi"; + reg = <0xb00 0x100>; + #address-cells = <1>; + #size-cells = <0>; + resets = <&rstctrl 18>; + reset-names = "spi"; +}; diff --git a/drivers/spi/Kconfig b/drivers/spi/Kconfig index f761655e2a36..8ce4f7df0ef2 100644 --- a/drivers/spi/Kconfig +++ b/drivers/spi/Kconfig @@ -426,6 +426,12 @@ config SPI_MT65XX say Y or M here.If you are not sure, say N. SPI drivers for Mediatek MT65XX and MT81XX series ARM SoCs. +config SPI_MT7621 + tristate "MediaTek MT7621 SPI Controller" + depends on RALINK || COMPILE_TEST + help + This selects a driver for the MediaTek MT7621 SPI Controller. + config SPI_NPCM_PSPI tristate "Nuvoton NPCM PSPI Controller" depends on ARCH_NPCM || COMPILE_TEST diff --git a/drivers/spi/Makefile b/drivers/spi/Makefile index d8fc03c9faa2..369f29a8a6af 100644 --- a/drivers/spi/Makefile +++ b/drivers/spi/Makefile @@ -60,6 +60,7 @@ obj-$(CONFIG_SPI_MPC512x_PSC) += spi-mpc512x-psc.o obj-$(CONFIG_SPI_MPC52xx_PSC) += spi-mpc52xx-psc.o obj-$(CONFIG_SPI_MPC52xx) += spi-mpc52xx.o obj-$(CONFIG_SPI_MT65XX) += spi-mt65xx.o +obj-$(CONFIG_SPI_MT7621) += spi-mt7621.o obj-$(CONFIG_SPI_MXIC) += spi-mxic.o obj-$(CONFIG_SPI_MXS) += spi-mxs.o obj-$(CONFIG_SPI_NPCM_PSPI) += spi-npcm-pspi.o diff --git a/drivers/spi/spi-mt7621.c b/drivers/spi/spi-mt7621.c new file mode 100644 index 000000000000..ae836114ee3d --- /dev/null +++ b/drivers/spi/spi-mt7621.c @@ -0,0 +1,421 @@ +// SPDX-License-Identifier: GPL-2.0 +// +// spi-mt7621.c -- MediaTek MT7621 SPI controller driver +// +// Copyright (C) 2011 Sergiy +// Copyright (C) 2011-2013 Gabor Juhos +// Copyright (C) 2014-2015 Felix Fietkau +// +// Some parts are based on spi-orion.c: +// Author: Shadi Ammouri +// Copyright (C) 2007-2008 Marvell Ltd. + +#include +#include +#include +#include +#include +#include +#include + +#define DRIVER_NAME "spi-mt7621" + +/* in usec */ +#define RALINK_SPI_WAIT_MAX_LOOP 2000 + +/* SPISTAT register bit field */ +#define SPISTAT_BUSY BIT(0) + +#define MT7621_SPI_TRANS 0x00 +#define SPITRANS_BUSY BIT(16) + +#define MT7621_SPI_OPCODE 0x04 +#define MT7621_SPI_DATA0 0x08 +#define MT7621_SPI_DATA4 0x18 +#define SPI_CTL_TX_RX_CNT_MASK 0xff +#define SPI_CTL_START BIT(8) + +#define MT7621_SPI_MASTER 0x28 +#define MASTER_MORE_BUFMODE BIT(2) +#define MASTER_FULL_DUPLEX BIT(10) +#define MASTER_RS_CLK_SEL GENMASK(27, 16) +#define MASTER_RS_CLK_SEL_SHIFT 16 +#define MASTER_RS_SLAVE_SEL GENMASK(31, 29) + +#define MT7621_SPI_MOREBUF 0x2c +#define MT7621_SPI_POLAR 0x38 +#define MT7621_SPI_SPACE 0x3c + +#define MT7621_CPHA BIT(5) +#define MT7621_CPOL BIT(4) +#define MT7621_LSB_FIRST BIT(3) + +struct mt7621_spi { + struct spi_controller *master; + void __iomem *base; + unsigned int sys_freq; + unsigned int speed; + struct clk *clk; + int pending_write; + + struct mt7621_spi_ops *ops; +}; + +static inline struct mt7621_spi *spidev_to_mt7621_spi(struct spi_device *spi) +{ + return spi_controller_get_devdata(spi->master); +} + +static inline u32 mt7621_spi_read(struct mt7621_spi *rs, u32 reg) +{ + return ioread32(rs->base + reg); +} + +static inline void mt7621_spi_write(struct mt7621_spi *rs, u32 reg, u32 val) +{ + iowrite32(val, rs->base + reg); +} + +static void mt7621_spi_set_cs(struct spi_device *spi, int enable) +{ + struct mt7621_spi *rs = spidev_to_mt7621_spi(spi); + int cs = spi->chip_select; + u32 polar = 0; + u32 master; + + /* + * Select SPI device 7, enable "more buffer mode" and disable + * full-duplex (only half-duplex really works on this chip + * reliably) + */ + master = mt7621_spi_read(rs, MT7621_SPI_MASTER); + master |= MASTER_RS_SLAVE_SEL | MASTER_MORE_BUFMODE; + master &= ~MASTER_FULL_DUPLEX; + mt7621_spi_write(rs, MT7621_SPI_MASTER, master); + + rs->pending_write = 0; + + if (enable) + polar = BIT(cs); + mt7621_spi_write(rs, MT7621_SPI_POLAR, polar); +} + +static int mt7621_spi_prepare(struct spi_device *spi, unsigned int speed) +{ + struct mt7621_spi *rs = spidev_to_mt7621_spi(spi); + u32 rate; + u32 reg; + + dev_dbg(&spi->dev, "speed:%u\n", speed); + + rate = DIV_ROUND_UP(rs->sys_freq, speed); + dev_dbg(&spi->dev, "rate-1:%u\n", rate); + + if (rate > 4097) + return -EINVAL; + + if (rate < 2) + rate = 2; + + reg = mt7621_spi_read(rs, MT7621_SPI_MASTER); + reg &= ~MASTER_RS_CLK_SEL; + reg |= (rate - 2) << MASTER_RS_CLK_SEL_SHIFT; + rs->speed = speed; + + reg &= ~MT7621_LSB_FIRST; + if (spi->mode & SPI_LSB_FIRST) + reg |= MT7621_LSB_FIRST; + + /* + * This SPI controller seems to be tested on SPI flash only and some + * bits are swizzled under other SPI modes probably due to incorrect + * wiring inside the silicon. Only mode 0 works correctly. + */ + reg &= ~(MT7621_CPHA | MT7621_CPOL); + + mt7621_spi_write(rs, MT7621_SPI_MASTER, reg); + + return 0; +} + +static inline int mt7621_spi_wait_till_ready(struct mt7621_spi *rs) +{ + int i; + + for (i = 0; i < RALINK_SPI_WAIT_MAX_LOOP; i++) { + u32 status; + + status = mt7621_spi_read(rs, MT7621_SPI_TRANS); + if ((status & SPITRANS_BUSY) == 0) + return 0; + cpu_relax(); + udelay(1); + } + + return -ETIMEDOUT; +} + +static void mt7621_spi_read_half_duplex(struct mt7621_spi *rs, + int rx_len, u8 *buf) +{ + int tx_len; + + /* + * Combine with any pending write, and perform one or more half-duplex + * transactions reading 'len' bytes. Data to be written is already in + * MT7621_SPI_DATA. + */ + tx_len = rs->pending_write; + rs->pending_write = 0; + + while (rx_len || tx_len) { + int i; + u32 val = (min(tx_len, 4) * 8) << 24; + int rx = min(rx_len, 32); + + if (tx_len > 4) + val |= (tx_len - 4) * 8; + val |= (rx * 8) << 12; + mt7621_spi_write(rs, MT7621_SPI_MOREBUF, val); + + tx_len = 0; + + val = mt7621_spi_read(rs, MT7621_SPI_TRANS); + val |= SPI_CTL_START; + mt7621_spi_write(rs, MT7621_SPI_TRANS, val); + + mt7621_spi_wait_till_ready(rs); + + for (i = 0; i < rx; i++) { + if ((i % 4) == 0) + val = mt7621_spi_read(rs, MT7621_SPI_DATA0 + i); + *buf++ = val & 0xff; + val >>= 8; + } + + rx_len -= i; + } +} + +static inline void mt7621_spi_flush(struct mt7621_spi *rs) +{ + mt7621_spi_read_half_duplex(rs, 0, NULL); +} + +static void mt7621_spi_write_half_duplex(struct mt7621_spi *rs, + int tx_len, const u8 *buf) +{ + int len = rs->pending_write; + int val = 0; + + if (len & 3) { + val = mt7621_spi_read(rs, MT7621_SPI_OPCODE + (len & ~3)); + if (len < 4) { + val <<= (4 - len) * 8; + val = swab32(val); + } + } + + while (tx_len > 0) { + if (len >= 36) { + rs->pending_write = len; + mt7621_spi_flush(rs); + len = 0; + } + + val |= *buf++ << (8 * (len & 3)); + len++; + if ((len & 3) == 0) { + if (len == 4) + /* The byte-order of the opcode is weird! */ + val = swab32(val); + mt7621_spi_write(rs, MT7621_SPI_OPCODE + len - 4, val); + val = 0; + } + tx_len -= 1; + } + + if (len & 3) { + if (len < 4) { + val = swab32(val); + val >>= (4 - len) * 8; + } + mt7621_spi_write(rs, MT7621_SPI_OPCODE + (len & ~3), val); + } + + rs->pending_write = len; +} + +static int mt7621_spi_transfer_one_message(struct spi_controller *master, + struct spi_message *m) +{ + struct mt7621_spi *rs = spi_controller_get_devdata(master); + struct spi_device *spi = m->spi; + unsigned int speed = spi->max_speed_hz; + struct spi_transfer *t = NULL; + int status = 0; + + mt7621_spi_wait_till_ready(rs); + + list_for_each_entry(t, &m->transfers, transfer_list) + if (t->speed_hz < speed) + speed = t->speed_hz; + + if (mt7621_spi_prepare(spi, speed)) { + status = -EIO; + goto msg_done; + } + + /* Assert CS */ + mt7621_spi_set_cs(spi, 1); + + m->actual_length = 0; + list_for_each_entry(t, &m->transfers, transfer_list) { + if ((t->rx_buf) && (t->tx_buf)) { + /* + * This controller will shift some extra data out + * of spi_opcode if (mosi_bit_cnt > 0) && + * (cmd_bit_cnt == 0). So the claimed full-duplex + * support is broken since we have no way to read + * the MISO value during that bit. + */ + status = -EIO; + goto msg_done; + } else if (t->rx_buf) { + mt7621_spi_read_half_duplex(rs, t->len, t->rx_buf); + } else if (t->tx_buf) { + mt7621_spi_write_half_duplex(rs, t->len, t->tx_buf); + } + m->actual_length += t->len; + } + + /* Flush data and deassert CS */ + mt7621_spi_flush(rs); + mt7621_spi_set_cs(spi, 0); + +msg_done: + m->status = status; + spi_finalize_current_message(master); + + return 0; +} + +static int mt7621_spi_setup(struct spi_device *spi) +{ + struct mt7621_spi *rs = spidev_to_mt7621_spi(spi); + + if ((spi->max_speed_hz == 0) || + (spi->max_speed_hz > (rs->sys_freq / 2))) + spi->max_speed_hz = (rs->sys_freq / 2); + + if (spi->max_speed_hz < (rs->sys_freq / 4097)) { + dev_err(&spi->dev, "setup: requested speed is too low %d Hz\n", + spi->max_speed_hz); + return -EINVAL; + } + + return 0; +} + +static const struct of_device_id mt7621_spi_match[] = { + { .compatible = "ralink,mt7621-spi" }, + {}, +}; +MODULE_DEVICE_TABLE(of, mt7621_spi_match); + +static int mt7621_spi_probe(struct platform_device *pdev) +{ + const struct of_device_id *match; + struct spi_controller *master; + struct mt7621_spi *rs; + void __iomem *base; + struct resource *r; + int status = 0; + struct clk *clk; + struct mt7621_spi_ops *ops; + int ret; + + match = of_match_device(mt7621_spi_match, &pdev->dev); + if (!match) + return -EINVAL; + ops = (struct mt7621_spi_ops *)match->data; + + r = platform_get_resource(pdev, IORESOURCE_MEM, 0); + base = devm_ioremap_resource(&pdev->dev, r); + if (IS_ERR(base)) + return PTR_ERR(base); + + clk = devm_clk_get(&pdev->dev, NULL); + if (IS_ERR(clk)) { + dev_err(&pdev->dev, "unable to get SYS clock, err=%d\n", + status); + return PTR_ERR(clk); + } + + status = clk_prepare_enable(clk); + if (status) + return status; + + master = spi_alloc_master(&pdev->dev, sizeof(*rs)); + if (!master) { + dev_info(&pdev->dev, "master allocation failed\n"); + return -ENOMEM; + } + + master->mode_bits = SPI_LSB_FIRST; + master->flags = SPI_CONTROLLER_HALF_DUPLEX; + master->setup = mt7621_spi_setup; + master->transfer_one_message = mt7621_spi_transfer_one_message; + master->bits_per_word_mask = SPI_BPW_MASK(8); + master->dev.of_node = pdev->dev.of_node; + master->num_chipselect = 2; + + dev_set_drvdata(&pdev->dev, master); + + rs = spi_controller_get_devdata(master); + rs->base = base; + rs->clk = clk; + rs->master = master; + rs->sys_freq = clk_get_rate(rs->clk); + rs->ops = ops; + rs->pending_write = 0; + dev_info(&pdev->dev, "sys_freq: %u\n", rs->sys_freq); + + ret = device_reset(&pdev->dev); + if (ret) { + dev_err(&pdev->dev, "SPI reset failed!\n"); + return ret; + } + + return devm_spi_register_controller(&pdev->dev, master); +} + +static int mt7621_spi_remove(struct platform_device *pdev) +{ + struct spi_controller *master; + struct mt7621_spi *rs; + + master = dev_get_drvdata(&pdev->dev); + rs = spi_controller_get_devdata(master); + + clk_disable_unprepare(rs->clk); + + return 0; +} + +MODULE_ALIAS("platform:" DRIVER_NAME); + +static struct platform_driver mt7621_spi_driver = { + .driver = { + .name = DRIVER_NAME, + .of_match_table = mt7621_spi_match, + }, + .probe = mt7621_spi_probe, + .remove = mt7621_spi_remove, +}; + +module_platform_driver(mt7621_spi_driver); + +MODULE_DESCRIPTION("MT7621 SPI driver"); +MODULE_AUTHOR("Felix Fietkau "); +MODULE_LICENSE("GPL"); diff --git a/drivers/staging/Kconfig b/drivers/staging/Kconfig index c0901b96cfe4..3241bd50d139 100644 --- a/drivers/staging/Kconfig +++ b/drivers/staging/Kconfig @@ -106,8 +106,6 @@ source "drivers/staging/mt7621-pci-phy/Kconfig" source "drivers/staging/mt7621-pinctrl/Kconfig" -source "drivers/staging/mt7621-spi/Kconfig" - source "drivers/staging/mt7621-dma/Kconfig" source "drivers/staging/ralink-gdma/Kconfig" diff --git a/drivers/staging/Makefile b/drivers/staging/Makefile index 57c6bce13ff4..296ff11ecfae 100644 --- a/drivers/staging/Makefile +++ b/drivers/staging/Makefile @@ -43,7 +43,6 @@ obj-$(CONFIG_PI433) += pi433/ obj-$(CONFIG_PCI_MT7621) += mt7621-pci/ obj-$(CONFIG_PCI_MT7621_PHY) += mt7621-pci-phy/ obj-$(CONFIG_PINCTRL_RT2880) += mt7621-pinctrl/ -obj-$(CONFIG_SPI_MT7621) += mt7621-spi/ obj-$(CONFIG_SOC_MT7621) += mt7621-dma/ obj-$(CONFIG_DMA_RALINK) += ralink-gdma/ obj-$(CONFIG_MTK_MMC) += mt7621-mmc/ diff --git a/drivers/staging/mt7621-spi/Kconfig b/drivers/staging/mt7621-spi/Kconfig deleted file mode 100644 index 0b90f4cfa426..000000000000 --- a/drivers/staging/mt7621-spi/Kconfig +++ /dev/null @@ -1,6 +0,0 @@ -config SPI_MT7621 - tristate "MediaTek MT7621 SPI Controller" - depends on RALINK - help - This selects a driver for the MediaTek MT7621 SPI Controller. - diff --git a/drivers/staging/mt7621-spi/Makefile b/drivers/staging/mt7621-spi/Makefile deleted file mode 100644 index 3be508f63bac..000000000000 --- a/drivers/staging/mt7621-spi/Makefile +++ /dev/null @@ -1 +0,0 @@ -obj-$(CONFIG_SPI_MT7621) += spi-mt7621.o diff --git a/drivers/staging/mt7621-spi/TODO b/drivers/staging/mt7621-spi/TODO deleted file mode 100644 index fdbc5002c32a..000000000000 --- a/drivers/staging/mt7621-spi/TODO +++ /dev/null @@ -1,5 +0,0 @@ - -- general code review and clean up -- ensure device-tree requirements are documented - -Cc: NeilBrown diff --git a/drivers/staging/mt7621-spi/spi-mt7621.c b/drivers/staging/mt7621-spi/spi-mt7621.c deleted file mode 100644 index b509f9fe3346..000000000000 --- a/drivers/staging/mt7621-spi/spi-mt7621.c +++ /dev/null @@ -1,422 +0,0 @@ -// SPDX-License-Identifier: GPL-2.0 -/* - * spi-mt7621.c -- MediaTek MT7621 SPI controller driver - * - * Copyright (C) 2011 Sergiy - * Copyright (C) 2011-2013 Gabor Juhos - * Copyright (C) 2014-2015 Felix Fietkau - * - * Some parts are based on spi-orion.c: - * Author: Shadi Ammouri - * Copyright (C) 2007-2008 Marvell Ltd. - */ - -#include -#include -#include -#include -#include -#include -#include - -#define DRIVER_NAME "spi-mt7621" - -/* in usec */ -#define RALINK_SPI_WAIT_MAX_LOOP 2000 - -/* SPISTAT register bit field */ -#define SPISTAT_BUSY BIT(0) - -#define MT7621_SPI_TRANS 0x00 -#define SPITRANS_BUSY BIT(16) - -#define MT7621_SPI_OPCODE 0x04 -#define MT7621_SPI_DATA0 0x08 -#define MT7621_SPI_DATA4 0x18 -#define SPI_CTL_TX_RX_CNT_MASK 0xff -#define SPI_CTL_START BIT(8) - -#define MT7621_SPI_MASTER 0x28 -#define MASTER_MORE_BUFMODE BIT(2) -#define MASTER_FULL_DUPLEX BIT(10) -#define MASTER_RS_CLK_SEL GENMASK(27, 16) -#define MASTER_RS_CLK_SEL_SHIFT 16 -#define MASTER_RS_SLAVE_SEL GENMASK(31, 29) - -#define MT7621_SPI_MOREBUF 0x2c -#define MT7621_SPI_POLAR 0x38 -#define MT7621_SPI_SPACE 0x3c - -#define MT7621_CPHA BIT(5) -#define MT7621_CPOL BIT(4) -#define MT7621_LSB_FIRST BIT(3) - -struct mt7621_spi { - struct spi_master *master; - void __iomem *base; - unsigned int sys_freq; - unsigned int speed; - struct clk *clk; - int pending_write; - - struct mt7621_spi_ops *ops; -}; - -static inline struct mt7621_spi *spidev_to_mt7621_spi(struct spi_device *spi) -{ - return spi_master_get_devdata(spi->master); -} - -static inline u32 mt7621_spi_read(struct mt7621_spi *rs, u32 reg) -{ - return ioread32(rs->base + reg); -} - -static inline void mt7621_spi_write(struct mt7621_spi *rs, u32 reg, u32 val) -{ - iowrite32(val, rs->base + reg); -} - -static void mt7621_spi_reset(struct mt7621_spi *rs) -{ - u32 master = mt7621_spi_read(rs, MT7621_SPI_MASTER); - - /* - * Select SPI device 7, enable "more buffer mode" and disable - * full-duplex (only half-duplex really works on this chip - * reliably) - */ - master |= MASTER_RS_SLAVE_SEL | MASTER_MORE_BUFMODE; - master &= ~MASTER_FULL_DUPLEX; - - mt7621_spi_write(rs, MT7621_SPI_MASTER, master); - rs->pending_write = 0; -} - -static void mt7621_spi_set_cs(struct spi_device *spi, int enable) -{ - struct mt7621_spi *rs = spidev_to_mt7621_spi(spi); - int cs = spi->chip_select; - u32 polar = 0; - - mt7621_spi_reset(rs); - if (enable) - polar = BIT(cs); - mt7621_spi_write(rs, MT7621_SPI_POLAR, polar); -} - -static int mt7621_spi_prepare(struct spi_device *spi, unsigned int speed) -{ - struct mt7621_spi *rs = spidev_to_mt7621_spi(spi); - u32 rate; - u32 reg; - - dev_dbg(&spi->dev, "speed:%u\n", speed); - - rate = DIV_ROUND_UP(rs->sys_freq, speed); - dev_dbg(&spi->dev, "rate-1:%u\n", rate); - - if (rate > 4097) - return -EINVAL; - - if (rate < 2) - rate = 2; - - reg = mt7621_spi_read(rs, MT7621_SPI_MASTER); - reg &= ~MASTER_RS_CLK_SEL; - reg |= (rate - 2) << MASTER_RS_CLK_SEL_SHIFT; - rs->speed = speed; - - reg &= ~MT7621_LSB_FIRST; - if (spi->mode & SPI_LSB_FIRST) - reg |= MT7621_LSB_FIRST; - - /* - * This SPI controller seems to be tested on SPI flash only and some - * bits are swizzled under other SPI modes probably due to incorrect - * wiring inside the silicon. Only mode 0 works correctly. - */ - reg &= ~(MT7621_CPHA | MT7621_CPOL); - - mt7621_spi_write(rs, MT7621_SPI_MASTER, reg); - - return 0; -} - -static inline int mt7621_spi_wait_till_ready(struct mt7621_spi *rs) -{ - int i; - - for (i = 0; i < RALINK_SPI_WAIT_MAX_LOOP; i++) { - u32 status; - - status = mt7621_spi_read(rs, MT7621_SPI_TRANS); - if ((status & SPITRANS_BUSY) == 0) - return 0; - cpu_relax(); - udelay(1); - } - - return -ETIMEDOUT; -} - -static void mt7621_spi_read_half_duplex(struct mt7621_spi *rs, - int rx_len, u8 *buf) -{ - /* - * Combine with any pending write, and perform one or more half-duplex - * transactions reading 'len' bytes. Data to be written is already in - * MT7621_SPI_DATA. - */ - int tx_len = rs->pending_write; - - rs->pending_write = 0; - - while (rx_len || tx_len) { - int i; - u32 val = (min(tx_len, 4) * 8) << 24; - int rx = min(rx_len, 32); - - if (tx_len > 4) - val |= (tx_len - 4) * 8; - val |= (rx * 8) << 12; - mt7621_spi_write(rs, MT7621_SPI_MOREBUF, val); - - tx_len = 0; - - val = mt7621_spi_read(rs, MT7621_SPI_TRANS); - val |= SPI_CTL_START; - mt7621_spi_write(rs, MT7621_SPI_TRANS, val); - - mt7621_spi_wait_till_ready(rs); - - for (i = 0; i < rx; i++) { - if ((i % 4) == 0) - val = mt7621_spi_read(rs, MT7621_SPI_DATA0 + i); - *buf++ = val & 0xff; - val >>= 8; - } - - rx_len -= i; - } -} - -static inline void mt7621_spi_flush(struct mt7621_spi *rs) -{ - mt7621_spi_read_half_duplex(rs, 0, NULL); -} - -static void mt7621_spi_write_half_duplex(struct mt7621_spi *rs, - int tx_len, const u8 *buf) -{ - int val = 0; - int len = rs->pending_write; - - if (len & 3) { - val = mt7621_spi_read(rs, MT7621_SPI_OPCODE + (len & ~3)); - if (len < 4) { - val <<= (4 - len) * 8; - val = swab32(val); - } - } - - while (tx_len > 0) { - if (len >= 36) { - rs->pending_write = len; - mt7621_spi_flush(rs); - len = 0; - } - - val |= *buf++ << (8 * (len & 3)); - len++; - if ((len & 3) == 0) { - if (len == 4) - /* The byte-order of the opcode is weird! */ - val = swab32(val); - mt7621_spi_write(rs, MT7621_SPI_OPCODE + len - 4, val); - val = 0; - } - tx_len -= 1; - } - if (len & 3) { - if (len < 4) { - val = swab32(val); - val >>= (4 - len) * 8; - } - mt7621_spi_write(rs, MT7621_SPI_OPCODE + (len & ~3), val); - } - rs->pending_write = len; -} - -static int mt7621_spi_transfer_one_message(struct spi_master *master, - struct spi_message *m) -{ - struct mt7621_spi *rs = spi_master_get_devdata(master); - struct spi_device *spi = m->spi; - unsigned int speed = spi->max_speed_hz; - struct spi_transfer *t = NULL; - int status = 0; - - mt7621_spi_wait_till_ready(rs); - - list_for_each_entry(t, &m->transfers, transfer_list) - if (t->speed_hz < speed) - speed = t->speed_hz; - - if (mt7621_spi_prepare(spi, speed)) { - status = -EIO; - goto msg_done; - } - - mt7621_spi_set_cs(spi, 1); - m->actual_length = 0; - list_for_each_entry(t, &m->transfers, transfer_list) { - if ((t->rx_buf) && (t->tx_buf)) { - /* This controller will shift some extra data out - * of spi_opcode if (mosi_bit_cnt > 0) && - * (cmd_bit_cnt == 0). So the claimed full-duplex - * support is broken since we have no way to read - * the MISO value during that bit. - */ - status = -EIO; - goto msg_done; - } else if (t->rx_buf) { - mt7621_spi_read_half_duplex(rs, t->len, t->rx_buf); - } else if (t->tx_buf) { - mt7621_spi_write_half_duplex(rs, t->len, t->tx_buf); - } - m->actual_length += t->len; - } - mt7621_spi_flush(rs); - - mt7621_spi_set_cs(spi, 0); - -msg_done: - m->status = status; - spi_finalize_current_message(master); - - return 0; -} - -static int mt7621_spi_setup(struct spi_device *spi) -{ - struct mt7621_spi *rs = spidev_to_mt7621_spi(spi); - - if ((spi->max_speed_hz == 0) || - (spi->max_speed_hz > (rs->sys_freq / 2))) - spi->max_speed_hz = (rs->sys_freq / 2); - - if (spi->max_speed_hz < (rs->sys_freq / 4097)) { - dev_err(&spi->dev, "setup: requested speed is too low %d Hz\n", - spi->max_speed_hz); - return -EINVAL; - } - - return 0; -} - -static const struct of_device_id mt7621_spi_match[] = { - { .compatible = "ralink,mt7621-spi" }, - {}, -}; -MODULE_DEVICE_TABLE(of, mt7621_spi_match); - -static int mt7621_spi_probe(struct platform_device *pdev) -{ - const struct of_device_id *match; - struct spi_master *master; - struct mt7621_spi *rs; - void __iomem *base; - struct resource *r; - int status = 0; - struct clk *clk; - struct mt7621_spi_ops *ops; - int ret; - - match = of_match_device(mt7621_spi_match, &pdev->dev); - if (!match) - return -EINVAL; - ops = (struct mt7621_spi_ops *)match->data; - - r = platform_get_resource(pdev, IORESOURCE_MEM, 0); - base = devm_ioremap_resource(&pdev->dev, r); - if (IS_ERR(base)) - return PTR_ERR(base); - - clk = devm_clk_get(&pdev->dev, NULL); - if (IS_ERR(clk)) { - dev_err(&pdev->dev, "unable to get SYS clock, err=%d\n", - status); - return PTR_ERR(clk); - } - - status = clk_prepare_enable(clk); - if (status) - return status; - - master = spi_alloc_master(&pdev->dev, sizeof(*rs)); - if (!master) { - dev_info(&pdev->dev, "master allocation failed\n"); - return -ENOMEM; - } - - master->mode_bits = SPI_LSB_FIRST; - - master->setup = mt7621_spi_setup; - master->transfer_one_message = mt7621_spi_transfer_one_message; - master->bits_per_word_mask = SPI_BPW_MASK(8); - master->dev.of_node = pdev->dev.of_node; - master->num_chipselect = 2; - - dev_set_drvdata(&pdev->dev, master); - - rs = spi_master_get_devdata(master); - rs->base = base; - rs->clk = clk; - rs->master = master; - rs->sys_freq = clk_get_rate(rs->clk); - rs->ops = ops; - rs->pending_write = 0; - dev_info(&pdev->dev, "sys_freq: %u\n", rs->sys_freq); - - ret = device_reset(&pdev->dev); - if (ret) { - dev_err(&pdev->dev, "SPI reset failed!\n"); - return ret; - } - - mt7621_spi_reset(rs); - - return spi_register_master(master); -} - -static int mt7621_spi_remove(struct platform_device *pdev) -{ - struct spi_master *master; - struct mt7621_spi *rs; - - master = dev_get_drvdata(&pdev->dev); - rs = spi_master_get_devdata(master); - - clk_disable(rs->clk); - spi_unregister_master(master); - - return 0; -} - -MODULE_ALIAS("platform:" DRIVER_NAME); - -static struct platform_driver mt7621_spi_driver = { - .driver = { - .name = DRIVER_NAME, - .of_match_table = mt7621_spi_match, - }, - .probe = mt7621_spi_probe, - .remove = mt7621_spi_remove, -}; - -module_platform_driver(mt7621_spi_driver); - -MODULE_DESCRIPTION("MT7621 SPI driver"); -MODULE_AUTHOR("Felix Fietkau "); -MODULE_LICENSE("GPL"); -- cgit v1.2.3 From 4e92348dc0030b09b33c76ef15341e8ea383dddd Mon Sep 17 00:00:00 2001 From: Douglas Anderson Date: Fri, 22 Mar 2019 12:59:23 -0700 Subject: dt-bindings: ARM: dts: rockchip: Add rk3288-veyron-jerry rev 10-15 As far as I can tell/remember rev10 was originally created to support making a SKU of jerry that had a different LCD. rev11-rev15 were added to give some wiggle room for future builds. Downstream has a separate device tree for rev10-rev15 (compared to rev3-rev7) with the expectation that differences relating to the LCD would be accounted for there but nothing was ever added to the rev10-rev15 making it identical to the rev3-rev7 one. It's likely nothing actually shipped with rev10-rev15 but they are listed in the downstream kernel's device tree and it seems like it should add a little safety if we match them here just in case something actually shipped with one of these revisions and that device will break if we don't claim support. Signed-off-by: Douglas Anderson Reviewed-by: Rob Herring Signed-off-by: Heiko Stuebner --- Documentation/devicetree/bindings/arm/rockchip.yaml | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/rockchip.yaml b/Documentation/devicetree/bindings/arm/rockchip.yaml index 061a03edf9c8..81bc2a4138f2 100644 --- a/Documentation/devicetree/bindings/arm/rockchip.yaml +++ b/Documentation/devicetree/bindings/arm/rockchip.yaml @@ -159,6 +159,12 @@ properties: - description: Google Jerry (Hisense Chromebook C11 and more) items: + - const: google,veyron-jerry-rev15 + - const: google,veyron-jerry-rev14 + - const: google,veyron-jerry-rev13 + - const: google,veyron-jerry-rev12 + - const: google,veyron-jerry-rev11 + - const: google,veyron-jerry-rev10 - const: google,veyron-jerry-rev7 - const: google,veyron-jerry-rev6 - const: google,veyron-jerry-rev5 -- cgit v1.2.3 From 529766e0a0114438887382a68d97341fbf8349fb Mon Sep 17 00:00:00 2001 From: Elie Morisse Date: Tue, 5 Mar 2019 12:13:19 -0300 Subject: i2c: Add drivers for the AMD PCIe MP2 I2C controller MP2 controllers have two separate busses, so may accommodate up to two I2C adapters. Those adapters are listed in the ACPI namespace with the "AMDI0011" HID, and probed by a platform driver. Communication with the MP2 takes place through MMIO registers, or through DMA for more than 32 bytes transfers. This is major rework of the patch submitted by Nehal-bakulchandra Shah from AMD (https://patchwork.kernel.org/patch/10597369/). Most of the event handling of v3 was rewritten to make it work with more than one bus (e.g on Ryzen-based Lenovo Yoga 530), and this version contains many other improvements. Signed-off-by: Elie Morisse Signed-off-by: Wolfram Sang --- Documentation/i2c/busses/i2c-amd-mp2 | 23 ++ MAINTAINERS | 8 + drivers/i2c/busses/Kconfig | 10 + drivers/i2c/busses/Makefile | 1 + drivers/i2c/busses/i2c-amd-mp2-pci.c | 483 ++++++++++++++++++++++++++++++++++ drivers/i2c/busses/i2c-amd-mp2-plat.c | 367 ++++++++++++++++++++++++++ drivers/i2c/busses/i2c-amd-mp2.h | 219 +++++++++++++++ 7 files changed, 1111 insertions(+) create mode 100644 Documentation/i2c/busses/i2c-amd-mp2 create mode 100644 drivers/i2c/busses/i2c-amd-mp2-pci.c create mode 100644 drivers/i2c/busses/i2c-amd-mp2-plat.c create mode 100644 drivers/i2c/busses/i2c-amd-mp2.h (limited to 'Documentation') diff --git a/Documentation/i2c/busses/i2c-amd-mp2 b/Documentation/i2c/busses/i2c-amd-mp2 new file mode 100644 index 000000000000..6571487171f4 --- /dev/null +++ b/Documentation/i2c/busses/i2c-amd-mp2 @@ -0,0 +1,23 @@ +Kernel driver i2c-amd-mp2 + +Supported adapters: + * AMD MP2 PCIe interface + +Datasheet: not publicly available. + +Authors: + Shyam Sundar S K + Nehal Shah + Elie Morisse + +Description +----------- + +The MP2 is an ARM processor programmed as an I2C controller and communicating +with the x86 host through PCI. + +If you see something like this: + +03:00.7 MP2 I2C controller: Advanced Micro Devices, Inc. [AMD] Device 15e6 + +in your 'lspci -v', then this driver is for your device. diff --git a/MAINTAINERS b/MAINTAINERS index a766c8f13b22..e0ce75162e60 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -816,6 +816,14 @@ F: drivers/gpu/drm/amd/include/vi_structs.h F: drivers/gpu/drm/amd/include/v9_structs.h F: include/uapi/linux/kfd_ioctl.h +AMD MP2 I2C DRIVER +M: Elie Morisse +M: Nehal Shah +M: Shyam Sundar S K +L: linux-i2c@vger.kernel.org +S: Maintained +F: drivers/i2c/busses/i2c-amd-mp2* + AMD POWERPLAY M: Rex Zhu M: Evan Quan diff --git a/drivers/i2c/busses/Kconfig b/drivers/i2c/busses/Kconfig index 6b1f6dcdf533..2a978ec91b91 100644 --- a/drivers/i2c/busses/Kconfig +++ b/drivers/i2c/busses/Kconfig @@ -77,6 +77,16 @@ config I2C_AMD8111 This driver can also be built as a module. If so, the module will be called i2c-amd8111. +config I2C_AMD_MP2 + tristate "AMD MP2 PCIe" + depends on PCI && ACPI + help + If you say yes to this option, support will be included for the AMD + MP2 PCIe I2C adapter. + + This driver can also be built as modules. If so, the modules will + be called i2c-amd-mp2-pci and i2c-amd-mp2-plat. + config I2C_HIX5HD2 tristate "Hix5hd2 high-speed I2C driver" depends on ARCH_HISI || ARCH_HIX5HD2 || COMPILE_TEST diff --git a/drivers/i2c/busses/Makefile b/drivers/i2c/busses/Makefile index 59b22fbef90a..a3245231b0b7 100644 --- a/drivers/i2c/busses/Makefile +++ b/drivers/i2c/busses/Makefile @@ -33,6 +33,7 @@ obj-$(CONFIG_I2C_POWERMAC) += i2c-powermac.o # Embedded system I2C/SMBus host controller drivers obj-$(CONFIG_I2C_ALTERA) += i2c-altera.o +obj-$(CONFIG_I2C_AMD_MP2) += i2c-amd-mp2-pci.o i2c-amd-mp2-plat.o obj-$(CONFIG_I2C_ASPEED) += i2c-aspeed.o obj-$(CONFIG_I2C_AT91) += i2c-at91.o i2c-at91-objs := i2c-at91-core.o i2c-at91-master.o diff --git a/drivers/i2c/busses/i2c-amd-mp2-pci.c b/drivers/i2c/busses/i2c-amd-mp2-pci.c new file mode 100644 index 000000000000..455e1f36a2a3 --- /dev/null +++ b/drivers/i2c/busses/i2c-amd-mp2-pci.c @@ -0,0 +1,483 @@ +// SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause +/* + * AMD MP2 PCIe communication driver + * + * Authors: Shyam Sundar S K + * Elie Morisse + */ + +#include +#include +#include +#include +#include + +#include "i2c-amd-mp2.h" + +#include + +static void amd_mp2_c2p_mutex_lock(struct amd_i2c_common *i2c_common) +{ + struct amd_mp2_dev *privdata = i2c_common->mp2_dev; + + /* there is only one data mailbox for two i2c adapters */ + mutex_lock(&privdata->c2p_lock); + privdata->c2p_lock_busid = i2c_common->bus_id; +} + +static void amd_mp2_c2p_mutex_unlock(struct amd_i2c_common *i2c_common) +{ + struct amd_mp2_dev *privdata = i2c_common->mp2_dev; + + if (unlikely(privdata->c2p_lock_busid != i2c_common->bus_id)) { + dev_warn(ndev_dev(privdata), + "bus %d attempting to unlock C2P locked by bus %d\n", + i2c_common->bus_id, privdata->c2p_lock_busid); + return; + } + + mutex_unlock(&privdata->c2p_lock); +} + +static int amd_mp2_cmd(struct amd_i2c_common *i2c_common, + union i2c_cmd_base i2c_cmd_base) +{ + struct amd_mp2_dev *privdata = i2c_common->mp2_dev; + void __iomem *reg; + + i2c_common->reqcmd = i2c_cmd_base.s.i2c_cmd; + + reg = privdata->mmio + ((i2c_cmd_base.s.bus_id == 1) ? + AMD_C2P_MSG1 : AMD_C2P_MSG0); + writel(i2c_cmd_base.ul, reg); + + return 0; +} + +int amd_mp2_bus_enable_set(struct amd_i2c_common *i2c_common, bool enable) +{ + struct amd_mp2_dev *privdata = i2c_common->mp2_dev; + union i2c_cmd_base i2c_cmd_base; + + dev_dbg(ndev_dev(privdata), "%s id: %d\n", __func__, + i2c_common->bus_id); + + i2c_cmd_base.ul = 0; + i2c_cmd_base.s.i2c_cmd = enable ? i2c_enable : i2c_disable; + i2c_cmd_base.s.bus_id = i2c_common->bus_id; + i2c_cmd_base.s.i2c_speed = i2c_common->i2c_speed; + + amd_mp2_c2p_mutex_lock(i2c_common); + + return amd_mp2_cmd(i2c_common, i2c_cmd_base); +} +EXPORT_SYMBOL_GPL(amd_mp2_bus_enable_set); + +static void amd_mp2_cmd_rw_fill(struct amd_i2c_common *i2c_common, + union i2c_cmd_base *i2c_cmd_base, + enum i2c_cmd reqcmd) +{ + i2c_cmd_base->s.i2c_cmd = reqcmd; + i2c_cmd_base->s.bus_id = i2c_common->bus_id; + i2c_cmd_base->s.i2c_speed = i2c_common->i2c_speed; + i2c_cmd_base->s.slave_addr = i2c_common->msg->addr; + i2c_cmd_base->s.length = i2c_common->msg->len; +} + +int amd_mp2_rw(struct amd_i2c_common *i2c_common, enum i2c_cmd reqcmd) +{ + struct amd_mp2_dev *privdata = i2c_common->mp2_dev; + union i2c_cmd_base i2c_cmd_base; + + amd_mp2_cmd_rw_fill(i2c_common, &i2c_cmd_base, reqcmd); + amd_mp2_c2p_mutex_lock(i2c_common); + + if (i2c_common->msg->len <= 32) { + i2c_cmd_base.s.mem_type = use_c2pmsg; + if (reqcmd == i2c_write) + memcpy_toio(privdata->mmio + AMD_C2P_MSG2, + i2c_common->msg->buf, + i2c_common->msg->len); + } else { + i2c_cmd_base.s.mem_type = use_dram; + writeq((u64)i2c_common->dma_addr, + privdata->mmio + AMD_C2P_MSG2); + } + + return amd_mp2_cmd(i2c_common, i2c_cmd_base); +} +EXPORT_SYMBOL_GPL(amd_mp2_rw); + +static void amd_mp2_pci_check_rw_event(struct amd_i2c_common *i2c_common) +{ + struct amd_mp2_dev *privdata = i2c_common->mp2_dev; + int len = i2c_common->eventval.r.length; + u32 slave_addr = i2c_common->eventval.r.slave_addr; + bool err = false; + + if (unlikely(len != i2c_common->msg->len)) { + dev_err(ndev_dev(privdata), + "length %d in event doesn't match buffer length %d!\n", + len, i2c_common->msg->len); + err = true; + } + + if (unlikely(slave_addr != i2c_common->msg->addr)) { + dev_err(ndev_dev(privdata), + "unexpected slave address %x (expected: %x)!\n", + slave_addr, i2c_common->msg->addr); + err = true; + } + + if (!err) + i2c_common->cmd_success = true; +} + +static void __amd_mp2_process_event(struct amd_i2c_common *i2c_common) +{ + struct amd_mp2_dev *privdata = i2c_common->mp2_dev; + enum status_type sts = i2c_common->eventval.r.status; + enum response_type res = i2c_common->eventval.r.response; + int len = i2c_common->eventval.r.length; + + if (res != command_success) { + if (res != command_failed) + dev_err(ndev_dev(privdata), "invalid response to i2c command!\n"); + return; + } + + switch (i2c_common->reqcmd) { + case i2c_read: + if (sts == i2c_readcomplete_event) { + amd_mp2_pci_check_rw_event(i2c_common); + if (len <= 32) + memcpy_fromio(i2c_common->msg->buf, + privdata->mmio + AMD_C2P_MSG2, + len); + } else if (sts != i2c_readfail_event) { + dev_err(ndev_dev(privdata), + "invalid i2c status after read (%d)!\n", sts); + } + break; + case i2c_write: + if (sts == i2c_writecomplete_event) + amd_mp2_pci_check_rw_event(i2c_common); + else if (sts != i2c_writefail_event) + dev_err(ndev_dev(privdata), + "invalid i2c status after write (%d)!\n", sts); + break; + case i2c_enable: + if (sts == i2c_busenable_complete) + i2c_common->cmd_success = true; + else if (sts != i2c_busenable_failed) + dev_err(ndev_dev(privdata), + "invalid i2c status after bus enable (%d)!\n", + sts); + break; + case i2c_disable: + if (sts == i2c_busdisable_complete) + i2c_common->cmd_success = true; + else if (sts != i2c_busdisable_failed) + dev_err(ndev_dev(privdata), + "invalid i2c status after bus disable (%d)!\n", + sts); + break; + default: + break; + } +} + +void amd_mp2_process_event(struct amd_i2c_common *i2c_common) +{ + struct amd_mp2_dev *privdata = i2c_common->mp2_dev; + + if (unlikely(i2c_common->reqcmd == i2c_none)) { + dev_warn(ndev_dev(privdata), + "received msg but no cmd was sent (bus = %d)!\n", + i2c_common->bus_id); + return; + } + + __amd_mp2_process_event(i2c_common); + + i2c_common->reqcmd = i2c_none; + amd_mp2_c2p_mutex_unlock(i2c_common); +} +EXPORT_SYMBOL_GPL(amd_mp2_process_event); + +static irqreturn_t amd_mp2_irq_isr(int irq, void *dev) +{ + struct amd_mp2_dev *privdata = dev; + struct amd_i2c_common *i2c_common; + u32 val; + unsigned int bus_id; + void __iomem *reg; + enum irqreturn ret = IRQ_NONE; + + for (bus_id = 0; bus_id < 2; bus_id++) { + i2c_common = privdata->busses[bus_id]; + if (!i2c_common) + continue; + + reg = privdata->mmio + ((bus_id == 0) ? + AMD_P2C_MSG1 : AMD_P2C_MSG2); + val = readl(reg); + if (val != 0) { + writel(0, reg); + writel(0, privdata->mmio + AMD_P2C_MSG_INTEN); + i2c_common->eventval.ul = val; + i2c_common->cmd_completion(i2c_common); + + ret = IRQ_HANDLED; + } + } + + if (ret != IRQ_HANDLED) { + val = readl(privdata->mmio + AMD_P2C_MSG_INTEN); + if (val != 0) { + writel(0, privdata->mmio + AMD_P2C_MSG_INTEN); + dev_warn(ndev_dev(privdata), + "received irq without message\n"); + ret = IRQ_HANDLED; + } + } + + return ret; +} + +void amd_mp2_rw_timeout(struct amd_i2c_common *i2c_common) +{ + i2c_common->reqcmd = i2c_none; + amd_mp2_c2p_mutex_unlock(i2c_common); +} +EXPORT_SYMBOL_GPL(amd_mp2_rw_timeout); + +int amd_mp2_register_cb(struct amd_i2c_common *i2c_common) +{ + struct amd_mp2_dev *privdata = i2c_common->mp2_dev; + + if (i2c_common->bus_id > 1) + return -EINVAL; + + if (privdata->busses[i2c_common->bus_id]) { + dev_err(ndev_dev(privdata), + "Bus %d already taken!\n", i2c_common->bus_id); + return -EINVAL; + } + + privdata->busses[i2c_common->bus_id] = i2c_common; + + return 0; +} +EXPORT_SYMBOL_GPL(amd_mp2_register_cb); + +int amd_mp2_unregister_cb(struct amd_i2c_common *i2c_common) +{ + struct amd_mp2_dev *privdata = i2c_common->mp2_dev; + + privdata->busses[i2c_common->bus_id] = NULL; + + return 0; +} +EXPORT_SYMBOL_GPL(amd_mp2_unregister_cb); + +static void amd_mp2_clear_reg(struct amd_mp2_dev *privdata) +{ + int reg; + + for (reg = AMD_C2P_MSG0; reg <= AMD_C2P_MSG9; reg += 4) + writel(0, privdata->mmio + reg); + + for (reg = AMD_P2C_MSG1; reg <= AMD_P2C_MSG2; reg += 4) + writel(0, privdata->mmio + reg); +} + +static int amd_mp2_pci_init(struct amd_mp2_dev *privdata, + struct pci_dev *pci_dev) +{ + int rc; + + pci_set_drvdata(pci_dev, privdata); + + rc = pcim_enable_device(pci_dev); + if (rc) { + dev_err(ndev_dev(privdata), "Failed to enable MP2 PCI device\n"); + goto err_pci_enable; + } + + rc = pcim_iomap_regions(pci_dev, 1 << 2, pci_name(pci_dev)); + if (rc) { + dev_err(ndev_dev(privdata), "I/O memory remapping failed\n"); + goto err_pci_enable; + } + privdata->mmio = pcim_iomap_table(pci_dev)[2]; + + pci_set_master(pci_dev); + + rc = pci_set_dma_mask(pci_dev, DMA_BIT_MASK(64)); + if (rc) { + rc = pci_set_dma_mask(pci_dev, DMA_BIT_MASK(32)); + if (rc) + goto err_dma_mask; + } + + /* Set up intx irq */ + writel(0, privdata->mmio + AMD_P2C_MSG_INTEN); + pci_intx(pci_dev, 1); + rc = devm_request_irq(&pci_dev->dev, pci_dev->irq, amd_mp2_irq_isr, + IRQF_SHARED, dev_name(&pci_dev->dev), privdata); + if (rc) + dev_err(&pci_dev->dev, "Failure requesting irq %i: %d\n", + pci_dev->irq, rc); + + return rc; + +err_dma_mask: + pci_clear_master(pci_dev); +err_pci_enable: + pci_set_drvdata(pci_dev, NULL); + return rc; +} + +static int amd_mp2_pci_probe(struct pci_dev *pci_dev, + const struct pci_device_id *id) +{ + struct amd_mp2_dev *privdata; + int rc; + + privdata = devm_kzalloc(&pci_dev->dev, sizeof(*privdata), GFP_KERNEL); + if (!privdata) + return -ENOMEM; + + rc = amd_mp2_pci_init(privdata, pci_dev); + if (rc) + return rc; + + mutex_init(&privdata->c2p_lock); + privdata->pci_dev = pci_dev; + + pm_runtime_set_autosuspend_delay(&pci_dev->dev, 1000); + pm_runtime_use_autosuspend(&pci_dev->dev); + pm_runtime_put_autosuspend(&pci_dev->dev); + pm_runtime_allow(&pci_dev->dev); + + privdata->probed = true; + + dev_info(&pci_dev->dev, "MP2 device registered.\n"); + return 0; +} + +static void amd_mp2_pci_remove(struct pci_dev *pci_dev) +{ + struct amd_mp2_dev *privdata = pci_get_drvdata(pci_dev); + + pm_runtime_forbid(&pci_dev->dev); + pm_runtime_get_noresume(&pci_dev->dev); + + pci_intx(pci_dev, 0); + pci_clear_master(pci_dev); + + amd_mp2_clear_reg(privdata); +} + +#ifdef CONFIG_PM +static int amd_mp2_pci_suspend(struct device *dev) +{ + struct pci_dev *pci_dev = to_pci_dev(dev); + struct amd_mp2_dev *privdata = pci_get_drvdata(pci_dev); + struct amd_i2c_common *i2c_common; + unsigned int bus_id; + int ret = 0; + + for (bus_id = 0; bus_id < 2; bus_id++) { + i2c_common = privdata->busses[bus_id]; + if (i2c_common) + i2c_common->suspend(i2c_common); + } + + ret = pci_save_state(pci_dev); + if (ret) { + dev_err(ndev_dev(privdata), + "pci_save_state failed = %d\n", ret); + return ret; + } + + pci_disable_device(pci_dev); + return ret; +} + +static int amd_mp2_pci_resume(struct device *dev) +{ + struct pci_dev *pci_dev = to_pci_dev(dev); + struct amd_mp2_dev *privdata = pci_get_drvdata(pci_dev); + struct amd_i2c_common *i2c_common; + unsigned int bus_id; + int ret = 0; + + pci_restore_state(pci_dev); + ret = pci_enable_device(pci_dev); + if (ret < 0) { + dev_err(ndev_dev(privdata), + "pci_enable_device failed = %d\n", ret); + return ret; + } + + for (bus_id = 0; bus_id < 2; bus_id++) { + i2c_common = privdata->busses[bus_id]; + if (i2c_common) { + ret = i2c_common->resume(i2c_common); + if (ret < 0) + return ret; + } + } + + return ret; +} + +static UNIVERSAL_DEV_PM_OPS(amd_mp2_pci_pm_ops, amd_mp2_pci_suspend, + amd_mp2_pci_resume, NULL); +#endif /* CONFIG_PM */ + +static const struct pci_device_id amd_mp2_pci_tbl[] = { + {PCI_VDEVICE(AMD, PCI_DEVICE_ID_AMD_MP2)}, + {0} +}; +MODULE_DEVICE_TABLE(pci, amd_mp2_pci_tbl); + +static struct pci_driver amd_mp2_pci_driver = { + .name = "i2c_amd_mp2", + .id_table = amd_mp2_pci_tbl, + .probe = amd_mp2_pci_probe, + .remove = amd_mp2_pci_remove, +#ifdef CONFIG_PM + .driver = { + .pm = &amd_mp2_pci_pm_ops, + }, +#endif +}; +module_pci_driver(amd_mp2_pci_driver); + +static int amd_mp2_device_match(struct device *dev, void *data) +{ + return 1; +} + +struct amd_mp2_dev *amd_mp2_find_device(void) +{ + struct device *dev; + struct pci_dev *pci_dev; + + dev = driver_find_device(&amd_mp2_pci_driver.driver, NULL, NULL, + amd_mp2_device_match); + if (!dev) + return NULL; + + pci_dev = to_pci_dev(dev); + return (struct amd_mp2_dev *)pci_get_drvdata(pci_dev); +} +EXPORT_SYMBOL_GPL(amd_mp2_find_device); + +MODULE_DESCRIPTION("AMD(R) PCI-E MP2 I2C Controller Driver"); +MODULE_AUTHOR("Shyam Sundar S K "); +MODULE_AUTHOR("Elie Morisse "); +MODULE_LICENSE("Dual BSD/GPL"); diff --git a/drivers/i2c/busses/i2c-amd-mp2-plat.c b/drivers/i2c/busses/i2c-amd-mp2-plat.c new file mode 100644 index 000000000000..f5b3f00c6559 --- /dev/null +++ b/drivers/i2c/busses/i2c-amd-mp2-plat.c @@ -0,0 +1,367 @@ +// SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause +/* + * AMD MP2 platform driver + * + * Setup the I2C adapters enumerated in the ACPI namespace. + * MP2 controllers have 2 separate busses, up to 2 I2C adapters may be listed. + * + * Authors: Nehal Bakulchandra Shah + * Elie Morisse + */ + +#include +#include +#include +#include +#include +#include + +#include "i2c-amd-mp2.h" + +#define AMD_MP2_I2C_MAX_RW_LENGTH ((1 << 12) - 1) +#define AMD_I2C_TIMEOUT (msecs_to_jiffies(250)) + +/** + * struct amd_i2c_dev - MP2 bus/i2c adapter context + * @common: shared context with the MP2 PCI driver + * @pdev: platform driver node + * @adap: i2c adapter + * @cmd_complete: xfer completion object + */ +struct amd_i2c_dev { + struct amd_i2c_common common; + struct platform_device *pdev; + struct i2c_adapter adap; + struct completion cmd_complete; +}; + +#define amd_i2c_dev_common(__common) \ + container_of(__common, struct amd_i2c_dev, common) + +static int i2c_amd_dma_map(struct amd_i2c_common *i2c_common) +{ + struct device *dev_pci = &i2c_common->mp2_dev->pci_dev->dev; + struct amd_i2c_dev *i2c_dev = amd_i2c_dev_common(i2c_common); + enum dma_data_direction dma_direction = + i2c_common->msg->flags & I2C_M_RD ? + DMA_FROM_DEVICE : DMA_TO_DEVICE; + + i2c_common->dma_buf = i2c_get_dma_safe_msg_buf(i2c_common->msg, 0); + i2c_common->dma_addr = dma_map_single(dev_pci, i2c_common->dma_buf, + i2c_common->msg->len, + dma_direction); + + if (unlikely(dma_mapping_error(dev_pci, i2c_common->dma_addr))) { + dev_err(&i2c_dev->pdev->dev, + "Error while mapping dma buffer %p\n", + i2c_common->dma_buf); + return -EIO; + } + + return 0; +} + +static void i2c_amd_dma_unmap(struct amd_i2c_common *i2c_common) +{ + struct device *dev_pci = &i2c_common->mp2_dev->pci_dev->dev; + enum dma_data_direction dma_direction = + i2c_common->msg->flags & I2C_M_RD ? + DMA_FROM_DEVICE : DMA_TO_DEVICE; + + dma_unmap_single(dev_pci, i2c_common->dma_addr, + i2c_common->msg->len, dma_direction); + + i2c_put_dma_safe_msg_buf(i2c_common->dma_buf, i2c_common->msg, true); +} + +static void i2c_amd_start_cmd(struct amd_i2c_dev *i2c_dev) +{ + struct amd_i2c_common *i2c_common = &i2c_dev->common; + + reinit_completion(&i2c_dev->cmd_complete); + i2c_common->cmd_success = false; +} + +static void i2c_amd_cmd_completion(struct amd_i2c_common *i2c_common) +{ + struct amd_i2c_dev *i2c_dev = amd_i2c_dev_common(i2c_common); + union i2c_event *event = &i2c_common->eventval; + + if (event->r.status == i2c_readcomplete_event) + dev_dbg(&i2c_dev->pdev->dev, "%s readdata:%*ph\n", + __func__, event->r.length, + i2c_common->msg->buf); + + complete(&i2c_dev->cmd_complete); +} + +static int i2c_amd_check_cmd_completion(struct amd_i2c_dev *i2c_dev) +{ + struct amd_i2c_common *i2c_common = &i2c_dev->common; + unsigned long timeout; + + timeout = wait_for_completion_timeout(&i2c_dev->cmd_complete, + i2c_dev->adap.timeout); + + if ((i2c_common->reqcmd == i2c_read || + i2c_common->reqcmd == i2c_write) && + i2c_common->msg->len > 32) + i2c_amd_dma_unmap(i2c_common); + + if (timeout == 0) { + amd_mp2_rw_timeout(i2c_common); + return -ETIMEDOUT; + } + + amd_mp2_process_event(i2c_common); + + if (!i2c_common->cmd_success) + return -EIO; + + return 0; +} + +static int i2c_amd_enable_set(struct amd_i2c_dev *i2c_dev, bool enable) +{ + struct amd_i2c_common *i2c_common = &i2c_dev->common; + + i2c_amd_start_cmd(i2c_dev); + amd_mp2_bus_enable_set(i2c_common, enable); + + return i2c_amd_check_cmd_completion(i2c_dev); +} + +static int i2c_amd_xfer_msg(struct amd_i2c_dev *i2c_dev, struct i2c_msg *pmsg) +{ + struct amd_i2c_common *i2c_common = &i2c_dev->common; + + i2c_amd_start_cmd(i2c_dev); + i2c_common->msg = pmsg; + + if (pmsg->len > 32) + if (i2c_amd_dma_map(i2c_common)) + return -EIO; + + if (pmsg->flags & I2C_M_RD) + amd_mp2_rw(i2c_common, i2c_read); + else + amd_mp2_rw(i2c_common, i2c_write); + + return i2c_amd_check_cmd_completion(i2c_dev); +} + +static int i2c_amd_xfer(struct i2c_adapter *adap, struct i2c_msg *msgs, int num) +{ + struct amd_i2c_dev *i2c_dev = i2c_get_adapdata(adap); + int i; + struct i2c_msg *pmsg; + int err; + + /* the adapter might have been deleted while waiting for the bus lock */ + if (unlikely(!i2c_dev->common.mp2_dev)) + return -EINVAL; + + amd_mp2_pm_runtime_get(i2c_dev->common.mp2_dev); + + for (i = 0; i < num; i++) { + pmsg = &msgs[i]; + err = i2c_amd_xfer_msg(i2c_dev, pmsg); + if (err) + break; + } + + amd_mp2_pm_runtime_put(i2c_dev->common.mp2_dev); + return err ? err : num; +} + +static u32 i2c_amd_func(struct i2c_adapter *a) +{ + return I2C_FUNC_I2C | I2C_FUNC_SMBUS_EMUL; +} + +static const struct i2c_algorithm i2c_amd_algorithm = { + .master_xfer = i2c_amd_xfer, + .functionality = i2c_amd_func, +}; + +#ifdef CONFIG_PM +static int i2c_amd_suspend(struct amd_i2c_common *i2c_common) +{ + struct amd_i2c_dev *i2c_dev = amd_i2c_dev_common(i2c_common); + + i2c_amd_enable_set(i2c_dev, false); + return 0; +} + +static int i2c_amd_resume(struct amd_i2c_common *i2c_common) +{ + struct amd_i2c_dev *i2c_dev = amd_i2c_dev_common(i2c_common); + + return i2c_amd_enable_set(i2c_dev, true); +} +#endif + +static enum speed_enum i2c_amd_get_bus_speed(struct platform_device *pdev) +{ + u32 acpi_speed; + int i; + static const u32 supported_speeds[] = { + 0, 100000, 400000, 1000000, 1400000, 3400000 + }; + + acpi_speed = i2c_acpi_find_bus_speed(&pdev->dev); + /* round down to the lowest standard speed */ + for (i = 1; i < ARRAY_SIZE(supported_speeds); i++) { + if (acpi_speed < supported_speeds[i]) + break; + } + acpi_speed = supported_speeds[i - 1]; + + switch (acpi_speed) { + case 100000: + return speed100k; + case 400000: + return speed400k; + case 1000000: + return speed1000k; + case 1400000: + return speed1400k; + case 3400000: + return speed3400k; + default: + return speed400k; + } +} + +static const struct i2c_adapter_quirks amd_i2c_dev_quirks = { + .max_read_len = AMD_MP2_I2C_MAX_RW_LENGTH, + .max_write_len = AMD_MP2_I2C_MAX_RW_LENGTH, +}; + +static int i2c_amd_probe(struct platform_device *pdev) +{ + int ret; + struct amd_i2c_dev *i2c_dev; + acpi_handle handle = ACPI_HANDLE(&pdev->dev); + struct acpi_device *adev; + struct amd_mp2_dev *mp2_dev; + const char *uid; + + if (acpi_bus_get_device(handle, &adev)) + return -ENODEV; + + /* The ACPI namespace doesn't contain information about which MP2 PCI + * device an AMDI0011 ACPI device is related to, so assume that there's + * only one MP2 PCI device per system. + */ + mp2_dev = amd_mp2_find_device(); + if (!mp2_dev || !mp2_dev->probed) + /* The MP2 PCI device should get probed later */ + return -EPROBE_DEFER; + + i2c_dev = devm_kzalloc(&pdev->dev, sizeof(*i2c_dev), GFP_KERNEL); + if (!i2c_dev) + return -ENOMEM; + + i2c_dev->common.mp2_dev = mp2_dev; + i2c_dev->pdev = pdev; + platform_set_drvdata(pdev, i2c_dev); + + i2c_dev->common.cmd_completion = &i2c_amd_cmd_completion; +#ifdef CONFIG_PM + i2c_dev->common.suspend = &i2c_amd_suspend; + i2c_dev->common.resume = &i2c_amd_resume; +#endif + + uid = adev->pnp.unique_id; + if (!uid) { + dev_err(&pdev->dev, "missing UID/bus id!\n"); + return -EINVAL; + } else if (strcmp(uid, "0") == 0) { + i2c_dev->common.bus_id = 0; + } else if (strcmp(uid, "1") == 0) { + i2c_dev->common.bus_id = 1; + } else { + dev_err(&pdev->dev, "incorrect UID/bus id \"%s\"!\n", uid); + return -EINVAL; + } + dev_dbg(&pdev->dev, "bus id is %u\n", i2c_dev->common.bus_id); + + /* Register the adapter */ + amd_mp2_pm_runtime_get(mp2_dev); + + i2c_dev->common.reqcmd = i2c_none; + if (amd_mp2_register_cb(&i2c_dev->common)) + return -EINVAL; + device_link_add(&i2c_dev->pdev->dev, &mp2_dev->pci_dev->dev, + DL_FLAG_AUTOREMOVE_CONSUMER); + + i2c_dev->common.i2c_speed = i2c_amd_get_bus_speed(pdev); + + /* Setup i2c adapter description */ + i2c_dev->adap.owner = THIS_MODULE; + i2c_dev->adap.algo = &i2c_amd_algorithm; + i2c_dev->adap.quirks = &amd_i2c_dev_quirks; + i2c_dev->adap.dev.parent = &pdev->dev; + i2c_dev->adap.algo_data = i2c_dev; + i2c_dev->adap.timeout = AMD_I2C_TIMEOUT; + ACPI_COMPANION_SET(&i2c_dev->adap.dev, ACPI_COMPANION(&pdev->dev)); + i2c_dev->adap.dev.of_node = pdev->dev.of_node; + snprintf(i2c_dev->adap.name, sizeof(i2c_dev->adap.name), + "AMD MP2 i2c bus %u", i2c_dev->common.bus_id); + i2c_set_adapdata(&i2c_dev->adap, i2c_dev); + + init_completion(&i2c_dev->cmd_complete); + + /* Enable the bus */ + if (i2c_amd_enable_set(i2c_dev, true)) + dev_err(&pdev->dev, "initial bus enable failed\n"); + + /* Attach to the i2c layer */ + ret = i2c_add_adapter(&i2c_dev->adap); + + amd_mp2_pm_runtime_put(mp2_dev); + + if (ret < 0) + dev_err(&pdev->dev, "i2c add adapter failed = %d\n", ret); + + return ret; +} + +static int i2c_amd_remove(struct platform_device *pdev) +{ + struct amd_i2c_dev *i2c_dev = platform_get_drvdata(pdev); + struct amd_i2c_common *i2c_common = &i2c_dev->common; + + i2c_lock_bus(&i2c_dev->adap, I2C_LOCK_ROOT_ADAPTER); + + i2c_amd_enable_set(i2c_dev, false); + amd_mp2_unregister_cb(i2c_common); + i2c_common->mp2_dev = NULL; + + i2c_unlock_bus(&i2c_dev->adap, I2C_LOCK_ROOT_ADAPTER); + + i2c_del_adapter(&i2c_dev->adap); + return 0; +} + +static const struct acpi_device_id i2c_amd_acpi_match[] = { + { "AMDI0011" }, + { }, +}; +MODULE_DEVICE_TABLE(acpi, i2c_amd_acpi_match); + +static struct platform_driver i2c_amd_plat_driver = { + .probe = i2c_amd_probe, + .remove = i2c_amd_remove, + .driver = { + .name = "i2c_amd_mp2", + .acpi_match_table = ACPI_PTR(i2c_amd_acpi_match), + }, +}; +module_platform_driver(i2c_amd_plat_driver); + +MODULE_DESCRIPTION("AMD(R) MP2 I2C Platform Driver"); +MODULE_AUTHOR("Nehal Shah "); +MODULE_AUTHOR("Elie Morisse "); +MODULE_LICENSE("Dual BSD/GPL"); diff --git a/drivers/i2c/busses/i2c-amd-mp2.h b/drivers/i2c/busses/i2c-amd-mp2.h new file mode 100644 index 000000000000..058362edebaa --- /dev/null +++ b/drivers/i2c/busses/i2c-amd-mp2.h @@ -0,0 +1,219 @@ +/* SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause */ +/* + * AMD MP2 I2C adapter driver + * + * Authors: Shyam Sundar S K + * Elie Morisse + */ + +#ifndef I2C_AMD_PCI_MP2_H +#define I2C_AMD_PCI_MP2_H + +#include +#include +#include + +#define PCI_DEVICE_ID_AMD_MP2 0x15E6 + +struct amd_i2c_common; +struct amd_mp2_dev; + +enum { + /* MP2 C2P Message Registers */ + AMD_C2P_MSG0 = 0x10500, /* MP2 Message for I2C0 */ + AMD_C2P_MSG1 = 0x10504, /* MP2 Message for I2C1 */ + AMD_C2P_MSG2 = 0x10508, /* DRAM Address Lo / Data 0 */ + AMD_C2P_MSG3 = 0x1050c, /* DRAM Address HI / Data 1 */ + AMD_C2P_MSG4 = 0x10510, /* Data 2 */ + AMD_C2P_MSG5 = 0x10514, /* Data 3 */ + AMD_C2P_MSG6 = 0x10518, /* Data 4 */ + AMD_C2P_MSG7 = 0x1051c, /* Data 5 */ + AMD_C2P_MSG8 = 0x10520, /* Data 6 */ + AMD_C2P_MSG9 = 0x10524, /* Data 7 */ + + /* MP2 P2C Message Registers */ + AMD_P2C_MSG0 = 0x10680, /* Do not use */ + AMD_P2C_MSG1 = 0x10684, /* I2C0 interrupt register */ + AMD_P2C_MSG2 = 0x10688, /* I2C1 interrupt register */ + AMD_P2C_MSG3 = 0x1068C, /* MP2 debug info */ + AMD_P2C_MSG_INTEN = 0x10690, /* MP2 interrupt gen register */ + AMD_P2C_MSG_INTSTS = 0x10694, /* Interrupt status */ +}; + +/* Command register data structures */ + +#define i2c_none (-1) +enum i2c_cmd { + i2c_read = 0, + i2c_write, + i2c_enable, + i2c_disable, + number_of_sensor_discovered, + is_mp2_active, + invalid_cmd = 0xF, +}; + +enum speed_enum { + speed100k = 0, + speed400k = 1, + speed1000k = 2, + speed1400k = 3, + speed3400k = 4 +}; + +enum mem_type { + use_dram = 0, + use_c2pmsg = 1, +}; + +/** + * union i2c_cmd_base : bit access of C2P commands + * @i2c_cmd: bit 0..3 i2c R/W command + * @bus_id: bit 4..7 i2c bus index + * @slave_addr: bit 8..15 slave address + * @length: bit 16..27 read/write length + * @i2c_speed: bit 28..30 bus speed + * @mem_type: bit 31 0-DRAM; 1-C2P msg o/p + */ +union i2c_cmd_base { + u32 ul; + struct { + enum i2c_cmd i2c_cmd : 4; + u8 bus_id : 4; + u32 slave_addr : 8; + u32 length : 12; + enum speed_enum i2c_speed : 3; + enum mem_type mem_type : 1; + } s; +}; + +enum response_type { + invalid_response = 0, + command_success = 1, + command_failed = 2, +}; + +enum status_type { + i2c_readcomplete_event = 0, + i2c_readfail_event = 1, + i2c_writecomplete_event = 2, + i2c_writefail_event = 3, + i2c_busenable_complete = 4, + i2c_busenable_failed = 5, + i2c_busdisable_complete = 6, + i2c_busdisable_failed = 7, + invalid_data_length = 8, + invalid_slave_address = 9, + invalid_i2cbus_id = 10, + invalid_dram_addr = 11, + invalid_command = 12, + mp2_active = 13, + numberof_sensors_discovered_resp = 14, + i2c_bus_notinitialized +}; + +/** + * union i2c_event : bit access of P2C events + * @response: bit 0..1 i2c response type + * @status: bit 2..6 status_type + * @mem_type: bit 7 0-DRAM; 1-C2P msg o/p + * @bus_id: bit 8..11 i2c bus id + * @length: bit 12..23 message length + * @slave_addr: bit 24-31 slave address + */ +union i2c_event { + u32 ul; + struct { + enum response_type response : 2; + enum status_type status : 5; + enum mem_type mem_type : 1; + u8 bus_id : 4; + u32 length : 12; + u32 slave_addr : 8; + } r; +}; + +/** + * struct amd_i2c_common - per bus/i2c adapter context, shared + * between the pci and the platform driver + * @eventval: MP2 event value set by the IRQ handler + * @mp2_dev: MP2 pci device this adapter is part of + * @msg: i2c message + * @cmd_completion: function called by the IRQ handler to signal + * the platform driver + * @reqcmd: requested i2c command type + * @cmd_success: set to true if the MP2 responded to a command with + * the expected status and response type + * @bus_id: bus index + * @i2c_speed: i2c bus speed determined by the slowest slave + * @dma_buf: if msg length > 32, holds the DMA buffer virtual address + * @dma_addr: if msg length > 32, holds the DMA buffer address + */ +struct amd_i2c_common { + union i2c_event eventval; + struct amd_mp2_dev *mp2_dev; + struct i2c_msg *msg; + void (*cmd_completion)(struct amd_i2c_common *i2c_common); + enum i2c_cmd reqcmd; + u8 cmd_success; + u8 bus_id; + enum speed_enum i2c_speed; + u8 *dma_buf; + dma_addr_t dma_addr; +#ifdef CONFIG_PM + int (*suspend)(struct amd_i2c_common *i2c_common); + int (*resume)(struct amd_i2c_common *i2c_common); +#endif /* CONFIG_PM */ +}; + +/** + * struct amd_mp2_dev - per PCI device context + * @pci_dev: PCI driver node + * @busses: MP2 devices may have up to two busses, + * each bus corresponding to an i2c adapter + * @mmio: iommapped registers + * @c2p_lock: controls access to the C2P mailbox shared between + * the two adapters + * @c2p_lock_busid: id of the adapter which locked c2p_lock + */ +struct amd_mp2_dev { + struct pci_dev *pci_dev; + struct amd_i2c_common *busses[2]; + void __iomem *mmio; + struct mutex c2p_lock; + u8 c2p_lock_busid; + unsigned int probed; +}; + +#define ndev_pdev(ndev) ((ndev)->pci_dev) +#define ndev_name(ndev) pci_name(ndev_pdev(ndev)) +#define ndev_dev(ndev) (&ndev_pdev(ndev)->dev) +#define work_amd_i2c_common(__work) \ + container_of(__work, struct amd_i2c_common, work.work) + +/* PCIe communication driver */ + +int amd_mp2_rw(struct amd_i2c_common *i2c_common, enum i2c_cmd reqcmd); +int amd_mp2_bus_enable_set(struct amd_i2c_common *i2c_common, bool enable); + +void amd_mp2_process_event(struct amd_i2c_common *i2c_common); + +void amd_mp2_rw_timeout(struct amd_i2c_common *i2c_common); + +int amd_mp2_register_cb(struct amd_i2c_common *i2c_common); +int amd_mp2_unregister_cb(struct amd_i2c_common *i2c_common); + +struct amd_mp2_dev *amd_mp2_find_device(void); + +static inline void amd_mp2_pm_runtime_get(struct amd_mp2_dev *mp2_dev) +{ + pm_runtime_get_sync(&mp2_dev->pci_dev->dev); +} + +static inline void amd_mp2_pm_runtime_put(struct amd_mp2_dev *mp2_dev) +{ + pm_runtime_mark_last_busy(&mp2_dev->pci_dev->dev); + pm_runtime_put_autosuspend(&mp2_dev->pci_dev->dev); +} + +#endif -- cgit v1.2.3 From cc809ed885097eafff7b711ef03c20261651ec3a Mon Sep 17 00:00:00 2001 From: Jakub Wilk Date: Mon, 18 Mar 2019 18:34:21 +0100 Subject: Documentation: fix core_pattern max length The buffer size for core_pattern is 128, but one character is used for terminating null byte, so the actual limit is 127: # printf '%0999d' > /proc/sys/kernel/core_pattern # tr -d '\n' < /proc/sys/kernel/core_pattern | wc -c 127 Signed-off-by: Jakub Wilk Signed-off-by: Jonathan Corbet --- Documentation/sysctl/kernel.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/sysctl/kernel.txt b/Documentation/sysctl/kernel.txt index aa058aa7bf28..f0c86fbb3b48 100644 --- a/Documentation/sysctl/kernel.txt +++ b/Documentation/sysctl/kernel.txt @@ -196,7 +196,7 @@ CAP_LAST_CAP from the kernel. core_pattern: core_pattern is used to specify a core dumpfile pattern name. -. max length 128 characters; default value is "core" +. max length 127 characters; default value is "core" . core_pattern is used as a pattern template for the output filename; certain string patterns (beginning with '%') are substituted with their actual values. -- cgit v1.2.3 From 4318f9bb736c9874204b5c94c825f0c57bed78d7 Mon Sep 17 00:00:00 2001 From: Tom Levy Date: Thu, 21 Mar 2019 14:37:56 +1300 Subject: docs: remove spaces from shell variable assignment The instructions for generating patches are given as shell commands with variables as placeholders. They use the syntax "SRCTREE= linux", which is wrong for the Bourne shell family (it runs the command "linux" with the variable "SRCTREE" set to the empty string). Remove the spaces to avoid confusion. This breaks the pretty alignment but helps new contributors who try to run the commands as written. Signed-off-by: Tom Levy Cc: Jonathan Corbet Signed-off-by: Jonathan Corbet --- Documentation/process/submitting-patches.rst | 6 +++--- Documentation/translations/it_IT/process/submitting-patches.rst | 6 +++--- Documentation/translations/ja_JP/SubmittingPatches | 6 +++--- Documentation/translations/zh_CN/process/submitting-patches.rst | 6 +++--- 4 files changed, 12 insertions(+), 12 deletions(-) (limited to 'Documentation') diff --git a/Documentation/process/submitting-patches.rst b/Documentation/process/submitting-patches.rst index be7d1829c3af..33098adc5381 100644 --- a/Documentation/process/submitting-patches.rst +++ b/Documentation/process/submitting-patches.rst @@ -60,8 +60,8 @@ not in any lower subdirectory. To create a patch for a single file, it is often sufficient to do:: - SRCTREE= linux - MYFILE= drivers/net/mydriver.c + SRCTREE=linux + MYFILE=drivers/net/mydriver.c cd $SRCTREE cp $MYFILE $MYFILE.orig @@ -73,7 +73,7 @@ To create a patch for multiple files, you should unpack a "vanilla", or unmodified kernel source tree, and generate a ``diff`` against your own source tree. For example:: - MYSRC= /devel/linux + MYSRC=/devel/linux tar xvfz linux-3.19.tar.gz mv linux-3.19 linux-3.19-vanilla diff --git a/Documentation/translations/it_IT/process/submitting-patches.rst b/Documentation/translations/it_IT/process/submitting-patches.rst index 2ab9c1401aa1..713fba075b9d 100644 --- a/Documentation/translations/it_IT/process/submitting-patches.rst +++ b/Documentation/translations/it_IT/process/submitting-patches.rst @@ -67,8 +67,8 @@ sulla radice dei sorgenti del kernel, e non sulle sue sottocartelle. Per creare una patch per un singolo file, spesso è sufficiente fare:: - SRCTREE= linux - MYFILE= drivers/net/mydriver.c + SRCTREE=linux + MYFILE=drivers/net/mydriver.c cd $SRCTREE cp $MYFILE $MYFILE.orig @@ -80,7 +80,7 @@ Per creare una patch per molteplici file, dovreste spacchettare i sorgenti "vergini", o comunque non modificati, e fare un ``diff`` coi vostri. Per esempio:: - MYSRC= /devel/linux + MYSRC=/devel/linux tar xvfz linux-3.19.tar.gz mv linux-3.19 linux-3.19-vanilla diff --git a/Documentation/translations/ja_JP/SubmittingPatches b/Documentation/translations/ja_JP/SubmittingPatches index 02139656463e..ad979c3c06a6 100644 --- a/Documentation/translations/ja_JP/SubmittingPatches +++ b/Documentation/translations/ja_JP/SubmittingPatches @@ -58,8 +58,8 @@ Linux カーネルに対する全ての変更は diff(1) コマンドによる 1個のファイルについてのパッチを作成するためには、ほとんどの場合、 以下の作業を行えば十分です。 - SRCTREE= linux-2.6 - MYFILE= drivers/net/mydriver.c + SRCTREE=linux-2.6 + MYFILE=drivers/net/mydriver.c cd $SRCTREE cp $MYFILE $MYFILE.orig @@ -71,7 +71,7 @@ Linux カーネルに対する全ての変更は diff(1) コマンドによる なわち変更を加えてない Linux カーネルを展開し、自分の Linux カーネル ソースとの差分を生成しないといけません。例えば、 - MYSRC= /devel/linux-2.6 + MYSRC=/devel/linux-2.6 tar xvfz linux-2.6.12.tar.gz mv linux-2.6.12 linux-2.6.12-vanilla diff --git a/Documentation/translations/zh_CN/process/submitting-patches.rst b/Documentation/translations/zh_CN/process/submitting-patches.rst index 66c64acf86c1..1bd64832b424 100644 --- a/Documentation/translations/zh_CN/process/submitting-patches.rst +++ b/Documentation/translations/zh_CN/process/submitting-patches.rst @@ -41,8 +41,8 @@ Documentation/process/submitting-drivers.rst 。 何子目录。 为一个单独的文件创建补丁,一般来说这样做就够了:: - SRCTREE= linux-2.6 - MYFILE= drivers/net/mydriver.c + SRCTREE=linux-2.6 + MYFILE=drivers/net/mydriver.c cd $SRCTREE cp $MYFILE $MYFILE.orig @@ -53,7 +53,7 @@ Documentation/process/submitting-drivers.rst 。 为多个文件创建补丁,你可以解开一个没有修改过的内核源代码树,然后和你自 己的代码树之间做 diff 。例如:: - MYSRC= /devel/linux-2.6 + MYSRC=/devel/linux-2.6 tar xvfz linux-2.6.12.tar.gz mv linux-2.6.12 linux-2.6.12-vanilla -- cgit v1.2.3 From 224b1e860c74044b211c0322d0f757573106f184 Mon Sep 17 00:00:00 2001 From: Federico Vaga Date: Sat, 23 Mar 2019 18:54:16 +0100 Subject: doc: minor fixes to translation's disclaimer - move TOC on top because that's the most interesting part - a couple of minor fixes Signed-off-by: Federico Vaga Signed-off-by: Jonathan Corbet --- Documentation/translations/index.rst | 26 ++++++++++++-------------- 1 file changed, 12 insertions(+), 14 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/index.rst b/Documentation/translations/index.rst index d7a38fd28b50..e446e5ed00a6 100644 --- a/Documentation/translations/index.rst +++ b/Documentation/translations/index.rst @@ -4,12 +4,21 @@ Translations ============ +.. toctree:: + :maxdepth: 1 + + zh_CN/index + it_IT/index + ko_KR/index + ja_JP/index + + .. _translations_disclaimer: Disclaimer ---------- -Translation's purpose is to ease reading and understating in languages other +Translation's purpose is to ease reading and understanding in languages other than English. Its aim is to help people who do not understand English or have doubts about its interpretation. Additionally, some people prefer to read documentation in their native language, but please bear in mind that the @@ -40,16 +49,5 @@ translations, you may find slight differences that carry the same message but in a different form. If you need to communicate with the Linux community but you do not feel -comfortable to write in English, you can ask to the translation's -maintainers for help. - -Translations ------------- - -.. toctree:: - :maxdepth: 1 - - zh_CN/index - it_IT/index - ko_KR/index - ja_JP/index +comfortable writing in English, you can ask the translation's maintainers +for help. -- cgit v1.2.3 From 24a2bb90741bf86ddcf6558be419e182ff44fc95 Mon Sep 17 00:00:00 2001 From: Sean Christopherson Date: Fri, 22 Mar 2019 14:11:36 -0700 Subject: docs: Clarify the usage and sign-off requirements for Co-developed-by The documentation for Co-developed-by is a bit light on details, e.g. it doesn't explicitly state that: - Multiple Co-developed-by tags are perfectly acceptable - Co-developed-by and Signed-off-by must be paired together - SOB ordering should still follow standard sign-off procedure Lack of explicit direction has resulted in developers taking a variety of approaches, often lacking any intent whatsoever, e.g. scattering SOBs willy-nilly, collecting them all at the end or the beginning, etc... Tweak the wording to make it clear that multiple co-authors are allowed, and document the expectation that standard sign-off procedures are to be followed. The use of "original author" has also led to confusion as many patches don't have just one "original" author, e.g. when multiple developers are involved from the genesis of the patch. Remove all usage of "original" and instead call out that Co-developed-by is simply a way to provide attribution in addition to the From tag, i.e. neither tag is intended to imply anything with regard to who did what. Provide examples to (hopefully) eliminate any ambiguity. Cc: Tobin C. Harding Cc: Thomas Gleixner Cc: Jani Nikula Cc: Jorge Ramirez-Ortiz Cc: Jonathan Cameron Cc: Joe Perches Cc: Greg Kroah-Hartman Cc: Niklas Cassel Cc: Jonathan Corbet Signed-off-by: Sean Christopherson Signed-off-by: Jonathan Corbet --- Documentation/process/5.Posting.rst | 10 ++++--- Documentation/process/submitting-patches.rst | 40 ++++++++++++++++++++++++---- 2 files changed, 41 insertions(+), 9 deletions(-) (limited to 'Documentation') diff --git a/Documentation/process/5.Posting.rst b/Documentation/process/5.Posting.rst index 4213e580f273..855a70b80269 100644 --- a/Documentation/process/5.Posting.rst +++ b/Documentation/process/5.Posting.rst @@ -216,10 +216,12 @@ The tags in common use are: which can be found in :ref:`Documentation/process/submitting-patches.rst ` Code without a proper signoff cannot be merged into the mainline. - - Co-developed-by: states that the patch was also created by another developer - along with the original author. This is useful at times when multiple - people work on a single patch. Note, this person also needs to have a - Signed-off-by: line in the patch as well. + - Co-developed-by: states that the patch was co-created by several developers; + it is a used to give attribution to co-authors (in addition to the author + attributed by the From: tag) when multiple people work on a single patch. + Every Co-developed-by: must be immediately followed by a Signed-off-by: of + the associated co-author. Details and examples can be found in + :ref:`Documentation/process/submitting-patches.rst `. - Acked-by: indicates an agreement by another developer (often a maintainer of the relevant code) that the patch is appropriate for diff --git a/Documentation/process/submitting-patches.rst b/Documentation/process/submitting-patches.rst index 33098adc5381..9c4299293c72 100644 --- a/Documentation/process/submitting-patches.rst +++ b/Documentation/process/submitting-patches.rst @@ -545,10 +545,40 @@ person it names - but it should indicate that this person was copied on the patch. This tag documents that potentially interested parties have been included in the discussion. -A Co-developed-by: states that the patch was also created by another developer -along with the original author. This is useful at times when multiple people -work on a single patch. Note, this person also needs to have a Signed-off-by: -line in the patch as well. +Co-developed-by: states that the patch was co-created by multiple developers; +it is a used to give attribution to co-authors (in addition to the author +attributed by the From: tag) when several people work on a single patch. Since +Co-developed-by: denotes authorship, every Co-developed-by: must be immediately +followed by a Signed-off-by: of the associated co-author. Standard sign-off +procedure applies, i.e. the ordering of Signed-off-by: tags should reflect the +chronological history of the patch insofar as possible, regardless of whether +the author is attributed via From: or Co-developed-by:. Notably, the last +Signed-off-by: must always be that of the developer submitting the patch. + +Note, the From: tag is optional when the From: author is also the person (and +email) listed in the From: line of the email header. + +Example of a patch submitted by the From: author:: + + + + Co-developed-by: First Co-Author + Signed-off-by: First Co-Author + Co-developed-by: Second Co-Author + Signed-off-by: Second Co-Author + Signed-off-by: From Author + +Example of a patch submitted by a Co-developed-by: author:: + + From: From Author + + + + Co-developed-by: Random Co-Author + Signed-off-by: Random Co-Author + Signed-off-by: From Author + Co-developed-by: Submitting Co-Author + Signed-off-by: Submitting Co-Author 13) Using Reported-by:, Tested-by:, Reviewed-by:, Suggested-by: and Fixes: @@ -696,7 +726,7 @@ A couple of example Subjects:: The ``from`` line must be the very first line in the message body, and has the form: - From: Original Author + From: Patch Author The ``from`` line specifies who will be credited as the author of the patch in the permanent changelog. If the ``from`` line is missing, -- cgit v1.2.3 From c55760806d082ff9947560950cfd6cf180ab491e Mon Sep 17 00:00:00 2001 From: Joel Stanley Date: Mon, 25 Mar 2019 21:03:22 +1030 Subject: Documentation: rtc: Correct location of rtctest.c The useful little rtctest program moved location a while back. Fixes: a12ab9e125f1 ("selftests: move RTC tests to rtc subfolder") Signed-off-by: Joel Stanley Signed-off-by: Jonathan Corbet --- Documentation/rtc.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/rtc.txt b/Documentation/rtc.txt index a129acf38537..688c95b11919 100644 --- a/Documentation/rtc.txt +++ b/Documentation/rtc.txt @@ -136,5 +136,5 @@ a high functionality RTC is integrated into the SOC. That system might read the system clock from the discrete RTC, but use the integrated one for all other tasks, because of its greater functionality. -Check out tools/testing/selftests/timers/rtctest.c for an example usage of the +Check out tools/testing/selftests/rtc/rtctest.c for an example usage of the ioctl interface. -- cgit v1.2.3 From 90675d391e9196e95a9e9e31eaa9693d4a995927 Mon Sep 17 00:00:00 2001 From: Hans Verkuil Date: Wed, 6 Mar 2019 16:13:21 -0500 Subject: media: vb2: add requires_requests bit for stateless codecs Stateless codecs require the use of the Request API as opposed of it being optional. So add a bit to indicate this and let vb2 check for this. If an attempt is made to queue a buffer without an associated request, then the EBADR error is returned to userspace. Doing this check in the vb2 core simplifies drivers, since they don't have to check for this, they can just set this flag. Signed-off-by: Hans Verkuil Reviewed-by: Paul Kocialkowski Signed-off-by: Mauro Carvalho Chehab --- Documentation/media/uapi/v4l/vidioc-qbuf.rst | 4 ++++ drivers/media/common/videobuf2/videobuf2-core.c | 9 +++++++++ drivers/media/common/videobuf2/videobuf2-v4l2.c | 4 ++++ include/media/videobuf2-core.h | 3 +++ 4 files changed, 20 insertions(+) (limited to 'Documentation') diff --git a/Documentation/media/uapi/v4l/vidioc-qbuf.rst b/Documentation/media/uapi/v4l/vidioc-qbuf.rst index c138d149faea..5739c3676062 100644 --- a/Documentation/media/uapi/v4l/vidioc-qbuf.rst +++ b/Documentation/media/uapi/v4l/vidioc-qbuf.rst @@ -189,6 +189,10 @@ EACCES The ``V4L2_BUF_FLAG_REQUEST_FD`` flag was set but the device does not support requests for the given buffer type. +EBADR + The ``V4L2_BUF_FLAG_REQUEST_FD`` flag was not set but the device requires + that the buffer is part of a request. + EBUSY The first buffer was queued via a request, but the application now tries to queue it directly, or vice versa (it is not permitted to mix the two diff --git a/drivers/media/common/videobuf2/videobuf2-core.c b/drivers/media/common/videobuf2/videobuf2-core.c index 678a31a2b549..b98ec6e1a222 100644 --- a/drivers/media/common/videobuf2/videobuf2-core.c +++ b/drivers/media/common/videobuf2/videobuf2-core.c @@ -1507,6 +1507,12 @@ int vb2_core_qbuf(struct vb2_queue *q, unsigned int index, void *pb, vb = q->bufs[index]; + if (!req && vb->state != VB2_BUF_STATE_IN_REQUEST && + q->requires_requests) { + dprintk(1, "qbuf requires a request\n"); + return -EBADR; + } + if ((req && q->uses_qbuf) || (!req && vb->state != VB2_BUF_STATE_IN_REQUEST && q->uses_requests)) { @@ -2238,6 +2244,9 @@ int vb2_core_queue_init(struct vb2_queue *q) WARN_ON(!q->ops->buf_queue)) return -EINVAL; + if (WARN_ON(q->requires_requests && !q->supports_requests)) + return -EINVAL; + INIT_LIST_HEAD(&q->queued_list); INIT_LIST_HEAD(&q->done_list); spin_lock_init(&q->done_lock); diff --git a/drivers/media/common/videobuf2/videobuf2-v4l2.c b/drivers/media/common/videobuf2/videobuf2-v4l2.c index 74d3abf33b50..84de18b30a95 100644 --- a/drivers/media/common/videobuf2/videobuf2-v4l2.c +++ b/drivers/media/common/videobuf2/videobuf2-v4l2.c @@ -381,6 +381,10 @@ static int vb2_queue_or_prepare_buf(struct vb2_queue *q, struct media_device *md return 0; if (!(b->flags & V4L2_BUF_FLAG_REQUEST_FD)) { + if (q->requires_requests) { + dprintk(1, "%s: queue requires requests\n", opname); + return -EBADR; + } if (q->uses_requests) { dprintk(1, "%s: queue uses requests\n", opname); return -EBUSY; diff --git a/include/media/videobuf2-core.h b/include/media/videobuf2-core.h index c02af6370e9b..fe010ad62b90 100644 --- a/include/media/videobuf2-core.h +++ b/include/media/videobuf2-core.h @@ -482,6 +482,8 @@ struct vb2_buf_ops { * has not been called. This is a vb1 idiom that has been adopted * also by vb2. * @supports_requests: this queue supports the Request API. + * @requires_requests: this queue requires the Request API. If this is set to 1, + * then supports_requests must be set to 1 as well. * @uses_qbuf: qbuf was used directly for this queue. Set to 1 the first * time this is called. Set to 0 when the queue is canceled. * If this is 1, then you cannot queue buffers from a request. @@ -556,6 +558,7 @@ struct vb2_queue { unsigned allow_zero_bytesused:1; unsigned quirk_poll_must_check_waiting_for_buffers:1; unsigned supports_requests:1; + unsigned requires_requests:1; unsigned uses_qbuf:1; unsigned uses_requests:1; -- cgit v1.2.3 From e79c7159d471fa5e818bf9ec13e095e22033c792 Mon Sep 17 00:00:00 2001 From: Hans Verkuil Date: Wed, 20 Mar 2019 10:31:18 -0400 Subject: media: media requests: return EBADR instead of EACCES If requests are used when they shouldn't, or not used when they should, then return EBADR (Invalid request descriptor) instead of EACCES. The reason for this change is that EACCES has more to do with permissions (not being the owner of the resource), but in this case the request file descriptor is just wrong for the current mode of the device. Update the documentation accordingly. Signed-off-by: Hans Verkuil Signed-off-by: Mauro Carvalho Chehab --- Documentation/media/uapi/mediactl/request-api.rst | 2 +- Documentation/media/uapi/v4l/buffer.rst | 2 +- Documentation/media/uapi/v4l/vidioc-qbuf.rst | 12 +++++------- drivers/media/common/videobuf2/videobuf2-v4l2.c | 2 +- drivers/media/media-request.c | 4 ++-- include/media/media-request.h | 4 ++-- 6 files changed, 12 insertions(+), 14 deletions(-) (limited to 'Documentation') diff --git a/Documentation/media/uapi/mediactl/request-api.rst b/Documentation/media/uapi/mediactl/request-api.rst index 1ad631e549fe..a74c82d95609 100644 --- a/Documentation/media/uapi/mediactl/request-api.rst +++ b/Documentation/media/uapi/mediactl/request-api.rst @@ -93,7 +93,7 @@ A queued request cannot be modified anymore. .. caution:: For :ref:`memory-to-memory devices ` you can use requests only for output buffers, not for capture buffers. Attempting to add a capture buffer - to a request will result in an ``EACCES`` error. + to a request will result in an ``EBADR`` error. If the request contains configurations for multiple entities, individual drivers may synchronize so the requested pipeline's topology is applied before the diff --git a/Documentation/media/uapi/v4l/buffer.rst b/Documentation/media/uapi/v4l/buffer.rst index 81ffdcb89057..b9a2e9dc707c 100644 --- a/Documentation/media/uapi/v4l/buffer.rst +++ b/Documentation/media/uapi/v4l/buffer.rst @@ -326,7 +326,7 @@ struct v4l2_buffer Applications should not set ``V4L2_BUF_FLAG_REQUEST_FD`` for any ioctls other than :ref:`VIDIOC_QBUF `. - If the device does not support requests, then ``EACCES`` will be returned. + If the device does not support requests, then ``EBADR`` will be returned. If requests are supported but an invalid request file descriptor is given, then ``EINVAL`` will be returned. diff --git a/Documentation/media/uapi/v4l/vidioc-qbuf.rst b/Documentation/media/uapi/v4l/vidioc-qbuf.rst index 5739c3676062..dbf7b445a27b 100644 --- a/Documentation/media/uapi/v4l/vidioc-qbuf.rst +++ b/Documentation/media/uapi/v4l/vidioc-qbuf.rst @@ -111,7 +111,7 @@ in use. Setting it means that the buffer will not be passed to the driver until the request itself is queued. Also, the driver will apply any settings associated with the request for this buffer. This field will be ignored unless the ``V4L2_BUF_FLAG_REQUEST_FD`` flag is set. -If the device does not support requests, then ``EACCES`` will be returned. +If the device does not support requests, then ``EBADR`` will be returned. If requests are supported but an invalid request file descriptor is given, then ``EINVAL`` will be returned. @@ -125,7 +125,7 @@ then ``EINVAL`` will be returned. For :ref:`memory-to-memory devices ` you can specify the ``request_fd`` only for output buffers, not for capture buffers. Attempting - to specify this for a capture buffer will result in an ``EACCES`` error. + to specify this for a capture buffer will result in an ``EBADR`` error. Applications call the ``VIDIOC_DQBUF`` ioctl to dequeue a filled (capturing) or displayed (output) buffer from the driver's outgoing @@ -185,12 +185,10 @@ EPIPE codecs if a buffer with the ``V4L2_BUF_FLAG_LAST`` was already dequeued and no new buffers are expected to become available. -EACCES - The ``V4L2_BUF_FLAG_REQUEST_FD`` flag was set but the device does not - support requests for the given buffer type. - EBADR - The ``V4L2_BUF_FLAG_REQUEST_FD`` flag was not set but the device requires + The ``V4L2_BUF_FLAG_REQUEST_FD`` flag was set but the device does not + support requests for the given buffer type, or + the ``V4L2_BUF_FLAG_REQUEST_FD`` flag was not set but the device requires that the buffer is part of a request. EBUSY diff --git a/drivers/media/common/videobuf2/videobuf2-v4l2.c b/drivers/media/common/videobuf2/videobuf2-v4l2.c index 84de18b30a95..b11a779e97b0 100644 --- a/drivers/media/common/videobuf2/videobuf2-v4l2.c +++ b/drivers/media/common/videobuf2/videobuf2-v4l2.c @@ -392,7 +392,7 @@ static int vb2_queue_or_prepare_buf(struct vb2_queue *q, struct media_device *md return 0; } else if (!q->supports_requests) { dprintk(1, "%s: queue does not support requests\n", opname); - return -EACCES; + return -EBADR; } else if (q->uses_qbuf) { dprintk(1, "%s: queue does not use requests\n", opname); return -EBUSY; diff --git a/drivers/media/media-request.c b/drivers/media/media-request.c index eec2e2b2f6ec..ed87305b29f9 100644 --- a/drivers/media/media-request.c +++ b/drivers/media/media-request.c @@ -251,7 +251,7 @@ media_request_get_by_fd(struct media_device *mdev, int request_fd) if (!mdev || !mdev->ops || !mdev->ops->req_validate || !mdev->ops->req_queue) - return ERR_PTR(-EACCES); + return ERR_PTR(-EBADR); filp = fget(request_fd); if (!filp) @@ -407,7 +407,7 @@ int media_request_object_bind(struct media_request *req, int ret = -EBUSY; if (WARN_ON(!ops->release)) - return -EACCES; + return -EBADR; spin_lock_irqsave(&req->lock, flags); diff --git a/include/media/media-request.h b/include/media/media-request.h index bd36d7431698..3cd25a2717ce 100644 --- a/include/media/media-request.h +++ b/include/media/media-request.h @@ -198,7 +198,7 @@ void media_request_put(struct media_request *req); * Get the request represented by @request_fd that is owned * by the media device. * - * Return a -EACCES error pointer if requests are not supported + * Return a -EBADR error pointer if requests are not supported * by this driver. Return -EINVAL if the request was not found. * Return the pointer to the request if found: the caller will * have to call @media_request_put when it finished using the @@ -231,7 +231,7 @@ static inline void media_request_put(struct media_request *req) static inline struct media_request * media_request_get_by_fd(struct media_device *mdev, int request_fd) { - return ERR_PTR(-EACCES); + return ERR_PTR(-EBADR); } #endif -- cgit v1.2.3 From b663e57cb490cb7a712057e4a4e5159f174cf9e8 Mon Sep 17 00:00:00 2001 From: Dafna Hirschfeld Date: Wed, 6 Mar 2019 16:13:37 -0500 Subject: media: vicodec: add documentation to V4L2_CID_FWHT_I/P_FRAME_QP add documentation to V4L2_CID_FWHT_I/P_FRAME_QP controls in ext-ctrls-codec.rst [mchehab+samsung@kernel.org: remove extra blank lines] Signed-off-by: Dafna Hirschfeld Signed-off-by: Hans Verkuil Signed-off-by: Mauro Carvalho Chehab --- Documentation/media/uapi/v4l/ext-ctrls-codec.rst | 8 ++++++++ 1 file changed, 8 insertions(+) (limited to 'Documentation') diff --git a/Documentation/media/uapi/v4l/ext-ctrls-codec.rst b/Documentation/media/uapi/v4l/ext-ctrls-codec.rst index c97fb7923be5..3a0fe41549f7 100644 --- a/Documentation/media/uapi/v4l/ext-ctrls-codec.rst +++ b/Documentation/media/uapi/v4l/ext-ctrls-codec.rst @@ -1537,6 +1537,14 @@ enum v4l2_mpeg_video_h264_hierarchical_coding_type - non-intra-coded frames, in zigzag scanning order. Only relevant for non-4:2:0 YUV formats. +``V4L2_CID_FWHT_I_FRAME_QP (integer)`` + Quantization parameter for an I frame for FWHT. Valid range: from 1 + to 31. + +``V4L2_CID_FWHT_P_FRAME_QP (integer)`` + Quantization parameter for a P frame for FWHT. Valid range: from 1 + to 31. + MFC 5.1 MPEG Controls ===================== -- cgit v1.2.3 From f94368e3b04aca0d204d56a076bfca572e2c6c5f Mon Sep 17 00:00:00 2001 From: Dafna Hirschfeld Date: Wed, 6 Mar 2019 16:13:38 -0500 Subject: media: vicodec: add documentation to V4L2_CID_MPEG_VIDEO_FWHT_PARAMS add documentation to V4L2_CID_MPEG_VIDEO_FWHT_PARAMS control and its related 'v4l2_ctrl_fwht_params' struct [mchehab+samsung@kernel.org: remove extra blank lines] Signed-off-by: Dafna Hirschfeld Signed-off-by: Hans Verkuil Signed-off-by: Mauro Carvalho Chehab --- Documentation/media/uapi/v4l/ext-ctrls-codec.rst | 116 +++++++++++++++++++++++ 1 file changed, 116 insertions(+) (limited to 'Documentation') diff --git a/Documentation/media/uapi/v4l/ext-ctrls-codec.rst b/Documentation/media/uapi/v4l/ext-ctrls-codec.rst index 3a0fe41549f7..0aaee04f81dd 100644 --- a/Documentation/media/uapi/v4l/ext-ctrls-codec.rst +++ b/Documentation/media/uapi/v4l/ext-ctrls-codec.rst @@ -1704,6 +1704,122 @@ enum v4l2_mpeg_mfc51_video_force_frame_type - - Force a non-coded frame. +.. _v4l2-mpeg-fwht: + +``V4L2_CID_MPEG_VIDEO_FWHT_PARAMS (struct)`` + Specifies the fwht parameters (as extracted from the bitstream) for the + associated FWHT data. This includes the necessary parameters for + configuring a stateless hardware decoding pipeline for FWHT. + + .. note:: + + This compound control is not yet part of the public kernel API and + it is expected to change. + +.. c:type:: v4l2_ctrl_fwht_params + +.. cssclass:: longtable + +.. flat-table:: struct v4l2_ctrl_fwht_params + :header-rows: 0 + :stub-columns: 0 + :widths: 1 1 2 + + * - __u64 + - ``backward_ref_ts`` + - Timestamp of the V4L2 capture buffer to use as backward reference, used + with P-coded frames. The timestamp refers to the + ``timestamp`` field in struct :c:type:`v4l2_buffer`. Use the + :c:func:`v4l2_timeval_to_ns()` function to convert the struct + :c:type:`timeval` in struct :c:type:`v4l2_buffer` to a __u64. + * - __u32 + - ``version`` + - The version of the codec + * - __u32 + - ``width`` + - The width of the frame + * - __u32 + - ``height`` + - The height of the frame + * - __u32 + - ``flags`` + - The flags of the frame, see :ref:`fwht-flags`. + * - __u32 + - ``colorspace`` + - The colorspace of the frame, from enum :c:type:`v4l2_colorspace`. + * - __u32 + - ``xfer_func`` + - The transfer function, from enum :c:type:`v4l2_xfer_func`. + * - __u32 + - ``ycbcr_enc`` + - The Y'CbCr encoding, from enum :c:type:`v4l2_ycbcr_encoding`. + * - __u32 + - ``quantization`` + - The quantization range, from enum :c:type:`v4l2_quantization`. + + + +.. _fwht-flags: + +FWHT Flags +============ +.. tabularcolumns:: |p{7.0cm}|p{2.2cm}|p{8.3cm}| + +.. cssclass:: longtable + +.. flat-table:: + :header-rows: 0 + :stub-columns: 0 + :widths: 3 1 4 + + * - ``FWHT_FL_IS_INTERLACED`` + - 0x00000001 + - Set if this is an interlaced format + * - ``FWHT_FL_IS_BOTTOM_FIRST`` + - 0x00000002 + - Set if this is a bottom-first (NTSC) interlaced format + * - ``FWHT_FL_IS_ALTERNATE`` + - 0x00000004 + - Set if each 'frame' contains just one field + * - ``FWHT_FL_IS_BOTTOM_FIELD`` + - 0x00000008 + - If FWHT_FL_IS_ALTERNATE was set, then this is set if this 'frame' is the + bottom field, else it is the top field. + * - ``FWHT_FL_LUMA_IS_UNCOMPRESSED`` + - 0x00000010 + - Set if the luma plane is uncompressed + * - ``FWHT_FL_CB_IS_UNCOMPRESSED`` + - 0x00000020 + - Set if the cb plane is uncompressed + * - ``FWHT_FL_CR_IS_UNCOMPRESSED`` + - 0x00000040 + - Set if the cr plane is uncompressed + * - ``FWHT_FL_CHROMA_FULL_HEIGHT`` + - 0x00000080 + - Set if the chroma plane has the same height as the luma plane, + else the chroma plane is half the height of the luma plane + * - ``FWHT_FL_CHROMA_FULL_WIDTH`` + - 0x00000100 + - Set if the chroma plane has the same width as the luma plane, + else the chroma plane is half the width of the luma plane + * - ``FWHT_FL_ALPHA_IS_UNCOMPRESSED`` + - 0x00000200 + - Set if the alpha plane is uncompressed + * - ``FWHT_FL_I_FRAME`` + - 0x00000400 + - Set if this is an I-frame + * - ``FWHT_FL_COMPONENTS_NUM_MSK`` + - 0x00070000 + - A 4-values flag - the number of components - 1 + * - ``FWHT_FL_PIXENC_YUV`` + - 0x00080000 + - Set if the pixel encoding is YUV + * - ``FWHT_FL_PIXENC_RGB`` + - 0x00100000 + - Set if the pixel encoding is RGB + * - ``FWHT_FL_PIXENC_HSV`` + - 0x00180000 + - Set if the pixel encoding is HSV CX2341x MPEG Controls -- cgit v1.2.3 From ee3963c492ccdb2aa32a45481dea62865bce603d Mon Sep 17 00:00:00 2001 From: Dafna Hirschfeld Date: Wed, 6 Mar 2019 16:13:39 -0500 Subject: media: vicodec: add documentation to V4L2_PIX_FMT_FWHT_STATELESS add documentation to V4L2_PIX_FMT_FWHT_STATELESS in pixfmt-compressed.rst Signed-off-by: Dafna Hirschfeld Signed-off-by: Hans Verkuil Signed-off-by: Mauro Carvalho Chehab --- Documentation/media/uapi/v4l/pixfmt-compressed.rst | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'Documentation') diff --git a/Documentation/media/uapi/v4l/pixfmt-compressed.rst b/Documentation/media/uapi/v4l/pixfmt-compressed.rst index 2675bef3eefe..6c961cfb74da 100644 --- a/Documentation/media/uapi/v4l/pixfmt-compressed.rst +++ b/Documentation/media/uapi/v4l/pixfmt-compressed.rst @@ -125,3 +125,9 @@ Compressed Formats - Video elementary stream using a codec based on the Fast Walsh Hadamard Transform. This codec is implemented by the vicodec ('Virtual Codec') driver. See the codec-fwht.h header for more details. + * .. _V4L2-PIX-FMT-FWHT-STATELESS: + + - ``V4L2_PIX_FMT_FWHT_STATELESS`` + - 'SFWH' + - Same format as V4L2_PIX_FMT_FWHT but requires stateless codec implementation. + See the :ref:`associated Codec Control IDs `. -- cgit v1.2.3 From 7ee02cb56c3f86c9707224f5770f70395ffbba70 Mon Sep 17 00:00:00 2001 From: Maxime Ripard Date: Fri, 15 Mar 2019 10:36:51 +0100 Subject: dt-bindings: Add YAML description for Allwinner boards We've never had a board compatibles documentation for the Allwinner boards so far. Let's create a json-schema for them. Reviewed-by: Rob Herring Signed-off-by: Maxime Ripard --- Documentation/devicetree/bindings/arm/sunxi.yaml | 797 +++++++++++++++++++++++ 1 file changed, 797 insertions(+) create mode 100644 Documentation/devicetree/bindings/arm/sunxi.yaml (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/sunxi.yaml b/Documentation/devicetree/bindings/arm/sunxi.yaml new file mode 100644 index 000000000000..11563d3f7c65 --- /dev/null +++ b/Documentation/devicetree/bindings/arm/sunxi.yaml @@ -0,0 +1,797 @@ +# SPDX-License-Identifier: (GPL-2.0+ OR X11) +%YAML 1.2 +--- +$id: http://devicetree.org/schemas/arm/sunxi.yaml# +$schema: http://devicetree.org/meta-schemas/core.yaml# + +title: Allwinner platforms device tree bindings + +maintainers: + - Chen-Yu Tsai + - Maxime Ripard + +properties: + $nodename: + const: '/' + compatible: + oneOf: + + - description: Allwinner A23 Evaluation Board + items: + - const: allwinner,sun8i-a23-evb + - const: allwinner,sun8i-a23 + + - description: Allwinner A31 APP4 Evaluation Board + items: + - const: allwinner,app4-evb1 + - const: allwinner,sun6i-a31 + + - description: Allwinner A83t Homlet Evaluation Board v2 + items: + - const: allwinner,h8homlet-v2 + - const: allwinner,sun8i-a83t + + - description: Allwinner GA10H Quad Core Tablet v1.1 + items: + - const: allwinner,ga10h-v1.1 + - const: allwinner,sun8i-a33 + + - description: Allwinner GT90H Tablet v4 + items: + - const: allwinner,gt90h-v4 + - const: allwinner,sun8i-a23 + + - description: Allwinner R16 EVB (Parrot) + items: + - const: allwinner,parrot + - const: allwinner,sun8i-a33 + + - description: Amarula A64 Relic + items: + - const: amarula,a64-relic + - const: allwinner,sun50i-a64 + + - description: Auxtek T003 A10s HDMI TV Stick + items: + - const: allwinner,auxtek-t003 + - const: allwinner,sun5i-a10s + + - description: Auxtek T004 A10s HDMI TV Stick + items: + - const: allwinner,auxtek-t004 + - const: allwinner,sun5i-a10s + + - description: BA10 TV Box + items: + - const: allwinner,ba10-tvbox + - const: allwinner,sun4i-a10 + + - description: BananaPi + items: + - const: lemaker,bananapi + - const: allwinner,sun7i-a20 + + - description: BananaPi M1 Plus + items: + - const: sinovoip,bpi-m1-plus + - const: allwinner,sun7i-a20 + + - description: BananaPi M2 + items: + - const: sinovoip,bpi-m2 + - const: allwinner,sun6i-a31s + + - description: BananaPi M2 Berry + items: + - const: sinovoip,bpi-m2-berry + - const: allwinner,sun8i-r40 + + - description: BananaPi M2 Plus + items: + - const: sinovoip,bpi-m2-plus + - const: allwinner,sun8i-h3 + + - description: BananaPi M2 Plus + items: + - const: sinovoip,bpi-m2-plus + - const: allwinner,sun50i-h5 + + - description: BananaPi M2 Plus v1.2 + items: + - const: bananapi,bpi-m2-plus-v1.2 + - const: allwinner,sun8i-h3 + + - description: BananaPi M2 Plus v1.2 + items: + - const: bananapi,bpi-m2-plus-v1.2 + - const: allwinner,sun50i-h5 + + - description: BananaPi M2 Magic + items: + - const: sinovoip,bananapi-m2m + - const: allwinner,sun8i-a33 + + - description: BananaPi M2 Ultra + items: + - const: sinovoip,bpi-m2-ultra + - const: allwinner,sun8i-r40 + + - description: BananaPi M2 Zero + items: + - const: sinovoip,bpi-m2-zero + - const: allwinner,sun8i-h2-plus + + - description: BananaPi M3 + items: + - const: sinovoip,bpi-m3 + - const: allwinner,sun8i-a83t + + - description: BananaPi M64 + items: + - const: sinovoip,bananapi-m64 + - const: allwinner,sun50i-a64 + + - description: BananaPro + items: + - const: lemaker,bananapro + - const: allwinner,sun7i-a20 + + - description: Beelink X2 + items: + - const: roofull,beelink-x2 + - const: allwinner,sun8i-h3 + + - description: Chuwi V7 CW0825 + items: + - const: chuwi,v7-cw0825 + - const: allwinner,sun4i-a10 + + - description: Colorfly E708 Q1 Tablet + items: + - const: colorfly,e708-q1 + - const: allwinner,sun6i-a31s + + - description: CSQ CS908 Set Top Box + items: + - const: csq,cs908 + - const: allwinner,sun6i-a31s + + - description: Cubietech Cubieboard + items: + - const: cubietech,a10-cubieboard + - const: allwinner,sun4i-a10 + + - description: Cubietech Cubieboard2 + items: + - const: cubietech,cubieboard2 + - const: allwinner,sun7i-a20 + + - description: Cubietech Cubieboard4 + items: + - const: cubietech,a80-cubieboard4 + - const: allwinner,sun9i-a80 + + - description: Cubietech Cubietruck + items: + - const: cubietech,cubietruck + - const: allwinner,sun7i-a20 + + - description: Cubietech Cubietruck Plus + items: + - const: cubietech,cubietruck-plus + - const: allwinner,sun8i-a83t + + - description: Difrnce DIT4350 + items: + - const: difrnce,dit4350 + - const: allwinner,sun5i-a13 + + - description: Dserve DSRV9703C + items: + - const: dserve,dsrv9703c + - const: allwinner,sun4i-a10 + + - description: Empire Electronix D709 Tablet + items: + - const: empire-electronix,d709 + - const: allwinner,sun5i-a13 + + - description: Empire Electronix M712 Tablet + items: + - const: empire-electronix,m712 + - const: allwinner,sun5i-a13 + + - description: FriendlyARM NanoPi A64 + items: + - const: friendlyarm,nanopi-a64 + - const: allwinner,sun50i-a64 + + - description: FriendlyARM NanoPi M1 + items: + - const: friendlyarm,nanopi-m1 + - const: allwinner,sun8i-h3 + + - description: FriendlyARM NanoPi M1 Plus + items: + - const: friendlyarm,nanopi-m1-plus + - const: allwinner,sun8i-h3 + + - description: FriendlyARM NanoPi Neo + items: + - const: friendlyarm,nanopi-neo + - const: allwinner,sun8i-h3 + + - description: FriendlyARM NanoPi Neo 2 + items: + - const: friendlyarm,nanopi-neo2 + - const: allwinner,sun50i-h5 + + - description: FriendlyARM NanoPi Neo Air + items: + - const: friendlyarm,nanopi-neo-air + - const: allwinner,sun8i-h3 + + - description: FriendlyARM NanoPi Neo Plus2 + items: + - const: friendlyarm,nanopi-neo-plus2 + - const: allwinner,sun50i-h5 + + - description: Gemei G9 Tablet + items: + - const: gemei,g9 + - const: allwinner,sun4i-a10 + + - description: Hyundai A7HD + items: + - const: hyundai,a7hd + - const: allwinner,sun4i-a10 + + - description: HSG H702 + items: + - const: hsg,h702 + - const: allwinner,sun5i-a13 + + - description: I12 TV Box + items: + - const: allwinner,i12-tvbox + - const: allwinner,sun7i-a20 + + - description: ICNova A20 SWAC + items: + - const: swac,icnova-a20-swac + - const: incircuit,icnova-a20 + - const: allwinner,sun7i-a20 + + - description: INet-1 + items: + - const: inet-tek,inet1 + - const: allwinner,sun4i-a10 + + - description: iNet-86DZ Rev 01 + items: + - const: primux,inet86dz + - const: allwinner,sun8i-a23 + + - description: iNet-9F Rev 03 + items: + - const: inet-tek,inet9f-rev03 + - const: allwinner,sun4i-a10 + + - description: iNet-97F Rev 02 + items: + - const: primux,inet97fv2 + - const: allwinner,sun4i-a10 + + - description: iNet-98V Rev 02 + items: + - const: primux,inet98v-rev2 + - const: allwinner,sun5i-a13 + + - description: iNet D978 Rev 02 Tablet + items: + - const: primux,inet-d978-rev2 + - const: allwinner,sun8i-a33 + + - description: iNet Q972 Tablet + items: + - const: inet-tek,inet-q972 + - const: allwinner,sun6i-a31s + + - description: Itead Ibox A20 + items: + - const: itead,itead-ibox-a20 + - const: allwinner,sun7i-a20 + + - description: Itead Iteaduino Plus A10 + items: + - const: itead,iteaduino-plus-a10 + - const: allwinner,sun4i-a10 + + - description: Jesurun Q5 + items: + - const: jesurun,q5 + - const: allwinner,sun4i-a10 + + - description: Lamobo R1 + items: + - const: lamobo,lamobo-r1 + - const: allwinner,sun7i-a20 + + - description: Libre Computer Board ALL-H3-CC H2+ + items: + - const: libretech,all-h3-cc-h2-plus + - const: allwinner,sun8i-h2-plus + + - description: Libre Computer Board ALL-H3-CC H3 + items: + - const: libretech,all-h3-cc-h3 + - const: allwinner,sun8i-h3 + + - description: Libre Computer Board ALL-H3-CC H5 + items: + - const: libretech,all-h3-cc-h5 + - const: allwinner,sun50i-h5 + + - description: Lichee Pi One + items: + - const: licheepi,licheepi-one + - const: allwinner,sun5i-a13 + + - description: Lichee Pi Zero + items: + - const: licheepi,licheepi-zero + - const: allwinner,sun8i-v3s + + - description: Lichee Pi Zero (with Dock) + items: + - const: licheepi,licheepi-zero-dock + - const: licheepi,licheepi-zero + - const: allwinner,sun8i-v3s + + - description: Linksprite PCDuino + items: + - const: linksprite,a10-pcduino + - const: allwinner,sun4i-a10 + + - description: Linksprite PCDuino2 + items: + - const: linksprite,a10-pcduino2 + - const: allwinner,sun4i-a10 + + - description: Linksprite PCDuino3 + items: + - const: linksprite,pcduino3 + - const: allwinner,sun7i-a20 + + - description: Linksprite PCDuino3 Nano + items: + - const: linksprite,pcduino3-nano + - const: allwinner,sun7i-a20 + + - description: HAOYU Electronics Marsboard A10 + items: + - const: haoyu,a10-marsboard + - const: allwinner,sun4i-a10 + + - description: MapleBoard MP130 + items: + - const: mapleboard,mp130 + - const: allwinner,sun8i-h3 + + - description: Mele A1000 + items: + - const: mele,a1000 + - const: allwinner,sun4i-a10 + + - description: Mele A1000G Quad Set Top Box + items: + - const: mele,a1000g-quad + - const: allwinner,sun6i-a31 + + - description: Mele I7 Quad Set Top Box + items: + - const: mele,i7 + - const: allwinner,sun6i-a31 + + - description: Mele M3 + items: + - const: mele,m3 + - const: allwinner,sun7i-a20 + + - description: Mele M9 Set Top Box + items: + - const: mele,m9 + - const: allwinner,sun6i-a31 + + - description: Merrii A20 Hummingboard + items: + - const: merrii,a20-hummingbird + - const: allwinner,sun7i-a20 + + - description: Merrii A31 Hummingboard + items: + - const: merrii,a31-hummingbird + - const: allwinner,sun6i-a31 + + - description: Merrii A80 Optimus + items: + - const: merrii,a80-optimus + - const: allwinner,sun9i-a80 + + - description: Miniand Hackberry + items: + - const: miniand,hackberry + - const: allwinner,sun4i-a10 + + - description: MK802 + items: + - const: allwinner,mk802 + - const: allwinner,sun4i-a10 + + - description: MK802-A10s + items: + - const: allwinner,a10s-mk802 + - const: allwinner,sun5i-a10s + + - description: MK802-II + items: + - const: allwinner,mk802ii + - const: allwinner,sun4i-a10 + + - description: MK808c + items: + - const: allwinner,mk808c + - const: allwinner,sun7i-a20 + + - description: MSI Primo81 Tablet + items: + - const: msi,primo81 + - const: allwinner,sun6i-a31s + + - description: Emlid Neutis N5 Developper Board + items: + - const: emlid,neutis-n5-devboard + - const: emlid,neutis-n5 + - const: allwinner,sun50i-h5 + + - description: NextThing Co. CHIP + items: + - const: nextthing,chip + - const: allwinner,sun5i-r8 + - const: allwinner,sun5i-a13 + + - description: NextThing Co. CHIP Pro + items: + - const: nextthing,chip-pro + - const: nextthing,gr8 + + - description: NextThing Co. GR8 Evaluation Board + items: + - const: nextthing,gr8-evb + - const: nextthing,gr8 + + - description: Nintendo NES Classic + items: + - const: nintendo,nes-classic + - const: allwinner,sun8i-r16 + - const: allwinner,sun8i-a33 + + - description: Nintendo Super NES Classic + items: + - const: nintendo,super-nes-classic + - const: nintendo,nes-classic + - const: allwinner,sun8i-r16 + - const: allwinner,sun8i-a33 + + - description: Oceanic 5inMFD (5205) + items: + - const: oceanic,5205-5inmfd + - const: allwinner,sun50i-a64 + + - description: Olimex A10-OlinuXino LIME + items: + - const: olimex,a10-olinuxino-lime + - const: allwinner,sun4i-a10 + + - description: Olimex A10s-OlinuXino Micro + items: + - const: olimex,a10s-olinuxino-micro + - const: allwinner,sun5i-a10s + + - description: Olimex A13-OlinuXino + items: + - const: olimex,a13-olinuxino + - const: allwinner,sun5i-a13 + + - description: Olimex A13-OlinuXino Micro + items: + - const: olimex,a13-olinuxino-micro + - const: allwinner,sun5i-a13 + + - description: Olimex A20-Olimex SOM Evaluation Board + items: + - const: olimex,a20-olimex-som-evb + - const: allwinner,sun7i-a20 + + - description: Olimex A20-Olimex SOM Evaluation Board (with eMMC) + items: + - const: olimex,a20-olimex-som-evb-emmc + - const: allwinner,sun7i-a20 + + - description: Olimex A20-OlinuXino LIME + items: + - const: olimex,a20-olinuxino-lime + - const: allwinner,sun7i-a20 + + - description: Olimex A20-OlinuXino LIME2 + items: + - const: olimex,a20-olinuxino-lime2 + - const: allwinner,sun7i-a20 + + - description: Olimex A20-OlinuXino LIME2 (with eMMC) + items: + - const: olimex,a20-olinuxino-lime2-emmc + - const: allwinner,sun7i-a20 + + - description: Olimex A20-OlinuXino Micro + items: + - const: olimex,a20-olinuxino-micro + - const: allwinner,sun7i-a20 + + - description: Olimex A20-OlinuXino Micro (with eMMC) + items: + - const: olimex,a20-olinuxino-micro-emmc + - const: allwinner,sun7i-a20 + + - description: Olimex A20-SOM204 Evaluation Board + items: + - const: olimex,a20-olimex-som204-evb + - const: allwinner,sun7i-a20 + + - description: Olimex A20-SOM204 Evaluation Board (with eMMC) + items: + - const: olimex,a20-olimex-som204-evb-emmc + - const: allwinner,sun7i-a20 + + - description: Olimex A33-OlinuXino + items: + - const: olimex,a33-olinuxino + - const: allwinner,sun8i-a33 + + - description: Olimex A64-OlinuXino + items: + - const: olimex,a64-olinuxino + - const: allwinner,sun50i-a64 + + - description: Olimex A64 Teres-I + items: + - const: olimex,a64-teres-i + - const: allwinner,sun50i-a64 + + - description: Pine64 + items: + - const: pine64,pine64 + - const: allwinner,sun50i-a64 + + - description: Pine64+ + items: + - const: pine64,pine64-plus + - const: allwinner,sun50i-a64 + + - description: Pine64 PineH64 + items: + - const: pine64,pine-h64 + - const: allwinner,sun50i-h6 + + - description: Pine64 LTS + items: + - const: pine64,pine64-lts + - const: allwinner,sun50i-r18 + - const: allwinner,sun50i-a64 + + - description: Pine64 Pinebook + items: + - const: pine64,pinebook + - const: allwinner,sun50i-a64 + + - description: Pine64 SoPine Baseboard + items: + - const: pine64,sopine-baseboard + - const: pine64,sopine + - const: allwinner,sun50i-a64 + + - description: PineRiver Mini X-Plus + items: + - const: pineriver,mini-xplus + - const: allwinner,sun4i-a10 + + - description: Point of View Protab2-IPS9 + items: + - const: pov,protab2-ips9 + - const: allwinner,sun4i-a10 + + - description: Polaroid MID2407PXE03 Tablet + items: + - const: polaroid,mid2407pxe03 + - const: allwinner,sun8i-a23 + + - description: Polaroid MID2809PXE04 Tablet + items: + - const: polaroid,mid2809pxe04 + - const: allwinner,sun8i-a23 + + - description: Q8 A13 Tablet + items: + - const: allwinner,q8-a13 + - const: allwinner,sun5i-a13 + + - description: Q8 A23 Tablet + items: + - const: allwinner,q8-a23 + - const: allwinner,sun8i-a23 + + - description: Q8 A33 Tablet + items: + - const: allwinner,q8-a33 + - const: allwinner,sun8i-a33 + + - description: Qihua CQA3T BV3 + items: + - const: qihua,t3-cqa3t-bv3 + - const: allwinner,sun8i-t3 + - const: allwinner,sun8i-r40 + + - description: R7 A10s HDMI TV Stick + items: + - const: allwinner,r7-tv-dongle + - const: allwinner,sun5i-a10s + + - description: RerVision H3-DVK + items: + - const: rervision,h3-dvk + - const: allwinner,sun8i-h3 + + - description: Sinlinx SinA31s Core Board + items: + - const: sinlinx,sina31s + - const: allwinner,sun6i-a31s + + - description: Sinlinx SinA31s Development Board + items: + - const: sinlinx,sina31s-sdk + - const: allwinner,sun6i-a31s + + - description: Sinlinx SinA33 + items: + - const: sinlinx,sina33 + - const: allwinner,sun8i-a33 + + - description: TBS A711 Tablet + items: + - const: tbs-biometrics,a711 + - const: allwinner,sun8i-a83t + + - description: Utoo P66 + items: + - const: utoo,p66 + - const: allwinner,sun5i-a13 + + - description: Wexler TAB7200 + items: + - const: wexler,tab7200 + - const: allwinner,sun7i-a20 + + - description: WITS A31 Colombus Evaluation Board + items: + - const: wits,colombus + - const: allwinner,sun6i-a31 + + - description: WITS Pro A20 DKT + items: + - const: wits,pro-a20-dkt + - const: allwinner,sun7i-a20 + + - description: Wobo i5 + items: + - const: wobo,a10s-wobo-i5 + - const: allwinner,sun5i-a10s + + - description: Yones TopTech BS1078 v2 Tablet + items: + - const: yones-toptech,bs1078-v2 + - const: allwinner,sun6i-a31s + + - description: Xunlong OrangePi + items: + - const: xunlong,orangepi + - const: allwinner,sun7i-a20 + + - description: Xunlong OrangePi 2 + items: + - const: xunlong,orangepi-2 + - const: allwinner,sun8i-h3 + + - description: Xunlong OrangePi Lite + items: + - const: xunlong,orangepi-lite + - const: allwinner,sun8i-h3 + + - description: Xunlong OrangePi Lite2 + items: + - const: xunlong,orangepi-lite2 + - const: allwinner,sun50i-h6 + + - description: Xunlong OrangePi Mini + items: + - const: xunlong,orangepi-mini + - const: allwinner,sun7i-a20 + + - description: Xunlong OrangePi One + items: + - const: xunlong,orangepi-one + - const: allwinner,sun8i-h3 + + - description: Xunlong OrangePi One Plus + items: + - const: xunlong,orangepi-one-plus + - const: allwinner,sun50i-h6 + + - description: Xunlong OrangePi PC + items: + - const: xunlong,orangepi-pc + - const: allwinner,sun8i-h3 + + - description: Xunlong OrangePi PC 2 + items: + - const: xunlong,orangepi-pc2 + - const: allwinner,sun50i-h5 + + - description: Xunlong OrangePi PC Plus + items: + - const: xunlong,orangepi-pc-plus + - const: allwinner,sun8i-h3 + + - description: Xunlong OrangePi Plus + items: + - const: xunlong,orangepi-plus + - const: allwinner,sun8i-h3 + + - description: Xunlong OrangePi Plus 2E + items: + - const: xunlong,orangepi-plus2e + - const: allwinner,sun8i-h3 + + - description: Xunlong OrangePi Prime + items: + - const: xunlong,orangepi-prime + - const: allwinner,sun50i-h5 + + - description: Xunlong OrangePi R1 + items: + - const: xunlong,orangepi-r1 + - const: allwinner,sun8i-h2-plus + + - description: Xunlong OrangePi Win + items: + - const: xunlong,orangepi-win + - const: allwinner,sun50i-a64 + + - description: Xunlong OrangePi Zero + items: + - const: xunlong,orangepi-zero + - const: allwinner,sun8i-h2-plus + + - description: Xunlong OrangePi Zero Plus + items: + - const: xunlong,orangepi-zero-plus + - const: allwinner,sun50i-h5 + + - description: Xunlong OrangePi Zero Plus2 + items: + - const: xunlong,orangepi-zero-plus2 + - const: allwinner,sun50i-h5 + + - description: Xunlong OrangePi Zero Plus2 + items: + - const: xunlong,orangepi-zero-plus2-h3 + - const: allwinner,sun8i-h3 -- cgit v1.2.3 From be354500c101d0cbd779fd8c86be2ed809db7ea9 Mon Sep 17 00:00:00 2001 From: Maxime Ripard Date: Mon, 25 Mar 2019 14:52:33 +0100 Subject: dt-bindings: arm: Remove the CPU compatible documentation Commit 1f8afea8fee0 ("dt-bindings: Add YAML description for Allwinner boards") added an exhaustive list of the valid compatibles used for both the SoCs and boards. We can therefore remove the old documentation, that never got as well updated as it should have. Acked-by: Chen-Yu Tsai Signed-off-by: Maxime Ripard --- Documentation/devicetree/bindings/arm/sunxi.txt | 23 ----------------------- 1 file changed, 23 deletions(-) delete mode 100644 Documentation/devicetree/bindings/arm/sunxi.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/sunxi.txt b/Documentation/devicetree/bindings/arm/sunxi.txt deleted file mode 100644 index 9254cbe7d516..000000000000 --- a/Documentation/devicetree/bindings/arm/sunxi.txt +++ /dev/null @@ -1,23 +0,0 @@ -Allwinner sunXi Platforms Device Tree Bindings - -Each device tree must specify which Allwinner SoC it uses, -using one of the following compatible strings: - - allwinner,sun4i-a10 - allwinner,sun5i-a10s - allwinner,sun5i-a13 - allwinner,sun5i-r8 - allwinner,sun6i-a31 - allwinner,sun7i-a20 - allwinner,sun8i-a23 - allwinner,sun8i-a33 - allwinner,sun8i-a83t - allwinner,sun8i-h2-plus - allwinner,sun8i-h3 - allwinner,sun8i-r40 - allwinner,sun8i-t3 - allwinner,sun8i-v3s - allwinner,sun9i-a80 - allwinner,sun50i-a64 - allwinner,suniv-f1c100s - nextthing,gr8 -- cgit v1.2.3 From 5930a57fb08ad93574b82592540006641fb3272a Mon Sep 17 00:00:00 2001 From: Uwe Kleine-König Date: Wed, 20 Mar 2019 10:12:52 +0100 Subject: dt-bindings: arm: fsl: Add devicetree binding for Eckelmann ci4x10 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Add devicetree binding for Eckelmann's ci4x10 board which is powered by an i.MX6DL SoC. Signed-off-by: Uwe Kleine-König Reviewed-by: Rob Herring Signed-off-by: Shawn Guo --- Documentation/devicetree/bindings/arm/fsl.yaml | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/fsl.yaml b/Documentation/devicetree/bindings/arm/fsl.yaml index 7e2cd6ad26bd..ae32a2e9e232 100644 --- a/Documentation/devicetree/bindings/arm/fsl.yaml +++ b/Documentation/devicetree/bindings/arm/fsl.yaml @@ -90,6 +90,7 @@ properties: - description: i.MX6DL based Boards items: - enum: + - eckelmann,imx6dl-ci4x10 - fsl,imx6dl-sabreauto # i.MX6 DualLite/Solo SABRE Automotive Board - fsl,imx6dl-sabresd # i.MX6 DualLite SABRE Smart Device Board - technologic,imx6dl-ts4900 -- cgit v1.2.3 From 9d9521e89081cbc332b35cd44bfd335ed2f0cf3b Mon Sep 17 00:00:00 2001 From: Jacky Bai Date: Fri, 22 Mar 2019 09:40:35 +0000 Subject: dt-bindings: arm: imx: Add the soc binding for imx8mm Add the soc & board binding for i.MX8MM. Signed-off-by: Jacky Bai Reviewed-by: Rob Herring Signed-off-by: Shawn Guo --- Documentation/devicetree/bindings/arm/fsl.yaml | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/fsl.yaml b/Documentation/devicetree/bindings/arm/fsl.yaml index ae32a2e9e232..b06aa2b94fe2 100644 --- a/Documentation/devicetree/bindings/arm/fsl.yaml +++ b/Documentation/devicetree/bindings/arm/fsl.yaml @@ -155,6 +155,12 @@ properties: - const: compulab,cl-som-imx7 - const: fsl,imx7d + - description: i.MX8MM based Boards + items: + - enum: + - fsl,imx8mm-evk # i.MX8MM EVK Board + - const: fsl,imx8mm + - description: i.MX8QXP based Boards items: - enum: -- cgit v1.2.3 From d0d9071b724123ebde89bdf6b52b86c3289abe85 Mon Sep 17 00:00:00 2001 From: Viorel Suman Date: Tue, 22 Jan 2019 11:14:27 +0000 Subject: ASoC: add fsl_audmix DT binding documentation Add the DT binding documentation for NXP Audio Mixer CPU DAI driver. Signed-off-by: Viorel Suman Signed-off-by: Mark Brown --- .../devicetree/bindings/sound/fsl,audmix.txt | 54 ++++++++++++++++++++++ 1 file changed, 54 insertions(+) create mode 100644 Documentation/devicetree/bindings/sound/fsl,audmix.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/sound/fsl,audmix.txt b/Documentation/devicetree/bindings/sound/fsl,audmix.txt new file mode 100644 index 000000000000..45f807ec21a5 --- /dev/null +++ b/Documentation/devicetree/bindings/sound/fsl,audmix.txt @@ -0,0 +1,54 @@ +NXP Audio Mixer (AUDMIX). + +The Audio Mixer is a on-chip functional module that allows mixing of two +audio streams into a single audio stream. Audio Mixer has two input serial +audio interfaces. These are driven by two Synchronous Audio interface +modules (SAI). Each input serial interface carries 8 audio channels in its +frame in TDM manner. Mixer mixes audio samples of corresponding channels +from two interfaces into a single sample. Before mixing, audio samples of +two inputs can be attenuated based on configuration. The output of the +Audio Mixer is also a serial audio interface. Like input interfaces it has +the same TDM frame format. This output is used to drive the serial DAC TDM +interface of audio codec and also sent to the external pins along with the +receive path of normal audio SAI module for readback by the CPU. + +The output of Audio Mixer can be selected from any of the three streams + - serial audio input 1 + - serial audio input 2 + - mixed audio + +Mixing operation is independent of audio sample rate but the two audio +input streams must have same audio sample rate with same number of channels +in TDM frame to be eligible for mixing. + +Device driver required properties: +================================= + - compatible : Compatible list, contains "fsl,imx8qm-audmix" + + - reg : Offset and length of the register set for the device. + + - clocks : Must contain an entry for each entry in clock-names. + + - clock-names : Must include the "ipg" for register access. + + - power-domains : Must contain the phandle to AUDMIX power domain node + + - dais : Must contain a list of phandles to AUDMIX connected + DAIs. The current implementation requires two phandles + to SAI interfaces to be provided, the first SAI in the + list being used to route the AUDMIX output. + + - model : Must contain machine driver name which will configure + and instantiate the appropriate audio card. + +Device driver configuration example: +====================================== + audmix: audmix@59840000 { + compatible = "fsl,imx8qm-audmix"; + reg = <0x0 0x59840000 0x0 0x10000>; + clocks = <&clk IMX8QXP_AUD_AUDMIX_IPG>; + clock-names = "ipg"; + power-domains = <&pd_audmix>; + dais = <&sai4>, <&sai5>; + model = "imx-audmix"; + }; -- cgit v1.2.3 From 4fea6ef0b219d66b8a901fea1744745a1ed2f79b Mon Sep 17 00:00:00 2001 From: "Paul E. McKenney" Date: Wed, 9 Jan 2019 14:48:09 -0800 Subject: doc: Remove obsolete RCU update functions from RCU documentation Now that synchronize_rcu_bh, synchronize_rcu_bh_expedited, call_rcu_bh, rcu_barrier_bh, synchronize_sched, synchronize_sched_expedited, call_rcu_sched, rcu_barrier_sched, get_state_synchronize_sched, and cond_synchronize_sched are obsolete, let's remove them from the documentation aside from a small historical section. Signed-off-by: Paul E. McKenney --- .../Design/Data-Structures/Data-Structures.html | 3 +- .../Expedited-Grace-Periods.html | 4 +- .../Memory-Ordering/Tree-RCU-Memory-Ordering.html | 5 +- Documentation/RCU/NMI-RCU.txt | 13 ++-- Documentation/RCU/UP.txt | 6 +- Documentation/RCU/checklist.txt | 76 ++++++++++------------ Documentation/RCU/rcu.txt | 8 +-- Documentation/RCU/rcubarrier.txt | 27 ++++---- 8 files changed, 66 insertions(+), 76 deletions(-) (limited to 'Documentation') diff --git a/Documentation/RCU/Design/Data-Structures/Data-Structures.html b/Documentation/RCU/Design/Data-Structures/Data-Structures.html index 18f179807563..c30c1957c7e6 100644 --- a/Documentation/RCU/Design/Data-Structures/Data-Structures.html +++ b/Documentation/RCU/Design/Data-Structures/Data-Structures.html @@ -155,8 +155,7 @@ keeping lock contention under control at all tree levels regardless of the level of loading on the system.

RCU updaters wait for normal grace periods by registering -RCU callbacks, either directly via call_rcu() and -friends (namely call_rcu_bh() and call_rcu_sched()), +RCU callbacks, either directly via call_rcu() or indirectly via synchronize_rcu() and friends. RCU callbacks are represented by rcu_head structures, which are queued on rcu_data structures while they are diff --git a/Documentation/RCU/Design/Expedited-Grace-Periods/Expedited-Grace-Periods.html b/Documentation/RCU/Design/Expedited-Grace-Periods/Expedited-Grace-Periods.html index 19e7a5fb6b73..57300db4b5ff 100644 --- a/Documentation/RCU/Design/Expedited-Grace-Periods/Expedited-Grace-Periods.html +++ b/Documentation/RCU/Design/Expedited-Grace-Periods/Expedited-Grace-Periods.html @@ -56,6 +56,7 @@ sections. RCU-preempt Expedited Grace Periods

+CONFIG_PREEMPT=y kernels implement RCU-preempt. The overall flow of the handling of a given CPU by an RCU-preempt expedited grace period is shown in the following diagram: @@ -139,6 +140,7 @@ or offline, among other things. RCU-sched Expedited Grace Periods

+CONFIG_PREEMPT=n kernels implement RCU-sched. The overall flow of the handling of a given CPU by an RCU-sched expedited grace period is shown in the following diagram: @@ -146,7 +148,7 @@ expedited grace period is shown in the following diagram:

As with RCU-preempt, RCU-sched's -synchronize_sched_expedited() ignores offline and +synchronize_rcu_expedited() ignores offline and idle CPUs, again because they are in remotely detectable quiescent states. However, because the diff --git a/Documentation/RCU/Design/Memory-Ordering/Tree-RCU-Memory-Ordering.html b/Documentation/RCU/Design/Memory-Ordering/Tree-RCU-Memory-Ordering.html index 8d21af02b1f0..c64f8d26609f 100644 --- a/Documentation/RCU/Design/Memory-Ordering/Tree-RCU-Memory-Ordering.html +++ b/Documentation/RCU/Design/Memory-Ordering/Tree-RCU-Memory-Ordering.html @@ -34,12 +34,11 @@ Similarly, any code that happens before the beginning of a given RCU grace period is guaranteed to see the effects of all accesses following the end of that grace period that are within RCU read-side critical sections. -

This guarantee is particularly pervasive for synchronize_sched(), -for which RCU-sched read-side critical sections include any region +

Note well that RCU-sched read-side critical sections include any region of code for which preemption is disabled. Given that each individual machine instruction can be thought of as an extremely small region of preemption-disabled code, one can think of -synchronize_sched() as smp_mb() on steroids. +synchronize_rcu() as smp_mb() on steroids.

RCU updaters use this guarantee by splitting their updates into two phases, one of which is executed before the grace period and diff --git a/Documentation/RCU/NMI-RCU.txt b/Documentation/RCU/NMI-RCU.txt index 687777f83b23..881353fd5bff 100644 --- a/Documentation/RCU/NMI-RCU.txt +++ b/Documentation/RCU/NMI-RCU.txt @@ -81,18 +81,19 @@ currently executing on some other CPU. We therefore cannot free up any data structures used by the old NMI handler until execution of it completes on all other CPUs. -One way to accomplish this is via synchronize_sched(), perhaps as +One way to accomplish this is via synchronize_rcu(), perhaps as follows: unset_nmi_callback(); - synchronize_sched(); + synchronize_rcu(); kfree(my_nmi_data); -This works because synchronize_sched() blocks until all CPUs complete -any preemption-disabled segments of code that they were executing. -Since NMI handlers disable preemption, synchronize_sched() is guaranteed +This works because (as of v4.20) synchronize_rcu() blocks until all +CPUs complete any preemption-disabled segments of code that they were +executing. +Since NMI handlers disable preemption, synchronize_rcu() is guaranteed not to return until all ongoing NMI handlers exit. It is therefore safe -to free up the handler's data as soon as synchronize_sched() returns. +to free up the handler's data as soon as synchronize_rcu() returns. Important note: for this to work, the architecture in question must invoke nmi_enter() and nmi_exit() on NMI entry and exit, respectively. diff --git a/Documentation/RCU/UP.txt b/Documentation/RCU/UP.txt index 90ec5341ee98..53bde717017b 100644 --- a/Documentation/RCU/UP.txt +++ b/Documentation/RCU/UP.txt @@ -86,10 +86,8 @@ even on a UP system. So do not do it! Even on a UP system, the RCU infrastructure -must- respect grace periods, and -must- invoke callbacks from a known environment in which no locks are held. -It -is- safe for synchronize_sched() and synchronize_rcu_bh() to return -immediately on an UP system. It is also safe for synchronize_rcu() -to return immediately on UP systems, except when running preemptable -RCU. +Note that it -is- safe for synchronize_rcu() to return immediately on +UP systems, including !PREEMPT SMP builds running on UP systems. Quick Quiz #3: Why can't synchronize_rcu() return immediately on UP systems running preemptable RCU? diff --git a/Documentation/RCU/checklist.txt b/Documentation/RCU/checklist.txt index 6f469864d9f5..fcc59fea5cd4 100644 --- a/Documentation/RCU/checklist.txt +++ b/Documentation/RCU/checklist.txt @@ -182,16 +182,13 @@ over a rather long period of time, but improvements are always welcome! when publicizing a pointer to a structure that can be traversed by an RCU read-side critical section. -5. If call_rcu(), or a related primitive such as call_rcu_bh(), - call_rcu_sched(), or call_srcu() is used, the callback function - will be called from softirq context. In particular, it cannot - block. +5. If call_rcu() or call_srcu() is used, the callback function will + be called from softirq context. In particular, it cannot block. -6. Since synchronize_rcu() can block, it cannot be called from - any sort of irq context. The same rule applies for - synchronize_rcu_bh(), synchronize_sched(), synchronize_srcu(), - synchronize_rcu_expedited(), synchronize_rcu_bh_expedited(), - synchronize_sched_expedite(), and synchronize_srcu_expedited(). +6. Since synchronize_rcu() can block, it cannot be called + from any sort of irq context. The same rule applies + for synchronize_srcu(), synchronize_rcu_expedited(), and + synchronize_srcu_expedited(). The expedited forms of these primitives have the same semantics as the non-expedited forms, but expediting is both expensive and @@ -212,20 +209,20 @@ over a rather long period of time, but improvements are always welcome! of the system, especially to real-time workloads running on the rest of the system. -7. If the updater uses call_rcu() or synchronize_rcu(), then the - corresponding readers must use rcu_read_lock() and - rcu_read_unlock(). If the updater uses call_rcu_bh() or - synchronize_rcu_bh(), then the corresponding readers must - use rcu_read_lock_bh() and rcu_read_unlock_bh(). If the - updater uses call_rcu_sched() or synchronize_sched(), then - the corresponding readers must disable preemption, possibly - by calling rcu_read_lock_sched() and rcu_read_unlock_sched(). - If the updater uses synchronize_srcu() or call_srcu(), then - the corresponding readers must use srcu_read_lock() and +7. As of v4.20, a given kernel implements only one RCU flavor, + which is RCU-sched for PREEMPT=n and RCU-preempt for PREEMPT=y. + If the updater uses call_rcu() or synchronize_rcu(), + then the corresponding readers my use rcu_read_lock() and + rcu_read_unlock(), rcu_read_lock_bh() and rcu_read_unlock_bh(), + or any pair of primitives that disables and re-enables preemption, + for example, rcu_read_lock_sched() and rcu_read_unlock_sched(). + If the updater uses synchronize_srcu() or call_srcu(), + then the corresponding readers must use srcu_read_lock() and srcu_read_unlock(), and with the same srcu_struct. The rules for the expedited primitives are the same as for their non-expedited counterparts. Mixing things up will result in confusion and - broken kernels. + broken kernels, and has even resulted in an exploitable security + issue. One exception to this rule: rcu_read_lock() and rcu_read_unlock() may be substituted for rcu_read_lock_bh() and rcu_read_unlock_bh() @@ -288,8 +285,7 @@ over a rather long period of time, but improvements are always welcome! d. Periodically invoke synchronize_rcu(), permitting a limited number of updates per grace period. - The same cautions apply to call_rcu_bh(), call_rcu_sched(), - call_srcu(), and kfree_rcu(). + The same cautions apply to call_srcu() and kfree_rcu(). Note that although these primitives do take action to avoid memory exhaustion when any given CPU has too many callbacks, a determined @@ -336,12 +332,12 @@ over a rather long period of time, but improvements are always welcome! to safely access and/or modify that data structure. RCU callbacks are -usually- executed on the same CPU that executed - the corresponding call_rcu(), call_rcu_bh(), or call_rcu_sched(), - but are by -no- means guaranteed to be. For example, if a given - CPU goes offline while having an RCU callback pending, then that - RCU callback will execute on some surviving CPU. (If this was - not the case, a self-spawning RCU callback would prevent the - victim CPU from ever going offline.) + the corresponding call_rcu() or call_srcu(). but are by -no- + means guaranteed to be. For example, if a given CPU goes offline + while having an RCU callback pending, then that RCU callback + will execute on some surviving CPU. (If this was not the case, + a self-spawning RCU callback would prevent the victim CPU from + ever going offline.) 13. Unlike other forms of RCU, it -is- permissible to block in an SRCU read-side critical section (demarked by srcu_read_lock() @@ -381,8 +377,7 @@ over a rather long period of time, but improvements are always welcome! SRCU's expedited primitive (synchronize_srcu_expedited()) never sends IPIs to other CPUs, so it is easier on - real-time workloads than is synchronize_rcu_expedited(), - synchronize_rcu_bh_expedited() or synchronize_sched_expedited(). + real-time workloads than is synchronize_rcu_expedited(). Note that rcu_dereference() and rcu_assign_pointer() relate to SRCU just as they do to other forms of RCU. @@ -428,22 +423,19 @@ over a rather long period of time, but improvements are always welcome! These debugging aids can help you find problems that are otherwise extremely difficult to spot. -17. If you register a callback using call_rcu(), call_rcu_bh(), - call_rcu_sched(), or call_srcu(), and pass in a function defined - within a loadable module, then it in necessary to wait for - all pending callbacks to be invoked after the last invocation - and before unloading that module. Note that it is absolutely - -not- sufficient to wait for a grace period! The current (say) - synchronize_rcu() implementation waits only for all previous - callbacks registered on the CPU that synchronize_rcu() is running - on, but it is -not- guaranteed to wait for callbacks registered - on other CPUs. +17. If you register a callback using call_rcu() or call_srcu(), + and pass in a function defined within a loadable module, + then it in necessary to wait for all pending callbacks to + be invoked after the last invocation and before unloading + that module. Note that it is absolutely -not- sufficient to + wait for a grace period! The current (say) synchronize_rcu() + implementation waits only for all previous callbacks registered + on the CPU that synchronize_rcu() is running on, but it is -not- + guaranteed to wait for callbacks registered on other CPUs. You instead need to use one of the barrier functions: o call_rcu() -> rcu_barrier() - o call_rcu_bh() -> rcu_barrier() - o call_rcu_sched() -> rcu_barrier() o call_srcu() -> srcu_barrier() However, these barrier functions are absolutely -not- guaranteed diff --git a/Documentation/RCU/rcu.txt b/Documentation/RCU/rcu.txt index 721b3e426515..c818cf65c5a9 100644 --- a/Documentation/RCU/rcu.txt +++ b/Documentation/RCU/rcu.txt @@ -52,10 +52,10 @@ o If I am running on a uniprocessor kernel, which can only do one o How can I see where RCU is currently used in the Linux kernel? Search for "rcu_read_lock", "rcu_read_unlock", "call_rcu", - "rcu_read_lock_bh", "rcu_read_unlock_bh", "call_rcu_bh", - "srcu_read_lock", "srcu_read_unlock", "synchronize_rcu", - "synchronize_net", "synchronize_srcu", and the other RCU - primitives. Or grab one of the cscope databases from: + "rcu_read_lock_bh", "rcu_read_unlock_bh", "srcu_read_lock", + "srcu_read_unlock", "synchronize_rcu", "synchronize_net", + "synchronize_srcu", and the other RCU primitives. Or grab one + of the cscope databases from: http://www.rdrop.com/users/paulmck/RCU/linuxusage/rculocktab.html diff --git a/Documentation/RCU/rcubarrier.txt b/Documentation/RCU/rcubarrier.txt index 5d7759071a3e..a2782df69732 100644 --- a/Documentation/RCU/rcubarrier.txt +++ b/Documentation/RCU/rcubarrier.txt @@ -83,16 +83,15 @@ Pseudo-code using rcu_barrier() is as follows: 2. Execute rcu_barrier(). 3. Allow the module to be unloaded. -There are also rcu_barrier_bh(), rcu_barrier_sched(), and srcu_barrier() -functions for the other flavors of RCU, and you of course must match -the flavor of rcu_barrier() with that of call_rcu(). If your module -uses multiple flavors of call_rcu(), then it must also use multiple +There is also an srcu_barrier() function for SRCU, and you of course +must match the flavor of rcu_barrier() with that of call_rcu(). If your +module uses multiple flavors of call_rcu(), then it must also use multiple flavors of rcu_barrier() when unloading that module. For example, if -it uses call_rcu_bh(), call_srcu() on srcu_struct_1, and call_srcu() on +it uses call_rcu(), call_srcu() on srcu_struct_1, and call_srcu() on srcu_struct_2(), then the following three lines of code will be required when unloading: - 1 rcu_barrier_bh(); + 1 rcu_barrier(); 2 srcu_barrier(&srcu_struct_1); 3 srcu_barrier(&srcu_struct_2); @@ -185,12 +184,12 @@ module invokes call_rcu() from timers, you will need to first cancel all the timers, and only then invoke rcu_barrier() to wait for any remaining RCU callbacks to complete. -Of course, if you module uses call_rcu_bh(), you will need to invoke -rcu_barrier_bh() before unloading. Similarly, if your module uses -call_rcu_sched(), you will need to invoke rcu_barrier_sched() before -unloading. If your module uses call_rcu(), call_rcu_bh(), -and- -call_rcu_sched(), then you will need to invoke each of rcu_barrier(), -rcu_barrier_bh(), and rcu_barrier_sched(). +Of course, if you module uses call_rcu(), you will need to invoke +rcu_barrier() before unloading. Similarly, if your module uses +call_srcu(), you will need to invoke srcu_barrier() before unloading, +and on the same srcu_struct structure. If your module uses call_rcu() +-and- call_srcu(), then you will need to invoke rcu_barrier() -and- +srcu_barrier(). Implementing rcu_barrier() @@ -223,8 +222,8 @@ shown below. Note that the final "1" in on_each_cpu()'s argument list ensures that all the calls to rcu_barrier_func() will have completed before on_each_cpu() returns. Line 9 then waits for the completion. -This code was rewritten in 2008 to support rcu_barrier_bh() and -rcu_barrier_sched() in addition to the original rcu_barrier(). +This code was rewritten in 2008 and several times thereafter, but this +still gives the general idea. The rcu_barrier_func() runs on each CPU, where it invokes call_rcu() to post an RCU callback, as follows: -- cgit v1.2.3 From 0fa201d1618e0b39a60b1045aa1b323f9d351721 Mon Sep 17 00:00:00 2001 From: Tycho Andersen Date: Tue, 29 Jan 2019 15:05:46 -0700 Subject: doc: Repair some whitespace damage A diagram in whatisRCU.txt has space character before tabs. This commit therefore makes this diagram consistent with elsewhere in the document: Use one leading tab, followed by spaces for any additional whitespace required. Signed-off-by: Tycho Andersen Signed-off-by: Paul E. McKenney --- Documentation/RCU/whatisRCU.txt | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) (limited to 'Documentation') diff --git a/Documentation/RCU/whatisRCU.txt b/Documentation/RCU/whatisRCU.txt index 1ace20815bb1..981651a8b65d 100644 --- a/Documentation/RCU/whatisRCU.txt +++ b/Documentation/RCU/whatisRCU.txt @@ -310,7 +310,7 @@ reader, updater, and reclaimer. rcu_assign_pointer() - +--------+ + +--------+ +---------------------->| reader |---------+ | +--------+ | | | | @@ -318,12 +318,12 @@ reader, updater, and reclaimer. | | | rcu_read_lock() | | | rcu_read_unlock() | rcu_dereference() | | - +---------+ | | - | updater |<---------------------+ | - +---------+ V + +---------+ | | + | updater |<----------------+ | + +---------+ V | +-----------+ +----------------------------------->| reclaimer | - +-----------+ + +-----------+ Defer: synchronize_rcu() & call_rcu() -- cgit v1.2.3 From d1b493bbe101d85c86970f1b6c0401d4c1c473ed Mon Sep 17 00:00:00 2001 From: "Paul E. McKenney" Date: Tue, 12 Feb 2019 07:51:24 -0800 Subject: doc: Describe choice of rcu_dereference() APIs and __rcu usage Reported-by: Andrew Morton Signed-off-by: Paul E. McKenney --- Documentation/RCU/rcu_dereference.txt | 103 ++++++++++++++++++++++++++++++++++ 1 file changed, 103 insertions(+) (limited to 'Documentation') diff --git a/Documentation/RCU/rcu_dereference.txt b/Documentation/RCU/rcu_dereference.txt index ab96227bad42..bf699e8cfc75 100644 --- a/Documentation/RCU/rcu_dereference.txt +++ b/Documentation/RCU/rcu_dereference.txt @@ -351,3 +351,106 @@ garbage values. In short, rcu_dereference() is -not- optional when you are going to dereference the resulting pointer. + + +WHICH MEMBER OF THE rcu_dereference() FAMILY SHOULD YOU USE? + +First, please avoid using rcu_dereference_raw() and also please avoid +using rcu_dereference_check() and rcu_dereference_protected() with a +second argument with a constant value of 1 (or true, for that matter). +With that caution out of the way, here is some guidance for which +member of the rcu_dereference() to use in various situations: + +1. If the access needs to be within an RCU read-side critical + section, use rcu_dereference(). With the new consolidated + RCU flavors, an RCU read-side critical section is entered + using rcu_read_lock(), anything that disables bottom halves, + anything that disables interrupts, or anything that disables + preemption. + +2. If the access might be within an RCU read-side critical section + on the one hand, or protected by (say) my_lock on the other, + use rcu_dereference_check(), for example: + + p1 = rcu_dereference_check(p->rcu_protected_pointer, + lockdep_is_held(&my_lock)); + + +3. If the access might be within an RCU read-side critical section + on the one hand, or protected by either my_lock or your_lock on + the other, again use rcu_dereference_check(), for example: + + p1 = rcu_dereference_check(p->rcu_protected_pointer, + lockdep_is_held(&my_lock) || + lockdep_is_held(&your_lock)); + +4. If the access is on the update side, so that it is always protected + by my_lock, use rcu_dereference_protected(): + + p1 = rcu_dereference_protected(p->rcu_protected_pointer, + lockdep_is_held(&my_lock)); + + This can be extended to handle multiple locks as in #3 above, + and both can be extended to check other conditions as well. + +5. If the protection is supplied by the caller, and is thus unknown + to this code, that is the rare case when rcu_dereference_raw() + is appropriate. In addition, rcu_dereference_raw() might be + appropriate when the lockdep expression would be excessively + complex, except that a better approach in that case might be to + take a long hard look at your synchronization design. Still, + there are data-locking cases where any one of a very large number + of locks or reference counters suffices to protect the pointer, + so rcu_dereference_raw() does have its place. + + However, its place is probably quite a bit smaller than one + might expect given the number of uses in the current kernel. + Ditto for its synonym, rcu_dereference_check( ... , 1), and + its close relative, rcu_dereference_protected(... , 1). + + +SPARSE CHECKING OF RCU-PROTECTED POINTERS + +The sparse static-analysis tool checks for direct access to RCU-protected +pointers, which can result in "interesting" bugs due to compiler +optimizations involving invented loads and perhaps also load tearing. +For example, suppose someone mistakenly does something like this: + + p = q->rcu_protected_pointer; + do_something_with(p->a); + do_something_else_with(p->b); + +If register pressure is high, the compiler might optimize "p" out +of existence, transforming the code to something like this: + + do_something_with(q->rcu_protected_pointer->a); + do_something_else_with(q->rcu_protected_pointer->b); + +This could fatally disappoint your code if q->rcu_protected_pointer +changed in the meantime. Nor is this a theoretical problem: Exactly +this sort of bug cost Paul E. McKenney (and several of his innocent +colleagues) a three-day weekend back in the early 1990s. + +Load tearing could of course result in dereferencing a mashup of a pair +of pointers, which also might fatally disappoint your code. + +These problems could have been avoided simply by making the code instead +read as follows: + + p = rcu_dereference(q->rcu_protected_pointer); + do_something_with(p->a); + do_something_else_with(p->b); + +Unfortunately, these sorts of bugs can be extremely hard to spot during +review. This is where the sparse tool comes into play, along with the +"__rcu" marker. If you mark a pointer declaration, whether in a structure +or as a formal parameter, with "__rcu", which tells sparse to complain if +this pointer is accessed directly. It will also cause sparse to complain +if a pointer not marked with "__rcu" is accessed using rcu_dereference() +and friends. For example, ->rcu_protected_pointer might be declared as +follows: + + struct foo __rcu *rcu_protected_pointer; + +Use of "__rcu" is opt-in. If you choose not to use it, then you should +ignore the sparse warnings. -- cgit v1.2.3 From 884b429ae66758bd2e006dc5fd56757e0fde896d Mon Sep 17 00:00:00 2001 From: "Paul E. McKenney" Date: Wed, 6 Mar 2019 11:24:35 -0800 Subject: doc: Fix typos and otherwise modernize checklist.txt This commit fixes some issues with Documentation/RCU/checklist.txt. Signed-off-by: Paul E. McKenney --- Documentation/RCU/checklist.txt | 43 ++++++++++++++++++++++++----------------- 1 file changed, 25 insertions(+), 18 deletions(-) (limited to 'Documentation') diff --git a/Documentation/RCU/checklist.txt b/Documentation/RCU/checklist.txt index fcc59fea5cd4..e98ff261a438 100644 --- a/Documentation/RCU/checklist.txt +++ b/Documentation/RCU/checklist.txt @@ -318,7 +318,7 @@ over a rather long period of time, but improvements are always welcome! 11. Any lock acquired by an RCU callback must be acquired elsewhere with softirq disabled, e.g., via spin_lock_irqsave(), - spin_lock_bh(), etc. Failing to disable irq on a given + spin_lock_bh(), etc. Failing to disable softirq on a given acquisition of that lock will result in deadlock as soon as the RCU softirq handler happens to run your RCU callback while interrupting that acquisition's critical section. @@ -331,13 +331,16 @@ over a rather long period of time, but improvements are always welcome! must use whatever locking or other synchronization is required to safely access and/or modify that data structure. - RCU callbacks are -usually- executed on the same CPU that executed - the corresponding call_rcu() or call_srcu(). but are by -no- - means guaranteed to be. For example, if a given CPU goes offline - while having an RCU callback pending, then that RCU callback - will execute on some surviving CPU. (If this was not the case, - a self-spawning RCU callback would prevent the victim CPU from - ever going offline.) + Do not assume that RCU callbacks will be executed on the same + CPU that executed the corresponding call_rcu() or call_srcu(). + For example, if a given CPU goes offline while having an RCU + callback pending, then that RCU callback will execute on some + surviving CPU. (If this was not the case, a self-spawning RCU + callback would prevent the victim CPU from ever going offline.) + Furthermore, CPUs designated by rcu_nocbs= might well -always- + have their RCU callbacks executed on some other CPUs, in fact, + for some real-time workloads, this is the whole point of using + the rcu_nocbs= kernel boot parameter. 13. Unlike other forms of RCU, it -is- permissible to block in an SRCU read-side critical section (demarked by srcu_read_lock() @@ -379,8 +382,9 @@ over a rather long period of time, but improvements are always welcome! never sends IPIs to other CPUs, so it is easier on real-time workloads than is synchronize_rcu_expedited(). - Note that rcu_dereference() and rcu_assign_pointer() relate to - SRCU just as they do to other forms of RCU. + Note that rcu_assign_pointer() relates to SRCU just as it does to + other forms of RCU, but instead of rcu_dereference() you should + use srcu_dereference() in order to avoid lockdep splats. 14. The whole point of call_rcu(), synchronize_rcu(), and friends is to wait until all pre-existing readers have finished before @@ -400,6 +404,9 @@ over a rather long period of time, but improvements are always welcome! read-side critical sections. It is the responsibility of the RCU update-side primitives to deal with this. + For SRCU readers, you can use smp_mb__after_srcu_read_unlock() + immediately after an srcu_read_unlock() to get a full barrier. + 16. Use CONFIG_PROVE_LOCKING, CONFIG_DEBUG_OBJECTS_RCU_HEAD, and the __rcu sparse checks to validate your RCU code. These can help find problems as follows: @@ -423,15 +430,15 @@ over a rather long period of time, but improvements are always welcome! These debugging aids can help you find problems that are otherwise extremely difficult to spot. -17. If you register a callback using call_rcu() or call_srcu(), - and pass in a function defined within a loadable module, - then it in necessary to wait for all pending callbacks to - be invoked after the last invocation and before unloading - that module. Note that it is absolutely -not- sufficient to - wait for a grace period! The current (say) synchronize_rcu() - implementation waits only for all previous callbacks registered - on the CPU that synchronize_rcu() is running on, but it is -not- +17. If you register a callback using call_rcu() or call_srcu(), and + pass in a function defined within a loadable module, then it in + necessary to wait for all pending callbacks to be invoked after + the last invocation and before unloading that module. Note that + it is absolutely -not- sufficient to wait for a grace period! + The current (say) synchronize_rcu() implementation is -not- guaranteed to wait for callbacks registered on other CPUs. + Or even on the current CPU if that CPU recently went offline + and came back online. You instead need to use one of the barrier functions: -- cgit v1.2.3 From da8739f23fadf05809c6c37c327367b229467045 Mon Sep 17 00:00:00 2001 From: "Paul E. McKenney" Date: Tue, 5 Mar 2019 15:28:19 -0800 Subject: rcu: Allow rcu_nocbs= to specify all CPUs Currently, the rcu_nocbs= kernel boot parameter requires that a specific list of CPUs be specified, and has no way to say "all of them". As noted by user RavFX in a comment to Phoronix topic 1002538, this is an inconvenient side effect of the removal of the RCU_NOCB_CPU_ALL Kconfig option. This commit therefore enables the rcu_nocbs= kernel boot parameter to be given the string "all", as in "rcu_nocbs=all" to specify that all CPUs on the system are to have their RCU callbacks offloaded. Another approach would be to make cpulist_parse() check for "all", but there are uses of cpulist_parse() that do other checking, which could conflict with an "all". This commit therefore focuses on the specific use of cpulist_parse() in rcu_nocb_setup(). Just a note to other people who would like changes to Linux-kernel RCU: If you send your requests to me directly, they might get fixed somewhat faster. RavFX's comment was posted on January 22, 2018 and I first saw it on March 5, 2019. And the only reason that I found it -at- -all- was that I was looking for projects using RCU, and my search engine showed me that Phoronix comment quite by accident. Your choice, though! ;-) Signed-off-by: Paul E. McKenney --- Documentation/admin-guide/kernel-parameters.txt | 4 +++- kernel/rcu/tree_plugin.h | 5 ++++- 2 files changed, 7 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt index 2b8ee90bb644..d377a2166b79 100644 --- a/Documentation/admin-guide/kernel-parameters.txt +++ b/Documentation/admin-guide/kernel-parameters.txt @@ -3623,7 +3623,9 @@ see CONFIG_RAS_CEC help text. rcu_nocbs= [KNL] - The argument is a cpu list, as described above. + The argument is a cpu list, as described above, + except that the string "all" can be used to + specify every CPU on the system. In kernels built with CONFIG_RCU_NOCB_CPU=y, set the specified list of CPUs to be no-callback CPUs. diff --git a/kernel/rcu/tree_plugin.h b/kernel/rcu/tree_plugin.h index d408661d5fb7..ed4a6dabf31d 100644 --- a/kernel/rcu/tree_plugin.h +++ b/kernel/rcu/tree_plugin.h @@ -1776,7 +1776,10 @@ static void zero_cpu_stall_ticks(struct rcu_data *rdp) static int __init rcu_nocb_setup(char *str) { alloc_bootmem_cpumask_var(&rcu_nocb_mask); - cpulist_parse(str, rcu_nocb_mask); + if (!strcasecmp(str, "all")) + cpumask_setall(rcu_nocb_mask); + else + cpulist_parse(str, rcu_nocb_mask); return 1; } __setup("rcu_nocbs=", rcu_nocb_setup); -- cgit v1.2.3 From 2291da5b4d305a6506d915d5bef85dedd7c94882 Mon Sep 17 00:00:00 2001 From: Dmitry Torokhov Date: Fri, 18 Jan 2019 13:37:40 -0800 Subject: [media] doc-rst: switch to new names for Full Screen/Aspect keys We defined better names for keys to activate full screen mode or change aspect ratio (while keeping the existing keycodes to avoid breaking userspace), so let's use them in the document. Signed-off-by: Dmitry Torokhov --- Documentation/media/uapi/rc/rc-tables.rst | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/media/uapi/rc/rc-tables.rst b/Documentation/media/uapi/rc/rc-tables.rst index c8ae9479f842..57797e56f45e 100644 --- a/Documentation/media/uapi/rc/rc-tables.rst +++ b/Documentation/media/uapi/rc/rc-tables.rst @@ -616,7 +616,7 @@ the remote via /dev/input/event devices. - .. row 78 - - ``KEY_SCREEN`` + - ``KEY_ASPECT_RATIO`` - Select screen aspect ratio @@ -624,7 +624,7 @@ the remote via /dev/input/event devices. - .. row 79 - - ``KEY_ZOOM`` + - ``KEY_FULL_SCREEN`` - Put device into zoom/full screen mode -- cgit v1.2.3 From d2a6cfdaca9eba061fba08ce9e8866ed500a948d Mon Sep 17 00:00:00 2001 From: Douglas Anderson Date: Mon, 25 Mar 2019 09:20:04 -0700 Subject: dt-bindings: ARM: dts: rockchip: Add bindings for rk3288-veyron-mighty Mighty is basically the same Chromebook as Jaq but it has a full-sized SD slot and some different (slightly more rugged) plastics around it. Like Jaq, Mighty may show up with various different brandings but all of them have the same board inside. Signed-off-by: Douglas Anderson Reviewed-by: Rob Herring Signed-off-by: Heiko Stuebner --- Documentation/devicetree/bindings/arm/rockchip.yaml | 13 ++++++++++++- 1 file changed, 12 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/rockchip.yaml b/Documentation/devicetree/bindings/arm/rockchip.yaml index 81bc2a4138f2..66d2f69e400d 100644 --- a/Documentation/devicetree/bindings/arm/rockchip.yaml +++ b/Documentation/devicetree/bindings/arm/rockchip.yaml @@ -146,7 +146,7 @@ properties: - const: google,gru - const: rockchip,rk3399 - - description: Google Jaq (Haier Chromebook 11 and more) + - description: Google Jaq (Haier Chromebook 11 and more w/ uSD) items: - const: google,veyron-jaq-rev5 - const: google,veyron-jaq-rev4 @@ -205,6 +205,17 @@ properties: - const: google,veyron - const: rockchip,rk3288 + - description: Google Mighty (Haier Chromebook 11 and more w/ SD) + items: + - const: google,veyron-mighty-rev5 + - const: google,veyron-mighty-rev4 + - const: google,veyron-mighty-rev3 + - const: google,veyron-mighty-rev2 + - const: google,veyron-mighty-rev1 + - const: google,veyron-mighty + - const: google,veyron + - const: rockchip,rk3288 + - description: Google Minnie (Asus Chromebook Flip C100P) items: - const: google,veyron-minnie-rev4 -- cgit v1.2.3 From 984df54e4304d1ebe3e2320a9750b12236f14f0a Mon Sep 17 00:00:00 2001 From: Lanqing Liu Date: Mon, 4 Mar 2019 16:58:21 +0800 Subject: dt-bindings: serial: sprd: Add clocks and clocks-names properties This patch adds clocks and clocks-names properties, which are used to do power management for our UART driver. Reviewed-by: Rob Herring Signed-off-by: Lanqing Liu Signed-off-by: Baolin Wang Signed-off-by: Greg Kroah-Hartman --- Documentation/devicetree/bindings/serial/sprd-uart.txt | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/serial/sprd-uart.txt b/Documentation/devicetree/bindings/serial/sprd-uart.txt index cab40f0f6f49..6eb5863aa548 100644 --- a/Documentation/devicetree/bindings/serial/sprd-uart.txt +++ b/Documentation/devicetree/bindings/serial/sprd-uart.txt @@ -7,7 +7,13 @@ Required properties: - reg: offset and length of the register set for the device - interrupts: exactly one interrupt specifier -- clocks: phandles to input clocks. +- clock-names: Should contain following entries: + "enable" for UART module enable clock, + "uart" for UART clock, + "source" for UART source (parent) clock. +- clocks: Should contain a clock specifier for each entry in clock-names. + UART clock and source clock are optional properties, but enable clock + is required. Example: uart0: serial@0 { @@ -15,5 +21,6 @@ Example: "sprd,sc9836-uart"; reg = <0x0 0x100>; interrupts = ; - clocks = <&ext_26m>; + clock-names = "enable", "uart", "source"; + clocks = <&clk_ap_apb_gates 9>, <&clk_uart0>, <&ext_26m>; }; -- cgit v1.2.3 From 083206100d971b457dc6a942748bdb3ccc72c947 Mon Sep 17 00:00:00 2001 From: Lanqing Liu Date: Mon, 4 Mar 2019 16:58:23 +0800 Subject: dt-bindings: serial: sprd: Add dma properties to support DMA mode This patch adds dmas and dma-names properties for the UART DMA mode. Signed-off-by: Lanqing Liu Signed-off-by: Baolin Wang Reviewed-by: Rob Herring Signed-off-by: Greg Kroah-Hartman --- Documentation/devicetree/bindings/serial/sprd-uart.txt | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/serial/sprd-uart.txt b/Documentation/devicetree/bindings/serial/sprd-uart.txt index 6eb5863aa548..9607dc616205 100644 --- a/Documentation/devicetree/bindings/serial/sprd-uart.txt +++ b/Documentation/devicetree/bindings/serial/sprd-uart.txt @@ -15,12 +15,18 @@ Required properties: UART clock and source clock are optional properties, but enable clock is required. +Optional properties: +- dma-names: Should contain "rx" for receive and "tx" for transmit channels. +- dmas: A list of dma specifiers, one for each entry in dma-names. + Example: uart0: serial@0 { compatible = "sprd,sc9860-uart", "sprd,sc9836-uart"; reg = <0x0 0x100>; interrupts = ; + dma-names = "rx", "tx"; + dmas = <&ap_dma 19>, <&ap_dma 20>; clock-names = "enable", "uart", "source"; clocks = <&clk_ap_apb_gates 9>, <&clk_uart0>, <&ext_26m>; }; -- cgit v1.2.3 From 8650e026c819f4b6dfc1bee078498a92a0f5a223 Mon Sep 17 00:00:00 2001 From: Andy Shevchenko Date: Mon, 18 Mar 2019 12:29:14 +0200 Subject: dt-bindings: sc16is7xx: Add alternative clock-frequency property For the platforms which have no clock provider for the sc16is7xx type of UART, introduce an alternative clock-frequency property which would be used instead. Cc: Rob Herring Cc: devicetree@vger.kernel.org Signed-off-by: Andy Shevchenko Signed-off-by: Greg Kroah-Hartman --- Documentation/devicetree/bindings/serial/nxp,sc16is7xx.txt | 2 ++ 1 file changed, 2 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/serial/nxp,sc16is7xx.txt b/Documentation/devicetree/bindings/serial/nxp,sc16is7xx.txt index e7921a8e276b..c1091a923a89 100644 --- a/Documentation/devicetree/bindings/serial/nxp,sc16is7xx.txt +++ b/Documentation/devicetree/bindings/serial/nxp,sc16is7xx.txt @@ -12,6 +12,8 @@ Required properties: - reg: I2C address of the SC16IS7xx device. - interrupts: Should contain the UART interrupt - clocks: Reference to the IC source clock. + OR (when there is no clock provider visible to the platform) +- clock-frequency: The source clock frequency for the IC. Optional properties: - gpio-controller: Marks the device node as a GPIO controller. -- cgit v1.2.3 From 1755ecedc485e8a898ac27b90be664784ddb6b57 Mon Sep 17 00:00:00 2001 From: "Paul E. McKenney" Date: Wed, 9 Jan 2019 14:50:29 -0800 Subject: doc/kprobes: Update obsolete RCU update functions The RCU flavors have been consolidated, so this commit replaces mentions of the now-obsolete synchronize_sched() function with synchronize_rcu(). Signed-off-by: Paul E. McKenney Cc: "Naveen N. Rao" Cc: Anil S Keshavamurthy Cc: "David S. Miller" Cc: Jonathan Corbet Cc: Acked-by: Masami Hiramatsu --- Documentation/kprobes.txt | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/kprobes.txt b/Documentation/kprobes.txt index 10f4499e677c..ee60e519438a 100644 --- a/Documentation/kprobes.txt +++ b/Documentation/kprobes.txt @@ -243,10 +243,10 @@ Optimization ^^^^^^^^^^^^ The Kprobe-optimizer doesn't insert the jump instruction immediately; -rather, it calls synchronize_sched() for safety first, because it's +rather, it calls synchronize_rcu() for safety first, because it's possible for a CPU to be interrupted in the middle of executing the -optimized region [3]_. As you know, synchronize_sched() can ensure -that all interruptions that were active when synchronize_sched() +optimized region [3]_. As you know, synchronize_rcu() can ensure +that all interruptions that were active when synchronize_rcu() was called are done, but only if CONFIG_PREEMPT=n. So, this version of kprobe optimization supports only kernels with CONFIG_PREEMPT=n [4]_. -- cgit v1.2.3 From d6e5a4f84e2882f95b088c20995aba73e90e35fd Mon Sep 17 00:00:00 2001 From: Amit Kucheria Date: Wed, 12 Dec 2018 15:47:54 +0530 Subject: dt-bindings: iio: adc: Add binding for ADC on pms405 PMIC PMS405 contains a variant of the spmi-adc-rev2 ADC. Create a new compatible inorder to handle any differences. Reviewed-by: Rob Herring Signed-off-by: Amit Kucheria Signed-off-by: Bjorn Andersson Signed-off-by: Andy Gross --- Documentation/devicetree/bindings/iio/adc/qcom,spmi-vadc.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/adc/qcom,spmi-vadc.txt b/Documentation/devicetree/bindings/iio/adc/qcom,spmi-vadc.txt index c81993f8d8c3..c8787688122a 100644 --- a/Documentation/devicetree/bindings/iio/adc/qcom,spmi-vadc.txt +++ b/Documentation/devicetree/bindings/iio/adc/qcom,spmi-vadc.txt @@ -13,6 +13,7 @@ VADC node: Definition: Should contain "qcom,spmi-vadc". Should contain "qcom,spmi-adc5" for PMIC5 ADC driver. Should contain "qcom,spmi-adc-rev2" for PMIC rev2 ADC driver. + Should contain "qcom,pms405-adc" for PMS405 PMIC - reg: Usage: required -- cgit v1.2.3 From cb79a81fd98fc485a9d0506391ad197791ba023f Mon Sep 17 00:00:00 2001 From: Marc Gonzalez Date: Mon, 25 Feb 2019 13:17:02 +0100 Subject: dt-bindings: ufs: Add msm8998 compatible string Add "qcom,msm8998-ufshc" compatible string. Tested-by: Lee Jones Signed-off-by: Marc Gonzalez Signed-off-by: Bjorn Andersson Signed-off-by: Andy Gross --- Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt b/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt index 5111e9130bc3..991e21ee7b44 100644 --- a/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt +++ b/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt @@ -11,6 +11,7 @@ Required properties: the appropriate jedec string: "qcom,msm8994-ufshc", "qcom,ufshc", "jedec,ufs-2.0" "qcom,msm8996-ufshc", "qcom,ufshc", "jedec,ufs-2.0" + "qcom,msm8998-ufshc", "qcom,ufshc", "jedec,ufs-2.0" "qcom,sdm845-ufshc", "qcom,ufshc", "jedec,ufs-2.0" - interrupts : - reg : -- cgit v1.2.3 From 4d720e2a8c5f5829ca6d79e02f653ca8b1470b8b Mon Sep 17 00:00:00 2001 From: Thomas Preston Date: Mon, 25 Mar 2019 16:53:38 +0000 Subject: Documentation: acpi: Add an example for PRP0001 Add an example for the magic PRP0001 device ID which allows matching ACPI devices against drivers using OF Device Tree compatible property. Signed-off-by: Thomas Preston Reviewed-by: Andy Shevchenko Acked-by: Mika Westerberg Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/enumeration.txt | 26 ++++++++++++++++++++++++++ 1 file changed, 26 insertions(+) (limited to 'Documentation') diff --git a/Documentation/acpi/enumeration.txt b/Documentation/acpi/enumeration.txt index 7bcf9c3d9fbe..1395b844649c 100644 --- a/Documentation/acpi/enumeration.txt +++ b/Documentation/acpi/enumeration.txt @@ -410,6 +410,32 @@ Specifically, the device IDs returned by _HID and preceding PRP0001 in the _CID return package will be checked first. Also in that case the bus type the device will be enumerated to depends on the device ID returned by _HID. +For example, the following ACPI sample might be used to enumerate an lm75-type +I2C temperature sensor and match it to the driver using the Device Tree +namespace link: + + Device (TMP0) + { + Name (_HID, "PRP0001") + Name (_DSD, Package() { + ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), + Package () { + Package (2) { "compatible", "ti,tmp75" }, + } + }) + Method (_CRS, 0, Serialized) + { + Name (SBUF, ResourceTemplate () + { + I2cSerialBusV2 (0x48, ControllerInitiated, + 400000, AddressingMode7Bit, + "\\_SB.PCI0.I2C1", 0x00, + ResourceConsumer, , Exclusive,) + }) + Return (SBUF) + } + } + It is valid to define device objects with a _HID returning PRP0001 and without the "compatible" property in the _DSD or a _CID as long as one of their ancestors provides a _DSD with a valid "compatible" property. Such device -- cgit v1.2.3 From db9630273f90a328eabef48fe46589b6af3f8ab9 Mon Sep 17 00:00:00 2001 From: Claudiu Beznea Date: Thu, 14 Feb 2019 15:54:37 +0000 Subject: dt-bindings: arm: atmel: add binding for SAM9X60 SoC Add device tree binding for SAM9X60 SoC. Signed-off-by: Claudiu Beznea Signed-off-by: Alexandre Belloni Signed-off-by: Ludovic Desroches --- Documentation/devicetree/bindings/arm/atmel-at91.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/atmel-at91.txt b/Documentation/devicetree/bindings/arm/atmel-at91.txt index 4bf1b4da7659..99dee23c74a4 100644 --- a/Documentation/devicetree/bindings/arm/atmel-at91.txt +++ b/Documentation/devicetree/bindings/arm/atmel-at91.txt @@ -25,6 +25,7 @@ compatible: must be one of: o "atmel,at91sam9n12" o "atmel,at91sam9rl" o "atmel,at91sam9xe" + o "microchip,sam9x60" * "atmel,sama5" for SoCs using a Cortex-A5, shall be extended with the specific SoC family: o "atmel,sama5d2" shall be extended with the specific SoC compatible: -- cgit v1.2.3 From 82d1c7a1e8c043e8be6d0d7c65d6617c4e084177 Mon Sep 17 00:00:00 2001 From: Andrey Smirnov Date: Mon, 25 Mar 2019 11:22:41 -0700 Subject: dt-bindings: arm: fsl: Add supported ZII VF610 boards to DT schema Add already supported ZII VF610 boards to DT schema. Signed-off-by: Andrey Smirnov Cc: Shawn Guo Cc: Chris Healy Cc: Andrew Lunn Cc: Fabio Estevam Cc: Rob Herring Cc: linux-arm-kernel@lists.infradead.org Cc: linux-kernel@vger.kernel.org Cc: devicetree@vger.kernel.org Reviewed-by: Rob Herring Signed-off-by: Shawn Guo --- Documentation/devicetree/bindings/arm/fsl.yaml | 12 ++++++++++++ 1 file changed, 12 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/fsl.yaml b/Documentation/devicetree/bindings/arm/fsl.yaml index b06aa2b94fe2..d15258e52ac5 100644 --- a/Documentation/devicetree/bindings/arm/fsl.yaml +++ b/Documentation/devicetree/bindings/arm/fsl.yaml @@ -183,6 +183,18 @@ properties: - fsl,vf610 - fsl,vf610m4 + - description: ZII's VF610 based Boards + items: + - enum: + - zii,vf610cfu1 # ZII VF610 CFU1 Board + - zii,vf610dev-c # ZII VF610 Development Board, Rev C + - zii,vf610dev-b # ZII VF610 Development Board, Rev B + - zii,vf610scu4-aib # ZII VF610 SCU4 AIB + - zii,vf610dtu # ZII VF610 SSMB DTU Board + - zii,vf610spu3 # ZII VF610 SSMB SPU3 Board + - const: zii,vf610dev + - const: fsl,vf610 + - description: LS1012A based Boards items: - enum: -- cgit v1.2.3 From 2bfad1f83eced545442fd2312963c4039c831a13 Mon Sep 17 00:00:00 2001 From: Andrey Smirnov Date: Mon, 25 Mar 2019 11:22:42 -0700 Subject: dt-bindings: arm: fsl: Add support for ZII VF610 SPB4 Add support for ZII VF610 SPB4. Signed-off-by: Andrey Smirnov Cc: Shawn Guo Cc: Chris Healy Cc: Andrew Lunn Cc: Fabio Estevam Cc: Rob Herring Cc: linux-arm-kernel@lists.infradead.org Cc: linux-kernel@vger.kernel.org Cc: devicetree@vger.kernel.org Reviewed-by: Rob Herring Signed-off-by: Shawn Guo --- Documentation/devicetree/bindings/arm/fsl.yaml | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/fsl.yaml b/Documentation/devicetree/bindings/arm/fsl.yaml index d15258e52ac5..3c7ad36ebd35 100644 --- a/Documentation/devicetree/bindings/arm/fsl.yaml +++ b/Documentation/devicetree/bindings/arm/fsl.yaml @@ -192,6 +192,7 @@ properties: - zii,vf610scu4-aib # ZII VF610 SCU4 AIB - zii,vf610dtu # ZII VF610 SSMB DTU Board - zii,vf610spu3 # ZII VF610 SSMB SPU3 Board + - zii,vf610spb4 # ZII VF610 SPB4 Board - const: zii,vf610dev - const: fsl,vf610 -- cgit v1.2.3 From fd3bc912d3d1ca3049beb9f905ee68df3b82282b Mon Sep 17 00:00:00 2001 From: Dave Martin Date: Fri, 28 Sep 2018 14:39:26 +0100 Subject: KVM: Documentation: Document arm64 core registers in detail Since the the sizes of individual members of the core arm64 registers vary, the list of register encodings that make sense is not a simple linear sequence. To clarify which encodings to use, this patch adds a brief list to the documentation. Signed-off-by: Dave Martin Reviewed-by: Julien Grall Reviewed-by: Peter Maydell Signed-off-by: Marc Zyngier --- Documentation/virtual/kvm/api.txt | 24 ++++++++++++++++++++++++ 1 file changed, 24 insertions(+) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/api.txt b/Documentation/virtual/kvm/api.txt index 7de9eee73fcd..2d4f7ce5e967 100644 --- a/Documentation/virtual/kvm/api.txt +++ b/Documentation/virtual/kvm/api.txt @@ -2107,6 +2107,30 @@ contains elements ranging from 32 to 128 bits. The index is a 32bit value in the kvm_regs structure seen as a 32bit array. 0x60x0 0000 0010 +Specifically: + Encoding Register Bits kvm_regs member +---------------------------------------------------------------- + 0x6030 0000 0010 0000 X0 64 regs.regs[0] + 0x6030 0000 0010 0002 X1 64 regs.regs[1] + ... + 0x6030 0000 0010 003c X30 64 regs.regs[30] + 0x6030 0000 0010 003e SP 64 regs.sp + 0x6030 0000 0010 0040 PC 64 regs.pc + 0x6030 0000 0010 0042 PSTATE 64 regs.pstate + 0x6030 0000 0010 0044 SP_EL1 64 sp_el1 + 0x6030 0000 0010 0046 ELR_EL1 64 elr_el1 + 0x6030 0000 0010 0048 SPSR_EL1 64 spsr[KVM_SPSR_EL1] (alias SPSR_SVC) + 0x6030 0000 0010 004a SPSR_ABT 64 spsr[KVM_SPSR_ABT] + 0x6030 0000 0010 004c SPSR_UND 64 spsr[KVM_SPSR_UND] + 0x6030 0000 0010 004e SPSR_IRQ 64 spsr[KVM_SPSR_IRQ] + 0x6060 0000 0010 0050 SPSR_FIQ 64 spsr[KVM_SPSR_FIQ] + 0x6040 0000 0010 0054 V0 128 fp_regs.vregs[0] + 0x6040 0000 0010 0058 V1 128 fp_regs.vregs[1] + ... + 0x6040 0000 0010 00d0 V31 128 fp_regs.vregs[31] + 0x6020 0000 0010 00d4 FPSR 32 fp_regs.fpsr + 0x6020 0000 0010 00d5 FPCR 32 fp_regs.fpcr + arm64 CCSIDR registers are demultiplexed by CSSELR value: 0x6020 0000 0011 00 -- cgit v1.2.3 From 395f562f2b4cf9aef0db540d460b859fcde110b6 Mon Sep 17 00:00:00 2001 From: Dave Martin Date: Tue, 15 Jan 2019 17:02:08 +0000 Subject: KVM: Document errors for KVM_GET_ONE_REG and KVM_SET_ONE_REG KVM_GET_ONE_REG and KVM_SET_ONE_REG return some error codes that are not documented (but hopefully not surprising either). To give an indication of what these may mean, this patch adds brief documentation. Signed-off-by: Dave Martin Signed-off-by: Marc Zyngier --- Documentation/virtual/kvm/api.txt | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/api.txt b/Documentation/virtual/kvm/api.txt index 2d4f7ce5e967..cd920dd1195c 100644 --- a/Documentation/virtual/kvm/api.txt +++ b/Documentation/virtual/kvm/api.txt @@ -1871,6 +1871,9 @@ Architectures: all Type: vcpu ioctl Parameters: struct kvm_one_reg (in) Returns: 0 on success, negative value on failure +Errors: +  ENOENT:   no such register +  EINVAL:   other errors, such as bad size encoding for a known register struct kvm_one_reg { __u64 id; @@ -2192,6 +2195,9 @@ Architectures: all Type: vcpu ioctl Parameters: struct kvm_one_reg (in and out) Returns: 0 on success, negative value on failure +Errors: +  ENOENT:   no such register +  EINVAL:   other errors, such as bad size encoding for a known register This ioctl allows to receive the value of a single register implemented in a vcpu. The register to read is indicated by the "id" field of the -- cgit v1.2.3 From 50036ad06b7f31f7312b43752185e37cf1d0b663 Mon Sep 17 00:00:00 2001 From: Dave Martin Date: Fri, 28 Sep 2018 14:39:27 +0100 Subject: KVM: arm64/sve: Document KVM API extensions for SVE This patch adds sections to the KVM API documentation describing the extensions for supporting the Scalable Vector Extension (SVE) in guests. Signed-off-by: Dave Martin Signed-off-by: Marc Zyngier --- Documentation/virtual/kvm/api.txt | 132 +++++++++++++++++++++++++++++++++++++- 1 file changed, 129 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/api.txt b/Documentation/virtual/kvm/api.txt index cd920dd1195c..68509dee23e8 100644 --- a/Documentation/virtual/kvm/api.txt +++ b/Documentation/virtual/kvm/api.txt @@ -1873,6 +1873,7 @@ Parameters: struct kvm_one_reg (in) Returns: 0 on success, negative value on failure Errors:  ENOENT:   no such register +  EPERM:    register access forbidden for architecture-dependent reasons  EINVAL:   other errors, such as bad size encoding for a known register struct kvm_one_reg { @@ -2127,13 +2128,20 @@ Specifically: 0x6030 0000 0010 004c SPSR_UND 64 spsr[KVM_SPSR_UND] 0x6030 0000 0010 004e SPSR_IRQ 64 spsr[KVM_SPSR_IRQ] 0x6060 0000 0010 0050 SPSR_FIQ 64 spsr[KVM_SPSR_FIQ] - 0x6040 0000 0010 0054 V0 128 fp_regs.vregs[0] - 0x6040 0000 0010 0058 V1 128 fp_regs.vregs[1] + 0x6040 0000 0010 0054 V0 128 fp_regs.vregs[0] (*) + 0x6040 0000 0010 0058 V1 128 fp_regs.vregs[1] (*) ... - 0x6040 0000 0010 00d0 V31 128 fp_regs.vregs[31] + 0x6040 0000 0010 00d0 V31 128 fp_regs.vregs[31] (*) 0x6020 0000 0010 00d4 FPSR 32 fp_regs.fpsr 0x6020 0000 0010 00d5 FPCR 32 fp_regs.fpcr +(*) These encodings are not accepted for SVE-enabled vcpus. See + KVM_ARM_VCPU_INIT. + + The equivalent register content can be accessed via bits [127:0] of + the corresponding SVE Zn registers instead for vcpus that have SVE + enabled (see below). + arm64 CCSIDR registers are demultiplexed by CSSELR value: 0x6020 0000 0011 00 @@ -2143,6 +2151,61 @@ arm64 system registers have the following id bit patterns: arm64 firmware pseudo-registers have the following bit pattern: 0x6030 0000 0014 +arm64 SVE registers have the following bit patterns: + 0x6080 0000 0015 00 Zn bits[2048*slice + 2047 : 2048*slice] + 0x6050 0000 0015 04 Pn bits[256*slice + 255 : 256*slice] + 0x6050 0000 0015 060 FFR bits[256*slice + 255 : 256*slice] + 0x6060 0000 0015 ffff KVM_REG_ARM64_SVE_VLS pseudo-register + +Access to slices beyond the maximum vector length configured for the +vcpu (i.e., where 16 * slice >= max_vq (**)) will fail with ENOENT. + +These registers are only accessible on vcpus for which SVE is enabled. +See KVM_ARM_VCPU_INIT for details. + +In addition, except for KVM_REG_ARM64_SVE_VLS, these registers are not +accessible until the vcpu's SVE configuration has been finalized +using KVM_ARM_VCPU_FINALIZE(KVM_ARM_VCPU_SVE). See KVM_ARM_VCPU_INIT +and KVM_ARM_VCPU_FINALIZE for more information about this procedure. + +KVM_REG_ARM64_SVE_VLS is a pseudo-register that allows the set of vector +lengths supported by the vcpu to be discovered and configured by +userspace. When transferred to or from user memory via KVM_GET_ONE_REG +or KVM_SET_ONE_REG, the value of this register is of type __u64[8], and +encodes the set of vector lengths as follows: + +__u64 vector_lengths[8]; + +if (vq >= SVE_VQ_MIN && vq <= SVE_VQ_MAX && + ((vector_lengths[(vq - 1) / 64] >> ((vq - 1) % 64)) & 1)) + /* Vector length vq * 16 bytes supported */ +else + /* Vector length vq * 16 bytes not supported */ + +(**) The maximum value vq for which the above condition is true is +max_vq. This is the maximum vector length available to the guest on +this vcpu, and determines which register slices are visible through +this ioctl interface. + +(See Documentation/arm64/sve.txt for an explanation of the "vq" +nomenclature.) + +KVM_REG_ARM64_SVE_VLS is only accessible after KVM_ARM_VCPU_INIT. +KVM_ARM_VCPU_INIT initialises it to the best set of vector lengths that +the host supports. + +Userspace may subsequently modify it if desired until the vcpu's SVE +configuration is finalized using KVM_ARM_VCPU_FINALIZE(KVM_ARM_VCPU_SVE). + +Apart from simply removing all vector lengths from the host set that +exceed some value, support for arbitrarily chosen sets of vector lengths +is hardware-dependent and may not be available. Attempting to configure +an invalid set of vector lengths via KVM_SET_ONE_REG will fail with +EINVAL. + +After the vcpu's SVE configuration is finalized, further attempts to +write this register will fail with EPERM. + MIPS registers are mapped using the lower 32 bits. The upper 16 of that is the register group type: @@ -2197,6 +2260,7 @@ Parameters: struct kvm_one_reg (in and out) Returns: 0 on success, negative value on failure Errors:  ENOENT:   no such register +  EPERM:    register access forbidden for architecture-dependent reasons  EINVAL:   other errors, such as bad size encoding for a known register This ioctl allows to receive the value of a single register implemented @@ -2690,6 +2754,33 @@ Possible features: - KVM_ARM_VCPU_PMU_V3: Emulate PMUv3 for the CPU. Depends on KVM_CAP_ARM_PMU_V3. + - KVM_ARM_VCPU_SVE: Enables SVE for the CPU (arm64 only). + Depends on KVM_CAP_ARM_SVE. + Requires KVM_ARM_VCPU_FINALIZE(KVM_ARM_VCPU_SVE): + + * After KVM_ARM_VCPU_INIT: + + - KVM_REG_ARM64_SVE_VLS may be read using KVM_GET_ONE_REG: the + initial value of this pseudo-register indicates the best set of + vector lengths possible for a vcpu on this host. + + * Before KVM_ARM_VCPU_FINALIZE(KVM_ARM_VCPU_SVE): + + - KVM_RUN and KVM_GET_REG_LIST are not available; + + - KVM_GET_ONE_REG and KVM_SET_ONE_REG cannot be used to access + the scalable archietctural SVE registers + KVM_REG_ARM64_SVE_ZREG(), KVM_REG_ARM64_SVE_PREG() or + KVM_REG_ARM64_SVE_FFR; + + - KVM_REG_ARM64_SVE_VLS may optionally be written using + KVM_SET_ONE_REG, to modify the set of vector lengths available + for the vcpu. + + * After KVM_ARM_VCPU_FINALIZE(KVM_ARM_VCPU_SVE): + + - the KVM_REG_ARM64_SVE_VLS pseudo-register is immutable, and can + no longer be written using KVM_SET_ONE_REG. 4.83 KVM_ARM_PREFERRED_TARGET @@ -3904,6 +3995,41 @@ number of valid entries in the 'entries' array, which is then filled. 'index' and 'flags' fields in 'struct kvm_cpuid_entry2' are currently reserved, userspace should not expect to get any particular value there. +4.119 KVM_ARM_VCPU_FINALIZE + +Capability: KVM_CAP_ARM_SVE +Architectures: arm, arm64 +Type: vcpu ioctl +Parameters: int feature (in) +Returns: 0 on success, -1 on error +Errors: + EPERM: feature not enabled, needs configuration, or already finalized + EINVAL: unknown feature + +Recognised values for feature: + arm64 KVM_ARM_VCPU_SVE + +Finalizes the configuration of the specified vcpu feature. + +The vcpu must already have been initialised, enabling the affected feature, by +means of a successful KVM_ARM_VCPU_INIT call with the appropriate flag set in +features[]. + +For affected vcpu features, this is a mandatory step that must be performed +before the vcpu is fully usable. + +Between KVM_ARM_VCPU_INIT and KVM_ARM_VCPU_FINALIZE, the feature may be +configured by use of ioctls such as KVM_SET_ONE_REG. The exact configuration +that should be performaned and how to do it are feature-dependent. + +Other calls that depend on a particular feature being finalized, such as +KVM_RUN, KVM_GET_REG_LIST, KVM_GET_ONE_REG and KVM_SET_ONE_REG, will fail with +-EPERM unless the feature has already been finalized by means of a +KVM_ARM_VCPU_FINALIZE call. + +See KVM_ARM_VCPU_INIT for details of vcpu features that require finalization +using this ioctl. + 5. The kvm_run structure ------------------------ -- cgit v1.2.3 From 8b0a61d1f72e75e43aaebd52d7bc89e9899cdb5f Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Fri, 29 Mar 2019 11:58:14 -0400 Subject: media: pixfmt-packed-yuv.rst: fix PDF output Some lines inside this table has more than 34 columns, which isn't what is expected, according to the .. tabularcolumns:: definition. That causes the PDF output to fail. This patch ensures that all columns will have exactly the same size, merging the unused ones using :cpan: Signed-off-by: Mauro Carvalho Chehab --- Documentation/media/uapi/v4l/pixfmt-packed-yuv.rst | 21 ++++++++++++++------- 1 file changed, 14 insertions(+), 7 deletions(-) (limited to 'Documentation') diff --git a/Documentation/media/uapi/v4l/pixfmt-packed-yuv.rst b/Documentation/media/uapi/v4l/pixfmt-packed-yuv.rst index 7fcee1c11ac4..9d2b281f06a2 100644 --- a/Documentation/media/uapi/v4l/pixfmt-packed-yuv.rst +++ b/Documentation/media/uapi/v4l/pixfmt-packed-yuv.rst @@ -44,6 +44,7 @@ component of each pixel in one 16 or 32 bit word. - :cspan:`7` Byte 2 - :cspan:`7` Byte 3 + * - - - 7 @@ -81,6 +82,7 @@ component of each pixel in one 16 or 32 bit word. - 2 - 1 - 0 + * .. _V4L2-PIX-FMT-YUV444: - ``V4L2_PIX_FMT_YUV444`` @@ -103,7 +105,9 @@ component of each pixel in one 16 or 32 bit word. - Y'\ :sub:`2` - Y'\ :sub:`1` - Y'\ :sub:`0` - - + + - :cspan:`15` + * .. _V4L2-PIX-FMT-YUV555: - ``V4L2_PIX_FMT_YUV555`` @@ -126,7 +130,8 @@ component of each pixel in one 16 or 32 bit word. - Y'\ :sub:`0` - Cb\ :sub:`4` - Cb\ :sub:`3` - - + + - :cspan:`15` * .. _V4L2-PIX-FMT-YUV565: - ``V4L2_PIX_FMT_YUV565`` @@ -149,7 +154,9 @@ component of each pixel in one 16 or 32 bit word. - Cb\ :sub:`5` - Cb\ :sub:`4` - Cb\ :sub:`3` - - + + - :cspan:`15` + * .. _V4L2-PIX-FMT-YUV32: - ``V4L2_PIX_FMT_YUV32`` @@ -190,7 +197,7 @@ component of each pixel in one 16 or 32 bit word. - Cr\ :sub:`2` - Cr\ :sub:`1` - Cr\ :sub:`0` - - + * .. _V4L2-PIX-FMT-AYUV32: - ``V4L2_PIX_FMT_AYUV32`` @@ -231,7 +238,7 @@ component of each pixel in one 16 or 32 bit word. - Cr\ :sub:`2` - Cr\ :sub:`1` - Cr\ :sub:`0` - - + * .. _V4L2-PIX-FMT-XYUV32: - ``V4L2_PIX_FMT_XYUV32`` @@ -272,7 +279,7 @@ component of each pixel in one 16 or 32 bit word. - Cr\ :sub:`2` - Cr\ :sub:`1` - Cr\ :sub:`0` - - + * .. _V4L2-PIX-FMT-VUYA32: - ``V4L2_PIX_FMT_VUYA32`` @@ -313,7 +320,7 @@ component of each pixel in one 16 or 32 bit word. - a\ :sub:`2` - a\ :sub:`1` - a\ :sub:`0` - - + * .. _V4L2-PIX-FMT-VUYX32: - ``V4L2_PIX_FMT_VUYX32`` -- cgit v1.2.3 From 94fa831e3b359f24c01b9936de33b84c38caacbb Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Fri, 29 Mar 2019 12:13:50 -0400 Subject: media: pdf docs: adjust several tables for better display Avoid cell overlapping by changing some sizes, and changing the font sizes when needed. Tested with Sphinx 1.7.8. Signed-off-by: Mauro Carvalho Chehab --- Documentation/media/uapi/v4l/buffer.rst | 19 +++-- Documentation/media/uapi/v4l/colorspaces-defs.rst | 4 +- Documentation/media/uapi/v4l/colorspaces.rst | 4 +- Documentation/media/uapi/v4l/dev-raw-vbi.rst | 4 +- Documentation/media/uapi/v4l/dev-rds.rst | 2 +- Documentation/media/uapi/v4l/dev-sliced-vbi.rst | 22 +++--- Documentation/media/uapi/v4l/dev-subdev.rst | 82 +++++++++++++++----- Documentation/media/uapi/v4l/ext-ctrls-camera.rst | 17 +++-- Documentation/media/uapi/v4l/ext-ctrls-codec.rst | 89 +++++++++++++++++++--- Documentation/media/uapi/v4l/ext-ctrls-detect.rst | 2 +- Documentation/media/uapi/v4l/ext-ctrls-dv.rst | 2 +- Documentation/media/uapi/v4l/ext-ctrls-flash.rst | 4 +- Documentation/media/uapi/v4l/ext-ctrls-jpeg.rst | 2 +- Documentation/media/uapi/v4l/field-order.rst | 4 +- Documentation/media/uapi/v4l/pixfmt-meta-d4xx.rst | 9 ++- .../media/uapi/v4l/pixfmt-meta-vsp1-hgt.rst | 9 +++ Documentation/media/uapi/v4l/pixfmt-packed-hsv.rst | 2 +- Documentation/media/uapi/v4l/pixfmt-packed-rgb.rst | 4 +- Documentation/media/uapi/v4l/pixfmt-packed-yuv.rst | 2 +- Documentation/media/uapi/v4l/pixfmt-srggb10p.rst | 2 +- Documentation/media/uapi/v4l/pixfmt-srggb12p.rst | 3 +- Documentation/media/uapi/v4l/pixfmt-srggb14p.rst | 24 +++++- .../media/uapi/v4l/pixfmt-v4l2-mplane.rst | 17 +++-- Documentation/media/uapi/v4l/pixfmt-y10p.rst | 10 +++ Documentation/media/uapi/v4l/subdev-formats.rst | 6 +- 25 files changed, 258 insertions(+), 87 deletions(-) (limited to 'Documentation') diff --git a/Documentation/media/uapi/v4l/buffer.rst b/Documentation/media/uapi/v4l/buffer.rst index b9a2e9dc707c..1cbd9cde57f3 100644 --- a/Documentation/media/uapi/v4l/buffer.rst +++ b/Documentation/media/uapi/v4l/buffer.rst @@ -165,7 +165,7 @@ of appropriately sized buffers for each use case). struct v4l2_buffer ================== -.. tabularcolumns:: |p{2.8cm}|p{2.5cm}|p{1.3cm}|p{10.5cm}| +.. tabularcolumns:: |p{2.8cm}|p{2.5cm}|p{1.6cm}|p{10.2cm}| .. cssclass:: longtable @@ -420,7 +420,7 @@ enum v4l2_buf_type .. cssclass:: longtable -.. tabularcolumns:: |p{7.2cm}|p{0.6cm}|p{9.7cm}| +.. tabularcolumns:: |p{7.8cm}|p{0.6cm}|p{9.1cm}| .. flat-table:: :header-rows: 0 @@ -482,7 +482,11 @@ enum v4l2_buf_type Buffer Flags ============ -.. tabularcolumns:: |p{7.0cm}|p{2.2cm}|p{8.3cm}| +.. raw:: latex + + \small + +.. tabularcolumns:: |p{7.0cm}|p{2.1cm}|p{8.4cm}| .. cssclass:: longtable @@ -681,6 +685,9 @@ Buffer Flags exposure of the frame has begun. This is only valid for the ``V4L2_BUF_TYPE_VIDEO_CAPTURE`` buffer type. +.. raw:: latex + + \normalsize .. c:type:: v4l2_memory @@ -688,7 +695,7 @@ Buffer Flags enum v4l2_memory ================ -.. tabularcolumns:: |p{6.6cm}|p{2.2cm}|p{8.7cm}| +.. tabularcolumns:: |p{5.0cm}|p{0.8cm}|p{11.7cm}| .. flat-table:: :header-rows: 0 @@ -724,7 +731,7 @@ The :c:type:`v4l2_buffer_timecode` structure is designed to hold a struct v4l2_timecode -------------------- -.. tabularcolumns:: |p{4.4cm}|p{4.4cm}|p{8.7cm}| +.. tabularcolumns:: |p{1.4cm}|p{2.8cm}|p{12.3cm}| .. flat-table:: :header-rows: 0 @@ -761,7 +768,7 @@ struct v4l2_timecode Timecode Types -------------- -.. tabularcolumns:: |p{6.6cm}|p{2.2cm}|p{8.7cm}| +.. tabularcolumns:: |p{5.6cm}|p{0.8cm}|p{11.1cm}| .. flat-table:: :header-rows: 0 diff --git a/Documentation/media/uapi/v4l/colorspaces-defs.rst b/Documentation/media/uapi/v4l/colorspaces-defs.rst index c4e8fc620379..e122bbe3d799 100644 --- a/Documentation/media/uapi/v4l/colorspaces-defs.rst +++ b/Documentation/media/uapi/v4l/colorspaces-defs.rst @@ -39,7 +39,7 @@ whole range, 0-255, dividing the angular value by 1.41. The enum colorspaces except for BT.2020 which uses limited range R'G'B' quantization. -.. tabularcolumns:: |p{6.0cm}|p{11.5cm}| +.. tabularcolumns:: |p{6.7cm}|p{10.8cm}| .. c:type:: v4l2_colorspace @@ -112,7 +112,7 @@ whole range, 0-255, dividing the angular value by 1.41. The enum .. c:type:: v4l2_ycbcr_encoding -.. tabularcolumns:: |p{6.5cm}|p{11.0cm}| +.. tabularcolumns:: |p{7.2cm}|p{10.3cm}| .. flat-table:: V4L2 Y'CbCr Encodings :header-rows: 1 diff --git a/Documentation/media/uapi/v4l/colorspaces.rst b/Documentation/media/uapi/v4l/colorspaces.rst index c5a560f0c13d..4f6c82fa057f 100644 --- a/Documentation/media/uapi/v4l/colorspaces.rst +++ b/Documentation/media/uapi/v4l/colorspaces.rst @@ -56,9 +56,9 @@ The Y value in the CIE XYZ colorspace corresponds to luminance. Often the CIE XYZ colorspace is transformed to the normalized CIE xyY colorspace: -x = X / (X + Y + Z) + x = X / (X + Y + Z) -y = Y / (X + Y + Z) + y = Y / (X + Y + Z) The x and y values are the chromaticity coordinates and can be used to define a color without the luminance component Y. It is very confusing diff --git a/Documentation/media/uapi/v4l/dev-raw-vbi.rst b/Documentation/media/uapi/v4l/dev-raw-vbi.rst index d6a707f0b24f..e06b03ca2ab2 100644 --- a/Documentation/media/uapi/v4l/dev-raw-vbi.rst +++ b/Documentation/media/uapi/v4l/dev-raw-vbi.rst @@ -106,7 +106,7 @@ VBI devices must implement both the :ref:`VIDIOC_G_FMT ` and and always returns default parameters as :ref:`VIDIOC_G_FMT ` does. :ref:`VIDIOC_TRY_FMT ` is optional. -.. tabularcolumns:: |p{2.4cm}|p{4.4cm}|p{10.7cm}| +.. tabularcolumns:: |p{1.6cm}|p{4.2cm}|p{11.7cm}| .. c:type:: v4l2_vbi_format @@ -190,7 +190,7 @@ and always returns default parameters as :ref:`VIDIOC_G_FMT ` does applications must set it to zero. -.. tabularcolumns:: |p{4.0cm}|p{1.5cm}|p{12.0cm}| +.. tabularcolumns:: |p{4.4cm}|p{1.5cm}|p{11.6cm}| .. _vbifmt-flags: diff --git a/Documentation/media/uapi/v4l/dev-rds.rst b/Documentation/media/uapi/v4l/dev-rds.rst index 624d6f95b842..64a724ef58f5 100644 --- a/Documentation/media/uapi/v4l/dev-rds.rst +++ b/Documentation/media/uapi/v4l/dev-rds.rst @@ -146,7 +146,7 @@ RDS datastructures .. _v4l2-rds-block-codes: -.. tabularcolumns:: |p{5.6cm}|p{2.0cm}|p{1.5cm}|p{7.0cm}| +.. tabularcolumns:: |p{6.4cm}|p{2.0cm}|p{1.2cm}|p{7.9cm}| .. flat-table:: Block defines :header-rows: 0 diff --git a/Documentation/media/uapi/v4l/dev-sliced-vbi.rst b/Documentation/media/uapi/v4l/dev-sliced-vbi.rst index 0aa6cb8a272b..e86346f66017 100644 --- a/Documentation/media/uapi/v4l/dev-sliced-vbi.rst +++ b/Documentation/media/uapi/v4l/dev-sliced-vbi.rst @@ -118,7 +118,7 @@ struct v4l2_sliced_vbi_format \scriptsize \setlength{\tabcolsep}{2pt} -.. tabularcolumns:: |p{.75cm}|p{3.3cm}|p{3.4cm}|p{3.4cm}|p{3.4cm}| +.. tabularcolumns:: |p{.85cm}|p{3.3cm}|p{4.4cm}|p{4.4cm}|p{4.4cm}| .. cssclass:: longtable @@ -223,7 +223,7 @@ Sliced VBI services .. raw:: latex - \footnotesize + \scriptsize .. tabularcolumns:: |p{4.1cm}|p{1.1cm}|p{2.4cm}|p{2.0cm}|p{7.3cm}| @@ -541,7 +541,7 @@ Magic Constants for struct v4l2_mpeg_vbi_fmt_ivtv magic field structs v4l2_mpeg_vbi_itv0 and v4l2_mpeg_vbi_ITV0 ------------------------------------------------- -.. tabularcolumns:: |p{4.9cm}|p{2.4cm}|p{10.2cm}| +.. tabularcolumns:: |p{5.2cm}|p{2.4cm}|p{9.9cm}| .. flat-table:: :header-rows: 0 @@ -561,12 +561,12 @@ structs v4l2_mpeg_vbi_itv0 and v4l2_mpeg_vbi_ITV0 :: - linemask[0] b0: line 6 first field - linemask[0] b17: line 23 first field - linemask[0] b18: line 6 second field - linemask[0] b31: line 19 second field - linemask[1] b0: line 20 second field - linemask[1] b3: line 23 second field + linemask[0] b0: line 6 first field + linemask[0] b17: line 23 first field + linemask[0] b18: line 6 second field + linemask[0] b31: line 19 second field + linemask[1] b0: line 20 second field + linemask[1] b3: line 23 second field linemask[1] b4-b31: unused and set to 0 * - struct :c:type:`v4l2_mpeg_vbi_itv0_line` @@ -590,7 +590,7 @@ structs v4l2_mpeg_vbi_itv0 and v4l2_mpeg_vbi_ITV0 struct v4l2_mpeg_vbi_ITV0 ------------------------- -.. tabularcolumns:: |p{4.9cm}|p{4.4cm}|p{8.2cm}| +.. tabularcolumns:: |p{5.2cm}|p{2.4cm}|p{9.9cm}| .. flat-table:: :header-rows: 0 @@ -635,7 +635,7 @@ struct v4l2_mpeg_vbi_itv0_line Line Identifiers for struct v4l2_mpeg_vbi_itv0_line id field ------------------------------------------------------------ -.. tabularcolumns:: |p{6.6cm}|p{2.2cm}|p{8.7cm}| +.. tabularcolumns:: |p{7.0cm}|p{1.8cm}|p{8.7cm}| .. flat-table:: :header-rows: 1 diff --git a/Documentation/media/uapi/v4l/dev-subdev.rst b/Documentation/media/uapi/v4l/dev-subdev.rst index 2c2768c7343b..029bb2d9928a 100644 --- a/Documentation/media/uapi/v4l/dev-subdev.rst +++ b/Documentation/media/uapi/v4l/dev-subdev.rst @@ -211,7 +211,7 @@ list entity names and pad numbers). .. raw:: latex - \tiny + \scriptsize .. tabularcolumns:: |p{2.0cm}|p{2.3cm}|p{2.3cm}|p{2.3cm}|p{2.3cm}|p{2.3cm}|p{2.3cm}| @@ -223,40 +223,80 @@ list entity names and pad numbers). :widths: 5 5 5 5 5 5 5 * - - - Sensor/0 format - - Frontend/0 format - - Frontend/1 format - - Scaler/0 format - - Scaler/0 compose selection rectangle - - Scaler/1 format + - Sensor/0 + + format + - Frontend/0 + + format + - Frontend/1 + + format + - Scaler/0 + + format + - Scaler/0 + + compose selection rectangle + - Scaler/1 + + format * - Initial state - - 2048x1536/SGRBG8_1X8 + - 2048x1536 + + SGRBG8_1X8 - (default) - (default) - (default) - (default) - (default) * - Configure frontend sink format - - 2048x1536/SGRBG8_1X8 - - *2048x1536/SGRBG8_1X8* - - *2046x1534/SGRBG8_1X8* + - 2048x1536 + + SGRBG8_1X8 + - *2048x1536* + + *SGRBG8_1X8* + - *2046x1534* + + *SGRBG8_1X8* - (default) - (default) - (default) * - Configure scaler sink format - - 2048x1536/SGRBG8_1X8 - - 2048x1536/SGRBG8_1X8 - - 2046x1534/SGRBG8_1X8 - - *2046x1534/SGRBG8_1X8* + - 2048x1536 + + SGRBG8_1X8 + - 2048x1536 + + SGRBG8_1X8 + - 2046x1534 + + SGRBG8_1X8 + - *2046x1534* + + *SGRBG8_1X8* - *0,0/2046x1534* - - *2046x1534/SGRBG8_1X8* + - *2046x1534* + + *SGRBG8_1X8* * - Configure scaler sink compose selection - - 2048x1536/SGRBG8_1X8 - - 2048x1536/SGRBG8_1X8 - - 2046x1534/SGRBG8_1X8 - - 2046x1534/SGRBG8_1X8 + - 2048x1536 + + SGRBG8_1X8 + - 2048x1536 + + SGRBG8_1X8 + - 2046x1534 + + SGRBG8_1X8 + - 2046x1534 + + SGRBG8_1X8 - *0,0/1280x960* - - *1280x960/SGRBG8_1X8* + - *1280x960* + + *SGRBG8_1X8* .. raw:: latex diff --git a/Documentation/media/uapi/v4l/ext-ctrls-camera.rst b/Documentation/media/uapi/v4l/ext-ctrls-camera.rst index d3a553cd86c9..51c1d5c9eb00 100644 --- a/Documentation/media/uapi/v4l/ext-ctrls-camera.rst +++ b/Documentation/media/uapi/v4l/ext-ctrls-camera.rst @@ -88,7 +88,7 @@ enum v4l2_exposure_metering - Determines how the camera measures the amount of light available for the frame exposure. Possible values are: -.. tabularcolumns:: |p{8.5cm}|p{9.0cm}| +.. tabularcolumns:: |p{8.7cm}|p{8.8cm}| .. flat-table:: :header-rows: 0 @@ -180,7 +180,7 @@ enum v4l2_exposure_metering - control may stop updates of the ``V4L2_CID_AUTO_FOCUS_STATUS`` control value. -.. tabularcolumns:: |p{6.5cm}|p{11.0cm}| +.. tabularcolumns:: |p{6.7cm}|p{10.8cm}| .. flat-table:: :header-rows: 0 @@ -206,7 +206,7 @@ enum v4l2_exposure_metering - enum v4l2_auto_focus_range - Determines auto focus distance range for which lens may be adjusted. -.. tabularcolumns:: |p{6.5cm}|p{11.0cm}| +.. tabularcolumns:: |p{6.8cm}|p{10.7cm}| .. flat-table:: :header-rows: 0 @@ -281,7 +281,7 @@ enum v4l2_auto_n_preset_white_balance - representation. The following white balance presets are listed in order of increasing color temperature. -.. tabularcolumns:: |p{7.0 cm}|p{10.5cm}| +.. tabularcolumns:: |p{7.2 cm}|p{10.3cm}| .. flat-table:: :header-rows: 0 @@ -387,7 +387,11 @@ enum v4l2_scene_mode - to ``V4L2_SCENE_MODE_NONE`` to make sure the other possibly related controls are accessible. The following scene programs are defined: -.. tabularcolumns:: |p{6.0cm}|p{11.5cm}| +.. raw:: latex + + \small + +.. tabularcolumns:: |p{5.9cm}|p{11.5cm}| .. flat-table:: :header-rows: 0 @@ -459,6 +463,9 @@ enum v4l2_scene_mode - may be switched to close-up mode and this setting may also involve some lens-distortion correction. +.. raw:: latex + + \normalsize ``V4L2_CID_3A_LOCK (bitmask)`` diff --git a/Documentation/media/uapi/v4l/ext-ctrls-codec.rst b/Documentation/media/uapi/v4l/ext-ctrls-codec.rst index 0aaee04f81dd..67a122339c0e 100644 --- a/Documentation/media/uapi/v4l/ext-ctrls-codec.rst +++ b/Documentation/media/uapi/v4l/ext-ctrls-codec.rst @@ -105,7 +105,7 @@ enum v4l2_mpeg_stream_vbi_fmt - -.. tabularcolumns:: |p{6 cm}|p{11.5cm}| +.. tabularcolumns:: |p{6.6 cm}|p{10.9cm}| .. flat-table:: :header-rows: 0 @@ -477,7 +477,7 @@ enum v4l2_mpeg_audio_dec_playback - -.. tabularcolumns:: |p{9.0cm}|p{8.5cm}| +.. tabularcolumns:: |p{9.8cm}|p{7.7cm}| .. flat-table:: :header-rows: 0 @@ -888,7 +888,7 @@ enum v4l2_mpeg_video_multi_slice_mode - -.. tabularcolumns:: |p{8.7cm}|p{8.8cm}| +.. tabularcolumns:: |p{9.6cm}|p{7.9cm}| .. flat-table:: :header-rows: 0 @@ -923,9 +923,11 @@ enum v4l2_mpeg_video_multi_slice_mode - enum v4l2_mpeg_video_h264_loop_filter_mode - Loop filter mode for H264 encoder. Possible values are: +.. raw:: latex + \small -.. tabularcolumns:: |p{14.0cm}|p{3.5cm}| +.. tabularcolumns:: |p{13.6cm}|p{3.9cm}| .. flat-table:: :header-rows: 0 @@ -938,6 +940,9 @@ enum v4l2_mpeg_video_h264_loop_filter_mode - * - ``V4L2_MPEG_VIDEO_H264_LOOP_FILTER_MODE_DISABLED_AT_SLICE_BOUNDARY`` - Loop filter is disabled at the slice boundary. +.. raw:: latex + + \normalsize ``V4L2_CID_MPEG_VIDEO_H264_LOOP_FILTER_ALPHA (integer)`` @@ -964,6 +969,8 @@ enum v4l2_mpeg_video_h264_entropy_mode - encoder. Possible values are: +.. tabularcolumns:: |p{9.0cm}|p{8.5cm}| + .. flat-table:: :header-rows: 0 @@ -1129,7 +1136,9 @@ enum v4l2_mpeg_video_header_mode - it returned together with the first frame. Applicable to encoders. Possible values are: +.. raw:: latex + \small .. tabularcolumns:: |p{10.3cm}|p{7.2cm}| @@ -1143,6 +1152,9 @@ enum v4l2_mpeg_video_header_mode - - The stream header is returned together with the first encoded frame. +.. raw:: latex + + \normalsize ``V4L2_CID_MPEG_VIDEO_REPEAT_SEQ_HEADER (boolean)`` @@ -1181,6 +1193,10 @@ enum v4l2_mpeg_video_h264_sei_fp_arrangement_type - Frame packing arrangement type for H264 SEI. Applicable to the H264 encoder. Possible values are: +.. raw:: latex + + \small + .. tabularcolumns:: |p{12cm}|p{5.5cm}| .. flat-table:: @@ -1200,6 +1216,10 @@ enum v4l2_mpeg_video_h264_sei_fp_arrangement_type - * - ``V4L2_MPEG_VIDEO_H264_SEI_FP_ARRANGEMENT_TYPE_TEMPORAL`` - One view per frame. +.. raw:: latex + + \normalsize + ``V4L2_CID_MPEG_VIDEO_H264_FMO (boolean)`` @@ -1217,6 +1237,10 @@ enum v4l2_mpeg_video_h264_fmo_map_type - patterns of macroblocks. Applicable to the H264 encoder. Possible values are: +.. raw:: latex + + \small + .. tabularcolumns:: |p{12.5cm}|p{5.0cm}| .. flat-table:: @@ -1240,6 +1264,10 @@ enum v4l2_mpeg_video_h264_fmo_map_type - * - ``V4L2_MPEG_VIDEO_H264_FMO_MAP_TYPE_EXPLICIT`` - User defined map type. +.. raw:: latex + + \normalsize + ``V4L2_CID_MPEG_VIDEO_H264_FMO_SLICE_GROUP (integer)`` @@ -1361,6 +1389,8 @@ enum v4l2_mpeg_video_h264_hierarchical_coding_type - .. cssclass:: longtable +.. tabularcolumns:: |p{5.8cm}|p{4.8cm}|p{6.6cm}| + .. flat-table:: struct v4l2_ctrl_mpeg2_slice_params :header-rows: 0 :stub-columns: 0 @@ -1402,6 +1432,8 @@ enum v4l2_mpeg_video_h264_hierarchical_coding_type - .. cssclass:: longtable +.. tabularcolumns:: |p{1.5cm}|p{6.3cm}|p{9.4cm}| + .. flat-table:: struct v4l2_mpeg2_sequence :header-rows: 0 :stub-columns: 0 @@ -1433,6 +1465,8 @@ enum v4l2_mpeg_video_h264_hierarchical_coding_type - .. cssclass:: longtable +.. tabularcolumns:: |p{1.5cm}|p{6.3cm}|p{9.4cm}| + .. flat-table:: struct v4l2_mpeg2_picture :header-rows: 0 :stub-columns: 0 @@ -1492,6 +1526,12 @@ enum v4l2_mpeg_video_h264_hierarchical_coding_type - .. cssclass:: longtable +.. tabularcolumns:: |p{1.2cm}|p{8.0cm}|p{7.4cm}| + +.. raw:: latex + + \small + .. flat-table:: struct v4l2_ctrl_mpeg2_quantization :header-rows: 0 :stub-columns: 0 @@ -1545,6 +1585,11 @@ enum v4l2_mpeg_video_h264_hierarchical_coding_type - Quantization parameter for a P frame for FWHT. Valid range: from 1 to 31. +.. raw:: latex + + \normalsize + + MFC 5.1 MPEG Controls ===================== @@ -1652,7 +1697,11 @@ enum v4l2_mpeg_mfc51_video_frame_skip_mode - are: -.. tabularcolumns:: |p{9.0cm}|p{8.5cm}| +.. tabularcolumns:: |p{9.2cm}|p{8.3cm}| + +.. raw:: latex + + \small .. flat-table:: :header-rows: 0 @@ -1667,7 +1716,9 @@ enum v4l2_mpeg_mfc51_video_frame_skip_mode - - Frame skip mode enabled and buffer limit is set by the VBV (MPEG1/2/4) or CPB (H264) buffer size control. +.. raw:: latex + \normalsize ``V4L2_CID_MPEG_MFC51_VIDEO_RC_FIXED_TARGET_BIT (integer)`` Enable rate-control with fixed target bit. If this setting is @@ -1690,7 +1741,7 @@ enum v4l2_mpeg_mfc51_video_force_frame_type - Force a frame type for the next queued buffer. Applicable to encoders. Possible values are: - +.. tabularcolumns:: |p{9.5cm}|p{8.0cm}| .. flat-table:: :header-rows: 0 @@ -1720,6 +1771,8 @@ enum v4l2_mpeg_mfc51_video_force_frame_type - .. cssclass:: longtable +.. tabularcolumns:: |p{1.4cm}|p{4.3cm}|p{11.8cm}| + .. flat-table:: struct v4l2_ctrl_fwht_params :header-rows: 0 :stub-columns: 0 @@ -1763,10 +1816,11 @@ enum v4l2_mpeg_mfc51_video_force_frame_type - FWHT Flags ============ -.. tabularcolumns:: |p{7.0cm}|p{2.2cm}|p{8.3cm}| .. cssclass:: longtable +.. tabularcolumns:: |p{6.8cm}|p{2.4cm}|p{8.3cm}| + .. flat-table:: :header-rows: 0 :stub-columns: 0 @@ -1869,9 +1923,11 @@ enum v4l2_mpeg_cx2341x_video_luma_spatial_filter_type - Select the algorithm to use for the Luma Spatial Filter (default ``1D_HOR``). Possible values: +.. tabularcolumns:: |p{14.5cm}|p{3.0cm}| +.. raw:: latex -.. tabularcolumns:: |p{14.5cm}|p{3.0cm}| + \small .. flat-table:: :header-rows: 0 @@ -1888,6 +1944,10 @@ enum v4l2_mpeg_cx2341x_video_luma_spatial_filter_type - * - ``V4L2_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE_2D_SYM_NON_SEPARABLE`` - Two-dimensional symmetrical non-separable +.. raw:: latex + + \normalsize + .. _chroma-spatial-filter-type: @@ -1900,6 +1960,7 @@ enum v4l2_mpeg_cx2341x_video_chroma_spatial_filter_type - ``1D_HOR``). Possible values are: +.. tabularcolumns:: |p{14.0cm}|p{3.5cm}| .. flat-table:: :header-rows: 0 @@ -2042,6 +2103,10 @@ enum v4l2_vp8_num_ref_frames - .. tabularcolumns:: |p{7.9cm}|p{9.6cm}| +.. raw:: latex + + \small + .. flat-table:: :header-rows: 0 :stub-columns: 0 @@ -2056,6 +2121,10 @@ enum v4l2_vp8_num_ref_frames - - The last encoded frame, the golden frame and the altref frame will be searched. +.. raw:: latex + + \normalsize + ``V4L2_CID_MPEG_VIDEO_VPX_FILTER_LEVEL (integer)`` @@ -2085,7 +2154,7 @@ enum v4l2_vp8_golden_frame_sel - .. raw:: latex - \footnotesize + \scriptsize .. tabularcolumns:: |p{9.0cm}|p{8.0cm}| @@ -2407,7 +2476,7 @@ enum v4l2_mpeg_video_hevc_loop_filter_mode - \footnotesize -.. tabularcolumns:: |p{10.7cm}|p{6.3cm}| +.. tabularcolumns:: |p{12.1cm}|p{5.4cm}| .. flat-table:: :header-rows: 0 diff --git a/Documentation/media/uapi/v4l/ext-ctrls-detect.rst b/Documentation/media/uapi/v4l/ext-ctrls-detect.rst index 8a45ce642829..80981d0cff42 100644 --- a/Documentation/media/uapi/v4l/ext-ctrls-detect.rst +++ b/Documentation/media/uapi/v4l/ext-ctrls-detect.rst @@ -30,7 +30,7 @@ Detect Control IDs ``V4L2_CID_DETECT_MD_MODE (menu)`` Sets the motion detection mode. -.. tabularcolumns:: |p{7.5cm}|p{10.0cm}| +.. tabularcolumns:: |p{7.7cm}|p{9.8cm}| .. flat-table:: :header-rows: 0 diff --git a/Documentation/media/uapi/v4l/ext-ctrls-dv.rst b/Documentation/media/uapi/v4l/ext-ctrls-dv.rst index 57edf211875c..5c70ac98f710 100644 --- a/Documentation/media/uapi/v4l/ext-ctrls-dv.rst +++ b/Documentation/media/uapi/v4l/ext-ctrls-dv.rst @@ -106,7 +106,7 @@ enum v4l2_dv_it_content_type - or an analog source. The enum v4l2_dv_it_content_type defines the possible content types: -.. tabularcolumns:: |p{7.0cm}|p{10.5cm}| +.. tabularcolumns:: |p{7.3cm}|p{10.4cm}| .. flat-table:: :header-rows: 0 diff --git a/Documentation/media/uapi/v4l/ext-ctrls-flash.rst b/Documentation/media/uapi/v4l/ext-ctrls-flash.rst index 5f30791c35b5..eff056b17167 100644 --- a/Documentation/media/uapi/v4l/ext-ctrls-flash.rst +++ b/Documentation/media/uapi/v4l/ext-ctrls-flash.rst @@ -87,7 +87,7 @@ Flash Control IDs ``V4L2_CID_FLASH_STROBE_SOURCE (menu)`` Defines the source of the flash LED strobe. -.. tabularcolumns:: |p{7.0cm}|p{10.5cm}| +.. tabularcolumns:: |p{7.5cm}|p{10.0cm}| .. flat-table:: :header-rows: 0 @@ -146,7 +146,7 @@ Flash Control IDs an effect is chip dependent. Reading the faults resets the control and returns the chip to a usable state if possible. -.. tabularcolumns:: |p{8.0cm}|p{9.5cm}| +.. tabularcolumns:: |p{8.4cm}|p{9.1cm}| .. flat-table:: :header-rows: 0 diff --git a/Documentation/media/uapi/v4l/ext-ctrls-jpeg.rst b/Documentation/media/uapi/v4l/ext-ctrls-jpeg.rst index cf9cd8a9f9b4..60ce3f949319 100644 --- a/Documentation/media/uapi/v4l/ext-ctrls-jpeg.rst +++ b/Documentation/media/uapi/v4l/ext-ctrls-jpeg.rst @@ -37,7 +37,7 @@ JPEG Control IDs how Cb and Cr components are downsampled after converting an input image from RGB to Y'CbCr color space. -.. tabularcolumns:: |p{7.0cm}|p{10.5cm}| +.. tabularcolumns:: |p{7.5cm}|p{10.0cm}| .. flat-table:: :header-rows: 0 diff --git a/Documentation/media/uapi/v4l/field-order.rst b/Documentation/media/uapi/v4l/field-order.rst index 8415268d439c..3fb473e3b8e2 100644 --- a/Documentation/media/uapi/v4l/field-order.rst +++ b/Documentation/media/uapi/v4l/field-order.rst @@ -64,7 +64,9 @@ enum v4l2_field .. c:type:: v4l2_field -.. tabularcolumns:: |p{6.6cm}|p{2.2cm}|p{8.7cm}| +.. tabularcolumns:: |p{5.8cm}|p{0.6cm}|p{11.1cm}| + +.. cssclass:: longtable .. flat-table:: :header-rows: 0 diff --git a/Documentation/media/uapi/v4l/pixfmt-meta-d4xx.rst b/Documentation/media/uapi/v4l/pixfmt-meta-d4xx.rst index 862e1f327150..87e8fd7d5d02 100644 --- a/Documentation/media/uapi/v4l/pixfmt-meta-d4xx.rst +++ b/Documentation/media/uapi/v4l/pixfmt-meta-d4xx.rst @@ -36,13 +36,16 @@ per frame, therefore their headers cannot be larger than 255 bytes. Below are proprietary Microsoft style metadata types, used by D4xx cameras, where all fields are in little endian order: +.. tabularcolumns:: |p{5.0cm}|p{12.5cm}| + + .. flat-table:: D4xx metadata - :widths: 1 4 + :widths: 1 2 :header-rows: 1 :stub-columns: 0 - * - Field - - Description + * - **Field** + - **Description** * - :cspan:`1` *Depth Control* * - __u32 ID - 0x80000000 diff --git a/Documentation/media/uapi/v4l/pixfmt-meta-vsp1-hgt.rst b/Documentation/media/uapi/v4l/pixfmt-meta-vsp1-hgt.rst index 2ebccdcca95d..d1a341af9c48 100644 --- a/Documentation/media/uapi/v4l/pixfmt-meta-vsp1-hgt.rst +++ b/Documentation/media/uapi/v4l/pixfmt-meta-vsp1-hgt.rst @@ -41,6 +41,10 @@ The Hue position **m** (0 - 5) of the bucket in the matrix depends on how the HGT Hue areas are configured. There are 6 user configurable Hue Areas which can be configured to cover overlapping Hue values: +.. raw:: latex + + \small + :: Area 0 Area 1 Area 2 Area 3 Area 4 Area 5 @@ -53,6 +57,11 @@ Areas which can be configured to cover overlapping Hue values: 5U 0L 0U 1L 1U 2L 2U 3L 3U 4L 4U 5L 5U 0L <0..............................Hue Value............................255> + +.. raw:: latex + + \normalsize + When two consecutive areas don't overlap (n+1L is equal to nU) the boundary value is considered as part of the lower area. diff --git a/Documentation/media/uapi/v4l/pixfmt-packed-hsv.rst b/Documentation/media/uapi/v4l/pixfmt-packed-hsv.rst index 38b1895a509f..dfc4a8367b3d 100644 --- a/Documentation/media/uapi/v4l/pixfmt-packed-hsv.rst +++ b/Documentation/media/uapi/v4l/pixfmt-packed-hsv.rst @@ -31,7 +31,7 @@ The values are packed in 24 or 32 bit formats. \tiny \setlength{\tabcolsep}{2pt} -.. tabularcolumns:: |p{2.0cm}|p{0.54cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}| +.. tabularcolumns:: |p{2.6cm}|p{0.8cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}| .. _packed-hsv-formats: diff --git a/Documentation/media/uapi/v4l/pixfmt-packed-rgb.rst b/Documentation/media/uapi/v4l/pixfmt-packed-rgb.rst index 6b3781c04dd5..4766a6f47222 100644 --- a/Documentation/media/uapi/v4l/pixfmt-packed-rgb.rst +++ b/Documentation/media/uapi/v4l/pixfmt-packed-rgb.rst @@ -27,7 +27,7 @@ next to each other in memory. \tiny \setlength{\tabcolsep}{2pt} -.. tabularcolumns:: |p{2.3cm}|p{1.6cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}| +.. tabularcolumns:: |p{2.8cm}|p{2.0cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}| .. _rgb-formats: @@ -656,7 +656,7 @@ either the corresponding ARGB or XRGB format, depending on the driver. \tiny \setlength{\tabcolsep}{2pt} -.. tabularcolumns:: |p{2.2cm}|p{0.60cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}| +.. tabularcolumns:: |p{2.6cm}|p{0.70cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}| .. _rgb-formats-deprecated: diff --git a/Documentation/media/uapi/v4l/pixfmt-packed-yuv.rst b/Documentation/media/uapi/v4l/pixfmt-packed-yuv.rst index 9d2b281f06a2..41b60fae703a 100644 --- a/Documentation/media/uapi/v4l/pixfmt-packed-yuv.rst +++ b/Documentation/media/uapi/v4l/pixfmt-packed-yuv.rst @@ -28,7 +28,7 @@ component of each pixel in one 16 or 32 bit word. .. _packed-yuv-formats: -.. tabularcolumns:: |p{2.0cm}|p{0.67cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}|p{0.29cm}| +.. tabularcolumns:: |p{2.5cm}|p{0.69cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}|p{0.31cm}| .. flat-table:: Packed YUV Image Formats :header-rows: 2 diff --git a/Documentation/media/uapi/v4l/pixfmt-srggb10p.rst b/Documentation/media/uapi/v4l/pixfmt-srggb10p.rst index cdb70ac26126..fd32660a3766 100644 --- a/Documentation/media/uapi/v4l/pixfmt-srggb10p.rst +++ b/Documentation/media/uapi/v4l/pixfmt-srggb10p.rst @@ -40,7 +40,7 @@ of a small V4L2_PIX_FMT_SBGGR10P image: **Byte Order.** Each cell is one byte. -.. tabularcolumns:: |p{2.0cm}|p{1.0cm}|p{1.0cm}|p{1.0cm}|p{1.0cm}|p{5.4cm}| +.. tabularcolumns:: |p{2.4cm}|p{1.4cm}|p{1.2cm}|p{1.2cm}|p{1.2cm}|p{6.4cm}| .. flat-table:: :header-rows: 0 diff --git a/Documentation/media/uapi/v4l/pixfmt-srggb12p.rst b/Documentation/media/uapi/v4l/pixfmt-srggb12p.rst index 01413be12916..960851275f23 100644 --- a/Documentation/media/uapi/v4l/pixfmt-srggb12p.rst +++ b/Documentation/media/uapi/v4l/pixfmt-srggb12p.rst @@ -18,6 +18,7 @@ V4L2_PIX_FMT_SRGGB12P ('pRAA'), V4L2_PIX_FMT_SGRBG12P ('pgAA'), V4L2_PIX_FMT_SGB 12-bit packed Bayer formats +--------------------------- Description @@ -37,7 +38,7 @@ Below is an example of a small V4L2_PIX_FMT_SBGGR12P image: **Byte Order.** Each cell is one byte. -.. tabularcolumns:: |p{2.0cm}|p{1.0cm}|p{1.0cm}|p{2.7cm}|p{1.0cm}|p{1.0cm}|p{2.7cm}| +.. tabularcolumns:: |p{2.2cm}|p{1.2cm}|p{1.2cm}|p{3.1cm}|p{1.2cm}|p{1.2cm}|p{3.1cm}| .. flat-table:: diff --git a/Documentation/media/uapi/v4l/pixfmt-srggb14p.rst b/Documentation/media/uapi/v4l/pixfmt-srggb14p.rst index b583531c2853..1a988d7e7ff8 100644 --- a/Documentation/media/uapi/v4l/pixfmt-srggb14p.rst +++ b/Documentation/media/uapi/v4l/pixfmt-srggb14p.rst @@ -41,17 +41,21 @@ of one of these formats: **Byte Order.** Each cell is one byte. +.. raw:: latex + \footnotesize + +.. tabularcolumns:: |p{1.8cm}|p{1.0cm}|p{1.0cm}|p{1.0cm}|p{1.1cm}|p{3.3cm}|p{3.3cm}|p{3.3cm}| .. flat-table:: :header-rows: 0 :stub-columns: 0 - :widths: 2 1 1 1 1 1 1 1 + :widths: 2 1 1 1 1 3 3 3 - .. row 1 - - start + 0: + - start + 0 - B\ :sub:`00high` @@ -62,17 +66,20 @@ Each cell is one byte. - G\ :sub:`03high` - G\ :sub:`01low bits 1--0`\ (bits 7--6) + B\ :sub:`00low bits 5--0`\ (bits 5--0) - R\ :sub:`02low bits 3--0`\ (bits 7--4) + G\ :sub:`01low bits 5--2`\ (bits 3--0) - G\ :sub:`03low bits 5--0`\ (bits 7--2) + R\ :sub:`02low bits 5--4`\ (bits 1--0) - .. row 2 - - start + 7: + - start + 7 - G\ :sub:`00high` @@ -83,12 +90,15 @@ Each cell is one byte. - R\ :sub:`03high` - R\ :sub:`01low bits 1--0`\ (bits 7--6) + G\ :sub:`00low bits 5--0`\ (bits 5--0) - G\ :sub:`02low bits 3--0`\ (bits 7--4) + R\ :sub:`01low bits 5--2`\ (bits 3--0) - R\ :sub:`03low bits 5--0`\ (bits 7--2) + G\ :sub:`02low bits 5--4`\ (bits 1--0) - .. row 3 @@ -104,12 +114,15 @@ Each cell is one byte. - G\ :sub:`23high` - G\ :sub:`21low bits 1--0`\ (bits 7--6) + B\ :sub:`20low bits 5--0`\ (bits 5--0) - R\ :sub:`22low bits 3--0`\ (bits 7--4) + G\ :sub:`21low bits 5--2`\ (bits 3--0) - G\ :sub:`23low bits 5--0`\ (bits 7--2) + R\ :sub:`22low bits 5--4`\ (bits 1--0) - .. row 4 @@ -132,3 +145,8 @@ Each cell is one byte. - R\ :sub:`33low bits 5--0`\ (bits 7--2) G\ :sub:`32low bits 5--4`\ (bits 1--0) + +.. raw:: latex + + \normalsize + diff --git a/Documentation/media/uapi/v4l/pixfmt-v4l2-mplane.rst b/Documentation/media/uapi/v4l/pixfmt-v4l2-mplane.rst index 7f82dad9013a..5688c816e334 100644 --- a/Documentation/media/uapi/v4l/pixfmt-v4l2-mplane.rst +++ b/Documentation/media/uapi/v4l/pixfmt-v4l2-mplane.rst @@ -19,6 +19,7 @@ array of struct :c:type:`v4l2_plane_pix_format` structures, describing all planes of that format. + .. tabularcolumns:: |p{4.4cm}|p{4.4cm}|p{8.7cm}| .. c:type:: v4l2_plane_pix_format @@ -41,6 +42,10 @@ describing all planes of that format. applications. +.. raw:: latex + + \small + .. tabularcolumns:: |p{4.4cm}|p{5.6cm}|p{7.5cm}| .. c:type:: v4l2_pix_format_mplane @@ -82,9 +87,7 @@ describing all planes of that format. * - __u8 - ``flags`` - Flags set by the application or driver, see :ref:`format-flags`. - * - union { - - (anonymous) - - + * - :cspan:`2` union { (anonymous) * - __u8 - ``ycbcr_enc`` - Y'CbCr encoding, from enum :c:type:`v4l2_ycbcr_encoding`. @@ -97,9 +100,7 @@ describing all planes of that format. This information supplements the ``colorspace`` and must be set by the driver for capture streams and by the application for output streams, see :ref:`colorspaces`. - * - } - - - - + * - :cspan:`2` } * - __u8 - ``quantization`` - Quantization range, from enum :c:type:`v4l2_quantization`. @@ -116,3 +117,7 @@ describing all planes of that format. - ``reserved[7]`` - Reserved for future extensions. Should be zeroed by drivers and applications. + +.. raw:: latex + + \normalsize diff --git a/Documentation/media/uapi/v4l/pixfmt-y10p.rst b/Documentation/media/uapi/v4l/pixfmt-y10p.rst index 7893642faee3..39cd789dcb59 100644 --- a/Documentation/media/uapi/v4l/pixfmt-y10p.rst +++ b/Documentation/media/uapi/v4l/pixfmt-y10p.rst @@ -27,6 +27,12 @@ in the same order. **Bit-packed representation.** +.. raw:: latex + + \small + +.. tabularcolumns:: |p{1.2cm}||p{1.2cm}||p{1.2cm}||p{1.2cm}|p{3.2cm}|p{3.2cm}| + .. flat-table:: :header-rows: 0 :stub-columns: 0 @@ -38,3 +44,7 @@ in the same order. - Y'\ :sub:`03[9:2]` - Y'\ :sub:`03[1:0]`\ (bits 7--6) Y'\ :sub:`02[1:0]`\ (bits 5--4) Y'\ :sub:`01[1:0]`\ (bits 3--2) Y'\ :sub:`00[1:0]`\ (bits 1--0) + +.. raw:: latex + + \normalsize diff --git a/Documentation/media/uapi/v4l/subdev-formats.rst b/Documentation/media/uapi/v4l/subdev-formats.rst index f5440d55d510..bf1dbb68eebc 100644 --- a/Documentation/media/uapi/v4l/subdev-formats.rst +++ b/Documentation/media/uapi/v4l/subdev-formats.rst @@ -7414,7 +7414,7 @@ The following table lists existing HSV/HSL formats. \tiny \setlength{\tabcolsep}{2pt} -.. tabularcolumns:: |p{3.0cm}|p{0.60cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}| +.. tabularcolumns:: |p{3.9cm}|p{0.73cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}|p{0.22cm}| .. _v4l2-mbus-pixelcode-hsv: @@ -7524,7 +7524,7 @@ The following table lists existing JPEG compressed formats. .. _v4l2-mbus-pixelcode-jpeg: -.. tabularcolumns:: |p{5.4cm}|p{1.4cm}|p{10.7cm}| +.. tabularcolumns:: |p{6.0cm}|p{1.4cm}|p{10.1cm}| .. flat-table:: JPEG Formats :header-rows: 1 @@ -7557,7 +7557,7 @@ formats. .. _v4l2-mbus-pixelcode-vendor-specific: -.. tabularcolumns:: |p{6.8cm}|p{1.4cm}|p{9.3cm}| +.. tabularcolumns:: |p{8.0cm}|p{1.4cm}|p{7.7cm}| .. flat-table:: Vendor and device specific formats :header-rows: 1 -- cgit v1.2.3 From 1c3ec30bb23023d738b538e64ac3028902d53692 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Sat, 30 Mar 2019 09:33:54 -0400 Subject: media: index.rst: exclude Indexes section from latex/pdf output With LaTex, the Index at the end will always be present. Having an extra chapter for it there will just add extra noise to the document. Signed-off-by: Mauro Carvalho Chehab --- Documentation/media/index.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/media/index.rst b/Documentation/media/index.rst index 0a222fc1d7ca..0301c25ff887 100644 --- a/Documentation/media/index.rst +++ b/Documentation/media/index.rst @@ -18,7 +18,7 @@ Linux Media Subsystem Documentation v4l-drivers/index cec-drivers/index -.. only:: subproject +.. only:: html and subproject Indices ======= -- cgit v1.2.3 From 9067cdea17954f4c5b0d5b114a588b8d85ce3219 Mon Sep 17 00:00:00 2001 From: Shunli Wang Date: Fri, 29 Mar 2019 16:34:47 +0800 Subject: ASoC: Mediatek: Add document for mt8183-mt6358-ts3a227-max98357 This patch adds document for the machine board with mt6358, ts3a227 and max98357 codecs. Signed-off-by: Shunli Wang Signed-off-by: Mark Brown --- .../bindings/sound/mt8183-mt6358-ts3a227-max98357.txt | 15 +++++++++++++++ 1 file changed, 15 insertions(+) create mode 100644 Documentation/devicetree/bindings/sound/mt8183-mt6358-ts3a227-max98357.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/sound/mt8183-mt6358-ts3a227-max98357.txt b/Documentation/devicetree/bindings/sound/mt8183-mt6358-ts3a227-max98357.txt new file mode 100644 index 000000000000..d6d5207fa996 --- /dev/null +++ b/Documentation/devicetree/bindings/sound/mt8183-mt6358-ts3a227-max98357.txt @@ -0,0 +1,15 @@ +MT8183 with MT6358, TS3A227 and MAX98357 CODECS + +Required properties: +- compatible : "mediatek,mt8183_mt6358_ts3a227_max98357" +- mediatek,headset-codec: the phandles of ts3a227 codecs +- mediatek,platform: the phandle of MT8183 ASoC platform + +Example: + + sound { + compatible = "mediatek,mt8183_mt6358_ts3a227_max98357"; + mediatek,headset-codec = <&ts3a227>; + mediatek,platform = <&afe>; + }; + -- cgit v1.2.3 From 5a79acf9a9188d85e1f1a697ed7531e0f0f36943 Mon Sep 17 00:00:00 2001 From: Shunli Wang Date: Fri, 29 Mar 2019 16:34:49 +0800 Subject: ASoC: Mediatek: Add document for mt8183-da7219-max98357 This patch adds document for the machine board with mt6358, da7219 and max98357 codecs. Signed-off-by: Shunli Wang Signed-off-by: Mark Brown --- .../devicetree/bindings/sound/mt8183-da7219-max98357.txt | 15 +++++++++++++++ 1 file changed, 15 insertions(+) create mode 100644 Documentation/devicetree/bindings/sound/mt8183-da7219-max98357.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/sound/mt8183-da7219-max98357.txt b/Documentation/devicetree/bindings/sound/mt8183-da7219-max98357.txt new file mode 100644 index 000000000000..92ac86f83822 --- /dev/null +++ b/Documentation/devicetree/bindings/sound/mt8183-da7219-max98357.txt @@ -0,0 +1,15 @@ +MT8183 with MT6358, DA7219 and MAX98357 CODECS + +Required properties: +- compatible : "mediatek,mt8183_da7219_max98357" +- mediatek,headset-codec: the phandles of da7219 codecs +- mediatek,platform: the phandle of MT8183 ASoC platform + +Example: + + sound { + compatible = "mediatek,mt8183_da7219_max98357"; + mediatek,headset-codec = <&da7219>; + mediatek,platform = <&afe>; + }; + -- cgit v1.2.3 From 4438cf50e7b315ff4bc4cfff8520b906428c3024 Mon Sep 17 00:00:00 2001 From: Paolo Valente Date: Tue, 12 Mar 2019 09:59:35 +0100 Subject: doc, block, bfq: add information on bfq execution time The execution time of BFQ has been slightly lowered. Report the new execution time in BFQ documentation. Signed-off-by: Paolo Valente Signed-off-by: Jens Axboe --- Documentation/block/bfq-iosched.txt | 29 ++++++++++++++++++++++------- 1 file changed, 22 insertions(+), 7 deletions(-) (limited to 'Documentation') diff --git a/Documentation/block/bfq-iosched.txt b/Documentation/block/bfq-iosched.txt index 98a8dd5ee385..1a0f2ac02eb6 100644 --- a/Documentation/block/bfq-iosched.txt +++ b/Documentation/block/bfq-iosched.txt @@ -20,13 +20,26 @@ for that device, by setting low_latency to 0. See Section 3 for details on how to configure BFQ for the desired tradeoff between latency and throughput, or on how to maximize throughput. -BFQ has a non-null overhead, which limits the maximum IOPS that a CPU -can process for a device scheduled with BFQ. To give an idea of the -limits on slow or average CPUs, here are, first, the limits of BFQ for -three different CPUs, on, respectively, an average laptop, an old -desktop, and a cheap embedded system, in case full hierarchical -support is enabled (i.e., CONFIG_BFQ_GROUP_IOSCHED is set), but -CONFIG_DEBUG_BLK_CGROUP is not set (Section 4-2): +As every I/O scheduler, BFQ adds some overhead to per-I/O-request +processing. To give an idea of this overhead, the total, +single-lock-protected, per-request processing time of BFQ---i.e., the +sum of the execution times of the request insertion, dispatch and +completion hooks---is, e.g., 1.9 us on an Intel Core i7-2760QM@2.40GHz +(dated CPU for notebooks; time measured with simple code +instrumentation, and using the throughput-sync.sh script of the S +suite [1], in performance-profiling mode). To put this result into +context, the total, single-lock-protected, per-request execution time +of the lightest I/O scheduler available in blk-mq, mq-deadline, is 0.7 +us (mq-deadline is ~800 LOC, against ~10500 LOC for BFQ). + +Scheduling overhead further limits the maximum IOPS that a CPU can +process (already limited by the execution of the rest of the I/O +stack). To give an idea of the limits with BFQ, on slow or average +CPUs, here are, first, the limits of BFQ for three different CPUs, on, +respectively, an average laptop, an old desktop, and a cheap embedded +system, in case full hierarchical support is enabled (i.e., +CONFIG_BFQ_GROUP_IOSCHED is set), but CONFIG_DEBUG_BLK_CGROUP is not +set (Section 4-2): - Intel i7-4850HQ: 400 KIOPS - AMD A8-3850: 250 KIOPS - ARM CortexTM-A53 Octa-core: 80 KIOPS @@ -566,3 +579,5 @@ applications. Unset this tunable if you need/want to control weights. Slightly extended version: http://algogroup.unimore.it/people/paolo/disk_sched/bfq-v1-suite- results.pdf + +[3] https://github.com/Algodev-github/S -- cgit v1.2.3 From 386cb76681ca6248878c7b76d3d5aa0e8b8a07bb Mon Sep 17 00:00:00 2001 From: Tony Lindgren Date: Fri, 22 Mar 2019 07:49:30 -0700 Subject: bus: ti-sysc: Handle missed no-idle property in addition to no-idle-on-init We have ti,no-idle in use in addition to ti,no-idle-on-init but we're missing handling for it in the ti-sysc interconnect target module driver. Let's also group the idle defines together and update the binding documentation for it. Cc: devicetree@vger.kernel.org Reviewed-by: Rob Herring Signed-off-by: Tony Lindgren --- Documentation/devicetree/bindings/bus/ti-sysc.txt | 2 ++ arch/arm/mach-omap2/omap_hwmod.c | 2 ++ drivers/bus/ti-sysc.c | 5 ++++- include/linux/platform_data/ti-sysc.h | 5 +++-- 4 files changed, 11 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/bus/ti-sysc.txt b/Documentation/devicetree/bindings/bus/ti-sysc.txt index 85a23f551f02..f200f45572ae 100644 --- a/Documentation/devicetree/bindings/bus/ti-sysc.txt +++ b/Documentation/devicetree/bindings/bus/ti-sysc.txt @@ -94,6 +94,8 @@ Optional properties: - ti,no-idle-on-init interconnect target module should not be idled at init +- ti,no-idle interconnect target module should not be idled + Example: Single instance of MUSB controller on omap4 using interconnect ranges using offsets from l4_cfg second segment (0x4a000000 + 0x80000 = 0x4a0ab000): diff --git a/arch/arm/mach-omap2/omap_hwmod.c b/arch/arm/mach-omap2/omap_hwmod.c index 9170fbfb7c59..a985844dbe39 100644 --- a/arch/arm/mach-omap2/omap_hwmod.c +++ b/arch/arm/mach-omap2/omap_hwmod.c @@ -3675,6 +3675,8 @@ int omap_hwmod_init_module(struct device *dev, if (error) return error; + if (data->cfg->quirks & SYSC_QUIRK_NO_IDLE) + oh->flags |= HWMOD_NO_IDLE; if (data->cfg->quirks & SYSC_QUIRK_NO_IDLE_ON_INIT) oh->flags |= HWMOD_INIT_NO_IDLE; if (data->cfg->quirks & SYSC_QUIRK_NO_RESET_ON_INIT) diff --git a/drivers/bus/ti-sysc.c b/drivers/bus/ti-sysc.c index 647caccacee6..bc315f1d3bf8 100644 --- a/drivers/bus/ti-sysc.c +++ b/drivers/bus/ti-sysc.c @@ -920,7 +920,8 @@ static int sysc_init_module(struct sysc *ddata) { int error; - if (ddata->cfg.quirks & SYSC_QUIRK_NO_IDLE_ON_INIT) { + if (ddata->cfg.quirks & + (SYSC_QUIRK_NO_IDLE | SYSC_QUIRK_NO_IDLE_ON_INIT)) { ddata->revision = sysc_read_revision(ddata); goto rev_quirks; } @@ -1281,6 +1282,8 @@ static const struct sysc_dts_quirk sysc_dts_quirks[] = { .mask = SYSC_QUIRK_NO_IDLE_ON_INIT, }, { .name = "ti,no-reset-on-init", .mask = SYSC_QUIRK_NO_RESET_ON_INIT, }, + { .name = "ti,no-idle", + .mask = SYSC_QUIRK_NO_IDLE, }, }; static void sysc_parse_dts_quirks(struct sysc *ddata, struct device_node *np, diff --git a/include/linux/platform_data/ti-sysc.h b/include/linux/platform_data/ti-sysc.h index 1ea3aab972b4..fa97b8c5d26d 100644 --- a/include/linux/platform_data/ti-sysc.h +++ b/include/linux/platform_data/ti-sysc.h @@ -46,8 +46,9 @@ struct sysc_regbits { s8 emufree_shift; }; -#define SYSC_QUIRK_LEGACY_IDLE BIT(8) -#define SYSC_QUIRK_RESET_STATUS BIT(7) +#define SYSC_QUIRK_LEGACY_IDLE BIT(9) +#define SYSC_QUIRK_RESET_STATUS BIT(8) +#define SYSC_QUIRK_NO_IDLE BIT(7) #define SYSC_QUIRK_NO_IDLE_ON_INIT BIT(6) #define SYSC_QUIRK_NO_RESET_ON_INIT BIT(5) #define SYSC_QUIRK_OPT_CLKS_NEEDED BIT(4) -- cgit v1.2.3 From 28f7c994255a9811caa17253353036559852c99c Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Sat, 30 Mar 2019 10:45:58 -0300 Subject: docs: Makefile: use latexmk if available In the past, Sphinx was generating a LaTex Makefile that would run xelatex 3 times. Running it multiple times is needed in order to make the indexes right. However, newer versions of it runs it just once, as it expects the machine to use the "latexmk" build, with automatically detects the need for rebuilds. So, add a logic at the Makefile in order to detect if latexmk is installed. If so, it will call it. As an additional bonus, the output of latexmk is a little bit better, making easier to identify build problems. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/Makefile | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/Makefile b/Documentation/Makefile index 9786957c6a35..e889e7cb8511 100644 --- a/Documentation/Makefile +++ b/Documentation/Makefile @@ -28,8 +28,13 @@ ifeq ($(HAVE_SPHINX),0) else # HAVE_SPHINX -# User-friendly check for pdflatex +# User-friendly check for pdflatex and latexmk HAVE_PDFLATEX := $(shell if which $(PDFLATEX) >/dev/null 2>&1; then echo 1; else echo 0; fi) +HAVE_LATEXMK := $(shell if which latexmk >/dev/null 2>&1; then echo 1; else echo 0; fi) + +ifeq ($(HAVE_LATEXMK),1) + PDFLATEX := latexmk -$(PDFLATEX) +endif #HAVE_LATEXMK # Internal variables. PAPEROPT_a4 = -D latex_paper_size=a4 @@ -82,7 +87,7 @@ pdfdocs: else # HAVE_PDFLATEX pdfdocs: latexdocs - $(foreach var,$(SPHINXDIRS), $(MAKE) PDFLATEX=$(PDFLATEX) LATEXOPTS="$(LATEXOPTS)" -C $(BUILDDIR)/$(var)/latex || exit;) + $(foreach var,$(SPHINXDIRS), $(MAKE) PDFLATEX="$(PDFLATEX)" LATEXOPTS="$(LATEXOPTS)" -C $(BUILDDIR)/$(var)/latex || exit;) endif # HAVE_PDFLATEX -- cgit v1.2.3 From 0663a0588440e6f3d41667287b6f001161d2d7c7 Mon Sep 17 00:00:00 2001 From: Federico Vaga Date: Wed, 27 Mar 2019 23:28:35 +0100 Subject: doc:it: alignement clarification about sign-off and Co-developed-by Align Italian documentation after the following patch to the main documents commit 24a2bb90741b docs: Clarify the usage and sign-off requirements for Co-developed-by Signed-off-by: Federico Vaga Signed-off-by: Jonathan Corbet --- .../translations/it_IT/process/5.Posting.rst | 10 +++--- .../it_IT/process/submitting-patches.rst | 41 +++++++++++++++++++--- 2 files changed, 42 insertions(+), 9 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/it_IT/process/5.Posting.rst b/Documentation/translations/it_IT/process/5.Posting.rst index b979266aa884..1476d51eb5e5 100644 --- a/Documentation/translations/it_IT/process/5.Posting.rst +++ b/Documentation/translations/it_IT/process/5.Posting.rst @@ -233,10 +233,12 @@ Le etichette in uso più comuni sono: :ref:`Documentation/translations/it_IT/process/submitting-patches.rst `. Codice che non presenta una firma appropriata non potrà essere integrato. - - Co-developed-by: indica che la patch è stata sviluppata anche da un altro - sviluppatore assieme all'autore originale. Questo è utile quando più - persone lavorano sulla stessa patch. Da notare che questa persona deve - avere anche una riga "Signed-off-by:" nella patch. + - Co-developed-by: indica che la patch è stata cosviluppata da diversi + sviluppatori; viene usato per assegnare più autori (in aggiunta a quello + associato all'etichetta From:) quando più persone lavorano ad una patch. + Ogni Co-developed-by: dev'essere seguito immediatamente da un Signed-off-by: + del corrispondente coautore. Maggiori dettagli ed esempi sono disponibili + in :ref:`Documentation/translations/it_IT/process/submitting-patches.rst `. - Acked-by: indica il consenso di un altro sviluppatore (spesso il manutentore del codice in oggetto) all'integrazione della patch nel kernel. diff --git a/Documentation/translations/it_IT/process/submitting-patches.rst b/Documentation/translations/it_IT/process/submitting-patches.rst index 713fba075b9d..7d7ea92c5c5a 100644 --- a/Documentation/translations/it_IT/process/submitting-patches.rst +++ b/Documentation/translations/it_IT/process/submitting-patches.rst @@ -567,11 +567,42 @@ alcunché - ma dovrebbe indicare che la persona ha ricevuto una copia della patch. Questa etichetta documenta che terzi potenzialmente interessati sono stati inclusi nella discussione. -L'etichetta Co-developed-by: indica che la patch è stata scritta dall'autore in -collaborazione con un altro sviluppatore. Qualche volta questo è utile quando -più persone lavorano sulla stessa patch. Notate, questa persona deve avere -nella patch anche una riga Signed-off-by:. +Co-developed-by: indica che la patch è stata cosviluppata da diversi +sviluppatori; viene usato per assegnare più autori (in aggiunta a quello +associato all'etichetta From:) quando più persone lavorano ad una patch. Dato +che Co-developed-by: implica la paternità della patch, ogni Co-developed-by: +dev'essere seguito immediatamente dal Signed-off-by: del corrispondente +coautore. Qui si applica la procedura di base per sign-off, in pratica +l'ordine delle etichette Signed-off-by: dovrebbe riflettere il più possibile +l'ordine cronologico della storia della patch, indipendentemente dal fatto che +la paternità venga assegnata via From: o Co-developed-by:. Da notare che +l'ultimo Signed-off-by: dev'essere quello di colui che ha sottomesso la patch. +Notate anche che l'etichetta From: è opzionale quando l'autore in From: è +anche la persona (e indirizzo email) indicato nel From: dell'intestazione +dell'email. + +Esempio di una patch sottomessa dall'autore in From::: + + + + Co-developed-by: First Co-Author + Signed-off-by: First Co-Author + Co-developed-by: Second Co-Author + Signed-off-by: Second Co-Author + Signed-off-by: From Author + +Esempio di una patch sottomessa dall'autore Co-developed-by::: + + From: From Author + + + + Co-developed-by: Random Co-Author + Signed-off-by: Random Co-Author + Signed-off-by: From Author + Co-developed-by: Submitting Co-Author + Signed-off-by: Submitting Co-Author 13) Utilizzare Reported-by:, Tested-by:, Reviewed-by:, Suggested-by: e Fixes: ----------------------------------------------------------------------------- @@ -719,7 +750,7 @@ Un paio di esempi di oggetti:: La riga ``from`` dev'essere la prima nel corpo del messaggio ed è nel formato: - From: Original Author + From: Patch Author La riga ``from`` indica chi verrà accreditato nel changelog permanente come l'autore della patch. Se la riga ``from`` è mancante, allora per determinare -- cgit v1.2.3 From bba757d8578ff65b5168f6420552fbba3c159774 Mon Sep 17 00:00:00 2001 From: Joe Perches Date: Sat, 30 Mar 2019 10:25:03 -0700 Subject: coding-style.rst: Generic alloc functions do not need OOM logging Generic allocation functions already emit a dump_stack() so additional error logging isn't useful. Document it as such and add a reference to the allocation API. Signed-off-by: Joe Perches Signed-off-by: Jonathan Corbet --- Documentation/process/coding-style.rst | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/process/coding-style.rst b/Documentation/process/coding-style.rst index 8ea913e99fa1..fa864a51e6ea 100644 --- a/Documentation/process/coding-style.rst +++ b/Documentation/process/coding-style.rst @@ -843,7 +843,8 @@ used. The kernel provides the following general purpose memory allocators: kmalloc(), kzalloc(), kmalloc_array(), kcalloc(), vmalloc(), and vzalloc(). Please refer to the API documentation for further information -about them. +about them. :ref:`Documentation/core-api/memory-allocation.rst +` The preferred form for passing a size of a struct is the following: @@ -874,6 +875,9 @@ The preferred form for allocating a zeroed array is the following: Both forms check for overflow on the allocation size n * sizeof(...), and return NULL if that occurred. +These generic allocation functions all emit a stack dump on failure when used +without __GFP_NOWARN so there is no use in emitting an additional failure +message when NULL is returned. 15) The inline disease ---------------------- -- cgit v1.2.3 From d5ff1adb3809e2f74a3b57cea2e57c8e37d693c4 Mon Sep 17 00:00:00 2001 From: Neil Armstrong Date: Fri, 15 Mar 2019 14:56:54 +0100 Subject: dt-bindings: gpu: mali-midgard: Add resets property The Amlogic ARM Mali Midgard requires reset controls to power on and software reset the GPU, adds these as optional in the bindings. Signed-off-by: Neil Armstrong Reviewed-by: Rob Herring Signed-off-by: Kevin Hilman --- Documentation/devicetree/bindings/gpu/arm,mali-midgard.txt | 14 ++++++++++++++ 1 file changed, 14 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/gpu/arm,mali-midgard.txt b/Documentation/devicetree/bindings/gpu/arm,mali-midgard.txt index 18a2cde2e5f3..1b1a74129141 100644 --- a/Documentation/devicetree/bindings/gpu/arm,mali-midgard.txt +++ b/Documentation/devicetree/bindings/gpu/arm,mali-midgard.txt @@ -37,6 +37,20 @@ Optional properties: - operating-points-v2 : Refer to Documentation/devicetree/bindings/opp/opp.txt for details. +- resets : Phandle of the GPU reset line. + +Vendor-specific bindings +------------------------ + +The Mali GPU is integrated very differently from one SoC to +another. In order to accomodate those differences, you have the option +to specify one more vendor-specific compatible, among: + +- "amlogic,meson-gxm-mali" + Required properties: + - resets : Should contain phandles of : + + GPU reset line + + GPU APB glue reset line Example for a Mali-T760: -- cgit v1.2.3 From a957abb58ddfc83fa95406bb97b4541f30c78421 Mon Sep 17 00:00:00 2001 From: Thor Thayer Date: Mon, 11 Mar 2019 17:18:04 -0500 Subject: dt-bindings: arm: socfpga: Add S10 System Manager binding Add the device tree bindings for the Stratix10 System Manager. Signed-off-by: Thor Thayer Reviewed-by: Rob Herring Reviewed-by: Arnd Bergmann Signed-off-by: Lee Jones --- .../devicetree/bindings/arm/altera/socfpga-system.txt | 12 ++++++++++++ 1 file changed, 12 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/altera/socfpga-system.txt b/Documentation/devicetree/bindings/arm/altera/socfpga-system.txt index f4d04a067282..82edbaaa3f85 100644 --- a/Documentation/devicetree/bindings/arm/altera/socfpga-system.txt +++ b/Documentation/devicetree/bindings/arm/altera/socfpga-system.txt @@ -11,3 +11,15 @@ Example: reg = <0xffd08000 0x1000>; cpu1-start-addr = <0xffd080c4>; }; + +ARM64 - Stratix10 +Required properties: +- compatible : "altr,sys-mgr-s10" +- reg : Should contain 1 register range(address and length) + for system manager register. + +Example: + sysmgr@ffd12000 { + compatible = "altr,sys-mgr-s10"; + reg = <0xffd12000 0x228>; + }; -- cgit v1.2.3 From de7b77e5bb9451417ca57f1b6501da654587c048 Mon Sep 17 00:00:00 2001 From: Josh Poimboeuf Date: Wed, 27 Mar 2019 07:00:29 -0500 Subject: cpu/hotplug: Create SMT sysfs interface for all arches Make the /sys/devices/system/cpu/smt/* files available on all arches, so user space has a consistent way to detect whether SMT is enabled. The 'control' file now shows 'notimplemented' for architectures which don't yet have CONFIG_HOTPLUG_SMT. [ tglx: Make notimplemented a real state ] Signed-off-by: Josh Poimboeuf Signed-off-by: Thomas Gleixner Cc: Andrea Arcangeli Cc: Waiman Long Cc: Peter Zijlstra Cc: Jiri Kosina Link: https://lkml.kernel.org/r/469c2b98055f2c41e75748e06447d592a64080c9.1553635520.git.jpoimboe@redhat.com --- Documentation/ABI/testing/sysfs-devices-system-cpu | 10 ++-- include/linux/cpu.h | 3 +- kernel/cpu.c | 64 +++++++++++++--------- 3 files changed, 47 insertions(+), 30 deletions(-) (limited to 'Documentation') diff --git a/Documentation/ABI/testing/sysfs-devices-system-cpu b/Documentation/ABI/testing/sysfs-devices-system-cpu index 9605dbd4b5b5..5eea46fefcb2 100644 --- a/Documentation/ABI/testing/sysfs-devices-system-cpu +++ b/Documentation/ABI/testing/sysfs-devices-system-cpu @@ -511,10 +511,12 @@ Description: Control Symetric Multi Threading (SMT) control: Read/write interface to control SMT. Possible values: - "on" SMT is enabled - "off" SMT is disabled - "forceoff" SMT is force disabled. Cannot be changed. - "notsupported" SMT is not supported by the CPU + "on" SMT is enabled + "off" SMT is disabled + "forceoff" SMT is force disabled. Cannot be changed. + "notsupported" SMT is not supported by the CPU + "notimplemented" SMT runtime toggling is not + implemented for the architecture If control status is "forceoff" or "notsupported" writes are rejected. diff --git a/include/linux/cpu.h b/include/linux/cpu.h index 5041357d0297..ae99dde02320 100644 --- a/include/linux/cpu.h +++ b/include/linux/cpu.h @@ -175,6 +175,7 @@ enum cpuhp_smt_control { CPU_SMT_DISABLED, CPU_SMT_FORCE_DISABLED, CPU_SMT_NOT_SUPPORTED, + CPU_SMT_NOT_IMPLEMENTED, }; #if defined(CONFIG_SMP) && defined(CONFIG_HOTPLUG_SMT) @@ -182,7 +183,7 @@ extern enum cpuhp_smt_control cpu_smt_control; extern void cpu_smt_disable(bool force); extern void cpu_smt_check_topology(void); #else -# define cpu_smt_control (CPU_SMT_ENABLED) +# define cpu_smt_control (CPU_SMT_NOT_IMPLEMENTED) static inline void cpu_smt_disable(bool force) { } static inline void cpu_smt_check_topology(void) { } #endif diff --git a/kernel/cpu.c b/kernel/cpu.c index 6754f3ecfd94..b8bf3f93e39b 100644 --- a/kernel/cpu.c +++ b/kernel/cpu.c @@ -2033,19 +2033,6 @@ static const struct attribute_group cpuhp_cpu_root_attr_group = { #ifdef CONFIG_HOTPLUG_SMT -static const char *smt_states[] = { - [CPU_SMT_ENABLED] = "on", - [CPU_SMT_DISABLED] = "off", - [CPU_SMT_FORCE_DISABLED] = "forceoff", - [CPU_SMT_NOT_SUPPORTED] = "notsupported", -}; - -static ssize_t -show_smt_control(struct device *dev, struct device_attribute *attr, char *buf) -{ - return snprintf(buf, PAGE_SIZE - 2, "%s\n", smt_states[cpu_smt_control]); -} - static void cpuhp_offline_cpu_device(unsigned int cpu) { struct device *dev = get_cpu_device(cpu); @@ -2116,9 +2103,10 @@ static int cpuhp_smt_enable(void) return ret; } + static ssize_t -store_smt_control(struct device *dev, struct device_attribute *attr, - const char *buf, size_t count) +__store_smt_control(struct device *dev, struct device_attribute *attr, + const char *buf, size_t count) { int ctrlval, ret; @@ -2156,14 +2144,44 @@ store_smt_control(struct device *dev, struct device_attribute *attr, unlock_device_hotplug(); return ret ? ret : count; } + +#else /* !CONFIG_HOTPLUG_SMT */ +static ssize_t +__store_smt_control(struct device *dev, struct device_attribute *attr, + const char *buf, size_t count) +{ + return -ENODEV; +} +#endif /* CONFIG_HOTPLUG_SMT */ + +static const char *smt_states[] = { + [CPU_SMT_ENABLED] = "on", + [CPU_SMT_DISABLED] = "off", + [CPU_SMT_FORCE_DISABLED] = "forceoff", + [CPU_SMT_NOT_SUPPORTED] = "notsupported", + [CPU_SMT_NOT_IMPLEMENTED] = "notimplemented", +}; + +static ssize_t +show_smt_control(struct device *dev, struct device_attribute *attr, char *buf) +{ + const char *state = smt_states[cpu_smt_control]; + + return snprintf(buf, PAGE_SIZE - 2, "%s\n", state); +} + +static ssize_t +store_smt_control(struct device *dev, struct device_attribute *attr, + const char *buf, size_t count) +{ + return __store_smt_control(dev, attr, buf, count); +} static DEVICE_ATTR(control, 0644, show_smt_control, store_smt_control); static ssize_t show_smt_active(struct device *dev, struct device_attribute *attr, char *buf) { - bool active = topology_max_smt_threads() > 1; - - return snprintf(buf, PAGE_SIZE - 2, "%d\n", active); + return snprintf(buf, PAGE_SIZE - 2, "%d\n", sched_smt_active()); } static DEVICE_ATTR(active, 0444, show_smt_active, NULL); @@ -2179,21 +2197,17 @@ static const struct attribute_group cpuhp_smt_attr_group = { NULL }; -static int __init cpu_smt_state_init(void) +static int __init cpu_smt_sysfs_init(void) { return sysfs_create_group(&cpu_subsys.dev_root->kobj, &cpuhp_smt_attr_group); } -#else -static inline int cpu_smt_state_init(void) { return 0; } -#endif - static int __init cpuhp_sysfs_init(void) { int cpu, ret; - ret = cpu_smt_state_init(); + ret = cpu_smt_sysfs_init(); if (ret) return ret; @@ -2214,7 +2228,7 @@ static int __init cpuhp_sysfs_init(void) return 0; } device_initcall(cpuhp_sysfs_init); -#endif +#endif /* CONFIG_SYSFS && CONFIG_HOTPLUG_CPU */ /* * cpu_bit_bitmap[] is a special, "compressed" data structure that -- cgit v1.2.3 From 5ee23456041a95c2236063eeba68236f7ee0af51 Mon Sep 17 00:00:00 2001 From: Alessia Mantegazza Date: Sat, 30 Mar 2019 22:19:56 +0100 Subject: doc:it_IT: translation for maintainer-pgp-guide It translates the maintainer-pgp-guide in Italian. Signed-off-by: Alessia Mantegazza Signed-off-by: Federico Vaga Signed-off-by: Jonathan Corbet --- .../it_IT/process/maintainer-pgp-guide.rst | 939 ++++++++++++++++++++- 1 file changed, 936 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/it_IT/process/maintainer-pgp-guide.rst b/Documentation/translations/it_IT/process/maintainer-pgp-guide.rst index 24a133f0a51d..276db0e37f43 100644 --- a/Documentation/translations/it_IT/process/maintainer-pgp-guide.rst +++ b/Documentation/translations/it_IT/process/maintainer-pgp-guide.rst @@ -1,13 +1,946 @@ .. include:: ../disclaimer-ita.rst :Original: :ref:`Documentation/process/maintainer-pgp-guide.rst ` +:Translator: Alessia Mantegazza .. _it_pgpguide: +========================================= +La guida a PGP per manutentori del kernel +========================================= + +:Author: Konstantin Ryabitsev + +Questo documento è destinato agli sviluppatori del kernel Linux, in particolar +modo ai manutentori. Contiene degli approfondimenti riguardo informazioni che +sono state affrontate in maniera più generale nella sezione +"`Protecting Code Integrity`_" pubblicata dalla Linux Foundation. +Per approfondire alcuni argomenti trattati in questo documento è consigliato +leggere il documento sopraindicato + +.. _`Protecting Code Integrity`: https://github.com/lfit/itpol/blob/master/protecting-code-integrity.md + +Il ruolo di PGP nello sviluppo del kernel Linux +=============================================== + +PGP aiuta ad assicurare l'integrità del codice prodotto dalla comunità +di sviluppo del kernel e, in secondo luogo, stabilisce canali di comunicazione +affidabili tra sviluppatori attraverso lo scambio di email firmate con PGP. + +Il codice sorgente del kernel Linux è disponibile principalmente in due +formati: + +- repositori distribuiti di sorgenti (git) +- rilasci periodici di istantanee (archivi tar) + +Sia i repositori git che gli archivi tar portano le firme PGP degli +sviluppatori che hanno creato i rilasci ufficiali del kernel. Queste firme +offrono una garanzia crittografica che le versioni scaricabili rese disponibili +via kernel.org, o altri portali, siano identiche a quelle che gli sviluppatori +hanno sul loro posto di lavoro. A tal scopo: + +- i repositori git forniscono firme PGP per ogni tag +- gli archivi tar hanno firme separate per ogni archivio + +.. _it_devs_not_infra: + +Fidatevi degli sviluppatori e non dell'infrastruttura +----------------------------------------------------- + +Fin dal 2011, quando i sistemi di kernel.org furono compromessi, il principio +generale del progetto Kernel Archives è stato quello di assumere che qualsiasi +parte dell'infrastruttura possa essere compromessa in ogni momento. Per questa +ragione, gli amministratori hanno intrapreso deliberatemene dei passi per +enfatizzare che la fiducia debba risiedere sempre negli sviluppatori e mai nel +codice che gestisce l'infrastruttura, indipendentemente da quali che siano le +pratiche di sicurezza messe in atto. + +Il principio sopra indicato è la ragione per la quale è necessaria questa +guida. Vogliamo essere sicuri che il riporre la fiducia negli sviluppatori +non sia fatto semplicemente per incolpare qualcun'altro per future falle di +sicurezza. L'obiettivo è quello di fornire una serie di linee guida che gli +sviluppatori possano seguire per creare un ambiente di lavoro sicuro e +salvaguardare le chiavi PGP usate nello stabilire l'integrità del kernel Linux +stesso. + +.. _it_pgp_tools: + +Strumenti PGP +============= + +Usare GnuPG v2 +-------------- + +La vostra distribuzione potrebbe avere già installato GnuPG, dovete solo +verificare che stia utilizzando la versione 2.x e non la serie 1.4 -- +molte distribuzioni forniscono entrambe, di base il comando ''gpg'' +invoca GnuPG v.1. Per controllate usate:: + + $ gpg --version | head -n1 + +Se visualizzate ``gpg (GnuPG) 1.4.x``, allora state usando GnuPG v.1. +Provate il comando ``gpg2`` (se non lo avete, potreste aver bisogno +di installare il pacchetto gnupg2):: + + $ gpg2 --version | head -n1 + +Se visualizzate ``gpg (GnuPG) 2.x.x``, allora siete pronti a partire. +Questa guida assume che abbiate la versione 2.2.(o successiva) di GnuPG. +Se state usando la versione 2.0, alcuni dei comandi indicati qui non +funzioneranno, in questo caso considerate un aggiornamento all'ultima versione, +la 2.2. Versioni di gnupg-2.1.11 e successive dovrebbero essere compatibili +per gli obiettivi di questa guida. + +Se avete entrambi i comandi: ``gpg`` e ``gpg2``, assicuratevi di utilizzare +sempre la versione V2, e non quella vecchia. Per evitare errori potreste creare +un alias:: + + $ alias gpg=gpg2 + +Potete mettere questa opzione nel vostro ``.bashrc`` in modo da essere sicuri. + +Configurare le opzioni di gpg-agent +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +L'agente GnuPG è uno strumento di aiuto che partirà automaticamente ogni volta +che userete il comando ``gpg`` e funzionerà in background con l'obiettivo di +individuare la passphrase. Ci sono due opzioni che dovreste conoscere +per personalizzare la scadenza della passphrase nella cache: + +- ``default-cache-ttl`` (secondi): Se usate ancora la stessa chiave prima + che il time-to-live termini, il conto alla rovescia si resetterà per un + altro periodo. Di base è di 600 (10 minuti). + +- ``max-cache-ttl`` (secondi): indipendentemente da quanto sia recente l'ultimo + uso della chiave da quando avete inserito la passphrase, se il massimo + time-to-live è scaduto, dovrete reinserire nuovamente la passphrase. + Di base è di 30 minuti. + +Se ritenete entrambe questi valori di base troppo corti (o troppo lunghi), +potete creare il vostro file ``~/.gnupg/gpg-agent.conf`` ed impostare i vostri +valori:: + + # set to 30 minutes for regular ttl, and 2 hours for max ttl + default-cache-ttl 1800 + max-cache-ttl 7200 + +.. note:: + + Non è più necessario far partire l'agente gpg manualmente all'inizio della + vostra sessione. Dovreste controllare i file rc per rimuovere tutto ciò che + riguarda vecchie le versioni di GnuPG, poiché potrebbero non svolgere più + bene il loro compito. + +Impostare un *refresh* con cronjob +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Potreste aver bisogno di rinfrescare regolarmente il vostro portachiavi in +modo aggiornare le chiavi pubbliche di altre persone, lavoro che è svolto +al meglio con un cronjob giornaliero:: + + @daily /usr/bin/gpg2 --refresh >/dev/null 2>&1 + +Controllate il percorso assoluto del vostro comando ``gpg`` o ``gpg2`` e usate +il comando ``gpg2`` se per voi ``gpg`` corrisponde alla versione GnuPG v.1. + +.. _it_master_key: + +Proteggere la vostra chiave PGP primaria ======================================== -Guida a PGP per i manutentori del kernel -======================================== + +Questa guida parte dal presupposto che abbiate già una chiave PGP che usate +per lo sviluppo del kernel Linux. Se non ne avete ancora una, date uno sguardo +al documento "`Protecting Code Integrity`_" che abbiamo menzionato prima. + +Dovreste inoltre creare una nuova chiave se quella attuale è inferiore a 2048 +bit (RSA). + +Chiave principale o sottochiavi +------------------------------- + +Le sottochiavi sono chiavi PGP totalmente indipendenti, e sono collegate alla +chiave principale attraverso firme certificate. È quindi importante +comprendere i seguenti punti: + +1. Non ci sono differenze tecniche tra la chiave principale e la sottochiave. +2. In fesa di creazione, assegniamo limitazioni funzionali ad ogni chiave + assegnando capacità specifiche. +3. Una chiave PGP può avere 4 capacità: + + - **[S]** può essere usata per firmare + - **[E]** può essere usata per criptare + - **[A]** può essere usata per autenticare + - **[C]** può essere usata per certificare altre chiavi + +4. Una singola chiave può avere più capacità +5. Una sottochiave è completamente indipendente dalla chiave principale. + Un messaggio criptato con la sottochiave non può essere decrittato con + quella principale. Se perdete la vostra sottochiave privata, non può + essere rigenerata in nessun modo da quella principale. + +La chiave con capacità **[C]** (certify) è identificata come la chiave +principale perché è l'unica che può essere usata per indicare la relazione +con altre chiavi. Solo la chiave **[C]** può essere usata per: + +- Aggiungere o revocare altre chiavi (sottochiavi) che hanno capacità S/E/A +- Aggiungere, modificare o eliminare le identità (unids) associate alla chiave +- Aggiungere o modificare la data di termine di sé stessa o di ogni sottochiave +- Firmare le chiavi di altre persone a scopo di creare una rete di fiducia + +Di base, alla creazione di nuove chiavi, GnuPG genera quanto segue: + +- Una chiave madre che porta sia la capacità di certificazione che quella + di firma (**[SC]**) +- Una sottochiave separata con capacità di criptaggio (**[E]**) + +Se avete usato i parametri di base per generare la vostra chiave, quello +sarà il risultato. Potete verificarlo utilizzando ``gpg --list-secret-keys``, +per esempio:: + + sec rsa2048 2018-01-23 [SC] [expires: 2020-01-23] + 000000000000000000000000AAAABBBBCCCCDDDD + uid [ultimate] Alice Dev + ssb rsa2048 2018-01-23 [E] [expires: 2020-01-23] + +Qualsiasi chiave che abbia la capacità **[C]** è la vostra chiave madre, +indipendentemente da quali altre capacità potreste averle assegnato. + +La lunga riga sotto la voce ``sec`` è la vostra impronta digitale -- +negli esempi che seguono, quando vedere ``[fpr]`` ci si riferisce a questa +stringa di 40 caratteri. + +Assicuratevi che la vostra passphrase sia forte +----------------------------------------------- + +GnuPG utilizza le passphrases per criptare la vostra chiave privata prima +di salvarla sul disco. In questo modo, anche se il contenuto della vostra +cartella ``.gnupg`` venisse letto o trafugato nella sia interezza, gli +attaccanti non potrebbero comunque utilizzare le vostre chiavi private senza +aver prima ottenuto la passphrase per decriptarle. + +È assolutamente essenziale che le vostre chiavi private siano protette da +una passphrase forte. Per impostarla o cambiarla, usate:: + + $ gpg --change-passphrase [fpr] + +Create una sottochiave di firma separata +---------------------------------------- + +Il nostro obiettivo è di proteggere la chiave primaria spostandola su un +dispositivo sconnesso dalla rete, dunque se avete solo una chiave combinata +**[SC]** allora dovreste creare una sottochiave di firma separata:: + + $ gpg --quick-add-key [fpr] ed25519 sign + +Ricordate di informare il keyserver del vostro cambiamento, cosicché altri +possano ricevere la vostra nuova sottochiave:: + + $ gpg --send-key [fpr] + +.. note:: Supporto ECC in GnuPG + GnuPG 2.1 e successivi supportano pienamente *Elliptic Curve Cryptography*, + con la possibilità di combinare sottochiavi ECC con le tradizionali chiavi + primarie RSA. Il principale vantaggio della crittografia ECC è che è molto + più veloce da calcolare e crea firme più piccole se confrontate byte per + byte con le chiavi RSA a più di 2048 bit. A meno che non pensiate di + utilizzare un dispositivo smartcard che non supporta le operazioni ECC, vi + raccomandiamo ti creare sottochiavi di firma ECC per il vostro lavoro col + kernel. + + Se per qualche ragione preferite rimanere con sottochiavi RSA, nel comando + precedente, sostituite "ed25519" con "rsa2048". + +Copia di riserva della chiave primaria per gestire il recupero da disastro +-------------------------------------------------------------------------- + +Maggiori sono le firme di altri sviluppatori che vengono applicate alla vostra, +maggiori saranno i motivi per avere una copia di riserva che non sia digitale, +al fine di effettuare un recupero da disastro. + +Il modo migliore per creare una copia fisica della vostra chiave privata è +l'uso del programma ``paperkey``. Consultate ``man paperkey`` per maggiori +dettagli sul formato dell'output ed i suoi punti di forza rispetto ad altre +soluzioni. Paperkey dovrebbe essere già pacchettizzato per la maggior parte +delle distribuzioni. + +Eseguite il seguente comando per creare una copia fisica di riserva della +vostra chiave privata:: + + $ gpg --export-secret-key [fpr] | paperkey -o /tmp/key-backup.txt + +Stampate il file (o fate un pipe direttamente verso lpr), poi prendete +una penna e scrivete la passphare sul margine del foglio. **Questo è +caldamente consigliato** perché la copia cartacea è comunque criptata con +la passphrase, e se mai doveste cambiarla non vi ricorderete qual'era al +momento della creazione di quella copia -- *garantito*. + +Mettete la copia cartacea e la passphrase scritta a mano in una busta e +mettetela in un posto sicuro e ben protetto, preferibilmente fuori casa, +magari in una cassetta di sicurezza in banca. + +.. note:: + + Probabilmente la vostra stampante non è più quello stupido dispositivo + connesso alla porta parallela, ma dato che il suo output è comunque + criptato con la passphrase, eseguire la stampa in un sistema "cloud" + moderno dovrebbe essere comunque relativamente sicuro. Un'opzione potrebbe + essere quella di cambiare la passphrase della vostra chiave primaria + subito dopo aver finito con paperkey. + +Copia di riserva di tutta la cartella GnuPG +------------------------------------------- .. warning:: - TODO ancora da tradurre + **!!!Non saltate questo passo!!!** + +Quando avete bisogno di recuperare le vostre chiavi PGP è importante avere +una copia di riserva pronta all'uso. Questo sta su un diverso piano di +prontezza rispetto al recupero da disastro che abbiamo risolto con +``paperkey``. Vi affiderete a queste copie esterne quando dovreste usare la +vostra chiave Certify -- ovvero quando fate modifiche alle vostre chiavi o +firmate le chiavi di altre persone ad una conferenza o ad un gruppo d'incontro. + +Incominciate con una piccola chiavetta di memoria USB (preferibilmente due) +che userete per le copie di riserva. Dovrete criptarle usando LUKS -- fate +riferimento alla documentazione della vostra distribuzione per capire come +fare. + +Per la passphrase di criptazione, potete usare la stessa della vostra chiave +primaria. + +Una volta che il processo di criptazione è finito, reinserite il disco USB ed +assicurativi che venga montato correttamente. Copiate interamente la cartella +``.gnugp`` nel disco criptato:: + + $ cp -a ~/.gnupg /media/disk/foo/gnupg-backup + +Ora dovreste verificare che tutto continui a funzionare:: + + $ gpg --homedir=/media/disk/foo/gnupg-backup --list-key [fpr] + +Se non vedete errori, allora dovreste avere fatto tutto con successo. +Smontate il disco USB, etichettatelo per bene di modo da evitare di +distruggerne il contenuto non appena vi serve una chiavetta USB a caso, ed +infine mettetelo in un posto sicuro -- ma non troppo lontano, perché vi servirà +di tanto in tanto per modificare le identità, aggiungere o revocare +sottochiavi, o firmare le chiavi di altre persone. + +Togliete la chiave primaria dalla vostra home +--------------------------------------------- + +I file che si trovano nella vostra cartella home non sono poi così ben protetti +come potreste pensare. Potrebbero essere letti o trafugati in diversi modi: + +- accidentalmente quando fate una rapida copia della cartella home per + configurare una nuova postazione +- da un amministratore di sistema negligente o malintenzionato +- attraverso copie di riserva insicure +- attraverso malware installato in alcune applicazioni (browser, lettori PDF, + eccetera) +- attraverso coercizione quando attraversate confini internazionali + +Proteggere la vostra chiave con una buona passphare aiuta notevolmente a +ridurre i rischi elencati qui sopra, ma le passphrase possono essere scoperte +attraverso i keylogger, il shoulder-surfing, o altri modi. Per questi motivi, +nella configurazione si raccomanda di rimuove la chiave primaria dalla vostra +cartella home e la si archivia su un dispositivo disconnesso. + +.. warning:: + + Per favore, fate riferimento alla sezione precedente e assicuratevi + di aver fatto una copia di riserva totale della cartella GnuPG. Quello + che stiamo per fare renderà la vostra chiave inutile se non avete delle + copie di riserva utilizzabili! + +Per prima cosa, identificate il keygrip della vostra chiave primaria:: + + $ gpg --with-keygrip --list-key [fpr] + +L'output assomiglierà a questo:: + + pub rsa2048 2018-01-24 [SC] [expires: 2020-01-24] + 000000000000000000000000AAAABBBBCCCCDDDD + Keygrip = 1111000000000000000000000000000000000000 + uid [ultimate] Alice Dev + sub rsa2048 2018-01-24 [E] [expires: 2020-01-24] + Keygrip = 2222000000000000000000000000000000000000 + sub ed25519 2018-01-24 [S] + Keygrip = 3333000000000000000000000000000000000000 + +Trovate la voce keygrid che si trova sotto alla riga ``pub`` (appena sotto +all'impronta digitale della chiave primaria). Questo corrisponderà direttamente +ad un file nella cartella ``~/.gnupg``:: + + $ cd ~/.gnupg/private-keys-v1.d + $ ls + 1111000000000000000000000000000000000000.key + 2222000000000000000000000000000000000000.key + 3333000000000000000000000000000000000000.key + +Quello che dovrete fare è rimuovere il file .key che corrisponde al keygrip +della chiave primaria:: + + $ cd ~/.gnupg/private-keys-v1.d + $ rm 1111000000000000000000000000000000000000.key + +Ora, se eseguite il comando ``--list-secret-keys``, vedrete che la chiave +primaria non compare più (il simbolo ``#`` indica che non è disponibile):: + + $ gpg --list-secret-keys + sec# rsa2048 2018-01-24 [SC] [expires: 2020-01-24] + 000000000000000000000000AAAABBBBCCCCDDDD + uid [ultimate] Alice Dev + ssb rsa2048 2018-01-24 [E] [expires: 2020-01-24] + ssb ed25519 2018-01-24 [S] + +Dovreste rimuovere anche i file ``secring.gpg`` che si trovano nella cartella +``~/.gnupg``, in quanto rimasugli delle versioni precedenti di GnuPG. + +Se non avete la cartella "private-keys-v1.d" +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Se non avete la cartella ``~/.gnupg/private-keys-v1.d``, allora le vostre +chiavi segrete sono ancora salvate nel vecchio file ``secring.gpg`` usato +da GnuPG v1. Effettuare una qualsiasi modifica alla vostra chiave, come +cambiare la passphare o aggiungere una sottochiave, dovrebbe convertire +automaticamente il vecchio formato ``secring.gpg``nel nuovo +``private-keys-v1.d``. + +Una volta che l'avete fatto, assicuratevi di rimuovere il file ``secring.gpg``, +che continua a contenere la vostra chiave privata. + +.. _it_smartcards: + +Spostare le sottochiavi in un apposito dispositivo criptato +=========================================================== + +Nonostante la chiave primaria sia ora al riparo da occhi e mani indiscrete, +le sottochiavi si trovano ancora nella vostra cartella home. Chiunque riesca +a mettere le sue mani su quelle chiavi riuscirà a decriptare le vostre +comunicazioni o a falsificare le vostre firme (se conoscono la passphrase). +Inoltre, ogni volta che viene fatta un'operazione con GnuPG, le chiavi vengono +caricate nella memoria di sistema e potrebbero essere rubate con l'uso di +malware sofisticati (pensate a Meltdown e a Spectre). + +Il miglior modo per proteggere le proprie chiave è di spostarle su un +dispositivo specializzato in grado di effettuare operazioni smartcard. + +I benefici di una smartcard +--------------------------- + +Una smartcard contiene un chip crittografico che è capace di immagazzinare +le chiavi private ed effettuare operazioni crittografiche direttamente sulla +carta stessa. Dato che la chiave non lascia mai la smartcard, il sistema +operativo usato sul computer non sarà in grado di accedere alle chiavi. +Questo è molto diverso dai dischi USB criptati che abbiamo usato allo scopo di +avere una copia di riserva sicura -- quando il dispositivo USB è connesso e +montato, il sistema operativo potrà accedere al contenuto delle chiavi private. + +L'uso di un disco USB criptato non può sostituire le funzioni di un dispositivo +capace di operazioni di tipo smartcard. + +Dispositivi smartcard disponibili +--------------------------------- + +A meno che tutti i vostri computer dispongano di lettori smartcard, il modo +più semplice è equipaggiarsi di un dispositivo USB specializzato che +implementi le funzionalità delle smartcard. Sul mercato ci sono diverse +soluzioni disponibili: + +- `Nitrokey Start`_: è Open hardware e Free Software, è basata sul progetto + `GnuK`_ della FSIJ. Ha il supporto per chiavi ECC, ma meno funzionalità di + sicurezza (come la resistenza alla manomissione o alcuni attacchi ad un + canale laterale). +- `Nitrokey Pro`_: è simile alla Nitrokey Start, ma è più resistente alla + manomissione e offre più funzionalità di sicurezza, ma l'ECC. +- `Yubikey 4`_: l'hardware e il software sono proprietari, ma è più economica + della Nitrokey Pro ed è venduta anche con porta USB-C il che è utile con i + computer portatili più recenti. In aggiunta, offre altre funzionalità di + sicurezza come FIDO, U2F, ma non l'ECC + +`Su LWN c'è una buona recensione`_ dei modelli elencati qui sopra e altri. +Se volete usare chiavi ECC, la vostra migliore scelta sul mercato è la +Nitrokey Start. + +.. _`Nitrokey Start`: https://shop.nitrokey.com/shop/product/nitrokey-start-6 +.. _`Nitrokey Pro`: https://shop.nitrokey.com/shop/product/nitrokey-pro-3 +.. _`Yubikey 4`: https://www.yubico.com/product/yubikey-4-series/ +.. _Gnuk: http://www.fsij.org/doc-gnuk/ +.. _`Su LWN c'è una buona recensione`: https://lwn.net/Articles/736231/ + +Configurare il vostro dispositivo smartcard +------------------------------------------- + +Il vostro dispositivo smartcard dovrebbe iniziare a funzionare non appena +lo collegate ad un qualsiasi computer Linux moderno. Potete verificarlo +eseguendo:: + + $ gpg --card-status + +Se vedete tutti i dettagli della smartcard, allora ci siamo. Sfortunatamente, +affrontare tutti i possibili motivi per cui le cose potrebbero non funzionare +non è lo scopo di questa guida. Se avete problemi nel far funzionare la carta +con GnuPG, cercate aiuto attraverso i soliti canali di supporto. + +Per configurare la vostra smartcard, dato che non c'è una via facile dalla +riga di comando, dovrete usate il menu di GnuPG:: + + $ gpg --card-edit + [...omitted...] + gpg/card> admin + Admin commands are allowed + gpg/card> passwd + +Dovreste impostare il PIN dell'utente (1), quello dell'amministratore (3) e il +codice di reset (4). Assicuratevi di annotare e salvare questi codici in un +posto sicuro -- specialmente il PIN dell'amministratore e il codice di reset +(che vi permetterà di azzerare completamente la smartcard). Il PIN +dell'amministratore viene usato così raramente che è inevitabile dimenticarselo +se non lo si annota. + +Tornando al nostro menu, potete impostare anche altri valori (come il nome, +il sesso, informazioni d'accesso, eccetera), ma non sono necessari e aggiunge +altre informazioni sulla carta che potrebbero trapelare in caso di smarrimento. + +.. note:: + + A dispetto del nome "PIN", né il PIN utente né quello dell'amministratore + devono essere esclusivamente numerici. + +Spostare le sottochiavi sulla smartcard +--------------------------------------- + +Uscite dal menu (usando "q") e salverete tutte le modifiche. Poi, spostiamo +tutte le sottochiavi sulla smartcard. Per la maggior parte delle operazioni +vi serviranno sia la passphrase della chiave PGP che il PIN +dell'amministratore:: + + $ gpg --edit-key [fpr] + + Secret subkeys are available. + + pub rsa2048/AAAABBBBCCCCDDDD + created: 2018-01-23 expires: 2020-01-23 usage: SC + trust: ultimate validity: ultimate + ssb rsa2048/1111222233334444 + created: 2018-01-23 expires: never usage: E + ssb ed25519/5555666677778888 + created: 2017-12-07 expires: never usage: S + [ultimate] (1). Alice Dev + + gpg> + +Usando ``--edit-key`` si tornerà alla modalità menu e noterete che +la lista delle chiavi è leggermente diversa. Da questo momento in poi, +tutti i comandi saranno eseguiti nella modalità menu, come indicato +da ``gpg>``. + +Per prima cosa, selezioniamo la chiave che verrà messa sulla carta -- +potete farlo digitando ``key 1`` (è la prima della lista, la sottochiave +**[E]**):: + + gpg> key 1 + +Nel'output dovreste vedere ``ssb*`` associato alla chiave **[E]**. Il simbolo +``*`` indica che la chiave è stata "selezionata". Funziona come un +interruttore, ovvero se scrivete nuovamente ``key 1``, il simbolo ``*`` sparirà +e la chiave non sarà più selezionata. + +Ora, spostiamo la chiave sulla smartcard:: + + gpg> keytocard + Please select where to store the key: + (2) Encryption key + Your selection? 2 + +Dato che è la nostra chiave **[E]**, ha senso metterla nella sezione criptata. +Quando confermerete la selezione, vi verrà chiesta la passphrase della vostra +chiave PGP, e poi il PIN dell'amministratore. Se il comando ritorna senza +errori, allora la vostra chiave è stata spostata con successo. + +**Importante**: digitate nuovamente ``key 1`` per deselezionare la prima chiave +e selezionate la seconda chiave **[S]** con ``key 2``:: + + gpg> key 1 + gpg> key 2 + gpg> keytocard + Please select where to store the key: + (1) Signature key + (3) Authentication key + Your selection? 1 + +Potete usare la chiave **[S]** sia per firmare che per autenticare, ma vogliamo +che sia nella sezione di firma, quindi scegliete (1). Ancora una volta, se il +comando ritorna senza errori, allora l'operazione è avvenuta con successo:: + + gpg> q + Save changes? (y/N) y + +Salvando le modifiche cancellerete dalla vostra cartella home tutte le chiavi +che avete spostato sulla carta (ma questo non è un problema, perché abbiamo +fatto delle copie di sicurezza nel caso in cui dovessimo configurare una +nuova smartcard). + +Verificare che le chiavi siano state spostate +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Ora, se doveste usare l'opzione ``--list-secret-keys``, vedrete una +sottile differenza nell'output:: + + $ gpg --list-secret-keys + sec# rsa2048 2018-01-24 [SC] [expires: 2020-01-24] + 000000000000000000000000AAAABBBBCCCCDDDD + uid [ultimate] Alice Dev + ssb> rsa2048 2018-01-24 [E] [expires: 2020-01-24] + ssb> ed25519 2018-01-24 [S] + +Il simbolo ``>`` in ``ssb>`` indica che la sottochiave è disponibile solo +nella smartcard. Se tornate nella vostra cartella delle chiavi segrete e +guardate al suo contenuto, noterete che i file ``.key`` sono stati sostituiti +con degli stub:: + + $ cd ~/.gnupg/private-keys-v1.d + $ strings *.key | grep 'private-key' + +Per indicare che i file sono solo degli stub e che in realtà il contenuto è +sulla smartcard, l'output dovrebbe mostrarvi ``shadowed-private-key``. + +Verificare che la smartcard funzioni +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Per verificare che la smartcard funzioni come dovuto, potete creare +una firma:: + + $ echo "Hello world" | gpg --clearsign > /tmp/test.asc + $ gpg --verify /tmp/test.asc + +Col primo comando dovrebbe chiedervi il PIN della smartcard, e poi dovrebbe +mostrare "Good signature" dopo l'esecuzione di ``gpg --verify``. + +Complimenti, siete riusciti a rendere estremamente difficile il furto della +vostra identità digitale di sviluppatore. + +Altre operazioni possibili con GnuPG +------------------------------------ + +Segue un breve accenno ad alcune delle operazioni più comuni che dovrete +fare con le vostre chiavi PGP. + +Montare il disco con la chiave primaria +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Vi servirà la vostra chiave principale per tutte le operazioni che seguiranno, +per cui per prima cosa dovrete accedere ai vostri backup e dire a GnuPG di +usarli:: + + $ export GNUPGHOME=/media/disk/foo/gnupg-backup + $ gpg --list-secret-keys + +Dovete assicurarvi di vedere ``sec`` e non ``sec#`` nell'output del programma +(il simbolo ``#`` significa che la chiave non è disponibile e che state ancora +utilizzando la vostra solita cartella di lavoro). + +Estendere la data di scadenza di una chiave +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +La chiave principale ha una data di scadenza di 2 anni dal momento della sua +creazione. Questo per motivi di sicurezza e per rendere obsolete le chiavi +che, eventualmente, dovessero sparire dai keyserver. + +Per estendere di un anno, dalla data odierna, la scadenza di una vostra chiave, +eseguite:: + + $ gpg --quick-set-expire [fpr] 1y + +Se per voi è più facile da memorizzare, potete anche utilizzare una data +specifica (per esempio, il vostro compleanno o capodanno):: + + $ gpg --quick-set-expire [fpr] 2020-07-01 + +Ricordatevi di inviare l'aggiornamento ai keyserver:: + + $ gpg --send-key [fpr] + +Aggiornare la vostra cartella di lavoro dopo ogni modifica +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Dopo aver fatto delle modifiche alle vostre chiavi usando uno spazio a parte, +dovreste importarle nella vostra cartella di lavoro abituale:: + + $ gpg --export | gpg --homedir ~/.gnupg --import + $ unset GNUPGHOME + + +Usare PGP con Git +================= + +Una delle caratteristiche fondanti di Git è la sua natura decentralizzata -- +una volta che il repositorio è stato clonato sul vostro sistema, avete la +storia completa del progetto, inclusi i suoi tag, i commit ed i rami. Tuttavia, +con i centinaia di repositori clonati che ci sono in giro, come si fa a +verificare che la loro copia di linux.git non è stata manomessa da qualcuno? + +Oppure, cosa succede se viene scoperta una backdoor nel codice e la riga +"Autore" dice che sei stato tu, mentre tu sei abbastanza sicuro di +`non averci niente a che fare`_? + +Per risolvere entrambi i problemi, Git ha introdotto l'integrazione con PGP. +I tag firmati dimostrano che il repositorio è integro assicurando che il suo +contenuto è lo stesso che si trova sulle macchine degli sviluppatori che hanno +creato il tag; mentre i commit firmati rendono praticamente impossibile +ad un malintenzionato di impersonarvi senza avere accesso alle vostre chiavi +PGP. + +.. _`non averci niente a che fare`: https://github.com/jayphelps/git-blame-someone-else + +Configurare git per usare la vostra chiave PGP +---------------------------------------------- + +Se avete solo una chiave segreta nel vostro portachiavi, allora non avete nulla +da fare in più dato che sarà la vostra chiave di base. Tuttavia, se doveste +avere più chiavi segrete, potete dire a git quale dovrebbe usare (``[fpg]`` +è la vostra impronta digitale):: + + $ git config --global user.signingKey [fpr] + +**IMPORTANTE**: se avete una comando dedicato per ``gpg2``, allora dovreste +dire a git di usare sempre quello piuttosto che il vecchio comando ``gpg``:: + + $ git config --global gpg.program gpg2 + +Come firmare i tag +------------------ + +Per creare un tag firmato, passate l'opzione ``-s`` al comando tag:: + + $ git tag -s [tagname] + +La nostra raccomandazione è quella di firmare sempre i tag git, perché +questo permette agli altri sviluppatori di verificare che il repositorio +git dal quale stanno prendendo il codice non è stato alterato intenzionalmente. + +Come verificare i tag firmati +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Per verificare un tag firmato, potete usare il comando ``verify-tag``:: + + $ git verify-tag [tagname] + +Se state prendendo un tag da un fork del repositorio del progetto, git +dovrebbe verificare automaticamente la firma di quello che state prendendo +e vi mostrerà il risultato durante l'operazione di merge:: + + $ git pull [url] tags/sometag + +Il merge conterrà qualcosa di simile:: + + Merge tag 'sometag' of [url] + + [Tag message] + + # gpg: Signature made [...] + # gpg: Good signature from [...] + +Se state verificando il tag di qualcun altro, allora dovrete importare +la loro chiave PGP. Fate riferimento alla sezione ":ref:`it_verify_identities`" +che troverete più avanti. + +Configurare git per firmare sempre i tag con annotazione +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Se state creando un tag con annotazione è molto probabile che vogliate +firmarlo. Per imporre a git di firmare sempre un tag con annotazione, +dovete impostare la seguente opzione globale:: + + $ git config --global tag.forceSignAnnotated true + +Come usare commit firmati +------------------------- + +Creare dei commit firmati è facile, ma è molto più difficile utilizzarli +nello sviluppo del kernel linux per via del fatto che ci si affida alle +liste di discussione e questo modo di procedere non mantiene le firme PGP +nei commit. In aggiunta, quando si usa *rebase* nel proprio repositorio +locale per allinearsi al kernel anche le proprie firme PGP verranno scartate. +Per questo motivo, la maggior parte degli sviluppatori del kernel non si +preoccupano troppo di firmare i propri commit ed ignoreranno quelli firmati +che si trovano in altri repositori usati per il proprio lavoro. + +Tuttavia, se avete il vostro repositorio di lavoro disponibile al pubblico +su un qualche servizio di hosting git (kernel.org, infradead.org, ozlabs.org, +o altri), allora la raccomandazione è di firmare tutti i vostri commit +anche se gli sviluppatori non ne beneficeranno direttamente. + +Vi raccomandiamo di farlo per i seguenti motivi: + +1. Se dovesse mai esserci la necessità di fare delle analisi forensi o + tracciare la provenienza di un codice, anche sorgenti mantenuti + esternamente che hanno firme PGP sui commit avranno un certo valore a + questo scopo. +2. Se dovesse mai capitarvi di clonare il vostro repositorio locale (per + esempio dopo un danneggiamento del disco), la firma vi permetterà di + verificare l'integrità del repositorio prima di riprendere il lavoro. +3. Se qualcuno volesse usare *cherry-pick* sui vostri commit, allora la firma + permetterà di verificare l'integrità dei commit prima di applicarli. + +Creare commit firmati +~~~~~~~~~~~~~~~~~~~~~ + +Per creare un commit firmato, dovete solamente aggiungere l'opzione ``-S`` +al comando ``git commit`` (si usa la lettera maiuscola per evitare +conflitti con un'altra opzione):: + + $ git commit -S + +Configurare git per firmare sempre i commit +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +Potete dire a git di firmare sempre i commit:: + + git config --global commit.gpgSign true + +.. note:: + + Assicuratevi di aver configurato ``gpg-agent`` prima di abilitare + questa opzione. + +.. _it_verify_identities: + +Come verificare l'identità degli sviluppatori del kernel +======================================================== + +Firmare i tag e i commit è facile, ma come si fa a verificare che la chiave +usata per firmare qualcosa appartenga davvero allo sviluppatore e non ad un +impostore? + +Configurare l'auto-key-retrieval usando WKD e DANE +-------------------------------------------------- + +Se non siete ancora in possesso di una vasta collezione di chiavi pubbliche +di altri sviluppatori, allora potreste iniziare il vostro portachiavi +affidandovi ai servizi di auto-scoperta e auto-recupero. GnuPG può affidarsi +ad altre tecnologie di delega della fiducia, come DNSSEC e TLS, per sostenervi +nel caso in cui iniziare una propria rete di fiducia da zero sia troppo +scoraggiante. + +Aggiungete il seguente testo al vostro file ``~/.gnupg/gpg.conf``:: + + auto-key-locate wkd,dane,local + auto-key-retrieve + +La *DNS-Based Authentication of Named Entities* ("DANE") è un metodo +per la pubblicazione di chiavi pubbliche su DNS e per renderle sicure usando +zone firmate con DNSSEC. Il *Web Key Directory* ("WKD") è un metodo +alternativo che usa https a scopo di ricerca. Quando si usano DANE o WKD +per la ricerca di chiavi pubbliche, GnuPG validerà i certificati DNSSEC o TLS +prima di aggiungere al vostro portachiavi locale le eventuali chiavi trovate. + +Kernel.org pubblica la WKD per tutti gli sviluppatori che hanno un account +kernel.org. Una volta che avete applicato le modifiche al file ``gpg.conf``, +potrete auto-recuperare le chiavi di Linus Torvalds e Greg Kroah-Hartman +(se non le avete già):: + + $ gpg --locate-keys torvalds@kernel.org gregkh@kernel.org + +Se avete un account kernel.org, al fine di rendere più utile l'uso di WKD +da parte di altri sviluppatori del kernel, dovreste `aggiungere alla vostra +chiave lo UID di kernel.org`_. + +.. _`aggiungere alla vostra chiave lo UID di kernel.org`: https://korg.wiki.kernel.org/userdoc/mail#adding_a_kernelorg_uid_to_your_pgp_key + +Web of Trust (WOT) o Trust on First Use (TOFU) +---------------------------------------------- + +PGP incorpora un meccanismo di delega della fiducia conosciuto come +"Web of Trust". Di base, questo è un tentativo di sostituire la necessità +di un'autorità certificativa centralizzata tipica del mondo HTTPS/TLS. +Invece di avere svariati produttori software che decidono chi dovrebbero +essere le entità di certificazione di cui dovreste fidarvi, PGP lascia +la responsabilità ad ogni singolo utente. + +Sfortunatamente, solo poche persone capiscono come funziona la rete di fiducia. +Nonostante sia un importante aspetto della specifica OpenPGP, recentemente +le versioni di GnuPG (2.2 e successive) hanno implementato un meccanisco +alternativo chiamato "Trust on First Use" (TOFU). Potete pensare a TOFU come +"ad un approccio all fidicia simile ad SSH". In SSH, la prima volta che vi +connettete ad un sistema remoto, l'impronta digitale della chiave viene +registrata e ricordata. Se la chiave dovesse cambiare in futuro, il programma +SSH vi avviserà e si rifiuterà di connettersi, obbligandovi a prendere una +decisione circa la fiducia che riponete nella nuova chiave. In modo simile, +la prima volta che importate la chiave PGP di qualcuno, si assume sia valida. +Se ad un certo punto GnuPG trova un'altra chiave con la stessa identità, +entrambe, la vecchia e la nuova, verranno segnate come invalide e dovrete +verificare manualmente quale tenere. + +Vi raccomandiamo di usare il meccanisco TOFU+PGP (che è la nuova configurazione +di base di GnuPG v2). Per farlo, aggiungete (o modificate) l'impostazione +``trust-model`` in ``~/.gnupg/gpg.conf``:: + + trust-model tofu+pgp + +Come usare i keyserver in sicurezza +----------------------------------- +Se ottenete l'errore "No public key" quando cercate di validate il tag di +qualcuno, allora dovreste cercare quella chiave usando un keyserver. È +importante tenere bene a mente che non c'è alcuna garanzia che la chiave +che avete recuperato da un keyserver PGP appartenga davvero alla persona +reale -- è progettato così. Dovreste usare il Web of Trust per assicurarvi +che la chiave sia valida. + +Come mantenere il Web of Trust va oltre gli scopi di questo documento, +semplicemente perché farlo come si deve richiede sia sforzi che perseveranza +che tendono ad andare oltre al livello di interesse della maggior parte degli +esseri umani. Qui di seguito alcuni rapidi suggerimenti per aiutarvi a ridurre +il rischio di importare chiavi maligne. + +Primo, diciamo che avete provato ad eseguire ``git verify-tag`` ma restituisce +un errore dicendo che la chiave non è stata trovata:: + + $ git verify-tag sunxi-fixes-for-4.15-2 + gpg: Signature made Sun 07 Jan 2018 10:51:55 PM EST + gpg: using RSA key DA73759BF8619E484E5A3B47389A54219C0F2430 + gpg: issuer "wens@...org" + gpg: Can't check signature: No public key + +Cerchiamo nel keyserver per maggiori informazioni sull'impronta digitale +della chiave (l'impronta digitale, probabilmente, appartiene ad una +sottochiave, dunque non possiamo usarla direttamente senza trovare prima +l'ID della chiave primaria associata ad essa):: + + $ gpg --search DA73759BF8619E484E5A3B47389A54219C0F2430 + gpg: data source: hkp://keys.gnupg.net + (1) Chen-Yu Tsai + 4096 bit RSA key C94035C21B4F2AEB, created: 2017-03-14, expires: 2019-03-15 + Keys 1-1 of 1 for "DA73759BF8619E484E5A3B47389A54219C0F2430". Enter number(s), N)ext, or Q)uit > q + +Localizzate l'ID della chiave primaria, nel nostro esempio +``C94035C21B4F2AEB``. Ora visualizzate le chiavi di Linus Torvalds +che avete nel vostro portachiavi:: + + $ gpg --list-key torvalds@kernel.org + pub rsa2048 2011-09-20 [SC] + ABAF11C65A2970B130ABE3C479BE3E4300411886 + uid [ unknown] Linus Torvalds + sub rsa2048 2011-09-20 [E] + +Poi, aprite il `PGP pathfinder`_. Nel campo "From", incollate l'impronta +digitale della chiave di Linus Torvalds che si vede nell'output qui sopra. +Nel campo "to", incollate il key-id della chiave sconosciuta che avete +trovato con ``gpg --search``, e poi verificare il risultato: + +- `Finding paths to Linus`_ + +Se trovate un paio di percorsi affidabili è un buon segno circa la validità +della chiave. Ora, potete aggiungerla al vostro portachiavi dal keyserver:: + + $ gpg --recv-key C94035C21B4F2AEB + +Questa procedura non è perfetta, e ovviamente state riponendo la vostra +fiducia nell'amministratore del servizio *PGP Pathfinder* sperando che non +sia malintenzionato (infatti, questo va contro :ref:`it_devs_not_infra`). +Tuttavia, se mantenete con cura la vostra rete di fiducia sarà un deciso +miglioramento rispetto alla cieca fiducia nei keyserver. + +.. _`PGP pathfinder`: https://pgp.cs.uu.nl/ +.. _`Finding paths to Linus`: https://pgp.cs.uu.nl/paths/79BE3E4300411886/to/C94035C21B4F2AEB.html -- cgit v1.2.3 From 4022ab4fc17d6b9b8107214125670059b53fa76e Mon Sep 17 00:00:00 2001 From: Jonathan Neuschäfer Date: Sun, 31 Mar 2019 23:41:58 +0200 Subject: docs: core-api: Drop reference to flexible-arrays MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This file doesn't exist anymore. Fixes: 586187d7de71 ("Drop flex_arrays") Reviewed-by: Mukesh Ojha Signed-off-by: Jonathan Neuschäfer Signed-off-by: Jonathan Corbet --- Documentation/core-api/index.rst | 1 - 1 file changed, 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/core-api/index.rst b/Documentation/core-api/index.rst index 6870baffef82..ee1bb8983a88 100644 --- a/Documentation/core-api/index.rst +++ b/Documentation/core-api/index.rst @@ -22,7 +22,6 @@ Core utilities workqueue genericirq xarray - flexible-arrays librs genalloc errseq -- cgit v1.2.3 From 491a3e883cef93acbbe3d68189892150537ed607 Mon Sep 17 00:00:00 2001 From: Jonathan Neuschäfer Date: Mon, 1 Apr 2019 00:34:22 +0200 Subject: Documentation: soundwire: Ensure that code is inside the code blocks MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The way the document is written now, Sphinx renders empty code blocks followed by the lines that should be inside them. Unindent the code-block directives to fix this. Signed-off-by: Jonathan Neuschäfer Signed-off-by: Jonathan Corbet --- Documentation/driver-api/soundwire/stream.rst | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) (limited to 'Documentation') diff --git a/Documentation/driver-api/soundwire/stream.rst b/Documentation/driver-api/soundwire/stream.rst index 26a6064503fd..5351bd2f34a8 100644 --- a/Documentation/driver-api/soundwire/stream.rst +++ b/Documentation/driver-api/soundwire/stream.rst @@ -201,7 +201,7 @@ Bus implements below API for allocate a stream which needs to be called once per stream. From ASoC DPCM framework, this stream state maybe linked to .startup() operation. - .. code-block:: c +.. code-block:: c int sdw_alloc_stream(char * stream_name); @@ -228,7 +228,7 @@ the respective Master(s) and Slave(s) associated with stream. These APIs can only be invoked once by respective Master(s) and Slave(s). From ASoC DPCM framework, this stream state is linked to .hw_params() operation. - .. code-block:: c +.. code-block:: c int sdw_stream_add_master(struct sdw_bus * bus, struct sdw_stream_config * stream_config, @@ -274,7 +274,7 @@ Bus implements below API for PREPARE state which needs to be called once per stream. From ASoC DPCM framework, this stream state is linked to .prepare() operation. - .. code-block:: c +.. code-block:: c int sdw_prepare_stream(struct sdw_stream_runtime * stream); @@ -304,7 +304,7 @@ Bus implements below API for ENABLE state which needs to be called once per stream. From ASoC DPCM framework, this stream state is linked to .trigger() start operation. - .. code-block:: c +.. code-block:: c int sdw_enable_stream(struct sdw_stream_runtime * stream); @@ -332,7 +332,7 @@ Bus implements below API for DISABLED state which needs to be called once per stream. From ASoC DPCM framework, this stream state is linked to .trigger() stop operation. - .. code-block:: c +.. code-block:: c int sdw_disable_stream(struct sdw_stream_runtime * stream); @@ -357,7 +357,7 @@ Bus implements below API for DEPREPARED state which needs to be called once per stream. From ASoC DPCM framework, this stream state is linked to .trigger() stop operation. - .. code-block:: c +.. code-block:: c int sdw_deprepare_stream(struct sdw_stream_runtime * stream); @@ -382,7 +382,7 @@ Bus implements below APIs for RELEASE state which needs to be called by all the Master(s) and Slave(s) associated with stream. From ASoC DPCM framework, this stream state is linked to .hw_free() operation. - .. code-block:: c +.. code-block:: c int sdw_stream_remove_master(struct sdw_bus * bus, struct sdw_stream_runtime * stream); @@ -395,7 +395,7 @@ stream assigned as part of ALLOCATED state. In .shutdown() the data structure maintaining stream state are freed up. - .. code-block:: c +.. code-block:: c void sdw_release_stream(struct sdw_stream_runtime * stream); -- cgit v1.2.3 From 9aacb03d05a5e4e1ce5e14696b523904773bc51d Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:08 +0800 Subject: docs/zh_CN: translate development-process into Chinese Start development process translation. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- .../zh_CN/process/development-process.rst | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) create mode 100644 Documentation/translations/zh_CN/process/development-process.rst (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/development-process.rst b/Documentation/translations/zh_CN/process/development-process.rst new file mode 100644 index 000000000000..500ca5056f60 --- /dev/null +++ b/Documentation/translations/zh_CN/process/development-process.rst @@ -0,0 +1,21 @@ +.. _cn_development_process_main: + +内核开发过程指南 +================ + +内容: + +.. toctree:: + :numbered: + :maxdepth: 2 + + 1.Intro + 2.Process + 3.Early-stage + 4.Coding + 5.Posting + 6.Followthrough + 7.AdvancedTopics + 8.Conclusion + +本文档的目的是帮助开发人员(及其经理)以最小的挫折感与开发社区合作。它试图记录这个社区如何以一种不熟悉Linux内核开发(或者实际上是自由软件开发)的人可以访问的方式工作。虽然这里有一些技术资料,但这是一个面向过程的讨论,不需要深入了解内核编程就可以理解。 -- cgit v1.2.3 From cc789dca4e582e6b61d87eff09b97b2514cdab0c Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:09 +0800 Subject: docs/zh_CN: add disclaimer and translator info in development-process Add disclaimer and translator info into development process doc Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/development-process.rst | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/development-process.rst b/Documentation/translations/zh_CN/process/development-process.rst index 500ca5056f60..30cffe66c075 100644 --- a/Documentation/translations/zh_CN/process/development-process.rst +++ b/Documentation/translations/zh_CN/process/development-process.rst @@ -1,3 +1,8 @@ +.. include:: ../disclaimer-zh_CN.rst + +:Original: :ref:`Documentation/process/development-process.rst ` +:Translator: Alex Shi + .. _cn_development_process_main: 内核开发过程指南 -- cgit v1.2.3 From 7fe1fde5d7a0e81248a672d7acab3fc7ecf12625 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:10 +0800 Subject: docs/zh_CN: link development-process into process index Then this doc could be find via process index. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/index.rst | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/index.rst b/Documentation/translations/zh_CN/process/index.rst index 03939e1a7b92..3942c3bb6548 100644 --- a/Documentation/translations/zh_CN/process/index.rst +++ b/Documentation/translations/zh_CN/process/index.rst @@ -25,6 +25,7 @@ howto submitting-patches coding-style + development-process email-clients 其它大多数开发人员感兴趣的社区指南: -- cgit v1.2.3 From 6c8d1355951f1ece4199b0990454aee0286f1837 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:11 +0800 Subject: docs/zh_CN: add Chinese 1.Intro file This is the Chinese version of 1.Intro.rst file. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- .../translations/zh_CN/process/1.Intro.rst | 181 +++++++++++++++++++++ 1 file changed, 181 insertions(+) create mode 100644 Documentation/translations/zh_CN/process/1.Intro.rst (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/1.Intro.rst b/Documentation/translations/zh_CN/process/1.Intro.rst new file mode 100644 index 000000000000..0da4b70a27db --- /dev/null +++ b/Documentation/translations/zh_CN/process/1.Intro.rst @@ -0,0 +1,181 @@ +.. _cn_development_process_intro: + +介绍 +==== + +执行摘要 +-------- + +本节的其余部分涵盖了内核开发过程的范围,以及开发人员及其雇主在这方面可能遇 +到的各种挫折。内核代码应该合并到正式的(“主线”)内核中有很多原因,包括对用 +户的自动可用性、多种形式的社区支持以及影响内核开发方向的能力。提供给Linux +内核的代码必须在与GPL兼容的许可证下可用。 + +:ref:`cn_development_process` 介绍了开发过程、内核发布周期和合并窗口的机制。 +涵盖了补丁开发、审查和合并周期中的各个阶段。有一些关于工具和邮件列表的讨论。 +鼓励希望开始内核开发的开发人员作为初始练习跟踪并修复bug。 + + +:ref:`cn_development_early_stage` 包括早期项目规划,重点是尽快让开发社区参与 + +:ref:`cn_development_coding` 是关于编码过程的;讨论了其他开发人员遇到的几个 +陷阱。对补丁的一些要求已经涵盖,并且介绍了一些工具,这些工具有助于确保内核 +补丁是正确的。 + +:ref:`cn_development_posting` 讨论发布补丁以供评审的过程。为了让开发社区 +认真对待,补丁必须正确格式化和描述,并且必须发送到正确的地方。遵循本节中的 +建议有助于确保为您的工作提供最好的接纳。 + +:ref:`cn_development_followthrough` 介绍了发布补丁之后发生的事情;该工作 +在这一点上还远远没有完成。与审阅者一起工作是开发过程中的一个重要部分;本节 +提供了一些关于如何在这个重要阶段避免问题的提示。当补丁被合并到主线中时, +开发人员要注意不要假定任务已经完成。 + +:ref:`cn_development_advancedtopics` 介绍了两个“高级”主题: +使用Git管理补丁和查看其他人发布的补丁。 + +:ref:`cn_development_conclusion` 总结了有关内核开发的更多信息,附带有带有 +指向资源的链接. + +这个文件是关于什么的 +-------------------- + +Linux内核有超过800万行代码,每个版本的贡献者超过1000人,是现存最大、最活跃 +的免费软件项目之一。从1991年开始,这个内核已经发展成为一个最好的操作系统 +组件,运行在袖珍数字音乐播放器、台式PC、现存最大的超级计算机以及所有类型的 +系统上。它是一种适用于几乎任何情况的健壮、高效和可扩展的解决方案。 + +随着Linux的发展,希望参与其开发的开发人员(和公司)的数量也在增加。硬件供应商 +希望确保Linux能够很好地支持他们的产品,使这些产品对Linux用户具有吸引力。嵌入 +式系统供应商使用Linux作为集成产品的组件,希望Linux能够尽可能地胜任手头的任务。 +分销商和其他基于Linux的软件供应商对Linux内核的功能、性能和可靠性有着明确的 +兴趣。最终用户也常常希望修改Linux,使之更好地满足他们的需求。 + +Linux最引人注目的特性之一是这些开发人员可以访问它;任何具备必要技能的人都可以 +改进Linux并影响其开发方向。专有产品不能提供这种开放性,这是自由软件的一个特点。 +但是,如果有什么不同的话,内核比大多数其他自由软件项目更开放。一个典型的三个月 +内核开发周期可以涉及1000多个开发人员,他们为100多个不同的公司 +(或者根本没有公司)工作。 + +与内核开发社区合作并不是特别困难。但是,尽管如此,许多潜在的贡献者在尝试做 +内核工作时遇到了困难。内核社区已经发展了自己独特的操作方式,使其能够在每天 +都要更改数千行代码的环境中顺利运行(并生成高质量的产品)。因此,Linux内核开发 +过程与专有的开发方法有很大的不同也就不足为奇了。 + +对于新开发人员来说,内核的开发过程可能会让人感到奇怪和恐惧,但这个背后有充分的 +理由和坚实的经验。一个不了解内核社区的方式的开发人员(或者更糟的是,他们试图 +抛弃或规避内核社区的方式)会有一个令人沮丧的体验。开发社区, 在帮助那些试图学习 +的人的同时,没有时间帮助那些不愿意倾听或不关心开发过程的人。 + +希望阅读本文的人能够避免这种令人沮丧的经历。这里有很多材料,但阅读时所做的 +努力会在短时间内得到回报。开发社区总是需要能让内核变更好的开发人员;下面的 +文本应该帮助您或为您工作的人员加入我们的社区。 + +致谢 +---- + +本文件由jonathan corbet撰写,corbet@lwn.net。以下人员的建议使之更为完善: +Johannes Berg, James Berry, Alex Chiang, Roland Dreier, Randy Dunlap, +Jake Edge, Jiri Kosina, Matt Mackall, Arthur Marsh, Amanda McPherson, +Andrew Morton, Andrew Price, Tsugikazu Shibata, 和 Jochen Voß. + +这项工作得到了Linux基金会的支持,特别感谢Amanda McPherson,他看到了这香工作 +的价值并使之发生。 + +代码进入主线的重要性 +-------------------- + +有些公司和开发人员偶尔会想,为什么他们要费心学习如何与内核社区合作,并将代码 +放入主线内核(“主线”是由Linus Torvalds维护的内核,Linux发行商将其用作基础)。 +在短期内,贡献代码看起来像是一种可以避免的开销;仅仅将代码分开并直接支持用户 +似乎更容易。事实上,保持代码独立(“树外”)是在经济上是错误的。 + +作为说明树外代码成本的一种方法,下面是内核开发过程的一些相关方面;本文稍后将 +更详细地讨论其中的大部分内容。考虑: + +- 所有Linux用户都可以使用合并到主线内核中的代码。它将自动出现在所有启用它的 + 发行版上。不需要驱动程序磁盘、下载,也不需要为多个发行版的多个版本提供支持; + 对于开发人员和用户来说,这一切都是可行的。并入主线解决了大量的分布和支持问题 + +- 当内核开发人员努力维护一个稳定的用户空间接口时,内部内核API处于不断变化之中. + 缺乏一个稳定的内部接口是一个深思熟虑的设计决策;它允许在任何时候进行基本的改 + 进,并产生更高质量的代码。但该策略的一个结果是,如果要使用新的内核,任何树外 + 代码都需要持续的维护。维护树外代码需要大量的工作才能使代码保持工作状态。 + + 相反,位于主线中的代码不需要这样做,因为一个简单的规则要求进行API更改的任何 + 开发人员也必须修复由于该更改而破坏的任何代码。因此,合并到主线中的代码大大 + 降低了维护成本。 + +- 除此之外,内核中的代码通常会被其他开发人员改进。令人惊讶的结果可能来自授权 + 您的用户社区和客户改进您的产品。 + +- 内核代码在合并到主线之前和之后都要经过审查。不管原始开发人员的技能有多强, + 这个审查过程总是能找到改进代码的方法。审查经常发现严重的错误和安全问题。 + 这对于在封闭环境中开发的代码尤其如此;这种代码从外部开发人员的审查中获益 + 匪浅。树外代码是低质量代码。 + +- 参与开发过程是您影响内核开发方向的方式。旁观者的抱怨会被听到,但是活跃的 + 开发人员有更强的声音——并且能够实现使内核更好地满足其需求的更改。 + +- 当单独维护代码时,总是存在第三方为类似功能提供不同实现的可能性。如果发生 + 这种情况,合并代码将变得更加困难——甚至到了不可能的地步。然后,您将面临以下 + 令人不快的选择:(1)无限期地维护树外的非标准特性,或(2)放弃代码并将用户 + 迁移到树内版本。 + +- 代码的贡献是使整个过程工作的根本。通过贡献代码,您可以向内核添加新功能,并 + 提供其他内核开发人员使用的功能和示例。如果您已经为Linux开发了代码(或者 + 正在考虑这样做),那么您显然对这个平台的持续成功感兴趣;贡献代码是确保成功 + 的最好方法之一。 + +上述所有理由都适用于任何树外内核代码,包括以专有的、仅二进制形式分发的代码。 +然而,在考虑任何类型的纯二进制内核代码分布之前,还需要考虑其他因素。这些包括: + +- 围绕专有内核模块分发的法律问题充其量是模糊的;相当多的内核版权所有者认为, + 大多数仅限二进制的模块是内核的派生产品,因此,它们的分发违反了GNU通用公共 + 许可证(下面将详细介绍)。您的作者不是律师,本文档中的任何内容都不可能被 + 视为法律建议。封闭源代码模块的真实法律地位只能由法院决定。但不管怎样,困扰 + 这些模块的不确定性仍然存在。 + +- 二进制模块大大增加了调试内核问题的难度,以至于大多数内核开发人员甚至都不会 + 尝试。因此,只分发二进制模块将使您的用户更难从社区获得支持。 + +- 对于只支持二进制的模块的发行者来说,支持也更加困难,他们必须为他们希望支持 + 的每个发行版和每个内核版本提供一个版本的模块。为了提供相当全面的覆盖范围, + 可能需要一个模块的几十个构建,并且每次升级内核时,您的用户都必须单独升级 + 您的模块。 + +- 上面提到的关于代码评审的所有问题都更加存在于封闭源代码。由于该代码根本不可 + 用,因此社区无法对其进行审查,毫无疑问,它将存在严重问题。 + +尤其是嵌入式系统的制造商,可能会倾向于忽视本节中所说的大部分内容,因为他们 +相信自己正在商用一种使用冻结内核版本的独立产品,在发布后不需要再进行开发。 +这个论点忽略了广泛的代码审查的价值以及允许用户向产品添加功能的价值。但这些 +产品也有有限的商业寿命,之后必须发布新版本的产品。在这一点上,代码在主线上 +并得到良好维护的供应商将能够更好地占位,以使新产品快速上市。 + +许可 +---- + +代码是根据一些许可证提供给Linux内核的,但是所有代码都必须与GNU通用公共许可 +证(GPLV2)的版本2兼容,该版本是覆盖整个内核分发的许可证。在实践中,这意味 +着所有代码贡献都由GPLv2(可选地,语言允许在更高版本的GPL下分发)或3子句BSD +许可(New BSD License, 译者注)覆盖。任何不包含在兼容许可证中的贡献都不会 +被接受到内核中。 + +贡献给内核的代码不需要(或请求)版权分配。合并到主线内核中的所有代码都保留 +其原始所有权;因此,内核现在拥有数千个所有者。 + +这种所有权结构的一个暗示是,任何改变内核许可的尝试都注定会失败。很少有实际 +的场景可以获得所有版权所有者的同意(或者从内核中删除他们的代码)。因此,特 +别是,在可预见的将来,不可能迁移到GPL的版本3。 + +所有贡献给内核的代码都必须是合法的免费软件。因此,不接受匿名(或匿名)贡献 +者的代码。所有贡献者都需要在他们的代码上“sign off”,声明代码可以在GPL下与内 +核一起分发。无法提供未被其所有者许可为免费软件的代码,或可能为内核造成版权 +相关问题的代码(例如,由缺乏适当保护的反向工程工作派生的代码)不能被接受。 + +有关版权相关问题的问题在Linux开发邮件列表中很常见。这样的问题通常会得到不少 +答案,但要记住,回答这些问题的人不是律师,不能提供法律咨询。如果您有关于 +Linux源代码的法律问题,那么与了解该领域的律师交流是无法替代的。依靠从技术 +邮件列表中获得的答案是一件冒险的事情。 + -- cgit v1.2.3 From 4a6c7b428dbbff744e29cf28288ef5442a72beed Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:12 +0800 Subject: docs/zh_CN: add disclaimer and translator info into 1.Intro So people know where to complain if the transolation isn't good. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/1.Intro.rst | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/1.Intro.rst b/Documentation/translations/zh_CN/process/1.Intro.rst index 0da4b70a27db..03bbafc00bd2 100644 --- a/Documentation/translations/zh_CN/process/1.Intro.rst +++ b/Documentation/translations/zh_CN/process/1.Intro.rst @@ -1,3 +1,8 @@ +.. include:: ../disclaimer-zh_CN.rst + +:Original: :ref:`Documentation/process/1.Intro.rst ` +:Translator: Alex Shi + .. _cn_development_process_intro: 介绍 -- cgit v1.2.3 From 061ea8c3e876c46088d04ae2f5f87159c2e08c23 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:13 +0800 Subject: docs/zh_CN: add 2.Process.rst for development-process New it's done. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- .../translations/zh_CN/process/2.Process.rst | 355 +++++++++++++++++++++ 1 file changed, 355 insertions(+) create mode 100644 Documentation/translations/zh_CN/process/2.Process.rst (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/2.Process.rst b/Documentation/translations/zh_CN/process/2.Process.rst new file mode 100644 index 000000000000..0b354ef49905 --- /dev/null +++ b/Documentation/translations/zh_CN/process/2.Process.rst @@ -0,0 +1,355 @@ +.. _development_process: + +开发流程如何工作 +================ + +90年代早期的Linux内核开发是一件相当松散的事情,涉及的用户和开发人员相对较 +少。由于拥有数以百万计的用户群,并且在一年的时间里有大约2000名开发人员参与 +进来,内核因此必须发展许多流程来保持开发的顺利进行。要成为流程的有效组成 +部分,需要对流程的工作方式有一个扎实的理解。 + +总览 +---- + +内核开发人员使用一个松散的基于时间的发布过程,每两到三个月发布一次新的主要 +内核版本。最近的发布历史记录如下: + + ====== ================= + 4.11 四月 30, 2017 + 4.12 七月 2, 2017 + 4.13 九月 3, 2017 + 4.14 十一月 12, 2017 + 4.15 一月 28, 2018 + 4.16 四月 1, 2018 + ====== ================= + +每4.x版本都是一个主要的内核版本,具有新特性、内部API更改等等。一个典型的4.x +版本包含大约13000个变更集,变更了几十万行代码。因此,4.x是Linux内核开发的前 +沿;内核使用滚动开发模型,不断集成重大变化。 + +对于每个版本的补丁合并,遵循一个相对简单的规则。在每个开发周期的开始,“合并 +窗口”被打开。当时,被认为足够稳定(并且被开发社区接受)的代码被合并到主线内 +核中。在这段时间内,新开发周期的大部分变更(以及所有主要变更)将以接近每天 +1000次变更(“补丁”或“变更集”)的速度合并。 + +(顺便说一句,值得注意的是,合并窗口期间集成的更改并不是凭空产生的;它们是 +提前收集、测试和分级的。稍后将详细描述该过程的工作方式)。 + +合并窗口持续大约两周。在这段时间结束时,LinusTorvalds将声明窗口已关闭,并 +释放第一个“rc”内核。例如,对于目标为4.14的内核,在合并窗口结束时发生的释放 +将被称为4.14-rc1。RC1版本是一个信号,表示合并新特性的时间已经过去,稳定下一 +个内核的时间已经开始。 + +在接下来的6到10周内,只有修复问题的补丁才应该提交给主线。有时会允许更大的 +更改,但这种情况很少发生;试图在合并窗口外合并新功能的开发人员往往会受到不 +友好的接待。一般来说,如果您错过了给定特性的合并窗口,最好的做法是等待下一 +个开发周期。(对于以前不支持的硬件,偶尔会对驱动程序进行例外;如果它们不 +改变已有代码,则不会导致回归,并且应该可以随时安全地添加)。 + +随着修复程序进入主线,补丁速度将随着时间的推移而变慢。Linus大约每周发布一次 +新的-rc内核;一个正常的系列将在-rc6和-rc9之间,内核被认为足够稳定并最终发布。 +然后,整个过程又重新开始了。 + +例如,这里是4.16的开发周期进行情况(2018年的所有日期): + + ============== ============================== + 一月 28 4.15 稳定版发布 + 二月 11 4.16-rc1, 合并窗口关闭 + 二月 18 4.16-rc2 + 二月 25 4.16-rc3 + 三月 4 4.16-rc4 + 三月 11 4.16-rc5 + 三月 18 4.16-rc6 + 三月 25 4.16-rc7 + 四月 1 4.16 稳定版发布 + ============== ============================== + +开发人员如何决定何时结束开发周期并创建稳定的版本?使用的最重要的指标是以前 +版本的回归列表。不欢迎出现任何错误,但是那些破坏了以前能工作的系统的错误被 +认为是特别严重的。因此,导致回归的补丁是不受欢迎的,很可能在稳定期内删除。 + +开发人员的目标是在稳定发布之前修复所有已知的回归。在现实世界中,这种完美是 +很难实现的;在这种规模的项目中,变量太多了。有一点,延迟最终版本只会使问题 +变得更糟;等待下一个合并窗口的一堆更改将变大,从而在下次创建更多的回归错误。 +因此,大多数4.x内核都有一些已知的回归错误,不过,希望没有一个是严重的。 + +一旦一个稳定的版本发布,它正在进行的维护工作就被移交给“稳定团队”,目前由 +Greg Kroah-Hartman组成。稳定团队将使用4.x.y编号方案不定期的发布稳定版本的更 +新。要加入更新版本,补丁程序必须(1)修复一个重要的bug,(2)已经合并到 +下一个开发主线中。内核通常会在超过其初始版本的一个以上的开发周期内接收稳定 +的更新。例如,4.13内核的历史如下 + + ============== =============================== + 九月 3 4.13 稳定版发布 + 九月 13 4.13.1 + 九月 20 4.13.2 + 九月 27 4.13.3 + 十月 5 4.13.4 + 十月 12 4.13.5 + ... ... + 十一月 24 4.13.16 + ============== =============================== + +4.13.16是4.13版本的最终稳定更新。 + +有些内核被指定为“长期”内核;它们将得到更长时间的支持。在本文中,当前的长期 +内核及其维护者是: + + ====== ====================== ============================== + 3.16 Ben Hutchings (长期稳定内核) + 4.1 Sasha Levin + 4.4 Greg Kroah-Hartman (长期稳定内核) + 4.9 Greg Kroah-Hartman + 4.14 Greg Kroah-Hartman + ====== ====================== ============================== + +为长期支持选择内核纯粹是维护人员有必要和时间来维护该版本的问题。目前还没有 +为即将发布的任何特定版本提供长期支持的已知计划。 + +补丁的生命周期 +-------------- + +补丁不会直接从开发人员的键盘进入主线内核。相反,有一个稍微复杂(如果有些非 +正式)的过程,旨在确保对每个补丁进行质量审查,并确保每个补丁实现了一个在主线 +中需要的更改。对于小的修复,这个过程可能会很快发生,或者,在大的和有争议的 +变更的情况下,会持续数年。许多开发人员的挫折来自于对这个过程缺乏理解或者 +试图绕过它。 + +为了减少这种挫折感,本文将描述补丁如何进入内核。下面是一个介绍,它以某种 +理想化的方式描述了这个过程。更详细的过程将在后面的章节中介绍。 + +补丁程序经历的阶段通常是: + +- 设计。这就是补丁的真正需求——以及满足这些需求的方式——的所在。设计工作通常 + 是在不涉及社区的情况下完成的,但是如果可能的话,最好是在公开的情况下完成 + 这项工作;这样可以节省很多稍后再重新设计的时间。 + +- 早期评审。补丁被发布到相关的邮件列表中,列表中的开发人员会回复他们可能有 + 的任何评论。如果一切顺利的话,这个过程应该会发现补丁的任何主要问题。 + +- 更广泛的评审。当补丁接近准备好纳入主线时,它应该被相关的子系统维护人员 + 接受——尽管这种接受并不能保证补丁会一直延伸到主线。补丁将出现在维护人员的 + 子系统树中,并进入 -next 树(如下所述)。当流程工作时,此步骤将导致对补丁 + 进行更广泛的审查,并发现由于将此补丁与其他人所做的工作集成而导致的任何 + 问题。 + +- 请注意,大多数维护人员也有日常工作,因此合并补丁可能不是他们的最高优先级。 + 如果您的补丁程序得到了关于所需更改的反馈,那么您应该进行这些更改,或者为 + 不应该进行这些更改的原因辩护。如果您的补丁没有评审意见,但没有被其相应的 + 子系统或驱动程序维护者接受,那么您应该坚持不懈地将补丁更新到当前内核,使 + 其干净地应用,并不断地将其发送以供审查和合并。 + +- 合并到主线。最终,一个成功的补丁将被合并到由LinusTorvalds管理的主线存储库 + 中。此时可能会出现更多的评论和/或问题;开发人员应对这些问题并解决出现的 + 任何问题很重要。 + +- 稳定版发布。可能受补丁影响的用户数量现在很大,因此可能再次出现新的问题。 + +- 长期维护。虽然开发人员在合并代码后可能会忘记代码,但这种行为往往会给开发 + 社区留下不良印象。合并代码消除了一些维护负担,因为其他代码将修复由API + 更改引起的问题。但是,如果代码要长期保持有用,原始开发人员应该继续为 + 代码负责。 + +内核开发人员(或他们的雇主)犯的最大错误之一是试图将流程简化为一个 +“合并到主线”步骤。这种方法总是会让所有相关人员感到沮丧。 + +补丁如何进入内核 +---------------- + +只有一个人可以将补丁合并到主线内核存储库中:LinusTorvalds。但是,在进入 +2.6.38内核的9500多个补丁中,只有112个(大约1.3%)是由Linus自己直接选择的。 +内核项目已经发展到一个规模,没有一个开发人员可以在没有支持的情况下检查和 +选择每个补丁。内核开发人员处理这种增长的方式是通过使用围绕信任链构建的 +助理系统。 + +内核代码库在逻辑上被分解为一组子系统:网络、特定的体系结构支持、内存管理、 +视频设备等。大多数子系统都有一个指定的维护人员,开发人员对该子系统中的代码 +负有全部责任。这些子系统维护者(松散地)是他们所管理的内核部分的守护者; +他们(通常)会接受一个补丁以包含到主线内核中。 + +子系统维护人员每个人都使用git源代码管理工具管理自己版本的内核源代码树。Git +等工具(以及Quilt或Mercurial等相关工具)允许维护人员跟踪补丁列表,包括作者 +信息和其他元数据。在任何给定的时间,维护人员都可以确定他或她的存储库中的哪 +些补丁在主线中找不到。 + +当合并窗口打开时,顶级维护人员将要求Linus从其存储库中“拉出”他们为合并选择 +的补丁。如果Linus同意,补丁流将流向他的存储库,成为主线内核的一部分。 +Linus对拉操作中接收到的特定补丁的关注程度各不相同。很明显,有时他看起来很 +关注。但是,作为一般规则,Linus相信子系统维护人员不会向上游发送坏补丁。 + +子系统维护人员反过来也可以从其他维护人员那里获取补丁。例如,网络树是由首先 +在专用于网络设备驱动程序、无线网络等的树中积累的补丁构建的。此存储链可以 +任意长,但很少超过两个或三个链接。由于链中的每个维护者都信任那些管理较低 +级别树的维护者,所以这个过程称为“信任链”。 + +显然,在这样的系统中,获取内核补丁取决于找到正确的维护者。直接向Linus发送 +补丁通常不是正确的方法。 + +Next 树 +------- + +子系统树链引导补丁流到内核,但它也提出了一个有趣的问题:如果有人想查看为 +下一个合并窗口准备的所有补丁怎么办?开发人员将感兴趣的是,还有什么其他的 +更改有待解决,以查看是否存在需要担心的冲突;例如,更改核心内核函数原型的 +修补程序将与使用该函数旧形式的任何其他修补程序冲突。审查人员和测试人员希望 +在所有这些变更到达主线内核之前,能够访问它们的集成形式中的变更。您可以从所有 +有趣的子系统树中提取更改,但这将是一项大型且容易出错的工作。 + +答案以-next树的形式出现,在这里子系统树被收集以供测试和审查。Andrew Morton +维护的这些旧树被称为“-mm”(用于内存管理,这就是它的启动名字)。-mm 树集成了 +一长串子系统树中的补丁;它还包含一些旨在帮助调试的补丁。 + +除此之外,-mm 还包含大量由Andrew直接选择的补丁。这些补丁可能已经发布在邮件 +列表上,或者它们可能应用于内核中没有指定子系统树的部分。结果,-mm 作为一种 +最后手段的子系统树运行;如果没有其他明显的路径可以让补丁进入主线,那么它很 +可能以-mm 结束。累积在-mm 中的各种补丁最终将被转发到适当的子系统树,或者直接 +发送到Linus。在典型的开发周期中,大约5-10%的补丁通过-mm 进入主线。 + +当前-mm 补丁可在“mmotm”(-mm of the moment)目录中找到,地址: + + http://www.ozlabs.org/~akpm/mmotm/ + +然而,使用mmotm树可能是一种令人沮丧的体验;它甚至可能无法编译。 + +下一个周期补丁合并的主要树是linux-next,由Stephen Rothwell 维护。根据设计 +linux-next 是下一个合并窗口关闭后主线的快照。linux-next树在Linux-kernel 和 +Linux-next 邮件列表中发布,可从以下位置下载: + + http://www.kernel.org/pub/linux/kernel/next/ + +Linux-next 已经成为内核开发过程中不可或缺的一部分;在一个给定的合并窗口中合并 +的所有补丁都应该在合并窗口打开之前的一段时间内找到进入Linux-next 的方法。 + +Staging 树 +---------- + +内核源代码树包含drivers/staging/directory,其中有许多驱动程序或文件系统的 +子目录正在被添加到内核树中。它们然需要更多的工作的时候可以保留在 +driver/staging目录中;一旦完成,就可以将它们移到内核中。这是一种跟踪不符合 +Linux内核编码或质量标准的驱动程序的方法,但人们可能希望使用它们并跟踪开发。 + +Greg Kroah Hartman 目前负责维护staging 树。仍需要工作的驱动程序将发送给他, +每个驱动程序在drivers/staging/中都有自己的子目录。除了驱动程序源文件之外, +目录中还应该有一个TODO文件。todo文件列出了驱动程序需要接受的挂起的工作, +以及驱动程序的任何补丁都应该抄送的人员列表。当前的规则要求,staging的驱动 +程序必须至少正确编译。 + +Staging 是一种相对容易的方法,可以让新的驱动程序进入主线,幸运的是,他们会 +引起其他开发人员的注意,并迅速改进。然而,进入staging并不是故事的结尾; +staging中没有看到常规进展的代码最终将被删除。经销商也倾向于相对不愿意使用 +staging驱动程序。因此,在成为一名合适的主线驱动的路上,staging 充其量只是 +一个停留。 + +工具 +---- + +从上面的文本可以看出,内核开发过程在很大程度上依赖于在不同方向上聚集补丁的 +能力。如果没有适当强大的工具,整个系统将无法在任何地方正常工作。关于如何使用 +这些工具的教程远远超出了本文档的范围,但是还是有一些指南的空间。 + +到目前为止,内核社区使用的主要源代码管理系统是git。Git是在自由软件社区中开发 +的许多分布式版本控制系统之一。它非常适合内核开发,因为它在处理大型存储库和 +大量补丁时性能非常好。它还有一个难以学习和使用的名声,尽管随着时间的推移它 +变得更好了。对于内核开发人员来说,对Git的某种熟悉几乎是一种要求;即使他们不 +将它用于自己的工作,他们也需要Git来跟上其他开发人员(以及主线)正在做的事情。 + +现在几乎所有的Linux发行版都打包了Git。主页位于: + + http://git-scm.com/ + +那个页面有指向文档和教程的指针。 + +在不使用git的内核开发人员中,最流行的选择几乎肯定是mercurial: + + http://www.seleric.com/mercurial/ + +Mercurial与Git共享许多特性,但它提供了一个界面,许多人觉得它更易于使用。 + +另一个值得了解的工具是quilt: + + http://savannah.nongnu.org/projects/quilt + +Quilt 是一个补丁管理系统,而不是源代码管理系统。它不会随着时间的推移跟踪历史; +相反,它面向根据不断发展的代码库跟踪一组特定的更改。一些主要的子系统维护人员 +使用Quilt来管理打算向上游移动的补丁。对于某些树的管理(例如-mm),quilt 是 +最好的工具。 + +邮件列表 +-------- + +大量的Linux内核开发工作是通过邮件列表完成的。如果不在某个地方加入至少一个列表, +就很难成为社区中一个功能完备的成员。但是,Linux邮件列表对开发人员来说也是一个 +潜在的危险,他们可能会被一堆电子邮件淹没,违反Linux列表上使用的约定,或者 +两者兼而有之。 + +大多数内核邮件列表都在vger.kernel.org上运行;主列表位于: + + http://vger.kernel.org/vger-lists.html + +不过,也有一些列表托管在别处;其中一些列表位于lists.redhat.com。 + +当然,内核开发的核心邮件列表是linux-kernel。这个名单是一个令人生畏的地方; +每天的信息量可以达到500条,噪音很高,谈话技术性很强,参与者并不总是表现出 +高度的礼貌。但是,没有其他地方可以让内核开发社区作为一个整体聚集在一起; +避免使用此列表的开发人员将错过重要信息。 + +有一些提示可以帮助在linux-kernel生存: + +- 将邮件转移到单独的文件夹,而不是主邮箱。我们必须能够持续地忽略洪流。 + +- 不要试图跟踪每一次谈话-其他人都不会。重要的是要对感兴趣的主题(尽管请 + 注意,长时间的对话可以在不更改电子邮件主题行的情况下偏离原始主题)和参与 + 的人进行筛选。 + +- 不要挑事。如果有人试图激起愤怒的反应,忽略他们。 + +- 当响应Linux内核电子邮件(或其他列表上的电子邮件)时,请为所有相关人员保留 + cc:header。如果没有强有力的理由(如明确的请求),则不应删除收件人。一定要 + 确保你要回复的人在cc:list中。这个惯例也使你不必在回复邮件时明确要求被抄送。 + +- 在提出问题之前,搜索列表档案(和整个网络)。有些开发人员可能会对那些显然 + 没有完成家庭作业的人感到不耐烦。 + +- 避免贴顶帖(把你的答案放在你要回复的引文上面的做法)。这会让你的回答更难 + 理解,印象也很差。 + +- 询问正确的邮件列表。linux-kernel 可能是通用的讨论点,但它不是从所有子系统 + 中寻找开发人员的最佳场所。 + +最后一点——找到正确的邮件列表——是开发人员出错的常见地方。在Linux内核上提出与 +网络相关的问题的人几乎肯定会收到一个礼貌的建议,转而在netdev列表上提出, +因为这是大多数网络开发人员经常出现的列表。还有其他列表可用于scsi、 +video4linux、ide、filesystem等子系统。查找邮件列表的最佳位置是与内核源代码 +一起打包的MAINTAINERS文件。 + +开始内核开发 +------------ + +关于如何开始内核开发过程的问题很常见——来自个人和公司。同样常见的是错误,这 +使得关系的开始比必须的更困难。 + +公司通常希望聘请知名的开发人员来启动开发团队。实际上,这是一种有效的技术。 +但它也往往是昂贵的,而且没有增长经验丰富的内核开发人员储备。考虑到时间的 +投入,可以让内部开发人员加快Linux内核的开发速度。花这个时间可以让雇主拥有 +一批了解内核和公司的开发人员,他们也可以帮助培训其他人。从中期来看,这往往 +是更有利可图的方法。 + +可以理解的是,单个开发人员往往对起步感到茫然。从一个大型项目开始可能会很 +吓人;人们往往想先用一些较小的东西来测试水域。这是一些开发人员开始创建修补 +拼写错误或轻微编码风格问题的补丁的地方。不幸的是,这样的补丁会产生一定程度 +的噪音,这会分散整个开发社区的注意力,因此,越来越多的人看不起它们。希望向 +社区介绍自己的新开发人员将无法通过这些方式获得他们想要的那种接待。 + +Andrew Morton 为有抱负的内核开发人员提供了这个建议 + +:: + + 所有内核初学者的No.1项目肯定是“确保内核在所有的机器上,你可以触摸 + 到的,始终运行良好" 通常这样做的方法是与其他人一起解决问题(这 + 可能需要坚持!)但这很好——这是内核开发的一部分 + +(http://lwn.net/articles/283982/) + +在没有明显问题需要解决的情况下,建议开发人员查看当前的回归和开放式错误列表. +解决需要修复的问题没有任何缺点;通过解决这些问题,开发人员将获得处理过程的 +经验,同时与开发社区的其他人建立尊重。 -- cgit v1.2.3 From a42d71ee6fd455285a41b22731e129c78950b753 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:14 +0800 Subject: docs/zh_CN: add disclaimer and translator info in 2.Process Now people know where to complain :). Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/2.Process.rst | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/2.Process.rst b/Documentation/translations/zh_CN/process/2.Process.rst index 0b354ef49905..ceb733bb0294 100644 --- a/Documentation/translations/zh_CN/process/2.Process.rst +++ b/Documentation/translations/zh_CN/process/2.Process.rst @@ -1,4 +1,9 @@ -.. _development_process: +.. include:: ../disclaimer-zh_CN.rst + +:Original: :ref:`Documentation/process/2.Process.rst ` +:Translator: Alex Shi + +.. _cn_development_process: 开发流程如何工作 ================ -- cgit v1.2.3 From 2c573b189ac11ca91b0613bf1d18a917a8c9b068 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:15 +0800 Subject: docs/zh_CN: translate 3.Early-stage of development process Now it is ready to appear in 'make htmldocs' Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- .../translations/zh_CN/process/3.Early-stage.rst | 156 +++++++++++++++++++++ 1 file changed, 156 insertions(+) create mode 100644 Documentation/translations/zh_CN/process/3.Early-stage.rst (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/3.Early-stage.rst b/Documentation/translations/zh_CN/process/3.Early-stage.rst new file mode 100644 index 000000000000..11c9e89c52ce --- /dev/null +++ b/Documentation/translations/zh_CN/process/3.Early-stage.rst @@ -0,0 +1,156 @@ +.. _cn_development_early_stage: + +早期规划 +======== + +当考虑一个Linux内核开发项目时,很可能会直接跳进去开始编码。然而,与任何重要 +的项目一样,成功的许多基础最好是在第一行代码编写之前就做好了。在早期计划和 +沟通中花费一些时间可以节省更多的时间。 + +详述问题 +-------- + +与任何工程项目一样,成功的内核增强从要解决的问题的清晰描述开始。在某些情况 +下,这个步骤很容易:例如,当某个特定硬件需要驱动程序时。不过,在其他方面, +将实际问题与建议的解决方案混淆是很有诱惑力的,这可能会导致困难。 + +举个例子:几年前,使用Linux音频的开发人员寻求一种方法来运行应用程序,而不因 +系统延迟过大而导致退出或其他工件。他们得到的解决方案是一个内核模块,旨在连 +接到Linux安全模块(LSM)框架中;这个模块可以配置为允许特定的应用程序访问 +实时调度程序。这个模块被实现并发送到Linux内核邮件列表,在那里它立即遇到问题。 + +对于音频开发人员来说,这个安全模块足以解决他们当前的问题。但是,对于更广泛的 +内核社区来说,这被视为对LSM框架的滥用(LSM框架并不打算授予他们原本不具备的 +进程特权),并对系统稳定性造成风险。他们首选的解决方案包括短期的通过rlimit +机制进行实时调度访问,以及长期的减少延迟的工作。 + +然而,音频社区看不到他们实施的特定解决方案的过去;他们不愿意接受替代方案。 +由此产生的分歧使这些开发人员对整个内核开发过程感到失望;其中一个开发人员返回 +到音频列表并发布了以下内容: + + 有很多非常好的Linux内核开发人员,但他们往往会被一群傲慢的傻瓜所压倒。 + 试图向这些人传达用户需求是浪费时间。他们太“聪明”了,根本听不到少数人 + 的话。 + +(http://lwn.net/articles/131776/) + +实际情况不同;与特定模块相比,内核开发人员更关心系统稳定性、长期维护以及找到 +正确的问题解决方案。这个故事的寓意是把重点放在问题上——而不是具体的解决方案 +上——并在投入创建代码之前与开发社区讨论这个问题。 + +因此,在考虑一个内核开发项目时,我们应该得到一组简短问题的答案: + + - 究竟需要解决的问题是什么? + + - 受此问题影响的用户是谁?解决方案应该解决哪些用例? + + - 内核现在为何没能解决这个问题? + +只有这样,才能开始考虑可能的解决方案。 + + +早期讨论 +-------- + +在计划内核开发项目时,在开始实施之前与社区进行讨论是很有意义的。早期沟通可以 +通过多种方式节省时间和麻烦: + + - 很可能问题是由内核以您不理解的方式解决的。Linux内核很大,具有许多不明显 + 的特性和功能。并不是所有的内核功能都像人们所希望的那样有文档记录,而且很 + 容易遗漏一些东西。你的作者发出了一个完整的驱动程序,复制了一个新作者不 + 知道的现有驱动程序。重新设计现有轮子的代码不仅浪费,而且不会被接受到主线 + 内核中。 + + - 建议的解决方案中可能有一些元素不适用于主线合并。在编写代码之前,最好先 + 了解这样的问题。 + + - 其他开发人员完全有可能考虑过这个问题;他们可能有更好的解决方案的想法,并且 + 可能愿意帮助创建这个解决方案。 + +在内核开发社区的多年经验给了我们一个明确的教训:闭门设计和开发的内核代码总是 +有一些问题,这些问题只有在代码发布到社区中时才会被发现。有时这些问题很严重, +需要数月或数年的努力才能使代码达到内核社区的标准。一些例子包括: + + - 设计并实现了单处理器系统的DeviceScape网络栈。只有使其适合于多处理器系统, + 才能将其合并到主线中。在代码中改装锁等等是一项困难的任务;因此,这段代码 + (现在称为mac80211)的合并被推迟了一年多。 + + - Reiser4文件系统包含许多功能,核心内核开发人员认为这些功能应该在虚拟文件 + 系统层中实现。它还包括一些特性,这些特性在不将系统暴露于用户引起的死锁的 + 情况下是不容易实现的。这些问题的最新发现——以及对其中一些问题的拒绝——已经 + 导致Reiser4远离了主线内核。 + + - Apparmor安全模块以被认为不安全和不可靠的方式使用内部虚拟文件系统数据结构。 + 这种担心(包括其他)使Apparmor多年不在主线上。 + +在每一种情况下,通过与内核开发人员的早期讨论,可以避免大量的痛苦和额外的工作。 + +找谁交流 +-------- + +当开发人员决定公开他们的计划时,下一个问题是:我们从哪里开始?答案是找到正确 +的邮件列表和正确的维护者。对于邮件列表,最好的方法是在维护者(MAINTAINERS)文件 +中查找要发布的相关位置。如果有一个合适的子系统列表,那么发布它通常比在Linux +内核上发布更可取;您更有可能接触到在相关子系统中具有专业知识的开发人员,并且 +环境可能具支持性。 + +找到维护人员可能会有点困难。同样,维护者文件是开始的地方。但是,该文件往往不总 +是最新的,并且并非所有子系统都在那里表示。实际上,维护者文件中列出的人员可能 +不是当前实际担任该角色的人员。因此,当对联系谁有疑问时,一个有用的技巧是使用 +git(尤其是“git-log”)查看感兴趣的子系统中当前活动的用户。看看谁在写补丁, +如果有人的话,谁会在这些补丁上加上用线签名的。这些人将是帮助新开发项目的最佳 +人选。 + +找到合适的维护者的任务有时是非常具有挑战性的,以至于内核开发人员添加了一个 +脚本来简化过程: + +:: + + .../scripts/get_maintainer.pl + +当给定“-f”选项时,此脚本将返回给定文件或目录的当前维护者。如果在命令行上传递 +了一个补丁,它将列出可能接收补丁副本的维护人员。有许多选项可以调节 +get_maintainer.pl搜索维护者的难易程度;请小心使用更具攻击性的选项,因为最终 +可能会包括对您正在修改的代码没有真正兴趣的开发人员。 + +如果所有其他方法都失败了,那么与Andrew Morton交谈可以成为一种有效的方法来跟踪 +特定代码段的维护人员。 + +何时邮寄? +---------- + +如果可能的话,在早期阶段发布你的计划只会有帮助。描述正在解决的问题以及已经 +制定的关于如何实施的任何计划。您可以提供的任何信息都可以帮助开发社区为项目 +提供有用的输入。 + +在这个阶段可能发生的一件令人沮丧的事情不是敌对的反应,而是很少或根本没有 +反应。可悲的事实是:(1)内核开发人员往往很忙;(2)不缺少有宏伟计划和很少 +代码(甚至代码前景)支持他们的人;(3)没有人有义务审查或评论别人发表的 +想法。除此之外,高级设计常常隐藏一些问题,这些问题只有在有人真正尝试实现 +这些设计时才会被发现;因此,内核开发人员宁愿看到代码。 + +如果发表评论的请求在评论的方式上没有什么效果,不要假设这意味着对项目没有 +兴趣。不幸的是,你也不能假设你的想法没有问题。在这种情况下,最好的做法是 +继续进行,把你的进展随时通知社区。 + +获得官方认可 +----------------------- + +如果您的工作是在公司环境中完成的,就像大多数Linux内核工作一样,显然,在您将 +公司的计划或代码发布到公共邮件列表之前,必须获得适当授权的经理的许可。发布 +不确定是否兼容GPL的代码可能是有特别问题的;公司的管理层和法律人员越早能够就 +发布内核开发项目达成一致,对参与的每个人都越好。 + +一些读者可能会认为他们的核心工作是为了支持还没有正式承认存在的产品。将雇主 +的计划公布在公共邮件列表上可能不是一个可行的选择。在这种情况下,有必要考虑 +保密是否真的是必要的;通常不需要把开发计划关在门内。 + +也就是说,有些情况下,一家公司在开发过程的早期就不能合法地披露其计划。拥有 +经验丰富的内核开发人员的公司可以选择以开环的方式进行,前提是他们以后能够避免 +严重的集成问题。对于没有这种内部专业知识的公司,最好的选择往往是聘请外部 +开发商根据保密协议审查计划。Linux基金会运行了一个NDA程序,旨在帮助解决这种 +情况; + + http://www.linuxfoundation.org/en/NDA_program + +这种审查通常足以避免以后出现严重问题,而无需公开披露项目。 -- cgit v1.2.3 From 7c691d647c2ae0bb945586501826dc0ede3aa99c Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:16 +0800 Subject: docs/zh_CN: add disclaimer/translator info in 3.Early-stage For people reviewing/complain. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/3.Early-stage.rst | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/3.Early-stage.rst b/Documentation/translations/zh_CN/process/3.Early-stage.rst index 11c9e89c52ce..b8676aec6005 100644 --- a/Documentation/translations/zh_CN/process/3.Early-stage.rst +++ b/Documentation/translations/zh_CN/process/3.Early-stage.rst @@ -1,3 +1,8 @@ +.. include:: ../disclaimer-zh_CN.rst + +:Original: :ref:`Documentation/process/3.Early-stage.rst ` +:Translator: Alex Shi + .. _cn_development_early_stage: 早期规划 -- cgit v1.2.3 From 513b308378a808c719ffaa77d95dfc91624db9e4 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:17 +0800 Subject: docs/zh_CN: add 4.Coding.rst The file was translated and could be found in developement-process Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- .../translations/zh_CN/process/4.Coding.rst | 284 +++++++++++++++++++++ 1 file changed, 284 insertions(+) create mode 100644 Documentation/translations/zh_CN/process/4.Coding.rst (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/4.Coding.rst b/Documentation/translations/zh_CN/process/4.Coding.rst new file mode 100644 index 000000000000..10a3236d4b21 --- /dev/null +++ b/Documentation/translations/zh_CN/process/4.Coding.rst @@ -0,0 +1,284 @@ +.. _cn_development_coding: + +使代码正确 +====================== + +虽然对于一个坚实的、面向社区的设计过程有很多话要说,但是任何内核开发项目的 +证明都在生成的代码中。它是将由其他开发人员检查并合并(或不合并)到主线树中 +的代码。所以这段代码的质量决定了项目的最终成功。 + +本节将检查编码过程。我们将从内核开发人员出错的几种方式开始。然后重点将转移 +到正确的事情和可以帮助这个任务的工具上。 + +陷阱 +---- + +编码风格 +******** + +内核长期以来都有一种标准的编码风格,如 +:ref:`Documentation/process/coding-style.rst ` 中所述。在大部分 +时间里,该文件中描述的政策被认为至多是建议性的。因此,内核中存在大量不符合编 +码风格准则的代码。代码的存在会给内核开发人员带来两个独立的危害。 + +首先,要相信内核编码标准并不重要,也不强制执行。事实上,如果没有按照标准对代 +码进行编码,那么向内核添加新代码是非常困难的;许多开发人员甚至会在审查代码之 +前要求对代码进行重新格式化。一个与内核一样大的代码库需要一些统一的代码,以使 +开发人员能够快速理解其中的任何部分。所以已经没有空间来存放奇怪的格式化代码了。 + +偶尔,内核的编码风格会与雇主的强制风格发生冲突。在这种情况下,内核的风格必须 +在代码合并之前获胜。将代码放入内核意味着以多种方式放弃一定程度的控制权——包括 +控制代码的格式化方式。 + +另一个陷阱是假定已经在内核中的代码迫切需要编码样式的修复。开发人员可能会开始 +生成重新格式化补丁,作为熟悉过程的一种方式,或者作为将其名称写入内核变更日志 +的一种方式,或者两者兼而有之。但是纯编码风格的修复被开发社区视为噪音;它们往 +往受到冷遇。因此,最好避免使用这种类型的补丁。由于其他原因,在处理一段代码的 +同时修复它的样式是很自然的,但是编码样式的更改不应该仅为了更改而进行。 + +编码风格的文档也不应该被视为绝对的法律,这是永远不会被违反的。如果有一个很好 +的理由反对这种样式(例如,如果拆分为适合80列限制的行,那么它的可读性就会大大 +降低),那么就这样做。 + +请注意,您还可以使用 ``clang-format`` 工具来帮助您处理这些规则,自动重新格式 +化部分代码,并查看完整的文件,以发现编码样式错误、拼写错误和可能的改进。它还 +可以方便地进行排序,包括对齐变量/宏、回流文本和其他类似任务。有关详细信息,请 +参阅文件 :ref:`Documentation/process/clang-format.rst ` + +抽象层 +****** + +计算机科学教授教学生以灵活性和信息隐藏的名义广泛使用抽象层。当然,内核广泛 +地使用了抽象;任何涉及数百万行代码的项目都不能做到这一点并存活下来。但经验 +表明,过度或过早的抽象可能和过早的优化一样有害。抽象应用于所需的级别, +不要过度。 + +在一个简单的级别上,考虑一个函数的参数,该参数总是由所有调用方作为零传递。 +我们可以保留这个论点: 以防有人最终需要使用它提供的额外灵活性。不过,到那时, +实现这个额外参数的代码很有可能以某种从未被注意到的微妙方式被破坏——因为它从 +未被使用过。或者,当需要额外的灵活性时,它不会以符合程序员早期期望的方式来 +这样做。内核开发人员通常会提交补丁来删除未使用的参数;一般来说,首先不应该 +添加这些参数。 + +隐藏硬件访问的抽象层——通常允许大量的驱动程序在多个操作系统中使用——尤其不受 +欢迎。这样的层使代码变得模糊,可能会造成性能损失;它们不属于Linux内核。 + +另一方面,如果您发现自己从另一个内核子系统复制了大量的代码,那么现在是时候 +问一下,事实上,将这些代码中的一些提取到单独的库中,或者在更高的层次上实现 +这些功能是否有意义。在整个内核中复制相同的代码没有价值。 + +#ifdef 和预处理 +*************** + +C预处理器似乎给一些C程序员带来了强大的诱惑,他们认为它是一种有效地将大量灵 +活性编码到源文件中的方法。但是预处理器不是C,大量使用它会导致代码对其他人来 +说更难读取,对编译器来说更难检查正确性。大量的预处理器几乎总是代码需要一些 +清理工作的标志。 + +使用ifdef的条件编译实际上是一个强大的功能,它在内核中使用。但是很少有人希望 +看到代码被大量地撒上ifdef块。作为一般规则,ifdef的使用应尽可能限制在头文件 +中。有条件编译的代码可以限制函数,如果代码不存在,这些函数就会变成空的。然后 +编译器将悄悄地优化对空函数的调用。结果是代码更加清晰,更容易理解。 + +C预处理器宏存在许多危险,包括可能对具有副作用且没有类型安全性的表达式进行多 +重评估。如果您试图定义宏,请考虑创建一个内联函数。结果相同的代码,但是内联 +函数更容易读取,不会多次计算其参数,并且允许编译器对参数和返回值执行类型检查。 + +内联函数 +******** + +不过,内联函数本身也存在风险。程序员可以倾心于避免函数调用和用内联函数填充源 +文件所固有的效率。然而,这些功能实际上会降低性能。因为它们的代码在每个调用站 +点都被复制,所以它们最终会增加编译内核的大小。反过来,这会对处理器的内存缓存 +造成压力,从而大大降低执行速度。通常,内联函数应该非常小,而且相对较少。毕竟, +函数调用的成本并不高;大量内联函数的创建是过早优化的典型例子。 + +一般来说,内核程序员会忽略缓存效果,这会带来危险。在开始的数据结构课程中,经 +典的时间/空间权衡通常不适用于当代硬件。空间就是时间,因为一个大的程序比一个 +更紧凑的程序运行得慢。 + +最近的编译器在决定一个给定函数是否应该被内联方面扮演着越来越积极的角色。 +因此,“inline”关键字的自由放置可能不仅仅是过度的,它也可能是无关的。 + +锁 +** + +2006年5月,“deviceescape”网络堆栈在GPL下发布,并被纳入主线内核。这是一个受 +欢迎的消息;对Linux中无线网络的支持充其量被认为是不合格的,而deviceescape +堆栈提供了修复这种情况的承诺。然而,直到2007年6月(2.6.22),这段代码才真 +正进入主线。发生了什么? + +这段代码显示了许多闭门造车的迹象。但一个特别大的问题是,它并不是设计用于多 +处理器系统。在合并这个网络堆栈(现在称为mac80211)之前,需要对其进行一个锁 +方案的改造。 + +曾经,Linux内核代码可以在不考虑多处理器系统所带来的并发性问题的情况下进行 +开发。然而,现在,这个文件是写在双核笔记本电脑上的。即使在单处理器系统上, +为提高响应能力所做的工作也会提高内核内的并发性水平。编写内核代码而不考虑锁 +的日子已经过去很长了。 + +可以由多个线程并发访问的任何资源(数据结构、硬件寄存器等)必须由锁保护。新 +的代码应该记住这一要求;事后改装锁是一项相当困难的任务。内核开发人员应该花 +时间充分了解可用的锁原语,以便为作业选择正确的工具。显示对并发性缺乏关注的 +代码进入主线将很困难。 + +回归 +**** + +最后一个值得一提的危险是:它可能会引起改变(这可能会带来很大的改进),从而 +导致现有用户的某些东西中断。这种变化被称为“回归”,回归已经成为主线内核最不 +受欢迎的。除少数例外情况外,如果回归不能及时修正,会导致回归的变化将被取消。 +最好首先避免回归。 + +人们常常争论,如果回归让更多人可以工作,远超过产生问题,那么回归是合理的。 +如果它破坏的一个系统却为十个系统带来新的功能,为什么不进行更改呢?2007年7月, +Linus对这个问题给出了最佳答案: + +:: + 所以我们不会通过引入新问题来修复错误。那样的谎言很疯狂,没有人知道 + 你是否真的有进展。是前进两步,后退一步,还是向前一步,向后两步? + +(http://lwn.net/articles/243460/) + +一种特别不受欢迎的回归类型是用户空间ABI的任何变化。一旦接口被导出到用户空间, +就必须无限期地支持它。这一事实使得用户空间接口的创建特别具有挑战性:因为它们 +不能以不兼容的方式进行更改,所以必须第一次正确地进行更改。因此,用户空间界面 +总是需要大量的思考、清晰的文档和广泛的审查。 + + +代码检查工具 +------------ + +至少目前,编写无错误代码仍然是我们中很少人能达到的理想状态。不过,我们希望做 +的是,在代码进入主线内核之前,尽可能多地捕获并修复这些错误。为此,内核开发人 +员已经组装了一系列令人印象深刻的工具,可以自动捕获各种各样的模糊问题。计算机 +发现的任何问题都是一个以后不会困扰用户的问题,因此,只要有可能,就应该使用 +自动化工具。 + +第一步只是注意编译器产生的警告。当代版本的GCC可以检测(并警告)大量潜在错误。 +通常,这些警告都指向真正的问题。提交以供审阅的代码通常不会产生任何编译器警告。 +在消除警告时,注意了解真正的原因,并尽量避免“修复”,使警告消失而不解决其原因。 + +请注意,并非所有编译器警告都默认启用。使用“make EXTRA_CFLAGS=-W”构建内核以 +获得完整集合。 + +内核提供了几个配置选项,可以打开调试功能;大多数配置选项位于“kernel hacking” +子菜单中。对于任何用于开发或测试目的的内核,都应该启用其中几个选项。特别是, +您应该打开: + + - 启用 ENABLE_MUST_CHECK and FRAME_WARN 以获得一组额外的警告,以解决使用不 + 推荐使用的接口或忽略函数的重要返回值等问题。这些警告生成的输出可能是冗长 + 的,但您不必担心来自内核其他部分的警告。 + + - DEBUG_OBJECTS 将添加代码,以跟踪内核创建的各种对象的生存期,并在出现问题时 + 发出警告。如果要添加创建(和导出)自己的复杂对象的子系统,请考虑添加对对象 + 调试基础结构的支持。 + + - DEBUG_SLAB 可以发现各种内存分配和使用错误;它应该用于大多数开发内核。 + + - DEBUG_SPINLOCK, DEBUG_ATOMIC_SLEEP and DEBUG_MUTEXES 会发现许多常见的 + 锁定错误. + +还有很多其他调试选项,其中一些将在下面讨论。其中一些具有显著的性能影响,不应 +一直使用。但是,在学习可用选项上花费的一些时间可能会在短期内得到多次回报。 + +其中一个较重的调试工具是锁定检查器或“lockdep”。该工具将跟踪系统中每个锁 +(spinlock或mutex)的获取和释放、获取锁的相对顺序、当前中断环境等等。然后, +它可以确保总是以相同的顺序获取锁,相同的中断假设适用于所有情况,等等。换句话 +说,lockdep可以找到许多场景,在这些场景中,系统很少会死锁。在部署的系统中, +这种问题可能会很痛苦(对于开发人员和用户而言);LockDep允许提前以自动方式 +发现问题。具有任何类型的非普通锁定的代码在提交包含前应在启用lockdep的情况 +下运行。 + +作为一个勤奋的内核程序员,毫无疑问,您将检查任何可能失败的操作(如内存分配) +的返回状态。然而,事实上,最终的故障恢复路径可能完全没有经过测试。未测试的 +代码往往会被破坏;如果所有这些错误处理路径都被执行了几次,那么您可能对代码 +更有信心。 + +内核提供了一个可以做到这一点的错误注入框架,特别是在涉及内存分配的情况下。 +启用故障注入后,内存分配的可配置百分比将失败;这些失败可以限制在特定的代码 +范围内。在启用了故障注入的情况下运行,程序员可以看到当情况恶化时代码如何响 +应。有关如何使用此工具的详细信息,请参阅 +Documentation/fault-injection/fault-injection.txt。 + +使用“sparse”静态分析工具可以发现其他类型的错误。对于sparse,可以警告程序员 +用户空间和内核空间地址之间的混淆、big endian和small endian数量的混合、在需 +要一组位标志的地方传递整数值等等。sparse必须单独安装(如果您的分发服务器没 +有将其打包,可以在 https://sparse.wiki.kernel.org/index.php/Main_page)找到, +然后可以通过在make命令中添加“C=1”在代码上运行它。 + +“Coccinelle”工具 :ref:`http://coccinelle.lip6.fr/ ` +能够发现各种潜在的编码问题;它还可以为这些问题提出修复方案。在 +scripts/coccinelle目录下已经打包了相当多的内核“语义补丁”;运行 +“make coccicheck”将运行这些语义补丁并报告发现的任何问题。有关详细信息,请参阅 +:ref:`Documentation/dev-tools/coccinelle.rst ` + + +其他类型的可移植性错误最好通过为其他体系结构编译代码来发现。如果没有S/390系统 +或Blackfin开发板,您仍然可以执行编译步骤。可以在以下位置找到一组用于x86系统的 +大型交叉编译器: + + http://www.kernel.org/pub/tools/crosstool/ + +花一些时间安装和使用这些编译器将有助于避免以后的尴尬。 + +文档 +---- + +文档通常比内核开发规则更为例外。即便如此,足够的文档将有助于简化将新代码合并 +到内核中的过程,使其他开发人员的生活更轻松,并对您的用户有所帮助。在许多情况 +下,文件的添加已基本上成为强制性的。 + +任何补丁的第一个文档是其关联的变更日志。日志条目应该描述正在解决的问题、解决 +方案的形式、处理补丁的人员、对性能的任何相关影响,以及理解补丁可能需要的任何 +其他内容。确保changelog说明了为什么补丁值得应用;大量开发人员未能提供这些信息。 + +任何添加新用户空间界面的代码(包括新的sysfs或/proc文件)都应该包含该界面的 +文档,该文档使用户空间开发人员能够知道他们在使用什么。请参阅 +Documentation/abi/readme,了解如何格式化此文档以及需要提供哪些信息。 + +文件 :ref:`Documentation/admin-guide/kernel-parameters.rst ` +描述了内核的所有引导时间参数。任何添加新参数的补丁都应该向该文件添加适当的 +条目。 + +任何新的配置选项都必须附有帮助文本,帮助文本清楚地解释了这些选项以及用户可能 +希望何时选择它们。 + +许多子系统的内部API信息通过专门格式化的注释进行记录;这些注释可以通过 +“kernel-doc”脚本以多种方式提取和格式化。如果您在具有kerneldoc注释的子系统中 +工作,则应该维护它们,并根据需要为外部可用的功能添加它们。即使在没有如此记录 +的领域中,为将来添加kerneldoc注释也没有坏处;实际上,这对于刚开始开发内核的人 +来说是一个有用的活动。这些注释的格式以及如何创建kerneldoc模板的一些信息可以在 +:ref:`Documentation/doc-guide/ ` 上找到。 + +任何阅读大量现有内核代码的人都会注意到,注释的缺失往往是最值得注意的。再一次, +对新代码的期望比过去更高;合并未注释的代码将更加困难。这就是说,人们几乎不希望 +用语言注释代码。代码本身应该是可读的,注释解释了更微妙的方面。 + +某些事情应该总是被注释。使用内存屏障时,应附上一行文字,解释为什么需要设置内存 +屏障。数据结构的锁定规则通常需要在某个地方解释。一般来说,主要数据结构需要全面 +的文档。应该指出单独代码位之间不明显的依赖性。任何可能诱使代码看门人进行错误的 +“清理”的事情都需要一个注释来说明为什么要这样做。等等。 + + +内部API更改 +----------- + +内核提供给用户空间的二进制接口不能被破坏,除非在最严重的情况下。相反,内核的 +内部编程接口是高度流动的,当需要时可以更改。如果你发现自己不得不处理一个内核 +API,或者仅仅因为它不满足你的需求而不使用特定的功能,这可能是API需要改变的一 +个标志。作为内核开发人员,您有权进行此类更改。 + +当然, 可以进行API更改,但它们必须是合理的。因此,任何进行内部API更改的补丁都 +应该附带一个关于更改内容和必要原因的描述。这种变化也应该分解成一个单独的补丁, +而不是埋在一个更大的补丁中。 + +另一个要点是,更改内部API的开发人员通常要负责修复内核树中被更改破坏的任何代码。 +对于一个广泛使用的函数,这个职责可以导致成百上千的变化,其中许多变化可能与其他 +开发人员正在做的工作相冲突。不用说,这可能是一项大工作,所以最好确保理由是 +可靠的。请注意,coccinelle工具可以帮助进行广泛的API更改。 + +在进行不兼容的API更改时,应尽可能确保编译器捕获未更新的代码。这将帮助您确保找 +到该接口的树内用处。它还将警告开发人员树外代码存在他们需要响应的更改。支持树外 +代码不是内核开发人员需要担心的事情,但是我们也不必使树外开发人员的生活有不必要 +的困难。 -- cgit v1.2.3 From c654ddd8ba911dc0b436743f29d2abc1645aa58d Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:18 +0800 Subject: docs/zh_CN: add disclaimer and translator info in 4.Coding To let people know where to complain. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/4.Coding.rst | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/4.Coding.rst b/Documentation/translations/zh_CN/process/4.Coding.rst index 10a3236d4b21..2b60752a81b2 100644 --- a/Documentation/translations/zh_CN/process/4.Coding.rst +++ b/Documentation/translations/zh_CN/process/4.Coding.rst @@ -1,3 +1,8 @@ +.. include:: ../disclaimer-zh_CN.rst + +:Original: :ref:`Documentation/process/4.Coding.rst ` +:Translator: Alex Shi + .. _cn_development_coding: 使代码正确 -- cgit v1.2.3 From ea09bbd4ce77dd89cdc8e2ee0b2bf469e59d4967 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:19 +0800 Subject: docs/zh_CN: add 5.Posting.rst into development-process Since the doc stub was mentained in development-process.rst, it will appears in 'make htmldocs'. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- .../translations/zh_CN/process/5.Posting.rst | 231 +++++++++++++++++++++ 1 file changed, 231 insertions(+) create mode 100644 Documentation/translations/zh_CN/process/5.Posting.rst (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/5.Posting.rst b/Documentation/translations/zh_CN/process/5.Posting.rst new file mode 100644 index 000000000000..547d99117452 --- /dev/null +++ b/Documentation/translations/zh_CN/process/5.Posting.rst @@ -0,0 +1,231 @@ +.. _cn_development_posting: + +发送补丁 +======== + +迟早,当您的工作准备好提交给社区进行审查,并最终包含到主线内核中时。不出所料, +内核开发社区已经发展出一套用于发布补丁的约定和过程;遵循这些约定和过程将使 +参与其中的每个人的生活更加轻松。本文件将试图合理详细地涵盖这些期望;更多信息 +也可在以下文件中找到 +:ref:`Documentation/process/submitting-patches.rst `, +:ref:`Documentation/process/submitting-drivers.rst ` +和 :ref:`Documentation/process/submit-checklist.rst `. + +何时邮寄 +-------- + +在补丁完全“准备好”之前,有一个不断的诱惑来避免发布补丁。对于简单的补丁, +这不是问题。但是,如果正在完成的工作很复杂,那么在工作完成之前从社区获得 +反馈就可以获得很多好处。因此,您应该考虑发布正在进行的工作,甚至使Git树 +可用,以便感兴趣的开发人员可以随时赶上您的工作。 + +当发布还没有准备好包含的代码时,最好在发布本身中这样说。还应提及任何有待完成 +的主要工作和任何已知问题。很少有人会看到那些被认为是半生不熟的补丁,但是那些 +人会想到他们可以帮助你把工作推向正确的方向。 + +创建补丁之前 +------------ + +在考虑将补丁发送到开发社区之前,有许多事情应该做。这些包括: + + - 尽可能地测试代码。利用内核的调试工具,确保内核使用所有合理的配置选项组合 + 进行构建,使用跨编译器为不同的体系结构进行构建等。 + + - 确保您的代码符合内核编码风格指南。 + + - 您的更改是否具有性能影响?如果是这样,您应该运行基准测试来显示您的变更的 + 影响(或好处);结果的摘要应该包含在补丁中。 + + - 确保您有权发布代码。如果这项工作是为雇主完成的,雇主对这项工作具有所有权, + 并且必须同意根据GPL对其进行放行。 + +一般来说,在发布代码之前进行一些额外的思考,几乎总是能在短时间内得到回报。 + +补丁准备 +-------- + +准备发布补丁可能是一个惊人的工作量,但再次尝试节省时间在这里通常是不明智的, +即使在短期内。 + +必须针对内核的特定版本准备补丁。作为一般规则,补丁程序应该基于Linus的Git树中 +的当前主线。当以主线为基础时,从一个众所周知的发布点开始——一个稳定的或RC的 +发布——而不是在一个主线分支任意点。 + +但是,可能需要针对-mm、linux-next或子系统树生成版本,以便于更广泛的测试和审查。 +根据补丁的区域以及其他地方的情况,针对这些其他树建立补丁可能需要大量的工作来 +解决冲突和处理API更改。 + +只有最简单的更改才应格式化为单个补丁;其他所有更改都应作为一系列逻辑更改进行。 +分割补丁是一门艺术;一些开发人员花了很长时间来弄清楚如何按照社区期望的方式来 +做。然而,有一些经验法则可以大大帮助: + + - 您发布的补丁程序系列几乎肯定不会是工作系统中的一系列更改。相反,您所做的 + 更改需要在最终形式中加以考虑,然后以有意义的方式进行拆分。开发人员对离散的、 + 自包含的更改感兴趣,而不是您获取这些更改的路径。 + + - 每个逻辑上独立的变更都应该格式化为单独的补丁。这些更改可以是小的(“向此 + 结构添加字段”)或大的(例如,添加一个重要的新驱动程序),但它们在概念上 + 应该是小的,并且可以接受一行描述。每个补丁都应该做一个特定的更改,可以单独 + 检查并验证它所做的事情。 + + - 作为重申上述准则的一种方法:不要在同一补丁中混合不同类型的更改。如果一个 + 补丁修复了一个关键的安全漏洞,重新排列了一些结构,并重新格式化了代码,那么 + 很有可能它会被忽略,而重要的修复将丢失。 + + - 每个补丁都应该产生一个内核,它可以正确地构建和运行;如果补丁系列在中间被 + 中断,那么结果应该仍然是一个工作的内核。补丁系列的部分应用是使用 + “git bisct”工具查找回归的一个常见场景;如果结果是一个损坏的内核,那么对于 + 那些从事追踪问题的高尚工作的开发人员和用户来说,将使他们的生活更加艰难。 + + - 不过,不要过分。一位开发人员曾经将一组编辑内容作为500个单独的补丁发布到一个 + 文件中,这并没有使他成为内核邮件列表中最受欢迎的人。一个补丁可以相当大, + 只要它仍然包含一个单一的逻辑变更。 + + - 用一系列补丁添加一个全新的基础设施是很有诱惑力的,但是在系列中的最后一个 + 补丁启用整个补丁之前,该基础设施是不使用的。如果可能的话,应该避免这种 + 诱惑;如果这个系列增加了回归,那么二分法将指出最后一个补丁是导致问题的 + 补丁,即使真正的bug在其他地方。只要有可能,添加新代码的补丁程序应该立即 + 激活该代码。 + +创建完美补丁系列的工作可能是一个令人沮丧的过程,在完成“真正的工作”之后需要花费 +大量的时间和思考。但是,如果做得好,这是一段很好的时间。 + +补丁格式和更改日志 +------------------ + +所以现在你有了一系列完美的补丁可以发布,但是这项工作还没有完成。每个补丁都 +需要被格式化成一条消息,它可以快速而清晰地将其目的传达给世界其他地方。为此, +每个补丁将由以下部分组成: + + - 命名补丁作者的可选“from”行。只有当你通过电子邮件传递别人的补丁时,这一行 + 才是必要的,但是如果有疑问,添加它不会有任何伤害。 + + - 一行描述补丁的作用。对于没有其他上下文的读者来说,此消息应该足够了解补丁 + 的范围;这是将在“短格式”变更日志中显示的行。此消息通常首先用相关的子系统 + 名称格式化,然后是补丁的目的。例如: + + :: + + gpio: fix build on CONFIG_GPIO_SYSFS=n + + - 一个空白行,后面是补丁内容的详细描述。这个描述可以是必需的;它应该说明补丁 + 的作用以及为什么它应该应用于内核。 + + - 一个或多个标记行,至少有一个由补丁作者的:signed-off-by 签名。签名将在下面 + 更详细地描述。 + +上面的项目一起构成补丁的变更日志。写一篇好的变更日志是一门至关重要但常常被 +忽视的艺术;值得花一点时间来讨论这个问题。当你写一个变更日志时,你应该记住 +有很多不同的人会读你的话。其中包括子系统维护人员和审查人员,他们需要决定是否 +应该包括补丁,分销商和其他维护人员试图决定是否应该将补丁反向移植到其他内核, +bug搜寻人员想知道补丁是否负责他们正在追查的问题,想知道内核如何变化的用户。 +等等。一个好的变更日志以最直接和最简洁的方式向所有这些人传达所需的信息。 + +为此,总结行应该描述变更的影响和动机,以及在一行约束条件下可能发生的变化。 +然后,详细的描述可以详述这些主题,并提供任何需要的附加信息。如果补丁修复了 +一个bug,请引用引入该bug的commit(如果可能,请在引用commits时同时提供commit id +和标题)。如果某个问题与特定的日志或编译器输出相关联,请包含该输出以帮助其他 +人搜索同一问题的解决方案。如果更改是为了支持以后补丁中的其他更改,那么就这么 +说。如果更改了内部API,请详细说明这些更改以及其他开发人员应该如何响应。一般 +来说,你越能把自己放在每个阅读你的changelog的人的位置上,changelog(和内核 +作为一个整体)就越好。 + +不用说,变更日志应该是将变更提交到修订控制系统时使用的文本。接下来是: + + - 补丁本身,采用统一的(“-u”)补丁格式。将“-p”选项用于diff将使函数名与更改 + 相关联,从而使结果补丁更容易被其他人读取。 + +您应该避免在补丁中包括对不相关文件(例如,由构建过程生成的文件或编辑器 +备份文件)的更改。文档目录中的文件“dontdiff”在这方面有帮助;使用“-X”选项将 +其传递给diff。 + +上面提到的标签用于描述各种开发人员如何与这个补丁的开发相关联。 +:ref:`documentation/process/submitting-patches.rst ` +文档中对它们进行了详细描述;下面是一个简短的总结。每一行的格式如下: + +:: + + tag: Full Name optional-other-stuff + +常用的标签有: + + - Signed-off-by: 这是一个开发人员的证明,他或她有权提交补丁以包含到内核中。 + 这是开发来源认证协议,其全文可在:ref:`documentation/process/submitting-patches.rst ` + 中找到,如果没有适当的签字,则不能合并到主线中。 + + - Co-developed-by: 声明补丁也是由另一个开发人员和原始作者一起创建的。当多 + 个人在一个补丁上工作时,这很有用。注意,此人也需要在补丁中有一个签名行。 + + - Acked-by: 表示另一个开发人员(通常是相关代码的维护人员)同意补丁适合包含 + 在内核中。 + + - Tested-by: 声明指定的人已经测试了补丁并发现它可以工作。 + + - Reviewed-by: 指定的开发人员已经审查了补丁的正确性;有关详细信息,请参阅 + :ref:`documentation/process/submitting-patches.rst ` + + - Reported-by: 指定报告此补丁修复的问题的用户;此标记用于提供感谢。 + + - Cc:指定的人收到了补丁的副本,并有机会对此发表评论。 + +在补丁中添加标签时要小心:只有cc:才适合在没有指定人员明确许可的情况下添加。 + +发送补丁 +-------- + +在邮寄补丁之前,您还需要注意以下几点: + + - 您确定您的邮件发送程序不会损坏补丁吗?有免费的空白更改或由邮件客户端 + 执行的行包装的补丁不会在另一端复原,并且通常不会进行任何详细检查。如果有 + 任何疑问,把补丁寄给你自己,让你自己相信它是完好无损的。 + + :ref:`documentation/process/email-clients.rst ` + 提供了一些有用的提示,可以让特定的邮件客户机工作以发送补丁。 + + - 你确定你的补丁没有愚蠢的错误吗?您应该始终通过scripts/checkpatch.pl运行 + 补丁程序,并解决它提出的投诉。请记住,checkpatch.pl虽然是大量思考内核 + 补丁应该是什么样子的体现,但它并不比您聪明。如果修复checkpatch.pl投诉会 + 使代码变得更糟,请不要这样做。 + +补丁应始终以纯文本形式发送。请不要将它们作为附件发送;这使得审阅者在答复中更难 +引用补丁的部分。相反,只需将补丁直接放到您的消息中。 + +邮寄补丁时,重要的是将副本发送给任何可能感兴趣的人。与其他一些项目不同,内核 +鼓励人们错误地发送过多的副本;不要假定相关人员会看到您在邮件列表中的发布。 +尤其是,副本应发送至: + + - 受影响子系统的维护人员。如前所述,维护人员文件是查找这些人员的第一个地方。 + + - 其他在同一领域工作的开发人员,尤其是那些现在可能在那里工作的开发人员。使用 + git查看还有谁修改了您正在处理的文件,这很有帮助。 + + - 如果您对错误报告或功能请求做出响应,也可以抄送原始发送人。 + + - 将副本发送到相关邮件列表,或者,如果没有其他应用,则发送到Linux内核列表。 + + - 如果您正在修复一个bug,请考虑该修复是否应进入下一个稳定更新。如果是这样, + stable@vger.kernel.org应该得到补丁的副本。另外,在补丁本身的标签中添加 + 一个“cc:stable@vger.kernel.org”;这将使稳定团队在修复进入主线时收到通知。 + +当为一个补丁选择接收者时,最好知道你认为谁最终会接受这个补丁并将其合并。虽然 +可以将补丁直接发送给LinusTorvalds并让他合并,但通常情况下不会这样做。Linus +很忙,并且有子系统维护人员负责监视内核的特定部分。通常您会希望维护人员合并您 +的补丁。如果没有明显的维护人员,Andrew Morton通常是最后的补丁目标。 + +补丁需要好的主题行。补丁程序行的规范格式如下: + +:: + + [PATCH nn/mm] subsys: one-line description of the patch + +其中“nn”是补丁的序号,“mm”是系列中补丁的总数,“subsys”是受影响子系统的名称。 +显然,一个单独的补丁可以省略nn/mm。 + +如果您有一系列重要的补丁,那么通常将介绍性描述作为零部分发送。不过,这种约定 +并没有得到普遍遵循;如果您使用它,请记住简介中的信息不会使它进入内核变更日志。 +因此,请确保补丁本身具有完整的变更日志信息。 + +一般来说,多部分补丁的第二部分和后续部分应作为对第一部分的回复发送,以便它们 +在接收端都连接在一起。像git和coilt这样的工具有命令,可以通过适当的线程发送 +一组补丁。但是,如果您有一个长系列,并且正在使用git,请远离–chain reply-to +选项,以避免创建异常深的嵌套。 -- cgit v1.2.3 From c9300515f0a068b42e3c68776f625c4c7ba07a52 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:20 +0800 Subject: docs/zh_CN: add disclaimer and translator info in 5.Posting To give way for people's comments Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/5.Posting.rst | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/5.Posting.rst b/Documentation/translations/zh_CN/process/5.Posting.rst index 547d99117452..c19b6ca57b8c 100644 --- a/Documentation/translations/zh_CN/process/5.Posting.rst +++ b/Documentation/translations/zh_CN/process/5.Posting.rst @@ -1,3 +1,8 @@ +.. include:: ../disclaimer-zh_CN.rst + +:Original: :ref:`Documentation/process/5.Posting.rst ` +:Translator: Alex Shi + .. _cn_development_posting: 发送补丁 -- cgit v1.2.3 From 3b12cfded0a608fec634a62e183e25a9ba0f5bb5 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:21 +0800 Subject: docs/zh_CN: add the 6th doc 6.Followthrought.rst Now the doc could be found with 'make htmldocs' in Chinese. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- .../translations/zh_CN/process/6.Followthrough.rst | 140 +++++++++++++++++++++ 1 file changed, 140 insertions(+) create mode 100644 Documentation/translations/zh_CN/process/6.Followthrough.rst (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/6.Followthrough.rst b/Documentation/translations/zh_CN/process/6.Followthrough.rst new file mode 100644 index 000000000000..28c81b80d3af --- /dev/null +++ b/Documentation/translations/zh_CN/process/6.Followthrough.rst @@ -0,0 +1,140 @@ +.. _cn_development_followthrough: + +跟进 +==== + +在这一点上,您已经遵循了到目前为止给出的指导方针,并且,随着您自己的工程技能 +的增加,已经发布了一系列完美的补丁。即使是经验丰富的内核开发人员也能犯的最大 +错误之一是,认为他们的工作现在已经完成了。事实上,发布补丁意味着进入流程的下 +一个阶段,可能还需要做很多工作。 + +一个补丁在第一次发布时就非常出色,没有改进的余地,这是很罕见的。内核开发流程 +认识到这一事实,因此,它非常注重对已发布代码的改进。作为代码的作者,您应该与 +内核社区合作,以确保您的代码符合内核的质量标准。如果不参与这个过程,很可能会 +阻止将补丁包含到主线中。 + +与审阅者合作 +------------ + +任何意义上的补丁都会导致其他开发人员在审查代码时发表大量评论。对于许多开发 +人员来说,与审查人员合作可能是内核开发过程中最令人生畏的部分。但是,如果你 +记住一些事情,生活会变得容易得多: + + - 如果你已经很好地解释了你的补丁,评论人员会理解它的价值,以及为什么你会 + 费尽心思去写它。但是这个并不能阻止他们提出一个基本的问题:五年或十年后 + 用这个代码维护一个内核会是什么感觉?你可能被要求做出的许多改变——从编码风格 + 的调整到大量的重写——都来自于对Linux的理解,即从现在起十年后,Linux仍将在 + 开发中。 + + - 代码审查是一项艰苦的工作,这是一项相对吃力不讨好的工作;人们记得谁编写了 + 内核代码,但对于那些审查它的人来说,几乎没有什么持久的名声。因此,评论 + 人员可能会变得暴躁,尤其是当他们看到同样的错误被一遍又一遍地犯下时。如果 + 你得到了一个看起来愤怒、侮辱或完全冒犯你的评论,抵制以同样方式回应的冲动。 + 代码审查是关于代码的,而不是关于人的,代码审查人员不会亲自攻击您。 + + - 同样,代码审查人员也不想以牺牲你雇主的利益为代价来宣传他们雇主的议程。 + 内核开发人员通常希望今后几年能在内核上工作,但他们明白他们的雇主可能会改 + 变。他们真的,几乎毫无例外地,致力于创造他们所能做到的最好的内核;他们并 + 没有试图给雇主的竞争对手造成不适。 + +所有这些归根结底都是,当审阅者向您发送评论时,您需要注意他们正在进行的技术 +观察。不要让他们的表达方式或你自己的骄傲阻止这种事情的发生。当你在一个补丁 +上得到评论时,花点时间去理解评论人想说什么。如果可能的话,请修复审阅者要求 +您修复的内容。然后回复审稿人:谢谢他们,并描述你将如何回答他们的问题。 + +请注意,您不必同意审阅者建议的每个更改。如果您认为审阅者误解了您的代码,请 +解释到底发生了什么。如果您对建议的更改有技术上的异议,请描述它并证明您对该 +问题的解决方案是正确的。如果你的解释有道理,审稿人会接受的。不过,如果你的 +解释不能证明是有说服力的,尤其是当其他人开始同意审稿人的观点时,请花些时间 +重新考虑一下。你很容易对自己解决问题的方法视而不见,以至于你没有意识到某个 +问题根本是错误的,或者你甚至没有解决正确的问题。 + +Andrew Morton建议,每一条不会导致代码更改的评论都应该导致额外的代码注释; +这可以帮助未来的评论人员避免出现第一次出现的问题。 + +一个致命的错误是忽视评论,希望它们会消失。他们不会走的。如果您在没有对之前 +收到的注释做出响应的情况下重新发布代码,那么很可能会发现补丁毫无用处。 + +说到重新发布代码:请记住,审阅者不会记住您上次发布的代码的所有细节。因此, +提醒审查人员以前提出的问题以及您如何处理这些问题总是一个好主意;补丁变更 +日志是提供此类信息的好地方。审阅者不必搜索列表档案来熟悉上次所说的内容; +如果您帮助他们开始运行,当他们重新访问您的代码时,他们的心情会更好。 + +如果你已经试着做正确的事情,但事情仍然没有进展呢?大多数技术上的分歧都可以 +通过讨论来解决,但有时人们只需要做出决定。如果你真的认为这个决定对你不利, +你可以试着向更高的权力上诉。在这篇文章中,更高的权力倾向于Andrew Morton。 +Andrew在内核开发社区中受i很大的尊重;他经常为似乎被绝望地阻塞事情清障。 +尽管如此,对Andrew的呼吁不应轻而易举,也不应在所有其他替代方案都被探索之前 +使用。当然,记住,他也可能不同意你的意见。 + +接下来会发生什么 +---------------- + +如果一个补丁被认为是添加到内核中的一件好事,并且一旦大多数审查问题得到解决, +下一步通常是进入子系统维护人员的树中。工作方式因子系统而异;每个维护人员都 +有自己的工作方式。特别是,可能有不止一棵树——一棵树,也许,专门用于计划下一 +个合并窗口的补丁,另一棵树用于长期工作。 + +对于应用于没有明显子系统树(例如内存管理修补程序)的区域的修补程序,默认树 +通常以-mm结尾。影响多个子系统的补丁也可以最终通过-mm树。 + +包含在子系统树中可以提高补丁的可见性。现在,使用该树的其他开发人员将默认获 +得补丁。子系统树通常也为Linux提供支持,使其内容对整个开发社区可见。在这一点 +上,您很可能会从一组新的审阅者那里得到更多的评论;这些评论需要像上一轮那样 +得到回答。 + +在这一点上也会发生什么,这取决于你的补丁的性质,是与其他人正在做的工作发生 +冲突。在最坏的情况下,严重的补丁冲突可能会导致一些工作被搁置,以便剩余的补丁 +可以成形并合并。另一些时候,冲突解决将涉及到与其他开发人员合作,可能还会 +在树之间移动一些补丁,以确保所有的应用都是干净的。这项工作可能是一件痛苦的 +事情,但要计算您的福祉:在Linux下一棵树出现之前,这些冲突通常只在合并窗口 +中出现,必须迅速解决。现在可以在合并窗口打开之前,在空闲时解决这些问题。 + +有朝一日,如果一切顺利,您将登录并看到您的补丁已经合并到主线内核中。祝贺你! +然而,一旦庆祝活动完成(并且您已经将自己添加到维护人员文件中),就值得记住 +一个重要的小事实:工作仍然没有完成。并入主线带来了自身的挑战。 + +首先,补丁的可见性再次提高。可能会有新一轮的开发者评论,他们以前不知道这 +个补丁。忽略它们可能很有诱惑力,因为您的代码不再存在任何被合并的问题。但是, +要抵制这种诱惑,您仍然需要对有问题或建议的开发人员作出响应。 + +不过,更重要的是:将代码包含在主线中会将代码交给更大的一组测试人员。即使您 +为尚未提供的硬件提供了驱动程序,您也会惊讶于有多少人会将您的代码构建到内核 +中。当然,如果有测试人员,也会有错误报告。 + +最糟糕的错误报告是回归。如果你的补丁导致回归,你会发现很多不舒服的眼睛盯着 +你;回归需要尽快修复。如果您不愿意或无法修复回归(其他人都不会为您修复), +那么在稳定期内,您的补丁几乎肯定会被移除。除了否定您为使补丁进入主线所做的 +所有工作之外,如果由于未能修复回归而取消补丁,很可能会使将来的工作更难合并。 + +在处理完任何回归之后,可能还有其他普通的bug需要处理。稳定期是修复这些错误并 +确保代码在主线内核版本中的首次发布尽可能可靠的最好机会。所以,请回答错误 +报告,并尽可能解决问题。这就是稳定期的目的;一旦解决了旧补丁的任何问题,就 +可以开始创建酷的新补丁。 + +别忘了,还有其他里程碑也可能会创建bug报告:下一个主线稳定版本,当著名的发行 +商选择包含补丁的内核版本时,等等。继续响应这些报告是您工作的基本骄傲。但是, +如果这不是足够的动机,那么也值得考虑的是,开发社区会记住那些在合并后对代码 +失去兴趣的开发人员。下一次你发布补丁时,他们会以你以后不会在身边维护它为假 +设来评估它。 + +其他可能发生的事情 +------------------ + +有一天,你可以打开你的邮件客户端,看到有人给你寄了一个代码补丁。毕竟,这是 +让您的代码公开存在的好处之一。如果您同意这个补丁,您可以将它转发给子系统 +维护人员(确保包含一个正确的From:行,这样属性是正确的,并添加一个您自己 +的签准),或者回复一个Acked-by,让原始发送者向上发送它。 + +如果您不同意补丁,请发送一个礼貌的回复,解释原因。如果可能的话,告诉作者需要 +做哪些更改才能让您接受补丁。对于代码的编写者和维护者所反对的合并补丁,存在着 +一定的阻力,但仅此而已。如果你被认为不必要的阻碍了好的工作,那么这些补丁最 +终会经过你身边并进入主线。在Linux内核中,没有人对任何代码拥有绝对的否决权。 +除了Linus。 + +在非常罕见的情况下,您可能会看到完全不同的东西:另一个开发人员发布了针对您 +的问题的不同解决方案。在这一点上,两个补丁中的一个可能不会合并,“我的在这里 +是第一个”不被认为是一个令人信服的技术论据。如果有人的补丁取代了你的补丁而进 +入了主线,那么只有一种方法可以回应你:高兴你的问题得到解决,继续你的工作。 +以这种方式把一个人的工作推到一边可能会伤害和气馁,但是在他们忘记了谁的补丁 +真正被合并很久之后,社区会记住你的反应。 -- cgit v1.2.3 From 13ea8294480bd8c837b43d67110eac19146da735 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:22 +0800 Subject: docs/zh_CN: add disclaimer and translator info in 6.Followthrough To let people know where to complain. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/6.Followthrough.rst | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/6.Followthrough.rst b/Documentation/translations/zh_CN/process/6.Followthrough.rst index 28c81b80d3af..f509e077e1cb 100644 --- a/Documentation/translations/zh_CN/process/6.Followthrough.rst +++ b/Documentation/translations/zh_CN/process/6.Followthrough.rst @@ -1,3 +1,8 @@ +.. include:: ../disclaimer-zh_CN.rst + +:Original: :ref:`Documentation/process/6.Followthrough.rst ` +:Translator: Alex Shi + .. _cn_development_followthrough: 跟进 -- cgit v1.2.3 From 455d59d30196b7e778b128019f43a1972585ecb7 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:23 +0800 Subject: docs/zh_CN: translate 7.AdvanceTopics.rst This is the 7th doc of development-process. Now we could get Chinese version in 'make htmldocs'. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- .../zh_CN/process/7.AdvancedTopics.rst | 119 +++++++++++++++++++++ 1 file changed, 119 insertions(+) create mode 100644 Documentation/translations/zh_CN/process/7.AdvancedTopics.rst (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/7.AdvancedTopics.rst b/Documentation/translations/zh_CN/process/7.AdvancedTopics.rst new file mode 100644 index 000000000000..46cfe267882c --- /dev/null +++ b/Documentation/translations/zh_CN/process/7.AdvancedTopics.rst @@ -0,0 +1,119 @@ +.. _cn_development_advancedtopics: + +高级主题 +======== + +现在,希望您能够掌握开发流程的工作方式。然而,还有更多的东西要学!本节将介绍 +一些主题,这些主题对希望成为Linux内核开发过程常规部分的开发人员有帮助。 + +使用Git管理补丁 +--------------- + +内核使用分布式版本控制始于2002年初,当时Linus首次开始使用专有的Bitkeeper应用 +程序。虽然bitkeeper存在争议,但它所体现的软件版本管理方法却肯定不是。分布式 +版本控制可以立即加速内核开发项目。在当前的时代,有几种免费的比特保持器替代品。 +无论好坏,内核项目都将Git作为其选择的工具。 + +使用Git管理补丁可以使开发人员的生活更加轻松,尤其是随着补丁数量的增加。Git +也有其粗糙的边缘和一定的危险,它是一个年轻和强大的工具,仍然在其开发人员完善 +中。本文档不会试图教会读者如何使用git;这会是个巨长的文档。相反,这里的重点 +将是Git如何特别适合内核开发过程。想要加快Git的开发人员可以在以下网站上找到 +更多信息: + + http://git-scm.com/ + + http://www.kernel.org/pub/software/scm/git/docs/user-manual.html + +在尝试使用它使补丁可供其他人使用之前,第一要务是阅读上述站点,对Git的工作 +方式有一个扎实的了解。使用Git的开发人员应该能够获得主线存储库的副本,探索 +修订历史,提交对树的更改,使用分支等。了解Git用于重写历史的工具(如Rebase) +也很有用。Git有自己的术语和概念;Git的新用户应该了解refs、远程分支、索引、 +快进合并、推拉、分离头等。一开始可能有点吓人,但这些概念不难通过一点学习来 +理解。 + +使用git生成通过电子邮件提交的补丁是提高速度的一个很好的练习。 + +当您准备好开始安装Git树供其他人查看时,您当然需要一个可以从中提取的服务器。 +如果您有一个可以访问Internet的系统,那么使用git守护进程设置这样的服务器相 +对简单。否则,免费的公共托管网站(例如github)开始出现在网络上。成熟的开发 +人员可以在kernel.org上获得一个帐户,但这些帐户并不容易找到;有关更多信息, +请参阅 http://kernel.org/faq/ + +正常的Git工作流程涉及到许多分支的使用。每一条开发线都可以分为单独的“主题 +分支”,并独立维护。Git的分支机构很便宜,没有理由不免费使用它们。而且,在 +任何情况下,您都不应该在任何您打算让其他人从中受益的分支中进行开发。应该 +小心地创建公开可用的分支;当它们处于完整的形式并准备好运行时(而不是之前), +合并开发分支的补丁。 + +Git提供了一些强大的工具,可以让您重写开发历史。一个不方便的补丁(比如说, +一个打破二分法的补丁,或者有其他一些明显的缺陷)可以在适当的位置修复,或者 +完全从历史中消失。一个补丁系列可以被重写,就好像它是在今天的主线之上写的 +一样,即使你已经花了几个月的时间在写它。可以透明地将更改从一个分支转移到另 +一个分支。等等。明智地使用git修改历史的能力可以帮助创建问题更少的干净补丁集。 + +然而,过度使用这种能力可能会导致其他问题,而不仅仅是对创建完美项目历史的 +简单痴迷。重写历史将重写该历史中包含的更改,将经过测试(希望)的内核树变 +为未经测试的内核树。但是,除此之外,如果开发人员没有对项目历史的共享视图, +他们就无法轻松地协作;如果您重写了其他开发人员拉入他们存储库的历史,您将 +使这些开发人员的生活更加困难。因此,这里有一个简单的经验法则:被导出到其他 +人的历史在此后通常被认为是不可变的。 + +因此,一旦将一组更改推送到公开可用的服务器上,就不应该重写这些更改。如果您 +尝试强制进行不会导致快进合并(即不共享同一历史记录的更改)的更改,Git将尝 +试强制执行此规则。可以重写此检查,有时可能需要重写导出的树。在树之间移动变 +更集以避免Linux-next中的冲突就是一个例子。但这种行为应该是罕见的。这就是为 +什么开发应该在私有分支中进行(必要时可以重写)并且只有在公共分支处于合理的 +高级状态时才转移到公共分支中的原因之一。 + +当主线(或其他一组变更所基于的树)前进时,很容易与该树合并以保持领先地位。 +对于一个私有的分支,rebasing 可能是一个很容易跟上另一棵树的方法,但是一旦 +一棵树被导出到全世界,rebasing就不是一个选项。一旦发生这种情况,就必须进行 +完全合并(merge)。合并有时是很有意义的,但是过于频繁的合并会不必要地扰乱 +历史。在这种情况下,建议的技术是不经常合并,通常只在特定的发布点(如主线-rc +发布)合并。如果您对特定的更改感到紧张,则可以始终在私有分支中执行测试合并。 +在这种情况下,git rerere 工具很有用;它记住合并冲突是如何解决的,这样您就 +不必重复相同的工作。 + +关于Git这样的工具的一个最大的反复抱怨是:补丁从一个存储库到另一个存储库的 +大量移动使得很容易陷入错误建议的变更中,这些变更避开审查雷达进入主线。当内 +核开发人员看到这种情况发生时,他们往往会感到不高兴;在Git树上放置未查看或 +主题外的补丁可能会影响您将来获取树的能力。引用Linus: + +:: + + 你可以给我发补丁,但要我从你哪里取一个Git补丁,我需要知道你知道 + 你在做什么,我需要能够相信事情而不去检查每个个人改变。 + +(http://lwn.net/articles/224135/)。 + +为了避免这种情况,请确保给定分支中的所有补丁都与相关主题紧密相关;“驱动程序 +修复”分支不应更改核心内存管理代码。而且,最重要的是,不要使用Git树来绕过 +审查过程。不时的将树的摘要发布到相关的列表中,当时间合适时,请求 +Linux-next 中包含该树。 + +如果其他人开始发送补丁以包含到您的树中,不要忘记查看它们。还要确保您维护正确 +的作者信息; ``git am`` 工具在这方面做得最好,但是如果它通过第三方转发给您, +您可能需要在补丁中添加“From:”行。 + +请求pull操作时,请务必提供所有相关信息:树的位置、要拉的分支以及拉操作将导致 +的更改。在这方面,git request pull 命令非常有用;它将按照其他开发人员的预期 +格式化请求,并检查以确保您记住了将这些更改推送到公共服务器。 + +审查补丁 +-------- + +一些读者当然会反对将本节与“高级主题”放在一起,因为即使是刚开始的内核开发人员 +也应该检查补丁。当然,学习如何在内核环境中编程没有比查看其他人发布的代码更好 +的方法了。此外,审阅者永远供不应求;通过查看代码,您可以对整个流程做出重大贡献。 + +审查代码可能是一个令人生畏的前景,特别是对于一个新的内核开发人员来说,他们 +可能会对公开询问代码感到紧张,而这些代码是由那些有更多经验的人发布的。不过, +即使是最有经验的开发人员编写的代码也可以得到改进。也许对评审员(所有评审员) +最好的建议是:把评审评论当成问题而不是批评。询问“在这条路径中如何释放锁?” +总是比说“这里的锁是错误的”更好。 + +不同的开发人员将从不同的角度审查代码。一些主要关注的是编码样式以及代码行是 +否有尾随空格。其他人将主要关注补丁作为一个整体实现的变更是否对内核有好处。 +然而,其他人会检查是否存在锁定问题、堆栈使用过度、可能的安全问题、在其他 +地方发现的代码重复、足够的文档、对性能的不利影响、用户空间ABI更改等。所有 +类型的检查,如果它们导致更好的代码进入内核,都是受欢迎和值得的。 -- cgit v1.2.3 From ca30230dd44a5ba99f0dadd7271f15ea9ffb5429 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:24 +0800 Subject: docs/zh_CN: add disclaimer and translator info in 7.Advancedtopics To let people know where to give comments. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/7.AdvancedTopics.rst | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/7.AdvancedTopics.rst b/Documentation/translations/zh_CN/process/7.AdvancedTopics.rst index 46cfe267882c..956815edbd18 100644 --- a/Documentation/translations/zh_CN/process/7.AdvancedTopics.rst +++ b/Documentation/translations/zh_CN/process/7.AdvancedTopics.rst @@ -1,3 +1,8 @@ +.. include:: ../disclaimer-zh_CN.rst + +:Original: :ref:`Documentation/process/7.AdvancedTopics.rst ` +:Translator: Alex Shi + .. _cn_development_advancedtopics: 高级主题 -- cgit v1.2.3 From b68a32258f3aa8ddfd36f38a52641bf89439fbe6 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:25 +0800 Subject: docs/zh_CN: add 8.Conclusion.rst in development-process Now, the full developmen-process doc appears in 'make htmldocs' in Chinese. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- .../translations/zh_CN/process/8.Conclusion.rst | 58 ++++++++++++++++++++++ 1 file changed, 58 insertions(+) create mode 100644 Documentation/translations/zh_CN/process/8.Conclusion.rst (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/8.Conclusion.rst b/Documentation/translations/zh_CN/process/8.Conclusion.rst new file mode 100644 index 000000000000..9f8791c5784f --- /dev/null +++ b/Documentation/translations/zh_CN/process/8.Conclusion.rst @@ -0,0 +1,58 @@ +.. _cn_development_conclusion: + +更多信息 +======== + +关于Linux内核开发和相关主题的信息来源很多。首先是在内核源代码分发中找到的 +文档目录。顶级:ref:`process/howto.rst ` 文件是一个重要的起点 +:ref:`process/submitting-patches.rst ` 和 +:ref:`process/submitting-drivers.rst ` 也是所有内核开发 +人员都应该阅读的内容。许多内部内核API都是使用kerneldoc机制记录的; +“make htmldocs”或“make pdfdocs”可用于以HTML或PDF格式生成这些文档(尽管某些 +发行版提供的tex版本会遇到内部限制,无法正确处理文档)。 + +不同的网站在各个细节层次上讨论内核开发。您的作者想谦虚地建议用http://lwn.net/ +作为来源;有关许多特定内核主题的信息可以通过以下网址的lwn内核索引找到: + + http://lwn.net/kernel/index/ + +除此之外,内核开发人员的一个宝贵资源是: + + http://kernelnewbies.org/ + +当然,我们不应该忘记 http://kernel.org/ 这是内核发布信息的最终位置。 + +关于内核开发有很多书: + + Linux设备驱动程序,第三版(Jonathan Corbet、Alessandro Rubini和Greg Kroah Hartman)。 + 在线:http://lwn.net/kernel/ldd3/ + + Linux内核开发(Robert Love)。 + + 了解Linux内核(Daniel Bovet和Marco Cesati)。 + +然而,所有这些书都有一个共同的缺点:当它们上架时,它们往往有些过时,而且它们 +已经上架一段时间了。不过,在那里还可以找到相当多的好信息。 + +有关git的文档,请访问: + + http://www.kernel.org/pub/software/scm/git/docs/ + + http://www.kernel.org/pub/software/scm/git/docs/user-manual.html + +结论 +==== + +祝贺所有通过这篇冗长的文件的人。希望它能够帮助您理解Linux内核是如何开发的, +以及您如何参与这个过程。 + +最后,重要的是参与。任何开源软件项目都不超过其贡献者投入其中的总和。Linux内核 +的发展速度和以前一样快,因为它得到了大量开发人员的帮助,他们都在努力使它变得 +更好。内核是一个主要的例子,说明当成千上万的人为了一个共同的目标一起工作时, +可以做些什么。 + +不过,内核总是可以从更大的开发人员基础中获益。总有更多的工作要做。但是,同样 +重要的是,Linux生态系统中的大多数其他参与者可以通过为内核做出贡献而受益。使 +代码进入主线是提高代码质量、降低维护和分发成本、提高对内核开发方向的影响程度 +等的关键。这是一种人人都赢的局面。踢开你的编辑,来加入我们吧,你会非常受 +欢迎的。 -- cgit v1.2.3 From cc5844ee781a2e93f3ec6d459bbee4017417cd55 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:26 +0800 Subject: docs/zh_CN: add disclaimer and translator info in 8.Conclusion Give people a link to send comments. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/8.Conclusion.rst | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/8.Conclusion.rst b/Documentation/translations/zh_CN/process/8.Conclusion.rst index 9f8791c5784f..32b4e617a451 100644 --- a/Documentation/translations/zh_CN/process/8.Conclusion.rst +++ b/Documentation/translations/zh_CN/process/8.Conclusion.rst @@ -1,3 +1,8 @@ +.. include:: ../disclaimer-zh_CN.rst + +:Original: :ref:`Documentation/process/8.Conclusion.rst ` +:Translator: Alex Shi + .. _cn_development_conclusion: 更多信息 -- cgit v1.2.3 From 173584cbdc289a13918071737589787d039df5fd Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:27 +0800 Subject: docs/zh_CN: add license-rules Chinese translation This is the first version of license-rules Chinese translation Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- .../translations/zh_CN/process/license-rules.rst | 365 +++++++++++++++++++++ 1 file changed, 365 insertions(+) create mode 100644 Documentation/translations/zh_CN/process/license-rules.rst (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/license-rules.rst b/Documentation/translations/zh_CN/process/license-rules.rst new file mode 100644 index 000000000000..f70c8a238c3d --- /dev/null +++ b/Documentation/translations/zh_CN/process/license-rules.rst @@ -0,0 +1,365 @@ +.. SPDX-License-Identifier: GPL-2.0 + +.. _kernel_licensing: + +Linux内核许可规则 +================= + +Linux内核根据LICENSES/preferred/GPL-2.0中提供的GNU通用公共许可证版本2 +(GPL-2.0)的条款提供,并在LICENSES/exceptions/Linux-syscall-note中显式 +描述了例外的系统调用,如COPYING文件中所述。 + +此文档文件提供了如何对每个源文件进行注释以使其许可证清晰明确的说明。 +它不会取代内核的许可证。 + +内核源代码作为一个整体适用于COPYING文件中描述的许可证,但是单个源文件可以 +具有不同的与GPL-20兼容的许可证:: + + GPL-1.0+ : GNU通用公共许可证v1.0或更高版本 + GPL-2.0+ : GNU通用公共许可证v2.0或更高版本 + LGPL-2.0 : 仅限GNU库通用公共许可证v2 + LGPL-2.0+: GNU 库通用公共许可证v2或更高版本 + LGPL-2.1 : 仅限GNU宽通用公共许可证v2.1 + LGPL-2.1+: GNU宽通用公共许可证v2.1或更高版本 + +除此之外,个人文件可以在双重许可下提供,例如一个兼容的GPL变体,或者BSD, +MIT等许可。 + +用户空间API(UAPI)头文件描述了用户空间程序与内核的接口,这是一种特殊情况。 +根据内核COPYING文件中的注释,syscall接口是一个明确的边界,它不会将GPL要求 +扩展到任何使用它与内核通信的软件。由于UAPI头文件必须包含在创建在Linux内核 +上运行的可执行文件的任何源文件中,因此此例外必须记录在特别的许可证表述中。 + +表达源文件许可证的常用方法是将匹配的样板文本添加到文件的顶部注释中。由于 +格式,拼写错误等,这些“样板”很难通过那些在上下文中使用的验证许可证合规性 +的工具。 + +样板文本的替代方法是在每个源文件中使用软件包数据交换(SPDX)许可证标识符。 +SPDX许可证标识符是机器可解析的,并且是用于提供文件内容的许可证的精确缩写。 +SPDX许可证标识符由Linux 基金会的SPDX 工作组管理,并得到了整个行业,工具 +供应商和法律团队的合作伙伴的一致同意。有关详细信息,请参阅 +https://spdx.org/ + +Linux内核需要所有源文件中的精确SPDX标识符。内核中使用的有效标识符在 +`许可标识符`_ 一节中进行了解释,并且已可以在 +https://spdx.org/licenses/ 上的官方SPDX许可证列表中检索,并附带许可证 +文本。 + +许可标识符语法 +-------------- + +1.安置: + +   内核文件中的SPDX许可证标识符应添加到可包含注释的文件中的第一行。对于大多 + 数文件,这是第一行,除了那些在第一行中需要'#!PATH_TO_INTERPRETER'的脚本。 + 对于这些脚本,SPDX标识符进入第二行。 + +| + +2. 风格: + + SPDX许可证标识符以注释的形式添加。注释样式取决于文件类型:: + + C source: // SPDX-License-Identifier: + C header: /* SPDX-License-Identifier: */ + ASM: /* SPDX-License-Identifier: */ + scripts: # SPDX-License-Identifier: + .rst: .. SPDX-License-Identifier: + .dts{i}: // SPDX-License-Identifier: + + 如果特定工具无法处理标准注释样式,则应使用工具接受的相应注释机制。这是在 + C 头文件中使用“/\*\*/”样式注释的原因。过去在使用生成的.lds文件中观察到 + 构建被破坏,其中'ld'无法解析C++注释。现在已经解决了这个问题,但仍然有较 + 旧的汇编程序工具无法处理C++样式的注释。 + +| + +3. 句法: + + 是SPDX许可证列表中的SPDX短格式许可证标识符,或者在许可 + 证例外适用时由“WITH”分隔的两个SPDX短格式许可证标识符的组合。当应用多个许 + 可证时,表达式由分隔子表达式的关键字“AND”,“OR”组成,并由“(”,“)”包围。 + + 带有“或更高”选项的[L]GPL等许可证的许可证标识符通过使用“+”来表示“或更高” + 选项来构建。:: + + // SPDX-License-Identifier: GPL-2.0+ + // SPDX-License-Identifier: LGPL-2.1+ + + 当需要修正的许可证时,应使用WITH。 例如,linux内核UAPI文件使用表达式:: + + // SPDX-License-Identifier: GPL-2.0 WITH Linux-syscall-note + // SPDX-License-Identifier: GPL-2.0+ WITH Linux-syscall-note + + 其它在内核中使用WITH例外的事例如下:: + + // SPDX-License-Identifier: GPL-2.0 WITH mif-exception + // SPDX-License-Identifier: GPL-2.0+ WITH GCC-exception-2.0 + + 例外只能与特定的许可证标识符一起使用。有效的许可证标识符列在异常文本文件 + 的标记中。有关详细信息,请参阅“许可证标识符”_一章中的“例外” + + 如果文件是双重许可且只选择一个许可证,则应使用OR。例如,一些dtsi文件在双 + 许可下可用:: + + // SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause + + 内核中双许可文件中许可表达式的示例:: + + // SPDX-License-Identifier: GPL-2.0 OR MIT + // SPDX-License-Identifier: GPL-2.0 OR BSD-2-Clause + // SPDX-License-Identifier: GPL-2.0 OR Apache-2.0 + // SPDX-License-Identifier: GPL-2.0 OR MPL-1.1 + // SPDX-License-Identifier: (GPL-2.0 WITH Linux-syscall-note) OR MIT + // SPDX-License-Identifier: GPL-1.0+ OR BSD-3-Clause OR OpenSSL + + 如果文件具有多个许可证,其条款全部适用于使用该文件,则应使用AND。例如, + 如果代码是从另一个项目继承的,并且已经授予了将其放入内核的权限,但原始 + 许可条款需要保持有效:: + + // SPDX-License-Identifier: (GPL-2.0 WITH Linux-syscall-note) AND MIT + + 另一个需要遵守两套许可条款的例子是:: + + // SPDX-License-Identifier: GPL-1.0+ AND LGPL-2.1+ + +许可标识符 +---------- + +当前使用的许可证以及添加到内核的代码许可证可以分解为: + +1. _`优先许可`: + + 应尽可能使用这些许可证,因为它们已知完全兼容并广泛使用。这些许可证在内核 + 目录:: + + LICENSES/preferred/ + + 此目录中的文件包含完整的许可证文本和`元标记`_。文件名与SPDX许可证标识 + 符相同,后者应用于源文件中的许可证。 + + 例如:: + + LICENSES/preferred/GPL-2.0 + + 包含GPLv2许可证文本和所需的元标签:: + + LICENSES/preferred/MIT + + 包含MIT许可证文本和所需的元标记 + + _`元标记`: + + 许可证文件中必须包含以下元标记: + + - Valid-License-Identifier: + +   一行或多行, 声明那些许可标识符在项目内有效, 以引用此特定许可的文本。通 + 常这是一个有效的标识符,但是例如对于带有'或更高'选项的许可证,两个标识 + 符都有效。 + + - SPDX-URL: + + SPDX页面的URL,其中包含与许可证相关的其他信息. + + - Usage-Guidance: + + 使用建议的自由格式文本。该文本必须包含SPDX许可证标识符的正确示例,因为 + 它们应根据`许可标识符语法`_ 指南放入源文件中。 + + - License-Text: + + 此标记之后的所有文本都被视为原始许可文本 + + 文件格式示例:: + + Valid-License-Identifier: GPL-2.0 + Valid-License-Identifier: GPL-2.0+ + SPDX-URL: https://spdx.org/licenses/GPL-2.0.html + Usage-Guide: + To use this license in source code, put one of the following SPDX + tag/value pairs into a comment according to the placement + guidelines in the licensing rules documentation. + For 'GNU General Public License (GPL) version 2 only' use: + SPDX-License-Identifier: GPL-2.0 + For 'GNU General Public License (GPL) version 2 or any later version' use: + SPDX-License-Identifier: GPL-2.0+ + License-Text: + Full license text + + :: + + SPDX-License-Identifier: MIT + SPDX-URL: https://spdx.org/licenses/MIT.html + Usage-Guide: + To use this license in source code, put the following SPDX + tag/value pair into a comment according to the placement + guidelines in the licensing rules documentation. + SPDX-License-Identifier: MIT + License-Text: + Full license text + +| + +2. 不推荐的许可证: + + 这些许可证只应用于现有代码或从其他项目导入代码。这些许可证在内核目录:: + + LICENSES/other/ + + 此目录中的文件包含完整的许可证文本和`元标记`_。文件名与SPDX许可证标识 + 符相同,后者应用于源文件中的许可证。 + + 例如:: + + LICENSES/other/ISC + + 包含国际系统联合许可文本和所需的元标签:: + + LICENSES/other/ZLib + + 包含ZLIB许可文本和所需的元标签. + + 元标签: + + “其他”许可证的元标签要求与`优先许可`_的要求相同。 + + 文件格式示例:: + + Valid-License-Identifier: ISC + SPDX-URL: https://spdx.org/licenses/ISC.html + Usage-Guide: + Usage of this license in the kernel for new code is discouraged + and it should solely be used for importing code from an already + existing project. + To use this license in source code, put the following SPDX + tag/value pair into a comment according to the placement + guidelines in the licensing rules documentation. + SPDX-License-Identifier: ISC + License-Text: + Full license text + +| + +3. _`例外`: + + 某些许可证可以修改,并允许原始许可证不具有的某些例外权利。这些例外在 + 内核目录:: + + LICENSES/exceptions/ + + 此目录中的文件包含完整的例外文本和所需的`例外元标记`_. + + 例如:: + + LICENSES/exceptions/Linux-syscall-note + + 包含Linux内核的COPYING文件中记录的Linux系统调用例外,该文件用于UAPI + 头文件。例如:: + + LICENSES/exceptions/GCC-exception-2.0 + + 包含GCC'链接例外',它允许独立于其许可证的任何二进制文件与标记有此例外的 + 文件的编译版本链接。这是从GPL不兼容源代码创建可运行的可执行文件所必需的。 + + _`例外元标记`: + + 以下元标记必须在例外文件中可用: + + - SPDX-Exception-Identifier: + +   一个可与SPDX许可证标识符一起使用的例外标识符。 + + - SPDX-URL: + + SPDX页面的URL,其中包含与例外相关的其他信息。 + + - SPDX-Licenses: + +   以逗号分隔的例外可用的SPDX许可证标识符列表。 + + - Usage-Guidance: + + 使用建议的自由格式文本。必须在文本后面加上SPDX许可证标识符的正确示例, + 因为它们应根据`License identifier syntax`_指南放入源文件中。 + + - Exception-Text: + + 此标记之后的所有文本都被视为原始异常文本 + + 文件格式示例:: + + SPDX-Exception-Identifier: Linux-syscall-note + SPDX-URL: https://spdx.org/licenses/Linux-syscall-note.html + SPDX-Licenses: GPL-2.0, GPL-2.0+, GPL-1.0+, LGPL-2.0, LGPL-2.0+, LGPL-2.1, LGPL-2.1+ + Usage-Guidance: + This exception is used together with one of the above SPDX-Licenses + to mark user-space API (uapi) header files so they can be included + into non GPL compliant user-space application code. + To use this exception add it with the keyword WITH to one of the + identifiers in the SPDX-Licenses tag: + SPDX-License-Identifier: WITH Linux-syscall-note + Exception-Text: + Full exception text + + :: + + SPDX-Exception-Identifier: GCC-exception-2.0 + SPDX-URL: https://spdx.org/licenses/GCC-exception-2.0.html + SPDX-Licenses: GPL-2.0, GPL-2.0+ + Usage-Guidance: + The "GCC Runtime Library exception 2.0" is used together with one + of the above SPDX-Licenses for code imported from the GCC runtime + library. + To use this exception add it with the keyword WITH to one of the + identifiers in the SPDX-Licenses tag: + SPDX-License-Identifier: WITH GCC-exception-2.0 + Exception-Text: + Full exception text + + +所有SPDX许可证标识符和例外都必须在LICENSES子目录中具有相应的文件。这是允许 +工具验证(例如checkpatch.pl)以及准备好从源读取和提取许可证所必需的, 这是 +各种FOSS组织推荐的,例如 `FSFE REUSE initiative `_. + +_`模块许可` +----------------- + + 可加载内核模块还需要MODULE_LICENSE()标记。此标记既不替代正确的源代码 + 许可证信息(SPDX-License-Identifier),也不以任何方式表示或确定提供模块 + 源代码的确切许可证。 + + 此标记的唯一目的是提供足够的信息,该模块是否是自由软件或者是内核模块加 + 载器和用户空间工具的专有模块。 + + MODULE_LICENSE()的有效许可证字符串是: + + ============================= ============================================= + "GPL" 模块是根据GPL版本2许可的。这并不表示仅限于 + GPL-2.0或GPL-2.0或更高版本之间的任何区别。 + 最正确许可证信息只能通过相应源文件中的许可证 + 信息来确定 + + "GPL v2" 和"GPL"相同,它的存在是因为历史原因。 + + "GPL and additional rights" 表示模块源在GPL v2变体和MIT许可下双重许可的 + 历史变体。请不要在新代码中使用。 + + "Dual MIT/GPL" 表达该模块在GPL v2变体或MIT许可证选择下双重 + 许可的正确方式。 + + "Dual BSD/GPL" 该模块根据GPL v2变体或BSD许可证选择进行双重 + 许可。 BSD许可证的确切变体只能通过相应源文件 + 中的许可证信息来确定。 + + "Dual MPL/GPL" 该模块根据GPL v2变体或Mozilla Public License + (MPL)选项进行双重许可。 MPL许可证的确切变体 + 只能通过相应的源文件中的许可证信息来确定。 + + "Proprietary" 该模块属于专有许可。此字符串仅用于专有的第三 + 方模块,不能用于在内核树中具有源代码的模块。 + 以这种方式标记的模块在加载时会使用'P'标记污 + 染内核,并且内核模块加载器拒绝将这些模块链接 + 到使用EXPORT_SYMBOL_GPL()导出的符号。 + ============================= ============================================= + -- cgit v1.2.3 From 7c0a4a0a59a67c8f5711c48a25e5cc74a2823b45 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:28 +0800 Subject: docs/zh_CN: fix links failure in license-rules rST doc uses backquote `` to mark a link, which need a space before and after the backquote sign in Chinese docs. Otherwise the link will be translated as common context. Use this patch to highlight this request. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/license-rules.rst | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/license-rules.rst b/Documentation/translations/zh_CN/process/license-rules.rst index f70c8a238c3d..17ccba78962d 100644 --- a/Documentation/translations/zh_CN/process/license-rules.rst +++ b/Documentation/translations/zh_CN/process/license-rules.rst @@ -97,7 +97,7 @@ https://spdx.org/licenses/ 上的官方SPDX许可证列表中检索,并附带 // SPDX-License-Identifier: GPL-2.0+ WITH GCC-exception-2.0 例外只能与特定的许可证标识符一起使用。有效的许可证标识符列在异常文本文件 - 的标记中。有关详细信息,请参阅“许可证标识符”_一章中的“例外” + 的标记中。有关详细信息,请参阅 `许可标识符`_ 一章中的 `例外`_ 。 如果文件是双重许可且只选择一个许可证,则应使用OR。例如,一些dtsi文件在双 许可下可用:: @@ -135,7 +135,7 @@ https://spdx.org/licenses/ 上的官方SPDX许可证列表中检索,并附带 LICENSES/preferred/ - 此目录中的文件包含完整的许可证文本和`元标记`_。文件名与SPDX许可证标识 + 此目录中的文件包含完整的许可证文本和 `元标记`_ 。文件名与SPDX许可证标识 符相同,后者应用于源文件中的许可证。 例如:: @@ -165,7 +165,7 @@ https://spdx.org/licenses/ 上的官方SPDX许可证列表中检索,并附带 - Usage-Guidance: 使用建议的自由格式文本。该文本必须包含SPDX许可证标识符的正确示例,因为 - 它们应根据`许可标识符语法`_ 指南放入源文件中。 + 它们应根据 `许可标识符语法`_ 指南放入源文件中。 - License-Text: @@ -207,7 +207,7 @@ https://spdx.org/licenses/ 上的官方SPDX许可证列表中检索,并附带 LICENSES/other/ - 此目录中的文件包含完整的许可证文本和`元标记`_。文件名与SPDX许可证标识 + 此目录中的文件包含完整的许可证文本和 `元标记`_ 。文件名与SPDX许可证标识 符相同,后者应用于源文件中的许可证。 例如:: @@ -222,7 +222,7 @@ https://spdx.org/licenses/ 上的官方SPDX许可证列表中检索,并附带 元标签: - “其他”许可证的元标签要求与`优先许可`_的要求相同。 + “其他”许可证的元标签要求与 `优先许可`_ 的要求相同。 文件格式示例:: @@ -248,7 +248,7 @@ https://spdx.org/licenses/ 上的官方SPDX许可证列表中检索,并附带 LICENSES/exceptions/ - 此目录中的文件包含完整的例外文本和所需的`例外元标记`_. + 此目录中的文件包含完整的例外文本和所需的 `例外元标记`_ 。 例如:: @@ -281,7 +281,7 @@ https://spdx.org/licenses/ 上的官方SPDX许可证列表中检索,并附带 - Usage-Guidance: 使用建议的自由格式文本。必须在文本后面加上SPDX许可证标识符的正确示例, - 因为它们应根据`License identifier syntax`_指南放入源文件中。 + 因为它们应根据 `许可标识符语法`_ 指南放入源文件中。 - Exception-Text: -- cgit v1.2.3 From d355a5a4c69a006e17026d10751d3010dd30c798 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:29 +0800 Subject: docs/zh_CN: include Chinese translation header for license-rules Enable the Chinese translation disclaimer and translator info. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/license-rules.rst | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/license-rules.rst b/Documentation/translations/zh_CN/process/license-rules.rst index 17ccba78962d..30c272b2a292 100644 --- a/Documentation/translations/zh_CN/process/license-rules.rst +++ b/Documentation/translations/zh_CN/process/license-rules.rst @@ -1,6 +1,11 @@ .. SPDX-License-Identifier: GPL-2.0 -.. _kernel_licensing: +.. include:: ../disclaimer-zh_CN.rst + +:Original: :ref:`Documentation/process/license-rules.rst ` +:Translator: Alex Shi + +.. _cn_kernel_licensing: Linux内核许可规则 ================= -- cgit v1.2.3 From 2ca130147131f0c02c5e6e44eadb09f3d8f9f4b0 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:30 +0800 Subject: docs/zh_CN: link the license-rules file into process index Make it appear in 'make htmldocs' Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/index.rst | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/index.rst b/Documentation/translations/zh_CN/process/index.rst index 3942c3bb6548..70c0e9b61a53 100644 --- a/Documentation/translations/zh_CN/process/index.rst +++ b/Documentation/translations/zh_CN/process/index.rst @@ -27,6 +27,7 @@ coding-style development-process email-clients + license-rules 其它大多数开发人员感兴趣的社区指南: -- cgit v1.2.3 From 3cabb71cdc61e0502be5e8543b8d111ad519a7e6 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:31 +0800 Subject: docs/zh_CN: add submit-checklist file Now it appears in 'make htmldocs' in Chinese version. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- .../zh_CN/process/submit-checklist.rst | 102 +++++++++++++++++++++ 1 file changed, 102 insertions(+) create mode 100644 Documentation/translations/zh_CN/process/submit-checklist.rst (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/submit-checklist.rst b/Documentation/translations/zh_CN/process/submit-checklist.rst new file mode 100644 index 000000000000..012f2bf88a35 --- /dev/null +++ b/Documentation/translations/zh_CN/process/submit-checklist.rst @@ -0,0 +1,102 @@ +.. _cn_submitchecklist: + +Linux内核补丁提交清单 +~~~~~~~~~~~~~~~~~~~~~ + +如果开发人员希望看到他们的内核补丁提交更快地被接受,那么他们应该做一些基本 +的事情。 + +这些都是在 +:ref:`Documentation/process/submitting-patches.rst ` +和其他有关提交Linux内核补丁的文档中提供的。 + +1) 如果使用工具,则包括定义/声明该工具的文件。不要依赖于其他头文件拉入您使用 + 的头文件。 + +2) 干净的编译: + + a) 使用适用或修改的 ``CONFIG`` 选项 ``=y``、``=m`` 和 ``=n`` 。没有GCC + 警告/错误,没有链接器警告/错误。 + + b) 通过allnoconfig、allmodconfig + + c) 使用 ``O=builddir`` 时可以成功编译 + +3) 通过使用本地交叉编译工具或其他一些构建场在多个CPU体系结构上构建。 + +4) PPC64是一种很好的交叉编译检查体系结构,因为它倾向于对64位的数使用无符号 + 长整型。 + +5) 如下所述 :ref:`Documentation/process/coding-style.rst `. + 检查您的补丁是否为常规样式。在提交( ``scripts/check patch.pl`` )之前, + 使用补丁样式检查器检查是否有轻微的冲突。您应该能够处理您的补丁中存在的所有 + 违规行为。 + +6) 任何新的或修改过的 ``CONFIG`` 选项都不会弄脏配置菜单,并默认为关闭,除非 + 它们符合 ``Documentation/kbuild/kconfig-language.txt`` 中记录的异常条件, + 菜单属性:默认值. + +7) 所有新的 ``kconfig`` 选项都有帮助文本。 + +8) 已仔细审查了相关的 ``Kconfig`` 组合。这很难用测试来纠正——脑力在这里是有 + 回报的。 + +9) 用 sparse 检查干净。 + +10) 使用 ``make checkstack`` 和 ``make namespacecheck`` 并修复他们发现的任何 + 问题。 + + .. note:: + + ``checkstack`` 并没有明确指出问题,但是任何一个在堆栈上使用超过512 + 字节的函数都可以进行更改。 + +11) 包括 :ref:`kernel-doc ` 内核文档以记录全局内核API。(静态函数 + 不需要,但也可以。)使用 ``make htmldocs`` 或 ``make pdfdocs`` 检查 + :ref:`kernel-doc ` 并修复任何问题。 + +12) 通过以下选项同时启用的测试 ``CONFIG_PREEMPT``, ``CONFIG_DEBUG_PREEMPT``, + ``CONFIG_DEBUG_SLAB``, ``CONFIG_DEBUG_PAGEALLOC``, ``CONFIG_DEBUG_MUTEXES``, + ``CONFIG_DEBUG_SPINLOCK``, ``CONFIG_DEBUG_ATOMIC_SLEEP``, + ``CONFIG_PROVE_RCU`` and ``CONFIG_DEBUG_OBJECTS_RCU_HEAD`` + +13) 已经过构建和运行时测试,包括有或没有 ``CONFIG_SMP``, ``CONFIG_PREEMPT``. + +14) 如果补丁程序影响IO/磁盘等:使用或不使用 ``CONFIG_LBDAF`` 进行测试。 + +15) 所有代码路径都已在启用所有lockdep功能的情况下运行。 + +16) 所有新的/proc条目都记录在 ``Documentation/`` + +17) 所有新的内核引导参数都记录在 + Documentation/admin-guide/kernel-parameters.rst 中。 + +18) 所有新的模块参数都记录在 ``MODULE_PARM_DESC()`` + +19) 所有新的用户空间接口都记录在 ``Documentation/ABI/`` 中。有关详细信息, + 请参阅 ``Documentation/ABI/README`` 。更改用户空间接口的补丁应该抄送 + linux-api@vger.kernel.org。 + +20) 检查是否全部通过 ``make headers_check`` 。 + +21) 已通过至少注入slab和page分配失败进行检查。请参阅 ``Documentation/fault-injection/`` + 如果新代码是实质性的,那么添加子系统特定的故障注入可能是合适的。 + +22) 新添加的代码已经用 ``gcc -W`` 编译(使用 ``make EXTRA-CFLAGS=-W`` )。这 + 将产生大量噪声,但对于查找诸如“警告:有符号和无符号之间的比较”之类的错误 + 很有用。 + +23) 在它被合并到-mm补丁集中之后进行测试,以确保它仍然与所有其他排队的补丁以 + 及VM、VFS和其他子系统中的各种更改一起工作。 + +24) 所有内存屏障例如 ``barrier()``, ``rmb()``, ``wmb()`` 都需要源代码中的注 + 释来解释它们正在执行的操作及其原因的逻辑。 + +25) 如果补丁添加了任何ioctl,那么也要更新 ``Documentation/ioctl/ioctl-number.txt`` + +26) 如果修改后的源代码依赖或使用与以下 ``Kconfig`` 符号相关的任何内核API或 + 功能,则在禁用相关 ``Kconfig`` 符号和/或 ``=m`` (如果该选项可用)的情况 + 下测试以下多个构建[并非所有这些都同时存在,只是它们的各种/随机组合]: + + ``CONFIG_SMP``, ``CONFIG_SYSFS``, ``CONFIG_PROC_FS``, ``CONFIG_INPUT``, ``CONFIG_PCI``, ``CONFIG_BLOCK``, ``CONFIG_PM``, ``CONFIG_MAGIC_SYSRQ``, + ``CONFIG_NET``, ``CONFIG_INET=n`` (但是后者伴随 ``CONFIG_NET=y``). -- cgit v1.2.3 From e1d0ceca8c093cf2e8fa7b226222246732d28a26 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:32 +0800 Subject: docs/zh_CN: add disclaimer and transtlator info in submit-checklist Credit the translator and get a way for people to complain. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/submit-checklist.rst | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/submit-checklist.rst b/Documentation/translations/zh_CN/process/submit-checklist.rst index 012f2bf88a35..9ee1cb4cdab6 100644 --- a/Documentation/translations/zh_CN/process/submit-checklist.rst +++ b/Documentation/translations/zh_CN/process/submit-checklist.rst @@ -1,3 +1,8 @@ +.. include:: ../disclaimer-zh_CN.rst + +:Original: :ref:`Documentation/process/submit-checklist.rst ` +:Translator: Alex Shi + .. _cn_submitchecklist: Linux内核补丁提交清单 -- cgit v1.2.3 From 1ea0d2a3c812864537eb53a52c78d9b398ae1327 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:33 +0800 Subject: docs/zh_CN: link the submit-checklist into process/index That's helpful to let people find it in process/index.html. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/index.rst | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/index.rst b/Documentation/translations/zh_CN/process/index.rst index 70c0e9b61a53..19cc3fae8256 100644 --- a/Documentation/translations/zh_CN/process/index.rst +++ b/Documentation/translations/zh_CN/process/index.rst @@ -36,6 +36,7 @@ :maxdepth: 1 submitting-drivers + submit-checklist stable-api-nonsense stable-kernel-rules -- cgit v1.2.3 From 27a0f904348a8ab89510858f6b21b65df465ee3f Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:34 +0800 Subject: docs/zh_CN: add CoC doc Translated code-of-conduct doc in Chinese. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- .../translations/zh_CN/process/code-of-conduct.rst | 67 ++++++++++++++++++++++ 1 file changed, 67 insertions(+) create mode 100644 Documentation/translations/zh_CN/process/code-of-conduct.rst (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/code-of-conduct.rst b/Documentation/translations/zh_CN/process/code-of-conduct.rst new file mode 100644 index 000000000000..bfa03a3a3720 --- /dev/null +++ b/Documentation/translations/zh_CN/process/code-of-conduct.rst @@ -0,0 +1,67 @@ +.. _cn_code_of_conduct: + +贡献者契约行为准则 +++++++++++++++++++ + +我们的誓言 +========== + +为了营造一个开放、友好的环境,我们作为贡献者和维护人承诺,让我们的社区和参 +与者,拥有一个无骚扰的体验,无论年龄、体型、残疾、种族、性别特征、性别认同 +和表达、经验水平、教育程度、社会状况,经济地位、国籍、个人外貌、种族、宗教 +或性身份和取向。 + +我们的标准 +========== + +有助于创造积极环境的行为包括: + +* 使用欢迎和包容的语言 +* 尊重不同的观点和经验 +* 优雅地接受建设性的批评 +* 关注什么对社区最有利 +* 对其他社区成员表示同情 + +参与者的不可接受行为包括: + +* 使用性意味的语言或意象以及不受欢迎的性注意或者更过分的行为 +* 煽动、侮辱/贬损评论以及个人或政治攻击 +* 公开或私下骚扰 +* 未经明确许可,发布他人的私人信息,如物理或电子地址。 +* 在专业场合被合理认为不适当的其他行为 + +我们的责任 +========== + +维护人员负责澄清可接受行为的标准,并应针对任何不可接受行为采取适当和公平的 +纠正措施。 + +维护人员有权和责任删除、编辑或拒绝与本行为准则不一致的评论、承诺、代码、 +wiki编辑、问题和其他贡献,或暂时或永久禁止任何贡献者从事他们认为不适当、 +威胁、冒犯或有害的其他行为。 + +范围 +==== + +当个人代表项目或其社区时,本行为准则既适用于项目空间,也适用于公共空间。 +代表一个项目或社区的例子包括使用一个正式的项目电子邮件地址,通过一个正式 +的社交媒体帐户发布,或者在在线或离线事件中担任指定的代表。项目维护人员可以 +进一步定义和澄清项目的表示。 + +执行 +==== + +如有滥用、骚扰或其他不可接受的行为,可联系行为准则委员会。 +所有投诉都将接受审查和调查,并将得到必要和适当的答复。行为准则委员会有义务 +对事件报告人保密。具体执行政策的进一步细节可单独公布。 + +归属 +==== + +本行为准则改编自《贡献者契约》,版本1.4,可从 +https://www.contributor-covenant.org/version/1/4/code-of-conduct.html 获取。 + +解释 +==== + +有关Linux内核社区如何解释此文档,请参阅 :ref:`code_of_conduct_interpretation` -- cgit v1.2.3 From 7f2ac11bd4fe1b511ae1feb838cf64d82bb57302 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:35 +0800 Subject: docs/zh_CN: add disclaimer and translator info in CoC Give the translator credit and a way people to share complain. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/code-of-conduct.rst | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/code-of-conduct.rst b/Documentation/translations/zh_CN/process/code-of-conduct.rst index bfa03a3a3720..4054daafedf1 100644 --- a/Documentation/translations/zh_CN/process/code-of-conduct.rst +++ b/Documentation/translations/zh_CN/process/code-of-conduct.rst @@ -1,3 +1,8 @@ +.. include:: ../disclaimer-zh_CN.rst + +:Original: :ref:`Documentation/process/code-of-conduct.rst ` +:Translator: Alex Shi + .. _cn_code_of_conduct: 贡献者契约行为准则 -- cgit v1.2.3 From c670321486934e03867563e2019bddb411684c54 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:36 +0800 Subject: docs/zh_CN: link the CoC into process/index Let it appears in html links. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/index.rst | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/index.rst b/Documentation/translations/zh_CN/process/index.rst index 19cc3fae8256..ba9fd19b87d7 100644 --- a/Documentation/translations/zh_CN/process/index.rst +++ b/Documentation/translations/zh_CN/process/index.rst @@ -23,6 +23,7 @@ :maxdepth: 1 howto + code-of-conduct submitting-patches coding-style development-process -- cgit v1.2.3 From 60bef260f66390cc82c2426c984535ff2de4a488 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:37 +0800 Subject: docs/zh_CN: add CoC interpretation Translated CoC interpretation into Chinese Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- .../process/code-of-conduct-interpretation.rst | 103 +++++++++++++++++++++ 1 file changed, 103 insertions(+) create mode 100644 Documentation/translations/zh_CN/process/code-of-conduct-interpretation.rst (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/code-of-conduct-interpretation.rst b/Documentation/translations/zh_CN/process/code-of-conduct-interpretation.rst new file mode 100644 index 000000000000..39743a0ed0d3 --- /dev/null +++ b/Documentation/translations/zh_CN/process/code-of-conduct-interpretation.rst @@ -0,0 +1,103 @@ +.. _cn_code_of_conduct_interpretation: + +Linux内核贡献者契约行为准则解释 +=============================== + +:ref:`code_of_conduct` 准则是一个通用文档,旨在为几乎所有开源社区提供一套规则。 +每个开源社区都是独一无二的,Linux内核也不例外。因此,本文描述了Linux内核社区中 +如何解释它。我们也不希望这种解释随着时间的推移是静态的,并将根据需要进行调整。 + +与开发软件的“传统”方法相比,Linux内核开发工作是一个非常个人化的过程。你的贡献 +和背后的想法将被仔细审查,往往导致批判和批评。审查将几乎总是需要改进,材料才 +能包括在内核中。要知道这是因为所有相关人员都希望看到Linux整体成功的最佳解决方 +案。这个开发过程已经被证明可以创建有史以来最健壮的操作系统内核,我们不想做任何 +事情来导致提交质量和最终结果的下降。 + +维护者 +------ + +行为准则多次使用“维护者”一词。在内核社区中,“维护者”是负责子系统、驱动程序或 +文件的任何人,并在内核源代码树的维护者文件中列出。 + +责任 +---- + +《行为准则》提到了维护人员的权利和责任,这需要进一步澄清。 + +首先,最重要的是,有一个合理的期望是由维护人员通过实例来领导。 + +也就是说,我们的社区是广阔的,对维护者没有新的要求,他们单方面处理其他人在 +他们活跃的社区的行为。这一责任由我们所有人承担,最终《行为准则》记录了最终的 +上诉路径,以防有关行为问题的问题悬而未决。 + +维护人员应该愿意在出现问题时提供帮助,并在需要时与社区中的其他人合作。如果您 +不确定如何处理出现的情况,请不要害怕联系技术咨询委员会(TAB)或其他维护人员。 +除非您愿意,否则不会将其视为违规报告。如果您不确定是否该联系TAB 或任何其他维 +护人员,请联系我们的冲突调解人 Mishi Choudhary 。 + +最后,“善待对方”才是每个人的最终目标。我们知道每个人都是人,有时我们都会失败, +但我们所有人的首要目标应该是努力友好地解决问题。执行行为准则将是最后的选择。 + +我们的目标是创建一个强大的、技术先进的操作系统,以及所涉及的技术复杂性,这自 +然需要专业知识和决策。 + +所需的专业知识因贡献领域而异。它主要由上下文和技术复杂性决定,其次由贡献者和 +维护者的期望决定。 + +专家的期望和决策都要经过讨论,但在最后,为了取得进展,必须能够做出决策。这一 +特权掌握在维护人员和项目领导的手中,预计将善意使用。 + +因此,设定专业知识期望、作出决定和拒绝不适当的贡献不被视为违反行为准则。 + +虽然维护人员一般都欢迎新来者,但他们帮助(新)贡献者克服障碍的能力有限,因此 +他们必须确定优先事项。这也不应被视为违反了行为准则。内核社区意识到这一点,并 +以各种形式提供入门级节目,如 kernelnewbies.org 。 + +范围 +---- + +Linux内核社区主要在一组公共电子邮件列表上进行交互,这些列表分布在由多个不同 +公司或个人控制的多个不同服务器上。所有这些列表都在内核源代码树中的 +MAINTAINERS 文件中定义。发送到这些邮件列表的任何电子邮件都被视为包含在行为 +准则中。 + +使用 kernel.org bugzilla和其他子系统bugzilla 或bug跟踪工具的开发人员应该遵循 +行为准则的指导原则。Linux内核社区没有“官方”项目电子邮件地址或“官方”社交媒体 +地址。使用kernel.org电子邮件帐户执行的任何活动必须遵循为kernel.org发布的行为 +准则,就像任何使用公司电子邮件帐户的个人必须遵循该公司的特定规则一样。 + +行为准则并不禁止在邮件列表消息、内核更改日志消息或代码注释中继续包含名称、 +电子邮件地址和相关注释。 + +其他论坛中的互动包括在适用于上述论坛的任何规则中,通常不包括在行为准则中。 +除了在极端情况下可考虑的例外情况。 + +提交给内核的贡献应该使用适当的语言。在行为准则之前已经存在的内容现在不会被 +视为违反。然而,不适当的语言可以被视为一个bug;如果任何相关方提交补丁, +这样的bug将被更快地修复。当前属于用户/内核API的一部分的表达式,或者反映已 +发布标准或规范中使用的术语的表达式,不被视为bug。 + +执行 +---- + +行为准则中列出的地址属于行为准则委员会。https://kernel.org/code-of-conduct.html +列出了在任何给定时间接收这些电子邮件的确切成员。成员不能访问在加入委员会之前 +或离开委员会之后所做的报告。 + +最初的行为准则委员会由TAB的志愿者以及作为中立第三方的专业调解人组成。委员会 +的首要任务是建立文件化的流程,并将其公开。 + +如果报告人不希望将整个委员会纳入投诉或关切,可直接联系委员会的任何成员,包括 +调解人。 + +行为准则委员会根据流程审查案例(见上文),并根据需要和适当与TAB协商,例如请求 +和接收有关内核社区的信息。 + +委员会做出的任何决定都将提交到表中,以便在必要时与相关维护人员一起执行。行为 +准则委员会的决定可以通过三分之二的投票推翻。 + +每季度,行为准则委员会和标签将提供一份报告,概述行为准则委员会收到的匿名报告 +及其状态,以及任何否决决定的细节,包括完整和可识别的投票细节。 + +我们希望在启动期之后为行为准则委员会人员配备建立一个不同的流程。发生此情况时, +将使用该信息更新此文档。 -- cgit v1.2.3 From 883992a6052f16881c8c895c0c61161dcdeed0ae Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:38 +0800 Subject: docs/zh_CN: add disclaim and translator into CoC interp That's give translator credit and a way for complain Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- .../translations/zh_CN/process/code-of-conduct-interpretation.rst | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/code-of-conduct-interpretation.rst b/Documentation/translations/zh_CN/process/code-of-conduct-interpretation.rst index 39743a0ed0d3..a1daec0482e2 100644 --- a/Documentation/translations/zh_CN/process/code-of-conduct-interpretation.rst +++ b/Documentation/translations/zh_CN/process/code-of-conduct-interpretation.rst @@ -1,3 +1,8 @@ +.. include:: ../disclaimer-zh_CN.rst + +:Original: :ref:`Documentation/process/code-of-conduct-interpretation.rst ` +:Translator: Alex Shi + .. _cn_code_of_conduct_interpretation: Linux内核贡献者契约行为准则解释 -- cgit v1.2.3 From d0373af462d77cbe1543b25134541efa1152c1e2 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:39 +0800 Subject: docs/zh_CN: link CoC interpretation into index So people could be easy to find it. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/index.rst | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/index.rst b/Documentation/translations/zh_CN/process/index.rst index ba9fd19b87d7..e37c03a90ac8 100644 --- a/Documentation/translations/zh_CN/process/index.rst +++ b/Documentation/translations/zh_CN/process/index.rst @@ -24,6 +24,7 @@ howto code-of-conduct + code-of-conduct-interpretation submitting-patches coding-style development-process -- cgit v1.2.3 From 973a9f6c70de96337926fc045546cf5d48365cc4 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:40 +0800 Subject: docs/zh_CN: fix link issue in howto.rst Now we could follow links in created html files. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Federico Vaga Cc: SeongJae Park Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/howto.rst | 48 +++++++++++----------- 1 file changed, 25 insertions(+), 23 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/howto.rst b/Documentation/translations/zh_CN/process/howto.rst index 6ab167812325..246f76a97eaf 100644 --- a/Documentation/translations/zh_CN/process/howto.rst +++ b/Documentation/translations/zh_CN/process/howto.rst @@ -81,20 +81,21 @@ Linux内核代码中包含有大量的文档。这些文档对于学习如何与 的维护者解释这些变化。 以下是内核代码中需要阅读的文档: - README + :ref:`Documentation/admin-guide/README.rst ` 文件简要介绍了Linux内核的背景,并且描述了如何配置和编译内核。内核的 新用户应该从这里开始。 - Documentation/process/changes.rst + + :ref:`Documentation/process/changes.rst ` 文件给出了用来编译和使用内核所需要的最小软件包列表。 - Documentation/process/coding-style.rst + :ref:`Documentation/process/coding-style.rst ` 描述Linux内核的代码风格和理由。所有新代码需要遵守这篇文档中定义的规 范。大多数维护者只会接收符合规定的补丁,很多人也只会帮忙检查符合风格 的代码。 - Documentation/process/submitting-patches.rst - Documentation/process/submitting-drivers.rst + :ref:`Documentation/process/submitting-patches.rst ` + :ref:`Documentation/process/submitting-drivers.rst ` 这两份文档明确描述如何创建和发送补丁,其中包括(但不仅限于): - 邮件内容 @@ -113,7 +114,7 @@ Linux内核代码中包含有大量的文档。这些文档对于学习如何与 http://linux.yyz.us/patch-format.html - Documentation/process/stable-api-nonsense.rst + :ref:`Documentation/process/stable-api-nonsense.rst ` 论证内核为什么特意不包括稳定的内核内部API,也就是说不包括像这样的特 性: @@ -124,29 +125,29 @@ Linux内核代码中包含有大量的文档。这些文档对于学习如何与 这篇文档对于理解Linux的开发哲学至关重要。对于将开发平台从其他操作系 统转移到Linux的人来说也很重要。 - Documentation/admin-guide/security-bugs.rst + :ref:`Documentation/admin-guide/security-bugs.rst ` 如果你认为自己发现了Linux内核的安全性问题,请根据这篇文档中的步骤来 提醒其他内核开发者并帮助解决这个问题。 - Documentation/process/management-style.rst + :ref:`Documentation/process/management-style.rst ` 描述内核维护者的工作方法及其共有特点。这对于刚刚接触内核开发(或者对 它感到好奇)的人来说很重要,因为它解释了很多对于内核维护者独特行为的 普遍误解与迷惑。 - Documentation/process/stable-kernel-rules.rst + :ref:`Documentation/process/stable-kernel-rules.rst ` 解释了稳定版内核发布的规则,以及如何将改动放入这些版本的步骤。 - Documentation/process/kernel-docs.rst + :ref:`Documentation/process/kernel-docs.rst ` 有助于内核开发的外部文档列表。如果你在内核自带的文档中没有找到你想找 的内容,可以查看这些文档。 - Documentation/process/applying-patches.rst + :ref:`Documentation/process/applying-patches.rst ` 关于补丁是什么以及如何将它打在不同内核开发分支上的好介绍 内核还拥有大量从代码自动生成的文档。它包含内核内部API的全面介绍以及如何 妥善处理加锁的规则。生成的文档会放在 Documentation/DocBook/目录下。在内 核源码的主目录中使用以下不同命令将会分别生成PDF、Postscript、HTML和手册 -页等不同格式的文档: +页等不同格式的文档:: make pdfdocs make htmldocs @@ -212,8 +213,8 @@ kernel.org网站的pub/linux/kernel/v2.6/目录下找到它。它的开发遵循 - 每当一个新版本的内核被发布,为期两周的集成窗口将被打开。在这段时间里 维护者可以向Linus提交大段的修改,通常这些修改已经被放到-mm内核中几个 星期了。提交大量修改的首选方式是使用git工具(内核的代码版本管理工具 - ,更多的信息可以在http://git-scm.com/获取),不过使用普通补丁也是可以 - 的。 + ,更多的信息可以在 http://git-scm.com/ 获取),不过使用普通补丁也是 + 可以的。 - 两个星期以后-rc1版本内核发布。之后只有不包含可能影响整个内核稳定性的 新功能的补丁才可能被接受。请注意一个全新的驱动程序(或者文件系统)有 可能在-rc1后被接受是因为这样的修改完全独立,不会影响其他的代码,所以 @@ -243,8 +244,8 @@ kernel.org网站的pub/linux/kernel/v2.6/目录下找到它。它的开发遵循 2.6.x.y版本由“稳定版”小组(邮件地址)维护,一般隔周发 布新版本。 -内核源码中的Documentation/process/stable-kernel-rules.rst文件具体描述了可被稳定 -版内核接受的修改类型以及发布的流程。 +内核源码中的 :ref:`Documentation/process/stable-kernel-rules.rst ` +文件具体描述了可被稳定版内核接受的修改类型以及发布的流程。 2.6.x -mm补丁集 @@ -316,7 +317,7 @@ linux-kernel邮件列表中提供反馈,告诉大家你遇到了问题还是 - x86-64, 部分i386, Andi Kleen ftp.firstfloor.org:/pub/ak/x86_64/quilt/ - 其他内核源码树可以在http://git.kernel.org的列表中和MAINTAINERS文件里 + 其他内核源码树可以在 http://git.kernel.org 的列表中和MAINTAINERS文件里 找到。 报告bug @@ -339,7 +340,7 @@ bugzilla.kernel.org是Linux内核开发者们用来跟踪内核Bug的网站。 者感受到你的存在。修改bug是赢得其他开发者赞誉的最好办法,因为并不是很多 人都喜欢浪费时间去修改别人报告的bug。 -要尝试修改已知的bug,请访问http://bugzilla.kernel.org网址。如果你想获得 +要尝试修改已知的bug,请访问 http://bugzilla.kernel.org 网址。如果你想获得 最新bug的通知,可以订阅bugme-new邮件列表(只有新的bug报告会被寄到这里) 或者订阅bugme-janitor邮件列表(所有bugzilla的变动都会被寄到这里)。 @@ -384,11 +385,12 @@ MAINTAINERS文件中可以找到不同话题对应的邮件列表。 这几行。将你的评论加在被引用的段落之间而不要放在邮件的顶部。 如果你在邮件中附带补丁,请确认它们是可以直接阅读的纯文本(如 -Documentation/process/submitting-patches.rst文档中所述)。内核开发者们不希望遇到附件 -或者被压缩了的补丁。只有这样才能保证他们可以直接评论你的每行代码。请确保 -你使用的邮件发送程序不会修改空格和制表符。一个防范性的测试方法是先将邮件 -发送给自己,然后自己尝试是否可以顺利地打上收到的补丁。如果测试不成功,请 -调整或者更换你的邮件发送程序直到它正确工作为止。 +:ref:`Documentation/process/submitting-patches.rst ` +文档中所述)。内核开发者们不希望遇到附件或者被压缩了的补丁。只有这样才能 +保证他们可以直接评论你的每行代码。请确保你使用的邮件发送程序不会修改空格 +和制表符。一个防范性的测试方法是先将邮件发送给自己,然后自己尝试是否可以 +顺利地打上收到的补丁。如果测试不成功,请调整或者更换你的邮件发送程序直到 +它正确工作为止。 总而言之,请尊重其他的邮件列表订阅者。 -- cgit v1.2.3 From 40d93e4961800b5a7b047f0c8585f0eb8a85e2e3 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:41 +0800 Subject: docs/zh_CN: update howto.rst to latest version This removed the obsolete 2.6.x examples, sub-system tree and updated some links/items following latest Englisht version howto Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Federico Vaga Cc: SeongJae Park Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/howto.rst | 154 +++++++-------------- 1 file changed, 49 insertions(+), 105 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/howto.rst b/Documentation/translations/zh_CN/process/howto.rst index 246f76a97eaf..cb41336ccb80 100644 --- a/Documentation/translations/zh_CN/process/howto.rst +++ b/Documentation/translations/zh_CN/process/howto.rst @@ -63,9 +63,11 @@ Linux内核使用GNU C和GNU工具链开发。虽然它遵循ISO C89标准,但 -------- Linux内核源代码都是在GPL(通用公共许可证)的保护下发布的。要了解这种许可 -的细节请查看源代码主目录下的COPYING文件。如果你对它还有更深入问题请联系 -律师,而不要在Linux内核邮件组上提问。因为邮件组里的人并不是律师,不要期 -望他们的话有法律效力。 +的细节请查看源代码主目录下的COPYING文件。Linux内核许可准则和如果使用 +`SPDC ` 标志符说明在文件 +:ref:`Documentation/process/license-rules.rst ` +如果你对它还有更深入问题请联系律师,而不要在Linux内核邮件组上提问。因为 +邮件组里的人并不是律师,不要期望他们的话有法律效力。 对于GPL的常见问题和解答,请访问以下链接: http://www.gnu.org/licenses/gpl-faq.html @@ -177,19 +179,13 @@ Linux内核代码中包含有大量的文档。这些文档对于学习如何与 集成进内核的基本原理。如果还没有决定下一步要做什么的话,你还可能会得到方 向性的指点。 -如果你已经有一些现成的代码想要放到内核中,但是需要一些帮助来使它们拥有正 -确的格式。请访问“内核导师”计划。这个计划就是用来帮助你完成这个目标的。它 -是一个邮件列表,地址如下: - - http://selenic.com/mailman/listinfo/kernel-mentors - 在真正动手修改内核代码之前,理解要修改的代码如何运作是必需的。要达到这个 目的,没什么办法比直接读代码更有效了(大多数花招都会有相应的注释),而且 一些特制的工具还可以提供帮助。例如,“Linux代码交叉引用”项目就是一个值得 特别推荐的帮助工具,它将源代码显示在有编目和索引的网页上。其中一个更新及 时的内核源码库,可以通过以下地址访问: - http://sosdg.org/~coywolf/lxr/ + https://elixir.bootlin.com/ 开发流程 @@ -198,17 +194,16 @@ Linux内核代码中包含有大量的文档。这些文档对于学习如何与 目前Linux内核开发流程包括几个“主内核分支”和很多子系统相关的内核分支。这 些分支包括: - - 2.6.x主内核源码树 - - 2.6.x.y -stable内核源码树 - - 2.6.x -mm内核补丁集 - - 子系统相关的内核源码树和补丁集 + - Linus 的内核源码树 + - 多个主要版本的稳定版内核树 + - 子系统相关的内核树 + - linux-next 集成测试树 -2.6.x内核主源码树 ------------------ -2.6.x内核是由Linus Torvalds(Linux的创造者)亲自维护的。你可以在 -kernel.org网站的pub/linux/kernel/v2.6/目录下找到它。它的开发遵循以下步 -骤: +主线树 +------ +主线树是由Linus Torvalds 维护的。你可以在https://kernel.org 网站或者代码 +库中下找到它。它的开发遵循以下步骤: - 每当一个新版本的内核被发布,为期两周的集成窗口将被打开。在这段时间里 维护者可以向Linus提交大段的修改,通常这些修改已经被放到-mm内核中几个 @@ -229,96 +224,49 @@ kernel.org网站的pub/linux/kernel/v2.6/目录下找到它。它的开发遵循 “没有人知道新内核何时会被发布,因为发布是根据已知bug的情况来决定 的,而不是根据一个事先制定好的时间表。” +子系统特定树 +------------ -2.6.x.y -stable(稳定版)内核源码树 ------------------------------------ -由4个数字组成的内核版本号说明此内核是-stable版本。它们包含基于2.6.x版本 -内核的相对较小且至关重要的修补,这些修补针对安全性问题或者严重的内核退步。 - -这种版本的内核适用于那些期望获得最新的稳定版内核并且不想参与测试开发版或 -者实验版的用户。 - -如果没有2.6.x.y版本内核存在,那么最新的2.6.x版本内核就相当于是当前的稳定 -版内核。 - -2.6.x.y版本由“稳定版”小组(邮件地址)维护,一般隔周发 -布新版本。 - -内核源码中的 :ref:`Documentation/process/stable-kernel-rules.rst ` -文件具体描述了可被稳定版内核接受的修改类型以及发布的流程。 - - -2.6.x -mm补丁集 ---------------- -这是由Andrew Morton维护的试验性内核补丁集。Andrew将所有子系统的内核源码 -和补丁拼凑到一起,并且加入了大量从linux-kernel邮件列表中采集的补丁。这个 -源码树是新功能和补丁的试炼场。当补丁在-mm补丁集里证明了其价值以后Andrew -或者相应子系统的维护者会将补丁发给Linus以便集成进主内核源码树。 - -在将所有新补丁发给Linus以集成到主内核源码树之前,我们非常鼓励先把这些补 -丁放在-mm版内核源码树中进行测试。 +各种内核子系统的维护者——以及许多内核子系统开发人员——在源代码库中公开了他们 +当前的开发状态。这样,其他人就可以看到内核的不同区域发生了什么。在开发速度 +很快的领域,可能会要求开发人员将提交的内容建立在这样的子系统内核树上,这样 +就避免了提交与其他已经进行的工作之间的冲突。 -这些内核版本不适合在需要稳定运行的系统上运行,因为运行它们比运行任何其他 -内核分支都更具有风险。 +这些存储库中的大多数都是Git树,但是也有其他的scm在使用,或者补丁队列被发布 +为Quilt系列。这些子系统存储库的地址列在MAINTAINERS文件中。其中许多可以在 +https://git.kernel.org/上浏览。 -如果你想为内核开发进程提供帮助,请尝试并使用这些内核版本,并在 -linux-kernel邮件列表中提供反馈,告诉大家你遇到了问题还是一切正常。 +在将一个建议的补丁提交到这样的子系统树之前,需要对它进行审查,审查主要发生 +在邮件列表上(请参见下面相应的部分)。对于几个内核子系统,这个审查过程是通 +过工具补丁跟踪的。Patchwork提供了一个Web界面,显示补丁发布、对补丁的任何评 +论或修订,维护人员可以将补丁标记为正在审查、接受或拒绝。大多数补丁网站都列 +在 https://patchwork.kernel.org/ -通常-mm版补丁集不光包括这些额外的试验性补丁,还包括发布时-git版主源码树 -中的改动。 +Linux-next 集成测试树 +--------------------- --mm版内核没有固定的发布周期,但是通常在每两个-rc版内核发布之间都会有若干 -个-mm版内核发布(一般是1至3个)。 +在将子系统树的更新合并到主线树之前,需要对它们进行集成测试。为此,存在一个 +特殊的测试存储库,其中几乎每天都会提取所有子系统树: + https://git.kernel.org/?p=linux/kernel/git/next/linux-next.git -子系统相关内核源码树和补丁集 ----------------------------- -相当一部分内核子系统开发者会公开他们自己的开发源码树,以便其他人能了解内 -核的不同领域正在发生的事情。如上所述,这些源码树会被集成到-mm版本内核中。 +通过这种方式,Linux-next 对下一个合并阶段将进入主线内核的内容给出了一个概要 +展望。非常欢冒险的测试者运行测试Linux-next。 -下面是目前可用的一些内核源码树的列表: - 通过git管理的源码树: - - Kbuild开发源码树, Sam Ravnborg - git.kernel.org:/pub/scm/linux/kernel/git/sam/kbuild.git - - - ACPI开发源码树, Len Brown - git.kernel.org:/pub/scm/linux/kernel/git/lenb/linux-acpi-2.6.git - - - 块设备开发源码树, Jens Axboe - git.kernel.org:/pub/scm/linux/kernel/git/axboe/linux-2.6-block.git - - - DRM开发源码树, Dave Airlie - git.kernel.org:/pub/scm/linux/kernel/git/airlied/drm-2.6.git - - - ia64开发源码树, Tony Luck - git.kernel.org:/pub/scm/linux/kernel/git/aegl/linux-2.6.git - - - ieee1394开发源码树, Jody McIntyre - git.kernel.org:/pub/scm/linux/kernel/git/scjody/ieee1394.git - - - infiniband开发源码树, Roland Dreier - git.kernel.org:/pub/scm/linux/kernel/git/roland/infiniband.git - - - libata开发源码树, Jeff Garzik - git.kernel.org:/pub/scm/linux/kernel/git/jgarzik/libata-dev.git - - - 网络驱动程序开发源码树, Jeff Garzik - git.kernel.org:/pub/scm/linux/kernel/git/jgarzik/netdev-2.6.git +多个主要版本的稳定版内核树 +----------------------------------- +由3个数字组成的内核版本号说明此内核是-stable版本。它们包含内核的相对较小且 +至关重要的修补,这些修补针对安全性问题或者严重的内核退步。 - - pcmcia开发源码树, Dominik Brodowski - git.kernel.org:/pub/scm/linux/kernel/git/brodo/pcmcia-2.6.git +这种版本的内核适用于那些期望获得最新的稳定版内核并且不想参与测试开发版或 +者实验版的用户。 - - SCSI开发源码树, James Bottomley - git.kernel.org:/pub/scm/linux/kernel/git/jejb/scsi-misc-2.6.git +稳定版内核树版本由“稳定版”小组(邮件地址)维护,一般 +隔周发布新版本。 - 使用quilt管理的补丁集: - - USB, PCI, 驱动程序核心和I2C, Greg Kroah-Hartman - kernel.org/pub/linux/kernel/people/gregkh/gregkh-2.6/ - - x86-64, 部分i386, Andi Kleen - ftp.firstfloor.org:/pub/ak/x86_64/quilt/ +内核源码中的 :ref:`Documentation/process/stable-kernel-rules.rst ` +文件具体描述了可被稳定版内核接受的修改类型以及发布的流程。 - 其他内核源码树可以在 http://git.kernel.org 的列表中和MAINTAINERS文件里 - 找到。 报告bug ------- @@ -328,8 +276,9 @@ bugzilla.kernel.org是Linux内核开发者们用来跟踪内核Bug的网站。 http://test.kernel.org/bugzilla/faq.html -内核源码主目录中的admin-guide/reporting-bugs.rst文件里有一个很好的模板。它指导用户如何报 -告可能的内核bug以及需要提供哪些信息来帮助内核开发者们找到问题的根源。 +内核源码主目录中的:ref:`admin-guide/reporting-bugs.rst ` +文件里有一个很好的模板。它指导用户如何报告可能的内核bug以及需要提供哪些信息 +来帮助内核开发者们找到问题的根源。 利用bug报告 @@ -340,12 +289,7 @@ bugzilla.kernel.org是Linux内核开发者们用来跟踪内核Bug的网站。 者感受到你的存在。修改bug是赢得其他开发者赞誉的最好办法,因为并不是很多 人都喜欢浪费时间去修改别人报告的bug。 -要尝试修改已知的bug,请访问 http://bugzilla.kernel.org 网址。如果你想获得 -最新bug的通知,可以订阅bugme-new邮件列表(只有新的bug报告会被寄到这里) -或者订阅bugme-janitor邮件列表(所有bugzilla的变动都会被寄到这里)。 - - https://lists.linux-foundation.org/mailman/listinfo/bugme-new - https://lists.linux-foundation.org/mailman/listinfo/bugme-janitors +要尝试修改已知的bug,请访问 http://bugzilla.kernel.org 网址。 邮件列表 -- cgit v1.2.3 From 56d75cc22dc15f6e2b7aa6da0f833da10fc7baab Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:42 +0800 Subject: docs/zh_CN: update translator info and comments in howto Since we has disclaimer, don't need duplicate comments. Add myself into translators. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Federico Vaga Cc: SeongJae Park Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/howto.rst | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/howto.rst b/Documentation/translations/zh_CN/process/howto.rst index cb41336ccb80..8b62f7c4104d 100644 --- a/Documentation/translations/zh_CN/process/howto.rst +++ b/Documentation/translations/zh_CN/process/howto.rst @@ -4,13 +4,12 @@ :Original: :ref:`Documentation/process/howto.rst ` -如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 -交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者:: +译者:: 英文版维护者: Greg Kroah-Hartman 中文版维护者: 李阳 Li Yang 中文版翻译者: 李阳 Li Yang + 时奎亮 Alex Shi 中文版校译者: 钟宇 TripleX Chung 陈琦 Maggie Chen -- cgit v1.2.3 From da6cfbf90d033f8aed3118a2ff5c3701cc9b4db4 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:43 +0800 Subject: docs/zh_CN: redirect license-rules to Chinese doc The latest license-rules.rst was translated into Chinese. So it's time to set a link for it. Also fix typos around SPDX. Signed-off-by: Alex Shi Signed-off-by: Dust Li Cc: Harry Wei Cc: Jonathan Corbet Cc: Federico Vaga Cc: SeongJae Park Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/howto.rst | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/howto.rst b/Documentation/translations/zh_CN/process/howto.rst index 8b62f7c4104d..980d53e9612c 100644 --- a/Documentation/translations/zh_CN/process/howto.rst +++ b/Documentation/translations/zh_CN/process/howto.rst @@ -62,9 +62,9 @@ Linux内核使用GNU C和GNU工具链开发。虽然它遵循ISO C89标准,但 -------- Linux内核源代码都是在GPL(通用公共许可证)的保护下发布的。要了解这种许可 -的细节请查看源代码主目录下的COPYING文件。Linux内核许可准则和如果使用 -`SPDC ` 标志符说明在文件 -:ref:`Documentation/process/license-rules.rst ` +的细节请查看源代码主目录下的COPYING文件。Linux内核许可准则和如何使用 +`SPDX ` 标志符说明在这个文件中 +:ref:`Documentation/translations/zh_CN/process/license-rules.rst ` 如果你对它还有更深入问题请联系律师,而不要在Linux内核邮件组上提问。因为 邮件组里的人并不是律师,不要期望他们的话有法律效力。 -- cgit v1.2.3 From 5ada65696c7f6821e3cf5ed7e1a10183d10256dd Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:44 +0800 Subject: docs/zh_CN: redirect howto.rst link to Chinese version The howto doc is translated from latest version. Now it's time to point the link to it. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/8.Conclusion.rst | 13 +++++++------ 1 file changed, 7 insertions(+), 6 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/8.Conclusion.rst b/Documentation/translations/zh_CN/process/8.Conclusion.rst index 32b4e617a451..c164edc34687 100644 --- a/Documentation/translations/zh_CN/process/8.Conclusion.rst +++ b/Documentation/translations/zh_CN/process/8.Conclusion.rst @@ -9,12 +9,13 @@ ======== 关于Linux内核开发和相关主题的信息来源很多。首先是在内核源代码分发中找到的 -文档目录。顶级:ref:`process/howto.rst ` 文件是一个重要的起点 -:ref:`process/submitting-patches.rst ` 和 -:ref:`process/submitting-drivers.rst ` 也是所有内核开发 -人员都应该阅读的内容。许多内部内核API都是使用kerneldoc机制记录的; -“make htmldocs”或“make pdfdocs”可用于以HTML或PDF格式生成这些文档(尽管某些 -发行版提供的tex版本会遇到内部限制,无法正确处理文档)。 +文档目录。顶级 :ref:`Documentation/translations/zh_CN/process/howto.rst ` +文件是一个重要的起点 +:ref:`process/submitting-patches.rst ` +和:ref:`process/submitting-drivers.rst ` +也是所有内核开发人员都应该阅读的内容。许多内部内核API都是使用kerneldoc机制 +记录的;“make htmldocs”或“make pdfdocs”可用于以HTML或PDF格式生成这些文档( +尽管某些发行版提供的tex版本会遇到内部限制,无法正确处理文档)。 不同的网站在各个细节层次上讨论内核开发。您的作者想谦虚地建议用http://lwn.net/ 作为来源;有关许多特定内核主题的信息可以通过以下网址的lwn内核索引找到: -- cgit v1.2.3 From 62130affd7b30cce7f67f066922def351ba31aa4 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:45 +0800 Subject: docs/zh_CN: update to latest submitting-patches.rst Updated huge changes for this docs. Seems we forget this for decades. And use local stub to pointer this Chinese docs. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Tom Levy Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- .../zh_CN/process/submitting-patches.rst | 614 +++++++++++++++------ 1 file changed, 431 insertions(+), 183 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/submitting-patches.rst b/Documentation/translations/zh_CN/process/submitting-patches.rst index 1bd64832b424..5fa716584598 100644 --- a/Documentation/translations/zh_CN/process/submitting-patches.rst +++ b/Documentation/translations/zh_CN/process/submitting-patches.rst @@ -1,4 +1,4 @@ -.. _cn_process_submittingpatches: +.. _cn_submittingpatches: .. include:: ../disclaimer-zh_CN.rst @@ -19,15 +19,34 @@ 对于想要将改动提交到 Linux 内核的个人或者公司来说,如果不熟悉“规矩”, 提交的流程会让人畏惧。本文档收集了一系列建议,这些建议可以大大的提高你 -的改动被接受的机会。 -阅读 Documentation/process/submit-checklist.rst 来获得在提交代码前需要检查的项目的列 -表。如果你在提交一个驱动程序,那么同时阅读一下 -Documentation/process/submitting-drivers.rst 。 +的改动被接受的机会. +以下文档含有大量简洁的建议, 具体请见: +:ref:`Documentation/process ` +同样,:ref:`Documentation/process/submit-checklist.rst ` +给出在提交代码前需要检查的项目的列表。如果你在提交一个驱动程序,那么 +同时阅读一下: +:ref:`Documentation/process/submitting-drivers.rst ` ---------------------------- -第一节 - 创建并发送你的改动 ---------------------------- +其中许多步骤描述了Git版本控制系统的默认行为;如果您使用Git来准备补丁, +您将发现它为您完成的大部分机械工作,尽管您仍然需要准备和记录一组合理的 +补丁。一般来说,使用git将使您作为内核开发人员的生活更轻松。 + + +0) 获取当前源码树 +----------------- + +如果您没有一个可以使用当前内核源代码的存储库,请使用git获取一个。您将要 +从主线存储库开始,它可以通过以下方式获取:: + + git clone git://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git + +但是,请注意,您可能不希望直接针对主线树进行开发。大多数子系统维护人员运 +行自己的树,并希望看到针对这些树准备的补丁。请参见MAINTAINERS文件中子系 +统的 **T:** 项以查找该树,或者简单地询问维护者该树是否未在其中列出。 + +仍然可以通过tarballs下载内核版本(如下一节所述),但这是进行内核开发的 +一种困难的方式。 1) "diff -up" ------------- @@ -39,9 +58,10 @@ Documentation/process/submitting-drivers.rst 。 参数生成。而且,请使用 '-p' 参数,那样会显示每个改动所在的C函数,使得 产生的补丁容易读得多。补丁应该基于内核源代码树的根目录,而不是里边的任 何子目录。 + 为一个单独的文件创建补丁,一般来说这样做就够了:: - SRCTREE=linux-2.6 + SRCTREE=linux MYFILE=drivers/net/mydriver.c cd $SRCTREE @@ -53,38 +73,103 @@ Documentation/process/submitting-drivers.rst 。 为多个文件创建补丁,你可以解开一个没有修改过的内核源代码树,然后和你自 己的代码树之间做 diff 。例如:: - MYSRC=/devel/linux-2.6 + MYSRC=/devel/linux - tar xvfz linux-2.6.12.tar.gz - mv linux-2.6.12 linux-2.6.12-vanilla - diff -uprN -X linux-2.6.12-vanilla/Documentation/dontdiff \ - linux-2.6.12-vanilla $MYSRC > /tmp/patch + tar xvfz linux-3.19.tar.gz + mv linux-3.19 linux-3.19-vanilla + diff -uprN -X linux-3.19-vanilla/Documentation/dontdiff \ + linux-3.19-vanilla $MYSRC > /tmp/patch "dontdiff" 是内核在编译的时候产生的文件的列表,列表中的文件在 diff(1) -产生的补丁里会被跳过。"dontdiff" 文件被包含在2.6.12和之后版本的内核源代 -码树中。对于更早的内核版本,你可以从 - 获取它。 +产生的补丁里会被跳过。 + 确定你的补丁里没有包含任何不属于这次补丁提交的额外文件。记得在用diff(1) 生成补丁之后,审阅一次补丁,以确保准确。 + 如果你的改动很散乱,你应该研究一下如何将补丁分割成独立的部分,将改动分 割成一系列合乎逻辑的步骤。这样更容易让其他内核开发者审核,如果你想你的 -补丁被接受,这是很重要的。下面这些脚本能够帮助你做这件事情: -Quilt: -http://savannah.nongnu.org/projects/quilt +补丁被接受,这是很重要的。请参阅: +:ref:`cn_split_changes` + +如果你用 ``git`` , ``git rebase -i`` 可以帮助你这一点。如果你不用 ``git``, +``quilt`` 另外一个流行的选择。 + +.. _cn_describe_changes: + +2) 描述你的改动 +--------------- + +描述你的问题。无论您的补丁是一行错误修复还是5000行新功能,都必须有一个潜在 +的问题激励您完成这项工作。让审稿人相信有一个问题值得解决,让他们读完第一段 +是有意义的。 + +描述用户可见的影响。直接崩溃和锁定是相当有说服力的,但并不是所有的错误都那么 +明目张胆。即使在代码审查期间发现了这个问题,也要描述一下您认为它可能对用户产 +生的影响。请记住,大多数Linux安装运行的内核来自二级稳定树或特定于供应商/产品 +的树,只从上游精选特定的补丁,因此请包含任何可以帮助您将更改定位到下游的内容: +触发的场景、DMESG的摘录、崩溃描述、性能回归、延迟尖峰、锁定等。 + +量化优化和权衡。如果您声称在性能、内存消耗、堆栈占用空间或二进制大小方面有所 +改进,请包括支持它们的数字。但也要描述不明显的成本。优化通常不是免费的,而是 +在CPU、内存和可读性之间进行权衡;或者,探索性的工作,在不同的工作负载之间进 +行权衡。请描述优化的预期缺点,以便审阅者可以权衡成本和收益。 + +一旦问题建立起来,就要详细地描述一下您实际在做什么。对于审阅者来说,用简单的 +英语描述代码的变化是很重要的,以验证代码的行为是否符合您的意愿。 + +如果您将补丁描述写在一个表单中,这个表单可以很容易地作为“提交日志”放入Linux +的源代码管理系统git中,那么维护人员将非常感谢您。见 :ref:`cn_explicit_in_reply_to`. + +每个补丁只解决一个问题。如果你的描述开始变长,这就表明你可能需要拆分你的补丁。 +请见 :ref:`cn_split_changes` + +提交或重新提交修补程序或修补程序系列时,请包括完整的修补程序说明和理由。不要 +只说这是补丁(系列)的第几版。不要期望子系统维护人员引用更早的补丁版本或引用 +URL来查找补丁描述并将其放入补丁中。也就是说,补丁(系列)及其描述应该是独立的。 +这对维护人员和审查人员都有好处。一些评审者可能甚至没有收到补丁的早期版本。 + +描述你在命令语气中的变化,例如“make xyzzy do frotz”而不是“[这个补丁]make +xyzzy do frotz”或“[我]changed xyzzy to do frotz”,就好像你在命令代码库改变 +它的行为一样。 + +如果修补程序修复了一个记录的bug条目,请按编号和URL引用该bug条目。如果补丁来 +自邮件列表讨论,请给出邮件列表存档的URL;使用带有 ``Message-ID`` 的 +https://lkml.kernel.org/ 重定向,以确保链接不会过时。 + +但是,在没有外部资源的情况下,尽量让你的解释可理解。除了提供邮件列表存档或 +bug的URL之外,还要总结需要提交补丁的相关讨论要点。 + +如果您想要引用一个特定的提交,不要只引用提交的 SHA-1 ID。还请包括提交的一行 +摘要,以便于审阅者了解它是关于什么的。例如:: + + Commit e21d2170f36602ae2708 ("video: remove unnecessary + platform_set_drvdata()") removed the unnecessary + platform_set_drvdata(), but left the variable "dev" unused, + delete it. + +您还应该确保至少使用前12位 SHA-1 ID. 内核存储库包含*许多*对象,使与较短的ID +发生冲突的可能性很大。记住,即使现在不会与您的六个字符ID发生冲突,这种情况 +可能五年后改变。 + +如果修补程序修复了特定提交中的错误,例如,使用 ``git bisct`` ,请使用带有前 +12个字符SHA-1 ID 的"Fixes:"标记和单行摘要。为了简化不要将标记拆分为多个, +行、标记不受分析脚本“75列换行”规则的限制。例如:: -2)描述你的改动。 -描述你的改动包含的技术细节。 + Fixes: 54a4f0239f2e ("KVM: MMU: make kvm_mmu_zap_page() return the number of pages it actually freed") -要多具体就写多具体。最糟糕的描述可能是像下面这些语句:“更新了某驱动程 -序”,“修正了某驱动程序的bug”,或者“这个补丁包含了某子系统的修改,请 -使用。” +下列 ``git config`` 设置可以添加让 ``git log``, ``git show`` 漂亮的显示格式:: -如果你的描述开始变长,这表示你也许需要拆分你的补丁了,请看第3小节, -继续。 + [core] + abbrev = 12 + [pretty] + fixes = Fixes: %h (\"%s\") -3)拆分你的改动 +.. _cn_split_changes: -将改动拆分,逻辑类似的放到同一个补丁文件里。 +3) 拆分你的改动 +--------------- + +将每个逻辑更改分隔成一个单独的补丁。 例如,如果你的改动里同时有bug修正和性能优化,那么把这些改动拆分到两个或 者更多的补丁文件中。如果你的改动包含对API的修改,并且修改了驱动程序来适 @@ -96,64 +181,94 @@ http://savannah.nongnu.org/projects/quilt 如果有一个补丁依赖另外一个补丁来完成它的改动,那没问题。简单的在你的补 丁描述里指出“这个补丁依赖某补丁”就好了。 +在将您的更改划分为一系列补丁时,要特别注意确保内核在系列中的每个补丁之后 +都能正常构建和运行。使用 ``git bisect`` 来追踪问题的开发者可能会在任何时 +候分割你的补丁系列;如果你在中间引入错误,他们不会感谢你。 + 如果你不能将补丁浓缩成更少的文件,那么每次大约发送出15个,然后等待审查 -和整合。 +和集成。 + +4) 检查你的更改风格 +------------------- + +检查您的补丁是否存在基本样式冲突,详细信息可在 +:ref:`Documentation/process/coding-style.rst ` +中找到。如果不这样做,只会浪费审稿人的时间,并且会导致你的补丁被拒绝,甚至 +可能没有被阅读。 + +一个重要的例外是在将代码从一个文件移动到另一个文件时——在这种情况下,您不应 +该在移动代码的同一个补丁中修改移动的代码。这清楚地描述了移动代码和您的更改 +的行为。这大大有助于审查实际差异,并允许工具更好地跟踪代码本身的历史。 + +在提交之前,使用补丁样式检查程序检查补丁(scripts/check patch.pl)。不过, +请注意,样式检查程序应该被视为一个指南,而不是作为人类判断的替代品。如果您 +的代码看起来更好,但有违规行为,那么最好不要使用它。 + +检查者报告三个级别: -4)选择 e-mail 的收件人 + - ERROR:很可能出错的事情 + - WARNING:需要仔细审查的事项 + - CHECK:需要思考的事情 -看一遍 MAINTAINERS 文件和源代码,看看你所的改动所在的内核子系统有没有指 -定的维护者。如果有,给他们发e-mail。 +您应该能够判断您的补丁中存在的所有违规行为。 -如果没有找到维护者,或者维护者没有反馈,将你的补丁发送到内核开发者主邮 -件列表 linux-kernel@vger.kernel.org。大部分的内核开发者都跟踪这个邮件列 -表,可以评价你的改动。 +5) 选择补丁收件人 +----------------- -每次不要发送超过15个补丁到 vger 邮件列表!!! +您应该总是在任何补丁上复制相应的子系统维护人员,以获得他们维护的代码;查看 +维护人员文件和源代码修订历史记录,以了解这些维护人员是谁。脚本 +scripts/get_Maintainer.pl在这个步骤中非常有用。如果您找不到正在工作的子系统 +的维护人员,那么Andrew Morton(akpm@linux-foundation.org)将充当最后的维护 +人员。 + +您通常还应该选择至少一个邮件列表来接收补丁集的。linux-kernel@vger.kernel.org +作为最后一个解决办法的列表,但是这个列表上的体积已经引起了许多开发人员的拒绝。 +在MAINTAINERS文件中查找子系统特定的列表;您的补丁可能会在那里得到更多的关注。 +不过,请不要发送垃圾邮件到无关的列表。 + +许多与内核相关的列表托管在vger.kernel.org上;您可以在 +http://vger.kernel.org/vger-lists.html 上找到它们的列表。不过,也有与内核相关 +的列表托管在其他地方。 + +不要一次发送超过15个补丁到vger邮件列表!!!! Linus Torvalds 是决定改动能否进入 Linux 内核的最终裁决者。他的 e-mail 地址是 。他收到的 e-mail 很多,所以一般 的说,最好别给他发 e-mail。 -那些修正bug,“显而易见”的修改或者是类似的只需要很少讨论的补丁可以直接 -发送或者CC给Linus。那些需要讨论或者没有很清楚的好处的补丁,一般先发送到 -linux-kernel邮件列表。只有当补丁被讨论得差不多了,才提交给Linus。 +如果您有修复可利用安全漏洞的补丁,请将该补丁发送到 security@kernel.org。对于 +严重的bug,可以考虑短期暂停以允许分销商向用户发布补丁;在这种情况下,显然不应 +将补丁发送到任何公共列表。 -5)选择CC( e-mail 抄送)列表 +修复已发布内核中严重错误的补丁程序应该指向稳定版维护人员,方法是放这样的一行:: -除非你有理由不这样做,否则CC linux-kernel@vger.kernel.org。 + Cc: stable@vger.kernel.org -除了 Linus 之外,其他内核开发者也需要注意到你的改动,这样他们才能评论你 -的改动并提供代码审查和建议。linux-kernel 是 Linux 内核开发者主邮件列表 -。其它的邮件列表为特定的子系统提供服务,比如 USB,framebuffer 设备,虚 -拟文件系统,SCSI 子系统,等等。查看 MAINTAINERS 文件来获得和你的改动有 -关的邮件列表。 +进入补丁的签准区(注意,不是电子邮件收件人)。除了这个文件之外,您还应该阅读 +:ref:`Documentation/process/stable-kernel-rules.rst ` -Majordomo lists of VGER.KERNEL.ORG at: - +但是,请注意,一些子系统维护人员希望得出他们自己的结论,即哪些补丁应该被放到 +稳定的树上。尤其是网络维护人员,不希望看到单个开发人员在补丁中添加像上面这样 +的行。 -如果改动影响了用户空间和内核之间的接口,请给 MAN-PAGES 的维护者(列在 -MAINTAINERS 文件里的)发送一个手册页(man-pages)补丁,或者至少通知一下改 -变,让一些信息有途径进入手册页。 +如果更改影响到用户和内核接口,请向手册页维护人员(如维护人员文件中所列)发送 +手册页补丁,或至少发送更改通知,以便一些信息进入手册页。还应将用户空间API +更改复制到 linux-api@vger.kernel.org。 -即使在第四步的时候,维护者没有作出回应,也要确认在修改他们的代码的时候 -,一直将维护者拷贝到CC列表中。 +对于小的补丁,你也许会CC到搜集琐碎补丁的邮件列表(Trivial Patch Monkey) +trivial@kernel.org,那里专门收集琐碎的补丁。下面这样的补丁会被看作“琐碎的” +补丁: -对于小的补丁,你也许会CC到 Adrian Bunk 管理的搜集琐碎补丁的邮件列表 -(Trivial Patch Monkey)trivial@kernel.org,那里专门收集琐碎的补丁。下面这样 -的补丁会被看作“琐碎的”补丁: - - 文档的拼写修正。 - 修正会影响到 grep(1) 的拼写。 - 警告信息修正(频繁的打印无用的警告是不好的。) - 编译错误修正(代码逻辑的确是对的,只是编译有问题。) - 运行时修正(只要真的修正了错误。) - 移除使用了被废弃的函数/宏的代码(例如 check_region。) - 联系方式和文档修正。 - 用可移植的代码替换不可移植的代码(即使在体系结构相关的代码中,既然有 - 人拷贝,只要它是琐碎的) - 任何文件的作者/维护者对该文件的改动(例如 patch monkey 在重传模式下) - -EMAIL: trivial@kernel.org + - 文档的拼写修正。 + - 修正会影响到 grep(1) 的拼写。 + - 警告信息修正(频繁的打印无用的警告是不好的。) + - 编译错误修正(代码逻辑的确是对的,只是编译有问题。) + - 运行时修正(只要真的修正了错误。) + - 移除使用了被废弃的函数/宏的代码(例如 check_region。) + - 联系方式和文档修正。 + - 用可移植的代码替换不可移植的代码(即使在体系结构相关的代码中,既然有 + - 人拷贝,只要它是琐碎的) + - 任何文件的作者/维护者对该文件的改动(例如 patch monkey 在重传模式下) (译注,关于“琐碎补丁”的一些说明:因为原文的这一部分写得比较简单,所以不得不 违例写一下译注。"trivial"这个英文单词的本意是“琐碎的,不重要的。”但是在这里 @@ -164,100 +279,92 @@ EMAIL: trivial@kernel.org trivial@kernel.org邮件列表的目的是针对这样的补丁,为提交者提供一个中心,来 降低提交的门槛。) -6)没有 MIME 编码,没有链接,没有压缩,没有附件,只有纯文本。 +6) 没有 MIME 编码,没有链接,没有压缩,没有附件,只有纯文本 +----------------------------------------------------------- Linus 和其他的内核开发者需要阅读和评论你提交的改动。对于内核开发者来说 ,可以“引用”你的改动很重要,使用一般的 e-mail 工具,他们就可以在你的 代码的任何位置添加评论。 因为这个原因,所有的提交的补丁都是 e-mail 中“内嵌”的。 -警告:如果你使用剪切-粘贴你的补丁,小心你的编辑器的自动换行功能破坏你的 -补丁。 + +.. warning:: + 如果你使用剪切-粘贴你的补丁,小心你的编辑器的自动换行功能破坏你的补丁 不要将补丁作为 MIME 编码的附件,不管是否压缩。很多流行的 e-mail 软件不 是任何时候都将 MIME 编码的附件当作纯文本发送的,这会使得别人无法在你的 代码中加评论。另外,MIME 编码的附件会让 Linus 多花一点时间来处理,这就 降低了你的改动被接受的可能性。 -警告:一些邮件软件,比如 Mozilla 会将你的信息以如下格式发送: ----- 邮件头 ---- -Content-Type: text/plain; charset=us-ascii; format=flowed ----- 邮件头 ---- -问题在于 “format=flowed” 会让接收端的某些邮件软件将邮件中的制表符替换 -成空格以及做一些类似的替换。这样,你发送的时候看起来没问题的补丁就被破 -坏了。 - -要修正这个问题,只需要将你的 mozilla 的 defaults/pref/mailnews.js 文件 -里的 -pref("mailnews.send_plaintext_flowed", false); // RFC 2646======= -修改成 -pref("mailnews.display.disable_format_flowed_support", true); -就可以了。 +例外:如果你的邮递员弄坏了补丁,那么有人可能会要求你使用mime重新发送补丁 -7) e-mail 的大小 +请参阅 :ref:`Documentation/process/e-mail-clients.rst ` +以获取有关配置电子邮件客户端以使其不受影响地发送修补程序的提示。 -给 Linus 发送补丁的时候,永远按照第6小节说的做。 +7) e-mail 的大小 +---------------- 大的改动对邮件列表不合适,对某些维护者也不合适。如果你的补丁,在不压缩 -的情况下,超过了40kB,那么你最好将补丁放在一个能通过 internet 访问的服 -务器上,然后用指向你的补丁的 URL 替代。 +的情况下,超过了300kB,那么你最好将补丁放在一个能通过 internet 访问的服 +务器上,然后用指向你的补丁的 URL 替代。但是请注意,如果您的补丁超过了 +300kb,那么它几乎肯定需要被破坏。 -8) 指出你的内核版本 +8)回复评审意见 +--------------- -在标题和在补丁的描述中,指出补丁对应的内核的版本,是很重要的。 +你的补丁几乎肯定会得到评审者对补丁改进方法的评论。您必须对这些评论作出 +回应;让补丁被忽略的一个好办法就是忽略审阅者的意见。不会导致代码更改的 +意见或问题几乎肯定会带来注释或变更日志的改变,以便下一个评审者更好地了解 +正在发生的事情。 -如果补丁不能干净的在最新版本的内核上打上,Linus 是不会接受它的。 +一定要告诉审稿人你在做什么改变,并感谢他们的时间。代码审查是一个累人且 +耗时的过程,审查人员有时会变得暴躁。即使在这种情况下,也要礼貌地回应并 +解决他们指出的问题。 -9) 不要气馁,继续提交。 +9)不要泄气或不耐烦 +------------------- -当你提交了改动以后,耐心地等待。如果 Linus 喜欢你的改动并且同意它,那么 -它将在下一个内核发布版本中出现。 +提交更改后,请耐心等待。审阅者是忙碌的人,可能无法立即访问您的修补程序。 -然而,如果你的改动没有出现在下一个版本的内核中,可能有若干原因。减少那 -些原因,修正错误,重新提交更新后的改动,是你自己的工作。 +曾几何时,补丁曾在没有评论的情况下消失在空白中,但开发过程比现在更加顺利。 +您应该在一周左右的时间内收到评论;如果没有收到评论,请确保您已将补丁发送 +到正确的位置。在重新提交或联系审阅者之前至少等待一周-在诸如合并窗口之类的 +繁忙时间可能更长。 -Linus不给出任何评论就“丢弃”你的补丁是常见的事情。在系统中这样的事情很 -平常。如果他没有接受你的补丁,也许是由于以下原因: -* 你的补丁不能在最新版本的内核上干净的打上。 -* 你的补丁在 linux-kernel 邮件列表中没有得到充分的讨论。 -* 风格问题(参照第2小节) -* 邮件格式问题(重读本节) -* 你的改动有技术问题。 -* 他收到了成吨的 e-mail,而你的在混乱中丢失了。 -* 你让人为难。 +10)主题中包含 PATCH +-------------------- -有疑问的时候,在 linux-kernel 邮件列表上请求评论。 +由于到linus和linux内核的电子邮件流量很高,通常会在主题行前面加上[PATCH] +前缀. 这使Linus和其他内核开发人员更容易将补丁与其他电子邮件讨论区分开。 -10) 在标题上加上 PATCH 的字样 - -Linus 和 linux-kernel 邮件列表的 e-mail 流量都很高,一个通常的约定是标 -题行以 [PATCH] 开头。这样可以让 Linus 和其他内核开发人员可以从 e-mail -的讨论中很轻易的将补丁分辨出来。 - -11)为你的工作签名 +11)签署你的作品-开发者原始认证 +------------------------------- 为了加强对谁做了何事的追踪,尤其是对那些透过好几层的维护者的补丁,我们 建议在发送出去的补丁上加一个 “sign-off” 的过程。 "sign-off" 是在补丁的注释的最后的简单的一行文字,认证你编写了它或者其他 -人有权力将它作为开放源代码的补丁传递。规则很简单:如果你能认证如下信息 -: +人有权力将它作为开放源代码的补丁传递。规则很简单:如果你能认证如下信息: + 开发者来源证书 1.1 ^^^^^^^^^^^^^^^^^^ + 对于本项目的贡献,我认证如下信息: (a)这些贡献是完全或者部分的由我创建,我有权利以文件中指出 - 的开放源代码许可证提交它;或者 + 的开放源代码许可证提交它;或者 (b)这些贡献基于以前的工作,据我所知,这些以前的工作受恰当的开放 - 源代码许可证保护,而且,根据许可证,我有权提交修改后的贡献, - 无论是完全还是部分由我创造,这些贡献都使用同一个开放源代码许可证 - (除非我被允许用其它的许可证),正如文件中指出的;或者 + 源代码许可证保护,而且,根据许可证,我有权提交修改后的贡献, + 无论是完全还是部分由我创造,这些贡献都使用同一个开放源代码许可证 + (除非我被允许用其它的许可证),正如文件中指出的;或者 (c)这些贡献由认证(a),(b)或者(c)的人直接提供给我,而 - 且我没有修改它。 + 且我没有修改它。 (d)我理解并同意这个项目和贡献是公开的,贡献的记录(包括我 - 一起提交的个人记录,包括 sign-off )被永久维护并且可以和这个项目 - 或者开放源代码的许可证同步地再发行。 - 那么加入这样一行: + 一起提交的个人记录,包括 sign-off )被永久维护并且可以和这个项目 + 或者开放源代码的许可证同步地再发行。 + +那么加入这样一行:: + Signed-off-by: Random J Developer 使用你的真名(抱歉,不能使用假名或者匿名。) @@ -265,24 +372,141 @@ Linus 和 linux-kernel 邮件列表的 e-mail 流量都很高,一个通常的 有人在最后加上标签。现在这些东西会被忽略,但是你可以这样做,来标记公司 内部的过程,或者只是指出关于 sign-off 的一些特殊细节。 +如果您是子系统或分支维护人员,有时需要稍微修改收到的补丁,以便合并它们, +因为树和提交者中的代码不完全相同。如果你严格遵守规则(c),你应该要求提交者 +重新发布,但这完全是在浪费时间和精力。规则(b)允许您调整代码,但是更改一个 +提交者的代码并让他认可您的错误是非常不礼貌的。要解决此问题,建议在最后一个 +由签名行和您的行之间添加一行,指示更改的性质。虽然这并不是强制性的,但似乎 +在描述前加上您的邮件和/或姓名(全部用方括号括起来),这足以让人注意到您对最 +后一分钟的更改负有责任。例如:: + + Signed-off-by: Random J Developer + [lucky@maintainer.example.org: struct foo moved from foo.c to foo.h] + Signed-off-by: Lucky K Maintainer + +如果您维护一个稳定的分支机构,同时希望对作者进行致谢、跟踪更改、合并修复并 +保护提交者不受投诉,那么这种做法尤其有用。请注意,在任何情况下都不能更改作者 +的ID(From 头),因为它是出现在更改日志中的标识。 + +对回合(back-porters)的特别说明:在提交消息的顶部(主题行之后)插入一个补丁 +的起源指示似乎是一种常见且有用的实践,以便于跟踪。例如,下面是我们在3.x稳定 +版本中看到的内容:: + + Date: Tue Oct 7 07:26:38 2014 -0400 + + libata: Un-break ATA blacklist + + commit 1c40279960bcd7d52dbdf1d466b20d24b99176c8 upstream. + +还有, 这里是一个旧版内核中的一个回合补丁:: + + Date: Tue May 13 22:12:27 2008 +0200 + + wireless, airo: waitbusy() won't delay + + [backport of 2.6 commit b7acbdfbd1f277c1eb23f344f899cfa4cd0bf36a] + +12)何时使用Acked-by:,CC:,和Co-Developed by: +---------------------------------------------- + +Singed-off-by: 标记表示签名者参与了补丁的开发,或者他/她在补丁的传递路径中。 + +如果一个人没有直接参与补丁的准备或处理,但希望表示并记录他们对补丁的批准, +那么他们可以要求在补丁的变更日志中添加一个 Acked-by: + +Acked-by:通常由受影响代码的维护者使用,当该维护者既没有贡献也没有转发补丁时。 + +Acked-by: 不像签字人那样正式。这是一个记录,确认人至少审查了补丁,并表示接受。 +因此,补丁合并有时会手动将Acker的“Yep,looks good to me”转换为 Acked-By:(但 +请注意,通常最好要求一个明确的Ack)。 + +Acked-by:不一定表示对整个补丁的确认。例如,如果一个补丁影响多个子系统,并且 +有一个:来自一个子系统维护者,那么这通常表示只确认影响维护者代码的部分。这里 +应该仔细判断。如有疑问,应参考邮件列表档案中的原始讨论。 + +如果某人有机会对补丁进行评论,但没有提供此类评论,您可以选择在补丁中添加 ``Cc:`` +这是唯一一个标签,它可以在没有被它命名的人显式操作的情况下添加,但它应该表明 +这个人是在补丁上抄送的。讨论中包含了潜在利益相关方。 + +Co-developed-by: 声明补丁也是由另一个开发人员和原始作者一起创建的。当多个人 +在一个补丁上工作时,这很有用。注意,此人也需要在补丁中有一个 Signed-off-by: + +13)使用报告人:、测试人:、审核人:、建议人:、修复人: +-------------------------------------------------------- + +Reported-by: 给那些发现错误并报告错误的人致谢,它希望激励他们在将来再次帮助 +我们。请注意,如果bug是以私有方式报告的,那么在使用Reported-by标记之前,请 +先请求权限。 + +Tested-by: 标记表示补丁已由指定的人(在某些环境中)成功测试。这个标签通知 +维护人员已经执行了一些测试,为将来的补丁提供了一种定位测试人员的方法,并确 +保测试人员的信誉。 + +Reviewed-by:相反,根据审查人的声明,表明该补丁已被审查并被认为是可接受的: + + +审查人的监督声明 +^^^^^^^^^^^^^^^^ + +通过提供我的 Reviewed-by,我声明: + + (a) 我已经对这个补丁进行了一次技术审查,以评估它是否适合被包含到 + 主线内核中。 + + (b) 与补丁相关的任何问题、顾虑或问题都已反馈给提交者。我对提交者对 + 我的评论的回应感到满意。 + + (c) 虽然这一提交可能会改进一些东西,但我相信,此时,(1)对内核 + 进行了有价值的修改,(2)没有包含争论中涉及的已知问题。 + + (d) 虽然我已经审查了补丁并认为它是健全的,但我不会(除非另有明确 + 说明)作出任何保证或保证它将在任何给定情况下实现其规定的目的 + 或正常运行。 + +Reviewed-by 是一种观点声明,即补丁是对内核的适当修改,没有任何遗留的严重技术 +问题。任何感兴趣的审阅者(完成工作的人)都可以为一个补丁提供一个 Review-by +标签。此标签用于向审阅者提供致谢,并通知维护者已在修补程序上完成的审阅程度。 +Reviewed-by: 当由已知了解主题区域并执行彻底检查的审阅者提供时,通常会增加 +补丁进入内核的可能性。 + +Suggested-by: 表示补丁的想法是由指定的人提出的,并确保将此想法归功于指定的 +人。请注意,未经许可,不得添加此标签,特别是如果该想法未在公共论坛上发布。 +这就是说,如果我们勤快地致谢我们的创意者,他们很有希望在未来得到鼓舞,再次 +帮助我们。 + +Fixes: 指示补丁在以前的提交中修复了一个问题。它可以很容易地确定错误的来源, +这有助于检查错误修复。这个标记还帮助稳定内核团队确定应该接收修复的稳定内核 +版本。这是指示补丁修复的错误的首选方法。请参阅 :ref:`cn_describe_changes` +描述您的更改以了解更多详细信息。 + +.. _cn_the_canonical_patch_format: + 12)标准补丁格式 +---------------- + +本节描述如何格式化补丁本身。请注意,如果您的补丁存储在 ``Git`` 存储库中,则 +可以使用 ``git format-patch`` 进行正确的补丁格式设置。但是,这些工具无法创建 +必要的文本,因此请务必阅读下面的说明。 + +标准的补丁,标题行是:: -标准的补丁,标题行是: Subject: [PATCH 001/123] 子系统:一句话概述 标准补丁的信体存在如下部分: - - 一个 "from" 行指出补丁作者。 + - 一个 "from" 行指出补丁作者。后跟空行(仅当发送修补程序的人不是作者时才需要)。 + + - 解释的正文,行以75列包装,这将被复制到永久变更日志来描述这个补丁。 - 一个空行 - - 说明的主体,这些说明文字会被拷贝到描述该补丁的永久改动记录里。 + - 上面描述的“Signed-off-by” 行,也将出现在更改日志中。 - - 一个由"---"构成的标记行 + - 只包含 ``---`` 的标记线。 - - 不合适放到改动记录里的额外的注解。 + - 任何其他不适合放在变更日志的注释。 - - 补丁本身(diff 输出) + - 实际补丁( ``diff`` 输出)。 标题行的格式,使得对标题行按字母序排序非常的容易 - 很多 e-mail 客户端都 可以支持 - 因为序列号是用零填充的,所以按数字排序和按字母排序是一样的。 @@ -296,21 +520,35 @@ e-mail 标题中的“一句话概述”扼要的描述 e-mail 中的补丁。 记住 e-mail 的“一句话概述”会成为该补丁的全局唯一标识。它会蔓延到 git 的改动记录里。然后“一句话概述”会被用在开发者的讨论里,用来指代这个补 丁。用户将希望通过 google 来搜索"一句话概述"来找到那些讨论这个补丁的文 -章。 +章。当人们在两三个月后使用诸如 ``gitk`` 或 ``git log --oneline`` 之类 +的工具查看数千个补丁时,也会很快看到它。 + +出于这些原因,概述必须不超过70-75个字符,并且必须描述补丁的更改以及为 +什么需要补丁。既要简洁又要描述性很有挑战性,但写得好的概述应该这样做。 + +概述的前缀可以用方括号括起来:“Subject: [PATCH ...] <概述>”。标记 +不被视为概述的一部分,而是描述应该如何处理补丁。如果补丁的多个版本已发 +送出来以响应评审(即“v1,v2,v3”)或“rfc”,以指示评审请求,那么通用标记 +可能包括版本描述符。如果一个补丁系列中有四个补丁,那么各个补丁可以这样 +编号:1/4、2/4、3/4、4/4。这可以确保开发人员了解补丁应用的顺序,并且他们 +已经查看或应用了补丁系列中的所有补丁。 一些标题的例子:: Subject: [patch 2/5] ext2: improve scalability of bitmap searching Subject: [PATCHv2 001/207] x86: fix eflags tracking -"from" 行是信体里的最上面一行,具有如下格式: +"From" 行是信体里的最上面一行,具有如下格式: From: Original Author -"from" 行指明在永久改动日志里,谁会被确认为作者。如果没有 "from" 行,那 +"From" 行指明在永久改动日志里,谁会被确认为作者。如果没有 "From" 行,那 么邮件头里的 "From: " 行会被用来决定改动日志中的作者。 说明的主题将会被提交到永久的源代码改动日志里,因此对那些早已经不记得和 -这个补丁相关的讨论细节的有能力的读者来说,是有意义的。 +这个补丁相关的讨论细节的有能力的读者来说,是有意义的。包括补丁程序定位 +错误的(内核日志消息、OOPS消息等)症状,对于搜索提交日志以寻找适用补丁的人 +尤其有用。如果一个补丁修复了一个编译失败,那么可能不需要包含所有编译失败; +只要足够让搜索补丁的人能够找到它就行了。与概述一样,既要简洁又要描述性。 "---" 标记行对于补丁处理工具要找到哪里是改动日志信息的结束,是不可缺少 的。 @@ -324,65 +562,63 @@ e-mail 标题中的“一句话概述”扼要的描述 e-mail 中的补丁。 在后面的参考资料中能看到适当的补丁格式的更多细节。 -------------------------------- -第二节 提示,建议和诀窍 -------------------------------- +.. _cn_explicit_in_reply_to: -本节包含很多和提交到内核的代码有关的通常的"规则"。事情永远有例外...但是 -你必须真的有好的理由这样做。你可以把本节叫做Linus的计算机科学入门课。 +15) 明确回复邮件头(In-Reply-To) +------------------------------- -1) 读 Document/process/coding-style.rst +手动添加回复补丁的的标题头(In-Reply_To:) 是有帮助的(例如,使用 ``git send-email`` ) +将补丁与以前的相关讨论关联起来,例如,将bug修复程序链接到电子邮件和bug报告。 +但是,对于多补丁系列,最好避免在回复时使用链接到该系列的旧版本。这样, +补丁的多个版本就不会成为电子邮件客户端中无法管理的引用序列。如果链接有用, +可以使用 https://lkml.kernel.org/ 重定向器(例如,在封面电子邮件文本中) +链接到补丁系列的早期版本。 -Nuff 说过,如果你的代码和这个偏离太多,那么它有可能会被拒绝,没有更多的 -审查,没有更多的评价。 +16) 发送git pull请求 +-------------------- -2) #ifdef 是丑陋的 -混杂了 ifdef 的代码难以阅读和维护。别这样做。作为替代,将你的 ifdef 放 -在头文件里,有条件地定义 "static inline" 函数,或者宏,在代码里用这些东 -西。让编译器把那些"空操作"优化掉。 +如果您有一系列补丁,那么让维护人员通过git pull操作将它们直接拉入子系统存储 +库可能是最方便的。但是,请注意,从开发人员那里获取补丁比从邮件列表中获取补 +丁需要更高的信任度。因此,许多子系统维护人员不愿意接受请求,特别是来自新的 +未知开发人员的请求。如果有疑问,您可以在封面邮件中使用pull 请求作为补丁系列 +正常发布的一个选项,让维护人员可以选择使用其中之一。 -一个简单的例子,不好的代码:: +pull 请求的主题行中应该有[Git Pull]。请求本身应该在一行中包含存储库名称和 +感兴趣的分支;它应该看起来像:: - dev = alloc_etherdev (sizeof(struct funky_private)); - if (!dev) - return -ENODEV; - #ifdef CONFIG_NET_FUNKINESS - init_funky_net(dev); - #endif + Please pull from -清理后的例子: + git://jdelvare.pck.nerim.net/jdelvare-2.6 i2c-for-linus -(头文件里):: + to get these changes: - #ifndef CONFIG_NET_FUNKINESS - static inline void init_funky_net (struct net_device *d) {} - #endif -(代码文件里):: +pull 请求还应该包含一条整体消息,说明请求中将包含什么,一个补丁本身的 ``Git shortlog`` +以及一个显示补丁系列整体效果的 ``diffstat`` 。当然,将所有这些信息收集在一起 +的最简单方法是让 ``git`` 使用 ``git request-pull`` 命令为您完成这些工作。 - dev = alloc_etherdev (sizeof(struct funky_private)); - if (!dev) - return -ENODEV; - init_funky_net(dev); +一些维护人员(包括Linus)希望看到来自已签名提交的请求;这增加了他们对你的 +请求信心。特别是,在没有签名标签的情况下,Linus 不会从像 Github 这样的公共 +托管站点拉请求。 -3) 'static inline' 比宏好 +创建此类签名的第一步是生成一个 GNRPG 密钥,并由一个或多个核心内核开发人员对 +其进行签名。这一步对新开发人员来说可能很困难,但没有办法绕过它。参加会议是 +找到可以签署您的密钥的开发人员的好方法。 -Static inline 函数相比宏来说,是好得多的选择。Static inline 函数提供了 -类型安全,没有长度限制,没有格式限制,在 gcc 下开销和宏一样小。 +一旦您在Git 中准备了一个您希望有人拉的补丁系列,就用 ``git tag -s`` 创建一 +个签名标记。这将创建一个新标记,标识该系列中的最后一次提交,并包含用您的私 +钥创建的签名。您还可以将changelog样式的消息添加到标记中;这是一个描述拉请求 +整体效果的理想位置。 -宏只在 static inline 函数不是最优的时候[在 fast paths 里有很少的独立的 -案例],或者不可能用 static inline 函数的时候[例如字符串分配]。 -应该用 'static inline' 而不是 'static __inline__', 'extern inline' 和 -'extern __inline__' 。 +如果维护人员将要从中提取的树不是您正在使用的存储库,请不要忘记将已签名的标记 +显式推送到公共树。 -4) 不要过度设计 +生成拉请求时,请使用已签名的标记作为目标。这样的命令可以实现:: -不要试图预计模糊的未来事情,这些事情也许有用也许没有用:"让事情尽可能的 -简单,而不是更简单"。 + git request-pull master git://my.public.tree/linux.git my-signed-tag ----------------- -第三节 参考文献 ----------------- +参考文献 +-------- Andrew Morton, "The perfect patch" (tpp). @@ -391,16 +627,28 @@ Jeff Garzik, "Linux kernel patch submission format". Greg Kroah-Hartman, "How to piss off a kernel subsystem maintainer". - - - - + + + + + + + + + + + NO!!!! No more huge patch bombs to linux-kernel@vger.kernel.org people! Kernel Documentation/process/coding-style.rst: - + :ref:`Documentation/process/coding-style.rst ` Linus Torvalds's mail on the canonical patch format: + +Andi Kleen, "On submitting kernel patches" + Some strategies to get difficult or controversial changes in. + + http://halobates.de/on-submitting-patches.pdf -- cgit v1.2.3 From 1cc9990f528ddae93c25d454dbf8e38336cfde12 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:46 +0800 Subject: docs/zh_CN: update translator info in submitting-patches Add Alex as the 2nd translator, and remove duplicated infos. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Tom Levy Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/submitting-patches.rst | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/submitting-patches.rst b/Documentation/translations/zh_CN/process/submitting-patches.rst index 5fa716584598..f6e609b242e7 100644 --- a/Documentation/translations/zh_CN/process/submitting-patches.rst +++ b/Documentation/translations/zh_CN/process/submitting-patches.rst @@ -4,12 +4,11 @@ :Original: :ref:`Documentation/process/submitting-patches.rst ` -如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 -交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者:: +译者:: 中文版维护者: 钟宇 TripleX Chung 中文版翻译者: 钟宇 TripleX Chung + 时奎亮 Alex Shi 中文版校译者: 李阳 Li Yang 王聪 Wang Cong -- cgit v1.2.3 From 6db147a8bb89f62304ce5f0b30bf80ce9b2ea7cb Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:47 +0800 Subject: docs/zh_CN: redirect the submitting-patches to Chinese doc Now we have latest Chinese version submitting-patches.rst, it's time to use it in other docs. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Federico Vaga Cc: SeongJae Park Cc: James Morris Cc: Mauro Carvalho Chehab Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/5.Posting.rst | 11 ++++++----- Documentation/translations/zh_CN/process/8.Conclusion.rst | 6 +++--- Documentation/translations/zh_CN/process/howto.rst | 4 ++-- .../translations/zh_CN/process/stable-kernel-rules.rst | 2 +- Documentation/translations/zh_CN/process/submit-checklist.rst | 2 +- .../translations/zh_CN/process/submitting-drivers.rst | 2 +- 6 files changed, 14 insertions(+), 13 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/5.Posting.rst b/Documentation/translations/zh_CN/process/5.Posting.rst index c19b6ca57b8c..ae185114148b 100644 --- a/Documentation/translations/zh_CN/process/5.Posting.rst +++ b/Documentation/translations/zh_CN/process/5.Posting.rst @@ -12,7 +12,7 @@ 内核开发社区已经发展出一套用于发布补丁的约定和过程;遵循这些约定和过程将使 参与其中的每个人的生活更加轻松。本文件将试图合理详细地涵盖这些期望;更多信息 也可在以下文件中找到 -:ref:`Documentation/process/submitting-patches.rst `, +:ref:`Documentation/translations/zh_CN/process/submitting-patches.rst `, :ref:`Documentation/process/submitting-drivers.rst ` 和 :ref:`Documentation/process/submit-checklist.rst `. @@ -145,7 +145,7 @@ bug搜寻人员想知道补丁是否负责他们正在追查的问题,想知 其传递给diff。 上面提到的标签用于描述各种开发人员如何与这个补丁的开发相关联。 -:ref:`documentation/process/submitting-patches.rst ` +:ref:`Documentation/translations/zh_CN/process/submitting-patches.rst ` 文档中对它们进行了详细描述;下面是一个简短的总结。每一行的格式如下: :: @@ -155,7 +155,8 @@ bug搜寻人员想知道补丁是否负责他们正在追查的问题,想知 常用的标签有: - Signed-off-by: 这是一个开发人员的证明,他或她有权提交补丁以包含到内核中。 - 这是开发来源认证协议,其全文可在:ref:`documentation/process/submitting-patches.rst ` + 这是开发来源认证协议,其全文可在 + :ref:`Documentation/translations/zh_CN/process/submitting-patches.rst ` 中找到,如果没有适当的签字,则不能合并到主线中。 - Co-developed-by: 声明补丁也是由另一个开发人员和原始作者一起创建的。当多 @@ -167,7 +168,7 @@ bug搜寻人员想知道补丁是否负责他们正在追查的问题,想知 - Tested-by: 声明指定的人已经测试了补丁并发现它可以工作。 - Reviewed-by: 指定的开发人员已经审查了补丁的正确性;有关详细信息,请参阅 - :ref:`documentation/process/submitting-patches.rst ` + :ref:`Documentation/translations/zh_CN/process/submitting-patches.rst ` - Reported-by: 指定报告此补丁修复的问题的用户;此标记用于提供感谢。 @@ -209,7 +210,7 @@ bug搜寻人员想知道补丁是否负责他们正在追查的问题,想知 - 将副本发送到相关邮件列表,或者,如果没有其他应用,则发送到Linux内核列表。 - 如果您正在修复一个bug,请考虑该修复是否应进入下一个稳定更新。如果是这样, - stable@vger.kernel.org应该得到补丁的副本。另外,在补丁本身的标签中添加 + stable@vger.kernel.org 应该得到补丁的副本。另外,在补丁本身的标签中添加 一个“cc:stable@vger.kernel.org”;这将使稳定团队在修复进入主线时收到通知。 当为一个补丁选择接收者时,最好知道你认为谁最终会接受这个补丁并将其合并。虽然 diff --git a/Documentation/translations/zh_CN/process/8.Conclusion.rst b/Documentation/translations/zh_CN/process/8.Conclusion.rst index c164edc34687..2bbd76161e10 100644 --- a/Documentation/translations/zh_CN/process/8.Conclusion.rst +++ b/Documentation/translations/zh_CN/process/8.Conclusion.rst @@ -11,13 +11,13 @@ 关于Linux内核开发和相关主题的信息来源很多。首先是在内核源代码分发中找到的 文档目录。顶级 :ref:`Documentation/translations/zh_CN/process/howto.rst ` 文件是一个重要的起点 -:ref:`process/submitting-patches.rst ` -和:ref:`process/submitting-drivers.rst ` +:ref:`Documentation/translations/zh_CN/process/submitting-patches.rst ` +和 :ref:`process/submitting-drivers.rst ` 也是所有内核开发人员都应该阅读的内容。许多内部内核API都是使用kerneldoc机制 记录的;“make htmldocs”或“make pdfdocs”可用于以HTML或PDF格式生成这些文档( 尽管某些发行版提供的tex版本会遇到内部限制,无法正确处理文档)。 -不同的网站在各个细节层次上讨论内核开发。您的作者想谦虚地建议用http://lwn.net/ +不同的网站在各个细节层次上讨论内核开发。您的作者想谦虚地建议用 http://lwn.net/ 作为来源;有关许多特定内核主题的信息可以通过以下网址的lwn内核索引找到: http://lwn.net/kernel/index/ diff --git a/Documentation/translations/zh_CN/process/howto.rst b/Documentation/translations/zh_CN/process/howto.rst index 980d53e9612c..f52bb011cb2c 100644 --- a/Documentation/translations/zh_CN/process/howto.rst +++ b/Documentation/translations/zh_CN/process/howto.rst @@ -95,7 +95,7 @@ Linux内核代码中包含有大量的文档。这些文档对于学习如何与 范。大多数维护者只会接收符合规定的补丁,很多人也只会帮忙检查符合风格 的代码。 - :ref:`Documentation/process/submitting-patches.rst ` + :ref:`Documentation/translations/zh_CN/process/submitting-patches.rst ` :ref:`Documentation/process/submitting-drivers.rst ` 这两份文档明确描述如何创建和发送补丁,其中包括(但不仅限于): @@ -328,7 +328,7 @@ MAINTAINERS文件中可以找到不同话题对应的邮件列表。 这几行。将你的评论加在被引用的段落之间而不要放在邮件的顶部。 如果你在邮件中附带补丁,请确认它们是可以直接阅读的纯文本(如 -:ref:`Documentation/process/submitting-patches.rst ` +:ref:`Documentation/translations/zh_CN/process/submitting-patches.rst ` 文档中所述)。内核开发者们不希望遇到附件或者被压缩了的补丁。只有这样才能 保证他们可以直接评论你的每行代码。请确保你使用的邮件发送程序不会修改空格 和制表符。一个防范性的测试方法是先将邮件发送给自己,然后自己尝试是否可以 diff --git a/Documentation/translations/zh_CN/process/stable-kernel-rules.rst b/Documentation/translations/zh_CN/process/stable-kernel-rules.rst index fb048c42ae48..fba361f2ddfd 100644 --- a/Documentation/translations/zh_CN/process/stable-kernel-rules.rst +++ b/Documentation/translations/zh_CN/process/stable-kernel-rules.rst @@ -33,7 +33,7 @@ - 没有“理论上的竞争条件”,除非能给出竞争条件如何被利用的解释。 - 不能存在任何的“琐碎的”修正(拼写修正,去掉多余空格之类的)。 - 必须被相关子系统的维护者接受。 - - 必须遵循Documentation/process/submitting-patches.rst里的规则。 + - 必须遵循Documentation/translations/zh_CN/process/submitting-patches.rst里的规则。 向稳定版代码树提交补丁的过程: ------------------------------ diff --git a/Documentation/translations/zh_CN/process/submit-checklist.rst b/Documentation/translations/zh_CN/process/submit-checklist.rst index 9ee1cb4cdab6..c931273e1487 100644 --- a/Documentation/translations/zh_CN/process/submit-checklist.rst +++ b/Documentation/translations/zh_CN/process/submit-checklist.rst @@ -12,7 +12,7 @@ Linux内核补丁提交清单 的事情。 这些都是在 -:ref:`Documentation/process/submitting-patches.rst ` +:ref:`Documentation/translations/zh_CN/process/submitting-patches.rst ` 和其他有关提交Linux内核补丁的文档中提供的。 1) 如果使用工具,则包括定义/声明该工具的文件。不要依赖于其他头文件拉入您使用 diff --git a/Documentation/translations/zh_CN/process/submitting-drivers.rst b/Documentation/translations/zh_CN/process/submitting-drivers.rst index 3be51d998c80..72c6cd935821 100644 --- a/Documentation/translations/zh_CN/process/submitting-drivers.rst +++ b/Documentation/translations/zh_CN/process/submitting-drivers.rst @@ -22,7 +22,7 @@ 兴趣的是显卡驱动程序,你也许应该访问 XFree86 项目(http://www.xfree86.org/) 和/或 X.org 项目 (http://x.org)。 -另请参阅 Documentation/process/submitting-patches.rst 文档。 +另请参阅 Documentation/Documentation/translations/zh_CN/process/submitting-patches.rst 文档。 分配设备号 -- cgit v1.2.3 From c0099c97dabaf68442502ce3af570d2df137eeaa Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:48 +0800 Subject: docs/zh_CN: redirect submit-checklist Now we has the Chinese version submit-checklist, so redirect it in Chinese docs. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Tom Levy Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/5.Posting.rst | 2 +- Documentation/translations/zh_CN/process/submitting-patches.rst | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/5.Posting.rst b/Documentation/translations/zh_CN/process/5.Posting.rst index ae185114148b..19a042170f36 100644 --- a/Documentation/translations/zh_CN/process/5.Posting.rst +++ b/Documentation/translations/zh_CN/process/5.Posting.rst @@ -14,7 +14,7 @@ 也可在以下文件中找到 :ref:`Documentation/translations/zh_CN/process/submitting-patches.rst `, :ref:`Documentation/process/submitting-drivers.rst ` -和 :ref:`Documentation/process/submit-checklist.rst `. +和 :ref:`Documentation/translations/zh_CN/process/submit-checklist.rst `. 何时邮寄 -------- diff --git a/Documentation/translations/zh_CN/process/submitting-patches.rst b/Documentation/translations/zh_CN/process/submitting-patches.rst index f6e609b242e7..93239649fb71 100644 --- a/Documentation/translations/zh_CN/process/submitting-patches.rst +++ b/Documentation/translations/zh_CN/process/submitting-patches.rst @@ -22,7 +22,7 @@ 以下文档含有大量简洁的建议, 具体请见: :ref:`Documentation/process ` -同样,:ref:`Documentation/process/submit-checklist.rst ` +同样,:ref:`Documentation/translations/zh_CN/process/submit-checklist.rst ` 给出在提交代码前需要检查的项目的列表。如果你在提交一个驱动程序,那么 同时阅读一下: :ref:`Documentation/process/submitting-drivers.rst ` -- cgit v1.2.3 From 08075b0b1104d630621899840013ec94634774cb Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:49 +0800 Subject: docs/zh_CN: update co-developed-by info after English version commit 24a2bb90741b ("docs: Clarify the usage and sign-off requirements for Co-developed-by") give more info of co-developed-by tag usage. update Chinese docs to follow it. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Tom Levy Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- .../translations/zh_CN/process/5.Posting.rst | 7 +++-- .../zh_CN/process/submitting-patches.rst | 35 ++++++++++++++++++++-- 2 files changed, 37 insertions(+), 5 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/5.Posting.rst b/Documentation/translations/zh_CN/process/5.Posting.rst index 19a042170f36..12a9324d4b1a 100644 --- a/Documentation/translations/zh_CN/process/5.Posting.rst +++ b/Documentation/translations/zh_CN/process/5.Posting.rst @@ -159,8 +159,11 @@ bug搜寻人员想知道补丁是否负责他们正在追查的问题,想知 :ref:`Documentation/translations/zh_CN/process/submitting-patches.rst ` 中找到,如果没有适当的签字,则不能合并到主线中。 - - Co-developed-by: 声明补丁也是由另一个开发人员和原始作者一起创建的。当多 - 个人在一个补丁上工作时,这很有用。注意,此人也需要在补丁中有一个签名行。 + - Co-developed-by: 声明补丁是由多个开发人员共同创建的;当几个人在一个补丁上 + 工作时,它用于将属性赋予共同作者(除了 From: 所赋予的作者之外)。因为 + Co-developed-by: 表示作者身份,所以每个共同开发人, 必须紧跟在相关合作作者 + 的签名之后。具体内容和示例可以在以下文件中找到 + :ref:`Documentation/translations/zh_CN/process/submitting-patches.rst ` - Acked-by: 表示另一个开发人员(通常是相关代码的维护人员)同意补丁适合包含 在内核中。 diff --git a/Documentation/translations/zh_CN/process/submitting-patches.rst b/Documentation/translations/zh_CN/process/submitting-patches.rst index 93239649fb71..850c295a07a0 100644 --- a/Documentation/translations/zh_CN/process/submitting-patches.rst +++ b/Documentation/translations/zh_CN/process/submitting-patches.rst @@ -427,8 +427,37 @@ Acked-by:不一定表示对整个补丁的确认。例如,如果一个补丁 这是唯一一个标签,它可以在没有被它命名的人显式操作的情况下添加,但它应该表明 这个人是在补丁上抄送的。讨论中包含了潜在利益相关方。 -Co-developed-by: 声明补丁也是由另一个开发人员和原始作者一起创建的。当多个人 -在一个补丁上工作时,这很有用。注意,此人也需要在补丁中有一个 Signed-off-by: +Co-developed-by: 声明补丁是由多个开发人员共同创建的;当几个人在一个补丁上工 +作时,它用于将属性赋予共同作者(除了 From: 所赋予的作者之外)。因为 +Co-developed-by: 表示作者身份,所以每个共同开发人:必须紧跟在相关合作作者的 +签名之后。标准的签核程序要求:标记的签核顺序应尽可能反映补丁的时间历史,而不 +管作者是通过 From :还是由 Co-developed-by: 共同开发的。值得注意的是,最后一 +个签字人:必须始终是提交补丁的开发人员。 + +注意,当作者也是电子邮件标题“发件人:”行中列出的人时,“From: ” 标记是可选的。 + +作者提交的补丁程序示例:: + + + + Co-developed-by: First Co-Author + Signed-off-by: First Co-Author + Co-developed-by: Second Co-Author + Signed-off-by: Second Co-Author + Signed-off-by: From Author + +合作开发者提交的补丁示例:: + + From: From Author + + + + Co-developed-by: Random Co-Author + Signed-off-by: Random Co-Author + Signed-off-by: From Author + Co-developed-by: Submitting Co-Author + Signed-off-by: Submitting Co-Author + 13)使用报告人:、测试人:、审核人:、建议人:、修复人: -------------------------------------------------------- @@ -538,7 +567,7 @@ e-mail 标题中的“一句话概述”扼要的描述 e-mail 中的补丁。 Subject: [PATCHv2 001/207] x86: fix eflags tracking "From" 行是信体里的最上面一行,具有如下格式: - From: Original Author + From: Patch Author "From" 行指明在永久改动日志里,谁会被确认为作者。如果没有 "From" 行,那 么邮件头里的 "From: " 行会被用来决定改动日志中的作者。 -- cgit v1.2.3 From edf30385b686b9b1cc5694fa19506aa89fe27b25 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:50 +0800 Subject: docs/zh_CN: add programming-language.rst Now we have this file in Chinese. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- .../zh_CN/process/programming-language.rst | 36 ++++++++++++++++++++++ 1 file changed, 36 insertions(+) create mode 100644 Documentation/translations/zh_CN/process/programming-language.rst (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/programming-language.rst b/Documentation/translations/zh_CN/process/programming-language.rst new file mode 100644 index 000000000000..b1c7da529416 --- /dev/null +++ b/Documentation/translations/zh_CN/process/programming-language.rst @@ -0,0 +1,36 @@ +.. _cn_programming_language: + +程序设计语言 +============ + +内核是用C语言 [c-language]_ 编写的。更准确地说,内核通常是用 ``gcc`` [gcc]_ +在 ``-std=gnu89`` [gcc-c-dialect-options]_ 下编译的:ISO C90的 GNU 方言( +包括一些C99特性) + +这种方言包含对语言 [gnu-extensions]_ 的许多扩展,当然,它们许多都在内核中使用。 + +对于一些体系结构,有一些使用 ``clang`` [clang]_ 和 ``icc`` [icc]_ 编译内核 +的支持,尽管在编写此文档时还没有完成,仍需要第三方补丁。 + +属性 +---- + +在整个内核中使用的一个常见扩展是属性(attributes) [gcc-attribute-syntax]_ +属性允许将实现定义的语义引入语言实体(如变量、函数或类型),而无需对语言进行 +重大的语法更改(例如添加新关键字) [n2049]_ + +在某些情况下,属性是可选的(即不支持这些属性的编译器仍然应该生成正确的代码, +即使其速度较慢或执行的编译时检查/诊断次数不够) + +内核定义了伪关键字(例如, ``pure`` ),而不是直接使用GNU属性语法(例如, +``__attribute__((__pure__))`` ),以检测可以使用哪些关键字和/或缩短代码, 具体 +请参阅 ``include/linux/compiler_attributes.h`` + +.. [c-language] http://www.open-std.org/jtc1/sc22/wg14/www/standards +.. [gcc] https://gcc.gnu.org +.. [clang] https://clang.llvm.org +.. [icc] https://software.intel.com/en-us/c-compilers +.. [gcc-c-dialect-options] https://gcc.gnu.org/onlinedocs/gcc/C-Dialect-Options.html +.. [gnu-extensions] https://gcc.gnu.org/onlinedocs/gcc/C-Extensions.html +.. [gcc-attribute-syntax] https://gcc.gnu.org/onlinedocs/gcc/Attribute-Syntax.html +.. [n2049] http://www.open-std.org/jtc1/sc22/wg14/www/docs/n2049.pdf -- cgit v1.2.3 From 98a5c9fce71247987ad03cb3e7fd2ce2ff8bbf9f Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:51 +0800 Subject: docs/zh_CN: link programming-language into process/index It could be found in index now. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/index.rst | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/index.rst b/Documentation/translations/zh_CN/process/index.rst index e37c03a90ac8..74b19d5210bb 100644 --- a/Documentation/translations/zh_CN/process/index.rst +++ b/Documentation/translations/zh_CN/process/index.rst @@ -26,6 +26,7 @@ code-of-conduct code-of-conduct-interpretation submitting-patches + programming-language coding-style development-process email-clients -- cgit v1.2.3 From b307d9bdf17a0942fb839e7e1dc4fb8f3d251669 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:52 +0800 Subject: docs/zh_CN: add disclaimer and translator info into programming-language add disclaimer and translator info into programming-language.rst file Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/programming-language.rst | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/programming-language.rst b/Documentation/translations/zh_CN/process/programming-language.rst index b1c7da529416..51fd4ef48ea1 100644 --- a/Documentation/translations/zh_CN/process/programming-language.rst +++ b/Documentation/translations/zh_CN/process/programming-language.rst @@ -1,3 +1,8 @@ +.. include:: ../disclaimer-zh_CN.rst + +:Original: :ref:`Documentation/process/programming-language.rst ` +:Translator: Alex Shi + .. _cn_programming_language: 程序设计语言 -- cgit v1.2.3 From 4ed38de756c9e7562ce313e21148a4d877ab861f Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:53 +0800 Subject: docs/zh_CN: add git setting in email-clients Add the Chinese translation of git in email-clients file Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/email-clients.rst | 11 +++++++++++ 1 file changed, 11 insertions(+) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/email-clients.rst b/Documentation/translations/zh_CN/process/email-clients.rst index e8641a5899e4..e7751f3bde25 100644 --- a/Documentation/translations/zh_CN/process/email-clients.rst +++ b/Documentation/translations/zh_CN/process/email-clients.rst @@ -17,6 +17,17 @@ Linux邮件客户端配置信息 ======================= +Git +--- + +现在大多数开发人员使用 ``git send-email`` 而不是常规的电子邮件客户端。这方面 +的手册非常好。在接收端,维护人员使用 ``git am`` 加载补丁。 + +如果你是 ``git`` 新手,那么把你的第一个补丁发送给你自己。将其保存为包含所有 +标题的原始文本。运行 ``git am raw_email.txt`` ,然后使用 ``git log`` 查看更 +改日志。如果工作正常,再将补丁发送到相应的邮件列表。 + + 普通配置 -------- Linux内核补丁是通过邮件被提交的,最好把补丁作为邮件体的内嵌文本。有些维护者 -- cgit v1.2.3 From bb08dbb36a7ad0a7d68f111bbffce4dd92b0ca75 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:54 +0800 Subject: docs/zh_CN: Update mutt setting info in email-clients Update mutt setting info into Chinese. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- .../translations/zh_CN/process/email-clients.rst | 37 ++++++++++++++++++++++ 1 file changed, 37 insertions(+) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/email-clients.rst b/Documentation/translations/zh_CN/process/email-clients.rst index e7751f3bde25..d600ff5074f6 100644 --- a/Documentation/translations/zh_CN/process/email-clients.rst +++ b/Documentation/translations/zh_CN/process/email-clients.rst @@ -144,10 +144,47 @@ Mutt不自带编辑器,所以不管你使用什么编辑器都不应该带有 如果想要把补丁作为内嵌文本。 (a)ttach工作的很好,不带有"set paste"。 +你可以通过 ``git format-patch`` 生成补丁,然后用 Mutt发送它们:: + + $ mutt -H 0001-some-bug-fix.patch + 配置选项: 它应该以默认设置的形式工作。 然而,把"send_charset"设置为"us-ascii::utf-8"也是一个不错的主意。 +Mutt 是高度可配置的。 这里是个使用mutt通过 Gmail 发送的补丁的最小配置:: + + # .muttrc + # ================ IMAP ==================== + set imap_user = 'yourusername@gmail.com' + set imap_pass = 'yourpassword' + set spoolfile = imaps://imap.gmail.com/INBOX + set folder = imaps://imap.gmail.com/ + set record="imaps://imap.gmail.com/[Gmail]/Sent Mail" + set postponed="imaps://imap.gmail.com/[Gmail]/Drafts" + set mbox="imaps://imap.gmail.com/[Gmail]/All Mail" + + # ================ SMTP ==================== + set smtp_url = "smtp://username@smtp.gmail.com:587/" + set smtp_pass = $imap_pass + set ssl_force_tls = yes # Require encrypted connection + + # ================ Composition ==================== + set editor = `echo \$EDITOR` + set edit_headers = yes # See the headers when editing + set charset = UTF-8 # value of $LANG; also fallback for send_charset + # Sender, email address, and sign-off line must match + unset use_domain # because joe@localhost is just embarrassing + set realname = "YOUR NAME" + set from = "username@gmail.com" + set use_from = yes + +Mutt文档含有更多信息: + + http://dev.mutt.org/trac/wiki/UseCases/Gmail + + http://dev.mutt.org/doc/manual.html + Pine (TUI) ~~~~~~~~~~ -- cgit v1.2.3 From eebfcbbe4beba5308cf1122ede4a76b5e4df1508 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:55 +0800 Subject: docs/zh_CN: add Alex into translator in email-clients Give the credit/responsiblity to translator Alex. Also remove the duplicate part of disclaimer. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/email-clients.rst | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/email-clients.rst b/Documentation/translations/zh_CN/process/email-clients.rst index d600ff5074f6..102023651118 100644 --- a/Documentation/translations/zh_CN/process/email-clients.rst +++ b/Documentation/translations/zh_CN/process/email-clients.rst @@ -4,12 +4,11 @@ :Original: :ref:`Documentation/process/email-clients.rst ` -如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 -交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者:: +译者:: 中文版维护者: 贾威威 Harry Wei 中文版翻译者: 贾威威 Harry Wei + 时奎亮 Alex Shi 中文版校译者: Yinglin Luan Xiaochen Wang yaxinsn -- cgit v1.2.3 From d5187f5c1c0e829ecd7c143196a1a9c447f7ac2d Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:56 +0800 Subject: docs/zh_CN: redirect the email-clients link to Chinese version Since we update the email-clients docs to latest version, it's time to redirect it in Chinese version. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Tom Levy Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/5.Posting.rst | 2 +- Documentation/translations/zh_CN/process/submitting-patches.rst | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/5.Posting.rst b/Documentation/translations/zh_CN/process/5.Posting.rst index 12a9324d4b1a..41aba21ff050 100644 --- a/Documentation/translations/zh_CN/process/5.Posting.rst +++ b/Documentation/translations/zh_CN/process/5.Posting.rst @@ -188,7 +188,7 @@ bug搜寻人员想知道补丁是否负责他们正在追查的问题,想知 执行的行包装的补丁不会在另一端复原,并且通常不会进行任何详细检查。如果有 任何疑问,把补丁寄给你自己,让你自己相信它是完好无损的。 - :ref:`documentation/process/email-clients.rst ` + :ref:`Documentation/translations/zh_CN/process/email-clients.rst ` 提供了一些有用的提示,可以让特定的邮件客户机工作以发送补丁。 - 你确定你的补丁没有愚蠢的错误吗?您应该始终通过scripts/checkpatch.pl运行 diff --git a/Documentation/translations/zh_CN/process/submitting-patches.rst b/Documentation/translations/zh_CN/process/submitting-patches.rst index 850c295a07a0..4391feebde93 100644 --- a/Documentation/translations/zh_CN/process/submitting-patches.rst +++ b/Documentation/translations/zh_CN/process/submitting-patches.rst @@ -297,7 +297,7 @@ Linus 和其他的内核开发者需要阅读和评论你提交的改动。对 例外:如果你的邮递员弄坏了补丁,那么有人可能会要求你使用mime重新发送补丁 -请参阅 :ref:`Documentation/process/e-mail-clients.rst ` +请参阅 :ref:`Documentation/translations/zh_CN/process/email-clients.rst ` 以获取有关配置电子邮件客户端以使其不受影响地发送修补程序的提示。 7) e-mail 的大小 -- cgit v1.2.3 From f1ab43760e1c1c8e11da23f8ceb4744e4abcb74c Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:57 +0800 Subject: docs/zh_CN: add management-style.rst in Chinese It's a enjoy to read and translate this doc, although I cann't find the original author from git history -- it came with 2.6.12-rc2, the initial git repo. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- .../zh_CN/process/management-style.rst | 202 +++++++++++++++++++++ 1 file changed, 202 insertions(+) create mode 100644 Documentation/translations/zh_CN/process/management-style.rst (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/management-style.rst b/Documentation/translations/zh_CN/process/management-style.rst new file mode 100644 index 000000000000..de38615a834d --- /dev/null +++ b/Documentation/translations/zh_CN/process/management-style.rst @@ -0,0 +1,202 @@ +.. _cn_managementstyle: + +Linux内核管理风格 +================= + +这是一个简短的文档,描述了Linux内核的首选(或组成,取决于您问谁)管理风格。 +它的目的是在某种程度上参照 :ref:`process/coding-style.rst ` +主要是为了避免反复回答 [#cnf1]_ 相同(或类似)的问题。 + +管理风格是非常个人化的,比简单的编码风格规则更难以量化,因此本文档可能与实 +际情况有关,也可能与实际情况无关。起初它是一个玩笑,但这并不意味着它可能不 +是真的。你得自己决定。 + +顺便说一句,在谈到“核心管理者”时,主要是技术负责人,而不是在公司内部进行传 +统管理的人。如果你签署了采购订单或者对你的团队的预算有任何了解,你几乎肯定 +不是一个核心管理者。这些建议可能适用于您,也可能不适用于您。 + +首先,我建议你购买“高效人的七个习惯”,而不是阅读它。烧了它,这是一个伟大的 +象征性姿态。 + +.. [#cnf1] 本文件并不是通过回答问题,而是通过让提问者痛苦地明白,我们不知道 + 答案是什么。 + +不管怎样,这里是: + +.. _decisions: + +1)决策 +------- + +每个人都认为管理者做决定,而且决策很重要。决定越大越痛苦,管理者就必须越高级。 +这很明显,但事实并非如此。 + +游戏的名字是 **避免** 做出决定。尤其是,如果有人告诉你“选择(a)或(b), +我们真的需要你来做决定”,你就是陷入麻烦的管理者。你管理的人比你更了解细节, +所以如果他们来找你做技术决策,你完蛋了。你显然没有能力为他们做这个决定。 + +(推论:如果你管理的人不比你更了解细节,你也会被搞砸,尽管原因完全不同。 +也就是说,你的工作是错的,他们应该管理你的才智) + +所以游戏的名字是 **避免** 做出决定,至少是那些大而痛苦的决定。做一些小的 +和非结果性的决定是很好的,并且使您看起来好像知道自己在做什么,所以内核管理者 +需要做的是将那些大的和痛苦的决定变成那些没有人真正关心的小事情。 + +这有助于认识到一个大的决定和一个小的决定之间的关键区别是你是否可以在事后修正 +你的决定。任何决定都可以通过始终确保如果你错了(而且你一定会错),你以后总是 +可以通过回溯来弥补损失。突然间,你就要做两个无关紧要的决定,一个是错误的,另 +一个是正确的。 + +人们甚至会认为这是真正的领导能力(咳,胡说,咳)。 + +因此,避免重大决策的关键在于避免做那些无法挽回的事情。不要被引导到一个你无法 +逃离的角落。走投无路的老鼠可能很危险——走投无路的管理者真可怜。 + +事实证明,由于没有人会愚蠢到让内核管理者承担巨大的财政责任,所以通常很容易 +回溯。既然你不可能浪费掉你无法偿还的巨额资金,你唯一可以回溯的就是技术决策, +而回溯很容易:只要告诉大家你是个不称职的傻瓜,说对不起,然后撤销你去年让别 +人所做的毫无价值的工作。突然间,你一年前做的决定不在是一个重大的决定,因为 +它很容易被推翻。 + +事实证明,有些人对接受这种方法有困难,原因有两个: + + - 承认你是个白痴比看起来更难。我们都喜欢保持形象,在公共场合说你错了有时 + 确实很难。 + - 如果有人告诉你,你去年所做的工作终究是不值得的,那么对那些可怜的低级工 + 程师来说也是很困难的,虽然实际的 **工作** 很容易删除,但你可能已经不可 + 挽回地失去了工程师的信任。记住:“不可撤销”是我们一开始就试图避免的, + 而你的决定终究是一个重大的决定。 + +令人欣慰的是,这两个原因都可以通过预先承认你没有任何线索,提前告诉人们你的 +决定完全是初步的,而且可能是错误的事情来有效地缓解。你应该始终保留改变主意 +的权利,并让人们 **意识** 到这一点。当你 **还没有** 做过真正愚蠢的事情的时 +候,承认自己是愚蠢的要容易得多。 + +然后,当它真的被证明是愚蠢的时候,人们就转动他们的眼珠说“哎呀,下次不要了”。 + +这种对不称职的先发制人的承认,也可能使真正做这项工作的人也会三思是否值得做。 +毕竟,如果他们不确定这是否是一个好主意,你肯定不应该通过向他们保证他们所做 +的工作将会进入(内核)鼓励他们。在他们开始一项巨大的努力之前,至少让他们三 +思而后行。 + +记住:他们最好比你更了解细节,而且他们通常认为他们对每件事都有答案。作为一 +个管理者,你能做的最好的事情不是灌输自信,而是对他们所做的事情进行健康的批 +判性思考。 + +顺便说一句,另一种避免做出决定的方法是看起来很可怜的抱怨 “我们不能两者兼 +得吗?” 相信我,它是有效的。如果不清楚哪种方法更好,他们最终会弄清楚的。 +最终的答案可能是两个团队都会因为这种情况而感到沮丧,以至于他们放弃了。 + +这听起来像是一个失败,但这通常是一个迹象,表明两个项目都有问题,而参与其中 +的人不能做决定的原因是他们都是错误的。你最终会闻到玫瑰的味道,你避免了另一 +个你本可以搞砸的决定。 + +2)人 +----- + +大多数人都是白痴,做一名管理者意味着你必须处理好这件事,也许更重要的是, +**他们** 必须处理好你。 + +事实证明,虽然很容易纠正技术错误,但不容易纠正人格障碍。你只能和他们的和 +你的(人格障碍)共处。 + +但是,为了做好作为内核管理者的准备,最好记住不要烧掉任何桥梁,不要轰炸任何 +无辜的村民,也不要疏远太多的内核开发人员。事实证明,疏远人是相当容易的,而 +亲近一个疏远的人是很难的。因此,“疏远”立即属于“不可逆”的范畴,并根据 +:ref:`decisions` 成为绝不可以做的事情。 + +这里只有几个简单的规则: + + (1) 不要叫人笨蛋(至少不要在公共场合) + (2) 学习如何在忘记规则(1)时道歉 + +问题在于 #1 很容易去做,因为你可以用数百万种不同的方式说“你是一个笨蛋” [#cnf2]_ +有时甚至没有意识到,而且几乎总是带着一种白热化的信念,认为你是对的。 + +你越确信自己是对的(让我们面对现实吧,你可以把几乎所有人都称为坏人,而且你 +经常是对的),事后道歉就越难。 + +要解决此问题,您实际上只有两个选项: + + - 非常擅长道歉 + - 把“爱”均匀地散开,没有人会真正感觉到自己被不公平地瞄准了。让它有足够的 + 创造性,他们甚至可能会觉得好笑。 + +选择永远保持礼貌是不存在的。没有人会相信一个如此明显地隐藏了他们真实性格的人。 + +.. [#cnf2] 保罗·西蒙演唱了“离开爱人的50种方法”,因为坦率地说,“告诉开发者 + 他们是D*CKHEAD" 的100万种方法都无法确认。但我确信他已经这么想了。 + +3)人2 - 好人 +------------- + +虽然大多数人都是白痴,但不幸的是,据此推论你也是白痴,尽管我们都自我感觉良 +好,我们比普通人更好(让我们面对现实吧,没有人相信他们是普通人或低于普通人), +我们也应该承认我们不是最锋利的刀,而且会有其他人比你更不像白痴。 + +有些人对聪明人反应不好。其他人利用它们。 + +作为内核维护人员,确保您在第二组中。接受他们,因为他们会让你的工作更容易。 +特别是,他们能够为你做决定,这就是游戏的全部内容。 + +所以当你发现一个比你聪明的人时,就顺其自然吧。你的管理职责在很大程度上变成 +了“听起来像是个好主意——去尝试吧”,或者“听起来不错,但是XXX呢?”“。第二个版 +本尤其是一个很好的方法,要么学习一些关于“XXX”的新东西,要么通过指出一些聪明 +人没有想到的东西来显得更具管理性。无论哪种情况,你都会赢。 + +要注意的一件事是认识到一个领域的伟大不一定会转化为其他领域。所以你可能会向 +特定的方向刺激人们,但让我们面对现实吧,他们可能擅长他们所做的事情,而且对 +其他事情都很差劲。好消息是,人们往往会自然而然地重拾他们擅长的东西,所以当 +你向某个方向刺激他们时,你并不是在做不可逆转的事情,只是不要用力推。 + +4)责备 +------- + +事情会出问题的,人们希望去责备人。贴标签,你就是受责备的人。 + +事实上,接受责备并不难,尤其是当人们意识到这不 **全是** 你的过错时。这让我 +们找到了承担责任的最佳方式:为别人承担这件事。你会感觉很好,他们会感觉很好, +没有受到指责. 那谁,失去了他们的全部36GB色情收藏的人,因为你的无能将勉强承 +认,你至少没有试图逃避责任。 + +然后让真正搞砸了的开发人员(如果你能找到他们)私下知道他们搞砸了。不仅是为 +了将来可以避免,而且为了让他们知道他们欠你一个人情。而且,也许更重要的是, +他们也可能是能够解决问题的人。因为,让我们面对现实吧,肯定不是你。 + +承担责任也是你首先成为管理者的原因。这是让人们信任你,让你获得潜在的荣耀的 +一部分,因为你就是那个会说“我搞砸了”的人。如果你已经遵循了以前的规则,你现 +在已经很擅长说了。 + +5)应避免的事情 +--------------- + +有一件事人们甚至比被称为“笨蛋”更讨厌,那就是在一个神圣的声音中被称为“笨蛋”。 +第一个你可以道歉,第二个你不会真正得到机会。即使你做得很好,他们也可能不再 +倾听。 + +我们都认为自己比别人强,这意味着当别人装腔作势时,这会让我们很恼火。你也许 +在道德和智力上比你周围的每个人都优越,但不要试图太明显,除非你真的打算激怒 +某人 [#cnf3]_ + +同样,不要对事情太客气或太微妙。礼貌很容易落得落花流水,把问题隐藏起来, +正如他们所说,“在互联网上,没人能听到你的含蓄。”用一个钝器把这一点锤进去, +因为你不能真的依靠别人来获得你的观点。 + +一些幽默可以帮助缓和直率和道德化。过度到荒谬的地步,可以灌输一个观点,而不 +会让接受者感到痛苦,他们只是认为你是愚蠢的。因此,它可以帮助我们摆脱对批评 +的个人心理障碍。 + +.. [#cnf3] 提示:与你的工作没有直接关系的网络新闻组是消除你对他人不满的好 + 方法。偶尔写些侮辱性的帖子,打个喷嚏,让你的情绪得到净化。别把牢骚带回家 + +6)为什么是我? +--------------- + +既然你的主要责任似乎是为别人的错误承担责任,并且让别人痛苦地明白你是不称职 +的,那么显而易见的问题之一就变成了为什么首先要这样做。 + +首先,虽然你可能会或可能不会听到十几岁女孩(或男孩,让我们不要在这里评判或 +性别歧视)敲你的更衣室门,你会得到一个巨大的个人成就感为“负责”。别介意你真 +的在领导别人,你要跟上别人,尽可能快地追赶他们。每个人都会认为你是负责人。 + +如果你可以做到这个, 这是个伟大的工作! -- cgit v1.2.3 From c4b3b4383322d4e5abb6b3b1dde1d131e823e8e4 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:58 +0800 Subject: docs/zh_CN: add disclaimer and translator info in management-style Credit the translator. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/management-style.rst | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/management-style.rst b/Documentation/translations/zh_CN/process/management-style.rst index de38615a834d..63f9a73ff19c 100644 --- a/Documentation/translations/zh_CN/process/management-style.rst +++ b/Documentation/translations/zh_CN/process/management-style.rst @@ -1,3 +1,8 @@ +.. include:: ../disclaimer-zh_CN.rst + +:Original: :ref:`Documentation/process/management-style.rst ` +:Translator: Alex Shi + .. _cn_managementstyle: Linux内核管理风格 -- cgit v1.2.3 From e97f5f2fd763a835895ee9117141f8e7c0b01680 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:44:59 +0800 Subject: docs/zh_CN: link management-style into process/index Now we could find it's link after 'make htmldocs' etc. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/index.rst | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/index.rst b/Documentation/translations/zh_CN/process/index.rst index 74b19d5210bb..be1e764a80d2 100644 --- a/Documentation/translations/zh_CN/process/index.rst +++ b/Documentation/translations/zh_CN/process/index.rst @@ -42,6 +42,7 @@ submit-checklist stable-api-nonsense stable-kernel-rules + management-style 这些是一些总体技术指南,由于缺乏更好的地方,现在已经放在这里 -- cgit v1.2.3 From 9b73a0e90324ec9792635acce0509ed74d60a7cc Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:45:00 +0800 Subject: docs/zh_CN: redirect management-style to Chinese one It's time to redirect the link to Chinese version. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Federico Vaga Cc: SeongJae Park Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/howto.rst | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/howto.rst b/Documentation/translations/zh_CN/process/howto.rst index f52bb011cb2c..bacf4b1d7f9d 100644 --- a/Documentation/translations/zh_CN/process/howto.rst +++ b/Documentation/translations/zh_CN/process/howto.rst @@ -130,7 +130,8 @@ Linux内核代码中包含有大量的文档。这些文档对于学习如何与 如果你认为自己发现了Linux内核的安全性问题,请根据这篇文档中的步骤来 提醒其他内核开发者并帮助解决这个问题。 - :ref:`Documentation/process/management-style.rst ` + :ref:`Documentation/translations/zh_CN/process/management-style.rst ` + 描述内核维护者的工作方法及其共有特点。这对于刚刚接触内核开发(或者对 它感到好奇)的人来说很重要,因为它解释了很多对于内核维护者独特行为的 普遍误解与迷惑。 -- cgit v1.2.3 From a8f49dc4251820a8f41ebd5b97ba78b918616260 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:45:01 +0800 Subject: docs/zh_CN: Cleanup stable-api-nonscense in Chinese remove the duplicated disclaimers and maintainers info. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/stable-api-nonsense.rst | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/stable-api-nonsense.rst b/Documentation/translations/zh_CN/process/stable-api-nonsense.rst index beb94200b35e..b4ddb6e88d9d 100644 --- a/Documentation/translations/zh_CN/process/stable-api-nonsense.rst +++ b/Documentation/translations/zh_CN/process/stable-api-nonsense.rst @@ -5,11 +5,8 @@ :Original: :ref:`Documentation/process/stable-api-nonsense.rst ` -如果想评论或更新本文的内容,请直接联系原文档的维护者。如果你使用英文 -交流有困难的话,也可以向中文版维护者求助。如果本翻译更新不及时或者翻 -译存在问题,请联系中文版维护者:: +译者:: - 英文版维护者: Greg Kroah-Hartman 中文版维护者: 钟宇 TripleX Chung 中文版翻译者: 钟宇 TripleX Chung 中文版校译者: 李阳 Li Yang -- cgit v1.2.3 From f5acf9397b5d89de170ec738bc59fadee615a220 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:45:02 +0800 Subject: docs/zh_CN: redirect stable-api-nonsense to Chinese version It's time to redirect it to Chinese version. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Federico Vaga Cc: SeongJae Park Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/howto.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/howto.rst b/Documentation/translations/zh_CN/process/howto.rst index bacf4b1d7f9d..a969e3d2b5a9 100644 --- a/Documentation/translations/zh_CN/process/howto.rst +++ b/Documentation/translations/zh_CN/process/howto.rst @@ -115,7 +115,7 @@ Linux内核代码中包含有大量的文档。这些文档对于学习如何与 http://linux.yyz.us/patch-format.html - :ref:`Documentation/process/stable-api-nonsense.rst ` + :ref:`Documentation/translations/zh_CN/process/stable-api-nonsense.rst ` 论证内核为什么特意不包括稳定的内核内部API,也就是说不包括像这样的特 性: -- cgit v1.2.3 From efd298e4afddbb52228ca5c1633e53c984cc785b Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:45:03 +0800 Subject: docs/zh_CN: update coding-sytle.rst Replace the disclaimer part and give the link name of this file: cn_codingsytle. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Bart Van Assche Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- .../translations/zh_CN/process/coding-style.rst | 21 ++++----------------- 1 file changed, 4 insertions(+), 17 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/coding-style.rst b/Documentation/translations/zh_CN/process/coding-style.rst index 3cb09803e084..cab9ceafa267 100644 --- a/Documentation/translations/zh_CN/process/coding-style.rst +++ b/Documentation/translations/zh_CN/process/coding-style.rst @@ -1,19 +1,10 @@ -Chinese translated version of Documentation/process/coding-style.rst +.. include:: ../disclaimer-zh_CN.rst -If you have any comment or update to the content, please post to LKML directly. -However, if you have problem communicating in English you can also ask the -Chinese maintainer for help. Contact the Chinese maintainer, if this -translation is outdated or there is problem with translation. +:Original: :ref:`Documentation/process/coding-style.rst ` -Chinese maintainer: Zhang Le +.. _cn_codingstyle: ---------------------------------------------------------------------- - -Documentation/process/coding-style.rst 的中文翻译 - -如果想评论或更新本文的内容,请直接发信到LKML。如果你使用英文交流有困难的话, -也可以向中文版维护者求助。如果本翻译更新不及时或者翻译存在问题,请联系中文版 -维护者:: +译者:: 中文版维护者: 张乐 Zhang Le 中文版翻译者: 张乐 Zhang Le @@ -23,10 +14,6 @@ Documentation/process/coding-style.rst 的中文翻译 Li Zefan Wang Chen -以下为正文 - ---------------------------------------------------------------------- - Linux 内核代码风格 ========================= -- cgit v1.2.3 From 8cd43e35f345cb889ab94ed2fef524ce9bc947a5 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:45:04 +0800 Subject: docs/zh_CN: redirect coding-sytle to Chinese version It's time to link the doc into Chinese version. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: Federico Vaga Cc: SeongJae Park Cc: Tom Levy Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/4.Coding.rst | 7 ++++--- Documentation/translations/zh_CN/process/howto.rst | 2 +- Documentation/translations/zh_CN/process/submit-checklist.rst | 2 +- Documentation/translations/zh_CN/process/submitting-patches.rst | 4 ++-- 4 files changed, 8 insertions(+), 7 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/4.Coding.rst b/Documentation/translations/zh_CN/process/4.Coding.rst index 2b60752a81b2..5301e9d55255 100644 --- a/Documentation/translations/zh_CN/process/4.Coding.rst +++ b/Documentation/translations/zh_CN/process/4.Coding.rst @@ -22,9 +22,10 @@ ******** 内核长期以来都有一种标准的编码风格,如 -:ref:`Documentation/process/coding-style.rst ` 中所述。在大部分 -时间里,该文件中描述的政策被认为至多是建议性的。因此,内核中存在大量不符合编 -码风格准则的代码。代码的存在会给内核开发人员带来两个独立的危害。 +:ref:`Documentation/translations/zh_CN/process/coding-style.rst ` +中所述。在大部分时间里,该文件中描述的政策被认为至多是建议性的。因此,内核 +中存在大量不符合编码风格准则的代码。代码的存在会给内核开发人员带来两个独立 +的危害。 首先,要相信内核编码标准并不重要,也不强制执行。事实上,如果没有按照标准对代 码进行编码,那么向内核添加新代码是非常困难的;许多开发人员甚至会在审查代码之 diff --git a/Documentation/translations/zh_CN/process/howto.rst b/Documentation/translations/zh_CN/process/howto.rst index a969e3d2b5a9..5b671178b17b 100644 --- a/Documentation/translations/zh_CN/process/howto.rst +++ b/Documentation/translations/zh_CN/process/howto.rst @@ -90,7 +90,7 @@ Linux内核代码中包含有大量的文档。这些文档对于学习如何与 :ref:`Documentation/process/changes.rst ` 文件给出了用来编译和使用内核所需要的最小软件包列表。 - :ref:`Documentation/process/coding-style.rst ` + :ref:`Documentation/translations/zh_CN/process/coding-style.rst ` 描述Linux内核的代码风格和理由。所有新代码需要遵守这篇文档中定义的规 范。大多数维护者只会接收符合规定的补丁,很多人也只会帮忙检查符合风格 的代码。 diff --git a/Documentation/translations/zh_CN/process/submit-checklist.rst b/Documentation/translations/zh_CN/process/submit-checklist.rst index c931273e1487..89061aa8fdbe 100644 --- a/Documentation/translations/zh_CN/process/submit-checklist.rst +++ b/Documentation/translations/zh_CN/process/submit-checklist.rst @@ -32,7 +32,7 @@ Linux内核补丁提交清单 4) PPC64是一种很好的交叉编译检查体系结构,因为它倾向于对64位的数使用无符号 长整型。 -5) 如下所述 :ref:`Documentation/process/coding-style.rst `. +5) 如下所述 :ref:`Documentation/translations/zh_CN/process/coding-style.rst `. 检查您的补丁是否为常规样式。在提交( ``scripts/check patch.pl`` )之前, 使用补丁样式检查器检查是否有轻微的冲突。您应该能够处理您的补丁中存在的所有 违规行为。 diff --git a/Documentation/translations/zh_CN/process/submitting-patches.rst b/Documentation/translations/zh_CN/process/submitting-patches.rst index 4391feebde93..437c23b367bb 100644 --- a/Documentation/translations/zh_CN/process/submitting-patches.rst +++ b/Documentation/translations/zh_CN/process/submitting-patches.rst @@ -191,7 +191,7 @@ bug的URL之外,还要总结需要提交补丁的相关讨论要点。 ------------------- 检查您的补丁是否存在基本样式冲突,详细信息可在 -:ref:`Documentation/process/coding-style.rst ` +:ref:`Documentation/translations/zh_CN/process/coding-style.rst ` 中找到。如果不这样做,只会浪费审稿人的时间,并且会导致你的补丁被拒绝,甚至 可能没有被阅读。 @@ -671,7 +671,7 @@ NO!!!! No more huge patch bombs to linux-kernel@vger.kernel.org people! Kernel Documentation/process/coding-style.rst: - :ref:`Documentation/process/coding-style.rst ` + :ref:`Documentation/translations/zh_CN/process/coding-style.rst ` Linus Torvalds's mail on the canonical patch format: -- cgit v1.2.3 From ae7e727681006891c40a66c633f7cdeb1df1ed6a Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 1 Apr 2019 22:45:05 +0800 Subject: docs/zh_CN: correct the disclaimer file The original disclaimer remind people to get help from the specific Chinese doc maintainers. But there are lots docs has no 'specific maintainers' and some of maintainer doesn't updated the docs for years. So replace the Chinese word maintainer with translator. That's more precise for these people's role of their docs. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/disclaimer-zh_CN.rst | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/disclaimer-zh_CN.rst b/Documentation/translations/zh_CN/disclaimer-zh_CN.rst index 5934369b2606..dcf803ede85a 100644 --- a/Documentation/translations/zh_CN/disclaimer-zh_CN.rst +++ b/Documentation/translations/zh_CN/disclaimer-zh_CN.rst @@ -1,9 +1,9 @@ :orphan: .. warning:: - 此文件的目的是为让中文读者更容易阅读和理解,而不是作为一个分支。 因此,如果 - 您对此文件有任何意见或更新,请先尝试更新原始英文文件。 + 此文件的目的是为让中文读者更容易阅读和理解,而不是作为一个分支。 因此, + 如果您对此文件有任何意见或更新,请先尝试更新原始英文文件。 .. note:: - 如果您发现本文档与原始文件有任何不同或者有翻译问题,请联系该文件的维护者, + 如果您发现本文档与原始文件有任何不同或者有翻译问题,请联系该文件的译者, 或者请求时奎亮的帮助:。 -- cgit v1.2.3 From 5e3ec254e086f348346df3f00a6d372defd10d4e Mon Sep 17 00:00:00 2001 From: Jonathan Corbet Date: Tue, 2 Apr 2019 09:58:08 -0600 Subject: docs: Fix a build error in coding-style.rst A reference typo caused an unsightly build error; fix it. Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/coding-style.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/coding-style.rst b/Documentation/translations/zh_CN/process/coding-style.rst index cab9ceafa267..5479c591c2f7 100644 --- a/Documentation/translations/zh_CN/process/coding-style.rst +++ b/Documentation/translations/zh_CN/process/coding-style.rst @@ -1,6 +1,6 @@ .. include:: ../disclaimer-zh_CN.rst -:Original: :ref:`Documentation/process/coding-style.rst ` +:Original: :ref:`Documentation/process/coding-style.rst ` .. _cn_codingstyle: -- cgit v1.2.3 From d71eb0ce109a124b0fa714832823b9452f2762cf Mon Sep 17 00:00:00 2001 From: Josh Poimboeuf Date: Tue, 2 Apr 2019 09:59:33 -0500 Subject: x86/speculation/mds: Add mds=full,nosmt cmdline option Add the mds=full,nosmt cmdline option. This is like mds=full, but with SMT disabled if the CPU is vulnerable. Signed-off-by: Josh Poimboeuf Signed-off-by: Thomas Gleixner Reviewed-by: Tyler Hicks Acked-by: Jiri Kosina --- Documentation/admin-guide/hw-vuln/mds.rst | 3 +++ Documentation/admin-guide/kernel-parameters.txt | 6 ++++-- arch/x86/kernel/cpu/bugs.c | 10 ++++++++++ 3 files changed, 17 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/admin-guide/hw-vuln/mds.rst b/Documentation/admin-guide/hw-vuln/mds.rst index 1de29d28903d..244ab47d1fb3 100644 --- a/Documentation/admin-guide/hw-vuln/mds.rst +++ b/Documentation/admin-guide/hw-vuln/mds.rst @@ -260,6 +260,9 @@ time with the option "mds=". The valid arguments for this option are: It does not automatically disable SMT. + full,nosmt The same as mds=full, with SMT disabled on vulnerable + CPUs. This is the complete mitigation. + off Disables MDS mitigations completely. ============ ============================================================= diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt index 7325319c2c23..8f04985d3122 100644 --- a/Documentation/admin-guide/kernel-parameters.txt +++ b/Documentation/admin-guide/kernel-parameters.txt @@ -2372,8 +2372,10 @@ This parameter controls the MDS mitigation. The options are: - full - Enable MDS mitigation on vulnerable CPUs - off - Unconditionally disable MDS mitigation + full - Enable MDS mitigation on vulnerable CPUs + full,nosmt - Enable MDS mitigation and disable + SMT on vulnerable CPUs + off - Unconditionally disable MDS mitigation Not specifying this option is equivalent to mds=full. diff --git a/arch/x86/kernel/cpu/bugs.c b/arch/x86/kernel/cpu/bugs.c index 373ae1dcd301..9f252082a83b 100644 --- a/arch/x86/kernel/cpu/bugs.c +++ b/arch/x86/kernel/cpu/bugs.c @@ -221,6 +221,7 @@ static void x86_amd_ssb_disable(void) /* Default mitigation for L1TF-affected CPUs */ static enum mds_mitigations mds_mitigation __ro_after_init = MDS_MITIGATION_FULL; +static bool mds_nosmt __ro_after_init = false; static const char * const mds_strings[] = { [MDS_MITIGATION_OFF] = "Vulnerable", @@ -238,8 +239,13 @@ static void __init mds_select_mitigation(void) if (mds_mitigation == MDS_MITIGATION_FULL) { if (!boot_cpu_has(X86_FEATURE_MD_CLEAR)) mds_mitigation = MDS_MITIGATION_VMWERV; + static_branch_enable(&mds_user_clear); + + if (mds_nosmt && !boot_cpu_has(X86_BUG_MSBDS_ONLY)) + cpu_smt_disable(false); } + pr_info("%s\n", mds_strings[mds_mitigation]); } @@ -255,6 +261,10 @@ static int __init mds_cmdline(char *str) mds_mitigation = MDS_MITIGATION_OFF; else if (!strcmp(str, "full")) mds_mitigation = MDS_MITIGATION_FULL; + else if (!strcmp(str, "full,nosmt")) { + mds_mitigation = MDS_MITIGATION_FULL; + mds_nosmt = true; + } return 0; } -- cgit v1.2.3 From 6455959819bf2469190ae9f6b4ccebaa9827e884 Mon Sep 17 00:00:00 2001 From: Peter Zijlstra Date: Tue, 19 Feb 2019 14:38:37 +0100 Subject: ia64/tlb: Eradicate tlb_migrate_finish() callback Only ia64-sn2 uses this as an optimization, and there it is of questionable correctness due to the mm_users==1 test. Remove it entirely. No change in behavior intended. Signed-off-by: Peter Zijlstra (Intel) Cc: Andrew Morton Cc: Andy Lutomirski Cc: Borislav Petkov Cc: Dave Hansen Cc: H. Peter Anvin Cc: Linus Torvalds Cc: Peter Zijlstra Cc: Rik van Riel Cc: Thomas Gleixner Signed-off-by: Ingo Molnar --- Documentation/core-api/cachetlb.rst | 10 ---------- arch/ia64/include/asm/machvec.h | 13 ------------- arch/ia64/include/asm/machvec_sn2.h | 2 -- arch/ia64/include/asm/tlb.h | 2 -- arch/ia64/sn/kernel/sn2/sn2_smp.c | 7 ------- arch/nds32/include/asm/tlbflush.h | 1 - include/asm-generic/tlb.h | 4 ---- kernel/sched/core.c | 1 - 8 files changed, 40 deletions(-) (limited to 'Documentation') diff --git a/Documentation/core-api/cachetlb.rst b/Documentation/core-api/cachetlb.rst index 6eb9d3f090cd..93cb65d52720 100644 --- a/Documentation/core-api/cachetlb.rst +++ b/Documentation/core-api/cachetlb.rst @@ -101,16 +101,6 @@ changes occur: translations for software managed TLB configurations. The sparc64 port currently does this. -6) ``void tlb_migrate_finish(struct mm_struct *mm)`` - - This interface is called at the end of an explicit - process migration. This interface provides a hook - to allow a platform to update TLB or context-specific - information for the address space. - - The ia64 sn2 platform is one example of a platform - that uses this interface. - Next, we have the cache flushing interfaces. In general, when Linux is changing an existing virtual-->physical mapping to a new value, the sequence will be in one of the following forms:: diff --git a/arch/ia64/include/asm/machvec.h b/arch/ia64/include/asm/machvec.h index 5133739966bc..beae261fbcb4 100644 --- a/arch/ia64/include/asm/machvec.h +++ b/arch/ia64/include/asm/machvec.h @@ -30,7 +30,6 @@ typedef void ia64_mv_irq_init_t (void); typedef void ia64_mv_send_ipi_t (int, int, int, int); typedef void ia64_mv_timer_interrupt_t (int, void *); typedef void ia64_mv_global_tlb_purge_t (struct mm_struct *, unsigned long, unsigned long, unsigned long); -typedef void ia64_mv_tlb_migrate_finish_t (struct mm_struct *); typedef u8 ia64_mv_irq_to_vector (int); typedef unsigned int ia64_mv_local_vector_to_irq (u8); typedef char *ia64_mv_pci_get_legacy_mem_t (struct pci_bus *); @@ -79,11 +78,6 @@ machvec_noop (void) { } -static inline void -machvec_noop_mm (struct mm_struct *mm) -{ -} - static inline void machvec_noop_task (struct task_struct *task) { @@ -96,7 +90,6 @@ machvec_noop_bus (struct pci_bus *bus) extern void machvec_setup (char **); extern void machvec_timer_interrupt (int, void *); -extern void machvec_tlb_migrate_finish (struct mm_struct *); # if defined (CONFIG_IA64_HP_SIM) # include @@ -124,7 +117,6 @@ extern void machvec_tlb_migrate_finish (struct mm_struct *); # define platform_send_ipi ia64_mv.send_ipi # define platform_timer_interrupt ia64_mv.timer_interrupt # define platform_global_tlb_purge ia64_mv.global_tlb_purge -# define platform_tlb_migrate_finish ia64_mv.tlb_migrate_finish # define platform_dma_init ia64_mv.dma_init # define platform_dma_get_ops ia64_mv.dma_get_ops # define platform_irq_to_vector ia64_mv.irq_to_vector @@ -167,7 +159,6 @@ struct ia64_machine_vector { ia64_mv_send_ipi_t *send_ipi; ia64_mv_timer_interrupt_t *timer_interrupt; ia64_mv_global_tlb_purge_t *global_tlb_purge; - ia64_mv_tlb_migrate_finish_t *tlb_migrate_finish; ia64_mv_dma_init *dma_init; ia64_mv_dma_get_ops *dma_get_ops; ia64_mv_irq_to_vector *irq_to_vector; @@ -206,7 +197,6 @@ struct ia64_machine_vector { platform_send_ipi, \ platform_timer_interrupt, \ platform_global_tlb_purge, \ - platform_tlb_migrate_finish, \ platform_dma_init, \ platform_dma_get_ops, \ platform_irq_to_vector, \ @@ -270,9 +260,6 @@ extern const struct dma_map_ops *dma_get_ops(struct device *); #ifndef platform_global_tlb_purge # define platform_global_tlb_purge ia64_global_tlb_purge /* default to architected version */ #endif -#ifndef platform_tlb_migrate_finish -# define platform_tlb_migrate_finish machvec_noop_mm -#endif #ifndef platform_kernel_launch_event # define platform_kernel_launch_event machvec_noop #endif diff --git a/arch/ia64/include/asm/machvec_sn2.h b/arch/ia64/include/asm/machvec_sn2.h index b5153d300289..a243e4fb4877 100644 --- a/arch/ia64/include/asm/machvec_sn2.h +++ b/arch/ia64/include/asm/machvec_sn2.h @@ -34,7 +34,6 @@ extern ia64_mv_irq_init_t sn_irq_init; extern ia64_mv_send_ipi_t sn2_send_IPI; extern ia64_mv_timer_interrupt_t sn_timer_interrupt; extern ia64_mv_global_tlb_purge_t sn2_global_tlb_purge; -extern ia64_mv_tlb_migrate_finish_t sn_tlb_migrate_finish; extern ia64_mv_irq_to_vector sn_irq_to_vector; extern ia64_mv_local_vector_to_irq sn_local_vector_to_irq; extern ia64_mv_pci_get_legacy_mem_t sn_pci_get_legacy_mem; @@ -77,7 +76,6 @@ extern ia64_mv_pci_fixup_bus_t sn_pci_fixup_bus; #define platform_send_ipi sn2_send_IPI #define platform_timer_interrupt sn_timer_interrupt #define platform_global_tlb_purge sn2_global_tlb_purge -#define platform_tlb_migrate_finish sn_tlb_migrate_finish #define platform_pci_fixup sn_pci_fixup #define platform_inb __sn_inb #define platform_inw __sn_inw diff --git a/arch/ia64/include/asm/tlb.h b/arch/ia64/include/asm/tlb.h index 849fab9ccb33..86ec034ba499 100644 --- a/arch/ia64/include/asm/tlb.h +++ b/arch/ia64/include/asm/tlb.h @@ -47,8 +47,6 @@ #include #include -#define tlb_migrate_finish(mm) platform_tlb_migrate_finish(mm) - #include #endif /* _ASM_IA64_TLB_H */ diff --git a/arch/ia64/sn/kernel/sn2/sn2_smp.c b/arch/ia64/sn/kernel/sn2/sn2_smp.c index b73b0ebf8214..b510f4f17fd4 100644 --- a/arch/ia64/sn/kernel/sn2/sn2_smp.c +++ b/arch/ia64/sn/kernel/sn2/sn2_smp.c @@ -120,13 +120,6 @@ void sn_migrate(struct task_struct *task) cpu_relax(); } -void sn_tlb_migrate_finish(struct mm_struct *mm) -{ - /* flush_tlb_mm is inefficient if more than 1 users of mm */ - if (mm == current->mm && mm && atomic_read(&mm->mm_users) == 1) - flush_tlb_mm(mm); -} - static void sn2_ipi_flush_all_tlb(struct mm_struct *mm) { diff --git a/arch/nds32/include/asm/tlbflush.h b/arch/nds32/include/asm/tlbflush.h index 9b411f401903..38ee769b18d8 100644 --- a/arch/nds32/include/asm/tlbflush.h +++ b/arch/nds32/include/asm/tlbflush.h @@ -42,6 +42,5 @@ void local_flush_tlb_page(struct vm_area_struct *vma, unsigned long addr); void update_mmu_cache(struct vm_area_struct *vma, unsigned long address, pte_t * pte); -void tlb_migrate_finish(struct mm_struct *mm); #endif diff --git a/include/asm-generic/tlb.h b/include/asm-generic/tlb.h index fc661b4675ff..b9edc7608d90 100644 --- a/include/asm-generic/tlb.h +++ b/include/asm-generic/tlb.h @@ -604,8 +604,4 @@ static inline void tlb_end_vma(struct mmu_gather *tlb, struct vm_area_struct *vm #endif /* CONFIG_MMU */ -#ifndef tlb_migrate_finish -#define tlb_migrate_finish(mm) do {} while (0) -#endif - #endif /* _ASM_GENERIC__TLB_H */ diff --git a/kernel/sched/core.c b/kernel/sched/core.c index 4778c48a7fda..ade3f2287d1f 100644 --- a/kernel/sched/core.c +++ b/kernel/sched/core.c @@ -1151,7 +1151,6 @@ static int __set_cpus_allowed_ptr(struct task_struct *p, /* Need help from migration thread: drop lock and wait. */ task_rq_unlock(rq, p, &rf); stop_one_cpu(cpu_of(rq), migration_cpu_stop, &arg); - tlb_migrate_finish(p->mm); return 0; } else if (task_on_rq_queued(p)) { /* -- cgit v1.2.3 From 4b81dad109ad7d7b288804fcdc6475b48f242210 Mon Sep 17 00:00:00 2001 From: Christina Quast Date: Tue, 2 Apr 2019 14:16:48 +0200 Subject: ALSA: doc: my_chip has no element ioport chip->ioport is dereferenced in two places, but the struct is defined as follows: struct mychip { struct snd_card *card; struct pci_dev *pci; unsigned long port; int irq; }; Signed-off-by: Christina Quast Signed-off-by: Takashi Iwai --- Documentation/sound/kernel-api/writing-an-alsa-driver.rst | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/sound/kernel-api/writing-an-alsa-driver.rst b/Documentation/sound/kernel-api/writing-an-alsa-driver.rst index 6b154dbb02cc..132f5eb9b530 100644 --- a/Documentation/sound/kernel-api/writing-an-alsa-driver.rst +++ b/Documentation/sound/kernel-api/writing-an-alsa-driver.rst @@ -324,7 +324,7 @@ to details explained in the following section. strcpy(card->driver, "My Chip"); strcpy(card->shortname, "My Own Chip 123"); sprintf(card->longname, "%s at 0x%lx irq %i", - card->shortname, chip->ioport, chip->irq); + card->shortname, chip->port, chip->irq); /* (5) */ .... /* implemented later */ @@ -437,7 +437,7 @@ Since each component can be properly freed, the single strcpy(card->driver, "My Chip"); strcpy(card->shortname, "My Own Chip 123"); sprintf(card->longname, "%s at 0x%lx irq %i", - card->shortname, chip->ioport, chip->irq); + card->shortname, chip->port, chip->irq); The driver field holds the minimal ID string of the chip. This is used by alsa-lib's configurator, so keep it simple but unique. Even the -- cgit v1.2.3 From 682587080da998886461cb0dc9b609d1b6205277 Mon Sep 17 00:00:00 2001 From: Ray Jui Date: Tue, 2 Apr 2019 18:18:25 -0700 Subject: dt-bindings: i2c: iproc: make 'interrupts' optional Update the binding document to make the 'interrupts' property optional. For certain revisions of the I2C controller (e.g., iProc NIC I2C), I2C interrupt is unwired to the interrupt controller. In such case, this 'interrupts' property should be left unspecified, and driver will fall back to polling mode Signed-off-by: Ray Jui Signed-off-by: Rayagonda Kokatanur Reviewed-by: Rob Herring Signed-off-by: Wolfram Sang --- Documentation/devicetree/bindings/i2c/brcm,iproc-i2c.txt | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/i2c/brcm,iproc-i2c.txt b/Documentation/devicetree/bindings/i2c/brcm,iproc-i2c.txt index 81f982ccca31..7a32bf81bfa9 100644 --- a/Documentation/devicetree/bindings/i2c/brcm,iproc-i2c.txt +++ b/Documentation/devicetree/bindings/i2c/brcm,iproc-i2c.txt @@ -9,9 +9,6 @@ Required properties: Define the base and range of the I/O address space that contain the iProc I2C controller registers -- interrupts: - Should contain the I2C interrupt - - clock-frequency: This is the I2C bus clock. Need to be either 100000 or 400000 @@ -21,6 +18,14 @@ Required properties: - #size-cells: Always 0 +Optional properties: + +- interrupts: + Should contain the I2C interrupt. For certain revisions of the I2C + controller, I2C interrupt is unwired to the interrupt controller. In such + case, this property should be left unspecified, and driver will fall back + to polling mode + Example: i2c0: i2c@18008000 { compatible = "brcm,iproc-i2c"; -- cgit v1.2.3 From 12402f825d3b83de57bd2902989dc54a5a2128d4 Mon Sep 17 00:00:00 2001 From: Rayagonda Kokatanur Date: Tue, 2 Apr 2019 18:18:28 -0700 Subject: dt-bindings: i2c: iproc: add "brcm, iproc-nic-i2c" compatible string Update iProc I2C binding document to add new compatible string "brcm,iproc-nic-i2c". Optional property "brcm,ape-hsls-addr-mask" is also added that allows configuration of the host view into the APE's address for "brcm,iproc-nic-i2c" Signed-off-by: Rayagonda Kokatanur Signed-off-by: Ray Jui Reviewed-by: Rob Herring Signed-off-by: Wolfram Sang --- Documentation/devicetree/bindings/i2c/brcm,iproc-i2c.txt | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/i2c/brcm,iproc-i2c.txt b/Documentation/devicetree/bindings/i2c/brcm,iproc-i2c.txt index 7a32bf81bfa9..d12cc33cca6c 100644 --- a/Documentation/devicetree/bindings/i2c/brcm,iproc-i2c.txt +++ b/Documentation/devicetree/bindings/i2c/brcm,iproc-i2c.txt @@ -3,7 +3,7 @@ Broadcom iProc I2C controller Required properties: - compatible: - Must be "brcm,iproc-i2c" + Must be "brcm,iproc-i2c" or "brcm,iproc-nic-i2c" - reg: Define the base and range of the I/O address space that contain the iProc @@ -26,6 +26,10 @@ Optional properties: case, this property should be left unspecified, and driver will fall back to polling mode +- brcm,ape-hsls-addr-mask: + Required for "brcm,iproc-nic-i2c". Host view of address mask into the + 'APE' co-processor. Value must be unsigned, 32-bit + Example: i2c0: i2c@18008000 { compatible = "brcm,iproc-i2c"; -- cgit v1.2.3 From ae97fb589648cd5558f1ceea317404a639307501 Mon Sep 17 00:00:00 2001 From: Jagan Teki Date: Wed, 3 Apr 2019 15:20:26 -0700 Subject: Input: goodix - add regulators suppot Goodix CTP controllers require AVDD28, VDDIO regulators for power-on sequence. The delay between these regualtor operations as per Power-on Timing from datasheet[1] is 0 (T1 >= 0 usec). So, enable and disable these regulators in proper order using normal regulator functions without any delay in between. [1] GT5663 Datasheet_English_20151106_Rev.01 Signed-off-by: Jagan Teki Reviewed-by: Rob Herring Signed-off-by: Dmitry Torokhov --- .../bindings/input/touchscreen/goodix.txt | 2 + drivers/input/touchscreen/goodix.c | 52 ++++++++++++++++++++++ 2 files changed, 54 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/input/touchscreen/goodix.txt b/Documentation/devicetree/bindings/input/touchscreen/goodix.txt index 8cf0b4d38a7e..255673250bbd 100644 --- a/Documentation/devicetree/bindings/input/touchscreen/goodix.txt +++ b/Documentation/devicetree/bindings/input/touchscreen/goodix.txt @@ -19,6 +19,8 @@ Optional properties: - irq-gpios : GPIO pin used for IRQ. The driver uses the interrupt gpio pin as output to reset the device. - reset-gpios : GPIO pin used for reset + - AVDD28-supply : Analog power supply regulator on AVDD28 pin + - VDDIO-supply : GPIO power supply regulator on VDDIO pin - touchscreen-inverted-x - touchscreen-inverted-y - touchscreen-size-x diff --git a/drivers/input/touchscreen/goodix.c b/drivers/input/touchscreen/goodix.c index f57d82220a88..b1c071fd243a 100644 --- a/drivers/input/touchscreen/goodix.c +++ b/drivers/input/touchscreen/goodix.c @@ -27,6 +27,7 @@ #include #include #include +#include #include #include #include @@ -47,6 +48,8 @@ struct goodix_ts_data { struct touchscreen_properties prop; unsigned int max_touch_num; unsigned int int_trigger_type; + struct regulator *avdd28; + struct regulator *vddio; struct gpio_desc *gpiod_int; struct gpio_desc *gpiod_rst; u16 id; @@ -532,6 +535,24 @@ static int goodix_get_gpio_config(struct goodix_ts_data *ts) return -EINVAL; dev = &ts->client->dev; + ts->avdd28 = devm_regulator_get(dev, "AVDD28"); + if (IS_ERR(ts->avdd28)) { + error = PTR_ERR(ts->avdd28); + if (error != -EPROBE_DEFER) + dev_err(dev, + "Failed to get AVDD28 regulator: %d\n", error); + return error; + } + + ts->vddio = devm_regulator_get(dev, "VDDIO"); + if (IS_ERR(ts->vddio)) { + error = PTR_ERR(ts->vddio); + if (error != -EPROBE_DEFER) + dev_err(dev, + "Failed to get VDDIO regulator: %d\n", error); + return error; + } + /* Get the interrupt GPIO pin number */ gpiod = devm_gpiod_get_optional(dev, GOODIX_GPIO_INT_NAME, GPIOD_IN); if (IS_ERR(gpiod)) { @@ -764,6 +785,14 @@ err_release_cfg: complete_all(&ts->firmware_loading_complete); } +static void goodix_disable_regulators(void *arg) +{ + struct goodix_ts_data *ts = arg; + + regulator_disable(ts->vddio); + regulator_disable(ts->avdd28); +} + static int goodix_ts_probe(struct i2c_client *client, const struct i2c_device_id *id) { @@ -789,6 +818,29 @@ static int goodix_ts_probe(struct i2c_client *client, if (error) return error; + /* power up the controller */ + error = regulator_enable(ts->avdd28); + if (error) { + dev_err(&client->dev, + "Failed to enable AVDD28 regulator: %d\n", + error); + return error; + } + + error = regulator_enable(ts->vddio); + if (error) { + dev_err(&client->dev, + "Failed to enable VDDIO regulator: %d\n", + error); + regulator_disable(ts->avdd28); + return error; + } + + error = devm_add_action_or_reset(&client->dev, + goodix_disable_regulators, ts); + if (error) + return error; + if (ts->gpiod_int && ts->gpiod_rst) { /* reset the controller */ error = goodix_reset(ts); -- cgit v1.2.3 From a5f50c501321249d67611353dde6d68d48c5b959 Mon Sep 17 00:00:00 2001 From: Jagan Teki Date: Wed, 3 Apr 2019 16:05:34 -0700 Subject: Input: goodix - add GT5663 CTP support GT5663 is capacitive touch controller with customized smart wakeup gestures. Add support for it by adding compatible and supported chip data. The chip data on GT5663 is similar to GT1151, like - config data register has 0x8050 address - config data register max len is 240 - config data checksum has 16-bit Signed-off-by: Jagan Teki Reviewed-by: Rob Herring Signed-off-by: Dmitry Torokhov --- Documentation/devicetree/bindings/input/touchscreen/goodix.txt | 1 + drivers/input/touchscreen/goodix.c | 2 ++ 2 files changed, 3 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/input/touchscreen/goodix.txt b/Documentation/devicetree/bindings/input/touchscreen/goodix.txt index 255673250bbd..fc03ea4cf5ab 100644 --- a/Documentation/devicetree/bindings/input/touchscreen/goodix.txt +++ b/Documentation/devicetree/bindings/input/touchscreen/goodix.txt @@ -3,6 +3,7 @@ Device tree bindings for Goodix GT9xx series touchscreen controller Required properties: - compatible : Should be "goodix,gt1151" + or "goodix,gt5663" or "goodix,gt5688" or "goodix,gt911" or "goodix,gt9110" diff --git a/drivers/input/touchscreen/goodix.c b/drivers/input/touchscreen/goodix.c index b1c071fd243a..f7c1d168dd89 100644 --- a/drivers/input/touchscreen/goodix.c +++ b/drivers/input/touchscreen/goodix.c @@ -219,6 +219,7 @@ static const struct goodix_chip_data *goodix_get_chip_data(u16 id) { switch (id) { case 1151: + case 5663: case 5688: return >1x_chip_data; @@ -997,6 +998,7 @@ MODULE_DEVICE_TABLE(acpi, goodix_acpi_match); #ifdef CONFIG_OF static const struct of_device_id goodix_of_match[] = { { .compatible = "goodix,gt1151" }, + { .compatible = "goodix,gt5663" }, { .compatible = "goodix,gt5688" }, { .compatible = "goodix,gt911" }, { .compatible = "goodix,gt9110" }, -- cgit v1.2.3 From 5328efce9461ce39c04e7b0b6eec563f5ac1f3e9 Mon Sep 17 00:00:00 2001 From: Jan Kotas Date: Wed, 27 Mar 2019 14:44:04 +0000 Subject: scsi: dt-bindings: ufs-cdns: Update Cadence UFS compatibility list This patch adds a new compatible string description for CDNS UFS HCD + M31 16nm PHY. Signed-off-by: Jan Kotas Reviewed-by: Rob Herring Signed-off-by: Martin K. Petersen --- Documentation/devicetree/bindings/ufs/cdns,ufshc.txt | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/ufs/cdns,ufshc.txt b/Documentation/devicetree/bindings/ufs/cdns,ufshc.txt index a04a4989ec7f..02347b017abd 100644 --- a/Documentation/devicetree/bindings/ufs/cdns,ufshc.txt +++ b/Documentation/devicetree/bindings/ufs/cdns,ufshc.txt @@ -5,8 +5,9 @@ Each UFS controller instance should have its own node. Please see the ufshcd-pltfrm.txt for a list of all available properties. Required properties: -- compatible : Compatible list, contains the following controller: - "cdns,ufshc" +- compatible : Compatible list, contains one of the following controllers: + "cdns,ufshc" - Generic CDNS HCI, + "cdns,ufshc-m31-16nm" - CDNS UFS HC + M31 16nm PHY complemented with the JEDEC version: "jedec,ufs-2.0" -- cgit v1.2.3 From 55dc9b3c3156f469d1de209ea03afafeaf6fca08 Mon Sep 17 00:00:00 2001 From: Stanley Chu Date: Fri, 29 Mar 2019 23:32:47 +0800 Subject: scsi: dt-bindings: ufs: Remove custom property "-fixed-regulator" Custom device tree property "-fixed-regulator" can be removed because, 1) It is not used anywhere in tree. 2) All handlings for "-fixed-regulator" have been removed in UFS driver. 3) There is no issue if an existed regulator defined "-fixed-regulator" property in device tree. Signed-off-by: Stanley Chu Signed-off-by: Martin K. Petersen --- Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt | 2 -- 1 file changed, 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt b/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt index 5111e9130bc3..f3140cffc54d 100644 --- a/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt +++ b/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt @@ -31,7 +31,6 @@ Optional properties: - vcc-max-microamp : specifies max. load that can be drawn from vcc supply - vccq-max-microamp : specifies max. load that can be drawn from vccq supply - vccq2-max-microamp : specifies max. load that can be drawn from vccq2 supply -- -fixed-regulator : boolean property specifying that -supply is a fixed regulator - clocks : List of phandle and clock specifier pairs - clock-names : List of clock input name strings sorted in the same @@ -63,7 +62,6 @@ Example: interrupts = <0 28 0>; vdd-hba-supply = <&xxx_reg0>; - vdd-hba-fixed-regulator; vcc-supply = <&xxx_reg1>; vcc-supply-1p8; vccq-supply = <&xxx_reg2>; -- cgit v1.2.3 From c9d61a5aa39025caee2971dac7f471fbe761cb27 Mon Sep 17 00:00:00 2001 From: Stanley Chu Date: Fri, 29 Mar 2019 23:32:48 +0800 Subject: scsi: dt-bindings: ufs: Add VCC capability on MediaTek UFS driver Add VCC supply for ufs-mediatek driver to provide power-saving operation during low-power modes. For example VCC can be turned-off during system suspend and turned-on after system is resumed. Signed-off-by: Stanley Chu Signed-off-by: Martin K. Petersen --- Documentation/devicetree/bindings/ufs/ufs-mediatek.txt | 3 +++ 1 file changed, 3 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/ufs/ufs-mediatek.txt b/Documentation/devicetree/bindings/ufs/ufs-mediatek.txt index e25c007b95d7..72aab8547308 100644 --- a/Documentation/devicetree/bindings/ufs/ufs-mediatek.txt +++ b/Documentation/devicetree/bindings/ufs/ufs-mediatek.txt @@ -21,6 +21,7 @@ Required properties for UFS nodes: defined or a value in the array is "0" then it is assumed that the frequency is set by the parent clock or a fixed rate clock source. +- vcc-supply : phandle to VCC supply regulator node. Example: @@ -37,4 +38,6 @@ Example: clocks = <&infracfg_ao INFRACFG_AO_UFS_CG>; clock-names = "ufs"; freq-table-hz = <0 0>; + + vcc-supply = <&mt_pmic_vemc_ldo_reg>; }; -- cgit v1.2.3 From e3097b6b2e0d791a462b337941e9176c533d39f3 Mon Sep 17 00:00:00 2001 From: Charles Keepax Date: Tue, 19 Mar 2019 13:48:50 +0000 Subject: pinctrl: lochnagar: Add initial binding documentation Lochnagar is an evaluation and development board for Cirrus Logic Smart CODEC and Amp devices. It allows the connection of most Cirrus Logic devices on mini-cards, as well as allowing connection of various application processor systems to provide a full evaluation platform. This driver supports the board controller chip on the Lochnagar board. Signed-off-by: Charles Keepax Reviewed-by: Rob Herring Acked-by: Linus Walleij Signed-off-by: Linus Walleij --- .../bindings/pinctrl/cirrus,lochnagar.txt | 141 +++++++++++++++++++++ 1 file changed, 141 insertions(+) create mode 100644 Documentation/devicetree/bindings/pinctrl/cirrus,lochnagar.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/pinctrl/cirrus,lochnagar.txt b/Documentation/devicetree/bindings/pinctrl/cirrus,lochnagar.txt new file mode 100644 index 000000000000..a87447180e83 --- /dev/null +++ b/Documentation/devicetree/bindings/pinctrl/cirrus,lochnagar.txt @@ -0,0 +1,141 @@ +Cirrus Logic Lochnagar Audio Development Board + +Lochnagar is an evaluation and development board for Cirrus Logic +Smart CODEC and Amp devices. It allows the connection of most Cirrus +Logic devices on mini-cards, as well as allowing connection of +various application processor systems to provide a full evaluation +platform. Audio system topology, clocking and power can all be +controlled through the Lochnagar, allowing the device under test +to be used in a variety of possible use cases. + +This binding document describes the binding for the pinctrl portion +of the driver. + +Also see these documents for generic binding information: + [1] GPIO : ../gpio/gpio.txt + [2] Pinctrl: ../pinctrl/pinctrl-bindings.txt + +And these for relevant defines: + [3] include/dt-bindings/pinctrl/lochnagar.h + +This binding must be part of the Lochnagar MFD binding: + [4] ../mfd/cirrus,lochnagar.txt + +Required properties: + + - compatible : One of the following strings: + "cirrus,lochnagar-pinctrl" + + - gpio-controller : Indicates this device is a GPIO controller. + - #gpio-cells : Must be 2. The first cell is the pin number, see + [3] for available pins and the second cell is used to specify + optional parameters, see [1]. + - gpio-ranges : Range of pins managed by the GPIO controller, see + [1]. Both the GPIO and Pinctrl base should be set to zero and the + count to the appropriate of the LOCHNAGARx_PIN_NUM_GPIOS define, + see [3]. + + - pinctrl-names : A pinctrl state named "default" must be defined. + - pinctrl-0 : A phandle to the default pinctrl state. + +Required sub-nodes: + +The pin configurations are defined as a child of the pinctrl states +node, see [2]. Each sub-node can have the following properties: + - groups : A list of groups to select (either this or "pins" must be + specified), available groups: + codec-aif1, codec-aif2, codec-aif3, dsp-aif1, dsp-aif2, psia1, + psia2, gf-aif1, gf-aif2, gf-aif3, gf-aif4, spdif-aif, usb-aif1, + usb-aif2, adat-aif, soundcard-aif + - pins : A list of pin names to select (either this or "groups" must + be specified), available pins: + fpga-gpio1, fpga-gpio2, fpga-gpio3, fpga-gpio4, fpga-gpio5, + fpga-gpio6, codec-gpio1, codec-gpio2, codec-gpio3, codec-gpio4, + codec-gpio5, codec-gpio6, codec-gpio7, codec-gpio8, dsp-gpio1, + dsp-gpio2, dsp-gpio3, dsp-gpio4, dsp-gpio5, dsp-gpio6, gf-gpio2, + gf-gpio3, gf-gpio7, codec-aif1-bclk, codec-aif1-rxdat, + codec-aif1-lrclk, codec-aif1-txdat, codec-aif2-bclk, + codec-aif2-rxdat, codec-aif2-lrclk, codec-aif2-txdat, + codec-aif3-bclk, codec-aif3-rxdat, codec-aif3-lrclk, + codec-aif3-txdat, dsp-aif1-bclk, dsp-aif1-rxdat, dsp-aif1-lrclk, + dsp-aif1-txdat, dsp-aif2-bclk, dsp-aif2-rxdat, + dsp-aif2-lrclk, dsp-aif2-txdat, psia1-bclk, psia1-rxdat, + psia1-lrclk, psia1-txdat, psia2-bclk, psia2-rxdat, psia2-lrclk, + psia2-txdat, gf-aif3-bclk, gf-aif3-rxdat, gf-aif3-lrclk, + gf-aif3-txdat, gf-aif4-bclk, gf-aif4-rxdat, gf-aif4-lrclk, + gf-aif4-txdat, gf-aif1-bclk, gf-aif1-rxdat, gf-aif1-lrclk, + gf-aif1-txdat, gf-aif2-bclk, gf-aif2-rxdat, gf-aif2-lrclk, + gf-aif2-txdat, dsp-uart1-rx, dsp-uart1-tx, dsp-uart2-rx, + dsp-uart2-tx, gf-uart2-rx, gf-uart2-tx, usb-uart-rx, + codec-pdmclk1, codec-pdmdat1, codec-pdmclk2, codec-pdmdat2, + codec-dmicclk1, codec-dmicdat1, codec-dmicclk2, codec-dmicdat2, + codec-dmicclk3, codec-dmicdat3, codec-dmicclk4, codec-dmicdat4, + dsp-dmicclk1, dsp-dmicdat1, dsp-dmicclk2, dsp-dmicdat2, i2c2-scl, + i2c2-sda, i2c3-scl, i2c3-sda, i2c4-scl, i2c4-sda, dsp-standby, + codec-mclk1, codec-mclk2, dsp-clkin, psia1-mclk, psia2-mclk, + gf-gpio1, gf-gpio5, dsp-gpio20, led1, led2 + - function : The mux function to select, available functions: + aif, fpga-gpio1, fpga-gpio2, fpga-gpio3, fpga-gpio4, fpga-gpio5, + fpga-gpio6, codec-gpio1, codec-gpio2, codec-gpio3, codec-gpio4, + codec-gpio5, codec-gpio6, codec-gpio7, codec-gpio8, dsp-gpio1, + dsp-gpio2, dsp-gpio3, dsp-gpio4, dsp-gpio5, dsp-gpio6, gf-gpio2, + gf-gpio3, gf-gpio7, gf-gpio1, gf-gpio5, dsp-gpio20, codec-clkout, + dsp-clkout, pmic-32k, spdif-clkout, clk-12m288, clk-11m2986, + clk-24m576, clk-22m5792, xmos-mclk, gf-clkout1, gf-mclk1, + gf-mclk3, gf-mclk2, gf-clkout2, codec-mclk1, codec-mclk2, + dsp-clkin, psia1-mclk, psia2-mclk, spdif-mclk, codec-irq, + codec-reset, dsp-reset, dsp-irq, dsp-standby, codec-pdmclk1, + codec-pdmdat1, codec-pdmclk2, codec-pdmdat2, codec-dmicclk1, + codec-dmicdat1, codec-dmicclk2, codec-dmicdat2, codec-dmicclk3, + codec-dmicdat3, codec-dmicclk4, codec-dmicdat4, dsp-dmicclk1, + dsp-dmicdat1, dsp-dmicclk2, dsp-dmicdat2, dsp-uart1-rx, + dsp-uart1-tx, dsp-uart2-rx, dsp-uart2-tx, gf-uart2-rx, + gf-uart2-tx, usb-uart-rx, usb-uart-tx, i2c2-scl, i2c2-sda, + i2c3-scl, i2c3-sda, i2c4-scl, i2c4-sda, spdif-aif, psia1, + psia1-bclk, psia1-lrclk, psia1-rxdat, psia1-txdat, psia2, + psia2-bclk, psia2-lrclk, psia2-rxdat, psia2-txdat, codec-aif1, + codec-aif1-bclk, codec-aif1-lrclk, codec-aif1-rxdat, + codec-aif1-txdat, codec-aif2, codec-aif2-bclk, codec-aif2-lrclk, + codec-aif2-rxdat, codec-aif2-txdat, codec-aif3, codec-aif3-bclk, + codec-aif3-lrclk, codec-aif3-rxdat, codec-aif3-txdat, dsp-aif1, + dsp-aif1-bclk, dsp-aif1-lrclk, dsp-aif1-rxdat, dsp-aif1-txdat, + dsp-aif2, dsp-aif2-bclk, dsp-aif2-lrclk, dsp-aif2-rxdat, + dsp-aif2-txdat, gf-aif3, gf-aif3-bclk, gf-aif3-lrclk, + gf-aif3-rxdat, gf-aif3-txdat, gf-aif4, gf-aif4-bclk, + gf-aif4-lrclk, gf-aif4-rxdat, gf-aif4-txdat, gf-aif1, + gf-aif1-bclk, gf-aif1-lrclk, gf-aif1-rxdat, gf-aif1-txdat, + gf-aif2, gf-aif2-bclk, gf-aif2-lrclk, gf-aif2-rxdat, + gf-aif2-txdat, usb-aif1, usb-aif2, adat-aif, soundcard-aif, + + - output-enable : Specifies that an AIF group will be used as a master + interface (either this or input-enable is required if a group is + being muxed to an AIF) + - input-enable : Specifies that an AIF group will be used as a slave + interface (either this or output-enable is required if a group is + being muxed to an AIF) + +Example: + +lochnagar-pinctrl { + compatible = "cirrus,lochnagar-pinctrl"; + + gpio-controller; + #gpio-cells = <2>; + gpio-ranges = <&lochnagar 0 0 LOCHNAGAR2_PIN_NUM_GPIOS>; + + pinctrl-names = "default"; + pinctrl-0 = <&pin-settings>; + + pin-settings: pin-settings { + ap-aif { + input-enable; + groups = "gf-aif1"; + function = "codec-aif3"; + }; + codec-aif { + output-enable; + groups = "codec-aif3"; + function = "gf-aif1"; + }; + }; +}; -- cgit v1.2.3 From 87b7cbbc704ded68183e13e9382455e10e5c0e8e Mon Sep 17 00:00:00 2001 From: Linus Walleij Date: Tue, 19 Mar 2019 08:40:13 +0100 Subject: rtc: x1205: Add DT bindings This adds device tree bindings for the Xircom X1205 RTC found in the Linksys NSLU2. Cc: devicetree@vger.kernel.org Signed-off-by: Linus Walleij [alexandre.belloni@bootlin.com: move doc to rtc.txt] Signed-off-by: Alexandre Belloni --- Documentation/devicetree/bindings/rtc/rtc.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/rtc/rtc.txt b/Documentation/devicetree/bindings/rtc/rtc.txt index f4687c68c08c..a97fc6a9a75e 100644 --- a/Documentation/devicetree/bindings/rtc/rtc.txt +++ b/Documentation/devicetree/bindings/rtc/rtc.txt @@ -69,3 +69,4 @@ ricoh,rv5c386 I2C bus SERIAL INTERFACE REAL-TIME CLOCK IC ricoh,rv5c387a I2C bus SERIAL INTERFACE REAL-TIME CLOCK IC sii,s35390a 2-wire CMOS real-time clock whwave,sd3078 I2C bus SERIAL INTERFACE REAL-TIME CLOCK IC +xircom,x1205 Xircom X1205 I2C RTC -- cgit v1.2.3 From e3b371109e01a9f12715e7d43a3a4e187c246ae3 Mon Sep 17 00:00:00 2001 From: Joel Stanley Date: Wed, 27 Mar 2019 11:32:14 +1030 Subject: dt-bindings: rtc: Add on-chip ASPEED RTC documentation Describe the RTC as used in the ASPEED BMC SoCs. Signed-off-by: Joel Stanley Signed-off-by: Alexandre Belloni --- .../devicetree/bindings/rtc/rtc-aspeed.txt | 22 ++++++++++++++++++++++ 1 file changed, 22 insertions(+) create mode 100644 Documentation/devicetree/bindings/rtc/rtc-aspeed.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/rtc/rtc-aspeed.txt b/Documentation/devicetree/bindings/rtc/rtc-aspeed.txt new file mode 100644 index 000000000000..2e956b3dc276 --- /dev/null +++ b/Documentation/devicetree/bindings/rtc/rtc-aspeed.txt @@ -0,0 +1,22 @@ +ASPEED BMC RTC +============== + +Required properties: + - compatible: should be one of the following + * aspeed,ast2400-rtc for the ast2400 + * aspeed,ast2500-rtc for the ast2500 + * aspeed,ast2600-rtc for the ast2600 + + - reg: physical base address of the controller and length of memory mapped + region + + - interrupts: The interrupt number + +Example: + + rtc@1e781000 { + compatible = "aspeed,ast2400-rtc"; + reg = <0x1e781000 0x18>; + interrupts = <22>; + status = "disabled"; + }; -- cgit v1.2.3 From 0e2e87779ab8699e1c9a82fbf08b9462c34fd974 Mon Sep 17 00:00:00 2001 From: Alexandre Belloni Date: Mon, 1 Apr 2019 18:08:11 +0200 Subject: rtc: pcf85063: differentiate pcf85063a and pcf85063tp As stated in a comment pcf85063a and pcf85063tp don't have the same number of registers. Especially, pcf85063tp doesn't have alarm support. Signed-off-by: Alexandre Belloni --- .../devicetree/bindings/rtc/nxp,pcf85063.txt | 5 +++- drivers/rtc/rtc-pcf85063.c | 33 ++++++++++++++++++---- 2 files changed, 31 insertions(+), 7 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/rtc/nxp,pcf85063.txt b/Documentation/devicetree/bindings/rtc/nxp,pcf85063.txt index d3e380ad712d..1e31afbfffe9 100644 --- a/Documentation/devicetree/bindings/rtc/nxp,pcf85063.txt +++ b/Documentation/devicetree/bindings/rtc/nxp,pcf85063.txt @@ -1,7 +1,10 @@ * NXP PCF85063 Real Time Clock Required properties: -- compatible: Should contain "nxp,pcf85063". +- compatible: Should one of contain: + "nxp,pcf85063", + "nxp,pcf85063a", + "nxp,pcf85063tp" - reg: I2C address for chip. Optional property: diff --git a/drivers/rtc/rtc-pcf85063.c b/drivers/rtc/rtc-pcf85063.c index 37be02a17add..cba60e7031c3 100644 --- a/drivers/rtc/rtc-pcf85063.c +++ b/drivers/rtc/rtc-pcf85063.c @@ -30,6 +30,10 @@ #define PCF85063_REG_SC 0x04 /* datetime */ #define PCF85063_REG_SC_OS 0x80 +struct pcf85063_config { + struct regmap_config regmap; +}; + struct pcf85063 { struct rtc_device *rtc; struct regmap *regmap; @@ -147,10 +151,20 @@ static int pcf85063_load_capacitance(struct pcf85063 *pcf85063, PCF85063_REG_CTRL1_CAP_SEL, reg); } -static const struct regmap_config regmap_config = { - .reg_bits = 8, - .val_bits = 8, - .max_register = 0x11, +static const struct pcf85063_config pcf85063a_config = { + .regmap = { + .reg_bits = 8, + .val_bits = 8, + .max_register = 0x11, + }, +}; + +static const struct pcf85063_config pcf85063tp_config = { + .regmap = { + .reg_bits = 8, + .val_bits = 8, + .max_register = 0x0a, + }, }; static int pcf85063_probe(struct i2c_client *client) @@ -158,6 +172,8 @@ static int pcf85063_probe(struct i2c_client *client) struct pcf85063 *pcf85063; unsigned int tmp; int err; + const struct pcf85063_config *config = &pcf85063tp_config; + const void *data = of_device_get_match_data(&client->dev); dev_dbg(&client->dev, "%s\n", __func__); @@ -166,7 +182,10 @@ static int pcf85063_probe(struct i2c_client *client) if (!pcf85063) return -ENOMEM; - pcf85063->regmap = devm_regmap_init_i2c(client, ®map_config); + if (data) + config = data; + + pcf85063->regmap = devm_regmap_init_i2c(client, &config->regmap); if (IS_ERR(pcf85063->regmap)) return PTR_ERR(pcf85063->regmap); @@ -196,7 +215,9 @@ static int pcf85063_probe(struct i2c_client *client) #ifdef CONFIG_OF static const struct of_device_id pcf85063_of_match[] = { - { .compatible = "nxp,pcf85063" }, + { .compatible = "nxp,pcf85063", .data = &pcf85063tp_config }, + { .compatible = "nxp,pcf85063tp", .data = &pcf85063tp_config }, + { .compatible = "nxp,pcf85063a", .data = &pcf85063a_config }, {} }; MODULE_DEVICE_TABLE(of, pcf85063_of_match); -- cgit v1.2.3 From 5b3a3ade02937ab9c5aac2a9a36c6c81e1327eb8 Mon Sep 17 00:00:00 2001 From: Alexandre Belloni Date: Mon, 1 Apr 2019 18:08:13 +0200 Subject: rtc: pcf85063: add Micro Crystal RV8263 support The Micro Crystal RV8263 has the same IC as the pcf85063 but has an on board crystal. This means that the CAP_SEL bit has to be cleared so the correct capacitance is selected for the crystal. Signed-off-by: Alexandre Belloni --- .../devicetree/bindings/rtc/nxp,pcf85063.txt | 3 +- drivers/rtc/rtc-pcf85063.c | 32 +++++++++++++++++++--- 2 files changed, 30 insertions(+), 5 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/rtc/nxp,pcf85063.txt b/Documentation/devicetree/bindings/rtc/nxp,pcf85063.txt index 1e31afbfffe9..627bb533eff7 100644 --- a/Documentation/devicetree/bindings/rtc/nxp,pcf85063.txt +++ b/Documentation/devicetree/bindings/rtc/nxp,pcf85063.txt @@ -4,7 +4,8 @@ Required properties: - compatible: Should one of contain: "nxp,pcf85063", "nxp,pcf85063a", - "nxp,pcf85063tp" + "nxp,pcf85063tp", + "microcrystal,rv8263" - reg: I2C address for chip. Optional property: diff --git a/drivers/rtc/rtc-pcf85063.c b/drivers/rtc/rtc-pcf85063.c index 2131c55316f6..ba4e75fbf258 100644 --- a/drivers/rtc/rtc-pcf85063.c +++ b/drivers/rtc/rtc-pcf85063.c @@ -5,6 +5,9 @@ * * Author: Søren Andersen * Maintainers: http://www.nslu2-linux.org/ + * + * Copyright (C) 2019 Micro Crystal AG + * Author: Alexandre Belloni */ #include #include @@ -22,7 +25,10 @@ * * PCF85063A -- Rev. 6 — 18 November 2015 * PCF85063TP -- Rev. 4 — 6 May 2015 -*/ + * + * https://www.microcrystal.com/fileadmin/Media/Products/RTC/App.Manual/RV-8263-C7_App-Manual.pdf + * RV8263 -- Rev. 1.0 — January 2019 + */ #define PCF85063_REG_CTRL1 0x00 /* status */ #define PCF85063_REG_CTRL1_CAP_SEL BIT(0) @@ -41,6 +47,7 @@ struct pcf85063_config { struct regmap_config regmap; unsigned has_alarms:1; + unsigned force_cap_7000:1; }; struct pcf85063 { @@ -230,12 +237,17 @@ static const struct rtc_class_ops pcf85063_rtc_ops_alarm = { }; static int pcf85063_load_capacitance(struct pcf85063 *pcf85063, - const struct device_node *np) + const struct device_node *np, + unsigned int force_cap) { u32 load = 7000; u8 reg = 0; - of_property_read_u32(np, "quartz-load-femtofarads", &load); + if (force_cap) + load = force_cap; + else + of_property_read_u32(np, "quartz-load-femtofarads", &load); + switch (load) { default: dev_warn(&pcf85063->rtc->dev, "Unknown quartz-load-femtofarads value: %d. Assuming 7000", @@ -269,6 +281,16 @@ static const struct pcf85063_config pcf85063tp_config = { }, }; +static const struct pcf85063_config rv8263_config = { + .regmap = { + .reg_bits = 8, + .val_bits = 8, + .max_register = 0x11, + }, + .has_alarms = 1, + .force_cap_7000 = 1, +}; + static int pcf85063_probe(struct i2c_client *client) { struct pcf85063 *pcf85063; @@ -303,7 +325,8 @@ static int pcf85063_probe(struct i2c_client *client) if (IS_ERR(pcf85063->rtc)) return PTR_ERR(pcf85063->rtc); - err = pcf85063_load_capacitance(pcf85063, client->dev.of_node); + err = pcf85063_load_capacitance(pcf85063, client->dev.of_node, + config->force_cap_7000 ? 7000 : 0); if (err < 0) dev_warn(&client->dev, "failed to set xtal load capacitance: %d", err); @@ -339,6 +362,7 @@ static const struct of_device_id pcf85063_of_match[] = { { .compatible = "nxp,pcf85063", .data = &pcf85063tp_config }, { .compatible = "nxp,pcf85063tp", .data = &pcf85063tp_config }, { .compatible = "nxp,pcf85063a", .data = &pcf85063a_config }, + { .compatible = "microcrystal,rv8263", .data = &rv8263_config }, {} }; MODULE_DEVICE_TABLE(of, pcf85063_of_match); -- cgit v1.2.3 From 6bfff707985fff14fa79c851e53f9630e76a4860 Mon Sep 17 00:00:00 2001 From: Sugar Zhang Date: Thu, 4 Apr 2019 11:53:15 +0800 Subject: dt-bindings: sound: rockchip: add compatible for rk3308/px30 This patch adds bindings for rk3308/px30. Signed-off-by: Sugar Zhang Signed-off-by: Mark Brown --- Documentation/devicetree/bindings/sound/rockchip,pdm.txt | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/sound/rockchip,pdm.txt b/Documentation/devicetree/bindings/sound/rockchip,pdm.txt index 47f164fbd1d7..3e0eb7354ba6 100644 --- a/Documentation/devicetree/bindings/sound/rockchip,pdm.txt +++ b/Documentation/devicetree/bindings/sound/rockchip,pdm.txt @@ -3,6 +3,8 @@ Required properties: - compatible: "rockchip,pdm" + - "rockchip,px30-pdm" + - "rockchip,rk3308-pdm" - reg: physical base address of the controller and length of memory mapped region. - dmas: DMA specifiers for rx dma. See the DMA client binding, @@ -12,6 +14,8 @@ Required properties: - clock-names: should contain following: - "pdm_hclk": clock for PDM BUS - "pdm_clk" : clock for PDM controller +- resets: a list of phandle + reset-specifer paris, one for each entry in reset-names. +- reset-names: reset names, should include "pdm-m". - pinctrl-names: Must contain a "default" entry. - pinctrl-N: One property must exist for each entry in pinctrl-names. See ../pinctrl/pinctrl-bindings.txt -- cgit v1.2.3 From 2a050b7a746e2c59a733a3641eb1c01cf2e573b4 Mon Sep 17 00:00:00 2001 From: Sugar Zhang Date: Thu, 4 Apr 2019 11:55:45 +0800 Subject: dt-bindings: sound: add compatible for rk1808 This patch adds bindings for rk1808 soc. Signed-off-by: Sugar Zhang Signed-off-by: Mark Brown --- Documentation/devicetree/bindings/sound/rockchip,pdm.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/sound/rockchip,pdm.txt b/Documentation/devicetree/bindings/sound/rockchip,pdm.txt index 3e0eb7354ba6..98572a25122f 100644 --- a/Documentation/devicetree/bindings/sound/rockchip,pdm.txt +++ b/Documentation/devicetree/bindings/sound/rockchip,pdm.txt @@ -4,6 +4,7 @@ Required properties: - compatible: "rockchip,pdm" - "rockchip,px30-pdm" + - "rockchip,rk1808-pdm" - "rockchip,rk3308-pdm" - reg: physical base address of the controller and length of memory mapped region. -- cgit v1.2.3 From ae40e94fca6d5747f85188d01686df350e524019 Mon Sep 17 00:00:00 2001 From: Ondrej Jirman Date: Mon, 1 Apr 2019 13:56:15 +0200 Subject: dt-bindings: gnss: add u-blox,neo-6m compatible Add compatible for u-blox NEO-6M GPS module. Signed-off-by: Ondrej Jirman Reviewed-by: Rob Herring Signed-off-by: Johan Hovold --- Documentation/devicetree/bindings/gnss/u-blox.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/gnss/u-blox.txt b/Documentation/devicetree/bindings/gnss/u-blox.txt index e475659cb85f..7cdefd058fe0 100644 --- a/Documentation/devicetree/bindings/gnss/u-blox.txt +++ b/Documentation/devicetree/bindings/gnss/u-blox.txt @@ -9,6 +9,7 @@ Required properties: - compatible : Must be one of + "u-blox,neo-6m" "u-blox,neo-8" "u-blox,neo-m8" -- cgit v1.2.3 From 26bde6ad6d59b2e1347995de6198205ef6138b52 Mon Sep 17 00:00:00 2001 From: Olivier Moysan Date: Wed, 3 Apr 2019 15:23:31 +0200 Subject: ASoC: dt-bindings: update cs42l51 bindings Add compatible, reg, regulator, and reset to Cirrus CS42L51 audio codec bindings. Signed-off-by: Olivier Moysan Signed-off-by: Mark Brown --- Documentation/devicetree/bindings/sound/cs42l51.txt | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/sound/cs42l51.txt b/Documentation/devicetree/bindings/sound/cs42l51.txt index 4b5de33ce377..acbd68ddd2cb 100644 --- a/Documentation/devicetree/bindings/sound/cs42l51.txt +++ b/Documentation/devicetree/bindings/sound/cs42l51.txt @@ -1,6 +1,17 @@ CS42L51 audio CODEC +Required properties: + + - compatible : "cirrus,cs42l51" + + - reg : the I2C address of the device for I2C. + Optional properties: + - VL-supply, VD-supply, VA-supply, VAHP-supply: power supplies for the device, + as covered in Documentation/devicetree/bindings/regulator/regulator.txt. + + - reset-gpios : GPIO specification for the reset pin. If specified, it will be + deasserted before starting the communication with the codec. - clocks : a list of phandles + clock-specifiers, one for each entry in clock-names @@ -14,4 +25,9 @@ cs42l51: cs42l51@4a { reg = <0x4a>; clocks = <&mclk_prov>; clock-names = "MCLK"; + VL-supply = <®_audio>; + VD-supply = <®_audio>; + VA-supply = <®_audio>; + VAHP-supply = <®_audio>; + reset-gpios = <&gpiog 9 GPIO_ACTIVE_LOW>; }; -- cgit v1.2.3 From 24062fe85860debfdae0eeaa495f27c9971ec163 Mon Sep 17 00:00:00 2001 From: Shameer Kolothum Date: Tue, 26 Mar 2019 15:17:53 +0000 Subject: perf/smmuv3: Enable HiSilicon Erratum 162001800 quirk HiSilicon erratum 162001800 describes the limitation of SMMUv3 PMCG implementation on HiSilicon Hip08 platforms. On these platforms, the PMCG event counter registers (SMMU_PMCG_EVCNTRn) are read only and as a result it is not possible to set the initial counter period value on event monitor start. To work around this, the current value of the counter is read and used for delta calculations. OEM information from ACPI header is used to identify the affected hardware platforms. Signed-off-by: Shameer Kolothum Reviewed-by: Hanjun Guo Reviewed-by: Robin Murphy Acked-by: Lorenzo Pieralisi [will: update silicon-errata.txt and add reason string to acpi match] Signed-off-by: Will Deacon --- Documentation/arm64/silicon-errata.txt | 1 + drivers/acpi/arm64/iort.c | 16 +++++++++++- drivers/perf/arm_smmuv3_pmu.c | 48 +++++++++++++++++++++++++++++----- include/linux/acpi_iort.h | 1 + 4 files changed, 58 insertions(+), 8 deletions(-) (limited to 'Documentation') diff --git a/Documentation/arm64/silicon-errata.txt b/Documentation/arm64/silicon-errata.txt index d1e2bb801e1b..c00efb639e46 100644 --- a/Documentation/arm64/silicon-errata.txt +++ b/Documentation/arm64/silicon-errata.txt @@ -77,6 +77,7 @@ stable kernels. | Hisilicon | Hip0{5,6,7} | #161010101 | HISILICON_ERRATUM_161010101 | | Hisilicon | Hip0{6,7} | #161010701 | N/A | | Hisilicon | Hip07 | #161600802 | HISILICON_ERRATUM_161600802 | +| Hisilicon | Hip08 SMMU PMCG | #162001800 | N/A | | | | | | | Qualcomm Tech. | Kryo/Falkor v1 | E1003 | QCOM_FALKOR_ERRATUM_1003 | | Qualcomm Tech. | Falkor v1 | E1009 | QCOM_FALKOR_ERRATUM_1009 | diff --git a/drivers/acpi/arm64/iort.c b/drivers/acpi/arm64/iort.c index e2c9b26bbee6..2d70b349bd6c 100644 --- a/drivers/acpi/arm64/iort.c +++ b/drivers/acpi/arm64/iort.c @@ -1366,9 +1366,23 @@ static void __init arm_smmu_v3_pmcg_init_resources(struct resource *res, ACPI_EDGE_SENSITIVE, &res[2]); } +static struct acpi_platform_list pmcg_plat_info[] __initdata = { + /* HiSilicon Hip08 Platform */ + {"HISI ", "HIP08 ", 0, ACPI_SIG_IORT, greater_than_or_equal, + "Erratum #162001800", IORT_SMMU_V3_PMCG_HISI_HIP08}, + { } +}; + static int __init arm_smmu_v3_pmcg_add_platdata(struct platform_device *pdev) { - u32 model = IORT_SMMU_V3_PMCG_GENERIC; + u32 model; + int idx; + + idx = acpi_match_platform_list(pmcg_plat_info); + if (idx >= 0) + model = pmcg_plat_info[idx].data; + else + model = IORT_SMMU_V3_PMCG_GENERIC; return platform_device_add_data(pdev, &model, sizeof(model)); } diff --git a/drivers/perf/arm_smmuv3_pmu.c b/drivers/perf/arm_smmuv3_pmu.c index a4f4b488a2de..da71c741cb46 100644 --- a/drivers/perf/arm_smmuv3_pmu.c +++ b/drivers/perf/arm_smmuv3_pmu.c @@ -35,6 +35,7 @@ */ #include +#include #include #include #include @@ -93,6 +94,8 @@ #define SMMU_PMCG_PA_SHIFT 12 +#define SMMU_PMCG_EVCNTR_RDONLY BIT(0) + static int cpuhp_state_num; struct smmu_pmu { @@ -108,6 +111,7 @@ struct smmu_pmu { void __iomem *reg_base; void __iomem *reloc_base; u64 counter_mask; + u32 options; bool global_filter; u32 global_filter_span; u32 global_filter_sid; @@ -222,15 +226,27 @@ static void smmu_pmu_set_period(struct smmu_pmu *smmu_pmu, u32 idx = hwc->idx; u64 new; - /* - * We limit the max period to half the max counter value of the counter - * size, so that even in the case of extreme interrupt latency the - * counter will (hopefully) not wrap past its initial value. - */ - new = smmu_pmu->counter_mask >> 1; + if (smmu_pmu->options & SMMU_PMCG_EVCNTR_RDONLY) { + /* + * On platforms that require this quirk, if the counter starts + * at < half_counter value and wraps, the current logic of + * handling the overflow may not work. It is expected that, + * those platforms will have full 64 counter bits implemented + * so that such a possibility is remote(eg: HiSilicon HIP08). + */ + new = smmu_pmu_counter_get_value(smmu_pmu, idx); + } else { + /* + * We limit the max period to half the max counter value + * of the counter size, so that even in the case of extreme + * interrupt latency the counter will (hopefully) not wrap + * past its initial value. + */ + new = smmu_pmu->counter_mask >> 1; + smmu_pmu_counter_set_value(smmu_pmu, idx, new); + } local64_set(&hwc->prev_count, new); - smmu_pmu_counter_set_value(smmu_pmu, idx, new); } static void smmu_pmu_set_event_filter(struct perf_event *event, @@ -665,6 +681,22 @@ static void smmu_pmu_reset(struct smmu_pmu *smmu_pmu) smmu_pmu->reloc_base + SMMU_PMCG_OVSCLR0); } +static void smmu_pmu_get_acpi_options(struct smmu_pmu *smmu_pmu) +{ + u32 model; + + model = *(u32 *)dev_get_platdata(smmu_pmu->dev); + + switch (model) { + case IORT_SMMU_V3_PMCG_HISI_HIP08: + /* HiSilicon Erratum 162001800 */ + smmu_pmu->options |= SMMU_PMCG_EVCNTR_RDONLY; + break; + } + + dev_notice(smmu_pmu->dev, "option mask 0x%x\n", smmu_pmu->options); +} + static int smmu_pmu_probe(struct platform_device *pdev) { struct smmu_pmu *smmu_pmu; @@ -744,6 +776,8 @@ static int smmu_pmu_probe(struct platform_device *pdev) return -EINVAL; } + smmu_pmu_get_acpi_options(smmu_pmu); + /* Pick one CPU to be the preferred one to use */ smmu_pmu->on_cpu = raw_smp_processor_id(); WARN_ON(irq_set_affinity_hint(smmu_pmu->irq, diff --git a/include/linux/acpi_iort.h b/include/linux/acpi_iort.h index 052ef7b9f985..723e4dfa1c14 100644 --- a/include/linux/acpi_iort.h +++ b/include/linux/acpi_iort.h @@ -32,6 +32,7 @@ * do with hardware or with IORT specification. */ #define IORT_SMMU_V3_PMCG_GENERIC 0x00000000 /* Generic SMMUv3 PMCG */ +#define IORT_SMMU_V3_PMCG_HISI_HIP08 0x00000001 /* HiSilicon HIP08 PMCG */ int iort_register_domain_token(int trans_id, phys_addr_t base, struct fwnode_handle *fw_node); -- cgit v1.2.3 From 08d9dbe72b1f899468b2b34f9309e88a84f440f2 Mon Sep 17 00:00:00 2001 From: Keith Busch Date: Mon, 11 Mar 2019 14:56:00 -0600 Subject: node: Link memory nodes to their compute nodes Systems may be constructed with various specialized nodes. Some nodes may provide memory, some provide compute devices that access and use that memory, and others may provide both. Nodes that provide memory are referred to as memory targets, and nodes that can initiate memory access are referred to as memory initiators. Memory targets will often have varying access characteristics from different initiators, and platforms may have ways to express those relationships. In preparation for these systems, provide interfaces for the kernel to export the memory relationship among different nodes memory targets and their initiators with symlinks to each other. If a system provides access locality for each initiator-target pair, nodes may be grouped into ranked access classes relative to other nodes. The new interface allows a subsystem to register relationships of varying classes if available and desired to be exported. A memory initiator may have multiple memory targets in the same access class. The target memory's initiators in a given class indicate the nodes access characteristics share the same performance relative to other linked initiator nodes. Each target within an initiator's access class, though, do not necessarily perform the same as each other. A memory target node may have multiple memory initiators. All linked initiators in a target's class have the same access characteristics to that target. The following example show the nodes' new sysfs hierarchy for a memory target node 'Y' with access class 0 from initiator node 'X': # symlinks -v /sys/devices/system/node/nodeX/access0/ relative: /sys/devices/system/node/nodeX/access0/targets/nodeY -> ../../nodeY # symlinks -v /sys/devices/system/node/nodeY/access0/ relative: /sys/devices/system/node/nodeY/access0/initiators/nodeX -> ../../nodeX The new attributes are added to the sysfs stable documentation. Reviewed-by: Jonathan Cameron Signed-off-by: Keith Busch Reviewed-by: Rafael J. Wysocki Tested-by: Brice Goglin Signed-off-by: Greg Kroah-Hartman --- Documentation/ABI/stable/sysfs-devices-node | 25 ++++- drivers/base/node.c | 142 +++++++++++++++++++++++++++- include/linux/node.h | 6 ++ 3 files changed, 171 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/ABI/stable/sysfs-devices-node b/Documentation/ABI/stable/sysfs-devices-node index 3e90e1f3bf0a..433bcc04e542 100644 --- a/Documentation/ABI/stable/sysfs-devices-node +++ b/Documentation/ABI/stable/sysfs-devices-node @@ -90,4 +90,27 @@ Date: December 2009 Contact: Lee Schermerhorn Description: The node's huge page size control/query attributes. - See Documentation/admin-guide/mm/hugetlbpage.rst \ No newline at end of file + See Documentation/admin-guide/mm/hugetlbpage.rst + +What: /sys/devices/system/node/nodeX/accessY/ +Date: December 2018 +Contact: Keith Busch +Description: + The node's relationship to other nodes for access class "Y". + +What: /sys/devices/system/node/nodeX/accessY/initiators/ +Date: December 2018 +Contact: Keith Busch +Description: + The directory containing symlinks to memory initiator + nodes that have class "Y" access to this target node's + memory. CPUs and other memory initiators in nodes not in + the list accessing this node's memory may have different + performance. + +What: /sys/devices/system/node/nodeX/accessY/targets/ +Date: December 2018 +Contact: Keith Busch +Description: + The directory containing symlinks to memory targets that + this initiator node has class "Y" access. diff --git a/drivers/base/node.c b/drivers/base/node.c index 86d6cd92ce3d..6f4097680580 100644 --- a/drivers/base/node.c +++ b/drivers/base/node.c @@ -17,6 +17,7 @@ #include #include #include +#include #include #include @@ -59,6 +60,94 @@ static inline ssize_t node_read_cpulist(struct device *dev, static DEVICE_ATTR(cpumap, S_IRUGO, node_read_cpumask, NULL); static DEVICE_ATTR(cpulist, S_IRUGO, node_read_cpulist, NULL); +/** + * struct node_access_nodes - Access class device to hold user visible + * relationships to other nodes. + * @dev: Device for this memory access class + * @list_node: List element in the node's access list + * @access: The access class rank + */ +struct node_access_nodes { + struct device dev; + struct list_head list_node; + unsigned access; +}; +#define to_access_nodes(dev) container_of(dev, struct node_access_nodes, dev) + +static struct attribute *node_init_access_node_attrs[] = { + NULL, +}; + +static struct attribute *node_targ_access_node_attrs[] = { + NULL, +}; + +static const struct attribute_group initiators = { + .name = "initiators", + .attrs = node_init_access_node_attrs, +}; + +static const struct attribute_group targets = { + .name = "targets", + .attrs = node_targ_access_node_attrs, +}; + +static const struct attribute_group *node_access_node_groups[] = { + &initiators, + &targets, + NULL, +}; + +static void node_remove_accesses(struct node *node) +{ + struct node_access_nodes *c, *cnext; + + list_for_each_entry_safe(c, cnext, &node->access_list, list_node) { + list_del(&c->list_node); + device_unregister(&c->dev); + } +} + +static void node_access_release(struct device *dev) +{ + kfree(to_access_nodes(dev)); +} + +static struct node_access_nodes *node_init_node_access(struct node *node, + unsigned access) +{ + struct node_access_nodes *access_node; + struct device *dev; + + list_for_each_entry(access_node, &node->access_list, list_node) + if (access_node->access == access) + return access_node; + + access_node = kzalloc(sizeof(*access_node), GFP_KERNEL); + if (!access_node) + return NULL; + + access_node->access = access; + dev = &access_node->dev; + dev->parent = &node->dev; + dev->release = node_access_release; + dev->groups = node_access_node_groups; + if (dev_set_name(dev, "access%u", access)) + goto free; + + if (device_register(dev)) + goto free_name; + + pm_runtime_no_callbacks(dev); + list_add_tail(&access_node->list_node, &node->access_list); + return access_node; +free_name: + kfree_const(dev->kobj.name); +free: + kfree(access_node); + return NULL; +} + #define K(x) ((x) << (PAGE_SHIFT - 10)) static ssize_t node_read_meminfo(struct device *dev, struct device_attribute *attr, char *buf) @@ -340,7 +429,7 @@ static int register_node(struct node *node, int num) void unregister_node(struct node *node) { hugetlb_unregister_node(node); /* no-op, if memoryless node */ - + node_remove_accesses(node); device_unregister(&node->dev); } @@ -372,6 +461,56 @@ int register_cpu_under_node(unsigned int cpu, unsigned int nid) kobject_name(&node_devices[nid]->dev.kobj)); } +/** + * register_memory_node_under_compute_node - link memory node to its compute + * node for a given access class. + * @mem_node: Memory node number + * @cpu_node: Cpu node number + * @access: Access class to register + * + * Description: + * For use with platforms that may have separate memory and compute nodes. + * This function will export node relationships linking which memory + * initiator nodes can access memory targets at a given ranked access + * class. + */ +int register_memory_node_under_compute_node(unsigned int mem_nid, + unsigned int cpu_nid, + unsigned access) +{ + struct node *init_node, *targ_node; + struct node_access_nodes *initiator, *target; + int ret; + + if (!node_online(cpu_nid) || !node_online(mem_nid)) + return -ENODEV; + + init_node = node_devices[cpu_nid]; + targ_node = node_devices[mem_nid]; + initiator = node_init_node_access(init_node, access); + target = node_init_node_access(targ_node, access); + if (!initiator || !target) + return -ENOMEM; + + ret = sysfs_add_link_to_group(&initiator->dev.kobj, "targets", + &targ_node->dev.kobj, + dev_name(&targ_node->dev)); + if (ret) + return ret; + + ret = sysfs_add_link_to_group(&target->dev.kobj, "initiators", + &init_node->dev.kobj, + dev_name(&init_node->dev)); + if (ret) + goto err; + + return 0; + err: + sysfs_remove_link_from_group(&initiator->dev.kobj, "targets", + dev_name(&targ_node->dev)); + return ret; +} + int unregister_cpu_under_node(unsigned int cpu, unsigned int nid) { struct device *obj; @@ -580,6 +719,7 @@ int __register_one_node(int nid) register_cpu_under_node(cpu, nid); } + INIT_LIST_HEAD(&node_devices[nid]->access_list); /* initialize work queue for memory hot plug */ init_node_hugetlb_work(nid); diff --git a/include/linux/node.h b/include/linux/node.h index 257bb3d6d014..bb288817ed33 100644 --- a/include/linux/node.h +++ b/include/linux/node.h @@ -17,10 +17,12 @@ #include #include +#include #include struct node { struct device dev; + struct list_head access_list; #if defined(CONFIG_MEMORY_HOTPLUG_SPARSE) && defined(CONFIG_HUGETLBFS) struct work_struct node_work; @@ -75,6 +77,10 @@ extern int register_mem_sect_under_node(struct memory_block *mem_blk, extern int unregister_mem_sect_under_nodes(struct memory_block *mem_blk, unsigned long phys_index); +extern int register_memory_node_under_compute_node(unsigned int mem_nid, + unsigned int cpu_nid, + unsigned access); + #ifdef CONFIG_HUGETLBFS extern void register_hugetlbfs_with_node(node_registration_func_t doregister, node_registration_func_t unregister); -- cgit v1.2.3 From e1cf33aafb8462c7d0a0e6349925870316f040ee Mon Sep 17 00:00:00 2001 From: Keith Busch Date: Mon, 11 Mar 2019 14:56:01 -0600 Subject: node: Add heterogenous memory access attributes Heterogeneous memory systems provide memory nodes with different latency and bandwidth performance attributes. Provide a new kernel interface for subsystems to register the attributes under the memory target node's initiator access class. If the system provides this information, applications may query these attributes when deciding which node to request memory. The following example shows the new sysfs hierarchy for a node exporting performance attributes: # tree -P "read*|write*"/sys/devices/system/node/nodeY/accessZ/initiators/ /sys/devices/system/node/nodeY/accessZ/initiators/ |-- read_bandwidth |-- read_latency |-- write_bandwidth `-- write_latency The bandwidth is exported as MB/s and latency is reported in nanoseconds. The values are taken from the platform as reported by the manufacturer. Memory accesses from an initiator node that is not one of the memory's access "Z" initiator nodes linked in the same directory may observe different performance than reported here. When a subsystem makes use of this interface, initiators of a different access number may not have the same performance relative to initiators in other access numbers, or omitted from the any access class' initiators. Descriptions for memory access initiator performance access attributes are added to sysfs stable documentation. Acked-by: Jonathan Cameron Tested-by: Jonathan Cameron Signed-off-by: Keith Busch Reviewed-by: Rafael J. Wysocki Tested-by: Brice Goglin Signed-off-by: Greg Kroah-Hartman --- Documentation/ABI/stable/sysfs-devices-node | 28 ++++++++++++++ drivers/base/Kconfig | 8 ++++ drivers/base/node.c | 59 +++++++++++++++++++++++++++++ include/linux/node.h | 26 +++++++++++++ 4 files changed, 121 insertions(+) (limited to 'Documentation') diff --git a/Documentation/ABI/stable/sysfs-devices-node b/Documentation/ABI/stable/sysfs-devices-node index 433bcc04e542..735a40a3f9b2 100644 --- a/Documentation/ABI/stable/sysfs-devices-node +++ b/Documentation/ABI/stable/sysfs-devices-node @@ -114,3 +114,31 @@ Contact: Keith Busch Description: The directory containing symlinks to memory targets that this initiator node has class "Y" access. + +What: /sys/devices/system/node/nodeX/accessY/initiators/read_bandwidth +Date: December 2018 +Contact: Keith Busch +Description: + This node's read bandwidth in MB/s when accessed from + nodes found in this access class's linked initiators. + +What: /sys/devices/system/node/nodeX/accessY/initiators/read_latency +Date: December 2018 +Contact: Keith Busch +Description: + This node's read latency in nanoseconds when accessed + from nodes found in this access class's linked initiators. + +What: /sys/devices/system/node/nodeX/accessY/initiators/write_bandwidth +Date: December 2018 +Contact: Keith Busch +Description: + This node's write bandwidth in MB/s when accessed from + found in this access class's linked initiators. + +What: /sys/devices/system/node/nodeX/accessY/initiators/write_latency +Date: December 2018 +Contact: Keith Busch +Description: + This node's write latency in nanoseconds when access + from nodes found in this class's linked initiators. diff --git a/drivers/base/Kconfig b/drivers/base/Kconfig index 9fb2c4c92340..1d47ab987413 100644 --- a/drivers/base/Kconfig +++ b/drivers/base/Kconfig @@ -148,6 +148,14 @@ config DEBUG_TEST_DRIVER_REMOVE unusable. You should say N here unless you are explicitly looking to test this functionality. +config HMEM_REPORTING + bool + default n + depends on NUMA + help + Enable reporting for heterogenous memory access attributes under + their non-uniform memory nodes. + source "drivers/base/test/Kconfig" config SYS_HYPERVISOR diff --git a/drivers/base/node.c b/drivers/base/node.c index 6f4097680580..2de546a040a5 100644 --- a/drivers/base/node.c +++ b/drivers/base/node.c @@ -71,6 +71,9 @@ struct node_access_nodes { struct device dev; struct list_head list_node; unsigned access; +#ifdef CONFIG_HMEM_REPORTING + struct node_hmem_attrs hmem_attrs; +#endif }; #define to_access_nodes(dev) container_of(dev, struct node_access_nodes, dev) @@ -148,6 +151,62 @@ free: return NULL; } +#ifdef CONFIG_HMEM_REPORTING +#define ACCESS_ATTR(name) \ +static ssize_t name##_show(struct device *dev, \ + struct device_attribute *attr, \ + char *buf) \ +{ \ + return sprintf(buf, "%u\n", to_access_nodes(dev)->hmem_attrs.name); \ +} \ +static DEVICE_ATTR_RO(name); + +ACCESS_ATTR(read_bandwidth) +ACCESS_ATTR(read_latency) +ACCESS_ATTR(write_bandwidth) +ACCESS_ATTR(write_latency) + +static struct attribute *access_attrs[] = { + &dev_attr_read_bandwidth.attr, + &dev_attr_read_latency.attr, + &dev_attr_write_bandwidth.attr, + &dev_attr_write_latency.attr, + NULL, +}; + +/** + * node_set_perf_attrs - Set the performance values for given access class + * @nid: Node identifier to be set + * @hmem_attrs: Heterogeneous memory performance attributes + * @access: The access class the for the given attributes + */ +void node_set_perf_attrs(unsigned int nid, struct node_hmem_attrs *hmem_attrs, + unsigned access) +{ + struct node_access_nodes *c; + struct node *node; + int i; + + if (WARN_ON_ONCE(!node_online(nid))) + return; + + node = node_devices[nid]; + c = node_init_node_access(node, access); + if (!c) + return; + + c->hmem_attrs = *hmem_attrs; + for (i = 0; access_attrs[i] != NULL; i++) { + if (sysfs_add_file_to_group(&c->dev.kobj, access_attrs[i], + "initiators")) { + pr_info("failed to add performance attribute to node %d\n", + nid); + break; + } + } +} +#endif + #define K(x) ((x) << (PAGE_SHIFT - 10)) static ssize_t node_read_meminfo(struct device *dev, struct device_attribute *attr, char *buf) diff --git a/include/linux/node.h b/include/linux/node.h index bb288817ed33..4139d728f8b3 100644 --- a/include/linux/node.h +++ b/include/linux/node.h @@ -20,6 +20,32 @@ #include #include +/** + * struct node_hmem_attrs - heterogeneous memory performance attributes + * + * @read_bandwidth: Read bandwidth in MB/s + * @write_bandwidth: Write bandwidth in MB/s + * @read_latency: Read latency in nanoseconds + * @write_latency: Write latency in nanoseconds + */ +struct node_hmem_attrs { + unsigned int read_bandwidth; + unsigned int write_bandwidth; + unsigned int read_latency; + unsigned int write_latency; +}; + +#ifdef CONFIG_HMEM_REPORTING +void node_set_perf_attrs(unsigned int nid, struct node_hmem_attrs *hmem_attrs, + unsigned access); +#else +static inline void node_set_perf_attrs(unsigned int nid, + struct node_hmem_attrs *hmem_attrs, + unsigned access) +{ +} +#endif + struct node { struct device dev; struct list_head access_list; -- cgit v1.2.3 From acc02a109b0497e917c83f986a89c51e47d0022c Mon Sep 17 00:00:00 2001 From: Keith Busch Date: Mon, 11 Mar 2019 14:56:02 -0600 Subject: node: Add memory-side caching attributes System memory may have caches to help improve access speed to frequently requested address ranges. While the system provided cache is transparent to the software accessing these memory ranges, applications can optimize their own access based on cache attributes. Provide a new API for the kernel to register these memory-side caches under the memory node that provides it. The new sysfs representation is modeled from the existing cpu cacheinfo attributes, as seen from /sys/devices/system/cpu//cache/. Unlike CPU cacheinfo though, the node cache level is reported from the view of the memory. A higher level number is nearer to the CPU, while lower levels are closer to the last level memory. The exported attributes are the cache size, the line size, associativity indexing, and write back policy, and add the attributes for the system memory caches to sysfs stable documentation. Signed-off-by: Keith Busch Reviewed-by: Rafael J. Wysocki Reviewed-by: Brice Goglin Tested-by: Brice Goglin Signed-off-by: Greg Kroah-Hartman --- Documentation/ABI/stable/sysfs-devices-node | 34 +++++++ drivers/base/node.c | 151 ++++++++++++++++++++++++++++ include/linux/node.h | 39 +++++++ 3 files changed, 224 insertions(+) (limited to 'Documentation') diff --git a/Documentation/ABI/stable/sysfs-devices-node b/Documentation/ABI/stable/sysfs-devices-node index 735a40a3f9b2..f7ce68fbd4b9 100644 --- a/Documentation/ABI/stable/sysfs-devices-node +++ b/Documentation/ABI/stable/sysfs-devices-node @@ -142,3 +142,37 @@ Contact: Keith Busch Description: This node's write latency in nanoseconds when access from nodes found in this class's linked initiators. + +What: /sys/devices/system/node/nodeX/memory_side_cache/indexY/ +Date: December 2018 +Contact: Keith Busch +Description: + The directory containing attributes for the memory-side cache + level 'Y'. + +What: /sys/devices/system/node/nodeX/memory_side_cache/indexY/indexing +Date: December 2018 +Contact: Keith Busch +Description: + The caches associativity indexing: 0 for direct mapped, + non-zero if indexed. + +What: /sys/devices/system/node/nodeX/memory_side_cache/indexY/line_size +Date: December 2018 +Contact: Keith Busch +Description: + The number of bytes accessed from the next cache level on a + cache miss. + +What: /sys/devices/system/node/nodeX/memory_side_cache/indexY/size +Date: December 2018 +Contact: Keith Busch +Description: + The size of this memory side cache in bytes. + +What: /sys/devices/system/node/nodeX/memory_side_cache/indexY/write_policy +Date: December 2018 +Contact: Keith Busch +Description: + The cache write policy: 0 for write-back, 1 for write-through, + other or unknown. diff --git a/drivers/base/node.c b/drivers/base/node.c index 2de546a040a5..8598fcbd2a17 100644 --- a/drivers/base/node.c +++ b/drivers/base/node.c @@ -205,6 +205,155 @@ void node_set_perf_attrs(unsigned int nid, struct node_hmem_attrs *hmem_attrs, } } } + +/** + * struct node_cache_info - Internal tracking for memory node caches + * @dev: Device represeting the cache level + * @node: List element for tracking in the node + * @cache_attrs:Attributes for this cache level + */ +struct node_cache_info { + struct device dev; + struct list_head node; + struct node_cache_attrs cache_attrs; +}; +#define to_cache_info(device) container_of(device, struct node_cache_info, dev) + +#define CACHE_ATTR(name, fmt) \ +static ssize_t name##_show(struct device *dev, \ + struct device_attribute *attr, \ + char *buf) \ +{ \ + return sprintf(buf, fmt "\n", to_cache_info(dev)->cache_attrs.name);\ +} \ +DEVICE_ATTR_RO(name); + +CACHE_ATTR(size, "%llu") +CACHE_ATTR(line_size, "%u") +CACHE_ATTR(indexing, "%u") +CACHE_ATTR(write_policy, "%u") + +static struct attribute *cache_attrs[] = { + &dev_attr_indexing.attr, + &dev_attr_size.attr, + &dev_attr_line_size.attr, + &dev_attr_write_policy.attr, + NULL, +}; +ATTRIBUTE_GROUPS(cache); + +static void node_cache_release(struct device *dev) +{ + kfree(dev); +} + +static void node_cacheinfo_release(struct device *dev) +{ + struct node_cache_info *info = to_cache_info(dev); + kfree(info); +} + +static void node_init_cache_dev(struct node *node) +{ + struct device *dev; + + dev = kzalloc(sizeof(*dev), GFP_KERNEL); + if (!dev) + return; + + dev->parent = &node->dev; + dev->release = node_cache_release; + if (dev_set_name(dev, "memory_side_cache")) + goto free_dev; + + if (device_register(dev)) + goto free_name; + + pm_runtime_no_callbacks(dev); + node->cache_dev = dev; + return; +free_name: + kfree_const(dev->kobj.name); +free_dev: + kfree(dev); +} + +/** + * node_add_cache() - add cache attribute to a memory node + * @nid: Node identifier that has new cache attributes + * @cache_attrs: Attributes for the cache being added + */ +void node_add_cache(unsigned int nid, struct node_cache_attrs *cache_attrs) +{ + struct node_cache_info *info; + struct device *dev; + struct node *node; + + if (!node_online(nid) || !node_devices[nid]) + return; + + node = node_devices[nid]; + list_for_each_entry(info, &node->cache_attrs, node) { + if (info->cache_attrs.level == cache_attrs->level) { + dev_warn(&node->dev, + "attempt to add duplicate cache level:%d\n", + cache_attrs->level); + return; + } + } + + if (!node->cache_dev) + node_init_cache_dev(node); + if (!node->cache_dev) + return; + + info = kzalloc(sizeof(*info), GFP_KERNEL); + if (!info) + return; + + dev = &info->dev; + dev->parent = node->cache_dev; + dev->release = node_cacheinfo_release; + dev->groups = cache_groups; + if (dev_set_name(dev, "index%d", cache_attrs->level)) + goto free_cache; + + info->cache_attrs = *cache_attrs; + if (device_register(dev)) { + dev_warn(&node->dev, "failed to add cache level:%d\n", + cache_attrs->level); + goto free_name; + } + pm_runtime_no_callbacks(dev); + list_add_tail(&info->node, &node->cache_attrs); + return; +free_name: + kfree_const(dev->kobj.name); +free_cache: + kfree(info); +} + +static void node_remove_caches(struct node *node) +{ + struct node_cache_info *info, *next; + + if (!node->cache_dev) + return; + + list_for_each_entry_safe(info, next, &node->cache_attrs, node) { + list_del(&info->node); + device_unregister(&info->dev); + } + device_unregister(node->cache_dev); +} + +static void node_init_caches(unsigned int nid) +{ + INIT_LIST_HEAD(&node_devices[nid]->cache_attrs); +} +#else +static void node_init_caches(unsigned int nid) { } +static void node_remove_caches(struct node *node) { } #endif #define K(x) ((x) << (PAGE_SHIFT - 10)) @@ -489,6 +638,7 @@ void unregister_node(struct node *node) { hugetlb_unregister_node(node); /* no-op, if memoryless node */ node_remove_accesses(node); + node_remove_caches(node); device_unregister(&node->dev); } @@ -781,6 +931,7 @@ int __register_one_node(int nid) INIT_LIST_HEAD(&node_devices[nid]->access_list); /* initialize work queue for memory hot plug */ init_node_hugetlb_work(nid); + node_init_caches(nid); return error; } diff --git a/include/linux/node.h b/include/linux/node.h index 4139d728f8b3..1a557c589ecb 100644 --- a/include/linux/node.h +++ b/include/linux/node.h @@ -35,10 +35,45 @@ struct node_hmem_attrs { unsigned int write_latency; }; +enum cache_indexing { + NODE_CACHE_DIRECT_MAP, + NODE_CACHE_INDEXED, + NODE_CACHE_OTHER, +}; + +enum cache_write_policy { + NODE_CACHE_WRITE_BACK, + NODE_CACHE_WRITE_THROUGH, + NODE_CACHE_WRITE_OTHER, +}; + +/** + * struct node_cache_attrs - system memory caching attributes + * + * @indexing: The ways memory blocks may be placed in cache + * @write_policy: Write back or write through policy + * @size: Total size of cache in bytes + * @line_size: Number of bytes fetched on a cache miss + * @level: The cache hierarchy level + */ +struct node_cache_attrs { + enum cache_indexing indexing; + enum cache_write_policy write_policy; + u64 size; + u16 line_size; + u8 level; +}; + #ifdef CONFIG_HMEM_REPORTING +void node_add_cache(unsigned int nid, struct node_cache_attrs *cache_attrs); void node_set_perf_attrs(unsigned int nid, struct node_hmem_attrs *hmem_attrs, unsigned access); #else +static inline void node_add_cache(unsigned int nid, + struct node_cache_attrs *cache_attrs) +{ +} + static inline void node_set_perf_attrs(unsigned int nid, struct node_hmem_attrs *hmem_attrs, unsigned access) @@ -53,6 +88,10 @@ struct node { #if defined(CONFIG_MEMORY_HOTPLUG_SPARSE) && defined(CONFIG_HUGETLBFS) struct work_struct node_work; #endif +#ifdef CONFIG_HMEM_REPORTING + struct list_head cache_attrs; + struct device *cache_dev; +#endif }; struct memory_block; -- cgit v1.2.3 From 13bac55ef7aef8ecb67ff3005d24b05a464d28ea Mon Sep 17 00:00:00 2001 From: Keith Busch Date: Mon, 11 Mar 2019 14:56:06 -0600 Subject: doc/mm: New documentation for memory performance Platforms may provide system memory where some physical address ranges perform differently than others, or is cached by the system on the memory side. Add documentation describing a high level overview of such systems and the perforamnce and caching attributes the kernel provides for applications wishing to query this information. Reviewed-by: Mike Rapoport Reviewed-by: Jonathan Cameron Signed-off-by: Keith Busch Tested-by: Brice Goglin Signed-off-by: Greg Kroah-Hartman --- Documentation/admin-guide/mm/numaperf.rst | 169 ++++++++++++++++++++++++++++++ 1 file changed, 169 insertions(+) create mode 100644 Documentation/admin-guide/mm/numaperf.rst (limited to 'Documentation') diff --git a/Documentation/admin-guide/mm/numaperf.rst b/Documentation/admin-guide/mm/numaperf.rst new file mode 100644 index 000000000000..b79f70c04397 --- /dev/null +++ b/Documentation/admin-guide/mm/numaperf.rst @@ -0,0 +1,169 @@ +.. _numaperf: + +============= +NUMA Locality +============= + +Some platforms may have multiple types of memory attached to a compute +node. These disparate memory ranges may share some characteristics, such +as CPU cache coherence, but may have different performance. For example, +different media types and buses affect bandwidth and latency. + +A system supports such heterogeneous memory by grouping each memory type +under different domains, or "nodes", based on locality and performance +characteristics. Some memory may share the same node as a CPU, and others +are provided as memory only nodes. While memory only nodes do not provide +CPUs, they may still be local to one or more compute nodes relative to +other nodes. The following diagram shows one such example of two compute +nodes with local memory and a memory only node for each of compute node: + + +------------------+ +------------------+ + | Compute Node 0 +-----+ Compute Node 1 | + | Local Node0 Mem | | Local Node1 Mem | + +--------+---------+ +--------+---------+ + | | + +--------+---------+ +--------+---------+ + | Slower Node2 Mem | | Slower Node3 Mem | + +------------------+ +--------+---------+ + +A "memory initiator" is a node containing one or more devices such as +CPUs or separate memory I/O devices that can initiate memory requests. +A "memory target" is a node containing one or more physical address +ranges accessible from one or more memory initiators. + +When multiple memory initiators exist, they may not all have the same +performance when accessing a given memory target. Each initiator-target +pair may be organized into different ranked access classes to represent +this relationship. The highest performing initiator to a given target +is considered to be one of that target's local initiators, and given +the highest access class, 0. Any given target may have one or more +local initiators, and any given initiator may have multiple local +memory targets. + +To aid applications matching memory targets with their initiators, the +kernel provides symlinks to each other. The following example lists the +relationship for the access class "0" memory initiators and targets:: + + # symlinks -v /sys/devices/system/node/nodeX/access0/targets/ + relative: /sys/devices/system/node/nodeX/access0/targets/nodeY -> ../../nodeY + + # symlinks -v /sys/devices/system/node/nodeY/access0/initiators/ + relative: /sys/devices/system/node/nodeY/access0/initiators/nodeX -> ../../nodeX + +A memory initiator may have multiple memory targets in the same access +class. The target memory's initiators in a given class indicate the +nodes' access characteristics share the same performance relative to other +linked initiator nodes. Each target within an initiator's access class, +though, do not necessarily perform the same as each other. + +================ +NUMA Performance +================ + +Applications may wish to consider which node they want their memory to +be allocated from based on the node's performance characteristics. If +the system provides these attributes, the kernel exports them under the +node sysfs hierarchy by appending the attributes directory under the +memory node's access class 0 initiators as follows:: + + /sys/devices/system/node/nodeY/access0/initiators/ + +These attributes apply only when accessed from nodes that have the +are linked under the this access's inititiators. + +The performance characteristics the kernel provides for the local initiators +are exported are as follows:: + + # tree -P "read*|write*" /sys/devices/system/node/nodeY/access0/initiators/ + /sys/devices/system/node/nodeY/access0/initiators/ + |-- read_bandwidth + |-- read_latency + |-- write_bandwidth + `-- write_latency + +The bandwidth attributes are provided in MiB/second. + +The latency attributes are provided in nanoseconds. + +The values reported here correspond to the rated latency and bandwidth +for the platform. + +========== +NUMA Cache +========== + +System memory may be constructed in a hierarchy of elements with various +performance characteristics in order to provide large address space of +slower performing memory cached by a smaller higher performing memory. The +system physical addresses memory initiators are aware of are provided +by the last memory level in the hierarchy. The system meanwhile uses +higher performing memory to transparently cache access to progressively +slower levels. + +The term "far memory" is used to denote the last level memory in the +hierarchy. Each increasing cache level provides higher performing +initiator access, and the term "near memory" represents the fastest +cache provided by the system. + +This numbering is different than CPU caches where the cache level (ex: +L1, L2, L3) uses the CPU-side view where each increased level is lower +performing. In contrast, the memory cache level is centric to the last +level memory, so the higher numbered cache level corresponds to memory +nearer to the CPU, and further from far memory. + +The memory-side caches are not directly addressable by software. When +software accesses a system address, the system will return it from the +near memory cache if it is present. If it is not present, the system +accesses the next level of memory until there is either a hit in that +cache level, or it reaches far memory. + +An application does not need to know about caching attributes in order +to use the system. Software may optionally query the memory cache +attributes in order to maximize the performance out of such a setup. +If the system provides a way for the kernel to discover this information, +for example with ACPI HMAT (Heterogeneous Memory Attribute Table), +the kernel will append these attributes to the NUMA node memory target. + +When the kernel first registers a memory cache with a node, the kernel +will create the following directory:: + + /sys/devices/system/node/nodeX/memory_side_cache/ + +If that directory is not present, the system either does not not provide +a memory-side cache, or that information is not accessible to the kernel. + +The attributes for each level of cache is provided under its cache +level index:: + + /sys/devices/system/node/nodeX/memory_side_cache/indexA/ + /sys/devices/system/node/nodeX/memory_side_cache/indexB/ + /sys/devices/system/node/nodeX/memory_side_cache/indexC/ + +Each cache level's directory provides its attributes. For example, the +following shows a single cache level and the attributes available for +software to query:: + + # tree sys/devices/system/node/node0/memory_side_cache/ + /sys/devices/system/node/node0/memory_side_cache/ + |-- index1 + | |-- indexing + | |-- line_size + | |-- size + | `-- write_policy + +The "indexing" will be 0 if it is a direct-mapped cache, and non-zero +for any other indexed based, multi-way associativity. + +The "line_size" is the number of bytes accessed from the next cache +level on a miss. + +The "size" is the number of bytes provided by this cache level. + +The "write_policy" will be 0 for write-back, and non-zero for +write-through caching. + +======== +See Also +======== +.. [1] https://www.uefi.org/sites/default/files/resources/ACPI_6_2.pdf + Section 5.2.27 -- cgit v1.2.3 From 24541dede9dbe0638c82ace2b072c08fd1ec786b Mon Sep 17 00:00:00 2001 From: Vladimir Zapolskiy Date: Wed, 3 Apr 2019 10:52:49 -0700 Subject: Input: lpc32xx-key - add clocks property and fix DT binding example The keypad controller on NXP LPC32xx requires its clock gate to be open, therefore add description of the requires 'clocks' property. In addition adjust the example by adding description of required 'clocks' property and by fixing 'interrupts' property. Signed-off-by: Vladimir Zapolskiy Reviewed-by: Dmitry Torokhov Reviewed-by: Rob Herring Signed-off-by: Dmitry Torokhov --- Documentation/devicetree/bindings/input/lpc32xx-key.txt | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/input/lpc32xx-key.txt b/Documentation/devicetree/bindings/input/lpc32xx-key.txt index bcf62f856358..2b075a080d30 100644 --- a/Documentation/devicetree/bindings/input/lpc32xx-key.txt +++ b/Documentation/devicetree/bindings/input/lpc32xx-key.txt @@ -8,6 +8,7 @@ Required Properties: - reg: Physical base address of the controller and length of memory mapped region. - interrupts: The interrupt number to the cpu. +- clocks: phandle to clock controller plus clock-specifier pair - nxp,debounce-delay-ms: Debounce delay in ms - nxp,scan-delay-ms: Repeated scan period in ms - linux,keymap: the key-code to be reported when the key is pressed @@ -22,7 +23,9 @@ Example: key@40050000 { compatible = "nxp,lpc3220-key"; reg = <0x40050000 0x1000>; - interrupts = <54 0>; + clocks = <&clk LPC32XX_CLK_KEY>; + interrupt-parent = <&sic1>; + interrupts = <22 IRQ_TYPE_LEVEL_HIGH>; keypad,num-rows = <1>; keypad,num-columns = <1>; nxp,debounce-delay-ms = <3>; -- cgit v1.2.3 From 4c4591173f687a8e891b913b4e510807e821da5c Mon Sep 17 00:00:00 2001 From: Ziping Chen Date: Thu, 4 Apr 2019 11:47:14 -0700 Subject: Input: sun4i-a10-lradc-keys - add support for A83T Allwinner A83T SoC has a low res adc like the one in Allwinner A10 SoC, however, the A10 SoC's vref of lradc internally is divided by 2/3 and the A83T SoC's vref of lradc internally is divided by 3/4, thus add a hardware variant for it to be compatible with various devices. Signed-off-by: Ziping Chen Acked-by: Maxime Ripard Acked-by: Rob Herring Signed-off-by: Dmitry Torokhov --- .../devicetree/bindings/input/sun4i-lradc-keys.txt | 6 ++-- drivers/input/keyboard/sun4i-lradc-keys.c | 38 +++++++++++++++++++--- 2 files changed, 38 insertions(+), 6 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/input/sun4i-lradc-keys.txt b/Documentation/devicetree/bindings/input/sun4i-lradc-keys.txt index 1458c3179a63..496125c6bfb7 100644 --- a/Documentation/devicetree/bindings/input/sun4i-lradc-keys.txt +++ b/Documentation/devicetree/bindings/input/sun4i-lradc-keys.txt @@ -2,12 +2,14 @@ Allwinner sun4i low res adc attached tablet keys ------------------------------------------------ Required properties: - - compatible: "allwinner,sun4i-a10-lradc-keys" + - compatible: should be one of the following string: + "allwinner,sun4i-a10-lradc-keys" + "allwinner,sun8i-a83t-r-lradc" - reg: mmio address range of the chip - interrupts: interrupt to which the chip is connected - vref-supply: powersupply for the lradc reference voltage -Each key is represented as a sub-node of "allwinner,sun4i-a10-lradc-keys": +Each key is represented as a sub-node of the compatible mentioned above: Required subnode-properties: - label: Descriptive name of the key. diff --git a/drivers/input/keyboard/sun4i-lradc-keys.c b/drivers/input/keyboard/sun4i-lradc-keys.c index 57272df34cd5..df3eec72a9b2 100644 --- a/drivers/input/keyboard/sun4i-lradc-keys.c +++ b/drivers/input/keyboard/sun4i-lradc-keys.c @@ -46,6 +46,7 @@ #define CONTINUE_TIME_SEL(x) ((x) << 16) /* 4 bits */ #define KEY_MODE_SEL(x) ((x) << 12) /* 2 bits */ #define LEVELA_B_CNT(x) ((x) << 8) /* 4 bits */ +#define HOLD_KEY_EN(x) ((x) << 7) #define HOLD_EN(x) ((x) << 6) #define LEVELB_VOL(x) ((x) << 4) /* 2 bits */ #define SAMPLE_RATE(x) ((x) << 2) /* 2 bits */ @@ -63,6 +64,25 @@ #define CHAN0_KEYDOWN_IRQ BIT(1) #define CHAN0_DATA_IRQ BIT(0) +/* struct lradc_variant - Describe sun4i-a10-lradc-keys hardware variant + * @divisor_numerator: The numerator of lradc Vref internally divisor + * @divisor_denominator: The denominator of lradc Vref internally divisor + */ +struct lradc_variant { + u8 divisor_numerator; + u8 divisor_denominator; +}; + +static const struct lradc_variant lradc_variant_a10 = { + .divisor_numerator = 2, + .divisor_denominator = 3 +}; + +static const struct lradc_variant r_lradc_variant_a83t = { + .divisor_numerator = 3, + .divisor_denominator = 4 +}; + struct sun4i_lradc_keymap { u32 voltage; u32 keycode; @@ -74,6 +94,7 @@ struct sun4i_lradc_data { void __iomem *base; struct regulator *vref_supply; struct sun4i_lradc_keymap *chan0_map; + const struct lradc_variant *variant; u32 chan0_map_count; u32 chan0_keycode; u32 vref; @@ -128,9 +149,9 @@ static int sun4i_lradc_open(struct input_dev *dev) if (error) return error; - /* lradc Vref internally is divided by 2/3 */ - lradc->vref = regulator_get_voltage(lradc->vref_supply) * 2 / 3; - + lradc->vref = regulator_get_voltage(lradc->vref_supply) * + lradc->variant->divisor_numerator / + lradc->variant->divisor_denominator; /* * Set sample time to 4 ms / 250 Hz. Wait 2 * 4 ms for key to * stabilize on press, wait (1 + 1) * 4 ms for key release @@ -222,6 +243,12 @@ static int sun4i_lradc_probe(struct platform_device *pdev) if (error) return error; + lradc->variant = of_device_get_match_data(&pdev->dev); + if (!lradc->variant) { + dev_err(&pdev->dev, "Missing sun4i-a10-lradc-keys variant\n"); + return -EINVAL; + } + lradc->vref_supply = devm_regulator_get(dev, "vref"); if (IS_ERR(lradc->vref_supply)) return PTR_ERR(lradc->vref_supply); @@ -265,7 +292,10 @@ static int sun4i_lradc_probe(struct platform_device *pdev) } static const struct of_device_id sun4i_lradc_of_match[] = { - { .compatible = "allwinner,sun4i-a10-lradc-keys", }, + { .compatible = "allwinner,sun4i-a10-lradc-keys", + .data = &lradc_variant_a10 }, + { .compatible = "allwinner,sun8i-a83t-r-lradc", + .data = &r_lradc_variant_a83t }, { /* sentinel */ } }; MODULE_DEVICE_TABLE(of, sun4i_lradc_of_match); -- cgit v1.2.3 From faad0af1623c5dd214aa3207ba43186ee37c685d Mon Sep 17 00:00:00 2001 From: Tomasz Duszynski Date: Sun, 17 Feb 2019 20:22:13 +0100 Subject: dt-bindings: iio: chemical: pms7003: extend supported sensors list Add other sensors to the compatible list. Signed-off-by: Tomasz Duszynski Signed-off-by: Jonathan Cameron --- .../devicetree/bindings/iio/chemical/plantower,pms7003.txt | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/chemical/plantower,pms7003.txt b/Documentation/devicetree/bindings/iio/chemical/plantower,pms7003.txt index 7b5f06f324c8..c52ea2126eaa 100644 --- a/Documentation/devicetree/bindings/iio/chemical/plantower,pms7003.txt +++ b/Documentation/devicetree/bindings/iio/chemical/plantower,pms7003.txt @@ -1,7 +1,13 @@ * Plantower PMS7003 particulate matter sensor Required properties: -- compatible: must be "plantower,pms7003" +- compatible: must one of: + "plantower,pms1003" + "plantower,pms3003" + "plantower,pms5003" + "plantower,pms6003" + "plantower,pms7003" + "plantower,pmsa003" - vcc-supply: phandle to the regulator that provides power to the sensor Optional properties: -- cgit v1.2.3 From 1842a700ec592169c773ac6b6867a6f5e7166bc6 Mon Sep 17 00:00:00 2001 From: Stefan Popa Date: Wed, 27 Feb 2019 18:14:28 +0200 Subject: iio: imu: adis16480: Add docs for ADIS16480 IMU Document support for ADIS16480 Inertial Measurement Unit. Signed-off-by: Stefan Popa Reviewed-by: Rob Herring Signed-off-by: Jonathan Cameron --- .../devicetree/bindings/iio/imu/adi,adis16480.txt | 49 ++++++++++++++++++++++ MAINTAINERS | 1 + 2 files changed, 50 insertions(+) create mode 100644 Documentation/devicetree/bindings/iio/imu/adi,adis16480.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/imu/adi,adis16480.txt b/Documentation/devicetree/bindings/iio/imu/adi,adis16480.txt new file mode 100644 index 000000000000..39ab016658c0 --- /dev/null +++ b/Documentation/devicetree/bindings/iio/imu/adi,adis16480.txt @@ -0,0 +1,49 @@ + +Analog Devices ADIS16480 and similar IMUs + +Required properties for the ADIS16480: + +- compatible: Must be one of + * "adi,adis16375" + * "adi,adis16480" + * "adi,adis16485" + * "adi,adis16488" + * "adi,adis16495-1" + * "adi,adis16495-2" + * "adi,adis16495-3" + * "adi,adis16497-1" + * "adi,adis16497-2" + * "adi,adis16497-3" +- reg: SPI chip select number for the device +- spi-max-frequency: Max SPI frequency to use + see: Documentation/devicetree/bindings/spi/spi-bus.txt +- spi-cpha: See Documentation/devicetree/bindings/spi/spi-bus.txt +- spi-cpol: See Documentation/devicetree/bindings/spi/spi-bus.txt +- interrupts: interrupt mapping for IRQ, accepted values are: + * IRQF_TRIGGER_RISING + * IRQF_TRIGGER_FALLING + +Optional properties: + +- interrupt-names: Data ready line selection. Valid values are: + * DIO1 + * DIO2 + * DIO3 + * DIO4 + If this field is left empty, DIO1 is assigned as default data ready + signal. +- reset-gpios: must be the device tree identifier of the RESET pin. As the line + is active low, it should be marked GPIO_ACTIVE_LOW. + +Example: + + imu@0 { + compatible = "adi,adis16495-1"; + reg = <0>; + spi-max-frequency = <3200000>; + spi-cpol; + spi-cpha; + interrupts = <25 IRQF_TRIGGER_FALLING>; + interrupt-parent = <&gpio>; + interrupt-names = "DIO2"; + }; diff --git a/MAINTAINERS b/MAINTAINERS index 43b36dbed48e..e12215a88ff9 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -950,6 +950,7 @@ F: drivers/dma/dma-axi-dmac.c ANALOG DEVICES INC IIO DRIVERS M: Lars-Peter Clausen M: Michael Hennerich +M: Stefan Popa W: http://wiki.analog.com/ W: http://ez.analog.com/community/linux-device-drivers S: Supported -- cgit v1.2.3 From 722f2cca9a29b7dc27d8bdc15257aaba36394812 Mon Sep 17 00:00:00 2001 From: Tomasz Duszynski Date: Mon, 25 Feb 2019 19:17:40 +0100 Subject: iio: chemical: sps30: fix attribute kernel version 4.22 have never existed and this change was actually added to 5.0 hence fix the numbering. Signed-off-by: Tomasz Duszynski Signed-off-by: Jonathan Cameron --- Documentation/ABI/testing/sysfs-bus-iio-sps30 | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/ABI/testing/sysfs-bus-iio-sps30 b/Documentation/ABI/testing/sysfs-bus-iio-sps30 index 143df8e89d08..06e1c272537b 100644 --- a/Documentation/ABI/testing/sysfs-bus-iio-sps30 +++ b/Documentation/ABI/testing/sysfs-bus-iio-sps30 @@ -1,6 +1,6 @@ What: /sys/bus/iio/devices/iio:deviceX/start_cleaning Date: December 2018 -KernelVersion: 4.22 +KernelVersion: 5.0 Contact: linux-iio@vger.kernel.org Description: Writing 1 starts sensor self cleaning. Internal fan accelerates -- cgit v1.2.3 From 74896202dfb71e7142adc4042f0cc812cb4be4c5 Mon Sep 17 00:00:00 2001 From: Fabrice Gasnier Date: Mon, 25 Feb 2019 11:42:46 +0100 Subject: dt-bindings: iio: stm32-lptimer-counter: document pinctrl sleep state Add documentation for optional pinctrl sleep state that can be used by STM32 LPTimer encoder/counter. Signed-off-by: Fabrice Gasnier Signed-off-by: Jonathan Cameron --- .../devicetree/bindings/iio/counter/stm32-lptimer-cnt.txt | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/counter/stm32-lptimer-cnt.txt b/Documentation/devicetree/bindings/iio/counter/stm32-lptimer-cnt.txt index a04aa5c04103..e90bc47f752a 100644 --- a/Documentation/devicetree/bindings/iio/counter/stm32-lptimer-cnt.txt +++ b/Documentation/devicetree/bindings/iio/counter/stm32-lptimer-cnt.txt @@ -10,8 +10,9 @@ See ../mfd/stm32-lptimer.txt for details about the parent node. Required properties: - compatible: Must be "st,stm32-lptimer-counter". -- pinctrl-names: Set to "default". -- pinctrl-0: List of phandles pointing to pin configuration nodes, +- pinctrl-names: Set to "default". An additional "sleep" state can be + defined to set pins in sleep state. +- pinctrl-n: List of phandles pointing to pin configuration nodes, to set IN1/IN2 pins in mode of operation for Low-Power Timer input on external pin. @@ -21,7 +22,8 @@ Example: ... counter { compatible = "st,stm32-lptimer-counter"; - pinctrl-names = "default"; + pinctrl-names = "default", "sleep"; pinctrl-0 = <&lptim1_in_pins>; + pinctrl-1 = <&lptim1_sleep_in_pins>; }; }; -- cgit v1.2.3 From e132f62b9fabad809dccc9f8e1847496b1538376 Mon Sep 17 00:00:00 2001 From: Lorenzo Bianconi Date: Thu, 21 Feb 2019 16:20:21 +0100 Subject: dt-bindings: iio: imu: st_lsm6dsx: add asm330lhh device bindings Signed-off-by: Lorenzo Bianconi Signed-off-by: Jonathan Cameron --- Documentation/devicetree/bindings/iio/imu/st_lsm6dsx.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/imu/st_lsm6dsx.txt b/Documentation/devicetree/bindings/iio/imu/st_lsm6dsx.txt index 69d53d98d0f0..8f1b09e39c72 100644 --- a/Documentation/devicetree/bindings/iio/imu/st_lsm6dsx.txt +++ b/Documentation/devicetree/bindings/iio/imu/st_lsm6dsx.txt @@ -8,6 +8,7 @@ Required properties: "st,lsm6dsm" "st,ism330dlc" "st,lsm6dso" + "st,asm330lhh" - reg: i2c address of the sensor / spi cs line Optional properties: -- cgit v1.2.3 From a29b8657d322daef2b9fd3fd7c03f5f5bebfde86 Mon Sep 17 00:00:00 2001 From: Neil Armstrong Date: Mon, 4 Mar 2019 12:12:16 +0100 Subject: dt-bindings: iio: adc: document the Meson G12A support Update the documentation to explicitly support the Meson-G12A SoC. Signed-off-by: Neil Armstrong Reviewed-by: Martin Blumenstingl Signed-off-by: Jonathan Cameron --- Documentation/devicetree/bindings/iio/adc/amlogic,meson-saradc.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/adc/amlogic,meson-saradc.txt b/Documentation/devicetree/bindings/iio/adc/amlogic,meson-saradc.txt index 75c775954102..d57e9df25f4f 100644 --- a/Documentation/devicetree/bindings/iio/adc/amlogic,meson-saradc.txt +++ b/Documentation/devicetree/bindings/iio/adc/amlogic,meson-saradc.txt @@ -9,6 +9,7 @@ Required properties: - "amlogic,meson-gxl-saradc" for GXL - "amlogic,meson-gxm-saradc" for GXM - "amlogic,meson-axg-saradc" for AXG + - "amlogic,meson-g12a-saradc" for AXG along with the generic "amlogic,meson-saradc" - reg: the physical base address and length of the registers - interrupts: the interrupt indicating end of sampling -- cgit v1.2.3 From 2e5cee6c762297359d670a19e6b87c73c5ceaccb Mon Sep 17 00:00:00 2001 From: Robert Yang Date: Mon, 4 Mar 2019 10:19:10 -0500 Subject: dt-bindings: Add vendor prefix for Kionix, Inc. Kionix manufactured MEMs sensors. There are Kionix acceleromoter sensor drivers which can be used with device tree. Signed-off-by: Robert Yang Reviewed-by: Rob Herring Signed-off-by: Jonathan Cameron --- Documentation/devicetree/bindings/vendor-prefixes.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/vendor-prefixes.txt b/Documentation/devicetree/bindings/vendor-prefixes.txt index 8162b0eb4b50..f4ce79170185 100644 --- a/Documentation/devicetree/bindings/vendor-prefixes.txt +++ b/Documentation/devicetree/bindings/vendor-prefixes.txt @@ -210,6 +210,7 @@ kiebackpeter Kieback & Peter GmbH kinetic Kinetic Technologies kingdisplay King & Display Technology Co., Ltd. kingnovel Kingnovel Technology Co., Ltd. +kionix Kionix, Inc. koe Kaohsiung Opto-Electronics Inc. kosagi Sutajio Ko-Usagi PTE Ltd. kyo Kyocera Corporation -- cgit v1.2.3 From 0d90fe4786cb8542b900257b4fa7316cbdd9d01f Mon Sep 17 00:00:00 2001 From: Robert Yang Date: Mon, 4 Mar 2019 10:19:11 -0500 Subject: dt-bindings: iio: accel: kxcjk1013: Add device tree binding documentation Document device tree bindings for Kionix KXCJK-1013 Accelerometer driver. Signed-off-by: Robert Yang Reviewed-by: Rob Herring Signed-off-by: Jonathan Cameron --- .../devicetree/bindings/iio/accel/kionix,kxcjk1013.txt | 17 +++++++++++++++++ 1 file changed, 17 insertions(+) create mode 100644 Documentation/devicetree/bindings/iio/accel/kionix,kxcjk1013.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/accel/kionix,kxcjk1013.txt b/Documentation/devicetree/bindings/iio/accel/kionix,kxcjk1013.txt new file mode 100644 index 000000000000..eb76a02e2a82 --- /dev/null +++ b/Documentation/devicetree/bindings/iio/accel/kionix,kxcjk1013.txt @@ -0,0 +1,17 @@ +Kionix KXCJK-1013 Accelerometer device tree bindings + +Required properties: + +- compatible: Must be one of: + "kionix,kxcjk1013" + "kionix,kxcj91008" + "kionix,kxtj21009" + "kionix,kxtf9" + - reg: i2c slave address + +Example: + +kxtf9@f { + compatible = "kionix,kxtf9"; + reg = <0x0F>; +}; -- cgit v1.2.3 From 3b5de76b285eebe152d691a8481483e9cedd07a0 Mon Sep 17 00:00:00 2001 From: Stefan Popa Date: Mon, 11 Mar 2019 11:46:37 +0200 Subject: dt-bindings: iio: imu: adis16480: Document external clock Add documentation for optional use of external clock. All devices supported by this driver can work with an external clock in sync mode. Another mode, called Pulse Per Second (PPS) is supported only by adis1649x devices. The mode is selected by using the "clock-names" property. The pin which is used as external clock input is selected by using a custom optional property called "adi,ext-clk-pin". If this field is left empty, DIO2 is assigned as default external clock input pin. Signed-off-by: Stefan Popa Signed-off-by: Jonathan Cameron --- .../devicetree/bindings/iio/imu/adi,adis16480.txt | 36 ++++++++++++++++++++++ 1 file changed, 36 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/imu/adi,adis16480.txt b/Documentation/devicetree/bindings/iio/imu/adi,adis16480.txt index 39ab016658c0..ed7783f45233 100644 --- a/Documentation/devicetree/bindings/iio/imu/adi,adis16480.txt +++ b/Documentation/devicetree/bindings/iio/imu/adi,adis16480.txt @@ -34,6 +34,39 @@ Optional properties: signal. - reset-gpios: must be the device tree identifier of the RESET pin. As the line is active low, it should be marked GPIO_ACTIVE_LOW. +- clocks: phandle to the external clock. Should be set according to + "clock-names". + If this field is left empty together with the "clock-names" field, then + the internal clock is used. +- clock-names: The name of the external clock to be used. Valid values are: + * sync: In sync mode, the internal clock is disabled and the frequency + of the external clock signal establishes therate of data + collection and processing. See Fig 14 and 15 in the datasheet. + The clock-frequency must be: + * 3000 to 4500 Hz for adis1649x devices. + * 700 to 2400 Hz for adis1648x devices. + * pps: In Pulse Per Second (PPS) Mode, the rate of data collection and + production is equal to the product of the external clock + frequency and the scale factor in the SYNC_SCALE register, see + Table 154 in the datasheet. + The clock-frequency must be: + * 1 to 128 Hz for adis1649x devices. + * This mode is not supported by adis1648x devices. + If this field is left empty together with the "clocks" field, then the + internal clock is used. +- adi,ext-clk-pin: The DIOx line to be used as an external clock input. + Valid values are: + * DIO1 + * DIO2 + * DIO3 + * DIO4 + Each DIOx pin supports only one function at a time (data ready line + selection or external clock input). When a single pin has two + two assignments, the enable bit for the lower priority function + automatically resets to zero (disabling the lower priority function). + Data ready has highest priority. + If this field is left empty, DIO2 is assigned as default external clock + input pin. Example: @@ -46,4 +79,7 @@ Example: interrupts = <25 IRQF_TRIGGER_FALLING>; interrupt-parent = <&gpio>; interrupt-names = "DIO2"; + clocks = <&adis16495_sync>; + clock-names = "sync"; + adi,ext-clk-pin = "DIO1"; }; -- cgit v1.2.3 From 6be4f55456f938130891e76cb011e546162ad365 Mon Sep 17 00:00:00 2001 From: Lorenzo Bianconi Date: Fri, 15 Mar 2019 11:08:25 +0100 Subject: dt-bindings: iio: imu: st_lsm6dsx: add lsm6dsox device bindings Signed-off-by: Lorenzo Bianconi Signed-off-by: Jonathan Cameron --- Documentation/devicetree/bindings/iio/imu/st_lsm6dsx.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/imu/st_lsm6dsx.txt b/Documentation/devicetree/bindings/iio/imu/st_lsm6dsx.txt index 8f1b09e39c72..4640a012c17a 100644 --- a/Documentation/devicetree/bindings/iio/imu/st_lsm6dsx.txt +++ b/Documentation/devicetree/bindings/iio/imu/st_lsm6dsx.txt @@ -9,6 +9,7 @@ Required properties: "st,ism330dlc" "st,lsm6dso" "st,asm330lhh" + "st,lsm6dsox" - reg: i2c address of the sensor / spi cs line Optional properties: -- cgit v1.2.3 From caeffabc36cbb6a3cdfe5b7894f8e1bfef6504b3 Mon Sep 17 00:00:00 2001 From: Gregory CLEMENT Date: Fri, 15 Mar 2019 10:52:31 +0100 Subject: dt-bindings: iio: adc: lpc32xx-adc: Document vref-supply As most of the other ADC the lpc32xx one use a vref-supply property: document it. Reviewed-by: Rob Herring Signed-off-by: Gregory CLEMENT Signed-off-by: Jonathan Cameron --- Documentation/devicetree/bindings/iio/adc/lpc32xx-adc.txt | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/adc/lpc32xx-adc.txt b/Documentation/devicetree/bindings/iio/adc/lpc32xx-adc.txt index b3629d3a9adf..3a1bc669bd51 100644 --- a/Documentation/devicetree/bindings/iio/adc/lpc32xx-adc.txt +++ b/Documentation/devicetree/bindings/iio/adc/lpc32xx-adc.txt @@ -6,6 +6,10 @@ Required properties: region. - interrupts: The ADC interrupt +Optional: + - vref-supply: The regulator supply ADC reference voltage, optional + for legacy reason, but highly encouraging to us in new device tree + Example: adc@40048000 { @@ -13,4 +17,5 @@ Example: reg = <0x40048000 0x1000>; interrupt-parent = <&mic>; interrupts = <39 0>; + vref-supply = <&vcc>; }; -- cgit v1.2.3 From 46c1eb4bb137cd290ded6a2d593acff1594cbfe7 Mon Sep 17 00:00:00 2001 From: Renato Lui Geh Date: Fri, 15 Mar 2019 23:16:13 -0300 Subject: staging: iio: ad7780: add device tree binding Adds a device tree binding for the ad7780 driver. Signed-off-by: Renato Lui Geh Signed-off-by: Jonathan Cameron --- .../devicetree/bindings/iio/adc/adi,ad7780.txt | 48 ++++++++++++++++++++++ 1 file changed, 48 insertions(+) create mode 100644 Documentation/devicetree/bindings/iio/adc/adi,ad7780.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/adc/adi,ad7780.txt b/Documentation/devicetree/bindings/iio/adc/adi,ad7780.txt new file mode 100644 index 000000000000..440e52555349 --- /dev/null +++ b/Documentation/devicetree/bindings/iio/adc/adi,ad7780.txt @@ -0,0 +1,48 @@ +* Analog Devices AD7170/AD7171/AD7780/AD7781 + +Data sheets: + +- AD7170: + * https://www.analog.com/media/en/technical-documentation/data-sheets/AD7170.pdf +- AD7171: + * https://www.analog.com/media/en/technical-documentation/data-sheets/AD7171.pdf +- AD7780: + * https://www.analog.com/media/en/technical-documentation/data-sheets/ad7780.pdf +- AD7781: + * https://www.analog.com/media/en/technical-documentation/data-sheets/AD7781.pdf + +Required properties: + +- compatible: should be one of + * "adi,ad7170" + * "adi,ad7171" + * "adi,ad7780" + * "adi,ad7781" +- reg: spi chip select number for the device +- vref-supply: the regulator supply for the ADC reference voltage + +Optional properties: + +- powerdown-gpios: must be the device tree identifier of the PDRST pin. If + specified, it will be asserted during driver probe. As the + line is active high, it should be marked GPIO_ACTIVE_HIGH. +- adi,gain-gpios: must be the device tree identifier of the GAIN pin. Only for + the ad778x chips. If specified, it will be asserted during + driver probe. As the line is active low, it should be marked + GPIO_ACTIVE_LOW. +- adi,filter-gpios: must be the device tree identifier of the FILTER pin. Only + for the ad778x chips. If specified, it will be asserted + during driver probe. As the line is active low, it should be + marked GPIO_ACTIVE_LOW. + +Example: + +adc@0 { + compatible = "adi,ad7780"; + reg = <0>; + vref-supply = <&vdd_supply> + + powerdown-gpios = <&gpio 12 GPIO_ACTIVE_HIGH>; + adi,gain-gpios = <&gpio 5 GPIO_ACTIVE_LOW>; + adi,filter-gpios = <&gpio 15 GPIO_ACTIVE_LOW>; +}; -- cgit v1.2.3 From a816646f08ce18e8787d241e1dbda5cbc314e5ea Mon Sep 17 00:00:00 2001 From: Marcelo Schmitt Date: Sat, 16 Mar 2019 12:07:32 -0300 Subject: staging: iio: ad5933: add ABI documentation Add an ABI documentation for the ad5933 driver. Signed-off-by: Marcelo Schmitt Signed-off-by: Jonathan Cameron --- .../sysfs-bus-iio-impedance-analyzer-ad5933 | 35 ++++++++++++++++++++++ .../sysfs-bus-iio-impedance-analyzer-ad5933 | 30 ------------------- 2 files changed, 35 insertions(+), 30 deletions(-) create mode 100644 Documentation/ABI/testing/sysfs-bus-iio-impedance-analyzer-ad5933 delete mode 100644 drivers/staging/iio/Documentation/sysfs-bus-iio-impedance-analyzer-ad5933 (limited to 'Documentation') diff --git a/Documentation/ABI/testing/sysfs-bus-iio-impedance-analyzer-ad5933 b/Documentation/ABI/testing/sysfs-bus-iio-impedance-analyzer-ad5933 new file mode 100644 index 000000000000..0e86747c67f8 --- /dev/null +++ b/Documentation/ABI/testing/sysfs-bus-iio-impedance-analyzer-ad5933 @@ -0,0 +1,35 @@ +What: /sys/bus/iio/devices/iio:deviceX/out_altvoltageY_frequency_start +Date: March 2019 +KernelVersion: 3.1.0 +Contact: linux-iio@vger.kernel.org +Description: + Frequency sweep start frequency in Hz. + +What: /sys/bus/iio/devices/iio:deviceX/out_altvoltageY_frequency_increment +Date: March 2019 +KernelVersion: 3.1.0 +Contact: linux-iio@vger.kernel.org +Description: + Frequency increment in Hz (step size) between consecutive + frequency points along the sweep. + +What: /sys/bus/iio/devices/iio:deviceX/out_altvoltageY_frequency_points +Date: March 2019 +KernelVersion: 3.1.0 +Contact: linux-iio@vger.kernel.org +Description: + Number of frequency points (steps) in the frequency sweep. + This value, in conjunction with the + out_altvoltageY_frequency_start and the + out_altvoltageY_frequency_increment, determines the frequency + sweep range for the sweep operation. + +What: /sys/bus/iio/devices/iio:deviceX/out_altvoltageY_settling_cycles +Date: March 2019 +KernelVersion: 3.1.0 +Contact: linux-iio@vger.kernel.org +Description: + Number of output excitation cycles (settling time cycles) + that are allowed to pass through the unknown impedance, + after each frequency increment, and before the ADC is triggered + to perform a conversion sequence of the response signal. diff --git a/drivers/staging/iio/Documentation/sysfs-bus-iio-impedance-analyzer-ad5933 b/drivers/staging/iio/Documentation/sysfs-bus-iio-impedance-analyzer-ad5933 deleted file mode 100644 index 79c7e88c64cd..000000000000 --- a/drivers/staging/iio/Documentation/sysfs-bus-iio-impedance-analyzer-ad5933 +++ /dev/null @@ -1,30 +0,0 @@ -What: /sys/bus/iio/devices/iio:deviceX/outY_freq_start -KernelVersion: 3.1.0 -Contact: linux-iio@vger.kernel.org -Description: - Frequency sweep start frequency in Hz. - -What: /sys/bus/iio/devices/iio:deviceX/outY_freq_increment -KernelVersion: 3.1.0 -Contact: linux-iio@vger.kernel.org -Description: - Frequency increment in Hz (step size) between consecutive - frequency points along the sweep. - -What: /sys/bus/iio/devices/iio:deviceX/outY_freq_points -KernelVersion: 3.1.0 -Contact: linux-iio@vger.kernel.org -Description: - Number of frequency points (steps) in the frequency sweep. - This value, in conjunction with the outY_freq_start and the - outY_freq_increment, determines the frequency sweep range - for the sweep operation. - -What: /sys/bus/iio/devices/iio:deviceX/outY_settling_cycles -KernelVersion: 3.1.0 -Contact: linux-iio@vger.kernel.org -Description: - Number of output excitation cycles (settling time cycles) - that are allowed to pass through the unknown impedance, - after each frequency increment, and before the ADC is triggered - to perform a conversion sequence of the response signal. -- cgit v1.2.3 From 835ab93dcdcfb492609db7769c2717097b12e1ae Mon Sep 17 00:00:00 2001 From: Andreas Klinger Date: Sun, 17 Mar 2019 21:35:00 +0100 Subject: dt-bindings: Add vendor prefix for MaxBotix MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Add MaxBotix, which is a vendor of ultrasonic rangers in different varieties and interfaces. Signed-off-by: Andreas Klinger Reviewed-by: Andreas Färber Reviewed-by: Rob Herring Signed-off-by: Jonathan Cameron --- Documentation/devicetree/bindings/vendor-prefixes.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/vendor-prefixes.txt b/Documentation/devicetree/bindings/vendor-prefixes.txt index f4ce79170185..93753f447c20 100644 --- a/Documentation/devicetree/bindings/vendor-prefixes.txt +++ b/Documentation/devicetree/bindings/vendor-prefixes.txt @@ -234,6 +234,7 @@ lsi LSI Corp. (LSI Logic) lwn Liebherr-Werk Nenzing GmbH macnica Macnica Americas marvell Marvell Technology Group Ltd. +maxbotix MaxBotix Inc. maxim Maxim Integrated Products mbvl Mobiveil Inc. mcube mCube -- cgit v1.2.3 From 7483e40d7e43fb718d1014cee650b2333cf23116 Mon Sep 17 00:00:00 2001 From: Andreas Klinger Date: Sun, 17 Mar 2019 21:35:27 +0100 Subject: dt-bindings: maxbotix,mb1232: Add MaxBotix i2c ultrasonic rangers Add doc for dt binding maxbotix,mb1232. This binding is for MaxBotix I2CXL-MaxSonar ultrasonic rangers which share a common i2c interface. Signed-off-by: Andreas Klinger Reviewed-by: Rob Herring Signed-off-by: Jonathan Cameron --- .../bindings/iio/proximity/maxbotix,mb1232.txt | 29 ++++++++++++++++++++++ 1 file changed, 29 insertions(+) create mode 100644 Documentation/devicetree/bindings/iio/proximity/maxbotix,mb1232.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/proximity/maxbotix,mb1232.txt b/Documentation/devicetree/bindings/iio/proximity/maxbotix,mb1232.txt new file mode 100644 index 000000000000..dd1058fbe9c3 --- /dev/null +++ b/Documentation/devicetree/bindings/iio/proximity/maxbotix,mb1232.txt @@ -0,0 +1,29 @@ +* MaxBotix I2CXL-MaxSonar ultrasonic distance sensor of type mb1202, + mb1212, mb1222, mb1232, mb1242, mb7040 or mb7137 using the i2c interface + for ranging + +Required properties: + - compatible: "maxbotix,mb1202", + "maxbotix,mb1212", + "maxbotix,mb1222", + "maxbotix,mb1232", + "maxbotix,mb1242", + "maxbotix,mb7040" or + "maxbotix,mb7137" + + - reg: i2c address of the device, see also i2c/i2c.txt + +Optional properties: + - interrupts: Interrupt used to announce the preceding reading + request has finished and that data is available. + If no interrupt is specified the device driver + falls back to wait a fixed amount of time until + data can be retrieved. + +Example: +proximity@70 { + compatible = "maxbotix,mb1232"; + reg = <0x70>; + interrupt-parent = <&gpio2>; + interrupts = <2 IRQ_TYPE_EDGE_FALLING>; +}; -- cgit v1.2.3 From 5da8affed2f8f8251653733d7812807c7eac7637 Mon Sep 17 00:00:00 2001 From: "Angus Ainslie (Purism)" Date: Thu, 21 Mar 2019 08:40:45 -0700 Subject: dt-bindings: iio: light: add vcnl4000 devicetree bindings Document the vishay VCNL4000 devicetree bindings. Signed-off-by: Angus Ainslie (Purism) Reviewed-by: Rob Herring Signed-off-by: Jonathan Cameron --- .../devicetree/bindings/iio/light/vcnl4000.txt | 22 ++++++++++++++++++++++ 1 file changed, 22 insertions(+) create mode 100644 Documentation/devicetree/bindings/iio/light/vcnl4000.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/light/vcnl4000.txt b/Documentation/devicetree/bindings/iio/light/vcnl4000.txt new file mode 100644 index 000000000000..4a9d558a412a --- /dev/null +++ b/Documentation/devicetree/bindings/iio/light/vcnl4000.txt @@ -0,0 +1,22 @@ +VISHAY VCNL4000 - Ambient Light and proximity sensor + +This driver supports the VCNL4000/10/20 and VCNL4200 chips + +Required properties: + + -compatible: must be one of : + vishay,vcnl4000 + vishay,vcnl4010 + vishay,vcnl4020 + vishay,vcnl4200 + + -reg: I2C address of the sensor, should be one from below based on the model: + 0x13 + 0x51 + +Example: + +light-sensor@51 { + compatible = "vishay,vcnl4200"; + reg = <0x51>; +}; -- cgit v1.2.3 From 54480943235e0533d5ffd6d64697eb38df8b7c0c Mon Sep 17 00:00:00 2001 From: "Angus Ainslie (Purism)" Date: Thu, 21 Mar 2019 08:40:47 -0700 Subject: dt-bindings: iio: light: add vcnl4040 devicetree bindings Document the vishay VCNL4040 devicetree bindings. Signed-off-by: Angus Ainslie (Purism) Reviewed-by: Rob Herring Signed-off-by: Jonathan Cameron --- Documentation/devicetree/bindings/iio/light/vcnl4000.txt | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/light/vcnl4000.txt b/Documentation/devicetree/bindings/iio/light/vcnl4000.txt index 4a9d558a412a..955af4555c90 100644 --- a/Documentation/devicetree/bindings/iio/light/vcnl4000.txt +++ b/Documentation/devicetree/bindings/iio/light/vcnl4000.txt @@ -1,6 +1,6 @@ VISHAY VCNL4000 - Ambient Light and proximity sensor -This driver supports the VCNL4000/10/20 and VCNL4200 chips +This driver supports the VCNL4000/10/20/40 and VCNL4200 chips Required properties: @@ -8,11 +8,13 @@ Required properties: vishay,vcnl4000 vishay,vcnl4010 vishay,vcnl4020 + vishay,vcnl4040 vishay,vcnl4200 -reg: I2C address of the sensor, should be one from below based on the model: 0x13 0x51 + 0x60 Example: -- cgit v1.2.3 From e8379e05e811daa7a07aa0ac3ed958fedee1c504 Mon Sep 17 00:00:00 2001 From: "H. Nikolaus Schaller" Date: Mon, 18 Mar 2019 16:14:15 +0100 Subject: dt-bindings: iio: add Bosch BMG160 gyroscope sensor Define bindings for "bosch,bmg160" and "bosch,bmi055_gyro". Signed-off-by: H. Nikolaus Schaller Reviewed-by: Rob Herring Signed-off-by: Jonathan Cameron --- .../devicetree/bindings/iio/gyroscope/bmg160.txt | 20 ++++++++++++++++++++ 1 file changed, 20 insertions(+) create mode 100644 Documentation/devicetree/bindings/iio/gyroscope/bmg160.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/gyroscope/bmg160.txt b/Documentation/devicetree/bindings/iio/gyroscope/bmg160.txt new file mode 100644 index 000000000000..78e18a1e9c1d --- /dev/null +++ b/Documentation/devicetree/bindings/iio/gyroscope/bmg160.txt @@ -0,0 +1,20 @@ +* Bosch BMG160 triaxial rotation sensor (gyroscope) + +Required properties: + + - compatible : should be "bosch,bmg160" or "bosch,bmi055_gyro" + - reg : the I2C address of the sensor (0x69) + +Optional properties: + + - interrupts : interrupt mapping for GPIO IRQ, it should by configured with + flags IRQ_TYPE_EDGE_RISING + +Example: + +bmg160@69 { + compatible = "bosch,bmg160"; + reg = <0x69>; + interrupt-parent = <&gpio6>; + interrupts = <18 (IRQ_TYPE_EDGE_RISING)>; +}; -- cgit v1.2.3 From 52f171abaecb822f8c3fee4dc9887d12bea0e63a Mon Sep 17 00:00:00 2001 From: Andreas Klinger Date: Tue, 26 Mar 2019 14:39:40 +0100 Subject: devantech-srf04.yaml: transform DT binding to YAML devantech-srf04.yaml: yaml devicetree binding for iio ultrasonic proximity driver of devantech srf04 use devantech-srf04.txt, transform binding into yaml and remove the outdated DT documentation Signed-off-by: Andreas Klinger Reviewed-by: Rob Herring Signed-off-by: Jonathan Cameron --- .../bindings/iio/proximity/devantech-srf04.txt | 28 ---------- .../bindings/iio/proximity/devantech-srf04.yaml | 59 ++++++++++++++++++++++ 2 files changed, 59 insertions(+), 28 deletions(-) delete mode 100644 Documentation/devicetree/bindings/iio/proximity/devantech-srf04.txt create mode 100644 Documentation/devicetree/bindings/iio/proximity/devantech-srf04.yaml (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/proximity/devantech-srf04.txt b/Documentation/devicetree/bindings/iio/proximity/devantech-srf04.txt deleted file mode 100644 index d4dc7a227e2e..000000000000 --- a/Documentation/devicetree/bindings/iio/proximity/devantech-srf04.txt +++ /dev/null @@ -1,28 +0,0 @@ -* Devantech SRF04 ultrasonic range finder - Bit-banging driver using two GPIOs - -Required properties: - - compatible: Should be "devantech,srf04" - - - trig-gpios: Definition of the GPIO for the triggering (output) - This GPIO is set for about 10 us by the driver to tell the - device it should initiate the measurement cycle. - - - echo-gpios: Definition of the GPIO for the echo (input) - This GPIO is set by the device as soon as an ultrasonic - burst is sent out and reset when the first echo is - received. - Thus this GPIO is set while the ultrasonic waves are doing - one round trip. - It needs to be an GPIO which is able to deliver an - interrupt because the time between two interrupts is - measured in the driver. - See Documentation/devicetree/bindings/gpio/gpio.txt for - information on how to specify a consumer gpio. - -Example: -srf04@0 { - compatible = "devantech,srf04"; - trig-gpios = <&gpio1 15 GPIO_ACTIVE_HIGH>; - echo-gpios = <&gpio2 6 GPIO_ACTIVE_HIGH>; -}; diff --git a/Documentation/devicetree/bindings/iio/proximity/devantech-srf04.yaml b/Documentation/devicetree/bindings/iio/proximity/devantech-srf04.yaml new file mode 100644 index 000000000000..e7aab785c97d --- /dev/null +++ b/Documentation/devicetree/bindings/iio/proximity/devantech-srf04.yaml @@ -0,0 +1,59 @@ +# SPDX-License-Identifier: GPL-2.0 +%YAML 1.2 +--- +$id: http://devicetree.org/schemas/iio/proximity/devantech-srf04.yaml# +$schema: http://devicetree.org/meta-schemas/core.yaml# + +title: Devantech SRF04 ultrasonic range finder + +maintainers: + - Andreas Klinger + +description: | + Bit-banging driver using two GPIOs: + - trigger-gpio is raised by the driver to start sending out an ultrasonic + burst + - echo-gpio is held high by the sensor after sending ultrasonic burst + until it is received once again + + Specifications about the driver can be found at: + http://www.robot-electronics.co.uk/htm/srf04tech.htm + +properties: + compatible: + items: + - const: devantech,srf04 + + trig-gpios: + description: + Definition of the GPIO for the triggering (output) This GPIO is set + for about 10 us by the driver to tell the device it should initiate + the measurement cycle. + maxItems: 1 + + echo-gpios: + description: + Definition of the GPIO for the echo (input) + This GPIO is set by the device as soon as an ultrasonic burst is sent + out and reset when the first echo is received. + Thus this GPIO is set while the ultrasonic waves are doing one round + trip. + It needs to be an GPIO which is able to deliver an interrupt because + the time between two interrupts is measured in the driver. + See Documentation/devicetree/bindings/gpio/gpio.txt for information + on how to specify a consumer gpio. + maxItems: 1 + +required: + - compatible + - trig-gpios + - echo-gpios + +examples: + - | + #include + proximity { + compatible = "devantech,srf04"; + trig-gpios = <&gpio1 15 GPIO_ACTIVE_HIGH>; + echo-gpios = <&gpio2 6 GPIO_ACTIVE_HIGH>; + }; -- cgit v1.2.3 From 023e41632e065d49bcbe31b3c4b336217f96a271 Mon Sep 17 00:00:00 2001 From: Patrick Havelange Date: Tue, 26 Mar 2019 12:18:40 +0100 Subject: dt-bindings: iio/temperature: Add thermocouple types (and doc) This patch introduces common thermocouple types used by various temperature sensors. Also a brief documentation explaining this "thermocouple-type" property. Signed-off-by: Patrick Havelange Signed-off-by: Jonathan Cameron --- .../bindings/iio/temperature/temperature-bindings.txt | 7 +++++++ include/dt-bindings/iio/temperature/thermocouple.h | 16 ++++++++++++++++ 2 files changed, 23 insertions(+) create mode 100644 Documentation/devicetree/bindings/iio/temperature/temperature-bindings.txt create mode 100644 include/dt-bindings/iio/temperature/thermocouple.h (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/temperature/temperature-bindings.txt b/Documentation/devicetree/bindings/iio/temperature/temperature-bindings.txt new file mode 100644 index 000000000000..8f339cab74ae --- /dev/null +++ b/Documentation/devicetree/bindings/iio/temperature/temperature-bindings.txt @@ -0,0 +1,7 @@ +If the temperature sensor device can be configured to use some specific +thermocouple type, you can use the defined types provided in the file +"include/dt-bindings/iio/temperature/thermocouple.h". + +Property: +thermocouple-type: A single cell representing the type of the thermocouple + used by the device. diff --git a/include/dt-bindings/iio/temperature/thermocouple.h b/include/dt-bindings/iio/temperature/thermocouple.h new file mode 100644 index 000000000000..ce037f5238ac --- /dev/null +++ b/include/dt-bindings/iio/temperature/thermocouple.h @@ -0,0 +1,16 @@ +/* SPDX-License-Identifier: GPL-2.0 */ + +#ifndef _DT_BINDINGS_TEMPERATURE_THERMOCOUPLE_H +#define _DT_BINDINGS_TEMPERATURE_THERMOCOUPLE_H + + +#define THERMOCOUPLE_TYPE_B 0x00 +#define THERMOCOUPLE_TYPE_E 0x01 +#define THERMOCOUPLE_TYPE_J 0x02 +#define THERMOCOUPLE_TYPE_K 0x03 +#define THERMOCOUPLE_TYPE_N 0x04 +#define THERMOCOUPLE_TYPE_R 0x05 +#define THERMOCOUPLE_TYPE_S 0x06 +#define THERMOCOUPLE_TYPE_T 0x07 + +#endif /* _DT_BINDINGS_TEMPERATURE_THERMOCOUPLE_H */ -- cgit v1.2.3 From 8fede567b8472b36e2af3eac94ba68b234533bac Mon Sep 17 00:00:00 2001 From: Paresh Chaudhary Date: Tue, 26 Mar 2019 12:18:41 +0100 Subject: iio:temperature:max31856:Add device tree bind info This patch added device tree binding info for MAX31856 driver. Signed-off-by: Paresh Chaudhary Signed-off-by: Matt Weber Signed-off-by: Patrick Havelange Reviewed-by: Rob Herring Signed-off-by: Jonathan Cameron --- .../bindings/iio/temperature/max31856.txt | 24 ++++++++++++++++++++++ 1 file changed, 24 insertions(+) create mode 100644 Documentation/devicetree/bindings/iio/temperature/max31856.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/temperature/max31856.txt b/Documentation/devicetree/bindings/iio/temperature/max31856.txt new file mode 100644 index 000000000000..06ab43bb4de8 --- /dev/null +++ b/Documentation/devicetree/bindings/iio/temperature/max31856.txt @@ -0,0 +1,24 @@ +Maxim MAX31856 thermocouple support + +https://datasheets.maximintegrated.com/en/ds/MAX31856.pdf + +Optional property: + - thermocouple-type: Type of thermocouple (THERMOCOUPLE_TYPE_K if + omitted). Supported types are B, E, J, K, N, R, S, T. + +Required properties: + - compatible: must be "maxim,max31856" + - reg: SPI chip select number for the device + - spi-max-frequency: As per datasheet max. supported freq is 5000000 + - spi-cpha: must be defined for max31856 to enable SPI mode 1 + + Refer to spi/spi-bus.txt for generic SPI slave bindings. + + Example: + temp-sensor@0 { + compatible = "maxim,max31856"; + reg = <0>; + spi-max-frequency = <5000000>; + spi-cpha; + thermocouple-type = ; + }; -- cgit v1.2.3 From fb55a51310d1791b439e8d70f693410f5ef616a4 Mon Sep 17 00:00:00 2001 From: Paresh Chaudhary Date: Tue, 26 Mar 2019 12:18:42 +0100 Subject: iio:temperature: Add MAX31856 thermocouple support This patch adds support for Maxim MAX31856 thermocouple temperature sensor support. More information can be found in: https://www.maximintegrated.com/en/ds/MAX31856.pdf NOTE: Driver support only Comparator Mode. Signed-off-by: Paresh Chaudhary Signed-off-by: Matt Weber Signed-off-by: Patrick Havelange Signed-off-by: Jonathan Cameron --- .../ABI/testing/sysfs-bus-iio-temperature-max31856 | 24 ++ drivers/iio/temperature/Kconfig | 10 + drivers/iio/temperature/Makefile | 1 + drivers/iio/temperature/max31856.c | 353 +++++++++++++++++++++ 4 files changed, 388 insertions(+) create mode 100644 Documentation/ABI/testing/sysfs-bus-iio-temperature-max31856 create mode 100644 drivers/iio/temperature/max31856.c (limited to 'Documentation') diff --git a/Documentation/ABI/testing/sysfs-bus-iio-temperature-max31856 b/Documentation/ABI/testing/sysfs-bus-iio-temperature-max31856 new file mode 100644 index 000000000000..3b3509a3ef2f --- /dev/null +++ b/Documentation/ABI/testing/sysfs-bus-iio-temperature-max31856 @@ -0,0 +1,24 @@ +What: /sys/bus/iio/devices/iio:deviceX/fault_oc +KernelVersion: 5.1 +Contact: linux-iio@vger.kernel.org +Description: + Open-circuit fault. The detection of open-circuit faults, + such as those caused by broken thermocouple wires. + Reading returns either '1' or '0'. + '1' = An open circuit such as broken thermocouple wires + has been detected. + '0' = No open circuit or broken thermocouple wires are detected + +What: /sys/bus/iio/devices/iio:deviceX/fault_ovuv +KernelVersion: 5.1 +Contact: linux-iio@vger.kernel.org +Description: + Overvoltage or Undervoltage Input Fault. The internal circuitry + is protected from excessive voltages applied to the thermocouple + cables by integrated MOSFETs at the T+ and T- inputs, and the + BIAS output. These MOSFETs turn off when the input voltage is + negative or greater than VDD. + Reading returns either '1' or '0'. + '1' = The input voltage is negative or greater than VDD. + '0' = The input voltage is positive and less than VDD (normal + state). diff --git a/drivers/iio/temperature/Kconfig b/drivers/iio/temperature/Kconfig index 7f0b8261c8ba..c185cbee25c7 100644 --- a/drivers/iio/temperature/Kconfig +++ b/drivers/iio/temperature/Kconfig @@ -97,4 +97,14 @@ config TSYS02D This driver can also be built as a module. If so, the module will be called tsys02d. +config MAX31856 + tristate "MAX31856 thermocouple sensor" + depends on SPI + help + If you say yes here you get support for MAX31856 + thermocouple sensor chip connected via SPI. + + This driver can also be built as a module. If so, the module + will be called max31856. + endmenu diff --git a/drivers/iio/temperature/Makefile b/drivers/iio/temperature/Makefile index 34a31db0bb63..baca4776ca0d 100644 --- a/drivers/iio/temperature/Makefile +++ b/drivers/iio/temperature/Makefile @@ -5,6 +5,7 @@ obj-$(CONFIG_HID_SENSOR_TEMP) += hid-sensor-temperature.o obj-$(CONFIG_MAXIM_THERMOCOUPLE) += maxim_thermocouple.o +obj-$(CONFIG_MAX31856) += max31856.o obj-$(CONFIG_MLX90614) += mlx90614.o obj-$(CONFIG_MLX90632) += mlx90632.o obj-$(CONFIG_TMP006) += tmp006.o diff --git a/drivers/iio/temperature/max31856.c b/drivers/iio/temperature/max31856.c new file mode 100644 index 000000000000..6b67d6b95cf9 --- /dev/null +++ b/drivers/iio/temperature/max31856.c @@ -0,0 +1,353 @@ +// SPDX-License-Identifier: GPL-2.0 +/* max31856.c + * + * Maxim MAX31856 thermocouple sensor driver + * + * Copyright (C) 2018-2019 Rockwell Collins + */ + +#include +#include +#include +#include +#include +#include +#include +/* + * The MSB of the register value determines whether the following byte will + * be written or read. If it is 0, one or more byte reads will follow. + */ +#define MAX31856_RD_WR_BIT BIT(7) + +#define MAX31856_CR0_AUTOCONVERT BIT(7) +#define MAX31856_CR0_1SHOT BIT(6) +#define MAX31856_CR0_OCFAULT BIT(4) +#define MAX31856_CR0_OCFAULT_MASK GENMASK(5, 4) +#define MAX31856_TC_TYPE_MASK GENMASK(3, 0) +#define MAX31856_FAULT_OVUV BIT(1) +#define MAX31856_FAULT_OPEN BIT(0) + +/* The MAX31856 registers */ +#define MAX31856_CR0_REG 0x00 +#define MAX31856_CR1_REG 0x01 +#define MAX31856_MASK_REG 0x02 +#define MAX31856_CJHF_REG 0x03 +#define MAX31856_CJLF_REG 0x04 +#define MAX31856_LTHFTH_REG 0x05 +#define MAX31856_LTHFTL_REG 0x06 +#define MAX31856_LTLFTH_REG 0x07 +#define MAX31856_LTLFTL_REG 0x08 +#define MAX31856_CJTO_REG 0x09 +#define MAX31856_CJTH_REG 0x0A +#define MAX31856_CJTL_REG 0x0B +#define MAX31856_LTCBH_REG 0x0C +#define MAX31856_LTCBM_REG 0x0D +#define MAX31856_LTCBL_REG 0x0E +#define MAX31856_SR_REG 0x0F + +static const struct iio_chan_spec max31856_channels[] = { + { /* Thermocouple Temperature */ + .type = IIO_TEMP, + .info_mask_separate = + BIT(IIO_CHAN_INFO_RAW) | BIT(IIO_CHAN_INFO_SCALE), + }, + { /* Cold Junction Temperature */ + .type = IIO_TEMP, + .channel2 = IIO_MOD_TEMP_AMBIENT, + .modified = 1, + .info_mask_separate = + BIT(IIO_CHAN_INFO_RAW) | BIT(IIO_CHAN_INFO_SCALE), + }, +}; + +struct max31856_data { + struct spi_device *spi; + u32 thermocouple_type; +}; + +static int max31856_read(struct max31856_data *data, u8 reg, + u8 val[], unsigned int read_size) +{ + return spi_write_then_read(data->spi, ®, 1, val, read_size); +} + +static int max31856_write(struct max31856_data *data, u8 reg, + unsigned int val) +{ + u8 buf[2]; + + buf[0] = reg | (MAX31856_RD_WR_BIT); + buf[1] = val; + + return spi_write(data->spi, buf, 2); +} + +static int max31856_init(struct max31856_data *data) +{ + int ret; + u8 reg_cr0_val, reg_cr1_val; + + /* Start by changing to Off mode before making changes as + * some settings are recommended to be set only when the device + * is off + */ + ret = max31856_read(data, MAX31856_CR0_REG, ®_cr0_val, 1); + if (ret) + return ret; + + reg_cr0_val &= ~MAX31856_CR0_AUTOCONVERT; + ret = max31856_write(data, MAX31856_CR0_REG, reg_cr0_val); + if (ret) + return ret; + + /* Set thermocouple type based on dts property */ + ret = max31856_read(data, MAX31856_CR1_REG, ®_cr1_val, 1); + if (ret) + return ret; + + reg_cr1_val &= ~MAX31856_TC_TYPE_MASK; + reg_cr1_val |= data->thermocouple_type; + ret = max31856_write(data, MAX31856_CR1_REG, reg_cr1_val); + if (ret) + return ret; + + /* + * Enable Open circuit fault detection + * Read datasheet for more information: Table 4. + * Value 01 means : Enabled (Once every 16 conversions) + */ + reg_cr0_val &= ~MAX31856_CR0_OCFAULT_MASK; + reg_cr0_val |= MAX31856_CR0_OCFAULT; + + /* Set Auto Conversion Mode */ + reg_cr0_val &= ~MAX31856_CR0_1SHOT; + reg_cr0_val |= MAX31856_CR0_AUTOCONVERT; + + return max31856_write(data, MAX31856_CR0_REG, reg_cr0_val); +} + +static int max31856_thermocouple_read(struct max31856_data *data, + struct iio_chan_spec const *chan, + int *val) +{ + int ret, offset_cjto; + u8 reg_val[3]; + + switch (chan->channel2) { + case IIO_NO_MOD: + /* + * Multibyte Read + * MAX31856_LTCBH_REG, MAX31856_LTCBM_REG, MAX31856_LTCBL_REG + */ + ret = max31856_read(data, MAX31856_LTCBH_REG, reg_val, 3); + if (ret) + return ret; + /* Skip last 5 dead bits of LTCBL */ + *val = (reg_val[0] << 16 | reg_val[1] << 8 | reg_val[2]) >> 5; + /* Check 7th bit of LTCBH reg. value for sign*/ + if (reg_val[0] & 0x80) + *val -= 0x80000; + break; + + case IIO_MOD_TEMP_AMBIENT: + /* + * Multibyte Read + * MAX31856_CJTO_REG, MAX31856_CJTH_REG, MAX31856_CJTL_REG + */ + ret = max31856_read(data, MAX31856_CJTO_REG, reg_val, 3); + if (ret) + return ret; + /* Get Cold Junction Temp. offset register value */ + offset_cjto = reg_val[0]; + /* Get CJTH and CJTL value and skip last 2 dead bits of CJTL */ + *val = (reg_val[1] << 8 | reg_val[2]) >> 2; + /* As per datasheet add offset into CJTH and CJTL */ + *val += offset_cjto; + /* Check 7th bit of CJTH reg. value for sign */ + if (reg_val[1] & 0x80) + *val -= 0x4000; + break; + + default: + return -EINVAL; + } + + ret = max31856_read(data, MAX31856_SR_REG, reg_val, 1); + if (ret) + return ret; + /* Check for over/under voltage or open circuit fault */ + if (reg_val[0] & (MAX31856_FAULT_OVUV | MAX31856_FAULT_OPEN)) + return -EIO; + + return ret; +} + +static int max31856_read_raw(struct iio_dev *indio_dev, + struct iio_chan_spec const *chan, + int *val, int *val2, long mask) +{ + struct max31856_data *data = iio_priv(indio_dev); + int ret; + + switch (mask) { + case IIO_CHAN_INFO_RAW: + ret = max31856_thermocouple_read(data, chan, val); + if (ret) + return ret; + return IIO_VAL_INT; + case IIO_CHAN_INFO_SCALE: + switch (chan->channel2) { + case IIO_MOD_TEMP_AMBIENT: + /* Cold junction Temp. Data resolution is 0.015625 */ + *val = 15; + *val2 = 625000; /* 1000 * 0.015625 */ + ret = IIO_VAL_INT_PLUS_MICRO; + break; + default: + /* Thermocouple Temp. Data resolution is 0.0078125 */ + *val = 7; + *val2 = 812500; /* 1000 * 0.0078125) */ + return IIO_VAL_INT_PLUS_MICRO; + } + break; + } + + return ret; +} + +static ssize_t show_fault(struct device *dev, u8 faultbit, char *buf) +{ + struct iio_dev *indio_dev = dev_to_iio_dev(dev); + struct max31856_data *data = iio_priv(indio_dev); + u8 reg_val; + int ret; + bool fault; + + ret = max31856_read(data, MAX31856_SR_REG, ®_val, 1); + if (ret) + return ret; + + fault = reg_val & faultbit; + + return sprintf(buf, "%d\n", fault); +} + +static ssize_t show_fault_ovuv(struct device *dev, + struct device_attribute *attr, + char *buf) +{ + return show_fault(dev, MAX31856_FAULT_OVUV, buf); +} + +static ssize_t show_fault_oc(struct device *dev, + struct device_attribute *attr, + char *buf) +{ + return show_fault(dev, MAX31856_FAULT_OPEN, buf); +} + +static IIO_DEVICE_ATTR(fault_ovuv, 0444, show_fault_ovuv, NULL, 0); +static IIO_DEVICE_ATTR(fault_oc, 0444, show_fault_oc, NULL, 0); + +static struct attribute *max31856_attributes[] = { + &iio_dev_attr_fault_ovuv.dev_attr.attr, + &iio_dev_attr_fault_oc.dev_attr.attr, + NULL, +}; + +static const struct attribute_group max31856_group = { + .attrs = max31856_attributes, +}; + +static const struct iio_info max31856_info = { + .read_raw = max31856_read_raw, + .attrs = &max31856_group, +}; + +static int max31856_probe(struct spi_device *spi) +{ + const struct spi_device_id *id = spi_get_device_id(spi); + struct iio_dev *indio_dev; + struct max31856_data *data; + int ret; + + indio_dev = devm_iio_device_alloc(&spi->dev, sizeof(*data)); + if (!indio_dev) + return -ENOMEM; + + data = iio_priv(indio_dev); + data->spi = spi; + + spi_set_drvdata(spi, indio_dev); + + indio_dev->info = &max31856_info; + indio_dev->name = id->name; + indio_dev->modes = INDIO_DIRECT_MODE; + indio_dev->channels = max31856_channels; + indio_dev->num_channels = ARRAY_SIZE(max31856_channels); + + ret = of_property_read_u32(spi->dev.of_node, "thermocouple-type", + &data->thermocouple_type); + + if (ret) { + dev_info(&spi->dev, + "Could not read thermocouple type DT property, configuring as a K-Type\n"); + data->thermocouple_type = THERMOCOUPLE_TYPE_K; + } + + /* + * no need to translate values as the supported types + * have the same value as the #defines + */ + switch (data->thermocouple_type) { + case THERMOCOUPLE_TYPE_B: + case THERMOCOUPLE_TYPE_E: + case THERMOCOUPLE_TYPE_J: + case THERMOCOUPLE_TYPE_K: + case THERMOCOUPLE_TYPE_N: + case THERMOCOUPLE_TYPE_R: + case THERMOCOUPLE_TYPE_S: + case THERMOCOUPLE_TYPE_T: + break; + default: + dev_err(&spi->dev, + "error: thermocouple-type %u not supported by max31856\n" + , data->thermocouple_type); + return -EINVAL; + } + + ret = max31856_init(data); + if (ret) { + dev_err(&spi->dev, "error: Failed to configure max31856\n"); + return ret; + } + + return devm_iio_device_register(&spi->dev, indio_dev); +} + +static const struct spi_device_id max31856_id[] = { + { "max31856", 0 }, + { } +}; +MODULE_DEVICE_TABLE(spi, max31856_id); + +static const struct of_device_id max31856_of_match[] = { + { .compatible = "maxim,max31856" }, + { } +}; +MODULE_DEVICE_TABLE(of, max31856_of_match); + +static struct spi_driver max31856_driver = { + .driver = { + .name = "max31856", + .of_match_table = max31856_of_match, + }, + .probe = max31856_probe, + .id_table = max31856_id, +}; +module_spi_driver(max31856_driver); + +MODULE_AUTHOR("Paresh Chaudhary "); +MODULE_AUTHOR("Patrick Havelange "); +MODULE_DESCRIPTION("Maxim MAX31856 thermocouple sensor driver"); +MODULE_LICENSE("GPL"); -- cgit v1.2.3 From 679f4e6cfd45bcc14bb563576e419ac9e43fad7c Mon Sep 17 00:00:00 2001 From: Jerome Brunet Date: Thu, 4 Apr 2019 13:17:28 +0200 Subject: ASoC: meson: add g12a compatibles Add new compatible strings for the g12a devices. Audio wise, the g12a is fairly to close to the axg, yet some differences need to be handled. Signed-off-by: Jerome Brunet Signed-off-by: Mark Brown --- Documentation/devicetree/bindings/sound/amlogic,axg-fifo.txt | 4 +++- Documentation/devicetree/bindings/sound/amlogic,axg-pdm.txt | 3 ++- Documentation/devicetree/bindings/sound/amlogic,axg-spdifin.txt | 3 ++- Documentation/devicetree/bindings/sound/amlogic,axg-spdifout.txt | 3 ++- .../devicetree/bindings/sound/amlogic,axg-tdm-formatters.txt | 4 +++- 5 files changed, 12 insertions(+), 5 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/sound/amlogic,axg-fifo.txt b/Documentation/devicetree/bindings/sound/amlogic,axg-fifo.txt index 3dfc2515e5c6..4330fc9dca6d 100644 --- a/Documentation/devicetree/bindings/sound/amlogic,axg-fifo.txt +++ b/Documentation/devicetree/bindings/sound/amlogic,axg-fifo.txt @@ -2,7 +2,9 @@ Required properties: - compatible: 'amlogic,axg-toddr' or - 'amlogic,axg-frddr' + 'amlogic,axg-toddr' or + 'amlogic,g12a-frddr' or + 'amlogic,g12a-toddr' - reg: physical base address of the controller and length of memory mapped region. - interrupts: interrupt specifier for the fifo. diff --git a/Documentation/devicetree/bindings/sound/amlogic,axg-pdm.txt b/Documentation/devicetree/bindings/sound/amlogic,axg-pdm.txt index 5672d0bc5b16..73f473a9365f 100644 --- a/Documentation/devicetree/bindings/sound/amlogic,axg-pdm.txt +++ b/Documentation/devicetree/bindings/sound/amlogic,axg-pdm.txt @@ -1,7 +1,8 @@ * Amlogic Audio PDM input Required properties: -- compatible: 'amlogic,axg-pdm' +- compatible: 'amlogic,axg-pdm' or + 'amlogic,g12a-pdm' - reg: physical base address of the controller and length of memory mapped region. - clocks: list of clock phandle, one for each entry clock-names. diff --git a/Documentation/devicetree/bindings/sound/amlogic,axg-spdifin.txt b/Documentation/devicetree/bindings/sound/amlogic,axg-spdifin.txt index 2e6cb7d9b202..0b82504fa419 100644 --- a/Documentation/devicetree/bindings/sound/amlogic,axg-spdifin.txt +++ b/Documentation/devicetree/bindings/sound/amlogic,axg-spdifin.txt @@ -1,7 +1,8 @@ * Amlogic Audio SPDIF Input Required properties: -- compatible: 'amlogic,axg-spdifin' +- compatible: 'amlogic,axg-spdifin' or + 'amlogic,g12a-spdifin' - interrupts: interrupt specifier for the spdif input. - clocks: list of clock phandle, one for each entry clock-names. - clock-names: should contain the following: diff --git a/Documentation/devicetree/bindings/sound/amlogic,axg-spdifout.txt b/Documentation/devicetree/bindings/sound/amlogic,axg-spdifout.txt index 521c38ad89e7..826152730508 100644 --- a/Documentation/devicetree/bindings/sound/amlogic,axg-spdifout.txt +++ b/Documentation/devicetree/bindings/sound/amlogic,axg-spdifout.txt @@ -1,7 +1,8 @@ * Amlogic Audio SPDIF Output Required properties: -- compatible: 'amlogic,axg-spdifout' +- compatible: 'amlogic,axg-spdifout' or + 'amlogic,g12a-spdifout' - clocks: list of clock phandle, one for each entry clock-names. - clock-names: should contain the following: * "pclk" : peripheral clock. diff --git a/Documentation/devicetree/bindings/sound/amlogic,axg-tdm-formatters.txt b/Documentation/devicetree/bindings/sound/amlogic,axg-tdm-formatters.txt index 1c1b7490554e..3b94a715a0b9 100644 --- a/Documentation/devicetree/bindings/sound/amlogic,axg-tdm-formatters.txt +++ b/Documentation/devicetree/bindings/sound/amlogic,axg-tdm-formatters.txt @@ -2,7 +2,9 @@ Required properties: - compatible: 'amlogic,axg-tdmin' or - 'amlogic,axg-tdmout' + 'amlogic,axg-tdmout' or + 'amlogic,g12a-tdmin' or + 'amlogic,g12a-tdmout' - reg: physical base address of the controller and length of memory mapped region. - clocks: list of clock phandle, one for each entry clock-names. -- cgit v1.2.3 From d2920ef5d094b59254bedfccb1fab984d101c332 Mon Sep 17 00:00:00 2001 From: Naga Sureshkumar Relli Date: Mon, 1 Apr 2019 13:28:32 +0530 Subject: dt-bindings: spi: Add device tree binding documentation for Zynq QSPI controller This patch adds the dts binding document for Zynq SOC QSPI controller. Reviewed-by: Rob Herring Signed-off-by: Naga Sureshkumar Relli Signed-off-by: Mark Brown --- .../devicetree/bindings/spi/spi-zynq-qspi.txt | 25 ++++++++++++++++++++++ 1 file changed, 25 insertions(+) create mode 100644 Documentation/devicetree/bindings/spi/spi-zynq-qspi.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/spi/spi-zynq-qspi.txt b/Documentation/devicetree/bindings/spi/spi-zynq-qspi.txt new file mode 100644 index 000000000000..16b734ad3102 --- /dev/null +++ b/Documentation/devicetree/bindings/spi/spi-zynq-qspi.txt @@ -0,0 +1,25 @@ +Xilinx Zynq QSPI controller Device Tree Bindings +------------------------------------------------------------------- + +Required properties: +- compatible : Should be "xlnx,zynq-qspi-1.0". +- reg : Physical base address and size of QSPI registers map. +- interrupts : Property with a value describing the interrupt + number. +- clock-names : List of input clock names - "ref_clk", "pclk" + (See clock bindings for details). +- clocks : Clock phandles (see clock bindings for details). + +Optional properties: +- num-cs : Number of chip selects used. + +Example: + qspi: spi@e000d000 { + compatible = "xlnx,zynq-qspi-1.0"; + reg = <0xe000d000 0x1000>; + interrupt-parent = <&intc>; + interrupts = <0 19 4>; + clock-names = "ref_clk", "pclk"; + clocks = <&clkc 10>, <&clkc 43>; + num-cs = <1>; + }; -- cgit v1.2.3 From 077d9951f7c9ef5845fdcf4363d3a4630d142e4f Mon Sep 17 00:00:00 2001 From: Martin Schiller Date: Fri, 8 Mar 2019 08:49:30 +0100 Subject: power: reset: syscon-reboot: add a mask property Make the syscon-reboot driver accept value and mask instead of just value. Prior to this patch, the property name for the value was 'mask'. If only the mask property is defined on a node, maintain compatibility by using it as the value. This patch is based on commit f2c199db477e ("power: reset: syscon-poweroff: add a mask property") and does the same change for the syscon-reboot driver. Signed-off-by: Martin Schiller Acked-by: Rob Herring Signed-off-by: Sebastian Reichel --- .../devicetree/bindings/power/reset/syscon-reboot.txt | 11 +++++++++-- drivers/power/reset/syscon-reboot.c | 19 +++++++++++++++++-- 2 files changed, 26 insertions(+), 4 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/power/reset/syscon-reboot.txt b/Documentation/devicetree/bindings/power/reset/syscon-reboot.txt index 11906316b43d..e23dea8344f8 100644 --- a/Documentation/devicetree/bindings/power/reset/syscon-reboot.txt +++ b/Documentation/devicetree/bindings/power/reset/syscon-reboot.txt @@ -3,13 +3,20 @@ Generic SYSCON mapped register reset driver This is a generic reset driver using syscon to map the reset register. The reset is generally performed with a write to the reset register defined by the register map pointed by syscon reference plus the offset -with the mask defined in the reboot node. +with the value and mask defined in the reboot node. Required properties: - compatible: should contain "syscon-reboot" - regmap: this is phandle to the register map node - offset: offset in the register map for the reboot register (in bytes) -- mask: the reset value written to the reboot register (32 bit access) +- value: the reset value written to the reboot register (32 bit access) + +Optional properties: +- mask: update only the register bits defined by the mask (32 bit) + +Legacy usage: +If a node doesn't contain a value property but contains a mask property, the +mask property is used as the value. Default will be little endian mode, 32 bit access only. diff --git a/drivers/power/reset/syscon-reboot.c b/drivers/power/reset/syscon-reboot.c index 7d0d269a0837..5a6bb638c331 100644 --- a/drivers/power/reset/syscon-reboot.c +++ b/drivers/power/reset/syscon-reboot.c @@ -27,6 +27,7 @@ struct syscon_reboot_context { struct regmap *map; u32 offset; + u32 value; u32 mask; struct notifier_block restart_handler; }; @@ -39,7 +40,7 @@ static int syscon_restart_handle(struct notifier_block *this, restart_handler); /* Issue the reboot */ - regmap_write(ctx->map, ctx->offset, ctx->mask); + regmap_update_bits(ctx->map, ctx->offset, ctx->mask, ctx->value); mdelay(1000); @@ -51,6 +52,7 @@ static int syscon_reboot_probe(struct platform_device *pdev) { struct syscon_reboot_context *ctx; struct device *dev = &pdev->dev; + int mask_err, value_err; int err; ctx = devm_kzalloc(&pdev->dev, sizeof(*ctx), GFP_KERNEL); @@ -64,8 +66,21 @@ static int syscon_reboot_probe(struct platform_device *pdev) if (of_property_read_u32(pdev->dev.of_node, "offset", &ctx->offset)) return -EINVAL; - if (of_property_read_u32(pdev->dev.of_node, "mask", &ctx->mask)) + value_err = of_property_read_u32(pdev->dev.of_node, "value", &ctx->value); + mask_err = of_property_read_u32(pdev->dev.of_node, "mask", &ctx->mask); + if (value_err && mask_err) { + dev_err(dev, "unable to read 'value' and 'mask'"); return -EINVAL; + } + + if (value_err) { + /* support old binding */ + ctx->value = ctx->mask; + ctx->mask = 0xFFFFFFFF; + } else if (mask_err) { + /* support value without mask*/ + ctx->mask = 0xFFFFFFFF; + } ctx->restart_handler.notifier_call = syscon_restart_handle; ctx->restart_handler.priority = 192; -- cgit v1.2.3 From ce8873c77c840977722deb73d7649653a4fcf31a Mon Sep 17 00:00:00 2001 From: Sebastien Bourdelin Date: Thu, 28 Mar 2019 16:35:18 -0400 Subject: dt-bindings: power: supply: gpio-charger: add missing semi-colon in example Fix the example documentation which is missing a semi-colon. Signed-off-by: Sebastien Bourdelin Signed-off-by: Sebastian Reichel --- Documentation/devicetree/bindings/power/supply/gpio-charger.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/power/supply/gpio-charger.txt b/Documentation/devicetree/bindings/power/supply/gpio-charger.txt index adbb5dc5b6e9..ddf7b7b971e1 100644 --- a/Documentation/devicetree/bindings/power/supply/gpio-charger.txt +++ b/Documentation/devicetree/bindings/power/supply/gpio-charger.txt @@ -20,7 +20,7 @@ Example: compatible = "gpio-charger"; charger-type = "usb-sdp"; gpios = <&gpf0 2 0 0 0>; - } + }; battery { power-supplies = <&usb_charger>; -- cgit v1.2.3 From ec4628effbb7cf1f5241b41936540d986715f3bb Mon Sep 17 00:00:00 2001 From: Claudiu Beznea Date: Thu, 21 Feb 2019 13:45:56 +0000 Subject: dt-bindings: arm: atmel: add binding for SAM9X60 shutdown controller Add documentation for SAM9X60 shutdown controller. Signed-off-by: Claudiu Beznea Acked-by: Nicolas Ferre Reviewed-by: Rob Herring Signed-off-by: Sebastian Reichel --- Documentation/devicetree/bindings/arm/atmel-sysregs.txt | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/atmel-sysregs.txt b/Documentation/devicetree/bindings/arm/atmel-sysregs.txt index e61d00e25b95..9fbde401a090 100644 --- a/Documentation/devicetree/bindings/arm/atmel-sysregs.txt +++ b/Documentation/devicetree/bindings/arm/atmel-sysregs.txt @@ -84,7 +84,7 @@ SHDWC SAMA5D2-Compatible Shutdown Controller 1) shdwc node required properties: -- compatible: should be "atmel,sama5d2-shdwc". +- compatible: should be "atmel,sama5d2-shdwc" or "microchip,sam9x60-shdwc". - reg: should contain registers location and length - clocks: phandle to input clock. - #address-cells: should be one. The cell is the wake-up input index. @@ -96,6 +96,9 @@ optional properties: microseconds. It's usually a board-related property. - atmel,wakeup-rtc-timer: boolean to enable Real-Time Clock wake-up. +optional microchip,sam9x60-shdwc properties: +- atmel,wakeup-rtt-timer: boolean to enable Real-time Timer Wake-up. + The node contains child nodes for each wake-up input that the platform uses. 2) input nodes -- cgit v1.2.3 From 1d960858bed2d975717703ccce0f3d0b736de813 Mon Sep 17 00:00:00 2001 From: Colin Ian King Date: Thu, 4 Apr 2019 12:16:57 +0100 Subject: Documentation: bus: ti-sysc: fix spelling mistakes "multipe" and "interconnet" There is are a couple of spelling mistakes in the Documentation. Fix them. Signed-off-by: Colin Ian King Reviewed-by: Mukesh Ojha Signed-off-by: Tony Lindgren --- Documentation/devicetree/bindings/bus/ti-sysc.txt | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/bus/ti-sysc.txt b/Documentation/devicetree/bindings/bus/ti-sysc.txt index f200f45572ae..233eb8294204 100644 --- a/Documentation/devicetree/bindings/bus/ti-sysc.txt +++ b/Documentation/devicetree/bindings/bus/ti-sysc.txt @@ -133,6 +133,6 @@ using offsets from l4_cfg second segment (0x4a000000 + 0x80000 = 0x4a0ab000): }; }; -Note that other SoCs, such as am335x can have multipe child devices. On am335x +Note that other SoCs, such as am335x can have multiple child devices. On am335x there are two MUSB instances, two USB PHY instances, and a single CPPI41 DMA -instance as children of a single interconnet target module. +instance as children of a single interconnect target module. -- cgit v1.2.3 From 72deb455b5ec619ff043c30bc90025aa3de3cdda Mon Sep 17 00:00:00 2001 From: Christoph Hellwig Date: Fri, 5 Apr 2019 18:08:59 +0200 Subject: block: remove CONFIG_LBDAF Currently support for 64-bit sector_t and blkcnt_t is optional on 32-bit architectures. These types are required to support block device and/or file sizes larger than 2 TiB, and have generally defaulted to on for a long time. Enabling the option only increases the i386 tinyconfig size by 145 bytes, and many data structures already always use 64-bit values for their in-core and on-disk data structures anyway, so there should not be a large change in dynamic memory usage either. Dropping this option removes a somewhat weird non-default config that has cause various bugs or compiler warnings when actually used. Signed-off-by: Christoph Hellwig Signed-off-by: Jens Axboe --- Documentation/process/submit-checklist.rst | 27 ++++++++---------- Documentation/translations/ja_JP/SubmitChecklist | 22 ++++++--------- arch/arc/configs/haps_hs_defconfig | 1 - arch/arc/configs/haps_hs_smp_defconfig | 1 - arch/arc/configs/nsim_700_defconfig | 1 - arch/arc/configs/nsim_hs_defconfig | 1 - arch/arc/configs/nsim_hs_smp_defconfig | 1 - arch/arc/configs/nsimosci_defconfig | 1 - arch/arc/configs/nsimosci_hs_defconfig | 1 - arch/arc/configs/nsimosci_hs_smp_defconfig | 1 - arch/arm/configs/aspeed_g4_defconfig | 1 - arch/arm/configs/aspeed_g5_defconfig | 1 - arch/arm/configs/at91_dt_defconfig | 1 - arch/arm/configs/clps711x_defconfig | 1 - arch/arm/configs/efm32_defconfig | 1 - arch/arm/configs/ezx_defconfig | 1 - arch/arm/configs/h3600_defconfig | 1 - arch/arm/configs/imote2_defconfig | 1 - arch/arm/configs/moxart_defconfig | 1 - arch/arm/configs/multi_v4t_defconfig | 1 - arch/arm/configs/omap1_defconfig | 1 - arch/arm/configs/stm32_defconfig | 1 - arch/arm/configs/u300_defconfig | 1 - arch/arm/configs/vexpress_defconfig | 1 - arch/m68k/configs/amcore_defconfig | 1 - arch/m68k/configs/m5475evb_defconfig | 1 - arch/m68k/configs/stmark2_defconfig | 1 - arch/mips/configs/ar7_defconfig | 1 - arch/mips/configs/decstation_defconfig | 1 - arch/mips/configs/decstation_r4k_defconfig | 1 - arch/mips/configs/loongson1b_defconfig | 1 - arch/mips/configs/loongson1c_defconfig | 1 - arch/mips/configs/rb532_defconfig | 1 - arch/mips/configs/rbtx49xx_defconfig | 1 - arch/parisc/configs/generic-32bit_defconfig | 1 - arch/sh/configs/apsh4ad0a_defconfig | 1 - arch/sh/configs/ecovec24-romimage_defconfig | 1 - arch/sh/configs/rsk7264_defconfig | 1 - arch/sh/configs/rsk7269_defconfig | 1 - arch/sh/configs/sh7785lcr_32bit_defconfig | 1 - block/Kconfig | 24 ---------------- drivers/block/drbd/drbd_int.h | 5 ---- drivers/block/ps3disk.c | 4 +-- drivers/md/dm-exception-store.h | 28 ++----------------- drivers/md/dm-integrity.c | 8 ++---- drivers/md/md.c | 6 ++-- drivers/nvdimm/pfn_devs.c | 4 +-- drivers/scsi/sd.c | 32 ---------------------- fs/ext4/resize.c | 2 -- fs/ext4/super.c | 32 +++++----------------- fs/gfs2/Kconfig | 1 - fs/nfs/Kconfig | 1 - fs/ocfs2/super.c | 10 ------- fs/stack.c | 15 +++++----- fs/xfs/Kconfig | 1 - fs/xfs/xfs_super.c | 10 +------ include/linux/genhd.h | 8 +++--- include/linux/kernel.h | 14 ++-------- include/linux/types.h | 5 ---- lib/Kconfig.debug | 1 - .../formal/srcu-cbmc/include/linux/types.h | 4 --- 61 files changed, 52 insertions(+), 250 deletions(-) (limited to 'Documentation') diff --git a/Documentation/process/submit-checklist.rst b/Documentation/process/submit-checklist.rst index 367353c54949..c88867b173d9 100644 --- a/Documentation/process/submit-checklist.rst +++ b/Documentation/process/submit-checklist.rst @@ -72,47 +72,44 @@ and elsewhere regarding submitting Linux kernel patches. 13) Has been build- and runtime tested with and without ``CONFIG_SMP`` and ``CONFIG_PREEMPT.`` -14) If the patch affects IO/Disk, etc: has been tested with and without - ``CONFIG_LBDAF.`` +16) All codepaths have been exercised with all lockdep features enabled. -15) All codepaths have been exercised with all lockdep features enabled. +17) All new ``/proc`` entries are documented under ``Documentation/`` -16) All new ``/proc`` entries are documented under ``Documentation/`` - -17) All new kernel boot parameters are documented in +18) All new kernel boot parameters are documented in ``Documentation/admin-guide/kernel-parameters.rst``. -18) All new module parameters are documented with ``MODULE_PARM_DESC()`` +19) All new module parameters are documented with ``MODULE_PARM_DESC()`` -19) All new userspace interfaces are documented in ``Documentation/ABI/``. +20) All new userspace interfaces are documented in ``Documentation/ABI/``. See ``Documentation/ABI/README`` for more information. Patches that change userspace interfaces should be CCed to linux-api@vger.kernel.org. -20) Check that it all passes ``make headers_check``. +21) Check that it all passes ``make headers_check``. -21) Has been checked with injection of at least slab and page-allocation +22) Has been checked with injection of at least slab and page-allocation failures. See ``Documentation/fault-injection/``. If the new code is substantial, addition of subsystem-specific fault injection might be appropriate. -22) Newly-added code has been compiled with ``gcc -W`` (use +23) Newly-added code has been compiled with ``gcc -W`` (use ``make EXTRA_CFLAGS=-W``). This will generate lots of noise, but is good for finding bugs like "warning: comparison between signed and unsigned". -23) Tested after it has been merged into the -mm patchset to make sure +24) Tested after it has been merged into the -mm patchset to make sure that it still works with all of the other queued patches and various changes in the VM, VFS, and other subsystems. -24) All memory barriers {e.g., ``barrier()``, ``rmb()``, ``wmb()``} need a +25) All memory barriers {e.g., ``barrier()``, ``rmb()``, ``wmb()``} need a comment in the source code that explains the logic of what they are doing and why. -25) If any ioctl's are added by the patch, then also update +26) If any ioctl's are added by the patch, then also update ``Documentation/ioctl/ioctl-number.txt``. -26) If your modified source code depends on or uses any of the kernel +27) If your modified source code depends on or uses any of the kernel APIs or features that are related to the following ``Kconfig`` symbols, then test multiple builds with the related ``Kconfig`` symbols disabled and/or ``=m`` (if that option is available) [not all of these at the diff --git a/Documentation/translations/ja_JP/SubmitChecklist b/Documentation/translations/ja_JP/SubmitChecklist index 60c7c35ac517..b42220d3d46c 100644 --- a/Documentation/translations/ja_JP/SubmitChecklist +++ b/Documentation/translations/ja_JP/SubmitChecklist @@ -74,38 +74,34 @@ Linux カーネルパッチ投稿者向けチェックリスト 13: CONFIG_SMP, CONFIG_PREEMPT を有効にした場合と無効にした場合の両方で ビルドした上、動作確認を行ってください。 -14: もしパッチがディスクのI/O性能などに影響を与えるようであれば、 - 'CONFIG_LBDAF'オプションを有効にした場合と無効にした場合の両方で - テストを実施してみてください。 +14: lockdepの機能を全て有効にした上で、全てのコードパスを評価してください。 -15: lockdepの機能を全て有効にした上で、全てのコードパスを評価してください。 - -16: /proc に新しいエントリを追加した場合には、Documentation/ 配下に +15: /proc に新しいエントリを追加した場合には、Documentation/ 配下に 必ずドキュメントを追加してください。 -17: 新しいブートパラメータを追加した場合には、 +16: 新しいブートパラメータを追加した場合には、 必ずDocumentation/admin-guide/kernel-parameters.rst に説明を追加してください。 -18: 新しくmoduleにパラメータを追加した場合には、MODULE_PARM_DESC()を +17: 新しくmoduleにパラメータを追加した場合には、MODULE_PARM_DESC()を 利用して必ずその説明を記述してください。 -19: 新しいuserspaceインタフェースを作成した場合には、Documentation/ABI/ に +18: 新しいuserspaceインタフェースを作成した場合には、Documentation/ABI/ に Documentation/ABI/README を参考にして必ずドキュメントを追加してください。 -20: 'make headers_check'を実行して全く問題がないことを確認してください。 +19: 'make headers_check'を実行して全く問題がないことを確認してください。 -21: 少なくともslabアロケーションとpageアロケーションに失敗した場合の +20: 少なくともslabアロケーションとpageアロケーションに失敗した場合の 挙動について、fault-injectionを利用して確認してください。 Documentation/fault-injection/ を参照してください。 追加したコードがかなりの量であったならば、サブシステム特有の fault-injectionを追加したほうが良いかもしれません。 -22: 新たに追加したコードは、`gcc -W'でコンパイルしてください。 +21: 新たに追加したコードは、`gcc -W'でコンパイルしてください。 このオプションは大量の不要なメッセージを出力しますが、 "warning: comparison between signed and unsigned" のようなメッセージは、 バグを見つけるのに役に立ちます。 -23: 投稿したパッチが -mm パッチセットにマージされた後、全ての既存のパッチや +22: 投稿したパッチが -mm パッチセットにマージされた後、全ての既存のパッチや VM, VFS およびその他のサブシステムに関する様々な変更と、現時点でも共存 できることを確認するテストを行ってください。 diff --git a/arch/arc/configs/haps_hs_defconfig b/arch/arc/configs/haps_hs_defconfig index f56cc2070c11..b117e6c16d41 100644 --- a/arch/arc/configs/haps_hs_defconfig +++ b/arch/arc/configs/haps_hs_defconfig @@ -15,7 +15,6 @@ CONFIG_PERF_EVENTS=y # CONFIG_COMPAT_BRK is not set CONFIG_SLAB=y CONFIG_MODULES=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_IOSCHED_DEADLINE is not set # CONFIG_IOSCHED_CFQ is not set diff --git a/arch/arc/configs/haps_hs_smp_defconfig b/arch/arc/configs/haps_hs_smp_defconfig index b6f2482c7e74..33a787c375e2 100644 --- a/arch/arc/configs/haps_hs_smp_defconfig +++ b/arch/arc/configs/haps_hs_smp_defconfig @@ -17,7 +17,6 @@ CONFIG_PERF_EVENTS=y CONFIG_SLAB=y CONFIG_KPROBES=y CONFIG_MODULES=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_IOSCHED_DEADLINE is not set # CONFIG_IOSCHED_CFQ is not set diff --git a/arch/arc/configs/nsim_700_defconfig b/arch/arc/configs/nsim_700_defconfig index 318e4cd29629..de398c7b10b3 100644 --- a/arch/arc/configs/nsim_700_defconfig +++ b/arch/arc/configs/nsim_700_defconfig @@ -18,7 +18,6 @@ CONFIG_PERF_EVENTS=y CONFIG_ISA_ARCOMPACT=y CONFIG_KPROBES=y CONFIG_MODULES=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_IOSCHED_DEADLINE is not set # CONFIG_IOSCHED_CFQ is not set diff --git a/arch/arc/configs/nsim_hs_defconfig b/arch/arc/configs/nsim_hs_defconfig index c15807b0e0c1..2dbd34a9ff07 100644 --- a/arch/arc/configs/nsim_hs_defconfig +++ b/arch/arc/configs/nsim_hs_defconfig @@ -20,7 +20,6 @@ CONFIG_MODULES=y CONFIG_MODULE_FORCE_LOAD=y CONFIG_MODULE_UNLOAD=y CONFIG_MODULE_FORCE_UNLOAD=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_IOSCHED_DEADLINE is not set # CONFIG_IOSCHED_CFQ is not set diff --git a/arch/arc/configs/nsim_hs_smp_defconfig b/arch/arc/configs/nsim_hs_smp_defconfig index 65e983fd942b..c7135f1e2583 100644 --- a/arch/arc/configs/nsim_hs_smp_defconfig +++ b/arch/arc/configs/nsim_hs_smp_defconfig @@ -18,7 +18,6 @@ CONFIG_MODULES=y CONFIG_MODULE_FORCE_LOAD=y CONFIG_MODULE_UNLOAD=y CONFIG_MODULE_FORCE_UNLOAD=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_IOSCHED_DEADLINE is not set # CONFIG_IOSCHED_CFQ is not set diff --git a/arch/arc/configs/nsimosci_defconfig b/arch/arc/configs/nsimosci_defconfig index 08c5b99ac341..385a71d3c478 100644 --- a/arch/arc/configs/nsimosci_defconfig +++ b/arch/arc/configs/nsimosci_defconfig @@ -18,7 +18,6 @@ CONFIG_PERF_EVENTS=y CONFIG_ISA_ARCOMPACT=y CONFIG_KPROBES=y CONFIG_MODULES=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_IOSCHED_DEADLINE is not set # CONFIG_IOSCHED_CFQ is not set diff --git a/arch/arc/configs/nsimosci_hs_defconfig b/arch/arc/configs/nsimosci_hs_defconfig index 5b5e26d67955..248a2c3bdc12 100644 --- a/arch/arc/configs/nsimosci_hs_defconfig +++ b/arch/arc/configs/nsimosci_hs_defconfig @@ -17,7 +17,6 @@ CONFIG_PERF_EVENTS=y # CONFIG_COMPAT_BRK is not set CONFIG_KPROBES=y CONFIG_MODULES=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_IOSCHED_DEADLINE is not set # CONFIG_IOSCHED_CFQ is not set diff --git a/arch/arc/configs/nsimosci_hs_smp_defconfig b/arch/arc/configs/nsimosci_hs_smp_defconfig index 26af9b2f7fcb..1a4bc7b660fb 100644 --- a/arch/arc/configs/nsimosci_hs_smp_defconfig +++ b/arch/arc/configs/nsimosci_hs_smp_defconfig @@ -12,7 +12,6 @@ CONFIG_PERF_EVENTS=y # CONFIG_COMPAT_BRK is not set CONFIG_KPROBES=y CONFIG_MODULES=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_IOSCHED_DEADLINE is not set # CONFIG_IOSCHED_CFQ is not set diff --git a/arch/arm/configs/aspeed_g4_defconfig b/arch/arm/configs/aspeed_g4_defconfig index 1446262921b4..bdbade6af9c7 100644 --- a/arch/arm/configs/aspeed_g4_defconfig +++ b/arch/arm/configs/aspeed_g4_defconfig @@ -23,7 +23,6 @@ CONFIG_SLAB_FREELIST_RANDOM=y CONFIG_JUMP_LABEL=y CONFIG_STRICT_KERNEL_RWX=y CONFIG_GCC_PLUGINS=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_BLK_DEBUG_FS is not set # CONFIG_IOSCHED_DEADLINE is not set diff --git a/arch/arm/configs/aspeed_g5_defconfig b/arch/arm/configs/aspeed_g5_defconfig index 02fa3a41add5..4bde84eae4eb 100644 --- a/arch/arm/configs/aspeed_g5_defconfig +++ b/arch/arm/configs/aspeed_g5_defconfig @@ -23,7 +23,6 @@ CONFIG_SLAB_FREELIST_RANDOM=y CONFIG_JUMP_LABEL=y CONFIG_STRICT_KERNEL_RWX=y CONFIG_GCC_PLUGINS=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_BLK_DEBUG_FS is not set # CONFIG_IOSCHED_DEADLINE is not set diff --git a/arch/arm/configs/at91_dt_defconfig b/arch/arm/configs/at91_dt_defconfig index e4b1be66b3f5..b7752929975c 100644 --- a/arch/arm/configs/at91_dt_defconfig +++ b/arch/arm/configs/at91_dt_defconfig @@ -9,7 +9,6 @@ CONFIG_EMBEDDED=y CONFIG_SLAB=y CONFIG_MODULES=y CONFIG_MODULE_UNLOAD=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_IOSCHED_DEADLINE is not set # CONFIG_IOSCHED_CFQ is not set diff --git a/arch/arm/configs/clps711x_defconfig b/arch/arm/configs/clps711x_defconfig index fc105c9178cc..09ae750164e0 100644 --- a/arch/arm/configs/clps711x_defconfig +++ b/arch/arm/configs/clps711x_defconfig @@ -6,7 +6,6 @@ CONFIG_RD_LZMA=y CONFIG_EMBEDDED=y CONFIG_SLOB=y CONFIG_JUMP_LABEL=y -# CONFIG_LBDAF is not set CONFIG_PARTITION_ADVANCED=y # CONFIG_IOSCHED_CFQ is not set CONFIG_ARCH_CLPS711X=y diff --git a/arch/arm/configs/efm32_defconfig b/arch/arm/configs/efm32_defconfig index ee42158f41ec..10ea92513a69 100644 --- a/arch/arm/configs/efm32_defconfig +++ b/arch/arm/configs/efm32_defconfig @@ -11,7 +11,6 @@ CONFIG_CC_OPTIMIZE_FOR_SIZE=y CONFIG_EMBEDDED=y # CONFIG_VM_EVENT_COUNTERS is not set # CONFIG_SLUB_DEBUG is not set -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_IOSCHED_DEADLINE is not set # CONFIG_IOSCHED_CFQ is not set diff --git a/arch/arm/configs/ezx_defconfig b/arch/arm/configs/ezx_defconfig index 484e51fbd4a6..e3afca5bd9d6 100644 --- a/arch/arm/configs/ezx_defconfig +++ b/arch/arm/configs/ezx_defconfig @@ -13,7 +13,6 @@ CONFIG_MODULES=y CONFIG_MODULE_UNLOAD=y CONFIG_MODULE_FORCE_UNLOAD=y CONFIG_MODVERSIONS=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_IOSCHED_CFQ is not set CONFIG_ARCH_PXA=y diff --git a/arch/arm/configs/h3600_defconfig b/arch/arm/configs/h3600_defconfig index ebeca11faa48..175881b7da7c 100644 --- a/arch/arm/configs/h3600_defconfig +++ b/arch/arm/configs/h3600_defconfig @@ -4,7 +4,6 @@ CONFIG_HIGH_RES_TIMERS=y CONFIG_LOG_BUF_SHIFT=14 CONFIG_BLK_DEV_INITRD=y CONFIG_MODULES=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_IOSCHED_DEADLINE is not set # CONFIG_IOSCHED_CFQ is not set diff --git a/arch/arm/configs/imote2_defconfig b/arch/arm/configs/imote2_defconfig index f204017c26b9..9b779e13e05d 100644 --- a/arch/arm/configs/imote2_defconfig +++ b/arch/arm/configs/imote2_defconfig @@ -12,7 +12,6 @@ CONFIG_MODULES=y CONFIG_MODULE_UNLOAD=y CONFIG_MODULE_FORCE_UNLOAD=y CONFIG_MODVERSIONS=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_IOSCHED_CFQ is not set CONFIG_ARCH_PXA=y diff --git a/arch/arm/configs/moxart_defconfig b/arch/arm/configs/moxart_defconfig index 078228a19339..6a11669fa536 100644 --- a/arch/arm/configs/moxart_defconfig +++ b/arch/arm/configs/moxart_defconfig @@ -15,7 +15,6 @@ CONFIG_EMBEDDED=y # CONFIG_VM_EVENT_COUNTERS is not set # CONFIG_SLUB_DEBUG is not set # CONFIG_COMPAT_BRK is not set -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_IOSCHED_DEADLINE is not set CONFIG_ARCH_MULTI_V4=y diff --git a/arch/arm/configs/multi_v4t_defconfig b/arch/arm/configs/multi_v4t_defconfig index 9a6390c172d6..eeea0c41138b 100644 --- a/arch/arm/configs/multi_v4t_defconfig +++ b/arch/arm/configs/multi_v4t_defconfig @@ -5,7 +5,6 @@ CONFIG_BLK_DEV_INITRD=y CONFIG_EMBEDDED=y CONFIG_SLOB=y CONFIG_JUMP_LABEL=y -# CONFIG_LBDAF is not set CONFIG_PARTITION_ADVANCED=y # CONFIG_IOSCHED_CFQ is not set CONFIG_ARCH_MULTI_V4T=y diff --git a/arch/arm/configs/omap1_defconfig b/arch/arm/configs/omap1_defconfig index cfc00b0961ec..8448a7f407a4 100644 --- a/arch/arm/configs/omap1_defconfig +++ b/arch/arm/configs/omap1_defconfig @@ -17,7 +17,6 @@ CONFIG_OPROFILE=y CONFIG_MODULES=y CONFIG_MODULE_UNLOAD=y CONFIG_MODULE_FORCE_UNLOAD=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_IOSCHED_DEADLINE is not set # CONFIG_IOSCHED_CFQ is not set diff --git a/arch/arm/configs/stm32_defconfig b/arch/arm/configs/stm32_defconfig index 0258ba891376..152321d2893e 100644 --- a/arch/arm/configs/stm32_defconfig +++ b/arch/arm/configs/stm32_defconfig @@ -13,7 +13,6 @@ CONFIG_CC_OPTIMIZE_FOR_SIZE=y CONFIG_EMBEDDED=y # CONFIG_VM_EVENT_COUNTERS is not set # CONFIG_SLUB_DEBUG is not set -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_IOSCHED_DEADLINE is not set # CONFIG_IOSCHED_CFQ is not set diff --git a/arch/arm/configs/u300_defconfig b/arch/arm/configs/u300_defconfig index 36d77406e31b..831ba6a9ee8b 100644 --- a/arch/arm/configs/u300_defconfig +++ b/arch/arm/configs/u300_defconfig @@ -9,7 +9,6 @@ CONFIG_EXPERT=y # CONFIG_VM_EVENT_COUNTERS is not set CONFIG_MODULES=y CONFIG_MODULE_UNLOAD=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set CONFIG_PARTITION_ADVANCED=y # CONFIG_IOSCHED_CFQ is not set diff --git a/arch/arm/configs/vexpress_defconfig b/arch/arm/configs/vexpress_defconfig index 392ed3b3613c..484d77a7f589 100644 --- a/arch/arm/configs/vexpress_defconfig +++ b/arch/arm/configs/vexpress_defconfig @@ -14,7 +14,6 @@ CONFIG_PROFILING=y CONFIG_OPROFILE=y CONFIG_MODULES=y CONFIG_MODULE_UNLOAD=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_IOSCHED_DEADLINE is not set # CONFIG_IOSCHED_CFQ is not set diff --git a/arch/m68k/configs/amcore_defconfig b/arch/m68k/configs/amcore_defconfig index 0857cdbfde0c..d5e683dd885d 100644 --- a/arch/m68k/configs/amcore_defconfig +++ b/arch/m68k/configs/amcore_defconfig @@ -12,7 +12,6 @@ CONFIG_EMBEDDED=y # CONFIG_VM_EVENT_COUNTERS is not set # CONFIG_SLUB_DEBUG is not set # CONFIG_COMPAT_BRK is not set -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_IOSCHED_CFQ is not set # CONFIG_MMU is not set diff --git a/arch/m68k/configs/m5475evb_defconfig b/arch/m68k/configs/m5475evb_defconfig index 4f4ccd13c11b..434bd3750966 100644 --- a/arch/m68k/configs/m5475evb_defconfig +++ b/arch/m68k/configs/m5475evb_defconfig @@ -11,7 +11,6 @@ CONFIG_SYSCTL_SYSCALL=y # CONFIG_AIO is not set CONFIG_EMBEDDED=y CONFIG_MODULES=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_IOSCHED_DEADLINE is not set # CONFIG_IOSCHED_CFQ is not set diff --git a/arch/m68k/configs/stmark2_defconfig b/arch/m68k/configs/stmark2_defconfig index 69f23c7b0497..27fa9465d19d 100644 --- a/arch/m68k/configs/stmark2_defconfig +++ b/arch/m68k/configs/stmark2_defconfig @@ -17,7 +17,6 @@ CONFIG_CC_OPTIMIZE_FOR_SIZE=y CONFIG_EMBEDDED=y # CONFIG_VM_EVENT_COUNTERS is not set # CONFIG_COMPAT_BRK is not set -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set CONFIG_BLK_CMDLINE_PARSER=y # CONFIG_MMU is not set diff --git a/arch/mips/configs/ar7_defconfig b/arch/mips/configs/ar7_defconfig index 9fbfb6e5c7d2..c83fdf649327 100644 --- a/arch/mips/configs/ar7_defconfig +++ b/arch/mips/configs/ar7_defconfig @@ -18,7 +18,6 @@ CONFIG_KEXEC=y # CONFIG_SECCOMP is not set CONFIG_MODULES=y CONFIG_MODULE_UNLOAD=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set CONFIG_PARTITION_ADVANCED=y CONFIG_BSD_DISKLABEL=y diff --git a/arch/mips/configs/decstation_defconfig b/arch/mips/configs/decstation_defconfig index 0c86ed86266a..30a6eafdb1d0 100644 --- a/arch/mips/configs/decstation_defconfig +++ b/arch/mips/configs/decstation_defconfig @@ -17,7 +17,6 @@ CONFIG_TC=y CONFIG_MODULES=y CONFIG_MODULE_UNLOAD=y CONFIG_MODULE_SRCVERSION_ALL=y -# CONFIG_LBDAF is not set CONFIG_PARTITION_ADVANCED=y CONFIG_OSF_PARTITION=y # CONFIG_EFI_PARTITION is not set diff --git a/arch/mips/configs/decstation_r4k_defconfig b/arch/mips/configs/decstation_r4k_defconfig index 0e54ab2680ce..e2b58dbf4aa9 100644 --- a/arch/mips/configs/decstation_r4k_defconfig +++ b/arch/mips/configs/decstation_r4k_defconfig @@ -16,7 +16,6 @@ CONFIG_TC=y CONFIG_MODULES=y CONFIG_MODULE_UNLOAD=y CONFIG_MODULE_SRCVERSION_ALL=y -# CONFIG_LBDAF is not set CONFIG_PARTITION_ADVANCED=y CONFIG_OSF_PARTITION=y # CONFIG_EFI_PARTITION is not set diff --git a/arch/mips/configs/loongson1b_defconfig b/arch/mips/configs/loongson1b_defconfig index b064d68a5424..aa7e98c5f5fc 100644 --- a/arch/mips/configs/loongson1b_defconfig +++ b/arch/mips/configs/loongson1b_defconfig @@ -19,7 +19,6 @@ CONFIG_MACH_LOONGSON32=y CONFIG_MODULES=y CONFIG_MODULE_UNLOAD=y CONFIG_MODVERSIONS=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_CORE_DUMP_DEFAULT_ELF_HEADERS is not set CONFIG_NET=y diff --git a/arch/mips/configs/loongson1c_defconfig b/arch/mips/configs/loongson1c_defconfig index 5d76559b56cd..520e7ef35383 100644 --- a/arch/mips/configs/loongson1c_defconfig +++ b/arch/mips/configs/loongson1c_defconfig @@ -20,7 +20,6 @@ CONFIG_LOONGSON1_LS1C=y CONFIG_MODULES=y CONFIG_MODULE_UNLOAD=y CONFIG_MODVERSIONS=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_CORE_DUMP_DEFAULT_ELF_HEADERS is not set CONFIG_NET=y diff --git a/arch/mips/configs/rb532_defconfig b/arch/mips/configs/rb532_defconfig index 7befe05fd813..ed1038f62a2c 100644 --- a/arch/mips/configs/rb532_defconfig +++ b/arch/mips/configs/rb532_defconfig @@ -19,7 +19,6 @@ CONFIG_PCI=y # CONFIG_PCI_QUIRKS is not set CONFIG_MODULES=y CONFIG_MODULE_UNLOAD=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set CONFIG_PARTITION_ADVANCED=y CONFIG_MAC_PARTITION=y diff --git a/arch/mips/configs/rbtx49xx_defconfig b/arch/mips/configs/rbtx49xx_defconfig index 50a2c9ad583f..b0f0c5f9ad9d 100644 --- a/arch/mips/configs/rbtx49xx_defconfig +++ b/arch/mips/configs/rbtx49xx_defconfig @@ -17,7 +17,6 @@ CONFIG_TOSHIBA_RBTX4938_MPLEX_KEEP=y CONFIG_PCI=y CONFIG_MODULES=y CONFIG_MODULE_UNLOAD=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set CONFIG_NET=y CONFIG_PACKET=y diff --git a/arch/parisc/configs/generic-32bit_defconfig b/arch/parisc/configs/generic-32bit_defconfig index 37ae4b57c001..a8f9bbef0975 100644 --- a/arch/parisc/configs/generic-32bit_defconfig +++ b/arch/parisc/configs/generic-32bit_defconfig @@ -14,7 +14,6 @@ CONFIG_SLAB=y CONFIG_MODULES=y CONFIG_MODULE_UNLOAD=y CONFIG_MODULE_FORCE_UNLOAD=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set CONFIG_PA7100LC=y CONFIG_SMP=y diff --git a/arch/sh/configs/apsh4ad0a_defconfig b/arch/sh/configs/apsh4ad0a_defconfig index 825c641726c4..d0d9ebc7165b 100644 --- a/arch/sh/configs/apsh4ad0a_defconfig +++ b/arch/sh/configs/apsh4ad0a_defconfig @@ -19,7 +19,6 @@ CONFIG_SLAB=y CONFIG_PROFILING=y CONFIG_MODULES=y CONFIG_MODULE_UNLOAD=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set CONFIG_CFQ_GROUP_IOSCHED=y CONFIG_CPU_SUBTYPE_SH7786=y diff --git a/arch/sh/configs/ecovec24-romimage_defconfig b/arch/sh/configs/ecovec24-romimage_defconfig index 0c5dfccbfe37..bdb61d1d0127 100644 --- a/arch/sh/configs/ecovec24-romimage_defconfig +++ b/arch/sh/configs/ecovec24-romimage_defconfig @@ -7,7 +7,6 @@ CONFIG_LOG_BUF_SHIFT=14 CONFIG_BLK_DEV_INITRD=y # CONFIG_KALLSYMS is not set CONFIG_SLAB=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set CONFIG_CPU_SUBTYPE_SH7724=y CONFIG_MEMORY_SIZE=0x10000000 diff --git a/arch/sh/configs/rsk7264_defconfig b/arch/sh/configs/rsk7264_defconfig index 2b9b731fc86b..ad003ee469ea 100644 --- a/arch/sh/configs/rsk7264_defconfig +++ b/arch/sh/configs/rsk7264_defconfig @@ -16,7 +16,6 @@ CONFIG_PERF_COUNTERS=y CONFIG_SLAB=y CONFIG_MMAP_ALLOW_UNINITIALIZED=y CONFIG_PROFILING=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set CONFIG_PARTITION_ADVANCED=y # CONFIG_IOSCHED_DEADLINE is not set diff --git a/arch/sh/configs/rsk7269_defconfig b/arch/sh/configs/rsk7269_defconfig index d041f7bcb84c..27fc01d58cf8 100644 --- a/arch/sh/configs/rsk7269_defconfig +++ b/arch/sh/configs/rsk7269_defconfig @@ -3,7 +3,6 @@ CONFIG_CC_OPTIMIZE_FOR_SIZE=y CONFIG_EMBEDDED=y # CONFIG_VM_EVENT_COUNTERS is not set CONFIG_SLAB=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set # CONFIG_IOSCHED_DEADLINE is not set # CONFIG_IOSCHED_CFQ is not set diff --git a/arch/sh/configs/sh7785lcr_32bit_defconfig b/arch/sh/configs/sh7785lcr_32bit_defconfig index 2ddf5ca7094e..a89ccc15af23 100644 --- a/arch/sh/configs/sh7785lcr_32bit_defconfig +++ b/arch/sh/configs/sh7785lcr_32bit_defconfig @@ -11,7 +11,6 @@ CONFIG_PROFILING=y CONFIG_GCOV_KERNEL=y CONFIG_MODULES=y CONFIG_MODULE_UNLOAD=y -# CONFIG_LBDAF is not set # CONFIG_BLK_DEV_BSG is not set CONFIG_CPU_SUBTYPE_SH7785=y CONFIG_MEMORY_START=0x40000000 diff --git a/block/Kconfig b/block/Kconfig index 028bc085dac8..1b220101a9cb 100644 --- a/block/Kconfig +++ b/block/Kconfig @@ -26,30 +26,6 @@ menuconfig BLOCK if BLOCK -config LBDAF - bool "Support for large (2TB+) block devices and files" - depends on !64BIT - default y - help - Enable block devices or files of size 2TB and larger. - - This option is required to support the full capacity of large - (2TB+) block devices, including RAID, disk, Network Block Device, - Logical Volume Manager (LVM) and loopback. - - This option also enables support for single files larger than - 2TB. - - The ext4 filesystem requires that this feature be enabled in - order to support filesystems that have the huge_file feature - enabled. Otherwise, it will refuse to mount in the read-write - mode any filesystems that use the huge_file feature, which is - enabled by default by mke2fs.ext4. - - The GFS2 filesystem also requires this feature. - - If unsure, say Y. - config BLK_SCSI_REQUEST bool diff --git a/drivers/block/drbd/drbd_int.h b/drivers/block/drbd/drbd_int.h index 000a2f4c0e92..acd7af3630e9 100644 --- a/drivers/block/drbd/drbd_int.h +++ b/drivers/block/drbd/drbd_int.h @@ -1317,10 +1317,6 @@ struct bm_extent { #define DRBD_MAX_SECTORS_FIXED_BM \ ((MD_128MB_SECT - MD_32kB_SECT - MD_4kB_SECT) * (1LL<<(BM_EXT_SHIFT-9))) -#if !defined(CONFIG_LBDAF) && BITS_PER_LONG == 32 -#define DRBD_MAX_SECTORS DRBD_MAX_SECTORS_32 -#define DRBD_MAX_SECTORS_FLEX DRBD_MAX_SECTORS_32 -#else #define DRBD_MAX_SECTORS DRBD_MAX_SECTORS_FIXED_BM /* 16 TB in units of sectors */ #if BITS_PER_LONG == 32 @@ -1333,7 +1329,6 @@ struct bm_extent { #define DRBD_MAX_SECTORS_FLEX (1UL << 51) /* corresponds to (1UL << 38) bits right now. */ #endif -#endif /* Estimate max bio size as 256 * PAGE_SIZE, * so for typical PAGE_SIZE of 4k, that is (1<<20) Byte. diff --git a/drivers/block/ps3disk.c b/drivers/block/ps3disk.c index 4e1d9b31f60c..cc61c5ce3ad5 100644 --- a/drivers/block/ps3disk.c +++ b/drivers/block/ps3disk.c @@ -102,7 +102,7 @@ static void ps3disk_scatter_gather(struct ps3_storage_device *dev, rq_for_each_segment(bvec, req, iter) { unsigned long flags; - dev_dbg(&dev->sbd.core, "%s:%u: bio %u: %u sectors from %lu\n", + dev_dbg(&dev->sbd.core, "%s:%u: bio %u: %u sectors from %llu\n", __func__, __LINE__, i, bio_sectors(iter.bio), iter.bio->bi_iter.bi_sector); @@ -496,7 +496,7 @@ static int ps3disk_probe(struct ps3_system_bus_device *_dev) dev->regions[dev->region_idx].size*priv->blocking_factor); dev_info(&dev->sbd.core, - "%s is a %s (%llu MiB total, %lu MiB for OtherOS)\n", + "%s is a %s (%llu MiB total, %llu MiB for OtherOS)\n", gendisk->disk_name, priv->model, priv->raw_capacity >> 11, get_capacity(gendisk) >> 11); diff --git a/drivers/md/dm-exception-store.h b/drivers/md/dm-exception-store.h index 12b5216c2cfe..721efc493942 100644 --- a/drivers/md/dm-exception-store.h +++ b/drivers/md/dm-exception-store.h @@ -135,9 +135,8 @@ struct dm_dev *dm_snap_cow(struct dm_snapshot *snap); /* * Funtions to manipulate consecutive chunks */ -# if defined(CONFIG_LBDAF) || (BITS_PER_LONG == 64) -# define DM_CHUNK_CONSECUTIVE_BITS 8 -# define DM_CHUNK_NUMBER_BITS 56 +#define DM_CHUNK_CONSECUTIVE_BITS 8 +#define DM_CHUNK_NUMBER_BITS 56 static inline chunk_t dm_chunk_number(chunk_t chunk) { @@ -163,29 +162,6 @@ static inline void dm_consecutive_chunk_count_dec(struct dm_exception *e) e->new_chunk -= (1ULL << DM_CHUNK_NUMBER_BITS); } -# else -# define DM_CHUNK_CONSECUTIVE_BITS 0 - -static inline chunk_t dm_chunk_number(chunk_t chunk) -{ - return chunk; -} - -static inline unsigned dm_consecutive_chunk_count(struct dm_exception *e) -{ - return 0; -} - -static inline void dm_consecutive_chunk_count_inc(struct dm_exception *e) -{ -} - -static inline void dm_consecutive_chunk_count_dec(struct dm_exception *e) -{ -} - -# endif - /* * Return the number of sectors in the device. */ diff --git a/drivers/md/dm-integrity.c b/drivers/md/dm-integrity.c index d57d997a52c8..0eb56ba89a7f 100644 --- a/drivers/md/dm-integrity.c +++ b/drivers/md/dm-integrity.c @@ -88,14 +88,10 @@ struct journal_entry { #if BITS_PER_LONG == 64 #define journal_entry_set_sector(je, x) do { smp_wmb(); WRITE_ONCE((je)->u.sector, cpu_to_le64(x)); } while (0) -#define journal_entry_get_sector(je) le64_to_cpu((je)->u.sector) -#elif defined(CONFIG_LBDAF) -#define journal_entry_set_sector(je, x) do { (je)->u.s.sector_lo = cpu_to_le32(x); smp_wmb(); WRITE_ONCE((je)->u.s.sector_hi, cpu_to_le32((x) >> 32)); } while (0) -#define journal_entry_get_sector(je) le64_to_cpu((je)->u.sector) #else -#define journal_entry_set_sector(je, x) do { (je)->u.s.sector_lo = cpu_to_le32(x); smp_wmb(); WRITE_ONCE((je)->u.s.sector_hi, cpu_to_le32(0)); } while (0) -#define journal_entry_get_sector(je) le32_to_cpu((je)->u.s.sector_lo) +#define journal_entry_set_sector(je, x) do { (je)->u.s.sector_lo = cpu_to_le32(x); smp_wmb(); WRITE_ONCE((je)->u.s.sector_hi, cpu_to_le32((x) >> 32)); } while (0) #endif +#define journal_entry_get_sector(je) le64_to_cpu((je)->u.sector) #define journal_entry_is_unused(je) ((je)->u.s.sector_hi == cpu_to_le32(-1)) #define journal_entry_set_unused(je) do { ((je)->u.s.sector_hi = cpu_to_le32(-1)); } while (0) #define journal_entry_is_inprogress(je) ((je)->u.s.sector_hi == cpu_to_le32(-2)) diff --git a/drivers/md/md.c b/drivers/md/md.c index d0f688399a56..1fa2682951f1 100644 --- a/drivers/md/md.c +++ b/drivers/md/md.c @@ -1106,8 +1106,7 @@ static int super_90_load(struct md_rdev *rdev, struct md_rdev *refdev, int minor * (not needed for Linear and RAID0 as metadata doesn't * record this size) */ - if (IS_ENABLED(CONFIG_LBDAF) && (u64)rdev->sectors >= (2ULL << 32) && - sb->level >= 1) + if ((u64)rdev->sectors >= (2ULL << 32) && sb->level >= 1) rdev->sectors = (sector_t)(2ULL << 32) - 2; if (rdev->sectors < ((sector_t)sb->size) * 2 && sb->level >= 1) @@ -1405,8 +1404,7 @@ super_90_rdev_size_change(struct md_rdev *rdev, sector_t num_sectors) /* Limit to 4TB as metadata cannot record more than that. * 4TB == 2^32 KB, or 2*2^32 sectors. */ - if (IS_ENABLED(CONFIG_LBDAF) && (u64)num_sectors >= (2ULL << 32) && - rdev->mddev->level >= 1) + if ((u64)num_sectors >= (2ULL << 32) && rdev->mddev->level >= 1) num_sectors = (sector_t)(2ULL << 32) - 2; do { md_super_write(rdev->mddev, rdev, rdev->sb_start, rdev->sb_size, diff --git a/drivers/nvdimm/pfn_devs.c b/drivers/nvdimm/pfn_devs.c index d271bd731af7..01f40672507f 100644 --- a/drivers/nvdimm/pfn_devs.c +++ b/drivers/nvdimm/pfn_devs.c @@ -391,7 +391,7 @@ static int nd_pfn_clear_memmap_errors(struct nd_pfn *nd_pfn) bb_present = badblocks_check(&nd_region->bb, meta_start, meta_num, &first_bad, &num_bad); if (bb_present) { - dev_dbg(&nd_pfn->dev, "meta: %x badblocks at %lx\n", + dev_dbg(&nd_pfn->dev, "meta: %x badblocks at %llx\n", num_bad, first_bad); nsoff = ALIGN_DOWN((nd_region->ndr_start + (first_bad << 9)) - nsio->res.start, @@ -410,7 +410,7 @@ static int nd_pfn_clear_memmap_errors(struct nd_pfn *nd_pfn) } if (rc) { dev_err(&nd_pfn->dev, - "error clearing %x badblocks at %lx\n", + "error clearing %x badblocks at %llx\n", num_bad, first_bad); return rc; } diff --git a/drivers/scsi/sd.c b/drivers/scsi/sd.c index 2b2bc4b49d78..92c34d93e051 100644 --- a/drivers/scsi/sd.c +++ b/drivers/scsi/sd.c @@ -2256,22 +2256,6 @@ static void read_capacity_error(struct scsi_disk *sdkp, struct scsi_device *sdp, #define READ_CAPACITY_RETRIES_ON_RESET 10 -/* - * Ensure that we don't overflow sector_t when CONFIG_LBDAF is not set - * and the reported logical block size is bigger than 512 bytes. Note - * that last_sector is a u64 and therefore logical_to_sectors() is not - * applicable. - */ -static bool sd_addressable_capacity(u64 lba, unsigned int sector_size) -{ - u64 last_sector = (lba + 1ULL) << (ilog2(sector_size) - 9); - - if (sizeof(sector_t) == 4 && last_sector > U32_MAX) - return false; - - return true; -} - static int read_capacity_16(struct scsi_disk *sdkp, struct scsi_device *sdp, unsigned char *buffer) { @@ -2337,14 +2321,6 @@ static int read_capacity_16(struct scsi_disk *sdkp, struct scsi_device *sdp, return -ENODEV; } - if (!sd_addressable_capacity(lba, sector_size)) { - sd_printk(KERN_ERR, sdkp, "Too big for this kernel. Use a " - "kernel compiled with support for large block " - "devices.\n"); - sdkp->capacity = 0; - return -EOVERFLOW; - } - /* Logical blocks per physical block exponent */ sdkp->physical_block_size = (1 << (buffer[13] & 0xf)) * sector_size; @@ -2426,14 +2402,6 @@ static int read_capacity_10(struct scsi_disk *sdkp, struct scsi_device *sdp, return sector_size; } - if (!sd_addressable_capacity(lba, sector_size)) { - sd_printk(KERN_ERR, sdkp, "Too big for this kernel. Use a " - "kernel compiled with support for large block " - "devices.\n"); - sdkp->capacity = 0; - return -EOVERFLOW; - } - sdkp->capacity = lba + 1; sdkp->physical_block_size = sector_size; return sector_size; diff --git a/fs/ext4/resize.c b/fs/ext4/resize.c index e7ae26e36c9c..38faf661e237 100644 --- a/fs/ext4/resize.c +++ b/fs/ext4/resize.c @@ -1760,8 +1760,6 @@ int ext4_group_extend(struct super_block *sb, struct ext4_super_block *es, ext4_msg(sb, KERN_ERR, "filesystem too large to resize to %llu blocks safely", n_blocks_count); - if (sizeof(sector_t) < 8) - ext4_warning(sb, "CONFIG_LBDAF not enabled"); return -EINVAL; } diff --git a/fs/ext4/super.c b/fs/ext4/super.c index 6ed4eb81e674..d10e9e724bdd 100644 --- a/fs/ext4/super.c +++ b/fs/ext4/super.c @@ -2706,13 +2706,9 @@ static loff_t ext4_max_size(int blkbits, int has_huge_files) loff_t res; loff_t upper_limit = MAX_LFS_FILESIZE; - /* small i_blocks in vfs inode? */ - if (!has_huge_files || sizeof(blkcnt_t) < sizeof(u64)) { - /* - * CONFIG_LBDAF is not enabled implies the inode - * i_block represent total blocks in 512 bytes - * 32 == size of vfs inode i_blocks * 8 - */ + BUILD_BUG_ON(sizeof(blkcnt_t) < sizeof(u64)); + + if (!has_huge_files) { upper_limit = (1LL << 32) - 1; /* total blocks in file system block size */ @@ -2753,11 +2749,11 @@ static loff_t ext4_max_bitmap_size(int bits, int has_huge_files) * number of 512-byte sectors of the file. */ - if (!has_huge_files || sizeof(blkcnt_t) < sizeof(u64)) { + if (!has_huge_files) { /* - * !has_huge_files or CONFIG_LBDAF not enabled implies that - * the inode i_block field represents total file blocks in - * 2^32 512-byte sectors == size of vfs inode i_blocks * 8 + * !has_huge_files or implies that the inode i_block field + * represents total file blocks in 2^32 512-byte sectors == + * size of vfs inode i_blocks * 8 */ upper_limit = (1LL << 32) - 1; @@ -2897,18 +2893,6 @@ static int ext4_feature_set_ok(struct super_block *sb, int readonly) ~EXT4_FEATURE_RO_COMPAT_SUPP)); return 0; } - /* - * Large file size enabled file system can only be mounted - * read-write on 32-bit systems if kernel is built with CONFIG_LBDAF - */ - if (ext4_has_feature_huge_file(sb)) { - if (sizeof(blkcnt_t) < sizeof(u64)) { - ext4_msg(sb, KERN_ERR, "Filesystem with huge files " - "cannot be mounted RDWR without " - "CONFIG_LBDAF"); - return 0; - } - } if (ext4_has_feature_bigalloc(sb) && !ext4_has_feature_extents(sb)) { ext4_msg(sb, KERN_ERR, "Can't support bigalloc feature without " @@ -4057,8 +4041,6 @@ static int ext4_fill_super(struct super_block *sb, void *data, int silent) if (err) { ext4_msg(sb, KERN_ERR, "filesystem" " too large to mount safely on this system"); - if (sizeof(sector_t) < 8) - ext4_msg(sb, KERN_WARNING, "CONFIG_LBDAF not enabled"); goto failed_mount; } diff --git a/fs/gfs2/Kconfig b/fs/gfs2/Kconfig index 3ed2b088dcfd..6a1e499543f5 100644 --- a/fs/gfs2/Kconfig +++ b/fs/gfs2/Kconfig @@ -1,6 +1,5 @@ config GFS2_FS tristate "GFS2 file system support" - depends on (64BIT || LBDAF) select FS_POSIX_ACL select CRC32 select LIBCRC32C diff --git a/fs/nfs/Kconfig b/fs/nfs/Kconfig index 5f93cfacb3d1..69d02cf8cf37 100644 --- a/fs/nfs/Kconfig +++ b/fs/nfs/Kconfig @@ -121,7 +121,6 @@ config PNFS_FILE_LAYOUT config PNFS_BLOCK tristate depends on NFS_V4_1 && BLK_DEV_DM - depends on 64BIT || LBDAF default NFS_V4 config PNFS_FLEXFILE_LAYOUT diff --git a/fs/ocfs2/super.c b/fs/ocfs2/super.c index 96ae7cedd487..fc3d29eceb2f 100644 --- a/fs/ocfs2/super.c +++ b/fs/ocfs2/super.c @@ -600,7 +600,6 @@ static unsigned long long ocfs2_max_file_offset(unsigned int bbits, */ #if BITS_PER_LONG == 32 -# if defined(CONFIG_LBDAF) BUILD_BUG_ON(sizeof(sector_t) != 8); /* * We might be limited by page cache size. @@ -614,15 +613,6 @@ static unsigned long long ocfs2_max_file_offset(unsigned int bbits, */ bitshift = 31; } -# else - /* - * We are limited by the size of sector_t. Use block size, as - * that's what we expose to the VFS. - */ - bytes = 1 << bbits; - trim = 1; - bitshift = 31; -# endif #endif /* diff --git a/fs/stack.c b/fs/stack.c index a54e33ed10f1..664ed35558bd 100644 --- a/fs/stack.c +++ b/fs/stack.c @@ -21,11 +21,10 @@ void fsstack_copy_inode_size(struct inode *dst, struct inode *src) i_size = i_size_read(src); /* - * But if CONFIG_LBDAF (on 32-bit), we ought to make an effort to - * keep the two halves of i_blocks in sync despite SMP or PREEMPT - - * though stat's generic_fillattr() doesn't bother, and we won't be - * applying quotas (where i_blocks does become important) at the - * upper level. + * But on 32-bit, we ought to make an effort to keep the two halves of + * i_blocks in sync despite SMP or PREEMPT - though stat's + * generic_fillattr() doesn't bother, and we won't be applying quotas + * (where i_blocks does become important) at the upper level. * * We don't actually know what locking is used at the lower level; * but if it's a filesystem that supports quotas, it will be using @@ -44,9 +43,9 @@ void fsstack_copy_inode_size(struct inode *dst, struct inode *src) * include/linux/fs.h). We don't necessarily hold i_mutex when this * is called, so take i_lock for that case. * - * And if CONFIG_LBDAF (on 32-bit), continue our effort to keep the - * two halves of i_blocks in sync despite SMP or PREEMPT: use i_lock - * for that case too, and do both at once by combining the tests. + * And if on 32-bit, continue our effort to keep the two halves of + * i_blocks in sync despite SMP or PREEMPT: use i_lock for that case + * too, and do both at once by combining the tests. * * There is none of this locking overhead in the 64-bit case. */ diff --git a/fs/xfs/Kconfig b/fs/xfs/Kconfig index 457ac9f97377..99af5e5bda9f 100644 --- a/fs/xfs/Kconfig +++ b/fs/xfs/Kconfig @@ -1,7 +1,6 @@ config XFS_FS tristate "XFS filesystem support" depends on BLOCK - depends on (64BIT || LBDAF) select EXPORTFS select LIBCRC32C select FS_IOMAP diff --git a/fs/xfs/xfs_super.c b/fs/xfs/xfs_super.c index f093ea244849..703b6be063ef 100644 --- a/fs/xfs/xfs_super.c +++ b/fs/xfs/xfs_super.c @@ -539,26 +539,18 @@ xfs_max_file_offset( /* Figure out maximum filesize, on Linux this can depend on * the filesystem blocksize (on 32 bit platforms). - * __block_write_begin does this in an [unsigned] long... + * __block_write_begin does this in an [unsigned] long long... * page->index << (PAGE_SHIFT - bbits) * So, for page sized blocks (4K on 32 bit platforms), * this wraps at around 8Tb (hence MAX_LFS_FILESIZE which is * (((u64)PAGE_SIZE << (BITS_PER_LONG-1))-1) * but for smaller blocksizes it is less (bbits = log2 bsize). - * Note1: get_block_t takes a long (implicit cast from above) - * Note2: The Large Block Device (LBD and HAVE_SECTOR_T) patch - * can optionally convert the [unsigned] long from above into - * an [unsigned] long long. */ #if BITS_PER_LONG == 32 -# if defined(CONFIG_LBDAF) ASSERT(sizeof(sector_t) == 8); pagefactor = PAGE_SIZE; bitshift = BITS_PER_LONG; -# else - pagefactor = PAGE_SIZE >> (PAGE_SHIFT - blockshift); -# endif #endif return (((uint64_t)pagefactor) << bitshift) - 1; diff --git a/include/linux/genhd.h b/include/linux/genhd.h index 06c0fd594097..98076b1b5e48 100644 --- a/include/linux/genhd.h +++ b/include/linux/genhd.h @@ -714,7 +714,7 @@ static inline void hd_free_part(struct hd_struct *part) */ static inline sector_t part_nr_sects_read(struct hd_struct *part) { -#if BITS_PER_LONG==32 && defined(CONFIG_LBDAF) && defined(CONFIG_SMP) +#if BITS_PER_LONG==32 && defined(CONFIG_SMP) sector_t nr_sects; unsigned seq; do { @@ -722,7 +722,7 @@ static inline sector_t part_nr_sects_read(struct hd_struct *part) nr_sects = part->nr_sects; } while (read_seqcount_retry(&part->nr_sects_seq, seq)); return nr_sects; -#elif BITS_PER_LONG==32 && defined(CONFIG_LBDAF) && defined(CONFIG_PREEMPT) +#elif BITS_PER_LONG==32 && defined(CONFIG_PREEMPT) sector_t nr_sects; preempt_disable(); @@ -741,11 +741,11 @@ static inline sector_t part_nr_sects_read(struct hd_struct *part) */ static inline void part_nr_sects_write(struct hd_struct *part, sector_t size) { -#if BITS_PER_LONG==32 && defined(CONFIG_LBDAF) && defined(CONFIG_SMP) +#if BITS_PER_LONG==32 && defined(CONFIG_SMP) write_seqcount_begin(&part->nr_sects_seq); part->nr_sects = size; write_seqcount_end(&part->nr_sects_seq); -#elif BITS_PER_LONG==32 && defined(CONFIG_LBDAF) && defined(CONFIG_PREEMPT) +#elif BITS_PER_LONG==32 && defined(CONFIG_PREEMPT) preempt_disable(); part->nr_sects = size; preempt_enable(); diff --git a/include/linux/kernel.h b/include/linux/kernel.h index 34a5036debd3..24ef5a018a5e 100644 --- a/include/linux/kernel.h +++ b/include/linux/kernel.h @@ -17,6 +17,7 @@ #include #include #include +#include #define STACK_MAGIC 0xdeadbeef @@ -175,18 +176,7 @@ #define _RET_IP_ (unsigned long)__builtin_return_address(0) #define _THIS_IP_ ({ __label__ __here; __here: (unsigned long)&&__here; }) -#ifdef CONFIG_LBDAF -# define sector_div(a, b) do_div(a, b) -#else -# define sector_div(n, b)( \ -{ \ - int _res; \ - _res = (n) % (b); \ - (n) /= (b); \ - _res; \ -} \ -) -#endif +#define sector_div(a, b) do_div(a, b) /** * upper_32_bits - return bits 32-63 of a number diff --git a/include/linux/types.h b/include/linux/types.h index cc0dbbe551d5..231114ae38f4 100644 --- a/include/linux/types.h +++ b/include/linux/types.h @@ -127,13 +127,8 @@ typedef s64 int64_t; * * blkcnt_t is the type of the inode's block count. */ -#ifdef CONFIG_LBDAF typedef u64 sector_t; typedef u64 blkcnt_t; -#else -typedef unsigned long sector_t; -typedef unsigned long blkcnt_t; -#endif /* * The type of an index into the pagecache. diff --git a/lib/Kconfig.debug b/lib/Kconfig.debug index 0d9e81779e37..d8781786cf63 100644 --- a/lib/Kconfig.debug +++ b/lib/Kconfig.debug @@ -1927,7 +1927,6 @@ config TEST_STATIC_KEYS config TEST_KMOD tristate "kmod stress tester" depends on m - depends on BLOCK && (64BIT || LBDAF) # for XFS, BTRFS depends on NETDEVICES && NET_CORE && INET # for TUN select TEST_LKM select XFS_FS diff --git a/tools/testing/selftests/rcutorture/formal/srcu-cbmc/include/linux/types.h b/tools/testing/selftests/rcutorture/formal/srcu-cbmc/include/linux/types.h index d27285f8ee82..8bc960e5e713 100644 --- a/tools/testing/selftests/rcutorture/formal/srcu-cbmc/include/linux/types.h +++ b/tools/testing/selftests/rcutorture/formal/srcu-cbmc/include/linux/types.h @@ -59,11 +59,7 @@ typedef __u32 uint32_t; * * blkcnt_t is the type of the inode's block count. */ -#ifdef CONFIG_LBDAF typedef u64 sector_t; -#else -typedef unsigned long sector_t; -#endif /* * The type of an index into the pagecache. -- cgit v1.2.3 From 867934e9c9babe9192797726f6910554bbdc28ce Mon Sep 17 00:00:00 2001 From: Jerome Brunet Date: Thu, 4 Apr 2019 15:11:44 +0200 Subject: dt-bindings: net: phy: add g12a mdio mux documentation Add documentation for the device tree bindings of the MDIO mux of Amlogic g12a SoC family Reviewed-by: Rob Herring Signed-off-by: Jerome Brunet Signed-off-by: David S. Miller --- .../bindings/net/mdio-mux-meson-g12a.txt | 48 ++++++++++++++++++++++ 1 file changed, 48 insertions(+) create mode 100644 Documentation/devicetree/bindings/net/mdio-mux-meson-g12a.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/net/mdio-mux-meson-g12a.txt b/Documentation/devicetree/bindings/net/mdio-mux-meson-g12a.txt new file mode 100644 index 000000000000..3a96cbed9294 --- /dev/null +++ b/Documentation/devicetree/bindings/net/mdio-mux-meson-g12a.txt @@ -0,0 +1,48 @@ +Properties for the MDIO bus multiplexer/glue of Amlogic G12a SoC family. + +This is a special case of a MDIO bus multiplexer. It allows to choose between +the internal mdio bus leading to the embedded 10/100 PHY or the external +MDIO bus. + +Required properties in addition to the generic multiplexer properties: +- compatible : amlogic,g12a-mdio-mux +- reg: physical address and length of the multiplexer/glue registers +- clocks: list of clock phandle, one for each entry clock-names. +- clock-names: should contain the following: + * "pclk" : peripheral clock. + * "clkin0" : platform crytal + * "clkin1" : SoC 50MHz MPLL + +Example : + +mdio_mux: mdio-multiplexer@4c000 { + compatible = "amlogic,g12a-mdio-mux"; + reg = <0x0 0x4c000 0x0 0xa4>; + clocks = <&clkc CLKID_ETH_PHY>, + <&xtal>, + <&clkc CLKID_MPLL_5OM>; + clock-names = "pclk", "clkin0", "clkin1"; + mdio-parent-bus = <&mdio0>; + #address-cells = <1>; + #size-cells = <0>; + + ext_mdio: mdio@0 { + reg = <0>; + #address-cells = <1>; + #size-cells = <0>; + }; + + int_mdio: mdio@1 { + reg = <1>; + #address-cells = <1>; + #size-cells = <0>; + + internal_ephy: ethernet-phy@8 { + compatible = "ethernet-phy-id0180.3301", + "ethernet-phy-ieee802.3-c22"; + interrupts = ; + reg = <8>; + max-speed = <100>; + }; + }; +}; -- cgit v1.2.3 From 6ccc7435fab7cc4f158440b086105c263b62a36f Mon Sep 17 00:00:00 2001 From: Dan Murphy Date: Thu, 21 Mar 2019 09:28:35 -0500 Subject: dt: lm3532: Add lm3532 dt doc and update ti_lmu doc Add the lm3532 device tree documentation. Remove lm3532 device tree reference from the ti_lmu devicetree documentation. With the addition of the dedicated lm3532 documentation the device can be removed from the ti_lmu.txt. The reason for this is that the lm3532 dt documentation now defines the ability to control LED output strings against different control banks or groups multiple strings to be controlled by a single control bank. Another addition was for ALS lighting control and configuration. The LM3532 has a feature that can take in the ALS reading from 2 separate ALS devices and adjust the brightness on the strings that are configured to support this feature. Finally the device specific properties were moved to the parent node as these properties are not control bank configurable. These include the runtime ramp and the ALS configuration. Signed-off-by: Dan Murphy Reviewed-by: Rob Herring Acked-for-MFD-by: Lee Jones Acked-by: Tony Lindgren Signed-off-by: Jacek Anaszewski --- .../devicetree/bindings/leds/leds-lm3532.txt | 101 +++++++++++++++++++++ Documentation/devicetree/bindings/mfd/ti-lmu.txt | 20 ---- 2 files changed, 101 insertions(+), 20 deletions(-) create mode 100644 Documentation/devicetree/bindings/leds/leds-lm3532.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/leds/leds-lm3532.txt b/Documentation/devicetree/bindings/leds/leds-lm3532.txt new file mode 100644 index 000000000000..c087f85ddddc --- /dev/null +++ b/Documentation/devicetree/bindings/leds/leds-lm3532.txt @@ -0,0 +1,101 @@ +* Texas Instruments - lm3532 White LED driver with ambient light sensing +capability. + +The LM3532 provides the 3 high-voltage, low-side current sinks. The device is +programmable over an I2C-compatible interface and has independent +current control for all three channels. The adaptive current regulation +method allows for different LED currents in each current sink thus allowing +for a wide variety of backlight and keypad applications. + +The main features of the LM3532 include dual ambient light sensor inputs +each with 32 internal voltage setting resistors, 8-bit logarithmic and linear +brightness control, dual external PWM brightness control inputs, and up to +1000:1 dimming ratio with programmable fade in and fade out settings. + +Required properties: + - compatible : "ti,lm3532" + - reg : I2C slave address + - #address-cells : 1 + - #size-cells : 0 + +Optional properties: + - enable-gpios : gpio pin to enable (active high)/disable the device. + - ramp-up-us - The Run time ramp rates/step are from one current + set-point to another after the device has reached its + initial target set point from turn-on + - ramp-down-us - The Run time ramp rates/step are from one current + set-point to another after the device has reached its + initial target set point from turn-on + Range for ramp settings: 8us - 65536us + +Optional properties if ALS mode is used: + - ti,als-vmin - Minimum ALS voltage defined in Volts + - ti,als-vmax - Maximum ALS voltage defined in Volts + Per the data sheet the max ALS voltage is 2V and the min is 0V + + - ti,als1-imp-sel - ALS1 impedance resistor selection in Ohms + - ti,als2-imp-sel - ALS2 impedance resistor selection in Ohms + Range for impedance select: 37000 Ohms - 1190 Ohms + Values above 37kohms will be set to the "High Impedance" setting + + - ti,als-avrg-time-us - Determines the length of time the device needs to + average the two ALS inputs. This is only used if + the input mode is LM3532_ALS_INPUT_AVRG. + Range: 17920us - 2293760us + - ti,als-input-mode - Determines how the device uses the attached ALS + devices. + 0x00 - ALS1 and ALS2 input average + 0x01 - ALS1 Input + 0x02 - ALS2 Input + 0x03 - Max of ALS1 and ALS2 + +Required child properties: + - reg : Indicates control bank the LED string is controlled by + - led-sources : see Documentation/devicetree/bindings/leds/common.txt + - ti,led-mode : Defines if the LED strings are manually controlled or + if the LED strings are controlled by the ALS. + 0x00 - LED strings are I2C controlled via full scale + brightness control register + 0x01 - LED strings are ALS controlled + +Optional LED child properties: + - label : see Documentation/devicetree/bindings/leds/common.txt + - linux,default-trigger : + see Documentation/devicetree/bindings/leds/common.txt + +Example: +led-controller@38 { + compatible = "ti,lm3532"; + #address-cells = <1>; + #size-cells = <0>; + reg = <0x38>; + + enable-gpios = <&gpio6 12 GPIO_ACTIVE_HIGH>; + ramp-up-us = <1024>; + ramp-down-us = <65536>; + + ti,als-vmin = <0>; + ti,als-vmax = <2000>; + ti,als1-imp-sel = <4110>; + ti,als2-imp-sel = <2180>; + ti,als-avrg-time-us = <17920>; + ti,als-input-mode = <0x00>; + + led@0 { + reg = <0>; + led-sources = <2>; + ti,led-mode = <1>; + label = ":backlight"; + linux,default-trigger = "backlight"; + }; + + led@1 { + reg = <1>; + led-sources = <1>; + ti,led-mode = <0>; + label = ":kbd_backlight"; + }; +}; + +For more product information please see the links below: +http://www.ti.com/product/LM3532 diff --git a/Documentation/devicetree/bindings/mfd/ti-lmu.txt b/Documentation/devicetree/bindings/mfd/ti-lmu.txt index c885cf89b8ce..980394d701a7 100644 --- a/Documentation/devicetree/bindings/mfd/ti-lmu.txt +++ b/Documentation/devicetree/bindings/mfd/ti-lmu.txt @@ -4,7 +4,6 @@ TI LMU driver supports lighting devices below. Name Child nodes ------ --------------------------------- - LM3532 Backlight LM3631 Backlight and regulator LM3632 Backlight and regulator LM3633 Backlight, LED and fault monitor @@ -13,7 +12,6 @@ TI LMU driver supports lighting devices below. Required properties: - compatible: Should be one of: - "ti,lm3532" "ti,lm3631" "ti,lm3632" "ti,lm3633" @@ -23,7 +21,6 @@ Required properties: 0x11 for LM3632 0x29 for LM3631 0x36 for LM3633, LM3697 - 0x38 for LM3532 0x63 for LM3695 Optional property: @@ -47,23 +44,6 @@ Optional nodes: [2] ../leds/leds-lm3633.txt [3] ../regulator/lm363x-regulator.txt -lm3532@38 { - compatible = "ti,lm3532"; - reg = <0x38>; - - enable-gpios = <&pioC 2 GPIO_ACTIVE_HIGH>; - - backlight { - compatible = "ti,lm3532-backlight"; - - lcd { - led-sources = <0 1 2>; - ramp-up-msec = <30>; - ramp-down-msec = <0>; - }; - }; -}; - lm3631@29 { compatible = "ti,lm3631"; reg = <0x29>; -- cgit v1.2.3 From 5861381d486601430cccf64849bd0a226154bc0d Mon Sep 17 00:00:00 2001 From: "Rafael J. Wysocki" Date: Thu, 21 Mar 2019 23:18:01 +0100 Subject: PM / arch: x86: Rework the MSR_IA32_ENERGY_PERF_BIAS handling The current handling of MSR_IA32_ENERGY_PERF_BIAS in the kernel is problematic, because it may cause changes made by user space to that MSR (with the help of the x86_energy_perf_policy tool, for example) to be lost every time a CPU goes offline and then back online as well as during system-wide power management transitions into sleep states and back into the working state. The first problem is that if the current EPB value for a CPU going online is 0 ('performance'), the kernel will change it to 6 ('normal') regardless of whether or not this is the first bring-up of that CPU. That also happens during system-wide resume from sleep states (including, but not limited to, hibernation). However, the EPB may have been adjusted by user space this way and the kernel should not blindly override that setting. The second problem is that if the platform firmware resets the EPB values for any CPUs during system-wide resume from a sleep state, the kernel will not restore their previous EPB values that may have been set by user space before the preceding system-wide suspend transition. Again, that behavior may at least be confusing from the user space perspective. In order to address these issues, rework the handling of MSR_IA32_ENERGY_PERF_BIAS so that the EPB value is saved on CPU offline and restored on CPU online as well as (for the boot CPU) during the syscore stages of system-wide suspend and resume transitions, respectively. However, retain the policy by which the EPB is set to 6 ('normal') on the first bring-up of each CPU if its initial value is 0, based on the observation that 0 may mean 'not initialized' just as well as 'performance' in that case. While at it, move the MSR_IA32_ENERGY_PERF_BIAS handling code into a separate file and document it in Documentation/admin-guide. Fixes: abe48b108247 (x86, intel, power: Initialize MSR_IA32_ENERGY_PERF_BIAS) Fixes: b51ef52df71c (x86/cpu: Restore MSR_IA32_ENERGY_PERF_BIAS after resume) Reported-by: Thomas Renninger Signed-off-by: Rafael J. Wysocki Reviewed-by: Hannes Reinecke Acked-by: Borislav Petkov Acked-by: Thomas Gleixner --- Documentation/admin-guide/pm/intel_epb.rst | 6 ++ Documentation/admin-guide/pm/working-state.rst | 1 + arch/x86/kernel/cpu/Makefile | 2 +- arch/x86/kernel/cpu/common.c | 17 ---- arch/x86/kernel/cpu/cpu.h | 1 - arch/x86/kernel/cpu/intel.c | 34 ------- arch/x86/kernel/cpu/intel_epb.c | 131 +++++++++++++++++++++++++ include/linux/cpuhotplug.h | 1 + 8 files changed, 140 insertions(+), 53 deletions(-) create mode 100644 Documentation/admin-guide/pm/intel_epb.rst create mode 100644 arch/x86/kernel/cpu/intel_epb.c (limited to 'Documentation') diff --git a/Documentation/admin-guide/pm/intel_epb.rst b/Documentation/admin-guide/pm/intel_epb.rst new file mode 100644 index 000000000000..e9cfa7ec5420 --- /dev/null +++ b/Documentation/admin-guide/pm/intel_epb.rst @@ -0,0 +1,6 @@ +====================================== +Intel Performance and Energy Bias Hint +====================================== + +.. kernel-doc:: arch/x86/kernel/cpu/intel_epb.c + :doc: overview diff --git a/Documentation/admin-guide/pm/working-state.rst b/Documentation/admin-guide/pm/working-state.rst index b6cef9b5e961..beb004d3632b 100644 --- a/Documentation/admin-guide/pm/working-state.rst +++ b/Documentation/admin-guide/pm/working-state.rst @@ -8,3 +8,4 @@ Working-State Power Management cpuidle cpufreq intel_pstate + intel_epb diff --git a/arch/x86/kernel/cpu/Makefile b/arch/x86/kernel/cpu/Makefile index cfd24f9f7614..1796d2bdcaaa 100644 --- a/arch/x86/kernel/cpu/Makefile +++ b/arch/x86/kernel/cpu/Makefile @@ -28,7 +28,7 @@ obj-y += cpuid-deps.o obj-$(CONFIG_PROC_FS) += proc.o obj-$(CONFIG_X86_FEATURE_NAMES) += capflags.o powerflags.o -obj-$(CONFIG_CPU_SUP_INTEL) += intel.o intel_pconfig.o +obj-$(CONFIG_CPU_SUP_INTEL) += intel.o intel_pconfig.o intel_epb.o obj-$(CONFIG_CPU_SUP_AMD) += amd.o obj-$(CONFIG_CPU_SUP_HYGON) += hygon.o obj-$(CONFIG_CPU_SUP_CYRIX_32) += cyrix.o diff --git a/arch/x86/kernel/cpu/common.c b/arch/x86/kernel/cpu/common.c index cb28e98a0659..5e37dfa4d9df 100644 --- a/arch/x86/kernel/cpu/common.c +++ b/arch/x86/kernel/cpu/common.c @@ -1864,23 +1864,6 @@ void cpu_init(void) } #endif -static void bsp_resume(void) -{ - if (this_cpu->c_bsp_resume) - this_cpu->c_bsp_resume(&boot_cpu_data); -} - -static struct syscore_ops cpu_syscore_ops = { - .resume = bsp_resume, -}; - -static int __init init_cpu_syscore(void) -{ - register_syscore_ops(&cpu_syscore_ops); - return 0; -} -core_initcall(init_cpu_syscore); - /* * The microcode loader calls this upon late microcode load to recheck features, * only when microcode has been updated. Caller holds microcode_mutex and CPU diff --git a/arch/x86/kernel/cpu/cpu.h b/arch/x86/kernel/cpu/cpu.h index 5eb946b9a9f3..c0e2407abdd6 100644 --- a/arch/x86/kernel/cpu/cpu.h +++ b/arch/x86/kernel/cpu/cpu.h @@ -14,7 +14,6 @@ struct cpu_dev { void (*c_init)(struct cpuinfo_x86 *); void (*c_identify)(struct cpuinfo_x86 *); void (*c_detect_tlb)(struct cpuinfo_x86 *); - void (*c_bsp_resume)(struct cpuinfo_x86 *); int c_x86_vendor; #ifdef CONFIG_X86_32 /* Optional vendor specific routine to obtain the cache size. */ diff --git a/arch/x86/kernel/cpu/intel.c b/arch/x86/kernel/cpu/intel.c index fc3c07fe7df5..f17c1a714779 100644 --- a/arch/x86/kernel/cpu/intel.c +++ b/arch/x86/kernel/cpu/intel.c @@ -596,36 +596,6 @@ detect_keyid_bits: c->x86_phys_bits -= keyid_bits; } -static void init_intel_energy_perf(struct cpuinfo_x86 *c) -{ - u64 epb; - - /* - * Initialize MSR_IA32_ENERGY_PERF_BIAS if not already initialized. - * (x86_energy_perf_policy(8) is available to change it at run-time.) - */ - if (!cpu_has(c, X86_FEATURE_EPB)) - return; - - rdmsrl(MSR_IA32_ENERGY_PERF_BIAS, epb); - if ((epb & 0xF) != ENERGY_PERF_BIAS_PERFORMANCE) - return; - - pr_warn_once("ENERGY_PERF_BIAS: Set to 'normal', was 'performance'\n"); - pr_warn_once("ENERGY_PERF_BIAS: View and update with x86_energy_perf_policy(8)\n"); - epb = (epb & ~0xF) | ENERGY_PERF_BIAS_NORMAL; - wrmsrl(MSR_IA32_ENERGY_PERF_BIAS, epb); -} - -static void intel_bsp_resume(struct cpuinfo_x86 *c) -{ - /* - * MSR_IA32_ENERGY_PERF_BIAS is lost across suspend/resume, - * so reinitialize it properly like during bootup: - */ - init_intel_energy_perf(c); -} - static void init_cpuid_fault(struct cpuinfo_x86 *c) { u64 msr; @@ -763,8 +733,6 @@ static void init_intel(struct cpuinfo_x86 *c) if (cpu_has(c, X86_FEATURE_TME)) detect_tme(c); - init_intel_energy_perf(c); - init_intel_misc_features(c); } @@ -1023,9 +991,7 @@ static const struct cpu_dev intel_cpu_dev = { .c_detect_tlb = intel_detect_tlb, .c_early_init = early_init_intel, .c_init = init_intel, - .c_bsp_resume = intel_bsp_resume, .c_x86_vendor = X86_VENDOR_INTEL, }; cpu_dev_register(intel_cpu_dev); - diff --git a/arch/x86/kernel/cpu/intel_epb.c b/arch/x86/kernel/cpu/intel_epb.c new file mode 100644 index 000000000000..8d53cc88bd22 --- /dev/null +++ b/arch/x86/kernel/cpu/intel_epb.c @@ -0,0 +1,131 @@ +// SPDX-License-Identifier: GPL-2.0 +/* + * Intel Performance and Energy Bias Hint support. + * + * Copyright (C) 2019 Intel Corporation + * + * Author: + * Rafael J. Wysocki + */ + +#include +#include +#include + +#include +#include + +/** + * DOC: overview + * + * The Performance and Energy Bias Hint (EPB) allows software to specify its + * preference with respect to the power-performance tradeoffs present in the + * processor. Generally, the EPB is expected to be set by user space through + * the generic MSR interface (with the help of the x86_energy_perf_policy tool), + * but there are two reasons for the kernel to touch it. + * + * First, there are systems where the platform firmware resets the EPB during + * system-wide transitions from sleep states back into the working state + * effectively causing the previous EPB updates by user space to be lost. + * Thus the kernel needs to save the current EPB values for all CPUs during + * system-wide transitions to sleep states and restore them on the way back to + * the working state. That can be achieved by saving EPB for secondary CPUs + * when they are taken offline during transitions into system sleep states and + * for the boot CPU in a syscore suspend operation, so that it can be restored + * for the boot CPU in a syscore resume operation and for the other CPUs when + * they are brought back online. However, CPUs that are already offline when + * a system-wide PM transition is started are not taken offline again, but their + * EPB values may still be reset by the platform firmware during the transition, + * so in fact it is necessary to save the EPB of any CPU taken offline and to + * restore it when the given CPU goes back online at all times. + * + * Second, on many systems the initial EPB value coming from the platform + * firmware is 0 ('performance') and at least on some of them that is because + * the platform firmware does not initialize EPB at all with the assumption that + * the OS will do that anyway. That sometimes is problematic, as it may cause + * the system battery to drain too fast, for example, so it is better to adjust + * it on CPU bring-up and if the initial EPB value for a given CPU is 0, the + * kernel changes it to 6 ('normal'). + */ + +static DEFINE_PER_CPU(u8, saved_epb); + +#define EPB_MASK 0x0fULL +#define EPB_SAVED 0x10ULL + +static int intel_epb_save(void) +{ + u64 epb; + + rdmsrl(MSR_IA32_ENERGY_PERF_BIAS, epb); + /* + * Ensure that saved_epb will always be nonzero after this write even if + * the EPB value read from the MSR is 0. + */ + this_cpu_write(saved_epb, (epb & EPB_MASK) | EPB_SAVED); + + return 0; +} + +static void intel_epb_restore(void) +{ + u64 val = this_cpu_read(saved_epb); + u64 epb; + + rdmsrl(MSR_IA32_ENERGY_PERF_BIAS, epb); + if (val) { + val &= EPB_MASK; + } else { + /* + * Because intel_epb_save() has not run for the current CPU yet, + * it is going online for the first time, so if its EPB value is + * 0 ('performance') at this point, assume that it has not been + * initialized by the platform firmware and set it to 6 + * ('normal'). + */ + val = epb & EPB_MASK; + if (val == ENERGY_PERF_BIAS_PERFORMANCE) { + val = ENERGY_PERF_BIAS_NORMAL; + pr_warn_once("ENERGY_PERF_BIAS: Set to 'normal', was 'performance'\n"); + } + } + wrmsrl(MSR_IA32_ENERGY_PERF_BIAS, (epb & ~EPB_MASK) | val); +} + +static struct syscore_ops intel_epb_syscore_ops = { + .suspend = intel_epb_save, + .resume = intel_epb_restore, +}; + +static int intel_epb_online(unsigned int cpu) +{ + intel_epb_restore(); + return 0; +} + +static int intel_epb_offline(unsigned int cpu) +{ + return intel_epb_save(); +} + +static __init int intel_epb_init(void) +{ + int ret; + + if (!boot_cpu_has(X86_FEATURE_EPB)) + return -ENODEV; + + ret = cpuhp_setup_state(CPUHP_AP_X86_INTEL_EPB_ONLINE, + "x86/intel/epb:online", intel_epb_online, + intel_epb_offline); + if (ret < 0) + goto err_out_online; + + register_syscore_ops(&intel_epb_syscore_ops); + return 0; + +err_out_online: + cpuhp_remove_state(CPUHP_AP_X86_INTEL_EPB_ONLINE); + return ret; +} +subsys_initcall(intel_epb_init); diff --git a/include/linux/cpuhotplug.h b/include/linux/cpuhotplug.h index e78281d07b70..dbfdd0fadbef 100644 --- a/include/linux/cpuhotplug.h +++ b/include/linux/cpuhotplug.h @@ -147,6 +147,7 @@ enum cpuhp_state { CPUHP_AP_X86_VDSO_VMA_ONLINE, CPUHP_AP_IRQ_AFFINITY_ONLINE, CPUHP_AP_ARM_MVEBU_SYNC_CLOCKS, + CPUHP_AP_X86_INTEL_EPB_ONLINE, CPUHP_AP_PERF_ONLINE, CPUHP_AP_PERF_X86_ONLINE, CPUHP_AP_PERF_X86_UNCORE_ONLINE, -- cgit v1.2.3 From b9c273babce791cf228fc466577f55056a699f9c Mon Sep 17 00:00:00 2001 From: "Rafael J. Wysocki" Date: Thu, 21 Mar 2019 23:20:17 +0100 Subject: PM / arch: x86: MSR_IA32_ENERGY_PERF_BIAS sysfs interface The Performance and Energy Bias Hint (EPB) is expected to be set by user space through the generic MSR interface, but that interface is not particularly nice and there are security concerns regarding it, so it is not always available. For this reason, add a sysfs interface for reading and updating the EPB, in the form of a new attribute, energy_perf_bias, located under /sys/devices/system/cpu/cpu#/power/ for online CPUs that support the EPB feature. Signed-off-by: Rafael J. Wysocki Reviewed-by: Hannes Reinecke Acked-by: Borislav Petkov --- Documentation/ABI/testing/sysfs-devices-system-cpu | 18 +++++ Documentation/admin-guide/pm/intel_epb.rst | 27 +++++++ arch/x86/kernel/cpu/intel_epb.c | 93 +++++++++++++++++++++- 3 files changed, 134 insertions(+), 4 deletions(-) (limited to 'Documentation') diff --git a/Documentation/ABI/testing/sysfs-devices-system-cpu b/Documentation/ABI/testing/sysfs-devices-system-cpu index 9605dbd4b5b5..7f4af7da3fbc 100644 --- a/Documentation/ABI/testing/sysfs-devices-system-cpu +++ b/Documentation/ABI/testing/sysfs-devices-system-cpu @@ -518,3 +518,21 @@ Description: Control Symetric Multi Threading (SMT) If control status is "forceoff" or "notsupported" writes are rejected. + +What: /sys/devices/system/cpu/cpu#/power/energy_perf_bias +Date: March 2019 +Contact: linux-pm@vger.kernel.org +Description: Intel Energy and Performance Bias Hint (EPB) + + EPB for the given CPU in a sliding scale 0 - 15, where a value + of 0 corresponds to a hint preference for highest performance + and a value of 15 corresponds to the maximum energy savings. + + In order to change the EPB value for the CPU, write either + a number in the 0 - 15 sliding scale above, or one of the + strings: "performance", "balance-performance", "normal", + "balance-power", "power" (that represent values reflected by + their meaning), to this attribute. + + This attribute is present for all online CPUs supporting the + Intel EPB feature. diff --git a/Documentation/admin-guide/pm/intel_epb.rst b/Documentation/admin-guide/pm/intel_epb.rst index e9cfa7ec5420..d100849edfc4 100644 --- a/Documentation/admin-guide/pm/intel_epb.rst +++ b/Documentation/admin-guide/pm/intel_epb.rst @@ -4,3 +4,30 @@ Intel Performance and Energy Bias Hint .. kernel-doc:: arch/x86/kernel/cpu/intel_epb.c :doc: overview + +Intel Performance and Energy Bias Attribute in ``sysfs`` +======================================================== + +The Intel Performance and Energy Bias Hint (EPB) value for a given (logical) CPU +can be checked or updated through a ``sysfs`` attribute (file) under +:file:`/sys/devices/system/cpu/cpu/power/`, where the CPU number ```` +is allocated at the system initialization time: + +``energy_perf_bias`` + Shows the current EPB value for the CPU in a sliding scale 0 - 15, where + a value of 0 corresponds to a hint preference for highest performance + and a value of 15 corresponds to the maximum energy savings. + + In order to update the EPB value for the CPU, this attribute can be + written to, either with a number in the 0 - 15 sliding scale above, or + with one of the strings: "performance", "balance-performance", "normal", + "balance-power", "power" that represent values reflected by their + meaning. + + This attribute is present for all online CPUs supporting the EPB + feature. + +Note that while the EPB interface to the processor is defined at the logical CPU +level, the physical register backing it may be shared by multiple CPUs (for +example, SMT siblings or cores in one package). For this reason, updating the +EPB value for one CPU may cause the EPB values for other CPUs to change. diff --git a/arch/x86/kernel/cpu/intel_epb.c b/arch/x86/kernel/cpu/intel_epb.c index 8d53cc88bd22..f4dd73396f28 100644 --- a/arch/x86/kernel/cpu/intel_epb.c +++ b/arch/x86/kernel/cpu/intel_epb.c @@ -9,8 +9,12 @@ */ #include +#include +#include #include +#include #include +#include #include #include @@ -20,9 +24,9 @@ * * The Performance and Energy Bias Hint (EPB) allows software to specify its * preference with respect to the power-performance tradeoffs present in the - * processor. Generally, the EPB is expected to be set by user space through - * the generic MSR interface (with the help of the x86_energy_perf_policy tool), - * but there are two reasons for the kernel to touch it. + * processor. Generally, the EPB is expected to be set by user space (directly + * via sysfs or with the help of the x86_energy_perf_policy tool), but there are + * two reasons for the kernel to update it. * * First, there are systems where the platform firmware resets the EPB during * system-wide transitions from sleep states back into the working state @@ -52,6 +56,7 @@ static DEFINE_PER_CPU(u8, saved_epb); #define EPB_MASK 0x0fULL #define EPB_SAVED 0x10ULL +#define MAX_EPB EPB_MASK static int intel_epb_save(void) { @@ -97,15 +102,95 @@ static struct syscore_ops intel_epb_syscore_ops = { .resume = intel_epb_restore, }; +static const char * const energy_perf_strings[] = { + "performance", + "balance-performance", + "normal", + "balance-power", + "power" +}; +static const u8 energ_perf_values[] = { + ENERGY_PERF_BIAS_PERFORMANCE, + ENERGY_PERF_BIAS_BALANCE_PERFORMANCE, + ENERGY_PERF_BIAS_NORMAL, + ENERGY_PERF_BIAS_BALANCE_POWERSAVE, + ENERGY_PERF_BIAS_POWERSAVE +}; + +static ssize_t energy_perf_bias_show(struct device *dev, + struct device_attribute *attr, + char *buf) +{ + unsigned int cpu = dev->id; + u64 epb; + int ret; + + ret = rdmsrl_on_cpu(cpu, MSR_IA32_ENERGY_PERF_BIAS, &epb); + if (ret < 0) + return ret; + + return sprintf(buf, "%llu\n", epb); +} + +static ssize_t energy_perf_bias_store(struct device *dev, + struct device_attribute *attr, + const char *buf, size_t count) +{ + unsigned int cpu = dev->id; + u64 epb, val; + int ret; + + ret = __sysfs_match_string(energy_perf_strings, + ARRAY_SIZE(energy_perf_strings), buf); + if (ret >= 0) + val = energ_perf_values[ret]; + else if (kstrtou64(buf, 0, &val) || val > MAX_EPB) + return -EINVAL; + + ret = rdmsrl_on_cpu(cpu, MSR_IA32_ENERGY_PERF_BIAS, &epb); + if (ret < 0) + return ret; + + ret = wrmsrl_on_cpu(cpu, MSR_IA32_ENERGY_PERF_BIAS, + (epb & ~EPB_MASK) | val); + if (ret < 0) + return ret; + + return count; +} + +static DEVICE_ATTR_RW(energy_perf_bias); + +static struct attribute *intel_epb_attrs[] = { + &dev_attr_energy_perf_bias.attr, + NULL +}; + +static const struct attribute_group intel_epb_attr_group = { + .name = power_group_name, + .attrs = intel_epb_attrs +}; + static int intel_epb_online(unsigned int cpu) { + struct device *cpu_dev = get_cpu_device(cpu); + intel_epb_restore(); + if (!cpuhp_tasks_frozen) + sysfs_merge_group(&cpu_dev->kobj, &intel_epb_attr_group); + return 0; } static int intel_epb_offline(unsigned int cpu) { - return intel_epb_save(); + struct device *cpu_dev = get_cpu_device(cpu); + + if (!cpuhp_tasks_frozen) + sysfs_unmerge_group(&cpu_dev->kobj, &intel_epb_attr_group); + + intel_epb_save(); + return 0; } static __init int intel_epb_init(void) -- cgit v1.2.3 From 24496da6927fa7399f7f60ab31b4cea27ec3ed00 Mon Sep 17 00:00:00 2001 From: Sowjanya Komatineni Date: Thu, 4 Apr 2019 17:14:15 -0700 Subject: spi-summary: document set_cs_timing This patch documents set_cs_timing SPI master method. Signed-off-by: Sowjanya Komatineni Signed-off-by: Mark Brown --- Documentation/spi/spi-summary | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'Documentation') diff --git a/Documentation/spi/spi-summary b/Documentation/spi/spi-summary index 1721c1b570c3..1a63194b74d7 100644 --- a/Documentation/spi/spi-summary +++ b/Documentation/spi/spi-summary @@ -572,6 +572,12 @@ SPI MASTER METHODS 0: transfer is finished 1: transfer is still in progress + master->set_cs_timing(struct spi_device *spi, u8 setup_clk_cycles, + u8 hold_clk_cycles, u8 inactive_clk_cycles) + This method allows SPI client drivers to request SPI master controller + for configuring device specific CS setup, hold and inactive timing + requirements. + DEPRECATED METHODS master->transfer(struct spi_device *spi, struct spi_message *message) -- cgit v1.2.3 From 7558f978f9b66a2bc284a0e8c0764b88305bc29f Mon Sep 17 00:00:00 2001 From: Sowjanya Komatineni Date: Thu, 4 Apr 2019 17:14:18 -0700 Subject: spi: document tx/rx clock delay properties Tegra SPI controller has TX and RX trimmers to tuning the delay of SPI master clock with respect to the data. TX and RX tap values are based on the platform validation across the PVT and the trimmer values vary based on the trace lengths to the corresponding SPI devices. Signed-off-by: Sowjanya Komatineni Signed-off-by: Mark Brown --- .../devicetree/bindings/spi/nvidia,tegra114-spi.txt | 20 ++++++++++++++++++++ 1 file changed, 20 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/spi/nvidia,tegra114-spi.txt b/Documentation/devicetree/bindings/spi/nvidia,tegra114-spi.txt index 9ba7c5a273b4..db8e0d71c5bc 100644 --- a/Documentation/devicetree/bindings/spi/nvidia,tegra114-spi.txt +++ b/Documentation/devicetree/bindings/spi/nvidia,tegra114-spi.txt @@ -23,6 +23,18 @@ Required properties: Recommended properties: - spi-max-frequency: Definition as per Documentation/devicetree/bindings/spi/spi-bus.txt +Optional properties: +- nvidia,tx-clk-tap-delay: Delays the clock going out to the external device + with this tap value. This property is used to tune the outgoing data from + Tegra SPI master with respect to outgoing Tegra SPI master clock. + Tap values vary based on the platform design trace lengths from Tegra SPI + to corresponding slave devices. Valid tap values are from 0 thru 63. +- nvidia,rx-clk-tap-delay: Delays the clock coming in from the external device + with this tap value. This property is used to adjust the Tegra SPI master + clock with respect to the data from the SPI slave device. + Tap values vary based on the platform design trace lengths from Tegra SPI + to corresponding slave devices. Valid tap values are from 0 thru 63. + Example: spi@7000d600 { @@ -38,4 +50,12 @@ spi@7000d600 { reset-names = "spi"; dmas = <&apbdma 16>, <&apbdma 16>; dma-names = "rx", "tx"; + @ { + ... + ... + nvidia,rx-clk-tap-delay = <0>; + nvidia,tx-clk-tap-delay = <16>; + ... + }; + }; -- cgit v1.2.3 From 8554926b3fcb703a788018d5eba0ddd377abeecd Mon Sep 17 00:00:00 2001 From: Jerome Brunet Date: Fri, 29 Mar 2019 17:06:46 +0100 Subject: dt-bindings: clk: axg-audio: add g12a support Add a new compatible string and additional clock ids for audio clock controller of the g12a SoC family. Signed-off-by: Jerome Brunet Reviewed-by: Rob Herring Signed-off-by: Neil Armstrong Link: https://lkml.kernel.org/r/20190329160649.31603-2-jbrunet@baylibre.com --- .../devicetree/bindings/clock/amlogic,axg-audio-clkc.txt | 3 ++- include/dt-bindings/clock/axg-audio-clkc.h | 10 ++++++++++ 2 files changed, 12 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/clock/amlogic,axg-audio-clkc.txt b/Documentation/devicetree/bindings/clock/amlogic,axg-audio-clkc.txt index 61777ad24f61..0f777749f4f1 100644 --- a/Documentation/devicetree/bindings/clock/amlogic,axg-audio-clkc.txt +++ b/Documentation/devicetree/bindings/clock/amlogic,axg-audio-clkc.txt @@ -6,7 +6,8 @@ devices. Required Properties: -- compatible : should be "amlogic,axg-audio-clkc" for the A113X and A113D +- compatible : should be "amlogic,axg-audio-clkc" for the A113X and A113D, + "amlogic,g12a-audio-clkc" for G12A. - reg : physical base address of the clock controller and length of memory mapped region. - clocks : a list of phandle + clock-specifier pairs for the clocks listed diff --git a/include/dt-bindings/clock/axg-audio-clkc.h b/include/dt-bindings/clock/axg-audio-clkc.h index eafb0de8466b..75901c636893 100644 --- a/include/dt-bindings/clock/axg-audio-clkc.h +++ b/include/dt-bindings/clock/axg-audio-clkc.h @@ -70,5 +70,15 @@ #define AUD_CLKID_TDMOUT_A_LRCLK 134 #define AUD_CLKID_TDMOUT_B_LRCLK 135 #define AUD_CLKID_TDMOUT_C_LRCLK 136 +#define AUD_CLKID_SPDIFOUT_B 151 +#define AUD_CLKID_SPDIFOUT_B_CLK 152 +#define AUD_CLKID_TDM_MCLK_PAD0 155 +#define AUD_CLKID_TDM_MCLK_PAD1 156 +#define AUD_CLKID_TDM_LRCLK_PAD0 157 +#define AUD_CLKID_TDM_LRCLK_PAD1 158 +#define AUD_CLKID_TDM_LRCLK_PAD2 159 +#define AUD_CLKID_TDM_SCLK_PAD0 160 +#define AUD_CLKID_TDM_SCLK_PAD1 161 +#define AUD_CLKID_TDM_SCLK_PAD2 162 #endif /* __AXG_AUDIO_CLKC_BINDINGS_H */ -- cgit v1.2.3 From 9f325c9837251519968821fe82cdd81b2c450a71 Mon Sep 17 00:00:00 2001 From: Zhiyong Tao Date: Mon, 1 Apr 2019 11:35:32 +0800 Subject: pinctrl: mt8183: add DT binding document The commit adds mt8183 compatible node in binding document. Signed-off-by: Zhiyong Tao Signed-off-by: Erin Lo Reviewed-by: Rob Herring Signed-off-by: Linus Walleij --- .../devicetree/bindings/pinctrl/pinctrl-mt8183.txt | 132 +++++++++++++++++++++ 1 file changed, 132 insertions(+) create mode 100644 Documentation/devicetree/bindings/pinctrl/pinctrl-mt8183.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/pinctrl/pinctrl-mt8183.txt b/Documentation/devicetree/bindings/pinctrl/pinctrl-mt8183.txt new file mode 100644 index 000000000000..eccbe3f55d3f --- /dev/null +++ b/Documentation/devicetree/bindings/pinctrl/pinctrl-mt8183.txt @@ -0,0 +1,132 @@ +* Mediatek MT8183 Pin Controller + +The Mediatek's Pin controller is used to control SoC pins. + +Required properties: +- compatible: value should be one of the following. + "mediatek,mt8183-pinctrl", compatible with mt8183 pinctrl. +- gpio-controller : Marks the device node as a gpio controller. +- #gpio-cells: number of cells in GPIO specifier. Since the generic GPIO + binding is used, the amount of cells must be specified as 2. See the below + mentioned gpio binding representation for description of particular cells. +- gpio-ranges : gpio valid number range. +- reg: physical address base for gpio base registers. There are 10 GPIO + physical address base in mt8183. + +Optional properties: +- reg-names: gpio base register names. There are 10 gpio base register + names in mt8183. They are "iocfg0", "iocfg1", "iocfg2", "iocfg3", "iocfg4", + "iocfg5", "iocfg6", "iocfg7", "iocfg8", "eint". +- interrupt-controller: Marks the device node as an interrupt controller +- #interrupt-cells: Should be two. +- interrupts : The interrupt outputs to sysirq. + +Please refer to pinctrl-bindings.txt in this directory for details of the +common pinctrl bindings used by client devices. + +Subnode format +A pinctrl node should contain at least one subnodes representing the +pinctrl groups available on the machine. Each subnode will list the +pins it needs, and how they should be configured, with regard to muxer +configuration, pullups, drive strength, input enable/disable and input schmitt. + + node { + pinmux = ; + GENERIC_PINCONFIG; + }; + +Required properties: +- pinmux: integer array, represents gpio pin number and mux setting. + Supported pin number and mux varies for different SoCs, and are defined + as macros in boot/dts/-pinfunc.h directly. + +Optional properties: +- GENERIC_PINCONFIG: is the generic pinconfig options to use, bias-disable, + bias-pull-down, bias-pull-up, input-enable, input-disable, output-low, + output-high, input-schmitt-enable, input-schmitt-disable + and drive-strength are valid. + + Some special pins have extra pull up strength, there are R0 and R1 pull-up + resistors available, but for user, it's only need to set R1R0 as 00, 01, + 10 or 11. So It needs config "mediatek,pull-up-adv" or + "mediatek,pull-down-adv" to support arguments for those special pins. + Valid arguments are from 0 to 3. + + mediatek,tdsel: An integer describing the steps for output level shifter + duty cycle when asserted (high pulse width adjustment). Valid arguments + are from 0 to 15. + mediatek,rdsel: An integer describing the steps for input level shifter + duty cycle when asserted (high pulse width adjustment). Valid arguments + are from 0 to 63. + + When config drive-strength, it can support some arguments, such as + MTK_DRIVE_4mA, MTK_DRIVE_6mA, etc. See dt-bindings/pinctrl/mt65xx.h. + It can only support 2/4/6/8/10/12/14/16mA in mt8183. + For I2C pins, there are existing generic driving setup and the specific + driving setup. I2C pins can only support 2/4/6/8/10/12/14/16mA driving + adjustment in generic driving setup. But in specific driving setup, + they can support 0.125/0.25/0.5/1mA adjustment. If we enable specific + driving setup for I2C pins, the existing generic driving setup will be + disabled. For some special features, we need the I2C pins specific + driving setup. The specific driving setup is controlled by E1E0EN. + So we need add extra vendor driving preperty instead of + the generic driving property. + We can add "mediatek,drive-strength-adv = ;" to describe the specific + driving setup property. "XXX" means the value of E1E0EN. EN is 0 or 1. + It is used to enable or disable the specific driving setup. + E1E0 is used to describe the detail strength specification of the I2C pin. + When E1=0/E0=0, the strength is 0.125mA. + When E1=0/E0=1, the strength is 0.25mA. + When E1=1/E0=0, the strength is 0.5mA. + When E1=1/E0=1, the strength is 1mA. + So the valid arguments of "mediatek,drive-strength-adv" are from 0 to 7. + +Examples: + +#include "mt8183-pinfunc.h" + +... +{ + pio: pinctrl@10005000 { + compatible = "mediatek,mt8183-pinctrl"; + reg = <0 0x10005000 0 0x1000>, + <0 0x11f20000 0 0x1000>, + <0 0x11e80000 0 0x1000>, + <0 0x11e70000 0 0x1000>, + <0 0x11e90000 0 0x1000>, + <0 0x11d30000 0 0x1000>, + <0 0x11d20000 0 0x1000>, + <0 0x11c50000 0 0x1000>, + <0 0x11f30000 0 0x1000>, + <0 0x1000b000 0 0x1000>; + reg-names = "iocfg0", "iocfg1", "iocfg2", + "iocfg3", "iocfg4", "iocfg5", + "iocfg6", "iocfg7", "iocfg8", + "eint"; + gpio-controller; + #gpio-cells = <2>; + gpio-ranges = <&pio 0 0 192>; + interrupt-controller; + interrupts = ; + #interrupt-cells = <2>; + + i2c0_pins_a: i2c0 { + pins1 { + pinmux = , + ; + mediatek,pull-up-adv = <3>; + mediatek,drive-strength-adv = <7>; + }; + }; + + i2c1_pins_a: i2c1 { + pins { + pinmux = , + ; + mediatek,pull-down-adv = <2>; + mediatek,drive-strength-adv = <4>; + }; + }; + ... + }; +}; -- cgit v1.2.3 From 1120b0f9850cb01fffcb5f4379a69c8ab7a6658f Mon Sep 17 00:00:00 2001 From: "Rafael J. Wysocki" Date: Thu, 4 Apr 2019 00:03:30 +0200 Subject: cpufreq: intel_pstate: Documentation: Add references sections Add separate refereces sections to the cpufreq.rst and intel_pstate.rst documents under admin-quide/pm and list the references to external documentation in there. Update the ACPI specification URL while at it. Signed-off-by: Rafael J. Wysocki Acked-by: Viresh Kumar --- Documentation/admin-guide/pm/cpufreq.rst | 10 +++++++--- Documentation/admin-guide/pm/intel_pstate.rst | 25 ++++++++++++++++--------- 2 files changed, 23 insertions(+), 12 deletions(-) (limited to 'Documentation') diff --git a/Documentation/admin-guide/pm/cpufreq.rst b/Documentation/admin-guide/pm/cpufreq.rst index 7eca9026a9ed..b97ce64d5976 100644 --- a/Documentation/admin-guide/pm/cpufreq.rst +++ b/Documentation/admin-guide/pm/cpufreq.rst @@ -396,8 +396,8 @@ RT or deadline scheduling classes, the governor will increase the frequency to the allowed maximum (that is, the ``scaling_max_freq`` policy limit). In turn, if it is invoked by the CFS scheduling class, the governor will use the Per-Entity Load Tracking (PELT) metric for the root control group of the -given CPU as the CPU utilization estimate (see the `Per-entity load tracking`_ -LWN.net article for a description of the PELT mechanism). Then, the new +given CPU as the CPU utilization estimate (see the *Per-entity load tracking* +LWN.net article [1]_ for a description of the PELT mechanism). Then, the new CPU frequency to apply is computed in accordance with the formula f = 1.25 * ``f_0`` * ``util`` / ``max`` @@ -698,4 +698,8 @@ hardware feature (e.g. all Intel ones), even if the :c:macro:`CONFIG_X86_ACPI_CPUFREQ_CPB` configuration option is set. -.. _Per-entity load tracking: https://lwn.net/Articles/531853/ +References +========== + +.. [1] Jonathan Corbet, *Per-entity load tracking*, + https://lwn.net/Articles/531853/ diff --git a/Documentation/admin-guide/pm/intel_pstate.rst b/Documentation/admin-guide/pm/intel_pstate.rst index ec0f7c111f65..6dba90b753d7 100644 --- a/Documentation/admin-guide/pm/intel_pstate.rst +++ b/Documentation/admin-guide/pm/intel_pstate.rst @@ -20,11 +20,10 @@ you have not done that yet.] For the processors supported by ``intel_pstate``, the P-state concept is broader than just an operating frequency or an operating performance point (see the -`LinuxCon Europe 2015 presentation by Kristen Accardi `_ for more +LinuxCon Europe 2015 presentation by Kristen Accardi [1]_ for more information about that). For this reason, the representation of P-states used by ``intel_pstate`` internally follows the hardware specification (for details -refer to `Intel® 64 and IA-32 Architectures Software Developer’s Manual -Volume 3: System Programming Guide `_). However, the ``CPUFreq`` core +refer to Intel Software Developer’s Manual [2]_). However, the ``CPUFreq`` core uses frequencies for identifying operating performance points of CPUs and frequencies are involved in the user space interface exposed by it, so ``intel_pstate`` maps its internal representation of P-states to frequencies too @@ -561,9 +560,9 @@ or to pin every task potentially sensitive to them to a specific CPU.] On the majority of systems supported by ``intel_pstate``, the ACPI tables provided by the platform firmware contain ``_PSS`` objects returning information -that can be used for CPU performance scaling (refer to the `ACPI specification`_ -for details on the ``_PSS`` objects and the format of the information returned -by them). +that can be used for CPU performance scaling (refer to the ACPI specification +[3]_ for details on the ``_PSS`` objects and the format of the information +returned by them). The information returned by the ACPI ``_PSS`` objects is used by the ``acpi-cpufreq`` scaling driver. On systems supported by ``intel_pstate`` @@ -728,6 +727,14 @@ P-state is called, the ``ftrace`` filter can be set to to -0 [000] ..s. 2537.654843: intel_pstate_set_pstate <-intel_pstate_timer_func -.. _LCEU2015: http://events.linuxfoundation.org/sites/events/files/slides/LinuxConEurope_2015.pdf -.. _SDM: http://www.intel.com/content/www/us/en/architecture-and-technology/64-ia-32-architectures-software-developer-system-programming-manual-325384.html -.. _ACPI specification: http://www.uefi.org/sites/default/files/resources/ACPI_6_1.pdf +References +========== + +.. [1] Kristen Accardi, *Balancing Power and Performance in the Linux Kernel*, + http://events.linuxfoundation.org/sites/events/files/slides/LinuxConEurope_2015.pdf + +.. [2] *Intel® 64 and IA-32 Architectures Software Developer’s Manual Volume 3: System Programming Guide*, + http://www.intel.com/content/www/us/en/architecture-and-technology/64-ia-32-architectures-software-developer-system-programming-manual-325384.html + +.. [3] *Advanced Configuration and Power Interface Specification*, + https://uefi.org/sites/default/files/resources/ACPI_6_3_final_Jan30.pdf -- cgit v1.2.3 From fc7db767b16cf2af3be9e87a4b88e206d0e1a8b2 Mon Sep 17 00:00:00 2001 From: "Rafael J. Wysocki" Date: Thu, 4 Apr 2019 00:04:43 +0200 Subject: Documentation: PM: Add SPDX license tags to multiple files Add SPDX license tags to .rst files under Documentation/driver-api/pm and Documentation/admin-quide/pm. Signed-off-by: Rafael J. Wysocki Acked-by: Viresh Kumar --- Documentation/admin-guide/pm/cpufreq.rst | 2 ++ Documentation/admin-guide/pm/cpuidle.rst | 2 ++ Documentation/admin-guide/pm/index.rst | 2 ++ Documentation/admin-guide/pm/intel_pstate.rst | 2 ++ Documentation/admin-guide/pm/sleep-states.rst | 2 ++ Documentation/admin-guide/pm/strategies.rst | 2 ++ Documentation/admin-guide/pm/system-wide.rst | 2 ++ Documentation/admin-guide/pm/working-state.rst | 2 ++ Documentation/driver-api/pm/cpuidle.rst | 2 ++ Documentation/driver-api/pm/devices.rst | 2 ++ Documentation/driver-api/pm/index.rst | 2 ++ Documentation/driver-api/pm/notifiers.rst | 2 ++ Documentation/driver-api/pm/types.rst | 2 ++ 13 files changed, 26 insertions(+) (limited to 'Documentation') diff --git a/Documentation/admin-guide/pm/cpufreq.rst b/Documentation/admin-guide/pm/cpufreq.rst index b97ce64d5976..63e54ba1fe0c 100644 --- a/Documentation/admin-guide/pm/cpufreq.rst +++ b/Documentation/admin-guide/pm/cpufreq.rst @@ -1,3 +1,5 @@ +.. SPDX-License-Identifier: GPL-2.0 + .. |struct cpufreq_policy| replace:: :c:type:`struct cpufreq_policy ` .. |intel_pstate| replace:: :doc:`intel_pstate ` diff --git a/Documentation/admin-guide/pm/cpuidle.rst b/Documentation/admin-guide/pm/cpuidle.rst index 9c58b35a81cb..ab8fa0856095 100644 --- a/Documentation/admin-guide/pm/cpuidle.rst +++ b/Documentation/admin-guide/pm/cpuidle.rst @@ -1,3 +1,5 @@ +.. SPDX-License-Identifier: GPL-2.0 + .. |struct cpuidle_state| replace:: :c:type:`struct cpuidle_state ` .. |cpufreq| replace:: :doc:`CPU Performance Scaling ` diff --git a/Documentation/admin-guide/pm/index.rst b/Documentation/admin-guide/pm/index.rst index 49237ac73442..39f8f9f81e7a 100644 --- a/Documentation/admin-guide/pm/index.rst +++ b/Documentation/admin-guide/pm/index.rst @@ -1,3 +1,5 @@ +.. SPDX-License-Identifier: GPL-2.0 + ================ Power Management ================ diff --git a/Documentation/admin-guide/pm/intel_pstate.rst b/Documentation/admin-guide/pm/intel_pstate.rst index 6dba90b753d7..5883c6c80315 100644 --- a/Documentation/admin-guide/pm/intel_pstate.rst +++ b/Documentation/admin-guide/pm/intel_pstate.rst @@ -1,3 +1,5 @@ +.. SPDX-License-Identifier: GPL-2.0 + =============================================== ``intel_pstate`` CPU Performance Scaling Driver =============================================== diff --git a/Documentation/admin-guide/pm/sleep-states.rst b/Documentation/admin-guide/pm/sleep-states.rst index dbf5acd49f35..6d3537ae9a94 100644 --- a/Documentation/admin-guide/pm/sleep-states.rst +++ b/Documentation/admin-guide/pm/sleep-states.rst @@ -1,3 +1,5 @@ +.. SPDX-License-Identifier: GPL-2.0 + =================== System Sleep States =================== diff --git a/Documentation/admin-guide/pm/strategies.rst b/Documentation/admin-guide/pm/strategies.rst index afe4d3f831fe..863172633fca 100644 --- a/Documentation/admin-guide/pm/strategies.rst +++ b/Documentation/admin-guide/pm/strategies.rst @@ -1,3 +1,5 @@ +.. SPDX-License-Identifier: GPL-2.0 + =========================== Power Management Strategies =========================== diff --git a/Documentation/admin-guide/pm/system-wide.rst b/Documentation/admin-guide/pm/system-wide.rst index 0c81e4c5de39..2b1f987b34f0 100644 --- a/Documentation/admin-guide/pm/system-wide.rst +++ b/Documentation/admin-guide/pm/system-wide.rst @@ -1,3 +1,5 @@ +.. SPDX-License-Identifier: GPL-2.0 + ============================ System-Wide Power Management ============================ diff --git a/Documentation/admin-guide/pm/working-state.rst b/Documentation/admin-guide/pm/working-state.rst index b6cef9b5e961..e5fbf322f256 100644 --- a/Documentation/admin-guide/pm/working-state.rst +++ b/Documentation/admin-guide/pm/working-state.rst @@ -1,3 +1,5 @@ +.. SPDX-License-Identifier: GPL-2.0 + ============================== Working-State Power Management ============================== diff --git a/Documentation/driver-api/pm/cpuidle.rst b/Documentation/driver-api/pm/cpuidle.rst index 5842ab621a58..7e0d850e0113 100644 --- a/Documentation/driver-api/pm/cpuidle.rst +++ b/Documentation/driver-api/pm/cpuidle.rst @@ -1,3 +1,5 @@ +.. SPDX-License-Identifier: GPL-2.0 + .. |struct cpuidle_governor| replace:: :c:type:`struct cpuidle_governor ` .. |struct cpuidle_device| replace:: :c:type:`struct cpuidle_device ` .. |struct cpuidle_driver| replace:: :c:type:`struct cpuidle_driver ` diff --git a/Documentation/driver-api/pm/devices.rst b/Documentation/driver-api/pm/devices.rst index 090c151aa86b..6885d72d85ca 100644 --- a/Documentation/driver-api/pm/devices.rst +++ b/Documentation/driver-api/pm/devices.rst @@ -1,3 +1,5 @@ +.. SPDX-License-Identifier: GPL-2.0 + .. |struct dev_pm_ops| replace:: :c:type:`struct dev_pm_ops ` .. |struct dev_pm_domain| replace:: :c:type:`struct dev_pm_domain ` .. |struct bus_type| replace:: :c:type:`struct bus_type ` diff --git a/Documentation/driver-api/pm/index.rst b/Documentation/driver-api/pm/index.rst index 56975c6bc789..c2a9ef8d115c 100644 --- a/Documentation/driver-api/pm/index.rst +++ b/Documentation/driver-api/pm/index.rst @@ -1,3 +1,5 @@ +.. SPDX-License-Identifier: GPL-2.0 + =============================== CPU and Device Power Management =============================== diff --git a/Documentation/driver-api/pm/notifiers.rst b/Documentation/driver-api/pm/notifiers.rst index 62f860026992..69678a0d9cc0 100644 --- a/Documentation/driver-api/pm/notifiers.rst +++ b/Documentation/driver-api/pm/notifiers.rst @@ -1,3 +1,5 @@ +.. SPDX-License-Identifier: GPL-2.0 + ============================= Suspend/Hibernation Notifiers ============================= diff --git a/Documentation/driver-api/pm/types.rst b/Documentation/driver-api/pm/types.rst index 3ebdecc54104..73a231caf764 100644 --- a/Documentation/driver-api/pm/types.rst +++ b/Documentation/driver-api/pm/types.rst @@ -1,3 +1,5 @@ +.. SPDX-License-Identifier: GPL-2.0 + ================================== Device Power Management Data Types ================================== -- cgit v1.2.3 From fc1860d6b17fa00d16df5e608eed0526e11ccad1 Mon Sep 17 00:00:00 2001 From: "Rafael J. Wysocki" Date: Thu, 4 Apr 2019 00:06:15 +0200 Subject: Documentation: PM: Unify copyright notices Unify copyright notices in the .rst files under Documentation/driver-api/pm and Documentation/admin-quide/pm. Signed-off-by: Rafael J. Wysocki Acked-by: Viresh Kumar --- Documentation/admin-guide/pm/cpufreq.rst | 6 ++++-- Documentation/admin-guide/pm/cpuidle.rst | 6 ++++-- Documentation/admin-guide/pm/intel_pstate.rst | 5 +++-- Documentation/admin-guide/pm/sleep-states.rst | 6 ++++-- Documentation/admin-guide/pm/strategies.rst | 6 ++++-- Documentation/driver-api/pm/cpuidle.rst | 5 +++-- Documentation/driver-api/pm/devices.rst | 10 ++++++---- Documentation/driver-api/pm/notifiers.rst | 6 ++++-- 8 files changed, 32 insertions(+), 18 deletions(-) (limited to 'Documentation') diff --git a/Documentation/admin-guide/pm/cpufreq.rst b/Documentation/admin-guide/pm/cpufreq.rst index 63e54ba1fe0c..0c74a7784964 100644 --- a/Documentation/admin-guide/pm/cpufreq.rst +++ b/Documentation/admin-guide/pm/cpufreq.rst @@ -1,4 +1,5 @@ .. SPDX-License-Identifier: GPL-2.0 +.. include:: .. |struct cpufreq_policy| replace:: :c:type:`struct cpufreq_policy ` .. |intel_pstate| replace:: :doc:`intel_pstate ` @@ -7,9 +8,10 @@ CPU Performance Scaling ======================= -:: +:Copyright: |copy| 2017 Intel Corporation + +:Author: Rafael J. Wysocki - Copyright (c) 2017 Intel Corp., Rafael J. Wysocki The Concept of CPU Performance Scaling ====================================== diff --git a/Documentation/admin-guide/pm/cpuidle.rst b/Documentation/admin-guide/pm/cpuidle.rst index ab8fa0856095..e70b365dbc60 100644 --- a/Documentation/admin-guide/pm/cpuidle.rst +++ b/Documentation/admin-guide/pm/cpuidle.rst @@ -1,4 +1,5 @@ .. SPDX-License-Identifier: GPL-2.0 +.. include:: .. |struct cpuidle_state| replace:: :c:type:`struct cpuidle_state ` .. |cpufreq| replace:: :doc:`CPU Performance Scaling ` @@ -7,9 +8,10 @@ CPU Idle Time Management ======================== -:: +:Copyright: |copy| 2018 Intel Corporation + +:Author: Rafael J. Wysocki - Copyright (c) 2018 Intel Corp., Rafael J. Wysocki Concepts ======== diff --git a/Documentation/admin-guide/pm/intel_pstate.rst b/Documentation/admin-guide/pm/intel_pstate.rst index 5883c6c80315..67e414e34f37 100644 --- a/Documentation/admin-guide/pm/intel_pstate.rst +++ b/Documentation/admin-guide/pm/intel_pstate.rst @@ -1,12 +1,13 @@ .. SPDX-License-Identifier: GPL-2.0 +.. include:: =============================================== ``intel_pstate`` CPU Performance Scaling Driver =============================================== -:: +:Copyright: |copy| 2017 Intel Corporation - Copyright (c) 2017 Intel Corp., Rafael J. Wysocki +:Author: Rafael J. Wysocki General Information diff --git a/Documentation/admin-guide/pm/sleep-states.rst b/Documentation/admin-guide/pm/sleep-states.rst index 6d3537ae9a94..cd3a28cb81f4 100644 --- a/Documentation/admin-guide/pm/sleep-states.rst +++ b/Documentation/admin-guide/pm/sleep-states.rst @@ -1,12 +1,14 @@ .. SPDX-License-Identifier: GPL-2.0 +.. include:: =================== System Sleep States =================== -:: +:Copyright: |copy| 2017 Intel Corporation + +:Author: Rafael J. Wysocki - Copyright (c) 2017 Intel Corp., Rafael J. Wysocki Sleep states are global low-power states of the entire system in which user space code cannot be executed and the overall system activity is significantly diff --git a/Documentation/admin-guide/pm/strategies.rst b/Documentation/admin-guide/pm/strategies.rst index 863172633fca..dd0362e32fa5 100644 --- a/Documentation/admin-guide/pm/strategies.rst +++ b/Documentation/admin-guide/pm/strategies.rst @@ -1,12 +1,14 @@ .. SPDX-License-Identifier: GPL-2.0 +.. include:: =========================== Power Management Strategies =========================== -:: +:Copyright: |copy| 2017 Intel Corporation + +:Author: Rafael J. Wysocki - Copyright (c) 2017 Intel Corp., Rafael J. Wysocki The Linux kernel supports two major high-level power management strategies. diff --git a/Documentation/driver-api/pm/cpuidle.rst b/Documentation/driver-api/pm/cpuidle.rst index 7e0d850e0113..006cf6db40c6 100644 --- a/Documentation/driver-api/pm/cpuidle.rst +++ b/Documentation/driver-api/pm/cpuidle.rst @@ -1,4 +1,5 @@ .. SPDX-License-Identifier: GPL-2.0 +.. include:: .. |struct cpuidle_governor| replace:: :c:type:`struct cpuidle_governor ` .. |struct cpuidle_device| replace:: :c:type:`struct cpuidle_device ` @@ -9,9 +10,9 @@ CPU Idle Time Management ======================== -:: +:Copyright: |copy| 2019 Intel Corporation - Copyright (c) 2019 Intel Corp., Rafael J. Wysocki +:Author: Rafael J. Wysocki CPU Idle Time Management Subsystem diff --git a/Documentation/driver-api/pm/devices.rst b/Documentation/driver-api/pm/devices.rst index 6885d72d85ca..30835683616a 100644 --- a/Documentation/driver-api/pm/devices.rst +++ b/Documentation/driver-api/pm/devices.rst @@ -1,4 +1,5 @@ .. SPDX-License-Identifier: GPL-2.0 +.. include:: .. |struct dev_pm_ops| replace:: :c:type:`struct dev_pm_ops ` .. |struct dev_pm_domain| replace:: :c:type:`struct dev_pm_domain ` @@ -14,11 +15,12 @@ Device Power Management Basics ============================== -:: +:Copyright: |copy| 2010-2011 Rafael J. Wysocki , Novell Inc. +:Copyright: |copy| 2010 Alan Stern +:Copyright: |copy| 2016 Intel Corporation + +:Author: Rafael J. Wysocki - Copyright (c) 2010-2011 Rafael J. Wysocki , Novell Inc. - Copyright (c) 2010 Alan Stern - Copyright (c) 2016 Intel Corp., Rafael J. Wysocki Most of the code in Linux is device drivers, so most of the Linux power management (PM) code is also driver-specific. Most drivers will do very diff --git a/Documentation/driver-api/pm/notifiers.rst b/Documentation/driver-api/pm/notifiers.rst index 69678a0d9cc0..186435c43b77 100644 --- a/Documentation/driver-api/pm/notifiers.rst +++ b/Documentation/driver-api/pm/notifiers.rst @@ -1,12 +1,14 @@ .. SPDX-License-Identifier: GPL-2.0 +.. include:: ============================= Suspend/Hibernation Notifiers ============================= -:: +:Copyright: |copy| 2016 Intel Corporation + +:Author: Rafael J. Wysocki - Copyright (c) 2016 Intel Corp., Rafael J. Wysocki There are some operations that subsystems or drivers may want to carry out before hibernation/suspend or after restore/resume, but they require the system -- cgit v1.2.3 From 7973b799dbea1770742851487a98276a24c961a5 Mon Sep 17 00:00:00 2001 From: "Rafael J. Wysocki" Date: Thu, 4 Apr 2019 00:08:18 +0200 Subject: admin-guide: pm: intel_epb: Add SPDX license tag and copyright notice Add an SPDX license tag and a copyright notice to the intel_epb.rst file under Documentation/admin-quide/pm. Signed-off-by: Rafael J. Wysocki Acked-by: Viresh Kumar --- Documentation/admin-guide/pm/intel_epb.rst | 8 ++++++++ 1 file changed, 8 insertions(+) (limited to 'Documentation') diff --git a/Documentation/admin-guide/pm/intel_epb.rst b/Documentation/admin-guide/pm/intel_epb.rst index d100849edfc4..005121167af7 100644 --- a/Documentation/admin-guide/pm/intel_epb.rst +++ b/Documentation/admin-guide/pm/intel_epb.rst @@ -1,7 +1,15 @@ +.. SPDX-License-Identifier: GPL-2.0 +.. include:: + ====================================== Intel Performance and Energy Bias Hint ====================================== +:Copyright: |copy| 2019 Intel Corporation + +:Author: Rafael J. Wysocki + + .. kernel-doc:: arch/x86/kernel/cpu/intel_epb.c :doc: overview -- cgit v1.2.3 From 4614bbdee35706ed77c130d23f12e21479b670ff Mon Sep 17 00:00:00 2001 From: Will Deacon Date: Mon, 11 Feb 2019 15:24:56 +0000 Subject: docs/memory-barriers.txt: Rewrite "KERNEL I/O BARRIER EFFECTS" section The "KERNEL I/O BARRIER EFFECTS" section of memory-barriers.txt is vague, x86-centric, out-of-date, incomplete and demonstrably incorrect in places. This is largely because I/O ordering is a horrible can of worms, but also because the document has stagnated as our understanding has evolved. Attempt to address some of that, by rewriting the section based on recent(-ish) discussions with Arnd, BenH and others. Maybe one day we'll find a way to formalise this stuff, but for now let's at least try to make the English easier to understand. Cc: Benjamin Herrenschmidt Cc: Michael Ellerman Cc: Arnd Bergmann Cc: Peter Zijlstra Cc: Andrea Parri Cc: Palmer Dabbelt Cc: Daniel Lustig Cc: David Howells Cc: Alan Stern Cc: "Maciej W. Rozycki" Cc: Mikulas Patocka Acked-by: Linus Torvalds Reviewed-by: Paul E. McKenney Signed-off-by: Will Deacon --- Documentation/memory-barriers.txt | 115 +++++++++++++++++++++++--------------- 1 file changed, 70 insertions(+), 45 deletions(-) (limited to 'Documentation') diff --git a/Documentation/memory-barriers.txt b/Documentation/memory-barriers.txt index 1c22b21ae922..5eb6f4c6a133 100644 --- a/Documentation/memory-barriers.txt +++ b/Documentation/memory-barriers.txt @@ -2599,72 +2599,97 @@ likely, then interrupt-disabling locks should be used to guarantee ordering. KERNEL I/O BARRIER EFFECTS ========================== -When accessing I/O memory, drivers should use the appropriate accessor -functions: +Interfacing with peripherals via I/O accesses is deeply architecture and device +specific. Therefore, drivers which are inherently non-portable may rely on +specific behaviours of their target systems in order to achieve synchronization +in the most lightweight manner possible. For drivers intending to be portable +between multiple architectures and bus implementations, the kernel offers a +series of accessor functions that provide various degrees of ordering +guarantees: - (*) inX(), outX(): + (*) readX(), writeX(): - These are intended to talk to I/O space rather than memory space, but - that's primarily a CPU-specific concept. The i386 and x86_64 processors - do indeed have special I/O space access cycles and instructions, but many - CPUs don't have such a concept. + The readX() and writeX() MMIO accessors take a pointer to the peripheral + being accessed as an __iomem * parameter. For pointers mapped with the + default I/O attributes (e.g. those returned by ioremap()), then the + ordering guarantees are as follows: - The PCI bus, amongst others, defines an I/O space concept which - on such - CPUs as i386 and x86_64 - readily maps to the CPU's concept of I/O - space. However, it may also be mapped as a virtual I/O space in the CPU's - memory map, particularly on those CPUs that don't support alternate I/O - spaces. + 1. All readX() and writeX() accesses to the same peripheral are ordered + with respect to each other. For example, this ensures that MMIO register + writes by the CPU to a particular device will arrive in program order. - Accesses to this space may be fully synchronous (as on i386), but - intermediary bridges (such as the PCI host bridge) may not fully honour - that. + 2. A writeX() by the CPU to the peripheral will first wait for the + completion of all prior CPU writes to memory. For example, this ensures + that writes by the CPU to an outbound DMA buffer allocated by + dma_alloc_coherent() will be visible to a DMA engine when the CPU writes + to its MMIO control register to trigger the transfer. - They are guaranteed to be fully ordered with respect to each other. + 3. A readX() by the CPU from the peripheral will complete before any + subsequent CPU reads from memory can begin. For example, this ensures + that reads by the CPU from an incoming DMA buffer allocated by + dma_alloc_coherent() will not see stale data after reading from the DMA + engine's MMIO status register to establish that the DMA transfer has + completed. - They are not guaranteed to be fully ordered with respect to other types of - memory and I/O operation. + 4. A readX() by the CPU from the peripheral will complete before any + subsequent delay() loop can begin execution. For example, this ensures + that two MMIO register writes by the CPU to a peripheral will arrive at + least 1us apart if the first write is immediately read back with readX() + and udelay(1) is called prior to the second writeX(). - (*) readX(), writeX(): + __iomem pointers obtained with non-default attributes (e.g. those returned + by ioremap_wc()) are unlikely to provide many of these guarantees. - Whether these are guaranteed to be fully ordered and uncombined with - respect to each other on the issuing CPU depends on the characteristics - defined for the memory window through which they're accessing. On later - i386 architecture machines, for example, this is controlled by way of the - MTRR registers. + (*) readX_relaxed(), writeX_relaxed(): - Ordinarily, these will be guaranteed to be fully ordered and uncombined, - provided they're not accessing a prefetchable device. + These are similar to readX() and writeX(), but provide weaker memory + ordering guarantees. Specifically, they do not guarantee ordering with + respect to normal memory accesses or delay() loops (i.e bullets 2-4 above) + but they are still guaranteed to be ordered with respect to other accesses + to the same peripheral when operating on __iomem pointers mapped with the + default I/O attributes. - However, intermediary hardware (such as a PCI bridge) may indulge in - deferral if it so wishes; to flush a store, a load from the same location - is preferred[*], but a load from the same device or from configuration - space should suffice for PCI. + (*) readsX(), writesX(): - [*] NOTE! attempting to load from the same location as was written to may - cause a malfunction - consider the 16550 Rx/Tx serial registers for - example. + The readsX() and writesX() MMIO accessors are designed for accessing + register-based, memory-mapped FIFOs residing on peripherals that are not + capable of performing DMA. Consequently, they provide only the ordering + guarantees of readX_relaxed() and writeX_relaxed(), as documented above. - Used with prefetchable I/O memory, an mmiowb() barrier may be required to - force stores to be ordered. + (*) inX(), outX(): - Please refer to the PCI specification for more information on interactions - between PCI transactions. + The inX() and outX() accessors are intended to access legacy port-mapped + I/O peripherals, which may require special instructions on some + architectures (notably x86). The port number of the peripheral being + accessed is passed as an argument. - (*) readX_relaxed(), writeX_relaxed() + Since many CPU architectures ultimately access these peripherals via an + internal virtual memory mapping, the portable ordering guarantees provided + by inX() and outX() are the same as those provided by readX() and writeX() + respectively when accessing a mapping with the default I/O attributes. - These are similar to readX() and writeX(), but provide weaker memory - ordering guarantees. Specifically, they do not guarantee ordering with - respect to normal memory accesses (e.g. DMA buffers) nor do they guarantee - ordering with respect to LOCK or UNLOCK operations. If the latter is - required, an mmiowb() barrier can be used. Note that relaxed accesses to - the same peripheral are guaranteed to be ordered with respect to each - other. + Device drivers may expect outX() to emit a non-posted write transaction + that waits for a completion response from the I/O peripheral before + returning. This is not guaranteed by all architectures and is therefore + not part of the portable ordering semantics. + + (*) insX(), outsX(): + + As above, the insX() and outsX() accessors provide the same ordering + guarantees as readsX() and writesX() respectively when accessing a mapping + with the default I/O attributes. (*) ioreadX(), iowriteX() These will perform appropriately for the type of access they're actually doing, be it inX()/outX() or readX()/writeX(). +All of these accessors assume that the underlying peripheral is little-endian, +and will therefore perform byte-swapping operations on big-endian architectures. + +Composing I/O ordering barriers with SMP ordering barriers and LOCK/UNLOCK +operations is a dangerous sport which may require the use of mmiowb(). See the +subsection "Acquires vs I/O accesses" for more information. ======================================== ASSUMED MINIMUM EXECUTION ORDERING MODEL -- cgit v1.2.3 From 915530396c788d75c40f200edd67b56ac363c728 Mon Sep 17 00:00:00 2001 From: Will Deacon Date: Fri, 22 Feb 2019 16:17:54 +0000 Subject: Documentation: Kill all references to mmiowb() The guarantees provided by mmiowb() are now provided implicitly by spin_unlock(), so remove all references to this most confusing of barriers from our Documentation. Good riddance. Acked-by: Linus Torvalds Signed-off-by: Will Deacon --- Documentation/driver-api/device-io.rst | 45 -------------- Documentation/driver-api/pci/p2pdma.rst | 4 -- Documentation/memory-barriers.txt | 103 ++------------------------------ 3 files changed, 4 insertions(+), 148 deletions(-) (limited to 'Documentation') diff --git a/Documentation/driver-api/device-io.rst b/Documentation/driver-api/device-io.rst index b00b23903078..0e389378f71d 100644 --- a/Documentation/driver-api/device-io.rst +++ b/Documentation/driver-api/device-io.rst @@ -103,51 +103,6 @@ continuing execution:: ha->flags.ints_enabled = 0; } -In addition to write posting, on some large multiprocessing systems -(e.g. SGI Challenge, Origin and Altix machines) posted writes won't be -strongly ordered coming from different CPUs. Thus it's important to -properly protect parts of your driver that do memory-mapped writes with -locks and use the :c:func:`mmiowb()` to make sure they arrive in the -order intended. Issuing a regular readX() will also ensure write ordering, -but should only be used when the -driver has to be sure that the write has actually arrived at the device -(not that it's simply ordered with respect to other writes), since a -full readX() is a relatively expensive operation. - -Generally, one should use :c:func:`mmiowb()` prior to releasing a spinlock -that protects regions using :c:func:`writeb()` or similar functions that -aren't surrounded by readb() calls, which will ensure ordering -and flushing. The following pseudocode illustrates what might occur if -write ordering isn't guaranteed via :c:func:`mmiowb()` or one of the -readX() functions:: - - CPU A: spin_lock_irqsave(&dev_lock, flags) - CPU A: ... - CPU A: writel(newval, ring_ptr); - CPU A: spin_unlock_irqrestore(&dev_lock, flags) - ... - CPU B: spin_lock_irqsave(&dev_lock, flags) - CPU B: writel(newval2, ring_ptr); - CPU B: ... - CPU B: spin_unlock_irqrestore(&dev_lock, flags) - -In the case above, newval2 could be written to ring_ptr before newval. -Fixing it is easy though:: - - CPU A: spin_lock_irqsave(&dev_lock, flags) - CPU A: ... - CPU A: writel(newval, ring_ptr); - CPU A: mmiowb(); /* ensure no other writes beat us to the device */ - CPU A: spin_unlock_irqrestore(&dev_lock, flags) - ... - CPU B: spin_lock_irqsave(&dev_lock, flags) - CPU B: writel(newval2, ring_ptr); - CPU B: ... - CPU B: mmiowb(); - CPU B: spin_unlock_irqrestore(&dev_lock, flags) - -See tg3.c for a real world example of how to use :c:func:`mmiowb()` - PCI ordering rules also guarantee that PIO read responses arrive after any outstanding DMA writes from that bus, since for some devices the result of a readb() call may signal to the driver that a DMA transaction is diff --git a/Documentation/driver-api/pci/p2pdma.rst b/Documentation/driver-api/pci/p2pdma.rst index 6d85b5a2598d..44deb52beeb4 100644 --- a/Documentation/driver-api/pci/p2pdma.rst +++ b/Documentation/driver-api/pci/p2pdma.rst @@ -132,10 +132,6 @@ precludes passing these pages to userspace. P2P memory is also technically IO memory but should never have any side effects behind it. Thus, the order of loads and stores should not be important and ioreadX(), iowriteX() and friends should not be necessary. -However, as the memory is not cache coherent, if access ever needs to -be protected by a spinlock then :c:func:`mmiowb()` must be used before -unlocking the lock. (See ACQUIRES VS I/O ACCESSES in -Documentation/memory-barriers.txt) P2P DMA Support Library diff --git a/Documentation/memory-barriers.txt b/Documentation/memory-barriers.txt index 5eb6f4c6a133..3522f0cc772f 100644 --- a/Documentation/memory-barriers.txt +++ b/Documentation/memory-barriers.txt @@ -1937,21 +1937,6 @@ There are some more advanced barrier functions: information on consistent memory. -MMIO WRITE BARRIER ------------------- - -The Linux kernel also has a special barrier for use with memory-mapped I/O -writes: - - mmiowb(); - -This is a variation on the mandatory write barrier that causes writes to weakly -ordered I/O regions to be partially ordered. Its effects may go beyond the -CPU->Hardware interface and actually affect the hardware at some level. - -See the subsection "Acquires vs I/O accesses" for more information. - - =============================== IMPLICIT KERNEL MEMORY BARRIERS =============================== @@ -2317,75 +2302,6 @@ But it won't see any of: *E, *F or *G following RELEASE Q - -ACQUIRES VS I/O ACCESSES ------------------------- - -Under certain circumstances (especially involving NUMA), I/O accesses within -two spinlocked sections on two different CPUs may be seen as interleaved by the -PCI bridge, because the PCI bridge does not necessarily participate in the -cache-coherence protocol, and is therefore incapable of issuing the required -read memory barriers. - -For example: - - CPU 1 CPU 2 - =============================== =============================== - spin_lock(Q) - writel(0, ADDR) - writel(1, DATA); - spin_unlock(Q); - spin_lock(Q); - writel(4, ADDR); - writel(5, DATA); - spin_unlock(Q); - -may be seen by the PCI bridge as follows: - - STORE *ADDR = 0, STORE *ADDR = 4, STORE *DATA = 1, STORE *DATA = 5 - -which would probably cause the hardware to malfunction. - - -What is necessary here is to intervene with an mmiowb() before dropping the -spinlock, for example: - - CPU 1 CPU 2 - =============================== =============================== - spin_lock(Q) - writel(0, ADDR) - writel(1, DATA); - mmiowb(); - spin_unlock(Q); - spin_lock(Q); - writel(4, ADDR); - writel(5, DATA); - mmiowb(); - spin_unlock(Q); - -this will ensure that the two stores issued on CPU 1 appear at the PCI bridge -before either of the stores issued on CPU 2. - - -Furthermore, following a store by a load from the same device obviates the need -for the mmiowb(), because the load forces the store to complete before the load -is performed: - - CPU 1 CPU 2 - =============================== =============================== - spin_lock(Q) - writel(0, ADDR) - a = readl(DATA); - spin_unlock(Q); - spin_lock(Q); - writel(4, ADDR); - b = readl(DATA); - spin_unlock(Q); - - -See Documentation/driver-api/device-io.rst for more information. - - ================================= WHERE ARE MEMORY BARRIERS NEEDED? ================================= @@ -2532,16 +2448,9 @@ the device to malfunction. Inside of the Linux kernel, I/O should be done through the appropriate accessor routines - such as inb() or writel() - which know how to make such accesses appropriately sequential. While this, for the most part, renders the explicit -use of memory barriers unnecessary, there are a couple of situations where they -might be needed: - - (1) On some systems, I/O stores are not strongly ordered across all CPUs, and - so for _all_ general drivers locks should be used and mmiowb() must be - issued prior to unlocking the critical section. - - (2) If the accessor functions are used to refer to an I/O memory window with - relaxed memory access properties, then _mandatory_ memory barriers are - required to enforce ordering. +use of memory barriers unnecessary, if the accessor functions are used to refer +to an I/O memory window with relaxed memory access properties, then _mandatory_ +memory barriers are required to enforce ordering. See Documentation/driver-api/device-io.rst for more information. @@ -2586,8 +2495,7 @@ explicit barriers are used. Normally this won't be a problem because the I/O accesses done inside such sections will include synchronous load operations on strictly ordered I/O -registers that form implicit I/O barriers. If this isn't sufficient then an -mmiowb() may need to be used explicitly. +registers that form implicit I/O barriers. A similar situation may occur between an interrupt routine and two routines @@ -2687,9 +2595,6 @@ guarantees: All of these accessors assume that the underlying peripheral is little-endian, and will therefore perform byte-swapping operations on big-endian architectures. -Composing I/O ordering barriers with SMP ordering barriers and LOCK/UNLOCK -operations is a dangerous sport which may require the use of mmiowb(). See the -subsection "Acquires vs I/O accesses" for more information. ======================================== ASSUMED MINIMUM EXECUTION ORDERING MODEL -- cgit v1.2.3 From 5490c77d596ad220022637b3e277edb50bb3ae35 Mon Sep 17 00:00:00 2001 From: Christina Quast Date: Wed, 13 Mar 2019 15:20:40 +0100 Subject: dt-bindings: pinctrl: imx7d: Fix PAD_CTL_DSE_X* In the iMX7d datasheet, the PAD_CTL_DSE_X* values are different from the documentation. Changes since v2: * Changed patch title to 'dt-bindings: pinctrl: imx7d:' Signed-off-by: Christina Quast Reviewed-by: Rob Herring Acked-by: Dong Aisheng Signed-off-by: Linus Walleij --- Documentation/devicetree/bindings/pinctrl/fsl,imx7d-pinctrl.txt | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/pinctrl/fsl,imx7d-pinctrl.txt b/Documentation/devicetree/bindings/pinctrl/fsl,imx7d-pinctrl.txt index 6666277c3acb..8ac1d0851a0f 100644 --- a/Documentation/devicetree/bindings/pinctrl/fsl,imx7d-pinctrl.txt +++ b/Documentation/devicetree/bindings/pinctrl/fsl,imx7d-pinctrl.txt @@ -48,9 +48,9 @@ PAD_CTL_HYS (1 << 3) PAD_CTL_SRE_SLOW (1 << 2) PAD_CTL_SRE_FAST (0 << 2) PAD_CTL_DSE_X1 (0 << 0) -PAD_CTL_DSE_X2 (1 << 0) -PAD_CTL_DSE_X3 (2 << 0) -PAD_CTL_DSE_X4 (3 << 0) +PAD_CTL_DSE_X4 (1 << 0) +PAD_CTL_DSE_X2 (2 << 0) +PAD_CTL_DSE_X6 (3 << 0) Examples: While iomuxc-lpsr is intended to be used by dedicated peripherals to take -- cgit v1.2.3 From 26a944917989d57c0dddec284b3088fa31127717 Mon Sep 17 00:00:00 2001 From: Tom Zanussi Date: Sun, 31 Mar 2019 18:48:24 -0500 Subject: tracing: Add tracing/error_log Documentation Move most of the hist trigger extended error documentation to ftrace.rst and expand on it to fully document tracing/error_log. Link: http://lkml.kernel.org/r/c5d53c8f643ef6844d6ad8d0200c116936730b01.1554072478.git.tom.zanussi@linux.intel.com Acked-by: Masami Hiramatsu Acked-by: Namhyung Kim Signed-off-by: Tom Zanussi Signed-off-by: Steven Rostedt (VMware) --- Documentation/trace/ftrace.rst | 31 +++++++++++++++++++++++++++++++ Documentation/trace/histogram.rst | 16 ++-------------- 2 files changed, 33 insertions(+), 14 deletions(-) (limited to 'Documentation') diff --git a/Documentation/trace/ftrace.rst b/Documentation/trace/ftrace.rst index 7c5e6d6ab5d1..809b39d066ee 100644 --- a/Documentation/trace/ftrace.rst +++ b/Documentation/trace/ftrace.rst @@ -765,6 +765,37 @@ Here is the list of current tracers that may be configured. tracers from tracing simply echo "nop" into current_tracer. +Error conditions +---------------- + + For most ftrace commands, failure modes are obvious and communicated + using standard return codes. + + For other more involved commands, extended error information may be + available via the tracing/error_log file. For the commands that + support it, reading the tracing/error_log file after an error will + display more detailed information about what went wrong, if + information is available. The tracing/error_log file is a circular + error log displaying a small number (currently, 8) of ftrace errors + for the last (8) failed commands. + + The extended error information and usage takes the form shown in + this example:: + + # echo xxx > /sys/kernel/debug/tracing/events/sched/sched_wakeup/trigger + echo: write error: Invalid argument + + # cat /sys/kernel/debug/tracing/error_log + [ 5348.887237] location: error: Couldn't yyy: zzz + Command: xxx + ^ + [ 7517.023364] location: error: Bad rrr: sss + Command: ppp qqq + ^ + + To clear the error log, echo the empty string into it:: + + # echo > /sys/kernel/debug/tracing/error_log Examples of using the tracer ---------------------------- diff --git a/Documentation/trace/histogram.rst b/Documentation/trace/histogram.rst index 0ea59d45aef1..7612c7ad5715 100644 --- a/Documentation/trace/histogram.rst +++ b/Documentation/trace/histogram.rst @@ -199,20 +199,8 @@ Extended error information For some error conditions encountered when invoking a hist trigger command, extended error information is available via the - corresponding event's 'hist' file. Reading the hist file after an - error will display more detailed information about what went wrong, - if information is available. This extended error information will - be available until the next hist trigger command for that event. - - If available for a given error condition, the extended error - information and usage takes the following form:: - - # echo xxx > /sys/kernel/debug/tracing/events/sched/sched_wakeup/trigger - echo: write error: Invalid argument - - # cat /sys/kernel/debug/tracing/events/sched/sched_wakeup/hist - ERROR: Couldn't yyy: zzz - Last command: xxx + tracing/error_log file. See Error Conditions in + :file:`Documentation/trace/ftrace.rst` for details. 6.2 'hist' trigger examples --------------------------- -- cgit v1.2.3 From 258bbef06ce962dbe1864c379aa90d84ff57f819 Mon Sep 17 00:00:00 2001 From: Manivannan Sadhasivam Date: Fri, 15 Feb 2019 11:19:54 +0530 Subject: dt-bindings: reset: Add HI3670 reset controller binding HI3670 SoC is architecturally same as the HI3660 SoC. Hence, the same driver is reused for HI3670 SoC and the binding is documented here which uses the fallback approach. Signed-off-by: Manivannan Sadhasivam Acked-by: Philipp Zabel Reviewed-by: Rob Herring Signed-off-by: Wei Xu --- Documentation/devicetree/bindings/reset/hisilicon,hi3660-reset.txt | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/reset/hisilicon,hi3660-reset.txt b/Documentation/devicetree/bindings/reset/hisilicon,hi3660-reset.txt index 2bf3344b2a02..2df4bddeb688 100644 --- a/Documentation/devicetree/bindings/reset/hisilicon,hi3660-reset.txt +++ b/Documentation/devicetree/bindings/reset/hisilicon,hi3660-reset.txt @@ -5,11 +5,12 @@ Please also refer to reset.txt in this directory for common reset controller binding usage. The reset controller registers are part of the system-ctl block on -hi3660 SoC. +hi3660 and hi3670 SoCs. Required properties: -- compatible: should be - "hisilicon,hi3660-reset" +- compatible: should be one of the following: + "hisilicon,hi3660-reset" for HI3660 + "hisilicon,hi3670-reset", "hisilicon,hi3660-reset" for HI3670 - hisi,rst-syscon: phandle of the reset's syscon. - #reset-cells : Specifies the number of cells needed to encode a reset source. The type shall be a and the value shall be 2. -- cgit v1.2.3 From 8aa576a8ee1ba1f76785ed3cd12de20121971854 Mon Sep 17 00:00:00 2001 From: Manivannan Sadhasivam Date: Thu, 28 Feb 2019 21:15:09 +0530 Subject: dt-bindings: mmc: Add HI3670 MMC controller binding HI3670 SoC is architecturally same as the HI3660 SoC. Hence, the same K3 specific designware driver is reused for HI3670 SoC and the binding is documented with fallback approach for compatible property. Signed-off-by: Manivannan Sadhasivam Reviewed-by: Rob Herring Signed-off-by: Wei Xu --- Documentation/devicetree/bindings/mmc/k3-dw-mshc.txt | 2 ++ 1 file changed, 2 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mmc/k3-dw-mshc.txt b/Documentation/devicetree/bindings/mmc/k3-dw-mshc.txt index 07242d141773..36c4bea675d5 100644 --- a/Documentation/devicetree/bindings/mmc/k3-dw-mshc.txt +++ b/Documentation/devicetree/bindings/mmc/k3-dw-mshc.txt @@ -13,6 +13,8 @@ Required Properties: * compatible: should be one of the following. - "hisilicon,hi3660-dw-mshc": for controllers with hi3660 specific extensions. + - "hisilicon,hi3670-dw-mshc", "hisilicon,hi3660-dw-mshc": for controllers + with hi3670 specific extensions. - "hisilicon,hi4511-dw-mshc": for controllers with hi4511 specific extensions. - "hisilicon,hi6220-dw-mshc": for controllers with hi6220 specific extensions. -- cgit v1.2.3 From d7e02a931235de0779d44c6f8d211df0eca304b8 Mon Sep 17 00:00:00 2001 From: Christoph Hellwig Date: Wed, 13 Mar 2019 18:45:21 +0100 Subject: dma-mapping: remove leftover NULL device support Most dma_map_ops implementations already had some issues with a NULL device, or did simply crash if one was fed to them. Now that we have cleaned up all the obvious offenders we can stop to pretend we support this mode. Signed-off-by: Christoph Hellwig --- Documentation/DMA-API-HOWTO.txt | 13 ++++++------- include/linux/dma-mapping.h | 6 +++--- kernel/dma/direct.c | 2 +- 3 files changed, 10 insertions(+), 11 deletions(-) (limited to 'Documentation') diff --git a/Documentation/DMA-API-HOWTO.txt b/Documentation/DMA-API-HOWTO.txt index 1a721d0f35c8..0e98cf7466dd 100644 --- a/Documentation/DMA-API-HOWTO.txt +++ b/Documentation/DMA-API-HOWTO.txt @@ -365,13 +365,12 @@ __get_free_pages() (but takes size instead of a page order). If your driver needs regions sized smaller than a page, you may prefer using the dma_pool interface, described below. -The consistent DMA mapping interfaces, for non-NULL dev, will by -default return a DMA address which is 32-bit addressable. Even if the -device indicates (via DMA mask) that it may address the upper 32-bits, -consistent allocation will only return > 32-bit addresses for DMA if -the consistent DMA mask has been explicitly changed via -dma_set_coherent_mask(). This is true of the dma_pool interface as -well. +The consistent DMA mapping interfaces, will by default return a DMA address +which is 32-bit addressable. Even if the device indicates (via the DMA mask) +that it may address the upper 32-bits, consistent allocation will only +return > 32-bit addresses for DMA if the consistent DMA mask has been +explicitly changed via dma_set_coherent_mask(). This is true of the +dma_pool interface as well. dma_alloc_coherent() returns two values: the virtual address which you can use to access it from the CPU and dma_handle which you pass to the diff --git a/include/linux/dma-mapping.h b/include/linux/dma-mapping.h index 75e60be91e5f..6309a721394b 100644 --- a/include/linux/dma-mapping.h +++ b/include/linux/dma-mapping.h @@ -267,9 +267,9 @@ size_t dma_direct_max_mapping_size(struct device *dev); static inline const struct dma_map_ops *get_dma_ops(struct device *dev) { - if (dev && dev->dma_ops) + if (dev->dma_ops) return dev->dma_ops; - return get_arch_dma_ops(dev ? dev->bus : NULL); + return get_arch_dma_ops(dev->bus); } static inline void set_dma_ops(struct device *dev, @@ -650,7 +650,7 @@ static inline void dma_free_coherent(struct device *dev, size_t size, static inline u64 dma_get_mask(struct device *dev) { - if (dev && dev->dma_mask && *dev->dma_mask) + if (dev->dma_mask && *dev->dma_mask) return *dev->dma_mask; return DMA_BIT_MASK(32); } diff --git a/kernel/dma/direct.c b/kernel/dma/direct.c index fcdb23e8d2fc..2c2772e9702a 100644 --- a/kernel/dma/direct.c +++ b/kernel/dma/direct.c @@ -311,7 +311,7 @@ static inline bool dma_direct_possible(struct device *dev, dma_addr_t dma_addr, size_t size) { return swiotlb_force != SWIOTLB_FORCE && - (!dev || dma_capable(dev, dma_addr, size)); + dma_capable(dev, dma_addr, size); } dma_addr_t dma_direct_map_page(struct device *dev, struct page *page, -- cgit v1.2.3 From bc236d6fb5617e990f692efe91ef2be9adf0c1a7 Mon Sep 17 00:00:00 2001 From: Fabien Parent Date: Sat, 23 Mar 2019 22:16:03 +0100 Subject: pinctrl: mt65xx: add OF bindings for MT8516 Add binding documentation of pinctrl-mt65xx for MT8516 SoC. Signed-off-by: Fabien Parent Acked-by: Rob Herring Signed-off-by: Linus Walleij --- Documentation/devicetree/bindings/pinctrl/pinctrl-mt65xx.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/pinctrl/pinctrl-mt65xx.txt b/Documentation/devicetree/bindings/pinctrl/pinctrl-mt65xx.txt index e7d6f81c227f..205be98ae078 100644 --- a/Documentation/devicetree/bindings/pinctrl/pinctrl-mt65xx.txt +++ b/Documentation/devicetree/bindings/pinctrl/pinctrl-mt65xx.txt @@ -11,6 +11,7 @@ Required properties: "mediatek,mt8127-pinctrl", compatible with mt8127 pinctrl. "mediatek,mt8135-pinctrl", compatible with mt8135 pinctrl. "mediatek,mt8173-pinctrl", compatible with mt8173 pinctrl. + "mediatek,mt8516-pinctrl", compatible with mt8516 pinctrl. - pins-are-numbered: Specify the subnodes are using numbered pinmux to specify pins. - gpio-controller : Marks the device node as a gpio controller. -- cgit v1.2.3 From ad4b009f2d7b06b86d18c2aa3e427b9e96657b48 Mon Sep 17 00:00:00 2001 From: Jonathan Neuschäfer Date: Sat, 6 Apr 2019 12:15:27 +0200 Subject: Documentation: kernel-docs: Remove entry for vfs.txt MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit It's unnecessary to point to an external mirror of the Documentation directory. Jonathan Corbet writes in favor of removing this entry, instead of moving it under "Docs at the Linux Kernel tree": > We don't want to turn kernel-docs.rst into yet another out-of-date > index for the rest of Documentation/, and the removal of the external > URL takes away the only bit of additional information that this entry > offers. Signed-off-by: Jonathan Neuschäfer Signed-off-by: Jonathan Corbet --- Documentation/process/kernel-docs.rst | 12 ------------ 1 file changed, 12 deletions(-) (limited to 'Documentation') diff --git a/Documentation/process/kernel-docs.rst b/Documentation/process/kernel-docs.rst index ab12dddc773e..7a45a8e36ea7 100644 --- a/Documentation/process/kernel-docs.rst +++ b/Documentation/process/kernel-docs.rst @@ -95,18 +95,6 @@ On-line docs [...]. This paper examines some common problems for submitting larger changes and some strategies to avoid problems. - * Title: **Overview of the Virtual File System** - - :Author: Richard Gooch. - :URL: http://www.mjmwired.net/kernel/Documentation/filesystems/vfs.txt - :Date: 2007 - :Keywords: VFS, File System, mounting filesystems, opening files, - dentries, dcache. - :Description: Brief introduction to the Linux Virtual File System. - What is it, how it works, operations taken when opening a file or - mounting a file system and description of important data - structures explaining the purpose of each of their entries. - * Title: **Linux Device Drivers, Third Edition** :Author: Jonathan Corbet, Alessandro Rubini, Greg Kroah-Hartman -- cgit v1.2.3 From 583b3845915de3b537560d4ab543cb3a9d8b5699 Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Mon, 8 Apr 2019 17:18:27 +0800 Subject: docs/zh_CN: correct a word in managment-style. "made up" used here means 'fictional' instead of 'consist of'. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/management-style.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/management-style.rst b/Documentation/translations/zh_CN/process/management-style.rst index 63f9a73ff19c..a181fa56d19e 100644 --- a/Documentation/translations/zh_CN/process/management-style.rst +++ b/Documentation/translations/zh_CN/process/management-style.rst @@ -8,7 +8,7 @@ Linux内核管理风格 ================= -这是一个简短的文档,描述了Linux内核的首选(或组成,取决于您问谁)管理风格。 +这是一个简短的文档,描述了Linux内核首选的(或胡编的,取决于您问谁)管理风格。 它的目的是在某种程度上参照 :ref:`process/coding-style.rst ` 主要是为了避免反复回答 [#cnf1]_ 相同(或类似)的问题。 -- cgit v1.2.3 From eebf4dd452377921e3a2635f0f5df2042470faef Mon Sep 17 00:00:00 2001 From: "Tobin C. Harding" Date: Fri, 5 Apr 2019 12:58:56 +1100 Subject: kselftest: Add test module framework header kselftest runs as a userspace process. Sometimes we need to test things from kernel space. One way of doing this is by creating a test module. Currently doing so requires developers to write a bunch of boiler plate in the module if kselftest is to be used to run the tests. This means we currently have a load of duplicate code to achieve these ends. If we have a uniform method for implementing test modules then we can reduce code duplication, ensure uniformity in the test framework, ease code maintenance, and reduce the work required to create tests. This all helps to encourage developers to write and run tests. Add a C header file that can be included in test modules. This provides a single point for common test functions/macros. Implement a few macros that make up the start of the test framework. Add documentation for new kselftest header to kselftest documentation. Acked-by: Kees Cook Signed-off-by: Tobin C. Harding Signed-off-by: Shuah Khan --- Documentation/dev-tools/kselftest.rst | 94 +++++++++++++++++++++++++++++- tools/testing/selftests/kselftest_module.h | 48 +++++++++++++++ 2 files changed, 140 insertions(+), 2 deletions(-) create mode 100644 tools/testing/selftests/kselftest_module.h (limited to 'Documentation') diff --git a/Documentation/dev-tools/kselftest.rst b/Documentation/dev-tools/kselftest.rst index 7756f7a7c23b..c8c03388b9de 100644 --- a/Documentation/dev-tools/kselftest.rst +++ b/Documentation/dev-tools/kselftest.rst @@ -14,6 +14,10 @@ in safe mode with a limited scope. In limited mode, cpu-hotplug test is run on a single cpu as opposed to all hotplug capable cpus, and memory hotplug test is run on 2% of hotplug capable memory instead of 10%. +kselftest runs as a userspace process. Tests that can be written/run in +userspace may wish to use the `Test Harness`_. Tests that need to be +run in kernel space may wish to use a `Test Module`_. + Running the selftests (hotplug tests are run in limited mode) ============================================================= @@ -161,11 +165,97 @@ Contributing new tests (details) e.g: tools/testing/selftests/android/config +Test Module +=========== + +Kselftest tests the kernel from userspace. Sometimes things need +testing from within the kernel, one method of doing this is to create a +test module. We can tie the module into the kselftest framework by +using a shell script test runner. ``kselftest_module.sh`` is designed +to facilitate this process. There is also a header file provided to +assist writing kernel modules that are for use with kselftest: + +- ``tools/testing/kselftest/kselftest_module.h`` +- ``tools/testing/kselftest/kselftest_module.sh`` + +How to use +---------- + +Here we show the typical steps to create a test module and tie it into +kselftest. We use kselftests for lib/ as an example. + +1. Create the test module + +2. Create the test script that will run (load/unload) the module + e.g. ``tools/testing/selftests/lib/printf.sh`` + +3. Add line to config file e.g. ``tools/testing/selftests/lib/config`` + +4. Add test script to makefile e.g. ``tools/testing/selftests/lib/Makefile`` + +5. Verify it works: + +.. code-block:: sh + + # Assumes you have booted a fresh build of this kernel tree + cd /path/to/linux/tree + make kselftest-merge + make modules + sudo make modules_install + make TARGETS=lib kselftest + +Example Module +-------------- + +A bare bones test module might look like this: + +.. code-block:: c + + // SPDX-License-Identifier: GPL-2.0+ + + #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt + + #include "../tools/testing/selftests/kselftest_module.h" + + KSTM_MODULE_GLOBALS(); + + /* + * Kernel module for testing the foobinator + */ + + static int __init test_function() + { + ... + } + + static void __init selftest(void) + { + KSTM_CHECK_ZERO(do_test_case("", 0)); + } + + KSTM_MODULE_LOADERS(test_foo); + MODULE_AUTHOR("John Developer "); + MODULE_LICENSE("GPL"); + +Example test script +------------------- + +.. code-block:: sh + + #!/bin/bash + # SPDX-License-Identifier: GPL-2.0+ + $(dirname $0)/../kselftest_module.sh "foo" test_foo + + Test Harness ============ -The kselftest_harness.h file contains useful helpers to build tests. The tests -from tools/testing/selftests/seccomp/seccomp_bpf.c can be used as example. +The kselftest_harness.h file contains useful helpers to build tests. The +test harness is for userspace testing, for kernel space testing see `Test +Module`_ above. + +The tests from tools/testing/selftests/seccomp/seccomp_bpf.c can be used as +example. Example ------- diff --git a/tools/testing/selftests/kselftest_module.h b/tools/testing/selftests/kselftest_module.h new file mode 100644 index 000000000000..e8eafaf0941a --- /dev/null +++ b/tools/testing/selftests/kselftest_module.h @@ -0,0 +1,48 @@ +/* SPDX-License-Identifier: GPL-2.0+ */ +#ifndef __KSELFTEST_MODULE_H +#define __KSELFTEST_MODULE_H + +#include + +/* + * Test framework for writing test modules to be loaded by kselftest. + * See Documentation/dev-tools/kselftest.rst for an example test module. + */ + +#define KSTM_MODULE_GLOBALS() \ +static unsigned int total_tests __initdata; \ +static unsigned int failed_tests __initdata + +#define KSTM_CHECK_ZERO(x) do { \ + total_tests++; \ + if (x) { \ + pr_warn("TC failed at %s:%d\n", __func__, __LINE__); \ + failed_tests++; \ + } \ +} while (0) + +static inline int kstm_report(unsigned int total_tests, unsigned int failed_tests) +{ + if (failed_tests == 0) + pr_info("all %u tests passed\n", total_tests); + else + pr_warn("failed %u out of %u tests\n", failed_tests, total_tests); + + return failed_tests ? -EINVAL : 0; +} + +#define KSTM_MODULE_LOADERS(__module) \ +static int __init __module##_init(void) \ +{ \ + pr_info("loaded.\n"); \ + selftest(); \ + return kstm_report(total_tests, failed_tests); \ +} \ +static void __exit __module##_exit(void) \ +{ \ + pr_info("unloaded.\n"); \ +} \ +module_init(__module##_init); \ +module_exit(__module##_exit) + +#endif /* __KSELFTEST_MODULE_H */ -- cgit v1.2.3 From be0faac952e1643237931956ab8ec5ceaeda41b0 Mon Sep 17 00:00:00 2001 From: Shalom Toledo Date: Mon, 8 Apr 2019 06:59:36 +0000 Subject: Documentation: networking: devlink-info-versions: Add fw.psid Add firmware parameter id (fw.psid). Signed-off-by: Shalom Toledo Acked-by: Jiri Pirko Signed-off-by: Ido Schimmel Acked-by: Jakub Kicinski Signed-off-by: David S. Miller --- Documentation/networking/devlink-info-versions.rst | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'Documentation') diff --git a/Documentation/networking/devlink-info-versions.rst b/Documentation/networking/devlink-info-versions.rst index c79ad8593383..4316342b7746 100644 --- a/Documentation/networking/devlink-info-versions.rst +++ b/Documentation/networking/devlink-info-versions.rst @@ -41,3 +41,8 @@ fw.ncsi Version of the software responsible for supporting/handling the Network Controller Sideband Interface. + +fw.psid +======= + +Unique identifier of the firmware parameter set. -- cgit v1.2.3 From 2c98d9e47533b35f583b330bc3380f566589a9bf Mon Sep 17 00:00:00 2001 From: Clément Péron Date: Mon, 8 Apr 2019 17:27:51 +0200 Subject: dt-bindings: vendor-prefixes: add AZW MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Shenzhen AZW Technology Co. Ltd. is a manufacturer specialized in Android smart TV boxes, Intel mini PCs and home cloud TV boxes with NAS. Add the vendor prefix for AZW. Signed-off-by: Clément Péron Reviewed-by: Robin Murphy Signed-off-by: Maxime Ripard --- Documentation/devicetree/bindings/vendor-prefixes.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/vendor-prefixes.txt b/Documentation/devicetree/bindings/vendor-prefixes.txt index 208889476a38..4933403c4b57 100644 --- a/Documentation/devicetree/bindings/vendor-prefixes.txt +++ b/Documentation/devicetree/bindings/vendor-prefixes.txt @@ -54,6 +54,7 @@ avic Shanghai AVIC Optoelectronics Co., Ltd. avnet Avnet, Inc. axentia Axentia Technologies AB axis Axis Communications AB +azw Shenzhen AZW Technology Co., Ltd. bananapi BIPAI KEJI LIMITED bhf Beckhoff Automation GmbH & Co. KG bitmain Bitmain Technologies -- cgit v1.2.3 From 1e7011fad854e64a7a30a8c4f217229c250fc8c6 Mon Sep 17 00:00:00 2001 From: Clément Péron Date: Mon, 8 Apr 2019 17:27:53 +0200 Subject: dt-bindings: arm: sunxi: Add Beelink GS1 board MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Beelink GS1 device-tree has been introduced. Add it to the sunxi yaml documentation. Signed-off-by: Clément Péron Signed-off-by: Maxime Ripard --- Documentation/devicetree/bindings/arm/sunxi.yaml | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/sunxi.yaml b/Documentation/devicetree/bindings/arm/sunxi.yaml index 11563d3f7c65..9ab9b266881d 100644 --- a/Documentation/devicetree/bindings/arm/sunxi.yaml +++ b/Documentation/devicetree/bindings/arm/sunxi.yaml @@ -136,6 +136,11 @@ properties: - const: lemaker,bananapro - const: allwinner,sun7i-a20 + - description: Beelink GS1 + items: + - const: azw,beelink-gs1 + - const: allwinner,sun50i-h6 + - description: Beelink X2 items: - const: roofull,beelink-x2 -- cgit v1.2.3 From 493ab13a5d382f1a06c4cb791f277acec55b9250 Mon Sep 17 00:00:00 2001 From: Ondrej Jirman Date: Tue, 9 Apr 2019 02:24:40 +0200 Subject: dt-bindings: sunxi: Add compatible for OrangePi 3 board Add new Xunlong Orange Pi 3 board compatible string to the bindings documentation. Signed-off-by: Ondrej Jirman Signed-off-by: Maxime Ripard --- Documentation/devicetree/bindings/arm/sunxi.yaml | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/sunxi.yaml b/Documentation/devicetree/bindings/arm/sunxi.yaml index 9ab9b266881d..285f4fc8519d 100644 --- a/Documentation/devicetree/bindings/arm/sunxi.yaml +++ b/Documentation/devicetree/bindings/arm/sunxi.yaml @@ -716,6 +716,11 @@ properties: - const: xunlong,orangepi-2 - const: allwinner,sun8i-h3 + - description: Xunlong OrangePi 3 + items: + - const: xunlong,orangepi-3 + - const: allwinner,sun50i-h6 + - description: Xunlong OrangePi Lite items: - const: xunlong,orangepi-lite -- cgit v1.2.3 From 0d413829bd20d5563c2c3287479a7348810cb13f Mon Sep 17 00:00:00 2001 From: Minwoo Im Date: Sun, 7 Apr 2019 17:19:38 +0900 Subject: block: null: Add documentation for "zone_nr_conv" param zone_nr_conv module parameter was introduced by a commit ea2c18e1("null_blk: Add conventional zone configuration for zoned support"). This patch describes "zone_nr_conv" module parameter to the document. Reviewed-by: Chaitanya Kulkarni Signed-off-by: Minwoo Im Signed-off-by: Jens Axboe --- Documentation/block/null_blk.txt | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'Documentation') diff --git a/Documentation/block/null_blk.txt b/Documentation/block/null_blk.txt index 4cad1024fff7..41f0a3d33bbd 100644 --- a/Documentation/block/null_blk.txt +++ b/Documentation/block/null_blk.txt @@ -93,3 +93,7 @@ zoned=[0/1]: Default: 0 zone_size=[MB]: Default: 256 Per zone size when exposed as a zoned block device. Must be a power of two. + +zone_nr_conv=[nr_conv]: Default: 0 + The number of conventional zones to create when block device is zoned. If + zone_nr_conv >= nr_zones, it will be reduced to nr_zones - 1. -- cgit v1.2.3 From 6dd677a044e606fd343e31c2108b13d74aec1ca5 Mon Sep 17 00:00:00 2001 From: Sebastian Andrzej Siewior Date: Wed, 3 Apr 2019 18:41:31 +0200 Subject: x86/fpu: Remove fpu__restore() MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit There are no users of fpu__restore() so it is time to remove it. The comment regarding fpu__restore() and TS bit is stale since commit b3b0870ef3ffe ("i387: do not preload FPU state at task switch time") and has no meaning since. Signed-off-by: Sebastian Andrzej Siewior Signed-off-by: Borislav Petkov Reviewed-by: Dave Hansen Reviewed-by: Thomas Gleixner Cc: Andy Lutomirski Cc: Aubrey Li Cc: Babu Moger Cc: "Chang S. Bae" Cc: Dmitry Safonov Cc: "H. Peter Anvin" Cc: Ingo Molnar Cc: Jann Horn Cc: "Jason A. Donenfeld" Cc: Joerg Roedel Cc: Jonathan Corbet Cc: kvm ML Cc: linux-doc@vger.kernel.org Cc: Nicolai Stange Cc: Paolo Bonzini Cc: Radim Krčmář Cc: Rik van Riel Cc: x86-ml Link: https://lkml.kernel.org/r/20190403164156.19645-3-bigeasy@linutronix.de --- Documentation/preempt-locking.txt | 1 - arch/x86/include/asm/fpu/internal.h | 1 - arch/x86/kernel/fpu/core.c | 24 ------------------------ arch/x86/kernel/process_32.c | 4 +--- arch/x86/kernel/process_64.c | 4 +--- 5 files changed, 2 insertions(+), 32 deletions(-) (limited to 'Documentation') diff --git a/Documentation/preempt-locking.txt b/Documentation/preempt-locking.txt index 509f5a422d57..dce336134e54 100644 --- a/Documentation/preempt-locking.txt +++ b/Documentation/preempt-locking.txt @@ -52,7 +52,6 @@ preemption must be disabled around such regions. Note, some FPU functions are already explicitly preempt safe. For example, kernel_fpu_begin and kernel_fpu_end will disable and enable preemption. -However, fpu__restore() must be called with preemption disabled. RULE #3: Lock acquire and release must be performed by same task diff --git a/arch/x86/include/asm/fpu/internal.h b/arch/x86/include/asm/fpu/internal.h index fb04a3ded7dd..75a1d5f712ee 100644 --- a/arch/x86/include/asm/fpu/internal.h +++ b/arch/x86/include/asm/fpu/internal.h @@ -28,7 +28,6 @@ extern void fpu__initialize(struct fpu *fpu); extern void fpu__prepare_read(struct fpu *fpu); extern void fpu__prepare_write(struct fpu *fpu); extern void fpu__save(struct fpu *fpu); -extern void fpu__restore(struct fpu *fpu); extern int fpu__restore_sig(void __user *buf, int ia32_frame); extern void fpu__drop(struct fpu *fpu); extern int fpu__copy(struct fpu *dst_fpu, struct fpu *src_fpu); diff --git a/arch/x86/kernel/fpu/core.c b/arch/x86/kernel/fpu/core.c index 2e5003fef51a..1d3ae7988f7f 100644 --- a/arch/x86/kernel/fpu/core.c +++ b/arch/x86/kernel/fpu/core.c @@ -303,30 +303,6 @@ void fpu__prepare_write(struct fpu *fpu) } } -/* - * 'fpu__restore()' is called to copy FPU registers from - * the FPU fpstate to the live hw registers and to activate - * access to the hardware registers, so that FPU instructions - * can be used afterwards. - * - * Must be called with kernel preemption disabled (for example - * with local interrupts disabled, as it is in the case of - * do_device_not_available()). - */ -void fpu__restore(struct fpu *fpu) -{ - fpu__initialize(fpu); - - /* Avoid __kernel_fpu_begin() right after fpregs_activate() */ - kernel_fpu_disable(); - trace_x86_fpu_before_restore(fpu); - fpregs_activate(fpu); - copy_kernel_to_fpregs(&fpu->state); - trace_x86_fpu_after_restore(fpu); - kernel_fpu_enable(); -} -EXPORT_SYMBOL_GPL(fpu__restore); - /* * Drops current FPU state: deactivates the fpregs and * the fpstate. NOTE: it still leaves previous contents diff --git a/arch/x86/kernel/process_32.c b/arch/x86/kernel/process_32.c index e471d8e6f0b2..7888a41a03cd 100644 --- a/arch/x86/kernel/process_32.c +++ b/arch/x86/kernel/process_32.c @@ -267,9 +267,7 @@ __switch_to(struct task_struct *prev_p, struct task_struct *next_p) /* * Leave lazy mode, flushing any hypercalls made here. * This must be done before restoring TLS segments so - * the GDT and LDT are properly updated, and must be - * done before fpu__restore(), so the TS bit is up - * to date. + * the GDT and LDT are properly updated. */ arch_end_context_switch(next_p); diff --git a/arch/x86/kernel/process_64.c b/arch/x86/kernel/process_64.c index 6a62f4af9fcf..e1983b3a16c4 100644 --- a/arch/x86/kernel/process_64.c +++ b/arch/x86/kernel/process_64.c @@ -538,9 +538,7 @@ __switch_to(struct task_struct *prev_p, struct task_struct *next_p) /* * Leave lazy mode, flushing any hypercalls made here. This * must be done after loading TLS entries in the GDT but before - * loading segments that might reference them, and and it must - * be done before fpu__restore(), so the TS bit is up to - * date. + * loading segments that might reference them. */ arch_end_context_switch(next_p); -- cgit v1.2.3 From 49afe7e99350b8eaf586ffdebe0c1c48c6d339c0 Mon Sep 17 00:00:00 2001 From: "Tobin C. Harding" Date: Tue, 9 Apr 2019 10:43:56 +1000 Subject: docs: Fix spelling mistake Documentation contains a spelling mistake / typo. s/descibed/described/ Fix spelling mistake. Signed-off-by: Tobin C. Harding Signed-off-by: Jonathan Corbet --- Documentation/process/howto.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/process/howto.rst b/Documentation/process/howto.rst index ad2b6c852b95..6ab75c11d2c3 100644 --- a/Documentation/process/howto.rst +++ b/Documentation/process/howto.rst @@ -62,7 +62,7 @@ Legal Issues The Linux kernel source code is released under the GPL. Please see the file COPYING in the main directory of the source tree. The Linux kernel licensing rules and how to use `SPDX `_ identifiers in source code are -descibed in :ref:`Documentation/process/license-rules.rst `. +described in :ref:`Documentation/process/license-rules.rst `. If you have further questions about the license, please contact a lawyer, and do not ask on the Linux kernel mailing list. The people on the mailing lists are not lawyers, and you should not rely on their statements on legal matters. -- cgit v1.2.3 From 66e9c46c5cdbd9767d730c88049e1ef0438f749a Mon Sep 17 00:00:00 2001 From: "Tobin C. Harding" Date: Tue, 9 Apr 2019 10:43:59 +1000 Subject: docs: Use reference to link to rst file Current document includes the path to an RST doc file. Since this is an RST file we can make this a link. Keeps the path as the link title since that what the original author wrote. Use reference to link to rst file. Signed-off-by: Tobin C. Harding Signed-off-by: Jonathan Corbet --- Documentation/vm/numa.rst | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/vm/numa.rst b/Documentation/vm/numa.rst index 185d8a568168..5cae13e9a08b 100644 --- a/Documentation/vm/numa.rst +++ b/Documentation/vm/numa.rst @@ -109,8 +109,8 @@ System administrators and application designers can restrict a task's migration to improve NUMA locality using various CPU affinity command line interfaces, such as taskset(1) and numactl(1), and program interfaces such as sched_setaffinity(2). Further, one can modify the kernel's default local -allocation behavior using Linux NUMA memory policy. -[see Documentation/admin-guide/mm/numa_memory_policy.rst.] +allocation behavior using Linux NUMA memory policy. [see +:ref:`Documentation/admin-guide/mm/numa_memory_policy.rst `]. System administrators can restrict the CPUs and nodes' memories that a non- privileged user can specify in the scheduling or NUMA commands and functions -- cgit v1.2.3 From 2e220e6eb3ce97af898046a78725715b6898fe23 Mon Sep 17 00:00:00 2001 From: Michael Hennerich Date: Tue, 9 Apr 2019 08:24:40 +0200 Subject: power: supply: ltc3651-charger: Fix device name There never was a device called LTC3651, it always was just LT3651. This circumstance makes it pretty difficult to identify what this driver is meant to control.channges since Signed-off-by: Michael Hennerich Signed-off-by: Sebastian Reichel --- .../bindings/power/supply/ltc3651-charger.txt | 10 +- drivers/power/supply/Kconfig | 8 +- drivers/power/supply/Makefile | 2 +- drivers/power/supply/ltc3651-charger.c | 123 ++++++++++----------- 4 files changed, 71 insertions(+), 72 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/power/supply/ltc3651-charger.txt b/Documentation/devicetree/bindings/power/supply/ltc3651-charger.txt index 71f2840e8209..40811ff8de10 100644 --- a/Documentation/devicetree/bindings/power/supply/ltc3651-charger.txt +++ b/Documentation/devicetree/bindings/power/supply/ltc3651-charger.txt @@ -1,14 +1,16 @@ -ltc3651-charger +Analog Devices LT3651 Charger Power Supply bindings: lt3651-charger Required properties: - - compatible: "lltc,ltc3651-charger" +- compatible: Should contain one of the following: + * "lltc,ltc3651-charger", (DEPRECATED: Use "lltc,lt3651-charger") + * "lltc,lt3651-charger" - lltc,acpr-gpios: Connect to ACPR output. See remark below. Optional properties: - lltc,fault-gpios: Connect to FAULT output. See remark below. - lltc,chrg-gpios: Connect to CHRG output. See remark below. -The ltc3651 outputs are open-drain type and active low. The driver assumes the +The lt3651 outputs are open-drain type and active low. The driver assumes the GPIO reports "active" when the output is asserted, so if the pins have been connected directly, the GPIO flags should be set to active low also. @@ -20,7 +22,7 @@ attributes to detect changes. Example: charger: battery-charger { - compatible = "lltc,ltc3651-charger"; + compatible = "lltc,lt3651-charger"; lltc,acpr-gpios = <&gpio0 68 GPIO_ACTIVE_LOW>; lltc,fault-gpios = <&gpio0 64 GPIO_ACTIVE_LOW>; lltc,chrg-gpios = <&gpio0 63 GPIO_ACTIVE_LOW>; diff --git a/drivers/power/supply/Kconfig b/drivers/power/supply/Kconfig index e901b9879e7e..e907521a7166 100644 --- a/drivers/power/supply/Kconfig +++ b/drivers/power/supply/Kconfig @@ -475,12 +475,12 @@ config CHARGER_MANAGER runtime and in suspend-to-RAM by waking up the system periodically with help of suspend_again support. -config CHARGER_LTC3651 - tristate "LTC3651 charger" +config CHARGER_LT3651 + tristate "Analog Devices LT3651 charger" depends on GPIOLIB help - Say Y to include support for the LTC3651 battery charger which reports - its status via GPIO lines. + Say Y to include support for the Analog Devices (Linear Technology) + LT3651 battery charger which reports its status via GPIO lines. config CHARGER_MAX14577 tristate "Maxim MAX14577/77836 battery charger driver" diff --git a/drivers/power/supply/Makefile b/drivers/power/supply/Makefile index b731c2a9b695..714c6029cff7 100644 --- a/drivers/power/supply/Makefile +++ b/drivers/power/supply/Makefile @@ -67,7 +67,7 @@ obj-$(CONFIG_CHARGER_LP8727) += lp8727_charger.o obj-$(CONFIG_CHARGER_LP8788) += lp8788-charger.o obj-$(CONFIG_CHARGER_GPIO) += gpio-charger.o obj-$(CONFIG_CHARGER_MANAGER) += charger-manager.o -obj-$(CONFIG_CHARGER_LTC3651) += ltc3651-charger.o +obj-$(CONFIG_CHARGER_LT3651) += ltc3651-charger.o obj-$(CONFIG_CHARGER_MAX14577) += max14577_charger.o obj-$(CONFIG_CHARGER_DETECTOR_MAX14656) += max14656_charger_detector.o obj-$(CONFIG_CHARGER_MAX77693) += max77693_charger.o diff --git a/drivers/power/supply/ltc3651-charger.c b/drivers/power/supply/ltc3651-charger.c index eea63ff211c4..8de500ffad95 100644 --- a/drivers/power/supply/ltc3651-charger.c +++ b/drivers/power/supply/ltc3651-charger.c @@ -1,11 +1,7 @@ +// SPDX-License-Identifier: GPL-2.0+ /* + * Driver for Analog Devices (Linear Technology) LT3651 charger IC. * Copyright (C) 2017, Topic Embedded Products - * Driver for LTC3651 charger IC. - * - * This program is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License as published by the - * Free Software Foundation; either version 2 of the License, or (at your - * option) any later version. */ #include @@ -19,7 +15,7 @@ #include #include -struct ltc3651_charger { +struct lt3651_charger { struct power_supply *charger; struct power_supply_desc charger_desc; struct gpio_desc *acpr_gpio; @@ -27,7 +23,7 @@ struct ltc3651_charger { struct gpio_desc *chrg_gpio; }; -static irqreturn_t ltc3651_charger_irq(int irq, void *devid) +static irqreturn_t lt3651_charger_irq(int irq, void *devid) { struct power_supply *charger = devid; @@ -36,37 +32,37 @@ static irqreturn_t ltc3651_charger_irq(int irq, void *devid) return IRQ_HANDLED; } -static inline struct ltc3651_charger *psy_to_ltc3651_charger( +static inline struct lt3651_charger *psy_to_lt3651_charger( struct power_supply *psy) { return power_supply_get_drvdata(psy); } -static int ltc3651_charger_get_property(struct power_supply *psy, +static int lt3651_charger_get_property(struct power_supply *psy, enum power_supply_property psp, union power_supply_propval *val) { - struct ltc3651_charger *ltc3651_charger = psy_to_ltc3651_charger(psy); + struct lt3651_charger *lt3651_charger = psy_to_lt3651_charger(psy); switch (psp) { case POWER_SUPPLY_PROP_STATUS: - if (!ltc3651_charger->chrg_gpio) { + if (!lt3651_charger->chrg_gpio) { val->intval = POWER_SUPPLY_STATUS_UNKNOWN; break; } - if (gpiod_get_value(ltc3651_charger->chrg_gpio)) + if (gpiod_get_value(lt3651_charger->chrg_gpio)) val->intval = POWER_SUPPLY_STATUS_CHARGING; else val->intval = POWER_SUPPLY_STATUS_NOT_CHARGING; break; case POWER_SUPPLY_PROP_ONLINE: - val->intval = gpiod_get_value(ltc3651_charger->acpr_gpio); + val->intval = gpiod_get_value(lt3651_charger->acpr_gpio); break; case POWER_SUPPLY_PROP_HEALTH: - if (!ltc3651_charger->fault_gpio) { + if (!lt3651_charger->fault_gpio) { val->intval = POWER_SUPPLY_HEALTH_UNKNOWN; break; } - if (!gpiod_get_value(ltc3651_charger->fault_gpio)) { + if (!gpiod_get_value(lt3651_charger->fault_gpio)) { val->intval = POWER_SUPPLY_HEALTH_GOOD; break; } @@ -74,11 +70,11 @@ static int ltc3651_charger_get_property(struct power_supply *psy, * If the fault pin is active, the chrg pin explains the type * of failure. */ - if (!ltc3651_charger->chrg_gpio) { + if (!lt3651_charger->chrg_gpio) { val->intval = POWER_SUPPLY_HEALTH_UNSPEC_FAILURE; break; } - val->intval = gpiod_get_value(ltc3651_charger->chrg_gpio) ? + val->intval = gpiod_get_value(lt3651_charger->chrg_gpio) ? POWER_SUPPLY_HEALTH_OVERHEAT : POWER_SUPPLY_HEALTH_DEAD; break; @@ -89,59 +85,59 @@ static int ltc3651_charger_get_property(struct power_supply *psy, return 0; } -static enum power_supply_property ltc3651_charger_properties[] = { +static enum power_supply_property lt3651_charger_properties[] = { POWER_SUPPLY_PROP_STATUS, POWER_SUPPLY_PROP_ONLINE, POWER_SUPPLY_PROP_HEALTH, }; -static int ltc3651_charger_probe(struct platform_device *pdev) +static int lt3651_charger_probe(struct platform_device *pdev) { struct power_supply_config psy_cfg = {}; - struct ltc3651_charger *ltc3651_charger; + struct lt3651_charger *lt3651_charger; struct power_supply_desc *charger_desc; int ret; - ltc3651_charger = devm_kzalloc(&pdev->dev, sizeof(*ltc3651_charger), + lt3651_charger = devm_kzalloc(&pdev->dev, sizeof(*lt3651_charger), GFP_KERNEL); - if (!ltc3651_charger) + if (!lt3651_charger) return -ENOMEM; - ltc3651_charger->acpr_gpio = devm_gpiod_get(&pdev->dev, + lt3651_charger->acpr_gpio = devm_gpiod_get(&pdev->dev, "lltc,acpr", GPIOD_IN); - if (IS_ERR(ltc3651_charger->acpr_gpio)) { - ret = PTR_ERR(ltc3651_charger->acpr_gpio); + if (IS_ERR(lt3651_charger->acpr_gpio)) { + ret = PTR_ERR(lt3651_charger->acpr_gpio); dev_err(&pdev->dev, "Failed to acquire acpr GPIO: %d\n", ret); return ret; } - ltc3651_charger->fault_gpio = devm_gpiod_get_optional(&pdev->dev, + lt3651_charger->fault_gpio = devm_gpiod_get_optional(&pdev->dev, "lltc,fault", GPIOD_IN); - if (IS_ERR(ltc3651_charger->fault_gpio)) { - ret = PTR_ERR(ltc3651_charger->fault_gpio); + if (IS_ERR(lt3651_charger->fault_gpio)) { + ret = PTR_ERR(lt3651_charger->fault_gpio); dev_err(&pdev->dev, "Failed to acquire fault GPIO: %d\n", ret); return ret; } - ltc3651_charger->chrg_gpio = devm_gpiod_get_optional(&pdev->dev, + lt3651_charger->chrg_gpio = devm_gpiod_get_optional(&pdev->dev, "lltc,chrg", GPIOD_IN); - if (IS_ERR(ltc3651_charger->chrg_gpio)) { - ret = PTR_ERR(ltc3651_charger->chrg_gpio); + if (IS_ERR(lt3651_charger->chrg_gpio)) { + ret = PTR_ERR(lt3651_charger->chrg_gpio); dev_err(&pdev->dev, "Failed to acquire chrg GPIO: %d\n", ret); return ret; } - charger_desc = <c3651_charger->charger_desc; + charger_desc = <3651_charger->charger_desc; charger_desc->name = pdev->dev.of_node->name; charger_desc->type = POWER_SUPPLY_TYPE_MAINS; - charger_desc->properties = ltc3651_charger_properties; - charger_desc->num_properties = ARRAY_SIZE(ltc3651_charger_properties); - charger_desc->get_property = ltc3651_charger_get_property; + charger_desc->properties = lt3651_charger_properties; + charger_desc->num_properties = ARRAY_SIZE(lt3651_charger_properties); + charger_desc->get_property = lt3651_charger_get_property; psy_cfg.of_node = pdev->dev.of_node; - psy_cfg.drv_data = ltc3651_charger; + psy_cfg.drv_data = lt3651_charger; - ltc3651_charger->charger = devm_power_supply_register(&pdev->dev, + lt3651_charger->charger = devm_power_supply_register(&pdev->dev, charger_desc, &psy_cfg); - if (IS_ERR(ltc3651_charger->charger)) { - ret = PTR_ERR(ltc3651_charger->charger); + if (IS_ERR(lt3651_charger->charger)) { + ret = PTR_ERR(lt3651_charger->charger); dev_err(&pdev->dev, "Failed to register power supply: %d\n", ret); return ret; @@ -152,59 +148,60 @@ static int ltc3651_charger_probe(struct platform_device *pdev) * support IRQs on these pins, userspace will have to poll the sysfs * files manually. */ - if (ltc3651_charger->acpr_gpio) { - ret = gpiod_to_irq(ltc3651_charger->acpr_gpio); + if (lt3651_charger->acpr_gpio) { + ret = gpiod_to_irq(lt3651_charger->acpr_gpio); if (ret >= 0) ret = devm_request_any_context_irq(&pdev->dev, ret, - ltc3651_charger_irq, + lt3651_charger_irq, IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING, - dev_name(&pdev->dev), ltc3651_charger->charger); + dev_name(&pdev->dev), lt3651_charger->charger); if (ret < 0) dev_warn(&pdev->dev, "Failed to request acpr irq\n"); } - if (ltc3651_charger->fault_gpio) { - ret = gpiod_to_irq(ltc3651_charger->fault_gpio); + if (lt3651_charger->fault_gpio) { + ret = gpiod_to_irq(lt3651_charger->fault_gpio); if (ret >= 0) ret = devm_request_any_context_irq(&pdev->dev, ret, - ltc3651_charger_irq, + lt3651_charger_irq, IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING, - dev_name(&pdev->dev), ltc3651_charger->charger); + dev_name(&pdev->dev), lt3651_charger->charger); if (ret < 0) dev_warn(&pdev->dev, "Failed to request fault irq\n"); } - if (ltc3651_charger->chrg_gpio) { - ret = gpiod_to_irq(ltc3651_charger->chrg_gpio); + if (lt3651_charger->chrg_gpio) { + ret = gpiod_to_irq(lt3651_charger->chrg_gpio); if (ret >= 0) ret = devm_request_any_context_irq(&pdev->dev, ret, - ltc3651_charger_irq, + lt3651_charger_irq, IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING, - dev_name(&pdev->dev), ltc3651_charger->charger); + dev_name(&pdev->dev), lt3651_charger->charger); if (ret < 0) dev_warn(&pdev->dev, "Failed to request chrg irq\n"); } - platform_set_drvdata(pdev, ltc3651_charger); + platform_set_drvdata(pdev, lt3651_charger); return 0; } -static const struct of_device_id ltc3651_charger_match[] = { - { .compatible = "lltc,ltc3651-charger" }, +static const struct of_device_id lt3651_charger_match[] = { + { .compatible = "lltc,ltc3651-charger" }, /* DEPRECATED */ + { .compatible = "lltc,lt3651-charger" }, { } }; -MODULE_DEVICE_TABLE(of, ltc3651_charger_match); +MODULE_DEVICE_TABLE(of, lt3651_charger_match); -static struct platform_driver ltc3651_charger_driver = { - .probe = ltc3651_charger_probe, +static struct platform_driver lt3651_charger_driver = { + .probe = lt3651_charger_probe, .driver = { - .name = "ltc3651-charger", - .of_match_table = ltc3651_charger_match, + .name = "lt3651-charger", + .of_match_table = lt3651_charger_match, }, }; -module_platform_driver(ltc3651_charger_driver); +module_platform_driver(lt3651_charger_driver); MODULE_AUTHOR("Mike Looijmans "); -MODULE_DESCRIPTION("Driver for LTC3651 charger"); +MODULE_DESCRIPTION("Driver for LT3651 charger"); MODULE_LICENSE("GPL"); -MODULE_ALIAS("platform:ltc3651-charger"); +MODULE_ALIAS("platform:lt3651-charger"); -- cgit v1.2.3 From d7830ce3c5e0fe6aee645a1a01c9ae367d31bb9e Mon Sep 17 00:00:00 2001 From: Michael Hennerich Date: Tue, 9 Apr 2019 08:24:41 +0200 Subject: power: supply: ltc3651-charger: Fix device name (rename files) rename only - no functional changes Signed-off-by: Michael Hennerich Signed-off-by: Sebastian Reichel --- .../bindings/power/supply/lt3651-charger.txt | 29 +++ .../bindings/power/supply/ltc3651-charger.txt | 29 --- drivers/power/supply/Makefile | 2 +- drivers/power/supply/lt3651-charger.c | 207 +++++++++++++++++++++ drivers/power/supply/ltc3651-charger.c | 207 --------------------- 5 files changed, 237 insertions(+), 237 deletions(-) create mode 100644 Documentation/devicetree/bindings/power/supply/lt3651-charger.txt delete mode 100644 Documentation/devicetree/bindings/power/supply/ltc3651-charger.txt create mode 100644 drivers/power/supply/lt3651-charger.c delete mode 100644 drivers/power/supply/ltc3651-charger.c (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/power/supply/lt3651-charger.txt b/Documentation/devicetree/bindings/power/supply/lt3651-charger.txt new file mode 100644 index 000000000000..40811ff8de10 --- /dev/null +++ b/Documentation/devicetree/bindings/power/supply/lt3651-charger.txt @@ -0,0 +1,29 @@ +Analog Devices LT3651 Charger Power Supply bindings: lt3651-charger + +Required properties: +- compatible: Should contain one of the following: + * "lltc,ltc3651-charger", (DEPRECATED: Use "lltc,lt3651-charger") + * "lltc,lt3651-charger" + - lltc,acpr-gpios: Connect to ACPR output. See remark below. + +Optional properties: + - lltc,fault-gpios: Connect to FAULT output. See remark below. + - lltc,chrg-gpios: Connect to CHRG output. See remark below. + +The lt3651 outputs are open-drain type and active low. The driver assumes the +GPIO reports "active" when the output is asserted, so if the pins have been +connected directly, the GPIO flags should be set to active low also. + +The driver will attempt to aquire interrupts for all GPIOs to detect changes in +line state. If the system is not capabale of providing interrupts, the driver +cannot report changes and userspace will need to periodically read the sysfs +attributes to detect changes. + +Example: + + charger: battery-charger { + compatible = "lltc,lt3651-charger"; + lltc,acpr-gpios = <&gpio0 68 GPIO_ACTIVE_LOW>; + lltc,fault-gpios = <&gpio0 64 GPIO_ACTIVE_LOW>; + lltc,chrg-gpios = <&gpio0 63 GPIO_ACTIVE_LOW>; + }; diff --git a/Documentation/devicetree/bindings/power/supply/ltc3651-charger.txt b/Documentation/devicetree/bindings/power/supply/ltc3651-charger.txt deleted file mode 100644 index 40811ff8de10..000000000000 --- a/Documentation/devicetree/bindings/power/supply/ltc3651-charger.txt +++ /dev/null @@ -1,29 +0,0 @@ -Analog Devices LT3651 Charger Power Supply bindings: lt3651-charger - -Required properties: -- compatible: Should contain one of the following: - * "lltc,ltc3651-charger", (DEPRECATED: Use "lltc,lt3651-charger") - * "lltc,lt3651-charger" - - lltc,acpr-gpios: Connect to ACPR output. See remark below. - -Optional properties: - - lltc,fault-gpios: Connect to FAULT output. See remark below. - - lltc,chrg-gpios: Connect to CHRG output. See remark below. - -The lt3651 outputs are open-drain type and active low. The driver assumes the -GPIO reports "active" when the output is asserted, so if the pins have been -connected directly, the GPIO flags should be set to active low also. - -The driver will attempt to aquire interrupts for all GPIOs to detect changes in -line state. If the system is not capabale of providing interrupts, the driver -cannot report changes and userspace will need to periodically read the sysfs -attributes to detect changes. - -Example: - - charger: battery-charger { - compatible = "lltc,lt3651-charger"; - lltc,acpr-gpios = <&gpio0 68 GPIO_ACTIVE_LOW>; - lltc,fault-gpios = <&gpio0 64 GPIO_ACTIVE_LOW>; - lltc,chrg-gpios = <&gpio0 63 GPIO_ACTIVE_LOW>; - }; diff --git a/drivers/power/supply/Makefile b/drivers/power/supply/Makefile index 714c6029cff7..a2b3ab157ca0 100644 --- a/drivers/power/supply/Makefile +++ b/drivers/power/supply/Makefile @@ -67,7 +67,7 @@ obj-$(CONFIG_CHARGER_LP8727) += lp8727_charger.o obj-$(CONFIG_CHARGER_LP8788) += lp8788-charger.o obj-$(CONFIG_CHARGER_GPIO) += gpio-charger.o obj-$(CONFIG_CHARGER_MANAGER) += charger-manager.o -obj-$(CONFIG_CHARGER_LT3651) += ltc3651-charger.o +obj-$(CONFIG_CHARGER_LT3651) += lt3651-charger.o obj-$(CONFIG_CHARGER_MAX14577) += max14577_charger.o obj-$(CONFIG_CHARGER_DETECTOR_MAX14656) += max14656_charger_detector.o obj-$(CONFIG_CHARGER_MAX77693) += max77693_charger.o diff --git a/drivers/power/supply/lt3651-charger.c b/drivers/power/supply/lt3651-charger.c new file mode 100644 index 000000000000..8de500ffad95 --- /dev/null +++ b/drivers/power/supply/lt3651-charger.c @@ -0,0 +1,207 @@ +// SPDX-License-Identifier: GPL-2.0+ +/* + * Driver for Analog Devices (Linear Technology) LT3651 charger IC. + * Copyright (C) 2017, Topic Embedded Products + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +struct lt3651_charger { + struct power_supply *charger; + struct power_supply_desc charger_desc; + struct gpio_desc *acpr_gpio; + struct gpio_desc *fault_gpio; + struct gpio_desc *chrg_gpio; +}; + +static irqreturn_t lt3651_charger_irq(int irq, void *devid) +{ + struct power_supply *charger = devid; + + power_supply_changed(charger); + + return IRQ_HANDLED; +} + +static inline struct lt3651_charger *psy_to_lt3651_charger( + struct power_supply *psy) +{ + return power_supply_get_drvdata(psy); +} + +static int lt3651_charger_get_property(struct power_supply *psy, + enum power_supply_property psp, union power_supply_propval *val) +{ + struct lt3651_charger *lt3651_charger = psy_to_lt3651_charger(psy); + + switch (psp) { + case POWER_SUPPLY_PROP_STATUS: + if (!lt3651_charger->chrg_gpio) { + val->intval = POWER_SUPPLY_STATUS_UNKNOWN; + break; + } + if (gpiod_get_value(lt3651_charger->chrg_gpio)) + val->intval = POWER_SUPPLY_STATUS_CHARGING; + else + val->intval = POWER_SUPPLY_STATUS_NOT_CHARGING; + break; + case POWER_SUPPLY_PROP_ONLINE: + val->intval = gpiod_get_value(lt3651_charger->acpr_gpio); + break; + case POWER_SUPPLY_PROP_HEALTH: + if (!lt3651_charger->fault_gpio) { + val->intval = POWER_SUPPLY_HEALTH_UNKNOWN; + break; + } + if (!gpiod_get_value(lt3651_charger->fault_gpio)) { + val->intval = POWER_SUPPLY_HEALTH_GOOD; + break; + } + /* + * If the fault pin is active, the chrg pin explains the type + * of failure. + */ + if (!lt3651_charger->chrg_gpio) { + val->intval = POWER_SUPPLY_HEALTH_UNSPEC_FAILURE; + break; + } + val->intval = gpiod_get_value(lt3651_charger->chrg_gpio) ? + POWER_SUPPLY_HEALTH_OVERHEAT : + POWER_SUPPLY_HEALTH_DEAD; + break; + default: + return -EINVAL; + } + + return 0; +} + +static enum power_supply_property lt3651_charger_properties[] = { + POWER_SUPPLY_PROP_STATUS, + POWER_SUPPLY_PROP_ONLINE, + POWER_SUPPLY_PROP_HEALTH, +}; + +static int lt3651_charger_probe(struct platform_device *pdev) +{ + struct power_supply_config psy_cfg = {}; + struct lt3651_charger *lt3651_charger; + struct power_supply_desc *charger_desc; + int ret; + + lt3651_charger = devm_kzalloc(&pdev->dev, sizeof(*lt3651_charger), + GFP_KERNEL); + if (!lt3651_charger) + return -ENOMEM; + + lt3651_charger->acpr_gpio = devm_gpiod_get(&pdev->dev, + "lltc,acpr", GPIOD_IN); + if (IS_ERR(lt3651_charger->acpr_gpio)) { + ret = PTR_ERR(lt3651_charger->acpr_gpio); + dev_err(&pdev->dev, "Failed to acquire acpr GPIO: %d\n", ret); + return ret; + } + lt3651_charger->fault_gpio = devm_gpiod_get_optional(&pdev->dev, + "lltc,fault", GPIOD_IN); + if (IS_ERR(lt3651_charger->fault_gpio)) { + ret = PTR_ERR(lt3651_charger->fault_gpio); + dev_err(&pdev->dev, "Failed to acquire fault GPIO: %d\n", ret); + return ret; + } + lt3651_charger->chrg_gpio = devm_gpiod_get_optional(&pdev->dev, + "lltc,chrg", GPIOD_IN); + if (IS_ERR(lt3651_charger->chrg_gpio)) { + ret = PTR_ERR(lt3651_charger->chrg_gpio); + dev_err(&pdev->dev, "Failed to acquire chrg GPIO: %d\n", ret); + return ret; + } + + charger_desc = <3651_charger->charger_desc; + charger_desc->name = pdev->dev.of_node->name; + charger_desc->type = POWER_SUPPLY_TYPE_MAINS; + charger_desc->properties = lt3651_charger_properties; + charger_desc->num_properties = ARRAY_SIZE(lt3651_charger_properties); + charger_desc->get_property = lt3651_charger_get_property; + psy_cfg.of_node = pdev->dev.of_node; + psy_cfg.drv_data = lt3651_charger; + + lt3651_charger->charger = devm_power_supply_register(&pdev->dev, + charger_desc, &psy_cfg); + if (IS_ERR(lt3651_charger->charger)) { + ret = PTR_ERR(lt3651_charger->charger); + dev_err(&pdev->dev, "Failed to register power supply: %d\n", + ret); + return ret; + } + + /* + * Acquire IRQs for the GPIO pins if possible. If the system does not + * support IRQs on these pins, userspace will have to poll the sysfs + * files manually. + */ + if (lt3651_charger->acpr_gpio) { + ret = gpiod_to_irq(lt3651_charger->acpr_gpio); + if (ret >= 0) + ret = devm_request_any_context_irq(&pdev->dev, ret, + lt3651_charger_irq, + IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING, + dev_name(&pdev->dev), lt3651_charger->charger); + if (ret < 0) + dev_warn(&pdev->dev, "Failed to request acpr irq\n"); + } + if (lt3651_charger->fault_gpio) { + ret = gpiod_to_irq(lt3651_charger->fault_gpio); + if (ret >= 0) + ret = devm_request_any_context_irq(&pdev->dev, ret, + lt3651_charger_irq, + IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING, + dev_name(&pdev->dev), lt3651_charger->charger); + if (ret < 0) + dev_warn(&pdev->dev, "Failed to request fault irq\n"); + } + if (lt3651_charger->chrg_gpio) { + ret = gpiod_to_irq(lt3651_charger->chrg_gpio); + if (ret >= 0) + ret = devm_request_any_context_irq(&pdev->dev, ret, + lt3651_charger_irq, + IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING, + dev_name(&pdev->dev), lt3651_charger->charger); + if (ret < 0) + dev_warn(&pdev->dev, "Failed to request chrg irq\n"); + } + + platform_set_drvdata(pdev, lt3651_charger); + + return 0; +} + +static const struct of_device_id lt3651_charger_match[] = { + { .compatible = "lltc,ltc3651-charger" }, /* DEPRECATED */ + { .compatible = "lltc,lt3651-charger" }, + { } +}; +MODULE_DEVICE_TABLE(of, lt3651_charger_match); + +static struct platform_driver lt3651_charger_driver = { + .probe = lt3651_charger_probe, + .driver = { + .name = "lt3651-charger", + .of_match_table = lt3651_charger_match, + }, +}; + +module_platform_driver(lt3651_charger_driver); + +MODULE_AUTHOR("Mike Looijmans "); +MODULE_DESCRIPTION("Driver for LT3651 charger"); +MODULE_LICENSE("GPL"); +MODULE_ALIAS("platform:lt3651-charger"); diff --git a/drivers/power/supply/ltc3651-charger.c b/drivers/power/supply/ltc3651-charger.c deleted file mode 100644 index 8de500ffad95..000000000000 --- a/drivers/power/supply/ltc3651-charger.c +++ /dev/null @@ -1,207 +0,0 @@ -// SPDX-License-Identifier: GPL-2.0+ -/* - * Driver for Analog Devices (Linear Technology) LT3651 charger IC. - * Copyright (C) 2017, Topic Embedded Products - */ - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -struct lt3651_charger { - struct power_supply *charger; - struct power_supply_desc charger_desc; - struct gpio_desc *acpr_gpio; - struct gpio_desc *fault_gpio; - struct gpio_desc *chrg_gpio; -}; - -static irqreturn_t lt3651_charger_irq(int irq, void *devid) -{ - struct power_supply *charger = devid; - - power_supply_changed(charger); - - return IRQ_HANDLED; -} - -static inline struct lt3651_charger *psy_to_lt3651_charger( - struct power_supply *psy) -{ - return power_supply_get_drvdata(psy); -} - -static int lt3651_charger_get_property(struct power_supply *psy, - enum power_supply_property psp, union power_supply_propval *val) -{ - struct lt3651_charger *lt3651_charger = psy_to_lt3651_charger(psy); - - switch (psp) { - case POWER_SUPPLY_PROP_STATUS: - if (!lt3651_charger->chrg_gpio) { - val->intval = POWER_SUPPLY_STATUS_UNKNOWN; - break; - } - if (gpiod_get_value(lt3651_charger->chrg_gpio)) - val->intval = POWER_SUPPLY_STATUS_CHARGING; - else - val->intval = POWER_SUPPLY_STATUS_NOT_CHARGING; - break; - case POWER_SUPPLY_PROP_ONLINE: - val->intval = gpiod_get_value(lt3651_charger->acpr_gpio); - break; - case POWER_SUPPLY_PROP_HEALTH: - if (!lt3651_charger->fault_gpio) { - val->intval = POWER_SUPPLY_HEALTH_UNKNOWN; - break; - } - if (!gpiod_get_value(lt3651_charger->fault_gpio)) { - val->intval = POWER_SUPPLY_HEALTH_GOOD; - break; - } - /* - * If the fault pin is active, the chrg pin explains the type - * of failure. - */ - if (!lt3651_charger->chrg_gpio) { - val->intval = POWER_SUPPLY_HEALTH_UNSPEC_FAILURE; - break; - } - val->intval = gpiod_get_value(lt3651_charger->chrg_gpio) ? - POWER_SUPPLY_HEALTH_OVERHEAT : - POWER_SUPPLY_HEALTH_DEAD; - break; - default: - return -EINVAL; - } - - return 0; -} - -static enum power_supply_property lt3651_charger_properties[] = { - POWER_SUPPLY_PROP_STATUS, - POWER_SUPPLY_PROP_ONLINE, - POWER_SUPPLY_PROP_HEALTH, -}; - -static int lt3651_charger_probe(struct platform_device *pdev) -{ - struct power_supply_config psy_cfg = {}; - struct lt3651_charger *lt3651_charger; - struct power_supply_desc *charger_desc; - int ret; - - lt3651_charger = devm_kzalloc(&pdev->dev, sizeof(*lt3651_charger), - GFP_KERNEL); - if (!lt3651_charger) - return -ENOMEM; - - lt3651_charger->acpr_gpio = devm_gpiod_get(&pdev->dev, - "lltc,acpr", GPIOD_IN); - if (IS_ERR(lt3651_charger->acpr_gpio)) { - ret = PTR_ERR(lt3651_charger->acpr_gpio); - dev_err(&pdev->dev, "Failed to acquire acpr GPIO: %d\n", ret); - return ret; - } - lt3651_charger->fault_gpio = devm_gpiod_get_optional(&pdev->dev, - "lltc,fault", GPIOD_IN); - if (IS_ERR(lt3651_charger->fault_gpio)) { - ret = PTR_ERR(lt3651_charger->fault_gpio); - dev_err(&pdev->dev, "Failed to acquire fault GPIO: %d\n", ret); - return ret; - } - lt3651_charger->chrg_gpio = devm_gpiod_get_optional(&pdev->dev, - "lltc,chrg", GPIOD_IN); - if (IS_ERR(lt3651_charger->chrg_gpio)) { - ret = PTR_ERR(lt3651_charger->chrg_gpio); - dev_err(&pdev->dev, "Failed to acquire chrg GPIO: %d\n", ret); - return ret; - } - - charger_desc = <3651_charger->charger_desc; - charger_desc->name = pdev->dev.of_node->name; - charger_desc->type = POWER_SUPPLY_TYPE_MAINS; - charger_desc->properties = lt3651_charger_properties; - charger_desc->num_properties = ARRAY_SIZE(lt3651_charger_properties); - charger_desc->get_property = lt3651_charger_get_property; - psy_cfg.of_node = pdev->dev.of_node; - psy_cfg.drv_data = lt3651_charger; - - lt3651_charger->charger = devm_power_supply_register(&pdev->dev, - charger_desc, &psy_cfg); - if (IS_ERR(lt3651_charger->charger)) { - ret = PTR_ERR(lt3651_charger->charger); - dev_err(&pdev->dev, "Failed to register power supply: %d\n", - ret); - return ret; - } - - /* - * Acquire IRQs for the GPIO pins if possible. If the system does not - * support IRQs on these pins, userspace will have to poll the sysfs - * files manually. - */ - if (lt3651_charger->acpr_gpio) { - ret = gpiod_to_irq(lt3651_charger->acpr_gpio); - if (ret >= 0) - ret = devm_request_any_context_irq(&pdev->dev, ret, - lt3651_charger_irq, - IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING, - dev_name(&pdev->dev), lt3651_charger->charger); - if (ret < 0) - dev_warn(&pdev->dev, "Failed to request acpr irq\n"); - } - if (lt3651_charger->fault_gpio) { - ret = gpiod_to_irq(lt3651_charger->fault_gpio); - if (ret >= 0) - ret = devm_request_any_context_irq(&pdev->dev, ret, - lt3651_charger_irq, - IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING, - dev_name(&pdev->dev), lt3651_charger->charger); - if (ret < 0) - dev_warn(&pdev->dev, "Failed to request fault irq\n"); - } - if (lt3651_charger->chrg_gpio) { - ret = gpiod_to_irq(lt3651_charger->chrg_gpio); - if (ret >= 0) - ret = devm_request_any_context_irq(&pdev->dev, ret, - lt3651_charger_irq, - IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING, - dev_name(&pdev->dev), lt3651_charger->charger); - if (ret < 0) - dev_warn(&pdev->dev, "Failed to request chrg irq\n"); - } - - platform_set_drvdata(pdev, lt3651_charger); - - return 0; -} - -static const struct of_device_id lt3651_charger_match[] = { - { .compatible = "lltc,ltc3651-charger" }, /* DEPRECATED */ - { .compatible = "lltc,lt3651-charger" }, - { } -}; -MODULE_DEVICE_TABLE(of, lt3651_charger_match); - -static struct platform_driver lt3651_charger_driver = { - .probe = lt3651_charger_probe, - .driver = { - .name = "lt3651-charger", - .of_match_table = lt3651_charger_match, - }, -}; - -module_platform_driver(lt3651_charger_driver); - -MODULE_AUTHOR("Mike Looijmans "); -MODULE_DESCRIPTION("Driver for LT3651 charger"); -MODULE_LICENSE("GPL"); -MODULE_ALIAS("platform:lt3651-charger"); -- cgit v1.2.3 From 5467a68cbf6884c9a9d91e2a89140afb1839c835 Mon Sep 17 00:00:00 2001 From: Al Viro Date: Fri, 15 Mar 2019 22:23:19 -0400 Subject: dcache: sort the freeing-without-RCU-delay mess for good. For lockless accesses to dentries we don't have pinned we rely (among other things) upon having an RCU delay between dropping the last reference and actually freeing the memory. On the other hand, for things like pipes and sockets we neither do that kind of lockless access, nor want to deal with the overhead of an RCU delay every time a socket gets closed. So delay was made optional - setting DCACHE_RCUACCESS in ->d_flags made sure it would happen. We tried to avoid setting it unless we knew we need it. Unfortunately, that had led to recurring class of bugs, in which we missed the need to set it. We only really need it for dentries that are created by d_alloc_pseudo(), so let's not bother with trying to be smart - just make having an RCU delay the default. The ones that do *not* get it set the replacement flag (DCACHE_NORCU) and we'd better use that sparingly. d_alloc_pseudo() is the only such user right now. FWIW, the race that finally prompted that switch had been between __lock_parent() of immediate subdirectory of what's currently the root of a disconnected tree (e.g. from open-by-handle in progress) racing with d_splice_alias() elsewhere picking another alias for the same inode, either on outright corrupted fs image, or (in case of open-by-handle on NFS) that subdirectory having been just moved on server. It's not easy to hit, so the sky is not falling, but that's not the first race on similar missed cases and the logics for settinf DCACHE_RCUACCESS has gotten ridiculously convoluted. Cc: stable@vger.kernel.org Signed-off-by: Al Viro --- Documentation/filesystems/porting | 5 +++++ fs/dcache.c | 24 +++++++++++++----------- fs/nsfs.c | 3 +-- include/linux/dcache.h | 2 +- 4 files changed, 20 insertions(+), 14 deletions(-) (limited to 'Documentation') diff --git a/Documentation/filesystems/porting b/Documentation/filesystems/porting index cf43bc4dbf31..a60fa516d4cb 100644 --- a/Documentation/filesystems/porting +++ b/Documentation/filesystems/porting @@ -638,3 +638,8 @@ in your dentry operations instead. inode to d_splice_alias() will also do the right thing (equivalent of d_add(dentry, NULL); return NULL;), so that kind of special cases also doesn't need a separate treatment. +-- +[mandatory] + DCACHE_RCUACCESS is gone; having an RCU delay on dentry freeing is the + default. DCACHE_NORCU opts out, and only d_alloc_pseudo() has any + business doing so. diff --git a/fs/dcache.c b/fs/dcache.c index aac41adf4743..c663c602f9ef 100644 --- a/fs/dcache.c +++ b/fs/dcache.c @@ -344,7 +344,7 @@ static void dentry_free(struct dentry *dentry) } } /* if dentry was never visible to RCU, immediate free is OK */ - if (!(dentry->d_flags & DCACHE_RCUACCESS)) + if (dentry->d_flags & DCACHE_NORCU) __d_free(&dentry->d_u.d_rcu); else call_rcu(&dentry->d_u.d_rcu, __d_free); @@ -1701,7 +1701,6 @@ struct dentry *d_alloc(struct dentry * parent, const struct qstr *name) struct dentry *dentry = __d_alloc(parent->d_sb, name); if (!dentry) return NULL; - dentry->d_flags |= DCACHE_RCUACCESS; spin_lock(&parent->d_lock); /* * don't need child lock because it is not subject @@ -1726,7 +1725,7 @@ struct dentry *d_alloc_cursor(struct dentry * parent) { struct dentry *dentry = d_alloc_anon(parent->d_sb); if (dentry) { - dentry->d_flags |= DCACHE_RCUACCESS | DCACHE_DENTRY_CURSOR; + dentry->d_flags |= DCACHE_DENTRY_CURSOR; dentry->d_parent = dget(parent); } return dentry; @@ -1739,10 +1738,17 @@ struct dentry *d_alloc_cursor(struct dentry * parent) * * For a filesystem that just pins its dentries in memory and never * performs lookups at all, return an unhashed IS_ROOT dentry. + * This is used for pipes, sockets et.al. - the stuff that should + * never be anyone's children or parents. Unlike all other + * dentries, these will not have RCU delay between dropping the + * last reference and freeing them. */ struct dentry *d_alloc_pseudo(struct super_block *sb, const struct qstr *name) { - return __d_alloc(sb, name); + struct dentry *dentry = __d_alloc(sb, name); + if (likely(dentry)) + dentry->d_flags |= DCACHE_NORCU; + return dentry; } EXPORT_SYMBOL(d_alloc_pseudo); @@ -1911,12 +1917,10 @@ struct dentry *d_make_root(struct inode *root_inode) if (root_inode) { res = d_alloc_anon(root_inode->i_sb); - if (res) { - res->d_flags |= DCACHE_RCUACCESS; + if (res) d_instantiate(res, root_inode); - } else { + else iput(root_inode); - } } return res; } @@ -2781,9 +2785,7 @@ static void __d_move(struct dentry *dentry, struct dentry *target, copy_name(dentry, target); target->d_hash.pprev = NULL; dentry->d_parent->d_lockref.count++; - if (dentry == old_parent) - dentry->d_flags |= DCACHE_RCUACCESS; - else + if (dentry != old_parent) /* wasn't IS_ROOT */ WARN_ON(!--old_parent->d_lockref.count); } else { target->d_parent = old_parent; diff --git a/fs/nsfs.c b/fs/nsfs.c index 60702d677bd4..30d150a4f0c6 100644 --- a/fs/nsfs.c +++ b/fs/nsfs.c @@ -85,13 +85,12 @@ slow: inode->i_fop = &ns_file_operations; inode->i_private = ns; - dentry = d_alloc_pseudo(mnt->mnt_sb, &empty_name); + dentry = d_alloc_anon(mnt->mnt_sb); if (!dentry) { iput(inode); return ERR_PTR(-ENOMEM); } d_instantiate(dentry, inode); - dentry->d_flags |= DCACHE_RCUACCESS; dentry->d_fsdata = (void *)ns->ops; d = atomic_long_cmpxchg(&ns->stashed, 0, (unsigned long)dentry); if (d) { diff --git a/include/linux/dcache.h b/include/linux/dcache.h index 60996e64c579..6e1e8e6602c6 100644 --- a/include/linux/dcache.h +++ b/include/linux/dcache.h @@ -176,7 +176,6 @@ struct dentry_operations { * typically using d_splice_alias. */ #define DCACHE_REFERENCED 0x00000040 /* Recently used, don't discard. */ -#define DCACHE_RCUACCESS 0x00000080 /* Entry has ever been RCU-visible */ #define DCACHE_CANT_MOUNT 0x00000100 #define DCACHE_GENOCIDE 0x00000200 @@ -217,6 +216,7 @@ struct dentry_operations { #define DCACHE_PAR_LOOKUP 0x10000000 /* being looked up (with parent locked shared) */ #define DCACHE_DENTRY_CURSOR 0x20000000 +#define DCACHE_NORCU 0x40000000 /* No RCU delay for freeing */ extern seqlock_t rename_lock; -- cgit v1.2.3 From ab1152dd5650d35da6f0f6d3c0cc18f86fdc0725 Mon Sep 17 00:00:00 2001 From: Al Viro Date: Fri, 15 Mar 2019 22:58:11 -0400 Subject: unexport d_alloc_pseudo() No modular uses since introducion of alloc_file_pseudo(), and the only non-modular user not in alloc_file_pseudo() had actually been wrong - should've been d_alloc_anon(). Signed-off-by: Al Viro --- Documentation/filesystems/porting | 5 +++++ fs/dcache.c | 4 +++- fs/internal.h | 1 + include/linux/dcache.h | 1 - 4 files changed, 9 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/filesystems/porting b/Documentation/filesystems/porting index a60fa516d4cb..7ed8188e7047 100644 --- a/Documentation/filesystems/porting +++ b/Documentation/filesystems/porting @@ -643,3 +643,8 @@ in your dentry operations instead. DCACHE_RCUACCESS is gone; having an RCU delay on dentry freeing is the default. DCACHE_NORCU opts out, and only d_alloc_pseudo() has any business doing so. +-- +[mandatory] + d_alloc_pseudo() is internal-only; uses outside of alloc_file_pseudo() are + very suspect (and won't work in modules). Such uses are very likely to + be misspelled d_alloc_anon(). diff --git a/fs/dcache.c b/fs/dcache.c index c663c602f9ef..6dd58ced8236 100644 --- a/fs/dcache.c +++ b/fs/dcache.c @@ -1742,6 +1742,9 @@ struct dentry *d_alloc_cursor(struct dentry * parent) * never be anyone's children or parents. Unlike all other * dentries, these will not have RCU delay between dropping the * last reference and freeing them. + * + * The only user is alloc_file_pseudo() and that's what should + * be considered a public interface. Don't use directly. */ struct dentry *d_alloc_pseudo(struct super_block *sb, const struct qstr *name) { @@ -1750,7 +1753,6 @@ struct dentry *d_alloc_pseudo(struct super_block *sb, const struct qstr *name) dentry->d_flags |= DCACHE_NORCU; return dentry; } -EXPORT_SYMBOL(d_alloc_pseudo); struct dentry *d_alloc_name(struct dentry *parent, const char *name) { diff --git a/fs/internal.h b/fs/internal.h index 2e7362837a6e..8102032432cf 100644 --- a/fs/internal.h +++ b/fs/internal.h @@ -155,6 +155,7 @@ extern struct dentry *__d_alloc(struct super_block *, const struct qstr *); extern int d_set_mounted(struct dentry *dentry); extern long prune_dcache_sb(struct super_block *sb, struct shrink_control *sc); extern struct dentry *d_alloc_cursor(struct dentry *); +extern struct dentry * d_alloc_pseudo(struct super_block *, const struct qstr *); /* * read_write.c diff --git a/include/linux/dcache.h b/include/linux/dcache.h index 6e1e8e6602c6..2f044e232e1b 100644 --- a/include/linux/dcache.h +++ b/include/linux/dcache.h @@ -235,7 +235,6 @@ extern void d_set_d_op(struct dentry *dentry, const struct dentry_operations *op /* allocate/de-allocate */ extern struct dentry * d_alloc(struct dentry *, const struct qstr *); extern struct dentry * d_alloc_anon(struct super_block *); -extern struct dentry * d_alloc_pseudo(struct super_block *, const struct qstr *); extern struct dentry * d_alloc_parallel(struct dentry *, const struct qstr *, wait_queue_head_t *); extern struct dentry * d_splice_alias(struct inode *, struct dentry *); -- cgit v1.2.3 From f063c889c9458354a92b235a51cbb60d30321070 Mon Sep 17 00:00:00 2001 From: Daniel Borkmann Date: Tue, 9 Apr 2019 23:20:08 +0200 Subject: bpf: add specification for BTF Var and DataSec kinds This adds the BTF specification and UAPI bits for supporting BTF Var and DataSec kinds. This is following LLVM upstream commit ac4082b77e07 ("[BPF] Add BTF Var and DataSec Support") which has been merged recently. Var itself is for describing a global variable and DataSec to describe ELF sections e.g. data/bss/rodata sections that hold one or multiple global variables. Signed-off-by: Daniel Borkmann Acked-by: Martin KaFai Lau Signed-off-by: Alexei Starovoitov --- Documentation/bpf/btf.rst | 57 +++++++++++++++++++++++++++++++++++++++++++++++ include/uapi/linux/btf.h | 32 ++++++++++++++++++++++---- 2 files changed, 85 insertions(+), 4 deletions(-) (limited to 'Documentation') diff --git a/Documentation/bpf/btf.rst b/Documentation/bpf/btf.rst index 9a60a5d60e38..60d87d7363ec 100644 --- a/Documentation/bpf/btf.rst +++ b/Documentation/bpf/btf.rst @@ -82,6 +82,8 @@ sequentially and type id is assigned to each recognized type starting from id #define BTF_KIND_RESTRICT 11 /* Restrict */ #define BTF_KIND_FUNC 12 /* Function */ #define BTF_KIND_FUNC_PROTO 13 /* Function Proto */ + #define BTF_KIND_VAR 14 /* Variable */ + #define BTF_KIND_DATASEC 15 /* Section */ Note that the type section encodes debug info, not just pure types. ``BTF_KIND_FUNC`` is not a type, and it represents a defined subprogram. @@ -393,6 +395,61 @@ refers to parameter type. If the function has variable arguments, the last parameter is encoded with ``name_off = 0`` and ``type = 0``. +2.2.14 BTF_KIND_VAR +~~~~~~~~~~~~~~~~~~~ + +``struct btf_type`` encoding requirement: + * ``name_off``: offset to a valid C identifier + * ``info.kind_flag``: 0 + * ``info.kind``: BTF_KIND_VAR + * ``info.vlen``: 0 + * ``type``: the type of the variable + +``btf_type`` is followed by a single ``struct btf_variable`` with the +following data:: + + struct btf_var { + __u32 linkage; + }; + +``struct btf_var`` encoding: + * ``linkage``: currently only static variable 0, or globally allocated + variable in ELF sections 1 + +Not all type of global variables are supported by LLVM at this point. +The following is currently available: + + * static variables with or without section attributes + * global variables with section attributes + +The latter is for future extraction of map key/value type id's from a +map definition. + +2.2.15 BTF_KIND_DATASEC +~~~~~~~~~~~~~~~~~~~~~~~ + +``struct btf_type`` encoding requirement: + * ``name_off``: offset to a valid name associated with a variable or + one of .data/.bss/.rodata + * ``info.kind_flag``: 0 + * ``info.kind``: BTF_KIND_DATASEC + * ``info.vlen``: # of variables + * ``size``: total section size in bytes (0 at compilation time, patched + to actual size by BPF loaders such as libbpf) + +``btf_type`` is followed by ``info.vlen`` number of ``struct btf_var_secinfo``.:: + + struct btf_var_secinfo { + __u32 type; + __u32 offset; + __u32 size; + }; + +``struct btf_var_secinfo`` encoding: + * ``type``: the type of the BTF_KIND_VAR variable + * ``offset``: the in-section offset of the variable + * ``size``: the size of the variable in bytes + 3. BTF Kernel API ***************** diff --git a/include/uapi/linux/btf.h b/include/uapi/linux/btf.h index 7b7475ef2f17..9310652ca4f9 100644 --- a/include/uapi/linux/btf.h +++ b/include/uapi/linux/btf.h @@ -39,11 +39,11 @@ struct btf_type { * struct, union and fwd */ __u32 info; - /* "size" is used by INT, ENUM, STRUCT and UNION. + /* "size" is used by INT, ENUM, STRUCT, UNION and DATASEC. * "size" tells the size of the type it is describing. * * "type" is used by PTR, TYPEDEF, VOLATILE, CONST, RESTRICT, - * FUNC and FUNC_PROTO. + * FUNC, FUNC_PROTO and VAR. * "type" is a type_id referring to another type. */ union { @@ -70,8 +70,10 @@ struct btf_type { #define BTF_KIND_RESTRICT 11 /* Restrict */ #define BTF_KIND_FUNC 12 /* Function */ #define BTF_KIND_FUNC_PROTO 13 /* Function Proto */ -#define BTF_KIND_MAX 13 -#define NR_BTF_KINDS 14 +#define BTF_KIND_VAR 14 /* Variable */ +#define BTF_KIND_DATASEC 15 /* Section */ +#define BTF_KIND_MAX BTF_KIND_DATASEC +#define NR_BTF_KINDS (BTF_KIND_MAX + 1) /* For some specific BTF_KIND, "struct btf_type" is immediately * followed by extra data. @@ -138,4 +140,26 @@ struct btf_param { __u32 type; }; +enum { + BTF_VAR_STATIC = 0, + BTF_VAR_GLOBAL_ALLOCATED, +}; + +/* BTF_KIND_VAR is followed by a single "struct btf_var" to describe + * additional information related to the variable such as its linkage. + */ +struct btf_var { + __u32 linkage; +}; + +/* BTF_KIND_DATASEC is followed by multiple "struct btf_var_secinfo" + * to describe all BTF_KIND_VAR types it contains along with it's + * in-section offset as well as size. + */ +struct btf_var_secinfo { + __u32 type; + __u32 offset; + __u32 size; +}; + #endif /* _UAPI__LINUX_BTF_H__ */ -- cgit v1.2.3 From b06ce8218c459df167202c75869924e193a2311b Mon Sep 17 00:00:00 2001 From: Rob Herring Date: Wed, 13 Mar 2019 09:53:15 -0500 Subject: dt-bindings: Add a guide of do's and don't's for writing bindings Devicetree binding reviews have a lot of repeated review comments. Much of the guidelines aren't written down. This list of do's and don't's is by no means an exhaustive guide for how to write bindings, but at least the "rules" are written down in some form. Signed-off-by: Rob Herring --- .../devicetree/bindings/writing-bindings.txt | 60 ++++++++++++++++++++++ 1 file changed, 60 insertions(+) create mode 100644 Documentation/devicetree/bindings/writing-bindings.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/writing-bindings.txt b/Documentation/devicetree/bindings/writing-bindings.txt new file mode 100644 index 000000000000..27dfd2d8016e --- /dev/null +++ b/Documentation/devicetree/bindings/writing-bindings.txt @@ -0,0 +1,60 @@ +DOs and DON'Ts for designing and writing Devicetree bindings + +This is a list of common review feedback items focused on binding design. With +every rule, there are exceptions and bindings have many gray areas. + +For guidelines related to patches, see +Documentation/devicetree/bindings/submitting-patches.txt + + +Overall design + +- DO attempt to make bindings complete even if a driver doesn't support some + features. For example, if a device has an interrupt, then include the + 'interrupts' property even if the driver is only polled mode. + +- DON'T refer to Linux or "device driver" in bindings. Bindings should be + based on what the hardware has, not what an OS and driver currently support. + +- DO use node names matching the class of the device. Many standard names are + defined in the DT Spec. If there isn't one, consider adding it. + +- DO check that the example matches the documentation especially after making + review changes. + +- DON'T create nodes just for the sake of instantiating drivers. Multi-function + devices only need child nodes when the child nodes have their own DT + resources. A single node can be multiple providers (e.g. clocks and resets). + +- DON'T use 'syscon' alone without a specific compatible string. A 'syscon' + hardware block should have a compatible string unique enough to infer the + register layout of the entire block (at a minimum). + + +Properties + +- DO make 'compatible' properties specific. DON'T use wildcards in compatible + strings. DO use fallback compatibles when devices are the same as or a subset + of prior implementations. DO add new compatibles in case there are new + features or bugs. + +- DO use a vendor prefix on device specific property names. Consider if + properties could be common among devices of the same class. Check other + existing bindings for similar devices. + +- DON'T redefine common properties. Just reference the definition and define + constraints specific to the device. + +- DO use common property unit suffixes for properties with scientific units. + See property-units.txt. + +- DO define properties in terms of constraints. How many entries? What are + possible values? What is the order? + + +Board/SoC .dts Files + +- DO put all MMIO devices under a bus node and not at the top-level. + +- DO use non-empty 'ranges' to limit the size of child buses/devices. 64-bit + platforms don't need all devices to have 64-bit address and size. -- cgit v1.2.3 From 99838f011a3a8fcfbda526bb17b2905e07288808 Mon Sep 17 00:00:00 2001 From: Rob Herring Date: Fri, 15 Mar 2019 18:59:21 -0500 Subject: dt-bindings: Require child nodes type to be 'object' A node is always an object (aka a dictionary), so make that explicit for child node schemas. A meta-schema update will enforce having 'type' specified. Cc: Mark Rutland Cc: Thomas Gleixner Cc: Jason Cooper Cc: Marc Zyngier Cc: Daniel Lezcano Signed-off-by: Rob Herring --- Documentation/devicetree/bindings/arm/cpus.yaml | 1 + Documentation/devicetree/bindings/interrupt-controller/arm,gic.yaml | 1 + Documentation/devicetree/bindings/timer/arm,arch_timer_mmio.yaml | 1 + 3 files changed, 3 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/cpus.yaml b/Documentation/devicetree/bindings/arm/cpus.yaml index 365dcf384d73..60eab6dc3c0b 100644 --- a/Documentation/devicetree/bindings/arm/cpus.yaml +++ b/Documentation/devicetree/bindings/arm/cpus.yaml @@ -67,6 +67,7 @@ properties: patternProperties: '^cpu@[0-9a-f]+$': + type: object properties: device_type: const: cpu diff --git a/Documentation/devicetree/bindings/interrupt-controller/arm,gic.yaml b/Documentation/devicetree/bindings/interrupt-controller/arm,gic.yaml index 758fbd7128e7..54838d4ea44c 100644 --- a/Documentation/devicetree/bindings/interrupt-controller/arm,gic.yaml +++ b/Documentation/devicetree/bindings/interrupt-controller/arm,gic.yaml @@ -129,6 +129,7 @@ required: patternProperties: "^v2m@[0-9a-f]+$": + type: object description: | * GICv2m extension for MSI/MSI-x support (Optional) diff --git a/Documentation/devicetree/bindings/timer/arm,arch_timer_mmio.yaml b/Documentation/devicetree/bindings/timer/arm,arch_timer_mmio.yaml index c4ab59550fc2..b3f0fe96ff0d 100644 --- a/Documentation/devicetree/bindings/timer/arm,arch_timer_mmio.yaml +++ b/Documentation/devicetree/bindings/timer/arm,arch_timer_mmio.yaml @@ -59,6 +59,7 @@ properties: patternProperties: '^frame@[0-9a-z]*$': + type: object description: A timer node has up to 8 frame sub-nodes, each with the following properties. properties: frame-number: -- cgit v1.2.3 From b9c8172eedc1a8285c373564174a724311394472 Mon Sep 17 00:00:00 2001 From: Thor Thayer Date: Thu, 4 Apr 2019 09:36:35 -0500 Subject: Documentation: dt: edac: Fix Stratix10 IRQ bindings Fix Stratix10 ECC bindings to specify only the single bit error. On Stratix10 double bit errors are handled as SErrors instead of interrupts. Indicate the differences between the ARM64 and ARM32 EDAC architecture in the bindings. Signed-off-by: Thor Thayer Signed-off-by: Borislav Petkov Acked-by: Rob Herring Cc: James Morse Cc: Mark Rutland Cc: devicetree@vger.kernel.org Cc: dinguyen@kernel.org Cc: linux-edac Cc: mark.rutland@arm.com Cc: mchehab@kernel.org Link: https://lkml.kernel.org/r/1554388597-28019-2-git-send-email-thor.thayer@linux.intel.com --- .../devicetree/bindings/edac/socfpga-eccmgr.txt | 29 ++++++++++++++-------- 1 file changed, 19 insertions(+), 10 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/edac/socfpga-eccmgr.txt b/Documentation/devicetree/bindings/edac/socfpga-eccmgr.txt index 5626560a6cfd..acb211c098c0 100644 --- a/Documentation/devicetree/bindings/edac/socfpga-eccmgr.txt +++ b/Documentation/devicetree/bindings/edac/socfpga-eccmgr.txt @@ -232,37 +232,46 @@ Example: }; }; -Stratix10 SoCFPGA ECC Manager +Stratix10 SoCFPGA ECC Manager (ARM64) The Stratix10 SoC ECC Manager handles the IRQs for each peripheral -in a shared register similar to the Arria10. However, ECC requires -access to registers that can only be read from Secure Monitor with -SMC calls. Therefore the device tree is slightly different. +in a shared register similar to the Arria10. However, Stratix10 ECC +requires access to registers that can only be read from Secure Monitor +with SMC calls. Therefore the device tree is slightly different. Note +that only 1 interrupt is sent in Stratix10 because the double bit errors +are treated as SErrors in ARM64 instead of IRQs in ARM32. Required Properties: - compatible : Should be "altr,socfpga-s10-ecc-manager" -- interrupts : Should be single bit error interrupt, then double bit error - interrupt. +- altr,sysgr-syscon : phandle to Stratix10 System Manager Block + containing the ECC manager registers. +- interrupts : Should be single bit error interrupt. - interrupt-controller : boolean indicator that ECC Manager is an interrupt controller - #interrupt-cells : must be set to 2. +- #address-cells: must be 1 +- #size-cells: must be 1 +- ranges : standard definition, should translate from local addresses Subcomponents: SDRAM ECC Required Properties: - compatible : Should be "altr,sdram-edac-s10" -- interrupts : Should be single bit error interrupt, then double bit error - interrupt, in this order. +- interrupts : Should be single bit error interrupt. Example: eccmgr { compatible = "altr,socfpga-s10-ecc-manager"; - interrupts = <0 15 4>, <0 95 4>; + altr,sysmgr-syscon = <&sysmgr>; + #address-cells = <1>; + #size-cells = <1>; + interrupts = <0 15 4>; interrupt-controller; #interrupt-cells = <2>; + ranges; sdramedac { compatible = "altr,sdram-edac-s10"; - interrupts = <16 4>, <48 4>; + interrupts = <16 IRQ_TYPE_LEVEL_HIGH>; }; }; -- cgit v1.2.3 From 71eec083eef10b1529f2300d6c3553f0949733a5 Mon Sep 17 00:00:00 2001 From: Thor Thayer Date: Thu, 4 Apr 2019 09:36:36 -0500 Subject: Documentation: dt: edac: Add Stratix10 Peripheral bindings Add peripheral bindings for Stratix10 EDAC to capture the differences between the ARM64 and ARM32 architecture. Signed-off-by: Thor Thayer Signed-off-by: Borislav Petkov Reviewed-by: Rob Herring Cc: James Morse Cc: Mark Rutland Cc: devicetree@vger.kernel.org Cc: dinguyen@kernel.org Cc: linux-edac Cc: mark.rutland@arm.com Cc: mchehab@kernel.org Link: https://lkml.kernel.org/r/1554388597-28019-3-git-send-email-thor.thayer@linux.intel.com --- .../devicetree/bindings/edac/socfpga-eccmgr.txt | 106 +++++++++++++++++++++ 1 file changed, 106 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/edac/socfpga-eccmgr.txt b/Documentation/devicetree/bindings/edac/socfpga-eccmgr.txt index acb211c098c0..8f52206cfd2a 100644 --- a/Documentation/devicetree/bindings/edac/socfpga-eccmgr.txt +++ b/Documentation/devicetree/bindings/edac/socfpga-eccmgr.txt @@ -258,6 +258,49 @@ Required Properties: - compatible : Should be "altr,sdram-edac-s10" - interrupts : Should be single bit error interrupt. +On-Chip RAM ECC +Required Properties: +- compatible : Should be "altr,socfpga-s10-ocram-ecc" +- reg : Address and size for ECC block registers. +- altr,ecc-parent : phandle to parent OCRAM node. +- interrupts : Should be single bit error interrupt. + +Ethernet FIFO ECC +Required Properties: +- compatible : Should be "altr,socfpga-s10-eth-mac-ecc" +- reg : Address and size for ECC block registers. +- altr,ecc-parent : phandle to parent Ethernet node. +- interrupts : Should be single bit error interrupt. + +NAND FIFO ECC +Required Properties: +- compatible : Should be "altr,socfpga-s10-nand-ecc" +- reg : Address and size for ECC block registers. +- altr,ecc-parent : phandle to parent NAND node. +- interrupts : Should be single bit error interrupt. + +DMA FIFO ECC +Required Properties: +- compatible : Should be "altr,socfpga-s10-dma-ecc" +- reg : Address and size for ECC block registers. +- altr,ecc-parent : phandle to parent DMA node. +- interrupts : Should be single bit error interrupt. + +USB FIFO ECC +Required Properties: +- compatible : Should be "altr,socfpga-s10-usb-ecc" +- reg : Address and size for ECC block registers. +- altr,ecc-parent : phandle to parent USB node. +- interrupts : Should be single bit error interrupt. + +SDMMC FIFO ECC +Required Properties: +- compatible : Should be "altr,socfpga-s10-sdmmc-ecc" +- reg : Address and size for ECC block registers. +- altr,ecc-parent : phandle to parent SD/MMC node. +- interrupts : Should be single bit error interrupt for port A + and then single bit error interrupt for port B. + Example: eccmgr { @@ -274,4 +317,67 @@ Example: compatible = "altr,sdram-edac-s10"; interrupts = <16 IRQ_TYPE_LEVEL_HIGH>; }; + + ocram-ecc@ff8cc000 { + compatible = "altr,socfpga-s10-ocram-ecc"; + reg = ; + altr,ecc-parent = <&ocram>; + interrupts = <1 IRQ_TYPE_LEVEL_HIGH>; + }; + + emac0-rx-ecc@ff8c0000 { + compatible = "altr,socfpga-s10-eth-mac-ecc"; + reg = <0xff8c0000 0x100>; + altr,ecc-parent = <&gmac0>; + interrupts = <4 IRQ_TYPE_LEVEL_HIGH>; + }; + + emac0-tx-ecc@ff8c0400 { + compatible = "altr,socfpga-s10-eth-mac-ecc"; + reg = <0xff8c0400 0x100>; + altr,ecc-parent = <&gmac0>; + interrupts = <5 IRQ_TYPE_LEVEL_HIGH>' + }; + + nand-buf-ecc@ff8c8000 { + compatible = "altr,socfpga-s10-nand-ecc"; + reg = <0xff8c8000 0x100>; + altr,ecc-parent = <&nand>; + interrupts = <11 IRQ_TYPE_LEVEL_HIGH>; + }; + + nand-rd-ecc@ff8c8400 { + compatible = "altr,socfpga-s10-nand-ecc"; + reg = <0xff8c8400 0x100>; + altr,ecc-parent = <&nand>; + interrupts = <13 IRQ_TYPE_LEVEL_HIGH>; + }; + + nand-wr-ecc@ff8c8800 { + compatible = "altr,socfpga-s10-nand-ecc"; + reg = <0xff8c8800 0x100>; + altr,ecc-parent = <&nand>; + interrupts = <12 IRQ_TYPE_LEVEL_HIGH>; + }; + + dma-ecc@ff8c9000 { + compatible = "altr,socfpga-s10-dma-ecc"; + reg = <0xff8c9000 0x100>; + altr,ecc-parent = <&pdma>; + interrupts = <10 IRQ_TYPE_LEVEL_HIGH>; + + usb0-ecc@ff8c4000 { + compatible = "altr,socfpga-s10-usb-ecc"; + reg = <0xff8c4000 0x100>; + altr,ecc-parent = <&usb0>; + interrupts = <2 IRQ_TYPE_LEVEL_HIGH>; + }; + + sdmmc-ecc@ff8c8c00 { + compatible = "altr,socfpga-s10-sdmmc-ecc"; + reg = <0xff8c8c00 0x100>; + altr,ecc-parent = <&mmc>; + interrupts = <14 IRQ_TYPE_LEVEL_HIGH>, + <15 IRQ_TYPE_LEVEL_HIGH>; + }; }; -- cgit v1.2.3 From 41475a3ebaceb270e47a77356ddc30960354cb00 Mon Sep 17 00:00:00 2001 From: Petr Vorel Date: Thu, 4 Apr 2019 20:23:22 +0200 Subject: doc/kernel-parameters.txt: Deprecate ima_appraise_tcb Signed-off-by: Petr Vorel Signed-off-by: Mimi Zohar --- Documentation/admin-guide/kernel-parameters.txt | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt index 2b8ee90bb644..45147fc40a57 100644 --- a/Documentation/admin-guide/kernel-parameters.txt +++ b/Documentation/admin-guide/kernel-parameters.txt @@ -1585,7 +1585,7 @@ Format: { "off" | "enforce" | "fix" | "log" } default: "enforce" - ima_appraise_tcb [IMA] + ima_appraise_tcb [IMA] Deprecated. Use ima_policy= instead. The builtin appraise policy appraises all files owned by uid=0. @@ -1612,8 +1612,7 @@ uid=0. The "appraise_tcb" policy appraises the integrity of - all files owned by root. (This is the equivalent - of ima_appraise_tcb.) + all files owned by root. The "secure_boot" policy appraises the integrity of files (eg. kexec kernel image, kernel modules, -- cgit v1.2.3 From c43a4469402f3d909c89af2c4523a786636605ea Mon Sep 17 00:00:00 2001 From: Maxime Ripard Date: Mon, 1 Apr 2019 10:56:41 +0200 Subject: dt-bindings: interconnect: Add a dma interconnect name The current DT bindings assume that the DMA will be performed by the devices through their parent DT node, and rely on that assumption for the address translation using dma-ranges. However, some SoCs have devices that will perform DMA through another bus, with separate address translation rules. We therefore need to express that relationship, through the special interconnect name "dma-mem". Acked-by: Georgi Djakov Signed-off-by: Maxime Ripard Signed-off-by: Rob Herring --- Documentation/devicetree/bindings/interconnect/interconnect.txt | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/interconnect/interconnect.txt b/Documentation/devicetree/bindings/interconnect/interconnect.txt index 5a3c575b387a..6f5d23a605b7 100644 --- a/Documentation/devicetree/bindings/interconnect/interconnect.txt +++ b/Documentation/devicetree/bindings/interconnect/interconnect.txt @@ -51,6 +51,10 @@ interconnect-names : List of interconnect path name strings sorted in the same interconnect-names to match interconnect paths with interconnect specifier pairs. + Reserved interconnect names: + * dma-mem: Path from the device to the main memory of + the system + Example: sdhci@7864000 { -- cgit v1.2.3 From e5ffa40c0305621a0af512ee11d0e1ef199498e5 Mon Sep 17 00:00:00 2001 From: Maxime Ripard Date: Mon, 1 Apr 2019 10:56:42 +0200 Subject: dt-bindings: bus: Add binding for the Allwinner MBUS controller The MBUS controller drives the MBUS that other devices in the SoC will use to perform DMA. It also has a register interface that allows to monitor and control the bandwidth and priorities for masters on that bus. Signed-off-by: Maxime Ripard Signed-off-by: Rob Herring --- .../devicetree/bindings/arm/sunxi/sunxi-mbus.txt | 36 ++++++++++++++++++++++ 1 file changed, 36 insertions(+) create mode 100644 Documentation/devicetree/bindings/arm/sunxi/sunxi-mbus.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/sunxi/sunxi-mbus.txt b/Documentation/devicetree/bindings/arm/sunxi/sunxi-mbus.txt new file mode 100644 index 000000000000..1464a4713553 --- /dev/null +++ b/Documentation/devicetree/bindings/arm/sunxi/sunxi-mbus.txt @@ -0,0 +1,36 @@ +Allwinner Memory Bus (MBUS) controller + +The MBUS controller drives the MBUS that other devices in the SoC will +use to perform DMA. It also has a register interface that allows to +monitor and control the bandwidth and priorities for masters on that +bus. + +Required properties: + - compatible: Must be one of: + - allwinner,sun5i-a13-mbus + - reg: Offset and length of the register set for the controller + - clocks: phandle to the clock driving the controller + - dma-ranges: See section 2.3.9 of the DeviceTree Specification + - #interconnect-cells: Must be one, with the argument being the MBUS + port ID + +Each device having to perform their DMA through the MBUS must have the +interconnects and interconnect-names properties set to the MBUS +controller and with "dma-mem" as the interconnect name. + +Example: + +mbus: dram-controller@1c01000 { + compatible = "allwinner,sun5i-a13-mbus"; + reg = <0x01c01000 0x1000>; + clocks = <&ccu CLK_MBUS>; + dma-ranges = <0x00000000 0x40000000 0x20000000>; + #interconnect-cells = <1>; +}; + +fe0: display-frontend@1e00000 { + compatible = "allwinner,sun5i-a13-display-frontend"; + ... + interconnects = <&mbus 19>; + interconnect-names = "dma-mem"; +}; -- cgit v1.2.3 From a32c3d9d9807edb310afd4b618615b5efca1d5fc Mon Sep 17 00:00:00 2001 From: Maxime Ripard Date: Mon, 1 Apr 2019 13:06:59 +0200 Subject: dt-bindings: Add schemas for simple-framebuffer The simple framebuffer is a binding that allows the bootloader to setup a framebuffer, describe it in the Device Tree for the OS to pick it up and use it as is. Replace the current binding by a schema to allow the validation tools to check those nodes. Cc: Bartlomiej Zolnierkiewicz Cc: Chen-Yu Tsai Cc: Hans de Goede Cc: Maxime Jourdan Signed-off-by: Maxime Ripard Signed-off-by: Rob Herring --- .../display/amlogic,simple-framebuffer.txt | 33 ----- .../bindings/display/simple-framebuffer-sunxi.txt | 36 ----- .../bindings/display/simple-framebuffer.txt | 91 ------------ .../bindings/display/simple-framebuffer.yaml | 160 +++++++++++++++++++++ 4 files changed, 160 insertions(+), 160 deletions(-) delete mode 100644 Documentation/devicetree/bindings/display/amlogic,simple-framebuffer.txt delete mode 100644 Documentation/devicetree/bindings/display/simple-framebuffer-sunxi.txt delete mode 100644 Documentation/devicetree/bindings/display/simple-framebuffer.txt create mode 100644 Documentation/devicetree/bindings/display/simple-framebuffer.yaml (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/display/amlogic,simple-framebuffer.txt b/Documentation/devicetree/bindings/display/amlogic,simple-framebuffer.txt deleted file mode 100644 index aaa6c24c8e70..000000000000 --- a/Documentation/devicetree/bindings/display/amlogic,simple-framebuffer.txt +++ /dev/null @@ -1,33 +0,0 @@ -Meson specific Simple Framebuffer bindings - -This binding documents meson specific extensions to the simple-framebuffer -bindings. The meson simplefb u-boot code relies on the devicetree containing -pre-populated simplefb nodes. - -These extensions are intended so that u-boot can select the right node based -on which pipeline is being used. As such they are solely intended for -firmware / bootloader use, and the OS should ignore them. - -Required properties: -- compatible: "amlogic,simple-framebuffer", "simple-framebuffer" -- amlogic,pipeline, one of: - "vpu-cvbs" - "vpu-hdmi" - -Example: - -chosen { - #address-cells = <2>; - #size-cells = <2>; - ranges; - - simplefb_hdmi: framebuffer-hdmi { - compatible = "amlogic,simple-framebuffer", - "simple-framebuffer"; - amlogic,pipeline = "vpu-hdmi"; - clocks = <&clkc CLKID_HDMI_PCLK>, - <&clkc CLKID_CLK81>, - <&clkc CLKID_GCLK_VENCI_INT0>; - power-domains = <&pwrc_vpu>; - }; -}; diff --git a/Documentation/devicetree/bindings/display/simple-framebuffer-sunxi.txt b/Documentation/devicetree/bindings/display/simple-framebuffer-sunxi.txt deleted file mode 100644 index d693b8dc9a62..000000000000 --- a/Documentation/devicetree/bindings/display/simple-framebuffer-sunxi.txt +++ /dev/null @@ -1,36 +0,0 @@ -Sunxi specific Simple Framebuffer bindings - -This binding documents sunxi specific extensions to the simple-framebuffer -bindings. The sunxi simplefb u-boot code relies on the devicetree containing -pre-populated simplefb nodes. - -These extensions are intended so that u-boot can select the right node based -on which pipeline is being used. As such they are solely intended for -firmware / bootloader use, and the OS should ignore them. - -Required properties: -- compatible: "allwinner,simple-framebuffer" -- allwinner,pipeline, one of: - "de_be0-lcd0" - "de_be1-lcd1" - "de_be0-lcd0-hdmi" - "de_be1-lcd1-hdmi" - "mixer0-lcd0" - "mixer0-lcd0-hdmi" - "mixer1-lcd1-hdmi" - "mixer1-lcd1-tve" - -Example: - -chosen { - #address-cells = <1>; - #size-cells = <1>; - ranges; - - framebuffer@0 { - compatible = "allwinner,simple-framebuffer", "simple-framebuffer"; - allwinner,pipeline = "de_be0-lcd0-hdmi"; - clocks = <&pll5 1>, <&ahb_gates 36>, <&ahb_gates 43>, - <&ahb_gates 44>; - }; -}; diff --git a/Documentation/devicetree/bindings/display/simple-framebuffer.txt b/Documentation/devicetree/bindings/display/simple-framebuffer.txt deleted file mode 100644 index 5a9ce511be88..000000000000 --- a/Documentation/devicetree/bindings/display/simple-framebuffer.txt +++ /dev/null @@ -1,91 +0,0 @@ -Simple Framebuffer - -A simple frame-buffer describes a frame-buffer setup by firmware or -the bootloader, with the assumption that the display hardware has already -been set up to scan out from the memory pointed to by the reg property. - -Since simplefb nodes represent runtime information they must be sub-nodes of -the chosen node (*). Simplefb nodes must be named "framebuffer@

". - -If the devicetree contains nodes for the display hardware used by a simplefb, -then the simplefb node must contain a property called "display", which -contains a phandle pointing to the primary display hw node, so that the OS -knows which simplefb to disable when handing over control to a driver for the -real hardware. The bindings for the hw nodes must specify which node is -considered the primary node. - -It is advised to add display# aliases to help the OS determine how to number -things. If display# aliases are used, then if the simplefb node contains a -"display" property then the /aliases/display# path must point to the display -hw node the "display" property points to, otherwise it must point directly -to the simplefb node. - -If a simplefb node represents the preferred console for user interaction, -then the chosen node's stdout-path property should point to it, or to the -primary display hw node, as with display# aliases. If display aliases are -used then it should be set to the alias instead. - -It is advised that devicetree files contain pre-filled, disabled framebuffer -nodes, so that the firmware only needs to update the mode information and -enable them. This way if e.g. later on support for more display clocks get -added, the simplefb nodes will already contain this info and the firmware -does not need to be updated. - -If pre-filled framebuffer nodes are used, the firmware may need extra -information to find the right node. In that case an extra platform specific -compatible and platform specific properties should be used and documented, -see e.g. simple-framebuffer-sunxi.txt . - -Required properties: -- compatible: "simple-framebuffer" -- reg: Should contain the location and size of the framebuffer memory. -- width: The width of the framebuffer in pixels. -- height: The height of the framebuffer in pixels. -- stride: The number of bytes in each line of the framebuffer. -- format: The format of the framebuffer surface. Valid values are: - - r5g6b5 (16-bit pixels, d[15:11]=r, d[10:5]=g, d[4:0]=b). - - a8b8g8r8 (32-bit pixels, d[31:24]=a, d[23:16]=b, d[15:8]=g, d[7:0]=r). - -Optional properties: -- clocks : List of clocks used by the framebuffer. -- *-supply : Any number of regulators used by the framebuffer. These should - be named according to the names in the device's design. - - The above resources are expected to already be configured correctly. - The OS must ensure they are not modified or disabled while the simple - framebuffer remains active. - -- display : phandle pointing to the primary display hardware node - -Example: - -aliases { - display0 = &lcdc0; -} - -chosen { - framebuffer0: framebuffer@1d385000 { - compatible = "simple-framebuffer"; - reg = <0x1d385000 (1600 * 1200 * 2)>; - width = <1600>; - height = <1200>; - stride = <(1600 * 2)>; - format = "r5g6b5"; - clocks = <&ahb_gates 36>, <&ahb_gates 43>, <&ahb_gates 44>; - lcd-supply = <®_dc1sw>; - display = <&lcdc0>; - }; - stdout-path = "display0"; -}; - -soc@1c00000 { - lcdc0: lcdc@1c0c000 { - compatible = "allwinner,sun4i-a10-lcdc"; - ... - }; -}; - - -*) Older devicetree files may have a compatible = "simple-framebuffer" node -in a different place, operating systems must first enumerate any compatible -nodes found under chosen and then check for other compatible nodes. diff --git a/Documentation/devicetree/bindings/display/simple-framebuffer.yaml b/Documentation/devicetree/bindings/display/simple-framebuffer.yaml new file mode 100644 index 000000000000..b052d76cf8b6 --- /dev/null +++ b/Documentation/devicetree/bindings/display/simple-framebuffer.yaml @@ -0,0 +1,160 @@ +# SPDX-License-Identifier: GPL-2.0 +%YAML 1.2 +--- +$id: http://devicetree.org/schemas/display/simple-framebuffer.yaml# +$schema: http://devicetree.org/meta-schemas/core.yaml# + +title: Simple Framebuffer Device Tree Bindings + +maintainers: + - Bartlomiej Zolnierkiewicz + - Hans de Goede + +description: |+ + A simple frame-buffer describes a frame-buffer setup by firmware or + the bootloader, with the assumption that the display hardware has + already been set up to scan out from the memory pointed to by the + reg property. + + Since simplefb nodes represent runtime information they must be + sub-nodes of the chosen node (*). Simplefb nodes must be named + framebuffer@
. + + If the devicetree contains nodes for the display hardware used by a + simplefb, then the simplefb node must contain a property called + display, which contains a phandle pointing to the primary display + hw node, so that the OS knows which simplefb to disable when handing + over control to a driver for the real hardware. The bindings for the + hw nodes must specify which node is considered the primary node. + + It is advised to add display# aliases to help the OS determine how + to number things. If display# aliases are used, then if the simplefb + node contains a display property then the /aliases/display# path + must point to the display hw node the display property points to, + otherwise it must point directly to the simplefb node. + + If a simplefb node represents the preferred console for user + interaction, then the chosen node stdout-path property should point + to it, or to the primary display hw node, as with display# + aliases. If display aliases are used then it should be set to the + alias instead. + + It is advised that devicetree files contain pre-filled, disabled + framebuffer nodes, so that the firmware only needs to update the + mode information and enable them. This way if e.g. later on support + for more display clocks get added, the simplefb nodes will already + contain this info and the firmware does not need to be updated. + + If pre-filled framebuffer nodes are used, the firmware may need + extra information to find the right node. In that case an extra + platform specific compatible and platform specific properties should + be used and documented. + +properties: + compatible: + items: + - enum: + - allwinner,simple-framebuffer + - amlogic,simple-framebuffer + - const: simple-framebuffer + + reg: + description: Location and size of the framebuffer memory + + clocks: + description: List of clocks used by the framebuffer. + + power-domains: + description: List of power domains used by the framebuffer. + + width: + $ref: /schemas/types.yaml#/definitions/uint32 + description: Width of the framebuffer in pixels + + height: + $ref: /schemas/types.yaml#/definitions/uint32 + description: Height of the framebuffer in pixels + + stride: + $ref: /schemas/types.yaml#/definitions/uint32 + description: Number of bytes of a line in the framebuffer + + format: + description: > + Format of the framebuffer: + * `a8b8g8r8` - 32-bit pixels, d[31:24]=a, d[23:16]=b, d[15:8]=g, d[7:0]=r + * `r5g6b5` - 16-bit pixels, d[15:11]=r, d[10:5]=g, d[4:0]=b + enum: + - a8b8g8r8 + - r5g6b5 + + display: + $ref: /schemas/types.yaml#/definitions/phandle + description: Primary display hardware node + + allwinner,pipeline: + description: Pipeline used by the framebuffer on Allwinner SoCs + enum: + - de_be0-lcd0 + - de_be0-lcd0-hdmi + - de_be0-lcd0-tve0 + - de_be1-lcd0 + - de_be1-lcd1-hdmi + - de_fe0-de_be0-lcd0 + - de_fe0-de_be0-lcd0-hdmi + - de_fe0-de_be0-lcd0-tve0 + - mixer0-lcd0 + - mixer0-lcd0-hdmi + - mixer1-lcd1-hdmi + - mixer1-lcd1-tve + + amlogic,pipeline: + description: Pipeline used by the framebuffer on Amlogic SoCs + enum: + - vpu-cvbs + - vpu-hdmi + +patternProperties: + "^[a-zA-Z0-9-]+-supply$": + $ref: /schemas/types.yaml#/definitions/phandle + description: + Regulators used by the framebuffer. These should be named + according to the names in the device design. + +required: + # The binding requires also reg, width, height, stride and format, + # but usually they will be filled by the bootloader. + - compatible + +additionalProperties: false + +examples: + - | + aliases { + display0 = &lcdc0; + }; + + chosen { + #address-cells = <1>; + #size-cells = <1>; + stdout-path = "display0"; + framebuffer0: framebuffer@1d385000 { + compatible = "simple-framebuffer"; + reg = <0x1d385000 3840000>; + width = <1600>; + height = <1200>; + stride = <3200>; + format = "r5g6b5"; + clocks = <&ahb_gates 36>, <&ahb_gates 43>, <&ahb_gates 44>; + lcd-supply = <®_dc1sw>; + display = <&lcdc0>; + }; + }; + + soc@1c00000 { + lcdc0: lcdc@1c0c000 { + compatible = "allwinner,sun4i-a10-lcdc"; + }; + }; + +... -- cgit v1.2.3 From 12eeae7147af32f7d3bbf0f1753313f88b8ce97b Mon Sep 17 00:00:00 2001 From: Miquel Raynal Date: Mon, 1 Apr 2019 15:09:00 +0200 Subject: dt-bindings: connector: Spelling mistake Cosmetic change multpile -> multiple. Fixes: 593aa2b405f9 ("dt-bindings: add bindings for USB physical connector") Signed-off-by: Miquel Raynal Signed-off-by: Rob Herring --- Documentation/devicetree/bindings/connector/usb-connector.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/connector/usb-connector.txt b/Documentation/devicetree/bindings/connector/usb-connector.txt index a9a2f2fc44f2..cef556d4e5ee 100644 --- a/Documentation/devicetree/bindings/connector/usb-connector.txt +++ b/Documentation/devicetree/bindings/connector/usb-connector.txt @@ -47,7 +47,7 @@ Required properties for usb-c-connector with power delivery support: Required nodes: - any data bus to the connector should be modeled using the OF graph bindings specified in bindings/graph.txt, unless the bus is between parent node and - the connector. Since single connector can have multpile data buses every bus + the connector. Since single connector can have multiple data buses every bus has assigned OF graph port number as follows: 0: High Speed (HS), present in all connectors, 1: Super Speed (SS), present in SS capable connectors, -- cgit v1.2.3 From e51fb2536aeafb729cf919f99418f88026c773e9 Mon Sep 17 00:00:00 2001 From: Bruno Thomsen Date: Wed, 3 Apr 2019 08:44:23 +0200 Subject: dt-bindings: add vendor prefix for TQ Systems GmbH TQ is a German embedded System-on-Module manufacture. Signed-off-by: Bruno Thomsen Reviewed-by: Rob Herring Signed-off-by: Shawn Guo --- Documentation/devicetree/bindings/vendor-prefixes.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/vendor-prefixes.txt b/Documentation/devicetree/bindings/vendor-prefixes.txt index 192249f30ab9..520f6186b352 100644 --- a/Documentation/devicetree/bindings/vendor-prefixes.txt +++ b/Documentation/devicetree/bindings/vendor-prefixes.txt @@ -416,6 +416,7 @@ toumaz Toumaz tpk TPK U.S.A. LLC tplink TP-LINK Technologies Co., Ltd. tpo TPO +tq TQ Systems GmbH tronfy Tronfy tronsmart Tronsmart truly Truly Semiconductors Limited -- cgit v1.2.3 From e2f6a7630fc1545c18f1648ca27ac5b3ca2abe13 Mon Sep 17 00:00:00 2001 From: Bruno Thomsen Date: Wed, 3 Apr 2019 08:44:24 +0200 Subject: dt-bindings: arm: add TQ boards MBa is a series of Carrier Boards / Single Board Computers (SBC) for evaluation of TQMa SoMs. The MBa7 carrier board can only interface with TQMa7 modules. The TQMa7 module can only be mounted with NXP i.MX7 Solo or Dual SoCs. Primary compatible strings are of the form "tq,-". Signed-off-by: Bruno Thomsen Reviewed-by: Rob Herring Signed-off-by: Shawn Guo --- Documentation/devicetree/bindings/arm/fsl.yaml | 7 +++++++ 1 file changed, 7 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/fsl.yaml b/Documentation/devicetree/bindings/arm/fsl.yaml index 3c7ad36ebd35..e762975f8c44 100644 --- a/Documentation/devicetree/bindings/arm/fsl.yaml +++ b/Documentation/devicetree/bindings/arm/fsl.yaml @@ -138,10 +138,17 @@ properties: - const: fsl,imx6ull # This seems odd. Should be last? - const: fsl,imx6ulz + - description: i.MX7S based Boards + items: + - enum: + - tq,imx7s-mba7 # i.MX7S TQ MBa7 with TQMa7S SoM + - const: fsl,imx7s + - description: i.MX7D based Boards items: - enum: - fsl,imx7d-sdb # i.MX7 SabreSD Board + - tq,imx7d-mba7 # i.MX7D TQ MBa7 with TQMa7D SoM - const: fsl,imx7d - description: -- cgit v1.2.3 From 189733b0a7e4147d55aa1b26f8741dcc82615ea5 Mon Sep 17 00:00:00 2001 From: Jonathan Neuschäfer Date: Sun, 31 Mar 2019 21:16:00 +0200 Subject: dt-bindings: Add vendor prefix for Rakuten Kobo, Inc. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Rakuten Kobo, Inc. (formerly Kobo, Inc.) is a company that sells e-book readers and related products. More information is available at: - https://en.wikipedia.org/wiki/Kobo_Inc. - https://www.kobo.com/ Signed-off-by: Jonathan Neuschäfer Reviewed-by: Rob Herring Signed-off-by: Shawn Guo --- Documentation/devicetree/bindings/vendor-prefixes.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/vendor-prefixes.txt b/Documentation/devicetree/bindings/vendor-prefixes.txt index 520f6186b352..fbb6f30dbb1b 100644 --- a/Documentation/devicetree/bindings/vendor-prefixes.txt +++ b/Documentation/devicetree/bindings/vendor-prefixes.txt @@ -210,6 +210,7 @@ kiebackpeter Kieback & Peter GmbH kinetic Kinetic Technologies kingdisplay King & Display Technology Co., Ltd. kingnovel Kingnovel Technology Co., Ltd. +kobo Rakuten Kobo Inc. koe Kaohsiung Opto-Electronics Inc. kosagi Sutajio Ko-Usagi PTE Ltd. kyo Kyocera Corporation -- cgit v1.2.3 From 42b3862658d94b2f9cd625200db4adf50f4b338f Mon Sep 17 00:00:00 2001 From: Jonathan Neuschäfer Date: Sun, 31 Mar 2019 21:16:01 +0200 Subject: dt-bindings: arm: fsl: Add i.MX50 based boards MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit fsl,imx50-evk has been used in a devicetree for a while. kobo,aura will be used soon. Signed-off-by: Jonathan Neuschäfer Signed-off-by: Shawn Guo --- Documentation/devicetree/bindings/arm/fsl.yaml | 7 +++++++ 1 file changed, 7 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/fsl.yaml b/Documentation/devicetree/bindings/arm/fsl.yaml index e762975f8c44..06762fe57227 100644 --- a/Documentation/devicetree/bindings/arm/fsl.yaml +++ b/Documentation/devicetree/bindings/arm/fsl.yaml @@ -51,6 +51,13 @@ properties: - const: i2se,duckbill-2 - const: fsl,imx28 + - description: i.MX50 based Boards + items: + - enum: + - fsl,imx50-evk + - kobo,aura + - const: fsl,imx50 + - description: i.MX51 Babbage Board items: - enum: -- cgit v1.2.3 From 9ad593bc959f9aea22df151c323eb0ed9a65c98f Mon Sep 17 00:00:00 2001 From: Anson Huang Date: Tue, 9 Apr 2019 04:59:49 +0000 Subject: dt-bindings: fsl: scu: add general interrupt support Add scu general interrupt function support. Signed-off-by: Anson Huang Reviewed-by: Rob Herring Reviewed-by: Dong Aisheng Signed-off-by: Shawn Guo --- .../devicetree/bindings/arm/freescale/fsl,scu.txt | 29 +++++++++++++++++----- 1 file changed, 23 insertions(+), 6 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/freescale/fsl,scu.txt b/Documentation/devicetree/bindings/arm/freescale/fsl,scu.txt index 72d481c8dd48..5d7dbabbb784 100644 --- a/Documentation/devicetree/bindings/arm/freescale/fsl,scu.txt +++ b/Documentation/devicetree/bindings/arm/freescale/fsl,scu.txt @@ -22,9 +22,11 @@ Required properties: ------------------- - compatible: should be "fsl,imx-scu". - mbox-names: should include "tx0", "tx1", "tx2", "tx3", - "rx0", "rx1", "rx2", "rx3". -- mboxes: List of phandle of 4 MU channels for tx and 4 MU channels - for rx. All 8 MU channels must be in the same MU instance. + "rx0", "rx1", "rx2", "rx3"; + include "gip3" if want to support general MU interrupt. +- mboxes: List of phandle of 4 MU channels for tx, 4 MU channels for + rx, and 1 optional MU channel for general interrupt. + All MU channels must be in the same MU instance. Cross instances are not allowed. The MU instance can only be one of LSIO MU0~M4 for imx8qxp and imx8qm. Users need to make sure use the one which is not conflict with other @@ -34,6 +36,7 @@ Required properties: Channel 1 must be "tx1" or "rx1". Channel 2 must be "tx2" or "rx2". Channel 3 must be "tx3" or "rx3". + General interrupt rx channel must be "gip3". e.g. mboxes = <&lsio_mu1 0 0 &lsio_mu1 0 1 @@ -42,10 +45,18 @@ Required properties: &lsio_mu1 1 0 &lsio_mu1 1 1 &lsio_mu1 1 2 - &lsio_mu1 1 3>; + &lsio_mu1 1 3 + &lsio_mu1 3 3>; See Documentation/devicetree/bindings/mailbox/fsl,mu.txt for detailed mailbox binding. +Note: Each mu which supports general interrupt should have an alias correctly +numbered in "aliases" node. +e.g. +aliases { + mu1 = &lsio_mu1; +}; + i.MX SCU Client Device Node: ============================================================ @@ -124,6 +135,10 @@ Required properties: Example (imx8qxp): ------------- +aliases { + mu1 = &lsio_mu1; +}; + lsio_mu1: mailbox@5d1c0000 { ... #mbox-cells = <2>; @@ -133,7 +148,8 @@ firmware { scu { compatible = "fsl,imx-scu"; mbox-names = "tx0", "tx1", "tx2", "tx3", - "rx0", "rx1", "rx2", "rx3"; + "rx0", "rx1", "rx2", "rx3", + "gip3"; mboxes = <&lsio_mu1 0 0 &lsio_mu1 0 1 &lsio_mu1 0 2 @@ -141,7 +157,8 @@ firmware { &lsio_mu1 1 0 &lsio_mu1 1 1 &lsio_mu1 1 2 - &lsio_mu1 1 3>; + &lsio_mu1 1 3 + &lsio_mu1 3 3>; clk: clk { compatible = "fsl,imx8qxp-clk", "fsl,scu-clk"; -- cgit v1.2.3 From 47fe944138a6e34697e1778a74eff00ed9472b2a Mon Sep 17 00:00:00 2001 From: Kishon Vijay Abraham I Date: Mon, 25 Mar 2019 15:09:24 +0530 Subject: dt-bindings: PCI: keystone: Add "reg-names" binding information Add "reg-names" binding information in order for device tree node to be populated with the correct register strings. This will break old DT compatibility. However Keystone PCI has never worked in upstream kernel due to lack of SERDES support, so, before SERDES support is added, cleanup the Keystone PCI dt-bindings. This new binding will also be used by PCI in AM654 platform. Signed-off-by: Kishon Vijay Abraham I Signed-off-by: Lorenzo Pieralisi Reviewed-by: Rob Herring --- Documentation/devicetree/bindings/pci/pci-keystone.txt | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/pci/pci-keystone.txt b/Documentation/devicetree/bindings/pci/pci-keystone.txt index 2030ee0dc4f9..3a551687cfa2 100644 --- a/Documentation/devicetree/bindings/pci/pci-keystone.txt +++ b/Documentation/devicetree/bindings/pci/pci-keystone.txt @@ -12,8 +12,10 @@ described here as well as properties that are not applicable. Required Properties:- compatibility: "ti,keystone-pcie" -reg: index 1 is the base address and length of DW application registers. - index 2 is the base address and length of PCI device ID register. +reg: Three register ranges as listed in the reg-names property +reg-names: "dbics" for the DesignWare PCIe registers, "app" for the + TI specific application registers, "config" for the + configuration space address pcie_msi_intc : Interrupt controller device node for MSI IRQ chip interrupt-cells: should be set to 1 -- cgit v1.2.3 From 0cde62a46e88499cf3f62e3682248a3489488f08 Mon Sep 17 00:00:00 2001 From: Will Deacon Date: Wed, 10 Apr 2019 14:01:06 +0100 Subject: docs/memory-barriers.txt: Fix style, spacing and grammar in I/O section Commit 4614bbdee357 ("docs/memory-barriers.txt: Rewrite "KERNEL I/O BARRIER EFFECTS" section") rewrote the I/O ordering section of memory-barriers.txt. Subsequently, Ingo noticed a number of issues with the style, spacing and grammar of the rewritten section. Fix them based on his suggestions. Link: https://lkml.kernel.org/r/20190410105833.GA116161@gmail.com Fixes: 4614bbdee357 ("docs/memory-barriers.txt: Rewrite "KERNEL I/O BARRIER EFFECTS" section") Reported-by: Ingo Molnar Acked-by: Ingo Molnar Signed-off-by: Will Deacon --- Documentation/memory-barriers.txt | 124 ++++++++++++++++++++------------------ 1 file changed, 66 insertions(+), 58 deletions(-) (limited to 'Documentation') diff --git a/Documentation/memory-barriers.txt b/Documentation/memory-barriers.txt index 3522f0cc772f..1660dde75e14 100644 --- a/Documentation/memory-barriers.txt +++ b/Documentation/memory-barriers.txt @@ -2517,80 +2517,88 @@ guarantees: (*) readX(), writeX(): - The readX() and writeX() MMIO accessors take a pointer to the peripheral - being accessed as an __iomem * parameter. For pointers mapped with the - default I/O attributes (e.g. those returned by ioremap()), then the - ordering guarantees are as follows: - - 1. All readX() and writeX() accesses to the same peripheral are ordered - with respect to each other. For example, this ensures that MMIO register - writes by the CPU to a particular device will arrive in program order. - - 2. A writeX() by the CPU to the peripheral will first wait for the - completion of all prior CPU writes to memory. For example, this ensures - that writes by the CPU to an outbound DMA buffer allocated by - dma_alloc_coherent() will be visible to a DMA engine when the CPU writes - to its MMIO control register to trigger the transfer. - - 3. A readX() by the CPU from the peripheral will complete before any - subsequent CPU reads from memory can begin. For example, this ensures - that reads by the CPU from an incoming DMA buffer allocated by - dma_alloc_coherent() will not see stale data after reading from the DMA - engine's MMIO status register to establish that the DMA transfer has - completed. - - 4. A readX() by the CPU from the peripheral will complete before any - subsequent delay() loop can begin execution. For example, this ensures - that two MMIO register writes by the CPU to a peripheral will arrive at - least 1us apart if the first write is immediately read back with readX() - and udelay(1) is called prior to the second writeX(). - - __iomem pointers obtained with non-default attributes (e.g. those returned - by ioremap_wc()) are unlikely to provide many of these guarantees. + The readX() and writeX() MMIO accessors take a pointer to the + peripheral being accessed as an __iomem * parameter. For pointers + mapped with the default I/O attributes (e.g. those returned by + ioremap()), the ordering guarantees are as follows: + + 1. All readX() and writeX() accesses to the same peripheral are ordered + with respect to each other. This ensures that MMIO register writes by + the CPU to a particular device will arrive in program order. + + 2. A writeX() by the CPU to the peripheral will first wait for the + completion of all prior CPU writes to memory. This ensures that + writes by the CPU to an outbound DMA buffer allocated by + dma_alloc_coherent() will be visible to a DMA engine when the CPU + writes to its MMIO control register to trigger the transfer. + + 3. A readX() by the CPU from the peripheral will complete before any + subsequent CPU reads from memory can begin. This ensures that reads + by the CPU from an incoming DMA buffer allocated by + dma_alloc_coherent() will not see stale data after reading from the + DMA engine's MMIO status register to establish that the DMA transfer + has completed. + + 4. A readX() by the CPU from the peripheral will complete before any + subsequent delay() loop can begin execution. This ensures that two + MMIO register writes by the CPU to a peripheral will arrive at least + 1us apart if the first write is immediately read back with readX() + and udelay(1) is called prior to the second writeX(): + + writel(42, DEVICE_REGISTER_0); // Arrives at the device... + readl(DEVICE_REGISTER_0); + udelay(1); + writel(42, DEVICE_REGISTER_1); // ...at least 1us before this. + + The ordering properties of __iomem pointers obtained with non-default + attributes (e.g. those returned by ioremap_wc()) are specific to the + underlying architecture and therefore the guarantees listed above cannot + generally be relied upon for accesses to these types of mappings. (*) readX_relaxed(), writeX_relaxed(): - These are similar to readX() and writeX(), but provide weaker memory - ordering guarantees. Specifically, they do not guarantee ordering with - respect to normal memory accesses or delay() loops (i.e bullets 2-4 above) - but they are still guaranteed to be ordered with respect to other accesses - to the same peripheral when operating on __iomem pointers mapped with the - default I/O attributes. + These are similar to readX() and writeX(), but provide weaker memory + ordering guarantees. Specifically, they do not guarantee ordering with + respect to normal memory accesses or delay() loops (i.e. bullets 2-4 + above) but they are still guaranteed to be ordered with respect to other + accesses to the same peripheral when operating on __iomem pointers + mapped with the default I/O attributes. (*) readsX(), writesX(): - The readsX() and writesX() MMIO accessors are designed for accessing - register-based, memory-mapped FIFOs residing on peripherals that are not - capable of performing DMA. Consequently, they provide only the ordering - guarantees of readX_relaxed() and writeX_relaxed(), as documented above. + The readsX() and writesX() MMIO accessors are designed for accessing + register-based, memory-mapped FIFOs residing on peripherals that are not + capable of performing DMA. Consequently, they provide only the ordering + guarantees of readX_relaxed() and writeX_relaxed(), as documented above. (*) inX(), outX(): - The inX() and outX() accessors are intended to access legacy port-mapped - I/O peripherals, which may require special instructions on some - architectures (notably x86). The port number of the peripheral being - accessed is passed as an argument. + The inX() and outX() accessors are intended to access legacy port-mapped + I/O peripherals, which may require special instructions on some + architectures (notably x86). The port number of the peripheral being + accessed is passed as an argument. - Since many CPU architectures ultimately access these peripherals via an - internal virtual memory mapping, the portable ordering guarantees provided - by inX() and outX() are the same as those provided by readX() and writeX() - respectively when accessing a mapping with the default I/O attributes. + Since many CPU architectures ultimately access these peripherals via an + internal virtual memory mapping, the portable ordering guarantees + provided by inX() and outX() are the same as those provided by readX() + and writeX() respectively when accessing a mapping with the default I/O + attributes. - Device drivers may expect outX() to emit a non-posted write transaction - that waits for a completion response from the I/O peripheral before - returning. This is not guaranteed by all architectures and is therefore - not part of the portable ordering semantics. + Device drivers may expect outX() to emit a non-posted write transaction + that waits for a completion response from the I/O peripheral before + returning. This is not guaranteed by all architectures and is therefore + not part of the portable ordering semantics. (*) insX(), outsX(): - As above, the insX() and outsX() accessors provide the same ordering - guarantees as readsX() and writesX() respectively when accessing a mapping - with the default I/O attributes. + As above, the insX() and outsX() accessors provide the same ordering + guarantees as readsX() and writesX() respectively when accessing a + mapping with the default I/O attributes. - (*) ioreadX(), iowriteX() + (*) ioreadX(), iowriteX(): - These will perform appropriately for the type of access they're actually - doing, be it inX()/outX() or readX()/writeX(). + These will perform appropriately for the type of access they're actually + doing, be it inX()/outX() or readX()/writeX(). All of these accessors assume that the underlying peripheral is little-endian, and will therefore perform byte-swapping operations on big-endian architectures. -- cgit v1.2.3 From 15e384c446d93d00ab96d34bf2a5c308e3b3d16b Mon Sep 17 00:00:00 2001 From: Alexandre Belloni Date: Tue, 9 Apr 2019 14:35:45 +0200 Subject: dt-bindings: gpio: pca953x: document the nxp,pca6416 The NXP PCA6416 is a variant of the PCA GPIO expander, with 16 GPIOs. Signed-off-by: Alexandre Belloni Signed-off-by: Linus Walleij --- Documentation/devicetree/bindings/gpio/gpio-pca953x.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/gpio/gpio-pca953x.txt b/Documentation/devicetree/bindings/gpio/gpio-pca953x.txt index 8678df2a5713..dab537c20def 100644 --- a/Documentation/devicetree/bindings/gpio/gpio-pca953x.txt +++ b/Documentation/devicetree/bindings/gpio/gpio-pca953x.txt @@ -2,6 +2,7 @@ Required properties: - compatible: Has to contain one of the following: + nxp,pca6416 nxp,pca9505 nxp,pca9534 nxp,pca9535 -- cgit v1.2.3 From 9fda5130d31cd0c008560122ca147034e504b63b Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 10 Apr 2019 06:56:20 -0300 Subject: docs: DMA-API-HOWTO: add a missing "=" The === line is shorter than the section title. As this will generate a warning with rst build, fix it. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/DMA-API-HOWTO.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/DMA-API-HOWTO.txt b/Documentation/DMA-API-HOWTO.txt index 1a721d0f35c8..db48c6fd3162 100644 --- a/Documentation/DMA-API-HOWTO.txt +++ b/Documentation/DMA-API-HOWTO.txt @@ -147,7 +147,7 @@ networking subsystems make sure that the buffers they use are valid for you to DMA from/to. DMA addressing capabilities -========================== +=========================== By default, the kernel assumes that your device can address 32-bits of DMA addressing. For a 64-bit capable device, this needs to be increased, and for -- cgit v1.2.3 From 49618364689cdfb89985e6fe8d21ba4079f947fc Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 10 Apr 2019 06:56:21 -0300 Subject: docs: atomic_bitops.txt: add a title for this document This document misses a title. Add it, in order to follow the documentation standard. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/atomic_bitops.txt | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/atomic_bitops.txt b/Documentation/atomic_bitops.txt index be70b32c95d9..093cdaefdb37 100644 --- a/Documentation/atomic_bitops.txt +++ b/Documentation/atomic_bitops.txt @@ -1,6 +1,6 @@ - -On atomic bitops. - +============= +Atomic bitops +============= While our bitmap_{}() functions are non-atomic, we have a number of operations operating on single bits in a bitmap that are atomic. -- cgit v1.2.3 From 26187d18b8d1be18a21bd84419cf89080fecfa1f Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 10 Apr 2019 06:56:22 -0300 Subject: docs: clearing-warn-once.txt: add a title for this document This document misses a title. Add it, in order to follow the documentation standard. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/clearing-warn-once.txt | 2 ++ 1 file changed, 2 insertions(+) (limited to 'Documentation') diff --git a/Documentation/clearing-warn-once.txt b/Documentation/clearing-warn-once.txt index 5b1f5d547be1..4aa938262d0e 100644 --- a/Documentation/clearing-warn-once.txt +++ b/Documentation/clearing-warn-once.txt @@ -1,3 +1,5 @@ +Clearing WARN_ONCE +------------------ WARN_ONCE / WARN_ON_ONCE only print a warning once. -- cgit v1.2.3 From 3ac10b02557361fbe5e4cd351a3594369be25774 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 10 Apr 2019 06:56:23 -0300 Subject: docs: ntb.txt: use Sphinx notation for the two ascii figures In order to make it to build with Sphinx, we need to fix the notation for two ascii artwork. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/ntb.txt | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) (limited to 'Documentation') diff --git a/Documentation/ntb.txt b/Documentation/ntb.txt index a043854d28df..344a075f81f5 100644 --- a/Documentation/ntb.txt +++ b/Documentation/ntb.txt @@ -41,9 +41,10 @@ mainly used to perform the proper memory window initialization. Typically there are two types of memory window interfaces supported by the NTB API: inbound translation configured on the local ntb port and outbound translation configured by the peer, on the peer ntb port. The first type is -depicted on the next figure +depicted on the next figure:: + + Inbound translation: -Inbound translation: Memory: Local NTB Port: Peer NTB Port: Peer MMIO: ____________ | dma-mapped |-ntb_mw_set_trans(addr) | @@ -58,9 +59,10 @@ maps corresponding outbound memory window so to have access to the shared memory region. The second type of interface, that implies the shared windows being -initialized by a peer device, is depicted on the figure: +initialized by a peer device, is depicted on the figure:: + + Outbound translation: -Outbound translation: Memory: Local NTB Port: Peer NTB Port: Peer MMIO: ____________ ______________ | dma-mapped | | | MW base addr |<== memory-mapped IO -- cgit v1.2.3 From 0da3e3e3643288cbce4acf55284ecca168a7b728 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 10 Apr 2019 06:56:24 -0300 Subject: docs: unaligned-memory-access.txt: use a lowercase title As all other titles at the documentation, use lower case for its title. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/unaligned-memory-access.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/unaligned-memory-access.txt b/Documentation/unaligned-memory-access.txt index 51b4ff031586..1ee82419d8aa 100644 --- a/Documentation/unaligned-memory-access.txt +++ b/Documentation/unaligned-memory-access.txt @@ -1,5 +1,5 @@ ========================= -UNALIGNED MEMORY ACCESSES +Unaligned Memory Accesses ========================= :Author: Daniel Drake , -- cgit v1.2.3 From cf566e1ee2a736967ee89915dbdcfcb7903988d6 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 10 Apr 2019 06:56:25 -0300 Subject: docs: video-output.txt: convert it to ReST format This file doesn't follow the documentation style we use within the Kernel. Fix it. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/video-output.txt | 52 +++++++++++++++++++++--------------------- 1 file changed, 26 insertions(+), 26 deletions(-) (limited to 'Documentation') diff --git a/Documentation/video-output.txt b/Documentation/video-output.txt index e517011be4f9..56d6fa2e2368 100644 --- a/Documentation/video-output.txt +++ b/Documentation/video-output.txt @@ -1,34 +1,34 @@ +Video Output Switcher Control +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - Video Output Switcher Control - ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - 2006 luming.yu@intel.com +2006 luming.yu@intel.com The output sysfs class driver provides an abstract video output layer that can be used to hook platform specific methods to enable/disable video output device through common sysfs interface. For example, on my IBM ThinkPad T42 laptop, The ACPI video driver registered its output devices and read/write -method for 'state' with output sysfs class. The user interface under sysfs is: +method for 'state' with output sysfs class. The user interface under sysfs is:: -linux:/sys/class/video_output # tree . -. -|-- CRT0 -| |-- device -> ../../../devices/pci0000:00/0000:00:01.0 -| |-- state -| |-- subsystem -> ../../../class/video_output -| `-- uevent -|-- DVI0 -| |-- device -> ../../../devices/pci0000:00/0000:00:01.0 -| |-- state -| |-- subsystem -> ../../../class/video_output -| `-- uevent -|-- LCD0 -| |-- device -> ../../../devices/pci0000:00/0000:00:01.0 -| |-- state -| |-- subsystem -> ../../../class/video_output -| `-- uevent -`-- TV0 - |-- device -> ../../../devices/pci0000:00/0000:00:01.0 - |-- state - |-- subsystem -> ../../../class/video_output - `-- uevent + linux:/sys/class/video_output # tree . + . + |-- CRT0 + | |-- device -> ../../../devices/pci0000:00/0000:00:01.0 + | |-- state + | |-- subsystem -> ../../../class/video_output + | `-- uevent + |-- DVI0 + | |-- device -> ../../../devices/pci0000:00/0000:00:01.0 + | |-- state + | |-- subsystem -> ../../../class/video_output + | `-- uevent + |-- LCD0 + | |-- device -> ../../../devices/pci0000:00/0000:00:01.0 + | |-- state + | |-- subsystem -> ../../../class/video_output + | `-- uevent + `-- TV0 + |-- device -> ../../../devices/pci0000:00/0000:00:01.0 + |-- state + |-- subsystem -> ../../../class/video_output + `-- uevent -- cgit v1.2.3 From 59bc64f0d07cceda125b85d17749f58178606aeb Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 10 Apr 2019 06:56:26 -0300 Subject: docs: ntb.txt: add blank lines to clean up some Sphinx warnings In order to make it easier to parse and produce the right output, add some extra blank lines. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/ntb.txt | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'Documentation') diff --git a/Documentation/ntb.txt b/Documentation/ntb.txt index 344a075f81f5..074a423c853c 100644 --- a/Documentation/ntb.txt +++ b/Documentation/ntb.txt @@ -77,11 +77,13 @@ outbound memory window so to have access to the shared memory region. As one can see the described scenarios can be combined in one portable algorithm. + Local device: 1) Allocate memory for a shared window 2) Initialize memory window by translated address of the allocated region (it may fail if local memory window initialization is unsupported) 3) Send the translated address and memory window index to a peer device + Peer device: 1) Initialize memory window with retrieved address of the allocated by another device memory region (it may fail if peer memory window @@ -90,6 +92,7 @@ algorithm. In accordance with this scenario, the NTB Memory Window API can be used as follows: + Local device: 1) ntb_mw_count(pidx) - retrieve number of memory ranges, which can be allocated for memory windows between local device and peer device @@ -105,6 +108,7 @@ follows: 5) Send translated base address (usually together with memory window number) to the peer device using, for instance, scratchpad or message registers. + Peer device: 1) ntb_peer_mw_set_trans(pidx, midx) - try to set received from other device (related to pidx) translated address for specified memory -- cgit v1.2.3 From 5d2a2c59108a00ee550fd9a51f26de72e209a703 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 10 Apr 2019 06:56:27 -0300 Subject: docs: speculation.txt: mark example blocks as such Identify the example blocks there, in order to avoid Sphinx warnings. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/speculation.txt | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) (limited to 'Documentation') diff --git a/Documentation/speculation.txt b/Documentation/speculation.txt index e9e6cbae2841..50d7ea857cff 100644 --- a/Documentation/speculation.txt +++ b/Documentation/speculation.txt @@ -17,7 +17,7 @@ observed to extract secret information. For example, in the presence of branch prediction, it is possible for bounds checks to be ignored by code which is speculatively executed. Consider the -following code: +following code:: int load_array(int *array, unsigned int index) { @@ -27,7 +27,7 @@ following code: return array[index]; } -Which, on arm64, may be compiled to an assembly sequence such as: +Which, on arm64, may be compiled to an assembly sequence such as:: CMP , #MAX_ARRAY_ELEMS B.LT less @@ -44,7 +44,7 @@ microarchitectural state which can be subsequently measured. More complex sequences involving multiple dependent memory accesses may result in sensitive information being leaked. Consider the following -code, building on the prior example: +code, building on the prior example:: int load_dependent_arrays(int *arr1, int *arr2, int index) { @@ -77,7 +77,7 @@ A call to array_index_nospec(index, size) returns a sanitized index value that is bounded to [0, size) even under cpu speculation conditions. -This can be used to protect the earlier load_array() example: +This can be used to protect the earlier load_array() example:: int load_array(int *array, unsigned int index) { -- cgit v1.2.3 From 2f41cd9b13ea891e7cc1bd037b70458132a12e31 Mon Sep 17 00:00:00 2001 From: Weiyi Lu Date: Tue, 5 Mar 2019 13:05:41 +0800 Subject: dt-bindings: ARM: Mediatek: Document bindings for MT8183 This patch adds the binding documentation for apmixedsys, audiosys, camsys, imgsys, infracfg, mcucfg, mfgcfg, mmsys, topckgen, vdecsys, vencsys and ipu for Mediatek MT8183. Signed-off-by: Weiyi Lu Reviewed-by: Rob Herring Acked-by: Stephen Boyd Signed-off-by: Stephen Boyd --- .../bindings/arm/mediatek/mediatek,apmixedsys.txt | 1 + .../bindings/arm/mediatek/mediatek,audsys.txt | 1 + .../bindings/arm/mediatek/mediatek,camsys.txt | 22 +++++++++++ .../bindings/arm/mediatek/mediatek,imgsys.txt | 1 + .../bindings/arm/mediatek/mediatek,infracfg.txt | 1 + .../bindings/arm/mediatek/mediatek,ipu.txt | 43 ++++++++++++++++++++++ .../bindings/arm/mediatek/mediatek,mcucfg.txt | 1 + .../bindings/arm/mediatek/mediatek,mfgcfg.txt | 1 + .../bindings/arm/mediatek/mediatek,mmsys.txt | 1 + .../bindings/arm/mediatek/mediatek,topckgen.txt | 1 + .../bindings/arm/mediatek/mediatek,vdecsys.txt | 1 + .../bindings/arm/mediatek/mediatek,vencsys.txt | 1 + 12 files changed, 75 insertions(+) create mode 100644 Documentation/devicetree/bindings/arm/mediatek/mediatek,camsys.txt create mode 100644 Documentation/devicetree/bindings/arm/mediatek/mediatek,ipu.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/mediatek/mediatek,apmixedsys.txt b/Documentation/devicetree/bindings/arm/mediatek/mediatek,apmixedsys.txt index de4075413d91..9adf28d0141b 100644 --- a/Documentation/devicetree/bindings/arm/mediatek/mediatek,apmixedsys.txt +++ b/Documentation/devicetree/bindings/arm/mediatek/mediatek,apmixedsys.txt @@ -14,6 +14,7 @@ Required Properties: - "mediatek,mt7629-apmixedsys" - "mediatek,mt8135-apmixedsys" - "mediatek,mt8173-apmixedsys" + - "mediatek,mt8183-apmixedsys", "syscon" - #clock-cells: Must be 1 The apmixedsys controller uses the common clk binding from diff --git a/Documentation/devicetree/bindings/arm/mediatek/mediatek,audsys.txt b/Documentation/devicetree/bindings/arm/mediatek/mediatek,audsys.txt index d1606b2c3e63..f3cef1a6d95c 100644 --- a/Documentation/devicetree/bindings/arm/mediatek/mediatek,audsys.txt +++ b/Documentation/devicetree/bindings/arm/mediatek/mediatek,audsys.txt @@ -9,6 +9,7 @@ Required Properties: - "mediatek,mt2701-audsys", "syscon" - "mediatek,mt7622-audsys", "syscon" - "mediatek,mt7623-audsys", "mediatek,mt2701-audsys", "syscon" + - "mediatek,mt8183-audiosys", "syscon" - #clock-cells: Must be 1 The AUDSYS controller uses the common clk binding from diff --git a/Documentation/devicetree/bindings/arm/mediatek/mediatek,camsys.txt b/Documentation/devicetree/bindings/arm/mediatek/mediatek,camsys.txt new file mode 100644 index 000000000000..d8930f64aa98 --- /dev/null +++ b/Documentation/devicetree/bindings/arm/mediatek/mediatek,camsys.txt @@ -0,0 +1,22 @@ +MediaTek CAMSYS controller +============================ + +The MediaTek camsys controller provides various clocks to the system. + +Required Properties: + +- compatible: Should be one of: + - "mediatek,mt8183-camsys", "syscon" +- #clock-cells: Must be 1 + +The camsys controller uses the common clk binding from +Documentation/devicetree/bindings/clock/clock-bindings.txt +The available clocks are defined in dt-bindings/clock/mt*-clk.h. + +Example: + +camsys: camsys@1a000000 { + compatible = "mediatek,mt8183-camsys", "syscon"; + reg = <0 0x1a000000 0 0x1000>; + #clock-cells = <1>; +}; diff --git a/Documentation/devicetree/bindings/arm/mediatek/mediatek,imgsys.txt b/Documentation/devicetree/bindings/arm/mediatek/mediatek,imgsys.txt index 3f99672163e3..e3bc4a1e7a6e 100644 --- a/Documentation/devicetree/bindings/arm/mediatek/mediatek,imgsys.txt +++ b/Documentation/devicetree/bindings/arm/mediatek/mediatek,imgsys.txt @@ -11,6 +11,7 @@ Required Properties: - "mediatek,mt6797-imgsys", "syscon" - "mediatek,mt7623-imgsys", "mediatek,mt2701-imgsys", "syscon" - "mediatek,mt8173-imgsys", "syscon" + - "mediatek,mt8183-imgsys", "syscon" - #clock-cells: Must be 1 The imgsys controller uses the common clk binding from diff --git a/Documentation/devicetree/bindings/arm/mediatek/mediatek,infracfg.txt b/Documentation/devicetree/bindings/arm/mediatek/mediatek,infracfg.txt index 417bd83d1378..0b324d216724 100644 --- a/Documentation/devicetree/bindings/arm/mediatek/mediatek,infracfg.txt +++ b/Documentation/devicetree/bindings/arm/mediatek/mediatek,infracfg.txt @@ -15,6 +15,7 @@ Required Properties: - "mediatek,mt7629-infracfg", "syscon" - "mediatek,mt8135-infracfg", "syscon" - "mediatek,mt8173-infracfg", "syscon" + - "mediatek,mt8183-infracfg", "syscon" - #clock-cells: Must be 1 - #reset-cells: Must be 1 diff --git a/Documentation/devicetree/bindings/arm/mediatek/mediatek,ipu.txt b/Documentation/devicetree/bindings/arm/mediatek/mediatek,ipu.txt new file mode 100644 index 000000000000..aabc8c5c8ed2 --- /dev/null +++ b/Documentation/devicetree/bindings/arm/mediatek/mediatek,ipu.txt @@ -0,0 +1,43 @@ +Mediatek IPU controller +============================ + +The Mediatek ipu controller provides various clocks to the system. + +Required Properties: + +- compatible: Should be one of: + - "mediatek,mt8183-ipu_conn", "syscon" + - "mediatek,mt8183-ipu_adl", "syscon" + - "mediatek,mt8183-ipu_core0", "syscon" + - "mediatek,mt8183-ipu_core1", "syscon" +- #clock-cells: Must be 1 + +The ipu controller uses the common clk binding from +Documentation/devicetree/bindings/clock/clock-bindings.txt +The available clocks are defined in dt-bindings/clock/mt*-clk.h. + +Example: + +ipu_conn: syscon@19000000 { + compatible = "mediatek,mt8183-ipu_conn", "syscon"; + reg = <0 0x19000000 0 0x1000>; + #clock-cells = <1>; +}; + +ipu_adl: syscon@19010000 { + compatible = "mediatek,mt8183-ipu_adl", "syscon"; + reg = <0 0x19010000 0 0x1000>; + #clock-cells = <1>; +}; + +ipu_core0: syscon@19180000 { + compatible = "mediatek,mt8183-ipu_core0", "syscon"; + reg = <0 0x19180000 0 0x1000>; + #clock-cells = <1>; +}; + +ipu_core1: syscon@19280000 { + compatible = "mediatek,mt8183-ipu_core1", "syscon"; + reg = <0 0x19280000 0 0x1000>; + #clock-cells = <1>; +}; diff --git a/Documentation/devicetree/bindings/arm/mediatek/mediatek,mcucfg.txt b/Documentation/devicetree/bindings/arm/mediatek/mediatek,mcucfg.txt index b8fb03f3613e..2b882b7ca72e 100644 --- a/Documentation/devicetree/bindings/arm/mediatek/mediatek,mcucfg.txt +++ b/Documentation/devicetree/bindings/arm/mediatek/mediatek,mcucfg.txt @@ -7,6 +7,7 @@ Required Properties: - compatible: Should be one of: - "mediatek,mt2712-mcucfg", "syscon" + - "mediatek,mt8183-mcucfg", "syscon" - #clock-cells: Must be 1 The mcucfg controller uses the common clk binding from diff --git a/Documentation/devicetree/bindings/arm/mediatek/mediatek,mfgcfg.txt b/Documentation/devicetree/bindings/arm/mediatek/mediatek,mfgcfg.txt index 859e67b416d5..72787e7dd227 100644 --- a/Documentation/devicetree/bindings/arm/mediatek/mediatek,mfgcfg.txt +++ b/Documentation/devicetree/bindings/arm/mediatek/mediatek,mfgcfg.txt @@ -7,6 +7,7 @@ Required Properties: - compatible: Should be one of: - "mediatek,mt2712-mfgcfg", "syscon" + - "mediatek,mt8183-mfgcfg", "syscon" - #clock-cells: Must be 1 The mfgcfg controller uses the common clk binding from diff --git a/Documentation/devicetree/bindings/arm/mediatek/mediatek,mmsys.txt b/Documentation/devicetree/bindings/arm/mediatek/mediatek,mmsys.txt index 15d977afad31..545eab717c96 100644 --- a/Documentation/devicetree/bindings/arm/mediatek/mediatek,mmsys.txt +++ b/Documentation/devicetree/bindings/arm/mediatek/mediatek,mmsys.txt @@ -11,6 +11,7 @@ Required Properties: - "mediatek,mt6797-mmsys", "syscon" - "mediatek,mt7623-mmsys", "mediatek,mt2701-mmsys", "syscon" - "mediatek,mt8173-mmsys", "syscon" + - "mediatek,mt8183-mmsys", "syscon" - #clock-cells: Must be 1 The mmsys controller uses the common clk binding from diff --git a/Documentation/devicetree/bindings/arm/mediatek/mediatek,topckgen.txt b/Documentation/devicetree/bindings/arm/mediatek/mediatek,topckgen.txt index d160c2b4b6fe..46a1cfeb8b1d 100644 --- a/Documentation/devicetree/bindings/arm/mediatek/mediatek,topckgen.txt +++ b/Documentation/devicetree/bindings/arm/mediatek/mediatek,topckgen.txt @@ -14,6 +14,7 @@ Required Properties: - "mediatek,mt7629-topckgen" - "mediatek,mt8135-topckgen" - "mediatek,mt8173-topckgen" + - "mediatek,mt8183-topckgen", "syscon" - #clock-cells: Must be 1 The topckgen controller uses the common clk binding from diff --git a/Documentation/devicetree/bindings/arm/mediatek/mediatek,vdecsys.txt b/Documentation/devicetree/bindings/arm/mediatek/mediatek,vdecsys.txt index 3212afc753c8..57176bb8dbb5 100644 --- a/Documentation/devicetree/bindings/arm/mediatek/mediatek,vdecsys.txt +++ b/Documentation/devicetree/bindings/arm/mediatek/mediatek,vdecsys.txt @@ -11,6 +11,7 @@ Required Properties: - "mediatek,mt6797-vdecsys", "syscon" - "mediatek,mt7623-vdecsys", "mediatek,mt2701-vdecsys", "syscon" - "mediatek,mt8173-vdecsys", "syscon" + - "mediatek,mt8183-vdecsys", "syscon" - #clock-cells: Must be 1 The vdecsys controller uses the common clk binding from diff --git a/Documentation/devicetree/bindings/arm/mediatek/mediatek,vencsys.txt b/Documentation/devicetree/bindings/arm/mediatek/mediatek,vencsys.txt index 851545357e94..c9faa6269087 100644 --- a/Documentation/devicetree/bindings/arm/mediatek/mediatek,vencsys.txt +++ b/Documentation/devicetree/bindings/arm/mediatek/mediatek,vencsys.txt @@ -9,6 +9,7 @@ Required Properties: - "mediatek,mt2712-vencsys", "syscon" - "mediatek,mt6797-vencsys", "syscon" - "mediatek,mt8173-vencsys", "syscon" + - "mediatek,mt8183-vencsys", "syscon" - #clock-cells: Must be 1 The vencsys controller uses the common clk binding from -- cgit v1.2.3 From 5f19c6e936f2300fa236773a4aef3b4ec8aaad7c Mon Sep 17 00:00:00 2001 From: Bjorn Andersson Date: Wed, 6 Mar 2019 09:47:56 -0800 Subject: dt-bindings: clock: Introduce Qualcomm Turing Clock controller Add devicetree binding for the turing clock controller found in QCS404. Signed-off-by: Bjorn Andersson Reviewed-by: Rob Herring Signed-off-by: Stephen Boyd --- .../devicetree/bindings/clock/qcom,turingcc.txt | 19 +++++++++++++++++++ include/dt-bindings/clock/qcom,turingcc-qcs404.h | 15 +++++++++++++++ 2 files changed, 34 insertions(+) create mode 100644 Documentation/devicetree/bindings/clock/qcom,turingcc.txt create mode 100644 include/dt-bindings/clock/qcom,turingcc-qcs404.h (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/clock/qcom,turingcc.txt b/Documentation/devicetree/bindings/clock/qcom,turingcc.txt new file mode 100644 index 000000000000..126517de5f9a --- /dev/null +++ b/Documentation/devicetree/bindings/clock/qcom,turingcc.txt @@ -0,0 +1,19 @@ +Qualcomm Turing Clock & Reset Controller Binding +------------------------------------------------ + +Required properties : +- compatible: shall contain "qcom,qcs404-turingcc". +- reg: shall contain base register location and length. +- clocks: ahb clock for the TuringCC +- #clock-cells: from common clock binding, shall contain 1. +- #reset-cells: from common reset binding, shall contain 1. + +Example: + turingcc: clock-controller@800000 { + compatible = "qcom,qcs404-turingcc"; + reg = <0x00800000 0x30000>; + clocks = <&gcc GCC_CDSP_CFG_AHB_CLK>; + + #clock-cells = <1>; + #reset-cells = <1>; + }; diff --git a/include/dt-bindings/clock/qcom,turingcc-qcs404.h b/include/dt-bindings/clock/qcom,turingcc-qcs404.h new file mode 100644 index 000000000000..838faef57c67 --- /dev/null +++ b/include/dt-bindings/clock/qcom,turingcc-qcs404.h @@ -0,0 +1,15 @@ +/* SPDX-License-Identifier: GPL-2.0 */ +/* + * Copyright (c) 2019, Linaro Ltd + */ + +#ifndef _DT_BINDINGS_CLK_TURING_QCS404_H +#define _DT_BINDINGS_CLK_TURING_QCS404_H + +#define TURING_Q6SS_Q6_AXIM_CLK 0 +#define TURING_Q6SS_AHBM_AON_CLK 1 +#define TURING_WRAPPER_AON_CLK 2 +#define TURING_Q6SS_AHBS_AON_CLK 3 +#define TURING_WRAPPER_QOS_AHBS_AON_CLK 4 + +#endif -- cgit v1.2.3 From badd9f19f1992218b771c72e0cdc8825dd45938c Mon Sep 17 00:00:00 2001 From: Jean-Philippe Brucker Date: Thu, 11 Apr 2019 13:40:26 +0100 Subject: dt-bindings: Add "external-facing" PCIe port property Provide a way for the firmware to tell the OS which devices are external to the machine and therefore untrusted. The property can describe for example Thunderbolt and other user-accessible ports, which should always have the strongest IOMMU protection. Signed-off-by: Jean-Philippe Brucker Signed-off-by: Bjorn Helgaas Reviewed-by: Grant Likely Reviewed-by: Rob Herring Reviewed-by: Robin Murphy --- Documentation/devicetree/bindings/pci/pci.txt | 50 +++++++++++++++++++++++++++ 1 file changed, 50 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/pci/pci.txt b/Documentation/devicetree/bindings/pci/pci.txt index c77981c5dd18..92c01db610df 100644 --- a/Documentation/devicetree/bindings/pci/pci.txt +++ b/Documentation/devicetree/bindings/pci/pci.txt @@ -24,3 +24,53 @@ driver implementation may support the following properties: unsupported link speed, for instance, trying to do training for unsupported link speed, etc. Must be '4' for gen4, '3' for gen3, '2' for gen2, and '1' for gen1. Any other values are invalid. + +PCI-PCI Bridge properties +------------------------- + +PCIe root ports and switch ports may be described explicitly in the device +tree, as children of the host bridge node. Even though those devices are +discoverable by probing, it might be necessary to describe properties that +aren't provided by standard PCIe capabilities. + +Required properties: + +- reg: + Identifies the PCI-PCI bridge. As defined in the IEEE Std 1275-1994 + document, it is a five-cell address encoded as (phys.hi phys.mid + phys.lo size.hi size.lo). phys.hi should contain the device's BDF as + 0b00000000 bbbbbbbb dddddfff 00000000. The other cells should be zero. + + The bus number is defined by firmware, through the standard bridge + configuration mechanism. If this port is a switch port, then firmware + allocates the bus number and writes it into the Secondary Bus Number + register of the bridge directly above this port. Otherwise, the bus + number of a root port is the first number in the bus-range property, + defaulting to zero. + + If firmware leaves the ARI Forwarding Enable bit set in the bridge + above this port, then phys.hi contains the 8-bit function number as + 0b00000000 bbbbbbbb ffffffff 00000000. Note that the PCIe specification + recommends that firmware only leaves ARI enabled when it knows that the + OS is ARI-aware. + +Optional properties: + +- external-facing: + When present, the port is external-facing. All bridges and endpoints + downstream of this port are external to the machine. The OS can, for + example, use this information to identify devices that cannot be + trusted with relaxed DMA protection, as users could easily attach + malicious devices to this port. + +Example: + +pcie@10000000 { + compatible = "pci-host-ecam-generic"; + ... + pcie@0008 { + /* Root port 00:01.0 is external-facing */ + reg = <0x00000800 0 0 0 0>; + external-facing; + }; +}; -- cgit v1.2.3 From 837f74116585dcd235fae1696e1e1471b6bb9e01 Mon Sep 17 00:00:00 2001 From: Nicolas Dichtel Date: Tue, 9 Apr 2019 17:16:59 +0200 Subject: xfrm: update doc about xfrm[46]_gc_thresh Those entries are not used anymore. CC: Florian Westphal Fixes: 09c7570480f7 ("xfrm: remove flow cache") Signed-off-by: Nicolas Dichtel Signed-off-by: Steffen Klassert --- Documentation/networking/ip-sysctl.txt | 2 ++ 1 file changed, 2 insertions(+) (limited to 'Documentation') diff --git a/Documentation/networking/ip-sysctl.txt b/Documentation/networking/ip-sysctl.txt index acdfb5d2bcaa..f1843b132453 100644 --- a/Documentation/networking/ip-sysctl.txt +++ b/Documentation/networking/ip-sysctl.txt @@ -1336,6 +1336,7 @@ tag - INTEGER Default value is 0. xfrm4_gc_thresh - INTEGER + (Obsolete since linux-4.14) The threshold at which we will start garbage collecting for IPv4 destination cache entries. At twice this value the system will refuse new allocations. @@ -1919,6 +1920,7 @@ echo_ignore_all - BOOLEAN Default: 0 xfrm6_gc_thresh - INTEGER + (Obsolete since linux-4.14) The threshold at which we will start garbage collecting for IPv6 destination cache entries. At twice this value the system will refuse new allocations. -- cgit v1.2.3 From 09f837546edfe7f79774a39f99ed8401bb9285f2 Mon Sep 17 00:00:00 2001 From: Roger Quadros Date: Fri, 5 Apr 2019 16:28:05 +0300 Subject: dt-binding: arm: omap: Add information for AM5748 Add DT binding details for AM5748 SoC and AM5748 IDK. Signed-off-by: Roger Quadros Signed-off-by: Tony Lindgren --- Documentation/devicetree/bindings/arm/omap/omap.txt | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/omap/omap.txt b/Documentation/devicetree/bindings/arm/omap/omap.txt index 2ecc712bf707..1c1e48fd94b5 100644 --- a/Documentation/devicetree/bindings/arm/omap/omap.txt +++ b/Documentation/devicetree/bindings/arm/omap/omap.txt @@ -92,6 +92,9 @@ SoCs: - DRA718 compatible = "ti,dra718", "ti,dra722", "ti,dra72", "ti,dra7" +- AM5748 + compatible = "ti,am5748", "ti,dra762", "ti,dra7" + - AM5728 compatible = "ti,am5728", "ti,dra742", "ti,dra74", "ti,dra7" @@ -184,6 +187,9 @@ Boards: - AM57XX SBC-AM57x compatible = "compulab,sbc-am57x", "compulab,cl-som-am57x", "ti,am5728", "ti,dra742", "ti,dra74", "ti,dra7" +- AM5748 IDK + compatible = "ti,am5748-idk", "ti,am5748", "ti,dra762", "ti,dra7"; + - AM5728 IDK compatible = "ti,am5728-idk", "ti,am5728", "ti,dra742", "ti,dra74", "ti,dra7" -- cgit v1.2.3 From df8c9581e258e9e9d50d0653094cc64fcbc7d8fc Mon Sep 17 00:00:00 2001 From: Erin Lo Date: Fri, 15 Feb 2019 14:02:33 +0800 Subject: dt-bindings: mtk-sysirq: Add compatible for Mediatek MT8183 This adds dt-binding documentation of SYSIRQ for Mediatek MT8183 SoC Platform. Signed-off-by: Erin Lo Acked-by: Rob Herring Reviewed-by: Matthias Brugger Signed-off-by: Matthias Brugger --- .../devicetree/bindings/interrupt-controller/mediatek,sysirq.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/interrupt-controller/mediatek,sysirq.txt b/Documentation/devicetree/bindings/interrupt-controller/mediatek,sysirq.txt index c5d589108a94..ade059db0aa3 100644 --- a/Documentation/devicetree/bindings/interrupt-controller/mediatek,sysirq.txt +++ b/Documentation/devicetree/bindings/interrupt-controller/mediatek,sysirq.txt @@ -5,6 +5,7 @@ interrupt. Required properties: - compatible: should be + "mediatek,mt8183-sysirq", "mediatek,mt6577-sysirq": for MT8183 "mediatek,mt8173-sysirq", "mediatek,mt6577-sysirq": for MT8173 "mediatek,mt8135-sysirq", "mediatek,mt6577-sysirq": for MT8135 "mediatek,mt8127-sysirq", "mediatek,mt6577-sysirq": for MT8127 -- cgit v1.2.3 From 4bad8b0709f59cc210207201b2cba86e4fc28bf5 Mon Sep 17 00:00:00 2001 From: Fabien Parent Date: Sat, 23 Mar 2019 22:15:51 +0100 Subject: dt-bindings: pwrap: mediatek: add pwrap support for MT8516 Add binding documentation of pwrap for MT8516 SoCs. Signed-off-by: Fabien Parent Acked-by: Rob Herring Signed-off-by: Matthias Brugger --- Documentation/devicetree/bindings/soc/mediatek/pwrap.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/soc/mediatek/pwrap.txt b/Documentation/devicetree/bindings/soc/mediatek/pwrap.txt index 5a2ef1726e2a..7a32404c6114 100644 --- a/Documentation/devicetree/bindings/soc/mediatek/pwrap.txt +++ b/Documentation/devicetree/bindings/soc/mediatek/pwrap.txt @@ -25,6 +25,7 @@ Required properties in pwrap device node. "mediatek,mt8135-pwrap" for MT8135 SoCs "mediatek,mt8173-pwrap" for MT8173 SoCs "mediatek,mt8183-pwrap" for MT8183 SoCs + "mediatek,mt8516-pwrap" for MT8516 SoCs - interrupts: IRQ for pwrap in SOC - reg-names: Must include the following entries: "pwrap": Main registers base -- cgit v1.2.3 From 3c91d114832027b75a6518734081a2507c5d7a87 Mon Sep 17 00:00:00 2001 From: Ioana Ciornei Date: Fri, 12 Apr 2019 14:55:18 +0300 Subject: Documentation: net: dsa: transition to the rst format This patch also performs some minor adjustments such as numbering for the receive path sequence, conversion of keywords to inline literals and adding an index page so it looks better in the output of 'make htmldocs'. Signed-off-by: Ioana Ciornei Signed-off-by: David S. Miller --- Documentation/networking/dsa/bcm_sf2.rst | 115 ++++++ Documentation/networking/dsa/bcm_sf2.txt | 114 ------ Documentation/networking/dsa/dsa.rst | 587 +++++++++++++++++++++++++++++++ Documentation/networking/dsa/dsa.txt | 584 ------------------------------ Documentation/networking/dsa/index.rst | 10 + Documentation/networking/dsa/lan9303.rst | 37 ++ Documentation/networking/dsa/lan9303.txt | 37 -- Documentation/networking/index.rst | 1 + 8 files changed, 750 insertions(+), 735 deletions(-) create mode 100644 Documentation/networking/dsa/bcm_sf2.rst delete mode 100644 Documentation/networking/dsa/bcm_sf2.txt create mode 100644 Documentation/networking/dsa/dsa.rst delete mode 100644 Documentation/networking/dsa/dsa.txt create mode 100644 Documentation/networking/dsa/index.rst create mode 100644 Documentation/networking/dsa/lan9303.rst delete mode 100644 Documentation/networking/dsa/lan9303.txt (limited to 'Documentation') diff --git a/Documentation/networking/dsa/bcm_sf2.rst b/Documentation/networking/dsa/bcm_sf2.rst new file mode 100644 index 000000000000..dee234039e1e --- /dev/null +++ b/Documentation/networking/dsa/bcm_sf2.rst @@ -0,0 +1,115 @@ +============================================= +Broadcom Starfighter 2 Ethernet switch driver +============================================= + +Broadcom's Starfighter 2 Ethernet switch hardware block is commonly found and +deployed in the following products: + +- xDSL gateways such as BCM63138 +- streaming/multimedia Set Top Box such as BCM7445 +- Cable Modem/residential gateways such as BCM7145/BCM3390 + +The switch is typically deployed in a configuration involving between 5 to 13 +ports, offering a range of built-in and customizable interfaces: + +- single integrated Gigabit PHY +- quad integrated Gigabit PHY +- quad external Gigabit PHY w/ MDIO multiplexer +- integrated MoCA PHY +- several external MII/RevMII/GMII/RGMII interfaces + +The switch also supports specific congestion control features which allow MoCA +fail-over not to lose packets during a MoCA role re-election, as well as out of +band back-pressure to the host CPU network interface when downstream interfaces +are connected at a lower speed. + +The switch hardware block is typically interfaced using MMIO accesses and +contains a bunch of sub-blocks/registers: + +- ``SWITCH_CORE``: common switch registers +- ``SWITCH_REG``: external interfaces switch register +- ``SWITCH_MDIO``: external MDIO bus controller (there is another one in SWITCH_CORE, + which is used for indirect PHY accesses) +- ``SWITCH_INDIR_RW``: 64-bits wide register helper block +- ``SWITCH_INTRL2_0/1``: Level-2 interrupt controllers +- ``SWITCH_ACB``: Admission control block +- ``SWITCH_FCB``: Fail-over control block + +Implementation details +====================== + +The driver is located in ``drivers/net/dsa/bcm_sf2.c`` and is implemented as a DSA +driver; see ``Documentation/networking/dsa/dsa.rst`` for details on the subsystem +and what it provides. + +The SF2 switch is configured to enable a Broadcom specific 4-bytes switch tag +which gets inserted by the switch for every packet forwarded to the CPU +interface, conversely, the CPU network interface should insert a similar tag for +packets entering the CPU port. The tag format is described in +``net/dsa/tag_brcm.c``. + +Overall, the SF2 driver is a fairly regular DSA driver; there are a few +specifics covered below. + +Device Tree probing +------------------- + +The DSA platform device driver is probed using a specific compatible string +provided in ``net/dsa/dsa.c``. The reason for that is because the DSA subsystem gets +registered as a platform device driver currently. DSA will provide the needed +device_node pointers which are then accessible by the switch driver setup +function to setup resources such as register ranges and interrupts. This +currently works very well because none of the of_* functions utilized by the +driver require a struct device to be bound to a struct device_node, but things +may change in the future. + +MDIO indirect accesses +---------------------- + +Due to a limitation in how Broadcom switches have been designed, external +Broadcom switches connected to a SF2 require the use of the DSA slave MDIO bus +in order to properly configure them. By default, the SF2 pseudo-PHY address, and +an external switch pseudo-PHY address will both be snooping for incoming MDIO +transactions, since they are at the same address (30), resulting in some kind of +"double" programming. Using DSA, and setting ``ds->phys_mii_mask`` accordingly, we +selectively divert reads and writes towards external Broadcom switches +pseudo-PHY addresses. Newer revisions of the SF2 hardware have introduced a +configurable pseudo-PHY address which circumvents the initial design limitation. + +Multimedia over CoAxial (MoCA) interfaces +----------------------------------------- + +MoCA interfaces are fairly specific and require the use of a firmware blob which +gets loaded onto the MoCA processor(s) for packet processing. The switch +hardware contains logic which will assert/de-assert link states accordingly for +the MoCA interface whenever the MoCA coaxial cable gets disconnected or the +firmware gets reloaded. The SF2 driver relies on such events to properly set its +MoCA interface carrier state and properly report this to the networking stack. + +The MoCA interfaces are supported using the PHY library's fixed PHY/emulated PHY +device and the switch driver registers a ``fixed_link_update`` callback for such +PHYs which reflects the link state obtained from the interrupt handler. + + +Power Management +---------------- + +Whenever possible, the SF2 driver tries to minimize the overall switch power +consumption by applying a combination of: + +- turning off internal buffers/memories +- disabling packet processing logic +- putting integrated PHYs in IDDQ/low-power +- reducing the switch core clock based on the active port count +- enabling and advertising EEE +- turning off RGMII data processing logic when the link goes down + +Wake-on-LAN +----------- + +Wake-on-LAN is currently implemented by utilizing the host processor Ethernet +MAC controller wake-on logic. Whenever Wake-on-LAN is requested, an intersection +between the user request and the supported host Ethernet interface WoL +capabilities is done and the intersection result gets configured. During +system-wide suspend/resume, only ports not participating in Wake-on-LAN are +disabled. diff --git a/Documentation/networking/dsa/bcm_sf2.txt b/Documentation/networking/dsa/bcm_sf2.txt deleted file mode 100644 index eba3a2431e91..000000000000 --- a/Documentation/networking/dsa/bcm_sf2.txt +++ /dev/null @@ -1,114 +0,0 @@ -Broadcom Starfighter 2 Ethernet switch driver -============================================= - -Broadcom's Starfighter 2 Ethernet switch hardware block is commonly found and -deployed in the following products: - -- xDSL gateways such as BCM63138 -- streaming/multimedia Set Top Box such as BCM7445 -- Cable Modem/residential gateways such as BCM7145/BCM3390 - -The switch is typically deployed in a configuration involving between 5 to 13 -ports, offering a range of built-in and customizable interfaces: - -- single integrated Gigabit PHY -- quad integrated Gigabit PHY -- quad external Gigabit PHY w/ MDIO multiplexer -- integrated MoCA PHY -- several external MII/RevMII/GMII/RGMII interfaces - -The switch also supports specific congestion control features which allow MoCA -fail-over not to lose packets during a MoCA role re-election, as well as out of -band back-pressure to the host CPU network interface when downstream interfaces -are connected at a lower speed. - -The switch hardware block is typically interfaced using MMIO accesses and -contains a bunch of sub-blocks/registers: - -* SWITCH_CORE: common switch registers -* SWITCH_REG: external interfaces switch register -* SWITCH_MDIO: external MDIO bus controller (there is another one in SWITCH_CORE, - which is used for indirect PHY accesses) -* SWITCH_INDIR_RW: 64-bits wide register helper block -* SWITCH_INTRL2_0/1: Level-2 interrupt controllers -* SWITCH_ACB: Admission control block -* SWITCH_FCB: Fail-over control block - -Implementation details -====================== - -The driver is located in drivers/net/dsa/bcm_sf2.c and is implemented as a DSA -driver; see Documentation/networking/dsa/dsa.txt for details on the subsystem -and what it provides. - -The SF2 switch is configured to enable a Broadcom specific 4-bytes switch tag -which gets inserted by the switch for every packet forwarded to the CPU -interface, conversely, the CPU network interface should insert a similar tag for -packets entering the CPU port. The tag format is described in -net/dsa/tag_brcm.c. - -Overall, the SF2 driver is a fairly regular DSA driver; there are a few -specifics covered below. - -Device Tree probing -------------------- - -The DSA platform device driver is probed using a specific compatible string -provided in net/dsa/dsa.c. The reason for that is because the DSA subsystem gets -registered as a platform device driver currently. DSA will provide the needed -device_node pointers which are then accessible by the switch driver setup -function to setup resources such as register ranges and interrupts. This -currently works very well because none of the of_* functions utilized by the -driver require a struct device to be bound to a struct device_node, but things -may change in the future. - -MDIO indirect accesses ----------------------- - -Due to a limitation in how Broadcom switches have been designed, external -Broadcom switches connected to a SF2 require the use of the DSA slave MDIO bus -in order to properly configure them. By default, the SF2 pseudo-PHY address, and -an external switch pseudo-PHY address will both be snooping for incoming MDIO -transactions, since they are at the same address (30), resulting in some kind of -"double" programming. Using DSA, and setting ds->phys_mii_mask accordingly, we -selectively divert reads and writes towards external Broadcom switches -pseudo-PHY addresses. Newer revisions of the SF2 hardware have introduced a -configurable pseudo-PHY address which circumvents the initial design limitation. - -Multimedia over CoAxial (MoCA) interfaces ------------------------------------------ - -MoCA interfaces are fairly specific and require the use of a firmware blob which -gets loaded onto the MoCA processor(s) for packet processing. The switch -hardware contains logic which will assert/de-assert link states accordingly for -the MoCA interface whenever the MoCA coaxial cable gets disconnected or the -firmware gets reloaded. The SF2 driver relies on such events to properly set its -MoCA interface carrier state and properly report this to the networking stack. - -The MoCA interfaces are supported using the PHY library's fixed PHY/emulated PHY -device and the switch driver registers a fixed_link_update callback for such -PHYs which reflects the link state obtained from the interrupt handler. - - -Power Management ----------------- - -Whenever possible, the SF2 driver tries to minimize the overall switch power -consumption by applying a combination of: - -- turning off internal buffers/memories -- disabling packet processing logic -- putting integrated PHYs in IDDQ/low-power -- reducing the switch core clock based on the active port count -- enabling and advertising EEE -- turning off RGMII data processing logic when the link goes down - -Wake-on-LAN ------------ - -Wake-on-LAN is currently implemented by utilizing the host processor Ethernet -MAC controller wake-on logic. Whenever Wake-on-LAN is requested, an intersection -between the user request and the supported host Ethernet interface WoL -capabilities is done and the intersection result gets configured. During -system-wide suspend/resume, only ports not participating in Wake-on-LAN are -disabled. diff --git a/Documentation/networking/dsa/dsa.rst b/Documentation/networking/dsa/dsa.rst new file mode 100644 index 000000000000..ca87068b9ab9 --- /dev/null +++ b/Documentation/networking/dsa/dsa.rst @@ -0,0 +1,587 @@ +============ +Architecture +============ + +This document describes the **Distributed Switch Architecture (DSA)** subsystem +design principles, limitations, interactions with other subsystems, and how to +develop drivers for this subsystem as well as a TODO for developers interested +in joining the effort. + +Design principles +================= + +The Distributed Switch Architecture is a subsystem which was primarily designed +to support Marvell Ethernet switches (MV88E6xxx, a.k.a Linkstreet product line) +using Linux, but has since evolved to support other vendors as well. + +The original philosophy behind this design was to be able to use unmodified +Linux tools such as bridge, iproute2, ifconfig to work transparently whether +they configured/queried a switch port network device or a regular network +device. + +An Ethernet switch is typically comprised of multiple front-panel ports, and one +or more CPU or management port. The DSA subsystem currently relies on the +presence of a management port connected to an Ethernet controller capable of +receiving Ethernet frames from the switch. This is a very common setup for all +kinds of Ethernet switches found in Small Home and Office products: routers, +gateways, or even top-of-the rack switches. This host Ethernet controller will +be later referred to as "master" and "cpu" in DSA terminology and code. + +The D in DSA stands for Distributed, because the subsystem has been designed +with the ability to configure and manage cascaded switches on top of each other +using upstream and downstream Ethernet links between switches. These specific +ports are referred to as "dsa" ports in DSA terminology and code. A collection +of multiple switches connected to each other is called a "switch tree". + +For each front-panel port, DSA will create specialized network devices which are +used as controlling and data-flowing endpoints for use by the Linux networking +stack. These specialized network interfaces are referred to as "slave" network +interfaces in DSA terminology and code. + +The ideal case for using DSA is when an Ethernet switch supports a "switch tag" +which is a hardware feature making the switch insert a specific tag for each +Ethernet frames it received to/from specific ports to help the management +interface figure out: + +- what port is this frame coming from +- what was the reason why this frame got forwarded +- how to send CPU originated traffic to specific ports + +The subsystem does support switches not capable of inserting/stripping tags, but +the features might be slightly limited in that case (traffic separation relies +on Port-based VLAN IDs). + +Note that DSA does not currently create network interfaces for the "cpu" and +"dsa" ports because: + +- the "cpu" port is the Ethernet switch facing side of the management + controller, and as such, would create a duplication of feature, since you + would get two interfaces for the same conduit: master netdev, and "cpu" netdev + +- the "dsa" port(s) are just conduits between two or more switches, and as such + cannot really be used as proper network interfaces either, only the + downstream, or the top-most upstream interface makes sense with that model + +Switch tagging protocols +------------------------ + +DSA currently supports 5 different tagging protocols, and a tag-less mode as +well. The different protocols are implemented in: + +- ``net/dsa/tag_trailer.c``: Marvell's 4 trailer tag mode (legacy) +- ``net/dsa/tag_dsa.c``: Marvell's original DSA tag +- ``net/dsa/tag_edsa.c``: Marvell's enhanced DSA tag +- ``net/dsa/tag_brcm.c``: Broadcom's 4 bytes tag +- ``net/dsa/tag_qca.c``: Qualcomm's 2 bytes tag + +The exact format of the tag protocol is vendor specific, but in general, they +all contain something which: + +- identifies which port the Ethernet frame came from/should be sent to +- provides a reason why this frame was forwarded to the management interface + +Master network devices +---------------------- + +Master network devices are regular, unmodified Linux network device drivers for +the CPU/management Ethernet interface. Such a driver might occasionally need to +know whether DSA is enabled (e.g.: to enable/disable specific offload features), +but the DSA subsystem has been proven to work with industry standard drivers: +``e1000e,`` ``mv643xx_eth`` etc. without having to introduce modifications to these +drivers. Such network devices are also often referred to as conduit network +devices since they act as a pipe between the host processor and the hardware +Ethernet switch. + +Networking stack hooks +---------------------- + +When a master netdev is used with DSA, a small hook is placed in in the +networking stack is in order to have the DSA subsystem process the Ethernet +switch specific tagging protocol. DSA accomplishes this by registering a +specific (and fake) Ethernet type (later becoming ``skb->protocol``) with the +networking stack, this is also known as a ``ptype`` or ``packet_type``. A typical +Ethernet Frame receive sequence looks like this: + +Master network device (e.g.: e1000e): + +1. Receive interrupt fires: + + - receive function is invoked + - basic packet processing is done: getting length, status etc. + - packet is prepared to be processed by the Ethernet layer by calling + ``eth_type_trans`` + +2. net/ethernet/eth.c:: + + eth_type_trans(skb, dev) + if (dev->dsa_ptr != NULL) + -> skb->protocol = ETH_P_XDSA + +3. drivers/net/ethernet/\*:: + + netif_receive_skb(skb) + -> iterate over registered packet_type + -> invoke handler for ETH_P_XDSA, calls dsa_switch_rcv() + +4. net/dsa/dsa.c:: + + -> dsa_switch_rcv() + -> invoke switch tag specific protocol handler in 'net/dsa/tag_*.c' + +5. net/dsa/tag_*.c: + + - inspect and strip switch tag protocol to determine originating port + - locate per-port network device + - invoke ``eth_type_trans()`` with the DSA slave network device + - invoked ``netif_receive_skb()`` + +Past this point, the DSA slave network devices get delivered regular Ethernet +frames that can be processed by the networking stack. + +Slave network devices +--------------------- + +Slave network devices created by DSA are stacked on top of their master network +device, each of these network interfaces will be responsible for being a +controlling and data-flowing end-point for each front-panel port of the switch. +These interfaces are specialized in order to: + +- insert/remove the switch tag protocol (if it exists) when sending traffic + to/from specific switch ports +- query the switch for ethtool operations: statistics, link state, + Wake-on-LAN, register dumps... +- external/internal PHY management: link, auto-negotiation etc. + +These slave network devices have custom net_device_ops and ethtool_ops function +pointers which allow DSA to introduce a level of layering between the networking +stack/ethtool, and the switch driver implementation. + +Upon frame transmission from these slave network devices, DSA will look up which +switch tagging protocol is currently registered with these network devices, and +invoke a specific transmit routine which takes care of adding the relevant +switch tag in the Ethernet frames. + +These frames are then queued for transmission using the master network device +``ndo_start_xmit()`` function, since they contain the appropriate switch tag, the +Ethernet switch will be able to process these incoming frames from the +management interface and delivers these frames to the physical switch port. + +Graphical representation +------------------------ + +Summarized, this is basically how DSA looks like from a network device +perspective:: + + + |--------------------------- + | CPU network device (eth0)| + ---------------------------- + | | + |--------------------------------------------| + | Switch driver | + |--------------------------------------------| + || || || + |-------| |-------| |-------| + | sw0p0 | | sw0p1 | | sw0p2 | + |-------| |-------| |-------| + + + +Slave MDIO bus +-------------- + +In order to be able to read to/from a switch PHY built into it, DSA creates a +slave MDIO bus which allows a specific switch driver to divert and intercept +MDIO reads/writes towards specific PHY addresses. In most MDIO-connected +switches, these functions would utilize direct or indirect PHY addressing mode +to return standard MII registers from the switch builtin PHYs, allowing the PHY +library and/or to return link status, link partner pages, auto-negotiation +results etc.. + +For Ethernet switches which have both external and internal MDIO busses, the +slave MII bus can be utilized to mux/demux MDIO reads and writes towards either +internal or external MDIO devices this switch might be connected to: internal +PHYs, external PHYs, or even external switches. + +Data structures +--------------- + +DSA data structures are defined in ``include/net/dsa.h`` as well as +``net/dsa/dsa_priv.h``: + +- ``dsa_chip_data``: platform data configuration for a given switch device, + this structure describes a switch device's parent device, its address, as + well as various properties of its ports: names/labels, and finally a routing + table indication (when cascading switches) + +- ``dsa_platform_data``: platform device configuration data which can reference + a collection of dsa_chip_data structure if multiples switches are cascaded, + the master network device this switch tree is attached to needs to be + referenced + +- ``dsa_switch_tree``: structure assigned to the master network device under + ``dsa_ptr``, this structure references a dsa_platform_data structure as well as + the tagging protocol supported by the switch tree, and which receive/transmit + function hooks should be invoked, information about the directly attached + switch is also provided: CPU port. Finally, a collection of dsa_switch are + referenced to address individual switches in the tree. + +- ``dsa_switch``: structure describing a switch device in the tree, referencing + a ``dsa_switch_tree`` as a backpointer, slave network devices, master network + device, and a reference to the backing``dsa_switch_ops`` + +- ``dsa_switch_ops``: structure referencing function pointers, see below for a + full description. + +Design limitations +================== + +Limits on the number of devices and ports +----------------------------------------- + +DSA currently limits the number of maximum switches within a tree to 4 +(``DSA_MAX_SWITCHES``), and the number of ports per switch to 12 (``DSA_MAX_PORTS``). +These limits could be extended to support larger configurations would this need +arise. + +Lack of CPU/DSA network devices +------------------------------- + +DSA does not currently create slave network devices for the CPU or DSA ports, as +described before. This might be an issue in the following cases: + +- inability to fetch switch CPU port statistics counters using ethtool, which + can make it harder to debug MDIO switch connected using xMII interfaces + +- inability to configure the CPU port link parameters based on the Ethernet + controller capabilities attached to it: http://patchwork.ozlabs.org/patch/509806/ + +- inability to configure specific VLAN IDs / trunking VLANs between switches + when using a cascaded setup + +Common pitfalls using DSA setups +-------------------------------- + +Once a master network device is configured to use DSA (dev->dsa_ptr becomes +non-NULL), and the switch behind it expects a tagging protocol, this network +interface can only exclusively be used as a conduit interface. Sending packets +directly through this interface (e.g.: opening a socket using this interface) +will not make us go through the switch tagging protocol transmit function, so +the Ethernet switch on the other end, expecting a tag will typically drop this +frame. + +Slave network devices check that the master network device is UP before allowing +you to administratively bring UP these slave network devices. A common +configuration mistake is forgetting to bring UP the master network device first. + +Interactions with other subsystems +================================== + +DSA currently leverages the following subsystems: + +- MDIO/PHY library: ``drivers/net/phy/phy.c``, ``mdio_bus.c`` +- Switchdev:``net/switchdev/*`` +- Device Tree for various of_* functions + +MDIO/PHY library +---------------- + +Slave network devices exposed by DSA may or may not be interfacing with PHY +devices (``struct phy_device`` as defined in ``include/linux/phy.h)``, but the DSA +subsystem deals with all possible combinations: + +- internal PHY devices, built into the Ethernet switch hardware +- external PHY devices, connected via an internal or external MDIO bus +- internal PHY devices, connected via an internal MDIO bus +- special, non-autonegotiated or non MDIO-managed PHY devices: SFPs, MoCA; a.k.a + fixed PHYs + +The PHY configuration is done by the ``dsa_slave_phy_setup()`` function and the +logic basically looks like this: + +- if Device Tree is used, the PHY device is looked up using the standard + "phy-handle" property, if found, this PHY device is created and registered + using ``of_phy_connect()`` + +- if Device Tree is used, and the PHY device is "fixed", that is, conforms to + the definition of a non-MDIO managed PHY as defined in + ``Documentation/devicetree/bindings/net/fixed-link.txt``, the PHY is registered + and connected transparently using the special fixed MDIO bus driver + +- finally, if the PHY is built into the switch, as is very common with + standalone switch packages, the PHY is probed using the slave MII bus created + by DSA + + +SWITCHDEV +--------- + +DSA directly utilizes SWITCHDEV when interfacing with the bridge layer, and +more specifically with its VLAN filtering portion when configuring VLANs on top +of per-port slave network devices. Since DSA primarily deals with +MDIO-connected switches, although not exclusively, SWITCHDEV's +prepare/abort/commit phases are often simplified into a prepare phase which +checks whether the operation is supported by the DSA switch driver, and a commit +phase which applies the changes. + +As of today, the only SWITCHDEV objects supported by DSA are the FDB and VLAN +objects. + +Device Tree +----------- + +DSA features a standardized binding which is documented in +``Documentation/devicetree/bindings/net/dsa/dsa.txt``. PHY/MDIO library helper +functions such as ``of_get_phy_mode()``, ``of_phy_connect()`` are also used to query +per-port PHY specific details: interface connection, MDIO bus location etc.. + +Driver development +================== + +DSA switch drivers need to implement a dsa_switch_ops structure which will +contain the various members described below. + +``register_switch_driver()`` registers this dsa_switch_ops in its internal list +of drivers to probe for. ``unregister_switch_driver()`` does the exact opposite. + +Unless requested differently by setting the priv_size member accordingly, DSA +does not allocate any driver private context space. + +Switch configuration +-------------------- + +- ``tag_protocol``: this is to indicate what kind of tagging protocol is supported, + should be a valid value from the ``dsa_tag_protocol`` enum + +- ``probe``: probe routine which will be invoked by the DSA platform device upon + registration to test for the presence/absence of a switch device. For MDIO + devices, it is recommended to issue a read towards internal registers using + the switch pseudo-PHY and return whether this is a supported device. For other + buses, return a non-NULL string + +- ``setup``: setup function for the switch, this function is responsible for setting + up the ``dsa_switch_ops`` private structure with all it needs: register maps, + interrupts, mutexes, locks etc.. This function is also expected to properly + configure the switch to separate all network interfaces from each other, that + is, they should be isolated by the switch hardware itself, typically by creating + a Port-based VLAN ID for each port and allowing only the CPU port and the + specific port to be in the forwarding vector. Ports that are unused by the + platform should be disabled. Past this function, the switch is expected to be + fully configured and ready to serve any kind of request. It is recommended + to issue a software reset of the switch during this setup function in order to + avoid relying on what a previous software agent such as a bootloader/firmware + may have previously configured. + +PHY devices and link management +------------------------------- + +- ``get_phy_flags``: Some switches are interfaced to various kinds of Ethernet PHYs, + if the PHY library PHY driver needs to know about information it cannot obtain + on its own (e.g.: coming from switch memory mapped registers), this function + should return a 32-bits bitmask of "flags", that is private between the switch + driver and the Ethernet PHY driver in ``drivers/net/phy/\*``. + +- ``phy_read``: Function invoked by the DSA slave MDIO bus when attempting to read + the switch port MDIO registers. If unavailable, return 0xffff for each read. + For builtin switch Ethernet PHYs, this function should allow reading the link + status, auto-negotiation results, link partner pages etc.. + +- ``phy_write``: Function invoked by the DSA slave MDIO bus when attempting to write + to the switch port MDIO registers. If unavailable return a negative error + code. + +- ``adjust_link``: Function invoked by the PHY library when a slave network device + is attached to a PHY device. This function is responsible for appropriately + configuring the switch port link parameters: speed, duplex, pause based on + what the ``phy_device`` is providing. + +- ``fixed_link_update``: Function invoked by the PHY library, and specifically by + the fixed PHY driver asking the switch driver for link parameters that could + not be auto-negotiated, or obtained by reading the PHY registers through MDIO. + This is particularly useful for specific kinds of hardware such as QSGMII, + MoCA or other kinds of non-MDIO managed PHYs where out of band link + information is obtained + +Ethtool operations +------------------ + +- ``get_strings``: ethtool function used to query the driver's strings, will + typically return statistics strings, private flags strings etc. + +- ``get_ethtool_stats``: ethtool function used to query per-port statistics and + return their values. DSA overlays slave network devices general statistics: + RX/TX counters from the network device, with switch driver specific statistics + per port + +- ``get_sset_count``: ethtool function used to query the number of statistics items + +- ``get_wol``: ethtool function used to obtain Wake-on-LAN settings per-port, this + function may, for certain implementations also query the master network device + Wake-on-LAN settings if this interface needs to participate in Wake-on-LAN + +- ``set_wol``: ethtool function used to configure Wake-on-LAN settings per-port, + direct counterpart to set_wol with similar restrictions + +- ``set_eee``: ethtool function which is used to configure a switch port EEE (Green + Ethernet) settings, can optionally invoke the PHY library to enable EEE at the + PHY level if relevant. This function should enable EEE at the switch port MAC + controller and data-processing logic + +- ``get_eee``: ethtool function which is used to query a switch port EEE settings, + this function should return the EEE state of the switch port MAC controller + and data-processing logic as well as query the PHY for its currently configured + EEE settings + +- ``get_eeprom_len``: ethtool function returning for a given switch the EEPROM + length/size in bytes + +- ``get_eeprom``: ethtool function returning for a given switch the EEPROM contents + +- ``set_eeprom``: ethtool function writing specified data to a given switch EEPROM + +- ``get_regs_len``: ethtool function returning the register length for a given + switch + +- ``get_regs``: ethtool function returning the Ethernet switch internal register + contents. This function might require user-land code in ethtool to + pretty-print register values and registers + +Power management +---------------- + +- ``suspend``: function invoked by the DSA platform device when the system goes to + suspend, should quiesce all Ethernet switch activities, but keep ports + participating in Wake-on-LAN active as well as additional wake-up logic if + supported + +- ``resume``: function invoked by the DSA platform device when the system resumes, + should resume all Ethernet switch activities and re-configure the switch to be + in a fully active state + +- ``port_enable``: function invoked by the DSA slave network device ndo_open + function when a port is administratively brought up, this function should be + fully enabling a given switch port. DSA takes care of marking the port with + ``BR_STATE_BLOCKING`` if the port is a bridge member, or ``BR_STATE_FORWARDING`` if it + was not, and propagating these changes down to the hardware + +- ``port_disable``: function invoked by the DSA slave network device ndo_close + function when a port is administratively brought down, this function should be + fully disabling a given switch port. DSA takes care of marking the port with + ``BR_STATE_DISABLED`` and propagating changes to the hardware if this port is + disabled while being a bridge member + +Bridge layer +------------ + +- ``port_bridge_join``: bridge layer function invoked when a given switch port is + added to a bridge, this function should be doing the necessary at the switch + level to permit the joining port from being added to the relevant logical + domain for it to ingress/egress traffic with other members of the bridge. + +- ``port_bridge_leave``: bridge layer function invoked when a given switch port is + removed from a bridge, this function should be doing the necessary at the + switch level to deny the leaving port from ingress/egress traffic from the + remaining bridge members. When the port leaves the bridge, it should be aged + out at the switch hardware for the switch to (re) learn MAC addresses behind + this port. + +- ``port_stp_state_set``: bridge layer function invoked when a given switch port STP + state is computed by the bridge layer and should be propagated to switch + hardware to forward/block/learn traffic. The switch driver is responsible for + computing a STP state change based on current and asked parameters and perform + the relevant ageing based on the intersection results + +Bridge VLAN filtering +--------------------- + +- ``port_vlan_filtering``: bridge layer function invoked when the bridge gets + configured for turning on or off VLAN filtering. If nothing specific needs to + be done at the hardware level, this callback does not need to be implemented. + When VLAN filtering is turned on, the hardware must be programmed with + rejecting 802.1Q frames which have VLAN IDs outside of the programmed allowed + VLAN ID map/rules. If there is no PVID programmed into the switch port, + untagged frames must be rejected as well. When turned off the switch must + accept any 802.1Q frames irrespective of their VLAN ID, and untagged frames are + allowed. + +- ``port_vlan_prepare``: bridge layer function invoked when the bridge prepares the + configuration of a VLAN on the given port. If the operation is not supported + by the hardware, this function should return ``-EOPNOTSUPP`` to inform the bridge + code to fallback to a software implementation. No hardware setup must be done + in this function. See port_vlan_add for this and details. + +- ``port_vlan_add``: bridge layer function invoked when a VLAN is configured + (tagged or untagged) for the given switch port + +- ``port_vlan_del``: bridge layer function invoked when a VLAN is removed from the + given switch port + +- ``port_vlan_dump``: bridge layer function invoked with a switchdev callback + function that the driver has to call for each VLAN the given port is a member + of. A switchdev object is used to carry the VID and bridge flags. + +- ``port_fdb_add``: bridge layer function invoked when the bridge wants to install a + Forwarding Database entry, the switch hardware should be programmed with the + specified address in the specified VLAN Id in the forwarding database + associated with this VLAN ID. If the operation is not supported, this + function should return ``-EOPNOTSUPP`` to inform the bridge code to fallback to + a software implementation. + +.. note:: VLAN ID 0 corresponds to the port private database, which, in the context + of DSA, would be the its port-based VLAN, used by the associated bridge device. + +- ``port_fdb_del``: bridge layer function invoked when the bridge wants to remove a + Forwarding Database entry, the switch hardware should be programmed to delete + the specified MAC address from the specified VLAN ID if it was mapped into + this port forwarding database + +- ``port_fdb_dump``: bridge layer function invoked with a switchdev callback + function that the driver has to call for each MAC address known to be behind + the given port. A switchdev object is used to carry the VID and FDB info. + +- ``port_mdb_prepare``: bridge layer function invoked when the bridge prepares the + installation of a multicast database entry. If the operation is not supported, + this function should return ``-EOPNOTSUPP`` to inform the bridge code to fallback + to a software implementation. No hardware setup must be done in this function. + See ``port_fdb_add`` for this and details. + +- ``port_mdb_add``: bridge layer function invoked when the bridge wants to install + a multicast database entry, the switch hardware should be programmed with the + specified address in the specified VLAN ID in the forwarding database + associated with this VLAN ID. + +.. note:: VLAN ID 0 corresponds to the port private database, which, in the context + of DSA, would be the its port-based VLAN, used by the associated bridge device. + +- ``port_mdb_del``: bridge layer function invoked when the bridge wants to remove a + multicast database entry, the switch hardware should be programmed to delete + the specified MAC address from the specified VLAN ID if it was mapped into + this port forwarding database. + +- ``port_mdb_dump``: bridge layer function invoked with a switchdev callback + function that the driver has to call for each MAC address known to be behind + the given port. A switchdev object is used to carry the VID and MDB info. + +TODO +==== + +Making SWITCHDEV and DSA converge towards an unified codebase +------------------------------------------------------------- + +SWITCHDEV properly takes care of abstracting the networking stack with offload +capable hardware, but does not enforce a strict switch device driver model. On +the other DSA enforces a fairly strict device driver model, and deals with most +of the switch specific. At some point we should envision a merger between these +two subsystems and get the best of both worlds. + +Other hanging fruits +-------------------- + +- making the number of ports fully dynamic and not dependent on ``DSA_MAX_PORTS`` +- allowing more than one CPU/management interface: + http://comments.gmane.org/gmane.linux.network/365657 +- porting more drivers from other vendors: + http://comments.gmane.org/gmane.linux.network/365510 diff --git a/Documentation/networking/dsa/dsa.txt b/Documentation/networking/dsa/dsa.txt deleted file mode 100644 index 43ef767bc440..000000000000 --- a/Documentation/networking/dsa/dsa.txt +++ /dev/null @@ -1,584 +0,0 @@ -Distributed Switch Architecture -=============================== - -Introduction -============ - -This document describes the Distributed Switch Architecture (DSA) subsystem -design principles, limitations, interactions with other subsystems, and how to -develop drivers for this subsystem as well as a TODO for developers interested -in joining the effort. - -Design principles -================= - -The Distributed Switch Architecture is a subsystem which was primarily designed -to support Marvell Ethernet switches (MV88E6xxx, a.k.a Linkstreet product line) -using Linux, but has since evolved to support other vendors as well. - -The original philosophy behind this design was to be able to use unmodified -Linux tools such as bridge, iproute2, ifconfig to work transparently whether -they configured/queried a switch port network device or a regular network -device. - -An Ethernet switch is typically comprised of multiple front-panel ports, and one -or more CPU or management port. The DSA subsystem currently relies on the -presence of a management port connected to an Ethernet controller capable of -receiving Ethernet frames from the switch. This is a very common setup for all -kinds of Ethernet switches found in Small Home and Office products: routers, -gateways, or even top-of-the rack switches. This host Ethernet controller will -be later referred to as "master" and "cpu" in DSA terminology and code. - -The D in DSA stands for Distributed, because the subsystem has been designed -with the ability to configure and manage cascaded switches on top of each other -using upstream and downstream Ethernet links between switches. These specific -ports are referred to as "dsa" ports in DSA terminology and code. A collection -of multiple switches connected to each other is called a "switch tree". - -For each front-panel port, DSA will create specialized network devices which are -used as controlling and data-flowing endpoints for use by the Linux networking -stack. These specialized network interfaces are referred to as "slave" network -interfaces in DSA terminology and code. - -The ideal case for using DSA is when an Ethernet switch supports a "switch tag" -which is a hardware feature making the switch insert a specific tag for each -Ethernet frames it received to/from specific ports to help the management -interface figure out: - -- what port is this frame coming from -- what was the reason why this frame got forwarded -- how to send CPU originated traffic to specific ports - -The subsystem does support switches not capable of inserting/stripping tags, but -the features might be slightly limited in that case (traffic separation relies -on Port-based VLAN IDs). - -Note that DSA does not currently create network interfaces for the "cpu" and -"dsa" ports because: - -- the "cpu" port is the Ethernet switch facing side of the management - controller, and as such, would create a duplication of feature, since you - would get two interfaces for the same conduit: master netdev, and "cpu" netdev - -- the "dsa" port(s) are just conduits between two or more switches, and as such - cannot really be used as proper network interfaces either, only the - downstream, or the top-most upstream interface makes sense with that model - -Switch tagging protocols ------------------------- - -DSA currently supports 5 different tagging protocols, and a tag-less mode as -well. The different protocols are implemented in: - -net/dsa/tag_trailer.c: Marvell's 4 trailer tag mode (legacy) -net/dsa/tag_dsa.c: Marvell's original DSA tag -net/dsa/tag_edsa.c: Marvell's enhanced DSA tag -net/dsa/tag_brcm.c: Broadcom's 4 bytes tag -net/dsa/tag_qca.c: Qualcomm's 2 bytes tag - -The exact format of the tag protocol is vendor specific, but in general, they -all contain something which: - -- identifies which port the Ethernet frame came from/should be sent to -- provides a reason why this frame was forwarded to the management interface - -Master network devices ----------------------- - -Master network devices are regular, unmodified Linux network device drivers for -the CPU/management Ethernet interface. Such a driver might occasionally need to -know whether DSA is enabled (e.g.: to enable/disable specific offload features), -but the DSA subsystem has been proven to work with industry standard drivers: -e1000e, mv643xx_eth etc. without having to introduce modifications to these -drivers. Such network devices are also often referred to as conduit network -devices since they act as a pipe between the host processor and the hardware -Ethernet switch. - -Networking stack hooks ----------------------- - -When a master netdev is used with DSA, a small hook is placed in in the -networking stack is in order to have the DSA subsystem process the Ethernet -switch specific tagging protocol. DSA accomplishes this by registering a -specific (and fake) Ethernet type (later becoming skb->protocol) with the -networking stack, this is also known as a ptype or packet_type. A typical -Ethernet Frame receive sequence looks like this: - -Master network device (e.g.: e1000e): - -Receive interrupt fires: -- receive function is invoked -- basic packet processing is done: getting length, status etc. -- packet is prepared to be processed by the Ethernet layer by calling - eth_type_trans - -net/ethernet/eth.c: - -eth_type_trans(skb, dev) - if (dev->dsa_ptr != NULL) - -> skb->protocol = ETH_P_XDSA - -drivers/net/ethernet/*: - -netif_receive_skb(skb) - -> iterate over registered packet_type - -> invoke handler for ETH_P_XDSA, calls dsa_switch_rcv() - -net/dsa/dsa.c: - -> dsa_switch_rcv() - -> invoke switch tag specific protocol handler in - net/dsa/tag_*.c - -net/dsa/tag_*.c: - -> inspect and strip switch tag protocol to determine originating port - -> locate per-port network device - -> invoke eth_type_trans() with the DSA slave network device - -> invoked netif_receive_skb() - -Past this point, the DSA slave network devices get delivered regular Ethernet -frames that can be processed by the networking stack. - -Slave network devices ---------------------- - -Slave network devices created by DSA are stacked on top of their master network -device, each of these network interfaces will be responsible for being a -controlling and data-flowing end-point for each front-panel port of the switch. -These interfaces are specialized in order to: - -- insert/remove the switch tag protocol (if it exists) when sending traffic - to/from specific switch ports -- query the switch for ethtool operations: statistics, link state, - Wake-on-LAN, register dumps... -- external/internal PHY management: link, auto-negotiation etc. - -These slave network devices have custom net_device_ops and ethtool_ops function -pointers which allow DSA to introduce a level of layering between the networking -stack/ethtool, and the switch driver implementation. - -Upon frame transmission from these slave network devices, DSA will look up which -switch tagging protocol is currently registered with these network devices, and -invoke a specific transmit routine which takes care of adding the relevant -switch tag in the Ethernet frames. - -These frames are then queued for transmission using the master network device -ndo_start_xmit() function, since they contain the appropriate switch tag, the -Ethernet switch will be able to process these incoming frames from the -management interface and delivers these frames to the physical switch port. - -Graphical representation ------------------------- - -Summarized, this is basically how DSA looks like from a network device -perspective: - - - |--------------------------- - | CPU network device (eth0)| - ---------------------------- - | | - |--------------------------------------------| - | Switch driver | - |--------------------------------------------| - || || || - |-------| |-------| |-------| - | sw0p0 | | sw0p1 | | sw0p2 | - |-------| |-------| |-------| - -Slave MDIO bus --------------- - -In order to be able to read to/from a switch PHY built into it, DSA creates a -slave MDIO bus which allows a specific switch driver to divert and intercept -MDIO reads/writes towards specific PHY addresses. In most MDIO-connected -switches, these functions would utilize direct or indirect PHY addressing mode -to return standard MII registers from the switch builtin PHYs, allowing the PHY -library and/or to return link status, link partner pages, auto-negotiation -results etc.. - -For Ethernet switches which have both external and internal MDIO busses, the -slave MII bus can be utilized to mux/demux MDIO reads and writes towards either -internal or external MDIO devices this switch might be connected to: internal -PHYs, external PHYs, or even external switches. - -Data structures ---------------- - -DSA data structures are defined in include/net/dsa.h as well as -net/dsa/dsa_priv.h. - -dsa_chip_data: platform data configuration for a given switch device, this -structure describes a switch device's parent device, its address, as well as -various properties of its ports: names/labels, and finally a routing table -indication (when cascading switches) - -dsa_platform_data: platform device configuration data which can reference a -collection of dsa_chip_data structure if multiples switches are cascaded, the -master network device this switch tree is attached to needs to be referenced - -dsa_switch_tree: structure assigned to the master network device under -"dsa_ptr", this structure references a dsa_platform_data structure as well as -the tagging protocol supported by the switch tree, and which receive/transmit -function hooks should be invoked, information about the directly attached switch -is also provided: CPU port. Finally, a collection of dsa_switch are referenced -to address individual switches in the tree. - -dsa_switch: structure describing a switch device in the tree, referencing a -dsa_switch_tree as a backpointer, slave network devices, master network device, -and a reference to the backing dsa_switch_ops - -dsa_switch_ops: structure referencing function pointers, see below for a full -description. - -Design limitations -================== - -Limits on the number of devices and ports ------------------------------------------ - -DSA currently limits the number of maximum switches within a tree to 4 -(DSA_MAX_SWITCHES), and the number of ports per switch to 12 (DSA_MAX_PORTS). -These limits could be extended to support larger configurations would this need -arise. - -Lack of CPU/DSA network devices -------------------------------- - -DSA does not currently create slave network devices for the CPU or DSA ports, as -described before. This might be an issue in the following cases: - -- inability to fetch switch CPU port statistics counters using ethtool, which - can make it harder to debug MDIO switch connected using xMII interfaces - -- inability to configure the CPU port link parameters based on the Ethernet - controller capabilities attached to it: http://patchwork.ozlabs.org/patch/509806/ - -- inability to configure specific VLAN IDs / trunking VLANs between switches - when using a cascaded setup - -Common pitfalls using DSA setups --------------------------------- - -Once a master network device is configured to use DSA (dev->dsa_ptr becomes -non-NULL), and the switch behind it expects a tagging protocol, this network -interface can only exclusively be used as a conduit interface. Sending packets -directly through this interface (e.g.: opening a socket using this interface) -will not make us go through the switch tagging protocol transmit function, so -the Ethernet switch on the other end, expecting a tag will typically drop this -frame. - -Slave network devices check that the master network device is UP before allowing -you to administratively bring UP these slave network devices. A common -configuration mistake is forgetting to bring UP the master network device first. - -Interactions with other subsystems -================================== - -DSA currently leverages the following subsystems: - -- MDIO/PHY library: drivers/net/phy/phy.c, mdio_bus.c -- Switchdev: net/switchdev/* -- Device Tree for various of_* functions - -MDIO/PHY library ----------------- - -Slave network devices exposed by DSA may or may not be interfacing with PHY -devices (struct phy_device as defined in include/linux/phy.h), but the DSA -subsystem deals with all possible combinations: - -- internal PHY devices, built into the Ethernet switch hardware -- external PHY devices, connected via an internal or external MDIO bus -- internal PHY devices, connected via an internal MDIO bus -- special, non-autonegotiated or non MDIO-managed PHY devices: SFPs, MoCA; a.k.a - fixed PHYs - -The PHY configuration is done by the dsa_slave_phy_setup() function and the -logic basically looks like this: - -- if Device Tree is used, the PHY device is looked up using the standard - "phy-handle" property, if found, this PHY device is created and registered - using of_phy_connect() - -- if Device Tree is used, and the PHY device is "fixed", that is, conforms to - the definition of a non-MDIO managed PHY as defined in - Documentation/devicetree/bindings/net/fixed-link.txt, the PHY is registered - and connected transparently using the special fixed MDIO bus driver - -- finally, if the PHY is built into the switch, as is very common with - standalone switch packages, the PHY is probed using the slave MII bus created - by DSA - - -SWITCHDEV ---------- - -DSA directly utilizes SWITCHDEV when interfacing with the bridge layer, and -more specifically with its VLAN filtering portion when configuring VLANs on top -of per-port slave network devices. Since DSA primarily deals with -MDIO-connected switches, although not exclusively, SWITCHDEV's -prepare/abort/commit phases are often simplified into a prepare phase which -checks whether the operation is supported by the DSA switch driver, and a commit -phase which applies the changes. - -As of today, the only SWITCHDEV objects supported by DSA are the FDB and VLAN -objects. - -Device Tree ------------ - -DSA features a standardized binding which is documented in -Documentation/devicetree/bindings/net/dsa/dsa.txt. PHY/MDIO library helper -functions such as of_get_phy_mode(), of_phy_connect() are also used to query -per-port PHY specific details: interface connection, MDIO bus location etc.. - -Driver development -================== - -DSA switch drivers need to implement a dsa_switch_ops structure which will -contain the various members described below. - -register_switch_driver() registers this dsa_switch_ops in its internal list -of drivers to probe for. unregister_switch_driver() does the exact opposite. - -Unless requested differently by setting the priv_size member accordingly, DSA -does not allocate any driver private context space. - -Switch configuration --------------------- - -- tag_protocol: this is to indicate what kind of tagging protocol is supported, - should be a valid value from the dsa_tag_protocol enum - -- probe: probe routine which will be invoked by the DSA platform device upon - registration to test for the presence/absence of a switch device. For MDIO - devices, it is recommended to issue a read towards internal registers using - the switch pseudo-PHY and return whether this is a supported device. For other - buses, return a non-NULL string - -- setup: setup function for the switch, this function is responsible for setting - up the dsa_switch_ops private structure with all it needs: register maps, - interrupts, mutexes, locks etc.. This function is also expected to properly - configure the switch to separate all network interfaces from each other, that - is, they should be isolated by the switch hardware itself, typically by creating - a Port-based VLAN ID for each port and allowing only the CPU port and the - specific port to be in the forwarding vector. Ports that are unused by the - platform should be disabled. Past this function, the switch is expected to be - fully configured and ready to serve any kind of request. It is recommended - to issue a software reset of the switch during this setup function in order to - avoid relying on what a previous software agent such as a bootloader/firmware - may have previously configured. - -PHY devices and link management -------------------------------- - -- get_phy_flags: Some switches are interfaced to various kinds of Ethernet PHYs, - if the PHY library PHY driver needs to know about information it cannot obtain - on its own (e.g.: coming from switch memory mapped registers), this function - should return a 32-bits bitmask of "flags", that is private between the switch - driver and the Ethernet PHY driver in drivers/net/phy/*. - -- phy_read: Function invoked by the DSA slave MDIO bus when attempting to read - the switch port MDIO registers. If unavailable, return 0xffff for each read. - For builtin switch Ethernet PHYs, this function should allow reading the link - status, auto-negotiation results, link partner pages etc.. - -- phy_write: Function invoked by the DSA slave MDIO bus when attempting to write - to the switch port MDIO registers. If unavailable return a negative error - code. - -- adjust_link: Function invoked by the PHY library when a slave network device - is attached to a PHY device. This function is responsible for appropriately - configuring the switch port link parameters: speed, duplex, pause based on - what the phy_device is providing. - -- fixed_link_update: Function invoked by the PHY library, and specifically by - the fixed PHY driver asking the switch driver for link parameters that could - not be auto-negotiated, or obtained by reading the PHY registers through MDIO. - This is particularly useful for specific kinds of hardware such as QSGMII, - MoCA or other kinds of non-MDIO managed PHYs where out of band link - information is obtained - -Ethtool operations ------------------- - -- get_strings: ethtool function used to query the driver's strings, will - typically return statistics strings, private flags strings etc. - -- get_ethtool_stats: ethtool function used to query per-port statistics and - return their values. DSA overlays slave network devices general statistics: - RX/TX counters from the network device, with switch driver specific statistics - per port - -- get_sset_count: ethtool function used to query the number of statistics items - -- get_wol: ethtool function used to obtain Wake-on-LAN settings per-port, this - function may, for certain implementations also query the master network device - Wake-on-LAN settings if this interface needs to participate in Wake-on-LAN - -- set_wol: ethtool function used to configure Wake-on-LAN settings per-port, - direct counterpart to set_wol with similar restrictions - -- set_eee: ethtool function which is used to configure a switch port EEE (Green - Ethernet) settings, can optionally invoke the PHY library to enable EEE at the - PHY level if relevant. This function should enable EEE at the switch port MAC - controller and data-processing logic - -- get_eee: ethtool function which is used to query a switch port EEE settings, - this function should return the EEE state of the switch port MAC controller - and data-processing logic as well as query the PHY for its currently configured - EEE settings - -- get_eeprom_len: ethtool function returning for a given switch the EEPROM - length/size in bytes - -- get_eeprom: ethtool function returning for a given switch the EEPROM contents - -- set_eeprom: ethtool function writing specified data to a given switch EEPROM - -- get_regs_len: ethtool function returning the register length for a given - switch - -- get_regs: ethtool function returning the Ethernet switch internal register - contents. This function might require user-land code in ethtool to - pretty-print register values and registers - -Power management ----------------- - -- suspend: function invoked by the DSA platform device when the system goes to - suspend, should quiesce all Ethernet switch activities, but keep ports - participating in Wake-on-LAN active as well as additional wake-up logic if - supported - -- resume: function invoked by the DSA platform device when the system resumes, - should resume all Ethernet switch activities and re-configure the switch to be - in a fully active state - -- port_enable: function invoked by the DSA slave network device ndo_open - function when a port is administratively brought up, this function should be - fully enabling a given switch port. DSA takes care of marking the port with - BR_STATE_BLOCKING if the port is a bridge member, or BR_STATE_FORWARDING if it - was not, and propagating these changes down to the hardware - -- port_disable: function invoked by the DSA slave network device ndo_close - function when a port is administratively brought down, this function should be - fully disabling a given switch port. DSA takes care of marking the port with - BR_STATE_DISABLED and propagating changes to the hardware if this port is - disabled while being a bridge member - -Bridge layer ------------- - -- port_bridge_join: bridge layer function invoked when a given switch port is - added to a bridge, this function should be doing the necessary at the switch - level to permit the joining port from being added to the relevant logical - domain for it to ingress/egress traffic with other members of the bridge. - -- port_bridge_leave: bridge layer function invoked when a given switch port is - removed from a bridge, this function should be doing the necessary at the - switch level to deny the leaving port from ingress/egress traffic from the - remaining bridge members. When the port leaves the bridge, it should be aged - out at the switch hardware for the switch to (re) learn MAC addresses behind - this port. - -- port_stp_state_set: bridge layer function invoked when a given switch port STP - state is computed by the bridge layer and should be propagated to switch - hardware to forward/block/learn traffic. The switch driver is responsible for - computing a STP state change based on current and asked parameters and perform - the relevant ageing based on the intersection results - -Bridge VLAN filtering ---------------------- - -- port_vlan_filtering: bridge layer function invoked when the bridge gets - configured for turning on or off VLAN filtering. If nothing specific needs to - be done at the hardware level, this callback does not need to be implemented. - When VLAN filtering is turned on, the hardware must be programmed with - rejecting 802.1Q frames which have VLAN IDs outside of the programmed allowed - VLAN ID map/rules. If there is no PVID programmed into the switch port, - untagged frames must be rejected as well. When turned off the switch must - accept any 802.1Q frames irrespective of their VLAN ID, and untagged frames are - allowed. - -- port_vlan_prepare: bridge layer function invoked when the bridge prepares the - configuration of a VLAN on the given port. If the operation is not supported - by the hardware, this function should return -EOPNOTSUPP to inform the bridge - code to fallback to a software implementation. No hardware setup must be done - in this function. See port_vlan_add for this and details. - -- port_vlan_add: bridge layer function invoked when a VLAN is configured - (tagged or untagged) for the given switch port - -- port_vlan_del: bridge layer function invoked when a VLAN is removed from the - given switch port - -- port_vlan_dump: bridge layer function invoked with a switchdev callback - function that the driver has to call for each VLAN the given port is a member - of. A switchdev object is used to carry the VID and bridge flags. - -- port_fdb_add: bridge layer function invoked when the bridge wants to install a - Forwarding Database entry, the switch hardware should be programmed with the - specified address in the specified VLAN Id in the forwarding database - associated with this VLAN ID. If the operation is not supported, this - function should return -EOPNOTSUPP to inform the bridge code to fallback to - a software implementation. - -Note: VLAN ID 0 corresponds to the port private database, which, in the context -of DSA, would be the its port-based VLAN, used by the associated bridge device. - -- port_fdb_del: bridge layer function invoked when the bridge wants to remove a - Forwarding Database entry, the switch hardware should be programmed to delete - the specified MAC address from the specified VLAN ID if it was mapped into - this port forwarding database - -- port_fdb_dump: bridge layer function invoked with a switchdev callback - function that the driver has to call for each MAC address known to be behind - the given port. A switchdev object is used to carry the VID and FDB info. - -- port_mdb_prepare: bridge layer function invoked when the bridge prepares the - installation of a multicast database entry. If the operation is not supported, - this function should return -EOPNOTSUPP to inform the bridge code to fallback - to a software implementation. No hardware setup must be done in this function. - See port_fdb_add for this and details. - -- port_mdb_add: bridge layer function invoked when the bridge wants to install - a multicast database entry, the switch hardware should be programmed with the - specified address in the specified VLAN ID in the forwarding database - associated with this VLAN ID. - -Note: VLAN ID 0 corresponds to the port private database, which, in the context -of DSA, would be the its port-based VLAN, used by the associated bridge device. - -- port_mdb_del: bridge layer function invoked when the bridge wants to remove a - multicast database entry, the switch hardware should be programmed to delete - the specified MAC address from the specified VLAN ID if it was mapped into - this port forwarding database. - -- port_mdb_dump: bridge layer function invoked with a switchdev callback - function that the driver has to call for each MAC address known to be behind - the given port. A switchdev object is used to carry the VID and MDB info. - -TODO -==== - -Making SWITCHDEV and DSA converge towards an unified codebase -------------------------------------------------------------- - -SWITCHDEV properly takes care of abstracting the networking stack with offload -capable hardware, but does not enforce a strict switch device driver model. On -the other DSA enforces a fairly strict device driver model, and deals with most -of the switch specific. At some point we should envision a merger between these -two subsystems and get the best of both worlds. - -Other hanging fruits --------------------- - -- making the number of ports fully dynamic and not dependent on DSA_MAX_PORTS -- allowing more than one CPU/management interface: - http://comments.gmane.org/gmane.linux.network/365657 -- porting more drivers from other vendors: - http://comments.gmane.org/gmane.linux.network/365510 diff --git a/Documentation/networking/dsa/index.rst b/Documentation/networking/dsa/index.rst new file mode 100644 index 000000000000..5c488d345a1e --- /dev/null +++ b/Documentation/networking/dsa/index.rst @@ -0,0 +1,10 @@ +=============================== +Distributed Switch Architecture +=============================== + +.. toctree:: + :maxdepth: 1 + + dsa + bcm_sf2 + lan9303 diff --git a/Documentation/networking/dsa/lan9303.rst b/Documentation/networking/dsa/lan9303.rst new file mode 100644 index 000000000000..e3c820db28ad --- /dev/null +++ b/Documentation/networking/dsa/lan9303.rst @@ -0,0 +1,37 @@ +============================== +LAN9303 Ethernet switch driver +============================== + +The LAN9303 is a three port 10/100 Mbps ethernet switch with integrated phys for +the two external ethernet ports. The third port is an RMII/MII interface to a +host master network interface (e.g. fixed link). + + +Driver details +============== + +The driver is implemented as a DSA driver, see ``Documentation/networking/dsa/dsa.rst``. + +See ``Documentation/devicetree/bindings/net/dsa/lan9303.txt`` for device tree +binding. + +The LAN9303 can be managed both via MDIO and I2C, both supported by this driver. + +At startup the driver configures the device to provide two separate network +interfaces (which is the default state of a DSA device). Due to HW limitations, +no HW MAC learning takes place in this mode. + +When both user ports are joined to the same bridge, the normal HW MAC learning +is enabled. This means that unicast traffic is forwarded in HW. Broadcast and +multicast is flooded in HW. STP is also supported in this mode. The driver +support fdb/mdb operations as well, meaning IGMP snooping is supported. + +If one of the user ports leave the bridge, the ports goes back to the initial +separated operation. + + +Driver limitations +================== + + - Support for VLAN filtering is not implemented + - The HW does not support VLAN-specific fdb entries diff --git a/Documentation/networking/dsa/lan9303.txt b/Documentation/networking/dsa/lan9303.txt deleted file mode 100644 index 144b02b95207..000000000000 --- a/Documentation/networking/dsa/lan9303.txt +++ /dev/null @@ -1,37 +0,0 @@ -LAN9303 Ethernet switch driver -============================== - -The LAN9303 is a three port 10/100 Mbps ethernet switch with integrated phys for -the two external ethernet ports. The third port is an RMII/MII interface to a -host master network interface (e.g. fixed link). - - -Driver details -============== - -The driver is implemented as a DSA driver, see -Documentation/networking/dsa/dsa.txt. - -See Documentation/devicetree/bindings/net/dsa/lan9303.txt for device tree -binding. - -The LAN9303 can be managed both via MDIO and I2C, both supported by this driver. - -At startup the driver configures the device to provide two separate network -interfaces (which is the default state of a DSA device). Due to HW limitations, -no HW MAC learning takes place in this mode. - -When both user ports are joined to the same bridge, the normal HW MAC learning -is enabled. This means that unicast traffic is forwarded in HW. Broadcast and -multicast is flooded in HW. STP is also supported in this mode. The driver -support fdb/mdb operations as well, meaning IGMP snooping is supported. - -If one of the user ports leave the bridge, the ports goes back to the initial -separated operation. - - -Driver limitations -================== - - - Support for VLAN filtering is not implemented - - The HW does not support VLAN-specific fdb entries diff --git a/Documentation/networking/index.rst b/Documentation/networking/index.rst index 984e68f9e026..269d6f2661d5 100644 --- a/Documentation/networking/index.rst +++ b/Documentation/networking/index.rst @@ -25,6 +25,7 @@ Contents: device_drivers/intel/i40e device_drivers/intel/iavf device_drivers/intel/ice + dsa/index devlink-info-versions ieee802154 kapi -- cgit v1.2.3 From 4611da30d679a4b0a2c2b5d4d7b3fbbafc922df7 Mon Sep 17 00:00:00 2001 From: Marc Dionne Date: Fri, 12 Apr 2019 16:33:47 +0100 Subject: rxrpc: Make rxrpc_kernel_check_life() indicate if call completed Make rxrpc_kernel_check_life() pass back the life counter through the argument list and return true if the call has not yet completed. Suggested-by: Marc Dionne Signed-off-by: David Howells Signed-off-by: David S. Miller --- Documentation/networking/rxrpc.txt | 16 +++++++++------- fs/afs/rxrpc.c | 4 ++-- include/net/af_rxrpc.h | 4 +++- net/rxrpc/af_rxrpc.c | 14 +++++++++----- 4 files changed, 23 insertions(+), 15 deletions(-) (limited to 'Documentation') diff --git a/Documentation/networking/rxrpc.txt b/Documentation/networking/rxrpc.txt index 2df5894353d6..cd7303d7fa25 100644 --- a/Documentation/networking/rxrpc.txt +++ b/Documentation/networking/rxrpc.txt @@ -1009,16 +1009,18 @@ The kernel interface functions are as follows: (*) Check call still alive. - u32 rxrpc_kernel_check_life(struct socket *sock, - struct rxrpc_call *call); + bool rxrpc_kernel_check_life(struct socket *sock, + struct rxrpc_call *call, + u32 *_life); void rxrpc_kernel_probe_life(struct socket *sock, struct rxrpc_call *call); - The first function returns a number that is updated when ACKs are received - from the peer (notably including PING RESPONSE ACKs which we can elicit by - sending PING ACKs to see if the call still exists on the server). The - caller should compare the numbers of two calls to see if the call is still - alive after waiting for a suitable interval. + The first function passes back in *_life a number that is updated when + ACKs are received from the peer (notably including PING RESPONSE ACKs + which we can elicit by sending PING ACKs to see if the call still exists + on the server). The caller should compare the numbers of two calls to see + if the call is still alive after waiting for a suitable interval. It also + returns true as long as the call hasn't yet reached the completed state. This allows the caller to work out if the server is still contactable and if the call is still alive on the server while waiting for the server to diff --git a/fs/afs/rxrpc.c b/fs/afs/rxrpc.c index 2c588f9bbbda..5cb11aff9298 100644 --- a/fs/afs/rxrpc.c +++ b/fs/afs/rxrpc.c @@ -621,7 +621,7 @@ static long afs_wait_for_call_to_complete(struct afs_call *call, rtt2 = 2; timeout = rtt2; - last_life = rxrpc_kernel_check_life(call->net->socket, call->rxcall); + rxrpc_kernel_check_life(call->net->socket, call->rxcall, &last_life); add_wait_queue(&call->waitq, &myself); for (;;) { @@ -639,7 +639,7 @@ static long afs_wait_for_call_to_complete(struct afs_call *call, if (afs_check_call_state(call, AFS_CALL_COMPLETE)) break; - life = rxrpc_kernel_check_life(call->net->socket, call->rxcall); + rxrpc_kernel_check_life(call->net->socket, call->rxcall, &life); if (timeout == 0 && life == last_life && signal_pending(current)) { if (stalled) diff --git a/include/net/af_rxrpc.h b/include/net/af_rxrpc.h index 2bfb87eb98ce..78c856cba4f5 100644 --- a/include/net/af_rxrpc.h +++ b/include/net/af_rxrpc.h @@ -61,10 +61,12 @@ int rxrpc_kernel_charge_accept(struct socket *, rxrpc_notify_rx_t, rxrpc_user_attach_call_t, unsigned long, gfp_t, unsigned int); void rxrpc_kernel_set_tx_length(struct socket *, struct rxrpc_call *, s64); -u32 rxrpc_kernel_check_life(const struct socket *, const struct rxrpc_call *); +bool rxrpc_kernel_check_life(const struct socket *, const struct rxrpc_call *, + u32 *); void rxrpc_kernel_probe_life(struct socket *, struct rxrpc_call *); u32 rxrpc_kernel_get_epoch(struct socket *, struct rxrpc_call *); bool rxrpc_kernel_get_reply_time(struct socket *, struct rxrpc_call *, ktime_t *); +bool rxrpc_kernel_call_is_complete(struct rxrpc_call *); #endif /* _NET_RXRPC_H */ diff --git a/net/rxrpc/af_rxrpc.c b/net/rxrpc/af_rxrpc.c index c54dce3ca0dd..ae8c5d7f3bf1 100644 --- a/net/rxrpc/af_rxrpc.c +++ b/net/rxrpc/af_rxrpc.c @@ -371,18 +371,22 @@ EXPORT_SYMBOL(rxrpc_kernel_end_call); * rxrpc_kernel_check_life - Check to see whether a call is still alive * @sock: The socket the call is on * @call: The call to check + * @_life: Where to store the life value * * Allow a kernel service to find out whether a call is still alive - ie. we're - * getting ACKs from the server. Returns a number representing the life state - * which can be compared to that returned by a previous call. + * getting ACKs from the server. Passes back in *_life a number representing + * the life state which can be compared to that returned by a previous call and + * return true if the call is still alive. * * If the life state stalls, rxrpc_kernel_probe_life() should be called and * then 2RTT waited. */ -u32 rxrpc_kernel_check_life(const struct socket *sock, - const struct rxrpc_call *call) +bool rxrpc_kernel_check_life(const struct socket *sock, + const struct rxrpc_call *call, + u32 *_life) { - return call->acks_latest; + *_life = call->acks_latest; + return call->state != RXRPC_CALL_COMPLETE; } EXPORT_SYMBOL(rxrpc_kernel_check_life); -- cgit v1.2.3 From 649cc7b17ce8c53d25f12dc0859285456850b9ac Mon Sep 17 00:00:00 2001 From: Lorenzo Bianconi Date: Thu, 4 Apr 2019 18:02:35 +0200 Subject: dt-bindings: iio: imu: st_lsm6dsx: add lsm6dsr device bindings Signed-off-by: Lorenzo Bianconi Reviewed-by: Rob Herring Signed-off-by: Jonathan Cameron --- Documentation/devicetree/bindings/iio/imu/st_lsm6dsx.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/imu/st_lsm6dsx.txt b/Documentation/devicetree/bindings/iio/imu/st_lsm6dsx.txt index 4640a012c17a..efec9ece034a 100644 --- a/Documentation/devicetree/bindings/iio/imu/st_lsm6dsx.txt +++ b/Documentation/devicetree/bindings/iio/imu/st_lsm6dsx.txt @@ -10,6 +10,7 @@ Required properties: "st,lsm6dso" "st,asm330lhh" "st,lsm6dsox" + "st,lsm6dsr" - reg: i2c address of the sensor / spi cs line Optional properties: -- cgit v1.2.3 From 3e5ffe47ed8cfe639cb9bd1516fd0fd3ab71b39e Mon Sep 17 00:00:00 2001 From: Beniamin Bia Date: Tue, 2 Apr 2019 16:18:41 +0300 Subject: dt-bindings: iio: adc: Add AD7616 ADC documentation Document support for AD7616 Analog to Digital Converter. Signed-off-by: Beniamin Bia Reviewed-by: Rob Herring Signed-off-by: Jonathan Cameron --- Documentation/devicetree/bindings/iio/adc/adi,ad7606.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/adc/adi,ad7606.txt b/Documentation/devicetree/bindings/iio/adc/adi,ad7606.txt index d7b6241ca881..d8652460198e 100644 --- a/Documentation/devicetree/bindings/iio/adc/adi,ad7606.txt +++ b/Documentation/devicetree/bindings/iio/adc/adi,ad7606.txt @@ -7,6 +7,7 @@ Required properties for the AD7606: * "adi,ad7606-8" * "adi,ad7606-6" * "adi,ad7606-4" + * "adi,ad7616" - reg: SPI chip select number for the device - spi-max-frequency: Max SPI frequency to use see: Documentation/devicetree/bindings/spi/spi-bus.txt -- cgit v1.2.3 From 5150ec3fe12579b877da17447687c6c90be20911 Mon Sep 17 00:00:00 2001 From: Andreas Klinger Date: Mon, 1 Apr 2019 19:33:54 +0200 Subject: avia-hx711.yaml: transform DT binding to YAML replace avia-hx711.txt by avia-hx711.yaml as yaml devicetree documentation for avia hx711 iio adc sensor Signed-off-by: Andreas Klinger Reviewed-by: Rob Herring Signed-off-by: Jonathan Cameron --- .../devicetree/bindings/iio/adc/avia-hx711.txt | 24 -------- .../devicetree/bindings/iio/adc/avia-hx711.yaml | 66 ++++++++++++++++++++++ 2 files changed, 66 insertions(+), 24 deletions(-) delete mode 100644 Documentation/devicetree/bindings/iio/adc/avia-hx711.txt create mode 100644 Documentation/devicetree/bindings/iio/adc/avia-hx711.yaml (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/adc/avia-hx711.txt b/Documentation/devicetree/bindings/iio/adc/avia-hx711.txt deleted file mode 100644 index 7222328a3d0d..000000000000 --- a/Documentation/devicetree/bindings/iio/adc/avia-hx711.txt +++ /dev/null @@ -1,24 +0,0 @@ -* AVIA HX711 ADC chip for weight cells - Bit-banging driver - -Required properties: - - compatible: Should be "avia,hx711" - - sck-gpios: Definition of the GPIO for the clock - - dout-gpios: Definition of the GPIO for data-out - See Documentation/devicetree/bindings/gpio/gpio.txt - - avdd-supply: Definition of the regulator used as analog supply - -Optional properties: - - clock-frequency: Frequency of PD_SCK in Hz - Minimum value allowed is 10 kHz because of maximum - high time of 50 microseconds. - -Example: -weight { - compatible = "avia,hx711"; - sck-gpios = <&gpio3 10 GPIO_ACTIVE_HIGH>; - dout-gpios = <&gpio0 7 GPIO_ACTIVE_HIGH>; - avdd-suppy = <&avdd>; - clock-frequency = <100000>; -}; - diff --git a/Documentation/devicetree/bindings/iio/adc/avia-hx711.yaml b/Documentation/devicetree/bindings/iio/adc/avia-hx711.yaml new file mode 100644 index 000000000000..8a4100ceeaf2 --- /dev/null +++ b/Documentation/devicetree/bindings/iio/adc/avia-hx711.yaml @@ -0,0 +1,66 @@ +# SPDX-License-Identifier: GPL-2.0 +%YAML 1.2 +--- +$id: "http://devicetree.org/schemas/iio/adc/avia-hx711.yaml#" +$schema: "http://devicetree.org/meta-schemas/core.yaml#" + +title: AVIA HX711 ADC chip for weight cells + +maintainers: + - Andreas Klinger + +description: | + Bit-banging driver using two GPIOs: + - sck-gpio gives a clock to the sensor with 24 cycles for data retrieval + and up to 3 cycles for selection of the input channel and gain for the + next measurement + - dout-gpio is the sensor data the sensor responds to the clock + + Specifications about the driver can be found at: + http://www.aviaic.com/ENProducts.aspx + +properties: + compatible: + enum: + - avia,hx711 + + sck-gpios: + description: + Definition of the GPIO for the clock (output). In the datasheet it is + named PD_SCK + maxItems: 1 + + dout-gpios: + description: + Definition of the GPIO for the data-out sent by the sensor in + response to the clock (input). + See Documentation/devicetree/bindings/gpio/gpio.txt for information + on how to specify a consumer gpio. + maxItems: 1 + + avdd-supply: + description: + Definition of the regulator used as analog supply + maxItems: 1 + + clock-frequency: + minimum: 20000 + maximum: 2500000 + default: 400000 + +required: + - compatible + - sck-gpios + - dout-gpios + - avdd-supply + +examples: + - | + #include + weight { + compatible = "avia,hx711"; + sck-gpios = <&gpio3 10 GPIO_ACTIVE_HIGH>; + dout-gpios = <&gpio0 7 GPIO_ACTIVE_HIGH>; + avdd-suppy = <&avdd>; + clock-frequency = <100000>; + }; -- cgit v1.2.3 From 88aa7ae661284accd4c058429d6d0a3b7397e081 Mon Sep 17 00:00:00 2001 From: Andreas Klinger Date: Mon, 1 Apr 2019 19:31:44 +0200 Subject: bmp085.yaml: transform DT documentation of iio sensor into YAML use bmp085.txt and change it into yaml format fix links to datasheets in replaced documentation Signed-off-by: Andreas Klinger Reviewed-by: Rob Herring Signed-off-by: Jonathan Cameron --- .../devicetree/bindings/iio/pressure/bmp085.txt | 27 --------- .../devicetree/bindings/iio/pressure/bmp085.yaml | 70 ++++++++++++++++++++++ 2 files changed, 70 insertions(+), 27 deletions(-) delete mode 100644 Documentation/devicetree/bindings/iio/pressure/bmp085.txt create mode 100644 Documentation/devicetree/bindings/iio/pressure/bmp085.yaml (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/pressure/bmp085.txt b/Documentation/devicetree/bindings/iio/pressure/bmp085.txt deleted file mode 100644 index 61c72e63c584..000000000000 --- a/Documentation/devicetree/bindings/iio/pressure/bmp085.txt +++ /dev/null @@ -1,27 +0,0 @@ -BMP085/BMP18x/BMP28x digital pressure sensors - -Required properties: -- compatible: must be one of: - "bosch,bmp085" - "bosch,bmp180" - "bosch,bmp280" - "bosch,bme280" - -Optional properties: -- interrupts: interrupt mapping for IRQ -- reset-gpios: a GPIO line handling reset of the sensor: as the line is - active low, it should be marked GPIO_ACTIVE_LOW (see gpio/gpio.txt) -- vddd-supply: digital voltage regulator (see regulator/regulator.txt) -- vdda-supply: analog voltage regulator (see regulator/regulator.txt) - -Example: - -pressure@77 { - compatible = "bosch,bmp085"; - reg = <0x77>; - interrupt-parent = <&gpio0>; - interrupts = <25 IRQ_TYPE_EDGE_RISING>; - reset-gpios = <&gpio0 26 GPIO_ACTIVE_LOW>; - vddd-supply = <&foo>; - vdda-supply = <&bar>; -}; diff --git a/Documentation/devicetree/bindings/iio/pressure/bmp085.yaml b/Documentation/devicetree/bindings/iio/pressure/bmp085.yaml new file mode 100644 index 000000000000..c6721a7e8938 --- /dev/null +++ b/Documentation/devicetree/bindings/iio/pressure/bmp085.yaml @@ -0,0 +1,70 @@ +# SPDX-License-Identifier: GPL-2.0 +%YAML 1.2 +--- +$id: http://devicetree.org/schemas/iio/pressure/bmp085.yaml# +$schema: http://devicetree.org/meta-schemas/core.yaml# + +title: BMP085/BMP180/BMP280/BME280 pressure iio sensors + +maintainers: + - Andreas Klinger + +description: | + Pressure, temperature and humidity iio sensors with i2c and spi interfaces + + Specifications about the sensor can be found at: + https://www.bosch-sensortec.com/bst/products/all_products/bmp180 + https://www.bosch-sensortec.com/bst/products/all_products/bmp280 + https://www.bosch-sensortec.com/bst/products/all_products/bme280 + +properties: + compatible: + enum: + - bosch,bmp085 + - bosch,bmp180 + - bosch,bmp280 + - bosch,bme280 + + vddd-supply: + description: + digital voltage regulator (see regulator/regulator.txt) + maxItems: 1 + + vdda-supply: + description: + analog voltage regulator (see regulator/regulator.txt) + maxItems: 1 + + reset-gpios: + description: + A GPIO line handling reset of the sensor. As the line is active low, + it should be marked GPIO_ACTIVE_LOW (see gpio/gpio.txt) + maxItems: 1 + + interrupts: + description: + interrupt mapping for IRQ (BMP085 only) + maxItems: 1 + +required: + - compatible + - vddd-supply + - vdda-supply + +examples: + - | + #include + #include + i2c0 { + #address-cells = <1>; + #size-cells = <0>; + pressure@77 { + compatible = "bosch,bmp085"; + reg = <0x77>; + interrupt-parent = <&gpio0>; + interrupts = <25 IRQ_TYPE_EDGE_RISING>; + reset-gpios = <&gpio0 26 GPIO_ACTIVE_LOW>; + vddd-supply = <&foo>; + vdda-supply = <&bar>; + }; + }; -- cgit v1.2.3 From 52e77d67dd8d48e4b74341c4825c2e915ceaedcd Mon Sep 17 00:00:00 2001 From: Robert Jones Date: Wed, 10 Apr 2019 17:12:08 -0700 Subject: dt-bindings: iio: accel: add LIS2DE12 sensor device binding Signed-off-by: Robert Jones Signed-off-by: Jonathan Cameron --- Documentation/devicetree/bindings/iio/st-sensors.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/st-sensors.txt b/Documentation/devicetree/bindings/iio/st-sensors.txt index 52ee4baec6f0..0ef64a444479 100644 --- a/Documentation/devicetree/bindings/iio/st-sensors.txt +++ b/Documentation/devicetree/bindings/iio/st-sensors.txt @@ -49,6 +49,7 @@ Accelerometers: - st,lis2dw12 - st,lis3dhh - st,lis3de +- st,lis2de12 Gyroscopes: - st,l3g4200d-gyro -- cgit v1.2.3 From d6edf95abdb56e252b183ebc12c9bb2cf831d154 Mon Sep 17 00:00:00 2001 From: Andreas Klinger Date: Tue, 9 Apr 2019 21:10:55 +0200 Subject: dt-bindings: iio: srf04: add Maxbotix ultrasonic iio proximity sensors add compatibles for Maxbotix ultrasonic iio sensor types to yaml documentation Signed-off-by: Andreas Klinger Reviewed-by: Rob Herring Signed-off-by: Jonathan Cameron --- .../bindings/iio/proximity/devantech-srf04.yaml | 25 ++++++++++++++-------- 1 file changed, 16 insertions(+), 9 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/proximity/devantech-srf04.yaml b/Documentation/devicetree/bindings/iio/proximity/devantech-srf04.yaml index e7aab785c97d..4e80ea7c1475 100644 --- a/Documentation/devicetree/bindings/iio/proximity/devantech-srf04.yaml +++ b/Documentation/devicetree/bindings/iio/proximity/devantech-srf04.yaml @@ -4,7 +4,7 @@ $id: http://devicetree.org/schemas/iio/proximity/devantech-srf04.yaml# $schema: http://devicetree.org/meta-schemas/core.yaml# -title: Devantech SRF04 ultrasonic range finder +title: Devantech SRF04 and Maxbotix mb1000 ultrasonic range finder maintainers: - Andreas Klinger @@ -16,19 +16,28 @@ description: | - echo-gpio is held high by the sensor after sending ultrasonic burst until it is received once again - Specifications about the driver can be found at: + Specifications about the devices can be found at: http://www.robot-electronics.co.uk/htm/srf04tech.htm + http://www.maxbotix.com/documents/LV-MaxSonar-EZ_Datasheet.pdf + properties: compatible: - items: - - const: devantech,srf04 + enum: + - devantech,srf04 + - maxbotix,mb1000 + - maxbotix,mb1010 + - maxbotix,mb1020 + - maxbotix,mb1030 + - maxbotix,mb1040 trig-gpios: description: - Definition of the GPIO for the triggering (output) This GPIO is set - for about 10 us by the driver to tell the device it should initiate - the measurement cycle. + Definition of the GPIO for the triggering (output) + This GPIO is set for about 10 us by the driver to tell the device it + should initiate the measurement cycle. + See Documentation/devicetree/bindings/gpio/gpio.txt for information + on how to specify a consumer gpio. maxItems: 1 echo-gpios: @@ -40,8 +49,6 @@ properties: trip. It needs to be an GPIO which is able to deliver an interrupt because the time between two interrupts is measured in the driver. - See Documentation/devicetree/bindings/gpio/gpio.txt for information - on how to specify a consumer gpio. maxItems: 1 required: -- cgit v1.2.3 From 955e007729542aa019044b4b3ae71a83c879eede Mon Sep 17 00:00:00 2001 From: Rui Miguel Silva Date: Fri, 12 Apr 2019 17:48:56 +0100 Subject: iio: gyro: add DT bindings to fxas21002c Add device tree bindings for the FXAS21002C gyroscope. Signed-off-by: Rui Miguel Silva Reviewed-by: Rob Herring Signed-off-by: Jonathan Cameron --- .../bindings/iio/gyroscope/nxp,fxas21002c.txt | 31 ++++++++++++++++++++++ 1 file changed, 31 insertions(+) create mode 100644 Documentation/devicetree/bindings/iio/gyroscope/nxp,fxas21002c.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/gyroscope/nxp,fxas21002c.txt b/Documentation/devicetree/bindings/iio/gyroscope/nxp,fxas21002c.txt new file mode 100644 index 000000000000..465e104bbf14 --- /dev/null +++ b/Documentation/devicetree/bindings/iio/gyroscope/nxp,fxas21002c.txt @@ -0,0 +1,31 @@ +* NXP FXAS21002C Gyroscope device tree bindings + +http://www.nxp.com/products/sensors/gyroscopes/3-axis-digital-gyroscope:FXAS21002C + +Required properties: + - compatible : should be "nxp,fxas21002c" + - reg : the I2C address of the sensor or SPI chip select number for the + device. + - vdd-supply: phandle to the regulator that provides power to the sensor. + - vddio-supply: phandle to the regulator that provides power to the bus. + +Optional properties: + - reset-gpios : gpio used to reset the device, see gpio/gpio.txt + - interrupts : device support 2 interrupts, INT1 and INT2, + the interrupts can be triggered on rising or falling edges. + See interrupt-controller/interrupts.txt + - interrupt-names: should contain "INT1" or "INT2", the gyroscope interrupt + line in use. + - drive-open-drain: the interrupt/data ready line will be configured + as open drain, which is useful if several sensors share + the same interrupt line. This is a boolean property. + (This binding is taken from pinctrl/pinctrl-bindings.txt) + +Example: + +gyroscope@20 { + compatible = "nxp,fxas21002c"; + reg = <0x20>; + vdd-supply = <®_peri_3p15v>; + vddio-supply = <®_peri_3p15v>; +}; -- cgit v1.2.3 From 9b0879620ea8b612f1baab188cb867fd055899d6 Mon Sep 17 00:00:00 2001 From: Nava kishore Manne Date: Mon, 15 Apr 2019 12:47:47 +0530 Subject: dt-bindings: fpga: Add bindings for ZynqMP fpga driver Add documentation to describe Xilinx ZynqMP fpga driver bindings. Signed-off-by: Nava kishore Manne Reviewed-by: Rob Herring Acked-by: Alan Tull Acked-by: Moritz Fischer Signed-off-by: Michal Simek --- .../bindings/fpga/xlnx,zynqmp-pcap-fpga.txt | 25 ++++++++++++++++++++++ 1 file changed, 25 insertions(+) create mode 100644 Documentation/devicetree/bindings/fpga/xlnx,zynqmp-pcap-fpga.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/fpga/xlnx,zynqmp-pcap-fpga.txt b/Documentation/devicetree/bindings/fpga/xlnx,zynqmp-pcap-fpga.txt new file mode 100644 index 000000000000..3052bf619dd5 --- /dev/null +++ b/Documentation/devicetree/bindings/fpga/xlnx,zynqmp-pcap-fpga.txt @@ -0,0 +1,25 @@ +Devicetree bindings for Zynq Ultrascale MPSoC FPGA Manager. +The ZynqMP SoC uses the PCAP (Processor configuration Port) to configure the +Programmable Logic (PL). The configuration uses the firmware interface. + +Required properties: +- compatible: should contain "xlnx,zynqmp-pcap-fpga" + +Example for full FPGA configuration: + + fpga-region0 { + compatible = "fpga-region"; + fpga-mgr = <&zynqmp_pcap>; + #address-cells = <0x1>; + #size-cells = <0x1>; + }; + + firmware { + zynqmp_firmware: zynqmp-firmware { + compatible = "xlnx,zynqmp-firmware"; + method = "smc"; + zynqmp_pcap: pcap { + compatible = "xlnx,zynqmp-pcap-fpga"; + }; + }; + }; -- cgit v1.2.3 From 3ec25826ae33618a03c28235af8d62e8a7f7f15f Mon Sep 17 00:00:00 2001 From: Paul Gortmaker Date: Fri, 12 Apr 2019 22:11:31 -0400 Subject: printk: Tie printk_once / printk_deferred_once into .data.once for reset In commit b1fca27d384e ("kernel debug: support resetting WARN*_ONCE") we got the opportunity to reset state on the one shot messages, without having to reboot. However printk_once (printk_deferred_once) live in a different file and didn't get the same kind of update/conversion, so they remain unconditionally one shot, until the system is rebooted. For example, we currently have: sched/rt.c: printk_deferred_once("sched: RT throttling activated\n"); ..which could reasonably be tripped as someone is testing and tuning a new system/workload and their task placements. For consistency, and to avoid reboots in the same vein as the original commit, we make these two instances of _once the same as the WARN*_ONCE instances are. Link: http://lkml.kernel.org/r/1555121491-31213-1-git-send-email-paul.gortmaker@windriver.com Cc: Andi Kleen Cc: Petr Mladek Cc: Sergey Senozhatsky Cc: Steven Rostedt Cc: Andrew Morton Signed-off-by: Paul Gortmaker Reviewed-by: Sergey Senozhatsky Signed-off-by: Petr Mladek --- Documentation/clearing-warn-once.txt | 2 +- include/linux/printk.h | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/clearing-warn-once.txt b/Documentation/clearing-warn-once.txt index 5b1f5d547be1..c68598b31428 100644 --- a/Documentation/clearing-warn-once.txt +++ b/Documentation/clearing-warn-once.txt @@ -1,5 +1,5 @@ -WARN_ONCE / WARN_ON_ONCE only print a warning once. +WARN_ONCE / WARN_ON_ONCE / printk_once only emit a message once. echo 1 > /sys/kernel/debug/clear_warn_once diff --git a/include/linux/printk.h b/include/linux/printk.h index d7c77ed1a4cb..84ea4d094af3 100644 --- a/include/linux/printk.h +++ b/include/linux/printk.h @@ -347,7 +347,7 @@ extern int kptr_restrict; #ifdef CONFIG_PRINTK #define printk_once(fmt, ...) \ ({ \ - static bool __print_once __read_mostly; \ + static bool __section(.data.once) __print_once; \ bool __ret_print_once = !__print_once; \ \ if (!__print_once) { \ @@ -358,7 +358,7 @@ extern int kptr_restrict; }) #define printk_deferred_once(fmt, ...) \ ({ \ - static bool __print_once __read_mostly; \ + static bool __section(.data.once) __print_once; \ bool __ret_print_once = !__print_once; \ \ if (!__print_once) { \ -- cgit v1.2.3 From ad64a7908c0a4f0712dc518e573054e2ade3aed6 Mon Sep 17 00:00:00 2001 From: Sowjanya Komatineni Date: Sat, 23 Mar 2019 21:45:21 -0700 Subject: dt-bindings: mmc: tegra: document Tegra194 compatible string SDHCI controller of Tegra194 is similar to SDHCI controller in Tegra186. This patch documents Tegra194 sdhci compatible string. Signed-off-by: Sowjanya Komatineni Signed-off-by: Ulf Hansson --- Documentation/devicetree/bindings/mmc/nvidia,tegra20-sdhci.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mmc/nvidia,tegra20-sdhci.txt b/Documentation/devicetree/bindings/mmc/nvidia,tegra20-sdhci.txt index 2cecdc71d94c..2cf3affa1be7 100644 --- a/Documentation/devicetree/bindings/mmc/nvidia,tegra20-sdhci.txt +++ b/Documentation/devicetree/bindings/mmc/nvidia,tegra20-sdhci.txt @@ -14,6 +14,7 @@ Required properties: - "nvidia,tegra124-sdhci": for Tegra124 and Tegra132 - "nvidia,tegra210-sdhci": for Tegra210 - "nvidia,tegra186-sdhci": for Tegra186 + - "nvidia,tegra194-sdhci": for Tegra194 - clocks : Must contain one entry, for the module clock. See ../clocks/clock-bindings.txt for details. - resets : Must contain an entry for each entry in reset-names. -- cgit v1.2.3 From 28f22fb755ecf9f933f045bc0afdb8140641b01c Mon Sep 17 00:00:00 2001 From: Christoph Muellner Date: Fri, 22 Mar 2019 12:38:04 +0100 Subject: dt-bindings: mmc: Add disable-cqe-dcmd property. Add disable-cqe-dcmd as optional property for MMC hosts. This property allows to disable or not enable the direct command features of the command queue engine. Signed-off-by: Christoph Muellner Signed-off-by: Philipp Tomsich Fixes: 84362d79f436 ("mmc: sdhci-of-arasan: Add CQHCI support for arasan,sdhci-5.1") Cc: stable@vger.kernel.org Signed-off-by: Ulf Hansson --- Documentation/devicetree/bindings/mmc/mmc.txt | 2 ++ 1 file changed, 2 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mmc/mmc.txt b/Documentation/devicetree/bindings/mmc/mmc.txt index cdbcfd3a4ff2..c269dbe384fe 100644 --- a/Documentation/devicetree/bindings/mmc/mmc.txt +++ b/Documentation/devicetree/bindings/mmc/mmc.txt @@ -64,6 +64,8 @@ Optional properties: whether pwrseq-simple is used. Default to 10ms if no available. - supports-cqe : The presence of this property indicates that the corresponding MMC host controller supports HW command queue feature. +- disable-cqe-dcmd: This property indicates that the MMC controller's command + queue engine (CQE) does not support direct commands (DCMDs). *NOTE* on CD and WP polarity. To use common for all SD/MMC host controllers line polarity properties, we have to fix the meaning of the "normal" and "inverted" -- cgit v1.2.3 From c29687c354c58cd56fb2529fb89266c280206cf9 Mon Sep 17 00:00:00 2001 From: Pascal PAILLET-LME Date: Mon, 15 Apr 2019 09:17:37 +0000 Subject: dt-bindings: regulator: Add stm32mp1 pwr regulators Document devicetree bindings for stm32mp1 pwr regulators. Signed-off-by: Pascal Paillet Signed-off-by: Mark Brown --- .../bindings/regulator/st,stm32mp1-pwr-reg.txt | 43 ++++++++++++++++++++++ 1 file changed, 43 insertions(+) create mode 100644 Documentation/devicetree/bindings/regulator/st,stm32mp1-pwr-reg.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/regulator/st,stm32mp1-pwr-reg.txt b/Documentation/devicetree/bindings/regulator/st,stm32mp1-pwr-reg.txt new file mode 100644 index 000000000000..e372dd3f0c8a --- /dev/null +++ b/Documentation/devicetree/bindings/regulator/st,stm32mp1-pwr-reg.txt @@ -0,0 +1,43 @@ +STM32MP1 PWR Regulators +----------------------- + +Available Regulators in STM32MP1 PWR block are: + - reg11 for regulator 1V1 + - reg18 for regulator 1V8 + - usb33 for the swtich USB3V3 + +Required properties: +- compatible: Must be "st,stm32mp1,pwr-reg" +- list of child nodes that specify the regulator reg11, reg18 or usb33 + initialization data for defined regulators. The definition for each of + these nodes is defined using the standard binding for regulators found at + Documentation/devicetree/bindings/regulator/regulator.txt. +- vdd-supply: phandle to the parent supply/regulator node for vdd input +- vdd_3v3_usbfs-supply: phandle to the parent supply/regulator node for usb33 + +Example: + +pwr_regulators: pwr@50001000 { + compatible = "st,stm32mp1,pwr-reg"; + reg = <0x50001000 0x10>; + vdd-supply = <&vdd>; + vdd_3v3_usbfs-supply = <&vdd_usb>; + + reg11: reg11 { + regulator-name = "reg11"; + regulator-min-microvolt = <1100000>; + regulator-max-microvolt = <1100000>; + }; + + reg18: reg18 { + regulator-name = "reg18"; + regulator-min-microvolt = <1800000>; + regulator-max-microvolt = <1800000>; + }; + + usb33: usb33 { + regulator-name = "usb33"; + regulator-min-microvolt = <3300000>; + regulator-max-microvolt = <3300000>; + }; +}; -- cgit v1.2.3 From a3438152c66728e5dc15a3aa167b836ce7329e68 Mon Sep 17 00:00:00 2001 From: Qii Wang Date: Tue, 2 Apr 2019 20:35:56 +0800 Subject: dt-bindings: i2c: Add Mediatek MT8183 i2c binding Add MT8183 i2c binding to binding file. Compare to MT2712 i2c controller, MT8183 has different registers, offsets, and clock. Signed-off-by: Qii Wang Reviewed-by: Rob Herring Reviewed-by: Matthias Brugger Signed-off-by: Wolfram Sang --- Documentation/devicetree/bindings/i2c/i2c-mtk.txt | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/i2c/i2c-mtk.txt b/Documentation/devicetree/bindings/i2c/i2c-mtk.txt index ee4c32454198..b052f29e72f0 100644 --- a/Documentation/devicetree/bindings/i2c/i2c-mtk.txt +++ b/Documentation/devicetree/bindings/i2c/i2c-mtk.txt @@ -12,13 +12,15 @@ Required properties: "mediatek,mt7623-i2c", "mediatek,mt6577-i2c": for MediaTek MT7623 "mediatek,mt7629-i2c", "mediatek,mt2712-i2c": for MediaTek MT7629 "mediatek,mt8173-i2c": for MediaTek MT8173 + "mediatek,mt8183-i2c": for MediaTek MT8183 - reg: physical base address of the controller and dma base, length of memory mapped region. - interrupts: interrupt number to the cpu. - clock-div: the fixed value for frequency divider of clock source in i2c module. Each IC may be different. - clocks: clock name from clock manager - - clock-names: Must include "main" and "dma", if enable have-pmic need include + - clock-names: Must include "main" and "dma", "arb" is for multi-master that + one bus has more than two i2c controllers, if enable have-pmic need include "pmic" extra. Optional properties: -- cgit v1.2.3 From 1c55c4263fe76f1a65b198787495c7f5f9e48002 Mon Sep 17 00:00:00 2001 From: Kishon Vijay Abraham I Date: Mon, 25 Mar 2019 15:09:28 +0530 Subject: dt-bindings: PCI: Add dt-binding to configure PCIe mode Add "ti,syscon-pcie-mode" dt-binding to hold phandle to the syscon register that should be used to configure PCIe in RC mode or EP mode. Signed-off-by: Kishon Vijay Abraham I Signed-off-by: Lorenzo Pieralisi Reviewed-by: Rob Herring --- Documentation/devicetree/bindings/pci/pci-keystone.txt | 2 ++ 1 file changed, 2 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/pci/pci-keystone.txt b/Documentation/devicetree/bindings/pci/pci-keystone.txt index 3a551687cfa2..8ee07197a063 100644 --- a/Documentation/devicetree/bindings/pci/pci-keystone.txt +++ b/Documentation/devicetree/bindings/pci/pci-keystone.txt @@ -23,6 +23,8 @@ pcie_msi_intc : Interrupt controller device node for MSI IRQ chip ti,syscon-pcie-id : phandle to the device control module required to set device id and vendor id. +ti,syscon-pcie-mode : phandle to the device control module required to configure + PCI in either RC mode or EP mode. Example: pcie_msi_intc: msi-interrupt-controller { -- cgit v1.2.3 From 26f51e85b3b61106ea8b9e1c0a277aa3851f7433 Mon Sep 17 00:00:00 2001 From: Kishon Vijay Abraham I Date: Mon, 25 Mar 2019 15:09:30 +0530 Subject: dt-bindings: PCI: Document "atu" reg-names Document "atu" reg-names required to get the register space for ATU in Synopsys designware core version >= 4.80. Signed-off-by: Kishon Vijay Abraham I Signed-off-by: Lorenzo Pieralisi --- Documentation/devicetree/bindings/pci/designware-pcie.txt | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/pci/designware-pcie.txt b/Documentation/devicetree/bindings/pci/designware-pcie.txt index c124f9bc11f3..5561a1c060d0 100644 --- a/Documentation/devicetree/bindings/pci/designware-pcie.txt +++ b/Documentation/devicetree/bindings/pci/designware-pcie.txt @@ -4,8 +4,11 @@ Required properties: - compatible: "snps,dw-pcie" for RC mode; "snps,dw-pcie-ep" for EP mode; -- reg: Should contain the configuration address space. -- reg-names: Must be "config" for the PCIe configuration space. +- reg: For designware cores version < 4.80 contains the configuration + address space. For designware core version >= 4.80, contains + the configuration and ATU address space +- reg-names: Must be "config" for the PCIe configuration space and "atu" for + the ATU address space. (The old way of getting the configuration address space from "ranges" is deprecated and should be avoided.) - num-lanes: number of lanes to use -- cgit v1.2.3 From 162aaa3b6cc151720392adbdf7c6db9a7e06c769 Mon Sep 17 00:00:00 2001 From: Kishon Vijay Abraham I Date: Mon, 25 Mar 2019 15:09:34 +0530 Subject: dt-bindings: PCI: Add PCI RC DT binding documentation for AM654 Add devicetree binding documentation for PCIe in RC mode present in AM654 SoC. Signed-off-by: Kishon Vijay Abraham I Signed-off-by: Lorenzo Pieralisi Reviewed-by: Rob Herring --- Documentation/devicetree/bindings/pci/pci-keystone.txt | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/pci/pci-keystone.txt b/Documentation/devicetree/bindings/pci/pci-keystone.txt index 8ee07197a063..5c60e911b8b1 100644 --- a/Documentation/devicetree/bindings/pci/pci-keystone.txt +++ b/Documentation/devicetree/bindings/pci/pci-keystone.txt @@ -11,7 +11,8 @@ described here as well as properties that are not applicable. Required Properties:- -compatibility: "ti,keystone-pcie" +compatibility: Should be "ti,keystone-pcie" for RC on Keystone2 SoC + Should be "ti,am654-pcie-rc" for RC on AM654x SoC reg: Three register ranges as listed in the reg-names property reg-names: "dbics" for the DesignWare PCIe registers, "app" for the TI specific application registers, "config" for the @@ -20,6 +21,9 @@ reg-names: "dbics" for the DesignWare PCIe registers, "app" for the pcie_msi_intc : Interrupt controller device node for MSI IRQ chip interrupt-cells: should be set to 1 interrupts: GIC interrupt lines connected to PCI MSI interrupt lines + (required if the compatible is "ti,keystone-pcie") +msi-map: As specified in Documentation/devicetree/bindings/pci/pci-msi.txt + (required if the compatible is "ti,am654-pcie-rc". ti,syscon-pcie-id : phandle to the device control module required to set device id and vendor id. -- cgit v1.2.3 From 14e14aaf61321ba30d0bbdf4c4668f260ca1141c Mon Sep 17 00:00:00 2001 From: Nick Crews Date: Thu, 4 Apr 2019 16:54:15 -0600 Subject: platform/chrome: wilco_ec: Standardize mailbox interface The current API for the wilco EC mailbox interface is bad. It assumes that most messages sent to the EC follow a similar structure, with a command byte in MBOX[0], followed by a junk byte, followed by actual data. This doesn't happen in several cases, such as setting the RTC time, using the raw debugfs interface, and reading or writing properties such as the Peak Shift policy (this last to be submitted soon). Similarly for the response message from the EC, the current interface assumes that the first byte of data is always 0, and the second byte is unused. However, in both setting and getting the RTC time, in the debugfs interface, and for reading and writing properties, this isn't true. The current way to resolve this is to use WILCO_EC_FLAG_RAW* flags to specify when and when not to skip these initial bytes in the sent and received message. They are confusing and used so much that they are normal, and not exceptions. In addition, the first byte of response in the debugfs interface is still always skipped, which is weird, since this raw interface should be giving the entire result. Additionally, sent messages assume the first byte is a command, and so struct wilco_ec_message contains the "command" field. In setting or getting properties however, the first byte is not a command, and so this field has to be filled with a byte that isn't actually a command. This is again inconsistent. wilco_ec_message contains a result field as well, copied from wilco_ec_response->result. The message result field should be removed: if the message fails, the cause is already logged, and the callers are alerted. They will never care about the actual state of the result flag. These flags and different cases make the wilco_ec_transfer() function, used in wilco_ec_mailbox(), really gross, dealing with a bunch of different cases. It's difficult to figure out what it is doing. Finally, making these assumptions about the structure of a message make it so that the messages do not correspond well with the specification for the EC's mailbox interface. For instance, this interface specification may say that MBOX[9] in the received message contains some information, but the calling code needs to remember that the first byte of response is always skipped, and because it didn't set the RESPONSE_RAW flag, the next byte is also skipped, so this information is actually contained within wilco_ec_message->response_data[7]. This makes it difficult to maintain this code in the future. To fix these problems this patch standardizes the mailbox interface by: - Removing the WILCO_EC_FLAG_RAW* flags - Removing the command and reserved_raw bytes from wilco_ec_request - Removing the mbox0 byte from wilco_ec_response - Simplifying wilco_ec_transfer() because of these changes - Gives the callers of wilco_ec_mailbox() the responsibility of exactly and consistently defining the structure of the mailbox request and response - Removing command and result from wilco_ec_message. This results in the reduction of total code, and makes it much more maintainable and understandable. Signed-off-by: Nick Crews Acked-by: Alexandre Belloni Signed-off-by: Enric Balletbo i Serra --- Documentation/ABI/testing/debugfs-wilco-ec | 32 +++++++++------ drivers/platform/chrome/wilco_ec/debugfs.c | 42 ++++---------------- drivers/platform/chrome/wilco_ec/mailbox.c | 53 ++++++++++--------------- drivers/rtc/rtc-wilco-ec.c | 63 ++++++++++++++++++------------ include/linux/platform_data/wilco-ec.h | 22 +---------- 5 files changed, 91 insertions(+), 121 deletions(-) (limited to 'Documentation') diff --git a/Documentation/ABI/testing/debugfs-wilco-ec b/Documentation/ABI/testing/debugfs-wilco-ec index f814f112e213..7ff6b45be703 100644 --- a/Documentation/ABI/testing/debugfs-wilco-ec +++ b/Documentation/ABI/testing/debugfs-wilco-ec @@ -4,20 +4,30 @@ KernelVersion: 5.1 Description: Write and read raw mailbox commands to the EC. - For writing: - Bytes 0-1 indicate the message type: - 00 F0 = Execute Legacy Command - 00 F2 = Read/Write NVRAM Property - Byte 2 provides the command code - Bytes 3+ consist of the data passed in the request + You can write a hexadecimal sentence to raw, and that series of + bytes will be sent to the EC. Then, you can read the bytes of + response by reading from raw. - At least three bytes are required, for the msg type and command, - with additional bytes optional for additional data. + For writing, bytes 0-1 indicate the message type, one of enum + wilco_ec_msg_type. Byte 2+ consist of the data passed in the + request, starting at MBOX[0] + + At least three bytes are required for writing, two for the type + and at least a single byte of data. Only the first + EC_MAILBOX_DATA_SIZE bytes of MBOX will be used. Example: // Request EC info type 3 (EC firmware build date) - $ echo 00 f0 38 00 03 00 > raw + // Corresponds with sending type 0x00f0 with + // MBOX = [38, 00, 03, 00] + $ echo 00 f0 38 00 03 00 > /sys/kernel/debug/wilco_ec/raw // View the result. The decoded ASCII result "12/21/18" is // included after the raw hex. - $ cat raw - 00 31 32 2f 32 31 2f 31 38 00 38 00 01 00 2f 00 .12/21/18.8... + // Corresponds with MBOX = [00, 00, 31, 32, 2f, 32, 31, 38, ...] + $ cat /sys/kernel/debug/wilco_ec/raw + 00 00 31 32 2f 32 31 2f 31 38 00 38 00 01 00 2f 00 ..12/21/18.8... + + Note that the first 32 bytes of the received MBOX[] will be + printed, even if some of the data is junk. It is up to you to + know how many of the first bytes of data are the actual + response. diff --git a/drivers/platform/chrome/wilco_ec/debugfs.c b/drivers/platform/chrome/wilco_ec/debugfs.c index c090db2cd5be..8d307378c1cb 100644 --- a/drivers/platform/chrome/wilco_ec/debugfs.c +++ b/drivers/platform/chrome/wilco_ec/debugfs.c @@ -4,31 +4,7 @@ * * Copyright 2019 Google LLC * - * There is only one attribute used for debugging, called raw. - * You can write a hexadecimal sentence to raw, and that series of bytes - * will be sent to the EC. Then, you can read the bytes of response - * by reading from raw. - * - * For writing: - * Bytes 0-1 indicate the message type: - * 00 F0 = Execute Legacy Command - * 00 F2 = Read/Write NVRAM Property - * Byte 2 provides the command code - * Bytes 3+ consist of the data passed in the request - * - * When referencing the EC interface spec, byte 2 corresponds to MBOX[0], - * byte 3 corresponds to MBOX[1], etc. - * - * At least three bytes are required, for the msg type and command, - * with additional bytes optional for additional data. - * - * Example: - * // Request EC info type 3 (EC firmware build date) - * $ echo 00 f0 38 00 03 00 > raw - * // View the result. The decoded ASCII result "12/21/18" is - * // included after the raw hex. - * $ cat raw - * 00 31 32 2f 32 31 2f 31 38 00 38 00 01 00 2f 00 .12/21/18.8... + * See Documentation/ABI/testing/debugfs-wilco-ec for usage. */ #include @@ -136,18 +112,15 @@ static ssize_t raw_write(struct file *file, const char __user *user_buf, ret = parse_hex_sentence(buf, kcount, request_data, TYPE_AND_DATA_SIZE); if (ret < 0) return ret; - /* Need at least two bytes for message type and one for command */ + /* Need at least two bytes for message type and one byte of data */ if (ret < 3) return -EINVAL; - /* Clear response data buffer */ - memset(debug_info->raw_data, '\0', EC_MAILBOX_DATA_SIZE_EXTENDED); - msg.type = request_data[0] << 8 | request_data[1]; - msg.flags = WILCO_EC_FLAG_RAW; - msg.command = request_data[2]; - msg.request_data = ret > 3 ? request_data + 3 : 0; - msg.request_size = ret - 3; + msg.flags = 0; + msg.request_data = request_data + 2; + msg.request_size = ret - 2; + memset(debug_info->raw_data, 0, sizeof(debug_info->raw_data)); msg.response_data = debug_info->raw_data; msg.response_size = EC_MAILBOX_DATA_SIZE; @@ -174,7 +147,8 @@ static ssize_t raw_read(struct file *file, char __user *user_buf, size_t count, fmt_len = hex_dump_to_buffer(debug_info->raw_data, debug_info->response_size, 16, 1, debug_info->formatted_data, - FORMATTED_BUFFER_SIZE, true); + sizeof(debug_info->formatted_data), + true); /* Only return response the first time it is read */ debug_info->response_size = 0; } diff --git a/drivers/platform/chrome/wilco_ec/mailbox.c b/drivers/platform/chrome/wilco_ec/mailbox.c index 14355668ddfa..7fb58b487963 100644 --- a/drivers/platform/chrome/wilco_ec/mailbox.c +++ b/drivers/platform/chrome/wilco_ec/mailbox.c @@ -92,21 +92,10 @@ static void wilco_ec_prepare(struct wilco_ec_message *msg, struct wilco_ec_request *rq) { memset(rq, 0, sizeof(*rq)); - - /* Handle messages without trimming bytes from the request */ - if (msg->request_size && msg->flags & WILCO_EC_FLAG_RAW_REQUEST) { - rq->reserved_raw = *(u8 *)msg->request_data; - msg->request_size--; - memmove(msg->request_data, msg->request_data + 1, - msg->request_size); - } - - /* Fill in request packet */ rq->struct_version = EC_MAILBOX_PROTO_VERSION; rq->mailbox_id = msg->type; rq->mailbox_version = EC_MAILBOX_VERSION; - rq->data_size = msg->request_size + EC_MAILBOX_DATA_EXTRA; - rq->command = msg->command; + rq->data_size = msg->request_size; /* Checksum header and data */ rq->checksum = wilco_ec_checksum(rq, sizeof(*rq)); @@ -159,6 +148,12 @@ static int wilco_ec_transfer(struct wilco_ec_device *ec, return -EIO; } + /* + * The EC always returns either EC_MAILBOX_DATA_SIZE or + * EC_MAILBOX_DATA_SIZE_EXTENDED bytes of data, so we need to + * calculate the checksum on **all** of this data, even if we + * won't use all of it. + */ if (msg->flags & WILCO_EC_FLAG_EXTENDED_DATA) size = EC_MAILBOX_DATA_SIZE_EXTENDED; else @@ -173,33 +168,26 @@ static int wilco_ec_transfer(struct wilco_ec_device *ec, return -EBADMSG; } - /* Check that the EC reported success */ - msg->result = rs->result; - if (msg->result) { - dev_dbg(ec->dev, "bad response: 0x%02x\n", msg->result); + if (rs->result) { + dev_dbg(ec->dev, "EC reported failure: 0x%02x\n", rs->result); return -EBADMSG; } - /* Check the returned data size, skipping the header */ if (rs->data_size != size) { dev_dbg(ec->dev, "unexpected packet size (%u != %zu)", rs->data_size, size); return -EMSGSIZE; } - /* Skip 1 response data byte unless specified */ - size = (msg->flags & WILCO_EC_FLAG_RAW_RESPONSE) ? 0 : 1; - if ((ssize_t) rs->data_size - size < msg->response_size) { - dev_dbg(ec->dev, "response data too short (%zd < %zu)", - (ssize_t) rs->data_size - size, msg->response_size); + if (rs->data_size < msg->response_size) { + dev_dbg(ec->dev, "EC didn't return enough data (%u < %zu)", + rs->data_size, msg->response_size); return -EMSGSIZE; } - /* Ignore response data bytes as requested */ - memcpy(msg->response_data, rs->data + size, msg->response_size); + memcpy(msg->response_data, rs->data, msg->response_size); - /* Return actual amount of data received */ - return msg->response_size; + return rs->data_size; } /** @@ -207,10 +195,12 @@ static int wilco_ec_transfer(struct wilco_ec_device *ec, * @ec: EC device. * @msg: EC message data for request and response. * - * On entry msg->type, msg->flags, msg->command, msg->request_size, - * msg->response_size, and msg->request_data should all be filled in. + * On entry msg->type, msg->request_size, and msg->request_data should all be + * filled in. If desired, msg->flags can be set. * - * On exit msg->result and msg->response_data will be filled. + * If a response is expected, msg->response_size should be set, and + * msg->response_data should point to a buffer with enough space. On exit + * msg->response_data will be filled. * * Return: number of bytes received or negative error code on failure. */ @@ -219,9 +209,8 @@ int wilco_ec_mailbox(struct wilco_ec_device *ec, struct wilco_ec_message *msg) struct wilco_ec_request *rq; int ret; - dev_dbg(ec->dev, "cmd=%02x type=%04x flags=%02x rslen=%zu rqlen=%zu\n", - msg->command, msg->type, msg->flags, msg->response_size, - msg->request_size); + dev_dbg(ec->dev, "type=%04x flags=%02x rslen=%zu rqlen=%zu\n", + msg->type, msg->flags, msg->response_size, msg->request_size); mutex_lock(&ec->mailbox_lock); /* Prepare request packet */ diff --git a/drivers/rtc/rtc-wilco-ec.c b/drivers/rtc/rtc-wilco-ec.c index e62bda0cb53e..8ad4c4e6d557 100644 --- a/drivers/rtc/rtc-wilco-ec.c +++ b/drivers/rtc/rtc-wilco-ec.c @@ -21,8 +21,20 @@ #define EC_CMOS_TOD_WRITE 0x02 #define EC_CMOS_TOD_READ 0x08 +/* Message sent to the EC to request the current time. */ +struct ec_rtc_read_request { + u8 command; + u8 reserved; + u8 param; +} __packed; +static struct ec_rtc_read_request read_rq = { + .command = EC_COMMAND_CMOS, + .param = EC_CMOS_TOD_READ, +}; + /** - * struct ec_rtc_read - Format of RTC returned by EC. + * struct ec_rtc_read_response - Format of RTC returned by EC. + * @reserved: Unused byte * @second: Second value (0..59) * @minute: Minute value (0..59) * @hour: Hour value (0..23) @@ -33,7 +45,8 @@ * * All values are presented in binary (not BCD). */ -struct ec_rtc_read { +struct ec_rtc_read_response { + u8 reserved; u8 second; u8 minute; u8 hour; @@ -44,8 +57,10 @@ struct ec_rtc_read { } __packed; /** - * struct ec_rtc_write - Format of RTC sent to the EC. - * @param: EC_CMOS_TOD_WRITE + * struct ec_rtc_write_request - Format of RTC sent to the EC. + * @command: Always EC_COMMAND_CMOS + * @reserved: Unused byte + * @param: Always EC_CMOS_TOD_WRITE * @century: Century value (full year / 100) * @year: Year value (full year % 100) * @month: Month value (1..12) @@ -57,7 +72,9 @@ struct ec_rtc_read { * * All values are presented in BCD. */ -struct ec_rtc_write { +struct ec_rtc_write_request { + u8 command; + u8 reserved; u8 param; u8 century; u8 year; @@ -72,19 +89,17 @@ struct ec_rtc_write { static int wilco_ec_rtc_read(struct device *dev, struct rtc_time *tm) { struct wilco_ec_device *ec = dev_get_drvdata(dev->parent); - u8 param = EC_CMOS_TOD_READ; - struct ec_rtc_read rtc; - struct wilco_ec_message msg = { - .type = WILCO_EC_MSG_LEGACY, - .flags = WILCO_EC_FLAG_RAW_RESPONSE, - .command = EC_COMMAND_CMOS, - .request_data = ¶m, - .request_size = sizeof(param), - .response_data = &rtc, - .response_size = sizeof(rtc), - }; + struct ec_rtc_read_response rtc; + struct wilco_ec_message msg; int ret; + memset(&msg, 0, sizeof(msg)); + msg.type = WILCO_EC_MSG_LEGACY; + msg.request_data = &read_rq; + msg.request_size = sizeof(read_rq); + msg.response_data = &rtc; + msg.response_size = sizeof(rtc); + ret = wilco_ec_mailbox(ec, &msg); if (ret < 0) return ret; @@ -106,14 +121,8 @@ static int wilco_ec_rtc_read(struct device *dev, struct rtc_time *tm) static int wilco_ec_rtc_write(struct device *dev, struct rtc_time *tm) { struct wilco_ec_device *ec = dev_get_drvdata(dev->parent); - struct ec_rtc_write rtc; - struct wilco_ec_message msg = { - .type = WILCO_EC_MSG_LEGACY, - .flags = WILCO_EC_FLAG_RAW_RESPONSE, - .command = EC_COMMAND_CMOS, - .request_data = &rtc, - .request_size = sizeof(rtc), - }; + struct ec_rtc_write_request rtc; + struct wilco_ec_message msg; int year = tm->tm_year + 1900; /* * Convert from 0=Sunday to 0=Saturday for the EC @@ -123,6 +132,7 @@ static int wilco_ec_rtc_write(struct device *dev, struct rtc_time *tm) int wday = tm->tm_wday == 6 ? 0 : tm->tm_wday + 1; int ret; + rtc.command = EC_COMMAND_CMOS; rtc.param = EC_CMOS_TOD_WRITE; rtc.century = bin2bcd(year / 100); rtc.year = bin2bcd(year % 100); @@ -133,6 +143,11 @@ static int wilco_ec_rtc_write(struct device *dev, struct rtc_time *tm) rtc.second = bin2bcd(tm->tm_sec); rtc.weekday = bin2bcd(wday); + memset(&msg, 0, sizeof(msg)); + msg.type = WILCO_EC_MSG_LEGACY; + msg.request_data = &rtc; + msg.request_size = sizeof(rtc); + ret = wilco_ec_mailbox(ec, &msg); if (ret < 0) return ret; diff --git a/include/linux/platform_data/wilco-ec.h b/include/linux/platform_data/wilco-ec.h index 446473a46b88..1ff224793c99 100644 --- a/include/linux/platform_data/wilco-ec.h +++ b/include/linux/platform_data/wilco-ec.h @@ -14,10 +14,6 @@ /* Message flags for using the mailbox() interface */ #define WILCO_EC_FLAG_NO_RESPONSE BIT(0) /* EC does not respond */ #define WILCO_EC_FLAG_EXTENDED_DATA BIT(1) /* EC returns 256 data bytes */ -#define WILCO_EC_FLAG_RAW_REQUEST BIT(2) /* Do not trim request data */ -#define WILCO_EC_FLAG_RAW_RESPONSE BIT(3) /* Do not trim response data */ -#define WILCO_EC_FLAG_RAW (WILCO_EC_FLAG_RAW_REQUEST | \ - WILCO_EC_FLAG_RAW_RESPONSE) /* Normal commands have a maximum 32 bytes of data */ #define EC_MAILBOX_DATA_SIZE 32 @@ -56,10 +52,7 @@ struct wilco_ec_device { * @mailbox_id: Mailbox identifier, specifies the command set. * @mailbox_version: Mailbox interface version %EC_MAILBOX_VERSION * @reserved: Set to zero. - * @data_size: Length of request, data + last 2 bytes of the header. - * @command: Mailbox command code, unique for each mailbox_id set. - * @reserved_raw: Set to zero for most commands, but is used by - * some command types and for raw commands. + * @data_size: Length of following data. */ struct wilco_ec_request { u8 struct_version; @@ -68,8 +61,6 @@ struct wilco_ec_request { u8 mailbox_version; u8 reserved; u16 data_size; - u8 command; - u8 reserved_raw; } __packed; /** @@ -79,8 +70,6 @@ struct wilco_ec_request { * @result: Result code from the EC. Non-zero indicates an error. * @data_size: Length of the response data buffer. * @reserved: Set to zero. - * @mbox0: EC returned data at offset 0 is unused (always 0) so this byte - * is treated as part of the header instead of the data. * @data: Response data buffer. Max size is %EC_MAILBOX_DATA_SIZE_EXTENDED. */ struct wilco_ec_response { @@ -89,7 +78,6 @@ struct wilco_ec_response { u16 result; u16 data_size; u8 reserved[2]; - u8 mbox0; u8 data[0]; } __packed; @@ -111,21 +99,15 @@ enum wilco_ec_msg_type { * struct wilco_ec_message - Request and response message. * @type: Mailbox message type. * @flags: Message flags, e.g. %WILCO_EC_FLAG_NO_RESPONSE. - * @command: Mailbox command code. - * @result: Result code from the EC. Non-zero indicates an error. * @request_size: Number of bytes to send to the EC. * @request_data: Buffer containing the request data. - * @response_size: Number of bytes expected from the EC. - * This is 32 by default and 256 if the flag - * is set for %WILCO_EC_FLAG_EXTENDED_DATA + * @response_size: Number of bytes to read from EC. * @response_data: Buffer containing the response data, should be * response_size bytes and allocated by caller. */ struct wilco_ec_message { enum wilco_ec_msg_type type; u8 flags; - u8 command; - u8 result; size_t request_size; void *request_data; size_t response_size; -- cgit v1.2.3 From c4fcbf1186e777c315d934202e9f0faf1987fe3a Mon Sep 17 00:00:00 2001 From: Ryder Lee Date: Sun, 17 Feb 2019 21:50:30 +0800 Subject: dt-bindings: mediatek: update bindings for MT7629 SoC This updates bindings for MT7629 SoC, which includes very basic items such as system timer, UART, sysirq and scpsys unit. Signed-off-by: Ryder Lee Cc: Marc Zyngier Cc: Greg Kroah-Hartman Reviewed-by: Rob Herring Signed-off-by: Matthias Brugger --- .../devicetree/bindings/interrupt-controller/mediatek,sysirq.txt | 5 +++-- Documentation/devicetree/bindings/serial/mtk-uart.txt | 3 ++- Documentation/devicetree/bindings/soc/mediatek/scpsys.txt | 3 ++- 3 files changed, 7 insertions(+), 4 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/interrupt-controller/mediatek,sysirq.txt b/Documentation/devicetree/bindings/interrupt-controller/mediatek,sysirq.txt index ade059db0aa3..9ef089400840 100644 --- a/Documentation/devicetree/bindings/interrupt-controller/mediatek,sysirq.txt +++ b/Documentation/devicetree/bindings/interrupt-controller/mediatek,sysirq.txt @@ -1,6 +1,6 @@ -+Mediatek MT65xx/MT67xx/MT81xx sysirq +MediaTek sysirq -Mediatek SOCs sysirq support controllable irq inverter for each GIC SPI +MediaTek SOCs sysirq support controllable irq inverter for each GIC SPI interrupt. Required properties: @@ -11,6 +11,7 @@ Required properties: "mediatek,mt8127-sysirq", "mediatek,mt6577-sysirq": for MT8127 "mediatek,mt7622-sysirq", "mediatek,mt6577-sysirq": for MT7622 "mediatek,mt7623-sysirq", "mediatek,mt6577-sysirq": for MT7623 + "mediatek,mt7629-sysirq", "mediatek,mt6577-sysirq": for MT7629 "mediatek,mt6795-sysirq", "mediatek,mt6577-sysirq": for MT6795 "mediatek,mt6797-sysirq", "mediatek,mt6577-sysirq": for MT6797 "mediatek,mt6765-sysirq", "mediatek,mt6577-sysirq": for MT6765 diff --git a/Documentation/devicetree/bindings/serial/mtk-uart.txt b/Documentation/devicetree/bindings/serial/mtk-uart.txt index 742cb470595b..4910f6316c3e 100644 --- a/Documentation/devicetree/bindings/serial/mtk-uart.txt +++ b/Documentation/devicetree/bindings/serial/mtk-uart.txt @@ -1,4 +1,4 @@ -* Mediatek Universal Asynchronous Receiver/Transmitter (UART) +* MediaTek Universal Asynchronous Receiver/Transmitter (UART) Required properties: - compatible should contain: @@ -13,6 +13,7 @@ Required properties: * "mediatek,mt6797-uart" for MT6797 compatible UARTS * "mediatek,mt7622-uart" for MT7622 compatible UARTS * "mediatek,mt7623-uart" for MT7623 compatible UARTS + * "mediatek,mt7629-uart" for MT7629 compatible UARTS * "mediatek,mt8127-uart" for MT8127 compatible UARTS * "mediatek,mt8135-uart" for MT8135 compatible UARTS * "mediatek,mt8173-uart" for MT8173 compatible UARTS diff --git a/Documentation/devicetree/bindings/soc/mediatek/scpsys.txt b/Documentation/devicetree/bindings/soc/mediatek/scpsys.txt index d6fe16f094af..9a88d418e7a1 100644 --- a/Documentation/devicetree/bindings/soc/mediatek/scpsys.txt +++ b/Documentation/devicetree/bindings/soc/mediatek/scpsys.txt @@ -23,6 +23,7 @@ Required properties: - "mediatek,mt7622-scpsys" - "mediatek,mt7623-scpsys", "mediatek,mt2701-scpsys": For MT7623 SoC - "mediatek,mt7623a-scpsys": For MT7623A SoC + - "mediatek,mt7629-scpsys", "mediatek,mt7622-scpsys": For MT7629 SoC - "mediatek,mt8173-scpsys" - #power-domain-cells: Must be 1 - reg: Address range of the SCPSYS unit @@ -33,7 +34,7 @@ Required properties: Required clocks for MT2701 or MT7623: "mm", "mfg", "ethif" Required clocks for MT2712: "mm", "mfg", "venc", "jpgdec", "audio", "vdec" Required clocks for MT6797: "mm", "mfg", "vdec" - Required clocks for MT7622: "hif_sel" + Required clocks for MT7622 or MT7629: "hif_sel" Required clocks for MT7622A: "ethif" Required clocks for MT8173: "mm", "mfg", "venc", "venc_lt" -- cgit v1.2.3 From 9ccd75c55ac50f0ac23cc5bbb724613d2d7f1c89 Mon Sep 17 00:00:00 2001 From: Ryder Lee Date: Sun, 17 Feb 2019 21:50:31 +0800 Subject: dt-bindings: soc: fix a typo for MT7623A This fixes a typo for MT7623A Signed-off-by: Ryder Lee Reviewed-by: Rob Herring Signed-off-by: Matthias Brugger --- Documentation/devicetree/bindings/soc/mediatek/scpsys.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/soc/mediatek/scpsys.txt b/Documentation/devicetree/bindings/soc/mediatek/scpsys.txt index 9a88d418e7a1..876693a7ada5 100644 --- a/Documentation/devicetree/bindings/soc/mediatek/scpsys.txt +++ b/Documentation/devicetree/bindings/soc/mediatek/scpsys.txt @@ -35,7 +35,7 @@ Required properties: Required clocks for MT2712: "mm", "mfg", "venc", "jpgdec", "audio", "vdec" Required clocks for MT6797: "mm", "mfg", "vdec" Required clocks for MT7622 or MT7629: "hif_sel" - Required clocks for MT7622A: "ethif" + Required clocks for MT7623A: "ethif" Required clocks for MT8173: "mm", "mfg", "venc", "venc_lt" Optional properties: -- cgit v1.2.3 From 6aae57b788132d2bbb4d58ad0aa2f324eac3a7d4 Mon Sep 17 00:00:00 2001 From: Artur Rojek Date: Sun, 14 Apr 2019 14:40:38 +0200 Subject: dt-bindings: power: supply: Add charge-status-gpios property Add documentation for the "charge-status-gpios" property. Update the "gpios" property with a valid example. Signed-off-by: Artur Rojek Reviewed-by: Rob Herring Signed-off-by: Sebastian Reichel --- Documentation/devicetree/bindings/power/supply/gpio-charger.txt | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/power/supply/gpio-charger.txt b/Documentation/devicetree/bindings/power/supply/gpio-charger.txt index ddf7b7b971e1..0fb33b2c62a6 100644 --- a/Documentation/devicetree/bindings/power/supply/gpio-charger.txt +++ b/Documentation/devicetree/bindings/power/supply/gpio-charger.txt @@ -14,12 +14,16 @@ Required properties : usb-cdp (USB charging downstream port) usb-aca (USB accessory charger adapter) +Optional properties: + - charge-status-gpios: GPIO indicating whether a battery is charging. + Example: usb_charger: charger { compatible = "gpio-charger"; charger-type = "usb-sdp"; - gpios = <&gpf0 2 0 0 0>; + gpios = <&gpd 28 GPIO_ACTIVE_LOW>; + charge-status-gpios = <&gpc 27 GPIO_ACTIVE_LOW>; }; battery { -- cgit v1.2.3 From 55d76e83a39d2cba7ed686327498efb386b7e8f7 Mon Sep 17 00:00:00 2001 From: Neil Armstrong Date: Wed, 13 Mar 2019 15:10:30 +0100 Subject: dt-bindings: power: amlogic, meson-gx-pwrc: Add G12A compatible The Amlogic G12A has a slighly different Power Control, but uses the same address space and sysctrl registers. Signed-off-by: Neil Armstrong Reviewed-by: Rob Herring Signed-off-by: Kevin Hilman --- Documentation/devicetree/bindings/power/amlogic,meson-gx-pwrc.txt | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/power/amlogic,meson-gx-pwrc.txt b/Documentation/devicetree/bindings/power/amlogic,meson-gx-pwrc.txt index 1cd050b4054c..0fdc3dd1125e 100644 --- a/Documentation/devicetree/bindings/power/amlogic,meson-gx-pwrc.txt +++ b/Documentation/devicetree/bindings/power/amlogic,meson-gx-pwrc.txt @@ -16,7 +16,9 @@ Device Tree Bindings: --------------------- Required properties: -- compatible: should be "amlogic,meson-gx-pwrc-vpu" for the Meson GX SoCs +- compatible: should be one of the following : + - "amlogic,meson-gx-pwrc-vpu" for the Meson GX SoCs + - "amlogic,meson-g12a-pwrc-vpu" for the Meson G12A SoCs - #power-domain-cells: should be 0 - amlogic,hhi-sysctrl: phandle to the HHI sysctrl node - resets: phandles to the reset lines needed for this power demain sequence -- cgit v1.2.3 From 5ad4d7ca2125e7056a959b12e3b75fb745c73b52 Mon Sep 17 00:00:00 2001 From: Charles Keepax Date: Thu, 28 Mar 2019 13:09:36 +0000 Subject: hwmon: lochnagar: Add device tree binding document Lochnagar is an evaluation and development board for Cirrus Logic Smart CODEC and Amp devices. It allows the connection of most Cirrus Logic devices on mini-cards, as well as allowing connection of various application processor systems to provide a full evaluation platform. This driver supports the board controller chip on the Lochnagar board. Signed-off-by: Charles Keepax Reviewed-by: Rob Herring Signed-off-by: Guenter Roeck --- .../devicetree/bindings/hwmon/cirrus,lochnagar.txt | 26 ++++++++++++++++++++++ 1 file changed, 26 insertions(+) create mode 100644 Documentation/devicetree/bindings/hwmon/cirrus,lochnagar.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/hwmon/cirrus,lochnagar.txt b/Documentation/devicetree/bindings/hwmon/cirrus,lochnagar.txt new file mode 100644 index 000000000000..ffb79ccf51ee --- /dev/null +++ b/Documentation/devicetree/bindings/hwmon/cirrus,lochnagar.txt @@ -0,0 +1,26 @@ +Cirrus Logic Lochnagar Audio Development Board + +Lochnagar is an evaluation and development board for Cirrus Logic +Smart CODEC and Amp devices. It allows the connection of most Cirrus +Logic devices on mini-cards, as well as allowing connection of +various application processor systems to provide a full evaluation +platform. Audio system topology, clocking and power can all be +controlled through the Lochnagar, allowing the device under test +to be used in a variety of possible use cases. + +This binding document describes the binding for the hardware monitor +portion of the driver. + +This binding must be part of the Lochnagar MFD binding: + [4] ../mfd/cirrus,lochnagar.txt + +Required properties: + + - compatible : One of the following strings: + "cirrus,lochnagar2-hwmon" + +Example: + +lochnagar-hwmon { + compatible = "cirrus,lochnagar2-hwmon"; +}; -- cgit v1.2.3 From 4cdb562147467b3530e86c7c51c3fbffe3067c09 Mon Sep 17 00:00:00 2001 From: Lucas Tanure Date: Thu, 28 Mar 2019 13:09:37 +0000 Subject: hwmon: lochnagar: Add Lochnagar 2 hardware monitoring driver Lochnagar is an evaluation and development board for Cirrus Logic Smart CODEC and Amp devices. It allows the connection of most Cirrus Logic devices on mini-cards, as well as allowing connection of various application processor systems to provide a full evaluation platform. This driver adds support for the hardware monitoring features of the Lochnagar 2 to the hwmon API. Monitoring is provided for the board voltages, currents and temperature supported by the board controller chip. Signed-off-by: Lucas Tanure Signed-off-by: Charles Keepax Signed-off-by: Guenter Roeck --- Documentation/hwmon/lochnagar | 80 ++++++++ MAINTAINERS | 3 + drivers/hwmon/Kconfig | 10 + drivers/hwmon/Makefile | 1 + drivers/hwmon/lochnagar-hwmon.c | 412 ++++++++++++++++++++++++++++++++++++++++ 5 files changed, 506 insertions(+) create mode 100644 Documentation/hwmon/lochnagar create mode 100644 drivers/hwmon/lochnagar-hwmon.c (limited to 'Documentation') diff --git a/Documentation/hwmon/lochnagar b/Documentation/hwmon/lochnagar new file mode 100644 index 000000000000..e9686fb3eb40 --- /dev/null +++ b/Documentation/hwmon/lochnagar @@ -0,0 +1,80 @@ +Kernel Driver Lochnagar +======================== + +Supported systems: + * Cirrus Logic : Lochnagar 2 + +Author: Lucas A. Tanure Alves + +Description +----------- + +Lochnagar 2 features built-in Current Monitor circuitry that allows for the +measurement of both voltage and current on up to eight of the supply voltage +rails provided to the minicards. The Current Monitor does not require any +hardware modifications or external circuitry to operate. + +The current and voltage measurements are obtained through the standard register +map interface to the Lochnagar board controller, and can therefore be monitored +by software. + +Sysfs attributes +---------------- + +temp1_input The Lochnagar board temperature (milliCelsius) +in0_input Measured voltage for DBVDD1 (milliVolts) +in0_label "DBVDD1" +curr1_input Measured current for DBVDD1 (milliAmps) +curr1_label "DBVDD1" +power1_average Measured average power for DBVDD1 (microWatts) +power1_average_interval Power averaging time input valid from 1 to 1708mS +power1_label "DBVDD1" +in1_input Measured voltage for 1V8 DSP (milliVolts) +in1_label "1V8 DSP" +curr2_input Measured current for 1V8 DSP (milliAmps) +curr2_label "1V8 DSP" +power2_average Measured average power for 1V8 DSP (microWatts) +power2_average_interval Power averaging time input valid from 1 to 1708mS +power2_label "1V8 DSP" +in2_input Measured voltage for 1V8 CDC (milliVolts) +in2_label "1V8 CDC" +curr3_input Measured current for 1V8 CDC (milliAmps) +curr3_label "1V8 CDC" +power3_average Measured average power for 1V8 CDC (microWatts) +power3_average_interval Power averaging time input valid from 1 to 1708mS +power3_label "1V8 CDC" +in3_input Measured voltage for VDDCORE DSP (milliVolts) +in3_label "VDDCORE DSP" +curr4_input Measured current for VDDCORE DSP (milliAmps) +curr4_label "VDDCORE DSP" +power4_average Measured average power for VDDCORE DSP (microWatts) +power4_average_interval Power averaging time input valid from 1 to 1708mS +power4_label "VDDCORE DSP" +in4_input Measured voltage for AVDD 1V8 (milliVolts) +in4_label "AVDD 1V8" +curr5_input Measured current for AVDD 1V8 (milliAmps) +curr5_label "AVDD 1V8" +power5_average Measured average power for AVDD 1V8 (microWatts) +power5_average_interval Power averaging time input valid from 1 to 1708mS +power5_label "AVDD 1V8" +curr6_input Measured current for SYSVDD (milliAmps) +curr6_label "SYSVDD" +power6_average Measured average power for SYSVDD (microWatts) +power6_average_interval Power averaging time input valid from 1 to 1708mS +power6_label "SYSVDD" +in6_input Measured voltage for VDDCORE CDC (milliVolts) +in6_label "VDDCORE CDC" +curr7_input Measured current for VDDCORE CDC (milliAmps) +curr7_label "VDDCORE CDC" +power7_average Measured average power for VDDCORE CDC (microWatts) +power7_average_interval Power averaging time input valid from 1 to 1708mS +power7_label "VDDCORE CDC" +in7_input Measured voltage for MICVDD (milliVolts) +in7_label "MICVDD" +curr8_input Measured current for MICVDD (milliAmps) +curr8_label "MICVDD" +power8_average Measured average power for MICVDD (microWatts) +power8_average_interval Power averaging time input valid from 1 to 1708mS +power8_label "MICVDD" + +Note: It is not possible to measure voltage on the SYSVDD rail. diff --git a/MAINTAINERS b/MAINTAINERS index 2359e12e4c41..cfd9884256af 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -3797,6 +3797,7 @@ M: Richard Fitzgerald L: patches@opensource.cirrus.com S: Supported F: drivers/clk/clk-lochnagar.c +F: drivers/hwmon/lochnagar-hwmon.c F: drivers/mfd/lochnagar-i2c.c F: drivers/pinctrl/cirrus/pinctrl-lochnagar.c F: drivers/regulator/lochnagar-regulator.c @@ -3805,8 +3806,10 @@ F: include/dt-bindings/pinctrl/lochnagar.h F: include/linux/mfd/lochnagar* F: Documentation/devicetree/bindings/mfd/cirrus,lochnagar.txt F: Documentation/devicetree/bindings/clock/cirrus,lochnagar.txt +F: Documentation/devicetree/bindings/hwmon/cirrus,lochnagar.txt F: Documentation/devicetree/bindings/pinctrl/cirrus,lochnagar.txt F: Documentation/devicetree/bindings/regulator/cirrus,lochnagar.txt +F: Documentation/hwmon/lochnagar CISCO FCOE HBA DRIVER M: Satish Kharat diff --git a/drivers/hwmon/Kconfig b/drivers/hwmon/Kconfig index d0f1dfe2bcbb..dedd5febd3aa 100644 --- a/drivers/hwmon/Kconfig +++ b/drivers/hwmon/Kconfig @@ -705,6 +705,16 @@ config SENSORS_LINEAGE This driver can also be built as a module. If so, the module will be called lineage-pem. +config SENSORS_LOCHNAGAR + tristate "Lochnagar Hardware Monitor" + depends on MFD_LOCHNAGAR + help + If you say yes here you get support for Lochnagar 2 temperature, + voltage and current sensors abilities. + + This driver can also be built as a module. If so, the module + will be called lochnagar-hwmon. + config SENSORS_LTC2945 tristate "Linear Technology LTC2945" depends on I2C diff --git a/drivers/hwmon/Makefile b/drivers/hwmon/Makefile index f5c7b442e69e..8db472ea04f0 100644 --- a/drivers/hwmon/Makefile +++ b/drivers/hwmon/Makefile @@ -89,6 +89,7 @@ obj-$(CONFIG_SENSORS_JZ4740) += jz4740-hwmon.o obj-$(CONFIG_SENSORS_K8TEMP) += k8temp.o obj-$(CONFIG_SENSORS_K10TEMP) += k10temp.o obj-$(CONFIG_SENSORS_LINEAGE) += lineage-pem.o +obj-$(CONFIG_SENSORS_LOCHNAGAR) += lochnagar-hwmon.o obj-$(CONFIG_SENSORS_LM63) += lm63.o obj-$(CONFIG_SENSORS_LM70) += lm70.o obj-$(CONFIG_SENSORS_LM73) += lm73.o diff --git a/drivers/hwmon/lochnagar-hwmon.c b/drivers/hwmon/lochnagar-hwmon.c new file mode 100644 index 000000000000..8b19adf2eeb0 --- /dev/null +++ b/drivers/hwmon/lochnagar-hwmon.c @@ -0,0 +1,412 @@ +// SPDX-License-Identifier: GPL-2.0 +/* + * Lochnagar hardware monitoring features + * + * Copyright (c) 2016-2019 Cirrus Logic, Inc. and + * Cirrus Logic International Semiconductor Ltd. + * + * Author: Lucas Tanure + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#define LN2_MAX_NSAMPLE 1023 +#define LN2_SAMPLE_US 1670 + +#define LN2_CURR_UNITS 1000 +#define LN2_VOLT_UNITS 1000 +#define LN2_TEMP_UNITS 1000 +#define LN2_PWR_UNITS 1000000 + +static const char * const lochnagar_chan_names[] = { + "DBVDD1", + "1V8 DSP", + "1V8 CDC", + "VDDCORE DSP", + "AVDD 1V8", + "SYSVDD", + "VDDCORE CDC", + "MICVDD", +}; + +struct lochnagar_hwmon { + struct regmap *regmap; + + long power_nsamples[ARRAY_SIZE(lochnagar_chan_names)]; + + /* Lock to ensure only a single sensor is read at a time */ + struct mutex sensor_lock; +}; + +enum lochnagar_measure_mode { + LN2_CURR = 0, + LN2_VOLT, + LN2_TEMP, +}; + +/** + * float_to_long - Convert ieee754 reading from hardware to an integer + * + * @data: Value read from the hardware + * @precision: Units to multiply up to eg. 1000 = milli, 1000000 = micro + * + * Return: Converted integer reading + * + * Depending on the measurement type the hardware returns an ieee754 + * floating point value in either volts, amps or celsius. This function + * will convert that into an integer in a smaller unit such as micro-amps + * or milli-celsius. The hardware does not return NaN, so consideration of + * that is not required. + */ +static long float_to_long(u32 data, u32 precision) +{ + u64 man = data & 0x007FFFFF; + int exp = ((data & 0x7F800000) >> 23) - 127 - 23; + bool negative = data & 0x80000000; + long result; + + man = (man + (1 << 23)) * precision; + + if (fls64(man) + exp > (int)sizeof(long) * 8 - 1) + result = LONG_MAX; + else if (exp < 0) + result = (man + (1ull << (-exp - 1))) >> -exp; + else + result = man << exp; + + return negative ? -result : result; +} + +static int do_measurement(struct regmap *regmap, int chan, + enum lochnagar_measure_mode mode, int nsamples) +{ + unsigned int val; + int ret; + + chan = 1 << (chan + LOCHNAGAR2_IMON_MEASURED_CHANNELS_SHIFT); + + ret = regmap_write(regmap, LOCHNAGAR2_IMON_CTRL1, + LOCHNAGAR2_IMON_ENA_MASK | chan | mode); + if (ret < 0) + return ret; + + ret = regmap_write(regmap, LOCHNAGAR2_IMON_CTRL2, nsamples); + if (ret < 0) + return ret; + + ret = regmap_write(regmap, LOCHNAGAR2_IMON_CTRL3, + LOCHNAGAR2_IMON_CONFIGURE_MASK); + if (ret < 0) + return ret; + + ret = regmap_read_poll_timeout(regmap, LOCHNAGAR2_IMON_CTRL3, val, + val & LOCHNAGAR2_IMON_DONE_MASK, + 1000, 10000); + if (ret < 0) + return ret; + + ret = regmap_write(regmap, LOCHNAGAR2_IMON_CTRL3, + LOCHNAGAR2_IMON_MEASURE_MASK); + if (ret < 0) + return ret; + + /* + * Actual measurement time is ~1.67mS per sample, approximate this + * with a 1.5mS per sample msleep and then poll for success up to + * ~0.17mS * 1023 (LN2_MAX_NSAMPLES). Normally for smaller values + * of nsamples the poll will complete on the first loop due to + * other latency in the system. + */ + msleep((nsamples * 3) / 2); + + ret = regmap_read_poll_timeout(regmap, LOCHNAGAR2_IMON_CTRL3, val, + val & LOCHNAGAR2_IMON_DONE_MASK, + 5000, 200000); + if (ret < 0) + return ret; + + return regmap_write(regmap, LOCHNAGAR2_IMON_CTRL3, 0); +} + +static int request_data(struct regmap *regmap, int chan, u32 *data) +{ + unsigned int val; + int ret; + + ret = regmap_write(regmap, LOCHNAGAR2_IMON_CTRL4, + LOCHNAGAR2_IMON_DATA_REQ_MASK | + chan << LOCHNAGAR2_IMON_CH_SEL_SHIFT); + if (ret < 0) + return ret; + + ret = regmap_read_poll_timeout(regmap, LOCHNAGAR2_IMON_CTRL4, val, + val & LOCHNAGAR2_IMON_DATA_RDY_MASK, + 1000, 10000); + if (ret < 0) + return ret; + + ret = regmap_read(regmap, LOCHNAGAR2_IMON_DATA1, &val); + if (ret < 0) + return ret; + + *data = val << 16; + + ret = regmap_read(regmap, LOCHNAGAR2_IMON_DATA2, &val); + if (ret < 0) + return ret; + + *data |= val; + + return regmap_write(regmap, LOCHNAGAR2_IMON_CTRL4, 0); +} + +static int read_sensor(struct device *dev, int chan, + enum lochnagar_measure_mode mode, int nsamples, + unsigned int precision, long *val) +{ + struct lochnagar_hwmon *priv = dev_get_drvdata(dev); + struct regmap *regmap = priv->regmap; + u32 data; + int ret; + + mutex_lock(&priv->sensor_lock); + + ret = do_measurement(regmap, chan, mode, nsamples); + if (ret < 0) { + dev_err(dev, "Failed to perform measurement: %d\n", ret); + goto error; + } + + ret = request_data(regmap, chan, &data); + if (ret < 0) { + dev_err(dev, "Failed to read measurement: %d\n", ret); + goto error; + } + + *val = float_to_long(data, precision); + +error: + mutex_unlock(&priv->sensor_lock); + + return ret; +} + +static int read_power(struct device *dev, int chan, long *val) +{ + struct lochnagar_hwmon *priv = dev_get_drvdata(dev); + int nsamples = priv->power_nsamples[chan]; + u64 power; + int ret; + + if (!strcmp("SYSVDD", lochnagar_chan_names[chan])) { + power = 5 * LN2_PWR_UNITS; + } else { + ret = read_sensor(dev, chan, LN2_VOLT, 1, LN2_PWR_UNITS, val); + if (ret < 0) + return ret; + + power = abs(*val); + } + + ret = read_sensor(dev, chan, LN2_CURR, nsamples, LN2_PWR_UNITS, val); + if (ret < 0) + return ret; + + power *= abs(*val); + power = DIV_ROUND_CLOSEST_ULL(power, LN2_PWR_UNITS); + + if (power > LONG_MAX) + *val = LONG_MAX; + else + *val = power; + + return 0; +} + +static umode_t lochnagar_is_visible(const void *drvdata, + enum hwmon_sensor_types type, + u32 attr, int chan) +{ + switch (type) { + case hwmon_in: + if (!strcmp("SYSVDD", lochnagar_chan_names[chan])) + return 0; + break; + case hwmon_power: + if (attr == hwmon_power_average_interval) + return 0644; + break; + default: + break; + } + + return 0444; +} + +static int lochnagar_read(struct device *dev, enum hwmon_sensor_types type, + u32 attr, int chan, long *val) +{ + struct lochnagar_hwmon *priv = dev_get_drvdata(dev); + int interval; + + switch (type) { + case hwmon_in: + return read_sensor(dev, chan, LN2_VOLT, 1, LN2_VOLT_UNITS, val); + case hwmon_curr: + return read_sensor(dev, chan, LN2_CURR, 1, LN2_CURR_UNITS, val); + case hwmon_temp: + return read_sensor(dev, chan, LN2_TEMP, 1, LN2_TEMP_UNITS, val); + case hwmon_power: + switch (attr) { + case hwmon_power_average: + return read_power(dev, chan, val); + case hwmon_power_average_interval: + interval = priv->power_nsamples[chan] * LN2_SAMPLE_US; + *val = DIV_ROUND_CLOSEST(interval, 1000); + return 0; + default: + return -EOPNOTSUPP; + } + default: + return -EOPNOTSUPP; + } +} + +static int lochnagar_read_string(struct device *dev, + enum hwmon_sensor_types type, u32 attr, + int chan, const char **str) +{ + switch (type) { + case hwmon_in: + case hwmon_curr: + case hwmon_power: + *str = lochnagar_chan_names[chan]; + return 0; + default: + return -EOPNOTSUPP; + } +} + +static int lochnagar_write(struct device *dev, enum hwmon_sensor_types type, + u32 attr, int chan, long val) +{ + struct lochnagar_hwmon *priv = dev_get_drvdata(dev); + + if (type != hwmon_power || attr != hwmon_power_average_interval) + return -EOPNOTSUPP; + + val = clamp_t(long, val, 1, (LN2_MAX_NSAMPLE * LN2_SAMPLE_US) / 1000); + val = DIV_ROUND_CLOSEST(val * 1000, LN2_SAMPLE_US); + + priv->power_nsamples[chan] = val; + + return 0; +} + +static const struct hwmon_ops lochnagar_ops = { + .is_visible = lochnagar_is_visible, + .read = lochnagar_read, + .read_string = lochnagar_read_string, + .write = lochnagar_write, +}; + +static const struct hwmon_channel_info *lochnagar_info[] = { + HWMON_CHANNEL_INFO(temp, HWMON_T_INPUT), + HWMON_CHANNEL_INFO(in, HWMON_I_INPUT | HWMON_I_LABEL, + HWMON_I_INPUT | HWMON_I_LABEL, + HWMON_I_INPUT | HWMON_I_LABEL, + HWMON_I_INPUT | HWMON_I_LABEL, + HWMON_I_INPUT | HWMON_I_LABEL, + HWMON_I_INPUT | HWMON_I_LABEL, + HWMON_I_INPUT | HWMON_I_LABEL, + HWMON_I_INPUT | HWMON_I_LABEL), + HWMON_CHANNEL_INFO(curr, HWMON_C_INPUT | HWMON_C_LABEL, + HWMON_C_INPUT | HWMON_C_LABEL, + HWMON_C_INPUT | HWMON_C_LABEL, + HWMON_C_INPUT | HWMON_C_LABEL, + HWMON_C_INPUT | HWMON_C_LABEL, + HWMON_C_INPUT | HWMON_C_LABEL, + HWMON_C_INPUT | HWMON_C_LABEL, + HWMON_C_INPUT | HWMON_C_LABEL), + HWMON_CHANNEL_INFO(power, HWMON_P_AVERAGE | HWMON_P_AVERAGE_INTERVAL | + HWMON_P_LABEL, + HWMON_P_AVERAGE | HWMON_P_AVERAGE_INTERVAL | + HWMON_P_LABEL, + HWMON_P_AVERAGE | HWMON_P_AVERAGE_INTERVAL | + HWMON_P_LABEL, + HWMON_P_AVERAGE | HWMON_P_AVERAGE_INTERVAL | + HWMON_P_LABEL, + HWMON_P_AVERAGE | HWMON_P_AVERAGE_INTERVAL | + HWMON_P_LABEL, + HWMON_P_AVERAGE | HWMON_P_AVERAGE_INTERVAL | + HWMON_P_LABEL, + HWMON_P_AVERAGE | HWMON_P_AVERAGE_INTERVAL | + HWMON_P_LABEL, + HWMON_P_AVERAGE | HWMON_P_AVERAGE_INTERVAL | + HWMON_P_LABEL), + NULL +}; + +static const struct hwmon_chip_info lochnagar_chip_info = { + .ops = &lochnagar_ops, + .info = lochnagar_info, +}; + +static const struct of_device_id lochnagar_of_match[] = { + { .compatible = "cirrus,lochnagar2-hwmon" }, + {} +}; +MODULE_DEVICE_TABLE(of, lochnagar_of_match); + +static int lochnagar_hwmon_probe(struct platform_device *pdev) +{ + struct device *dev = &pdev->dev; + struct device *hwmon_dev; + struct lochnagar_hwmon *priv; + int i; + + priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL); + if (!priv) + return -ENOMEM; + + mutex_init(&priv->sensor_lock); + + priv->regmap = dev_get_regmap(dev->parent, NULL); + if (!priv->regmap) { + dev_err(dev, "No register map found\n"); + return -EINVAL; + } + + for (i = 0; i < ARRAY_SIZE(priv->power_nsamples); i++) + priv->power_nsamples[i] = 96; + + hwmon_dev = devm_hwmon_device_register_with_info(dev, "Lochnagar", priv, + &lochnagar_chip_info, + NULL); + + return PTR_ERR_OR_ZERO(hwmon_dev); +} + +static struct platform_driver lochnagar_hwmon_driver = { + .driver = { + .name = "lochnagar-hwmon", + .of_match_table = lochnagar_of_match, + }, + .probe = lochnagar_hwmon_probe, +}; +module_platform_driver(lochnagar_hwmon_driver); + +MODULE_AUTHOR("Lucas Tanure "); +MODULE_DESCRIPTION("Lochnagar hardware monitoring features"); +MODULE_LICENSE("GPL"); -- cgit v1.2.3 From 6bf2db4621fc1ac7a00bb7b770462211a5b7fdf9 Mon Sep 17 00:00:00 2001 From: Guenter Roeck Date: Sun, 31 Mar 2019 10:22:24 -0700 Subject: hwmon: Documentation: Add usage example for HWMON_CHANNEL_INFO The new HWMON_CHANNEL_INFO macro simplifies the code, reduces the likelihood of errors, and makes the code easier to read. Add a usage example to help driver writers to actually use it. Signed-off-by: Guenter Roeck --- Documentation/hwmon/hwmon-kernel-api.txt | 13 +++++++++++++ 1 file changed, 13 insertions(+) (limited to 'Documentation') diff --git a/Documentation/hwmon/hwmon-kernel-api.txt b/Documentation/hwmon/hwmon-kernel-api.txt index 8bdefb41be30..f8e2ab5c21b9 100644 --- a/Documentation/hwmon/hwmon-kernel-api.txt +++ b/Documentation/hwmon/hwmon-kernel-api.txt @@ -207,6 +207,19 @@ static const struct hwmon_channel_info *lm75_info[] = { NULL }; +The HWMON_CHANNEL_INFO() macro can and should be used when possible. +With this macro, the above example can be simplified to + +static const struct hwmon_channel_info *lm75_info[] = { + HWMON_CHANNEL_INFO(chip, + HWMON_C_REGISTER_TZ | HWMON_C_UPDATE_INTERVAL), + HWMON_CHANNEL_INFO(temp, + HWMON_T_INPUT | HWMON_T_MAX | HWMON_T_MAX_HYST), + NULL +}; + +The remaining declarations are as follows. + static const struct hwmon_ops lm75_hwmon_ops = { .is_visible = lm75_is_visible, .read = lm75_read, -- cgit v1.2.3 From c7366e951469b542fa16ca94ac6d09ac2206d11a Mon Sep 17 00:00:00 2001 From: Stefan Wahren Date: Thu, 11 Apr 2019 15:30:09 +0200 Subject: dt-bindings: hwmon: (pwm-fan) Add tachometer interrupt This adds the tachometer interrupt to the pwm-fan binding, which is necessary for RPM support. Signed-off-by: Stefan Wahren Reviewed-by: Rob Herring Reviewed-by: Robin Murphy Signed-off-by: Guenter Roeck --- Documentation/devicetree/bindings/hwmon/pwm-fan.txt | 21 ++++++++++++++++++++- 1 file changed, 20 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/hwmon/pwm-fan.txt b/Documentation/devicetree/bindings/hwmon/pwm-fan.txt index 49ca5d83ed13..6ced829b0e58 100644 --- a/Documentation/devicetree/bindings/hwmon/pwm-fan.txt +++ b/Documentation/devicetree/bindings/hwmon/pwm-fan.txt @@ -7,7 +7,16 @@ Required properties: which correspond to thermal cooling states Optional properties: -- fan-supply : phandle to the regulator that provides power to the fan +- fan-supply : phandle to the regulator that provides power to the fan +- interrupts : This contains a single interrupt specifier which + describes the tachometer output of the fan as an + interrupt source. The output signal must generate a + defined number of interrupts per fan revolution, which + require that it must be self resetting edge interrupts. + See interrupt-controller/interrupts.txt for the format. +- pulses-per-revolution : define the tachometer pulses per fan revolution as + an integer (default is 2 interrupts per revolution). + The value must be greater than zero. Example: fan0: pwm-fan { @@ -38,3 +47,13 @@ Example: }; }; }; + +Example 2: + fan0: pwm-fan { + compatible = "pwm-fan"; + pwms = <&pwm 0 40000 0>; + fan-supply = <®_fan>; + interrupt-parent = <&gpio5>; + interrupts = <1 IRQ_TYPE_EDGE_FALLING>; + pulses-per-revolution = <2>; + }; -- cgit v1.2.3 From 285d7483aa3323c90891e26b73a0c9d9cc5f53e4 Mon Sep 17 00:00:00 2001 From: Stefan Wahren Date: Thu, 11 Apr 2019 15:30:10 +0200 Subject: Documentation: pwm-fan: Add description for RPM support This adds a short description for the new RPM support of the pwm-fan driver. Signed-off-by: Stefan Wahren Reviewed-by: Robin Murphy Signed-off-by: Guenter Roeck --- Documentation/hwmon/pwm-fan | 3 +++ 1 file changed, 3 insertions(+) (limited to 'Documentation') diff --git a/Documentation/hwmon/pwm-fan b/Documentation/hwmon/pwm-fan index 18529d2e3bcf..82fe96742fee 100644 --- a/Documentation/hwmon/pwm-fan +++ b/Documentation/hwmon/pwm-fan @@ -15,3 +15,6 @@ The driver implements a simple interface for driving a fan connected to a PWM output. It uses the generic PWM interface, thus it can be used with a range of SoCs. The driver exposes the fan to the user space through the hwmon's sysfs interface. + +The fan rotation speed returned via the optional 'fan1_input' is extrapolated +from the sampled interrupts from the tachometer signal within 1 second. -- cgit v1.2.3 From c49b7b3981f5c39b9b50dc65e32d3c6a553825de Mon Sep 17 00:00:00 2001 From: Patrick Venture Date: Fri, 12 Apr 2019 09:27:42 -0700 Subject: hwmon: (ir35221) fix company name Fix the company name from "Infinion" to "Infineon." Signed-off-by: Patrick Venture Signed-off-by: Guenter Roeck --- Documentation/hwmon/ir35221 | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/hwmon/ir35221 b/Documentation/hwmon/ir35221 index f7e112752c04..3e82f3d93f44 100644 --- a/Documentation/hwmon/ir35221 +++ b/Documentation/hwmon/ir35221 @@ -2,7 +2,7 @@ Kernel driver ir35221 ===================== Supported chips: - * Infinion IR35221 + * Infineon IR35221 Prefix: 'ir35221' Addresses scanned: - Datasheet: Datasheet is not publicly available. -- cgit v1.2.3 From 00669d196c616c0a9970a3a9ee66efab6868df0c Mon Sep 17 00:00:00 2001 From: Maxim Sloyko Date: Fri, 12 Apr 2019 13:37:56 -0700 Subject: hwmon: (pmbus/ir38064) Add driver for Infineon IR38064 Voltage Regulator Add the pmbus driver for the Infineon ir38064 voltage regulator. VOUT_MODE is not supported by the device. The driver fakes linear16 mode with exponent value -8. The device supports VOUT_PEAK, IOUT_PEAK, and TEMPERATURE_PEAK, however this driver does not enable them. Signed-off-by: Maxim Sloyko Signed-off-by: Patrick Venture Signed-off-by: Guenter Roeck --- Documentation/hwmon/ir38064 | 64 ++++++++++++++++++++++++++++++++++++++++++ drivers/hwmon/pmbus/Kconfig | 9 ++++++ drivers/hwmon/pmbus/Makefile | 1 + drivers/hwmon/pmbus/ir38064.c | 65 +++++++++++++++++++++++++++++++++++++++++++ 4 files changed, 139 insertions(+) create mode 100644 Documentation/hwmon/ir38064 create mode 100644 drivers/hwmon/pmbus/ir38064.c (limited to 'Documentation') diff --git a/Documentation/hwmon/ir38064 b/Documentation/hwmon/ir38064 new file mode 100644 index 000000000000..c3697d7aaaa4 --- /dev/null +++ b/Documentation/hwmon/ir38064 @@ -0,0 +1,64 @@ +Kernel driver ir38064 +===================== + +Supported chips: + * Infineon IR38064 + Prefix: 'ir38064' + Addresses scanned: - + Datasheet: Publicly available at the Infineon webiste + https://www.infineon.com/dgdl/Infineon-IR38064MTRPBF-DS-v03_07-EN.pdf?fileId=5546d462584d1d4a0158db0d9efb67ca + +Datasheet is not publicly available. + + +Authors: + Maxim Sloyko + Patrick Venture + +Description +----------- + +IR38064 is a Single-input Voltage, Synchronous Buck Regulator, DC-DC Converter. + +Usage Notes +----------- + +This driver does not probe for PMBus devices. You will have to instantiate +devices explicitly. + +Sysfs attributes +---------------- + +curr1_label "iout1" +curr1_input Measured output current +curr1_crit Critical maximum current +curr1_crit_alarm Current critical high alarm +curr1_max Maximum current +curr1_max_alarm Current high alarm + +in1_label "vin" +in1_input Measured input voltage +in1_crit Critical maximum input voltage +in1_crit_alarm Input voltage critical high alarm +in1_min Minimum input voltage +in1_min_alarm Input voltage low alarm + +in2_label "vout1" +in2_input Measured output voltage +in2_lcrit Critical minimum output voltage +in2_lcrit_alarm Output voltage critical low alarm +in2_crit Critical maximum output voltage +in2_crit_alarm Output voltage critical high alarm +in2_max Maximum output voltage +in2_max_alarm Output voltage high alarm +in2_min Minimum output voltage +in2_min_alarm Output voltage low alarm + +power1_label "pout1" +power1_input Measured output power + +temp1_input Measured temperature +temp1_crit Critical high temperature +temp1_crit_alarm Chip temperature critical high alarm +temp1_max Maximum temperature +temp1_max_alarm Chip temperature high alarm diff --git a/drivers/hwmon/pmbus/Kconfig b/drivers/hwmon/pmbus/Kconfig index 629cb45f8557..de87abab990e 100644 --- a/drivers/hwmon/pmbus/Kconfig +++ b/drivers/hwmon/pmbus/Kconfig @@ -54,6 +54,15 @@ config SENSORS_IR35221 This driver can also be built as a module. If so, the module will be called ir35521. +config SENSORS_IR38064 + tristate "Infineon IR38064" + help + If you say yes here you get hardware monitoring support for Infineon + IR38064. + + This driver can also be built as a module. If so, the module will + be called ir38064. + config SENSORS_LM25066 tristate "National Semiconductor LM25066 and compatibles" help diff --git a/drivers/hwmon/pmbus/Makefile b/drivers/hwmon/pmbus/Makefile index ea0e39518c21..7d1fa6b3c8c9 100644 --- a/drivers/hwmon/pmbus/Makefile +++ b/drivers/hwmon/pmbus/Makefile @@ -8,6 +8,7 @@ obj-$(CONFIG_SENSORS_PMBUS) += pmbus.o obj-$(CONFIG_SENSORS_ADM1275) += adm1275.o obj-$(CONFIG_SENSORS_IBM_CFFPS) += ibm-cffps.o obj-$(CONFIG_SENSORS_IR35221) += ir35221.o +obj-$(CONFIG_SENSORS_IR38064) += ir38064.o obj-$(CONFIG_SENSORS_LM25066) += lm25066.o obj-$(CONFIG_SENSORS_LTC2978) += ltc2978.o obj-$(CONFIG_SENSORS_LTC3815) += ltc3815.o diff --git a/drivers/hwmon/pmbus/ir38064.c b/drivers/hwmon/pmbus/ir38064.c new file mode 100644 index 000000000000..1820f5077f66 --- /dev/null +++ b/drivers/hwmon/pmbus/ir38064.c @@ -0,0 +1,65 @@ +// SPDX-License-Identifier: GPL-2.0+ +/* + * Hardware monitoring driver for Infineon IR38064 + * + * Copyright (c) 2017 Google Inc + * + * VOUT_MODE is not supported by the device. The driver fakes VOUT linear16 + * mode with exponent value -8 as direct mode with m=256/b=0/R=0. + * + * The device supports VOUT_PEAK, IOUT_PEAK, and TEMPERATURE_PEAK, however + * this driver does not currently support them. + */ + +#include +#include +#include +#include +#include +#include "pmbus.h" + +static struct pmbus_driver_info ir38064_info = { + .pages = 1, + .format[PSC_VOLTAGE_IN] = linear, + .format[PSC_VOLTAGE_OUT] = direct, + .format[PSC_CURRENT_OUT] = linear, + .format[PSC_POWER] = linear, + .format[PSC_TEMPERATURE] = linear, + .m[PSC_VOLTAGE_OUT] = 256, + .b[PSC_VOLTAGE_OUT] = 0, + .R[PSC_VOLTAGE_OUT] = 0, + .func[0] = PMBUS_HAVE_VIN | PMBUS_HAVE_STATUS_INPUT + | PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP + | PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT + | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT + | PMBUS_HAVE_POUT, +}; + +static int ir38064_probe(struct i2c_client *client, + const struct i2c_device_id *id) +{ + return pmbus_do_probe(client, id, &ir38064_info); +} + +static const struct i2c_device_id ir38064_id[] = { + {"ir38064", 0}, + {} +}; + +MODULE_DEVICE_TABLE(i2c, ir38064_id); + +/* This is the driver that will be inserted */ +static struct i2c_driver ir38064_driver = { + .driver = { + .name = "ir38064", + }, + .probe = ir38064_probe, + .remove = pmbus_do_remove, + .id_table = ir38064_id, +}; + +module_i2c_driver(ir38064_driver); + +MODULE_AUTHOR("Maxim Sloyko "); +MODULE_DESCRIPTION("PMBus driver for Infineon IR38064"); +MODULE_LICENSE("GPL"); -- cgit v1.2.3 From 8e742fc2e25ae6c2d2734a4656107ae745263794 Mon Sep 17 00:00:00 2001 From: Patrick Venture Date: Mon, 15 Apr 2019 07:17:28 -0700 Subject: hwmon: (ir38064) delete incorrect line Delete line indicating the datasheet was not publicly available. This line was originally present as a default during the write-up and was subsequently not removed once the datasheet was located. Signed-off-by: Patrick Venture Signed-off-by: Guenter Roeck --- Documentation/hwmon/ir38064 | 3 --- 1 file changed, 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/hwmon/ir38064 b/Documentation/hwmon/ir38064 index c3697d7aaaa4..9f218c39bfe6 100644 --- a/Documentation/hwmon/ir38064 +++ b/Documentation/hwmon/ir38064 @@ -8,9 +8,6 @@ Supported chips: Datasheet: Publicly available at the Infineon webiste https://www.infineon.com/dgdl/Infineon-IR38064MTRPBF-DS-v03_07-EN.pdf?fileId=5546d462584d1d4a0158db0d9efb67ca -Datasheet is not publicly available. - - Authors: Maxim Sloyko Patrick Venture -- cgit v1.2.3 From bfe033a048f7ce486e01f3ef5a7a24618088af44 Mon Sep 17 00:00:00 2001 From: "Adamski, Krzysztof (Nokia - PL/Wroclaw)" Date: Sun, 14 Apr 2019 21:58:40 +0000 Subject: hwmon: Document the samples attributes Document new ABI attributes: {in,power,curr,temp}_samples and samples. Signed-off-by: Krzysztof Adamski Signed-off-by: Guenter Roeck --- Documentation/hwmon/sysfs-interface | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) (limited to 'Documentation') diff --git a/Documentation/hwmon/sysfs-interface b/Documentation/hwmon/sysfs-interface index 2b9e1005d88b..7b91706d01c8 100644 --- a/Documentation/hwmon/sysfs-interface +++ b/Documentation/hwmon/sysfs-interface @@ -756,6 +756,24 @@ intrusion[0-*]_beep 1: enable RW +******************************** +* Average sample configuration * +******************************** + +Devices allowing for reading {in,power,curr,temp}_average values may export +attributes for controlling number of samples used to compute average. + +samples Sets number of average samples for all types of measurements. + RW + +in_samples +power_samples +curr_samples +temp_samples Sets number of average samples for specific type of measurements. + Note that on some devices it won't be possible to set all of them + to different values so changing one might also change some others. + RW + sysfs attribute writes interpretation ------------------------------------- -- cgit v1.2.3 From 038a9c3d1e42420943c60f879fdb00b62f207f9c Mon Sep 17 00:00:00 2001 From: Maxim Sloyko Date: Mon, 15 Apr 2019 15:28:07 -0700 Subject: hwmon: (pmbus/isl68137) Add driver for Intersil ISL68137 PWM Controller Intersil ISL68137 is a digital output 7-phase configurable PWM controller with an AVSBus interface. Signed-off-by: Maxim Sloyko Signed-off-by: Robert Lippert Signed-off-by: Patrick Venture Signed-off-by: Guenter Roeck --- Documentation/hwmon/isl68137 | 72 ++++++++++++++++++ drivers/hwmon/pmbus/Kconfig | 9 +++ drivers/hwmon/pmbus/Makefile | 1 + drivers/hwmon/pmbus/isl68137.c | 169 +++++++++++++++++++++++++++++++++++++++++ 4 files changed, 251 insertions(+) create mode 100644 Documentation/hwmon/isl68137 create mode 100644 drivers/hwmon/pmbus/isl68137.c (limited to 'Documentation') diff --git a/Documentation/hwmon/isl68137 b/Documentation/hwmon/isl68137 new file mode 100644 index 000000000000..92e5c5fc5b77 --- /dev/null +++ b/Documentation/hwmon/isl68137 @@ -0,0 +1,72 @@ +Kernel driver isl68137 +====================== + +Supported chips: + * Intersil ISL68137 + Prefix: 'isl68137' + Addresses scanned: - + Datasheet: Publicly available at the Intersil website + https://www.intersil.com/content/dam/Intersil/documents/isl6/isl68137.pdf + +Authors: + Maxim Sloyko + Robert Lippert + Patrick Venture + +Description +----------- + +Intersil ISL68137 is a digital output 7-phase configurable PWM +controller with an AVSBus interface. + +Usage Notes +----------- + +This driver does not probe for PMBus devices. You will have to instantiate +devices explicitly. + +The ISL68137 AVS operation mode must be enabled/disabled at runtime. + +Beyond the normal sysfs pmbus attributes, the driver exposes a control attribute. + +Additional Sysfs attributes +--------------------------- + +avs(0|1)_enable Controls the AVS state of each rail. + +curr1_label "iin" +curr1_input Measured input current +curr1_crit Critical maximum current +curr1_crit_alarm Current critical high alarm + +curr[2-3]_label "iout[1-2]" +curr[2-3]_input Measured output current +curr[2-3]_crit Critical maximum current +curr[2-3]_crit_alarm Current critical high alarm + +in1_label "vin" +in1_input Measured input voltage +in1_lcrit Critical minimum input voltage +in1_lcrit_alarm Input voltage critical low alarm +in1_crit Critical maximum input voltage +in1_crit_alarm Input voltage critical high alarm + +in[2-3]_label "vout[1-2]" +in[2-3]_input Measured output voltage +in[2-3]_lcrit Critical minimum output voltage +in[2-3]_lcrit_alarm Output voltage critical low alarm +in[2-3]_crit Critical maximum output voltage +in[2-3]_crit_alarm Output voltage critical high alarm + +power1_label "pin" +power1_input Measured input power +power1_alarm Input power high alarm + +power[2-3]_label "pout[1-2]" +power[2-3]_input Measured output power + +temp[1-3]_input Measured temperature +temp[1-3]_crit Critical high temperature +temp[1-3]_crit_alarm Chip temperature critical high alarm +temp[1-3]_max Maximum temperature +temp[1-3]_max_alarm Chip temperature high alarm diff --git a/drivers/hwmon/pmbus/Kconfig b/drivers/hwmon/pmbus/Kconfig index de87abab990e..7edab7e30eaf 100644 --- a/drivers/hwmon/pmbus/Kconfig +++ b/drivers/hwmon/pmbus/Kconfig @@ -63,6 +63,15 @@ config SENSORS_IR38064 This driver can also be built as a module. If so, the module will be called ir38064. +config SENSORS_ISL68137 + tristate "Intersil ISL68137" + help + If you say yes here you get hardware monitoring support for Intersil + ISL68137. + + This driver can also be built as a module. If so, the module will + be called isl68137. + config SENSORS_LM25066 tristate "National Semiconductor LM25066 and compatibles" help diff --git a/drivers/hwmon/pmbus/Makefile b/drivers/hwmon/pmbus/Makefile index 7d1fa6b3c8c9..2219b9300316 100644 --- a/drivers/hwmon/pmbus/Makefile +++ b/drivers/hwmon/pmbus/Makefile @@ -9,6 +9,7 @@ obj-$(CONFIG_SENSORS_ADM1275) += adm1275.o obj-$(CONFIG_SENSORS_IBM_CFFPS) += ibm-cffps.o obj-$(CONFIG_SENSORS_IR35221) += ir35221.o obj-$(CONFIG_SENSORS_IR38064) += ir38064.o +obj-$(CONFIG_SENSORS_ISL68137) += isl68137.o obj-$(CONFIG_SENSORS_LM25066) += lm25066.o obj-$(CONFIG_SENSORS_LTC2978) += ltc2978.o obj-$(CONFIG_SENSORS_LTC3815) += ltc3815.o diff --git a/drivers/hwmon/pmbus/isl68137.c b/drivers/hwmon/pmbus/isl68137.c new file mode 100644 index 000000000000..515596c92fe1 --- /dev/null +++ b/drivers/hwmon/pmbus/isl68137.c @@ -0,0 +1,169 @@ +// SPDX-License-Identifier: GPL-2.0+ +/* + * Hardware monitoring driver for Intersil ISL68137 + * + * Copyright (c) 2017 Google Inc + * + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include "pmbus.h" + +#define ISL68137_VOUT_AVS 0x30 + +static ssize_t isl68137_avs_enable_show_page(struct i2c_client *client, + int page, + char *buf) +{ + int val = pmbus_read_byte_data(client, page, PMBUS_OPERATION); + + return sprintf(buf, "%d\n", + (val & ISL68137_VOUT_AVS) == ISL68137_VOUT_AVS ? 1 : 0); +} + +static ssize_t isl68137_avs_enable_store_page(struct i2c_client *client, + int page, + const char *buf, size_t count) +{ + int rc, op_val; + bool result; + + rc = kstrtobool(buf, &result); + if (rc) + return rc; + + op_val = result ? ISL68137_VOUT_AVS : 0; + + /* + * Writes to VOUT setpoint over AVSBus will persist after the VRM is + * switched to PMBus control. Switching back to AVSBus control + * restores this persisted setpoint rather than re-initializing to + * PMBus VOUT_COMMAND. Writing VOUT_COMMAND first over PMBus before + * enabling AVS control is the workaround. + */ + if (op_val == ISL68137_VOUT_AVS) { + rc = pmbus_read_word_data(client, page, PMBUS_VOUT_COMMAND); + if (rc < 0) + return rc; + + rc = pmbus_write_word_data(client, page, PMBUS_VOUT_COMMAND, + rc); + if (rc < 0) + return rc; + } + + rc = pmbus_update_byte_data(client, page, PMBUS_OPERATION, + ISL68137_VOUT_AVS, op_val); + + return (rc < 0) ? rc : count; +} + +static ssize_t isl68137_avs_enable_show(struct device *dev, + struct device_attribute *devattr, + char *buf) +{ + struct i2c_client *client = to_i2c_client(dev->parent); + struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); + + return isl68137_avs_enable_show_page(client, attr->index, buf); +} + +static ssize_t isl68137_avs_enable_store(struct device *dev, + struct device_attribute *devattr, + const char *buf, size_t count) +{ + struct i2c_client *client = to_i2c_client(dev->parent); + struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); + + return isl68137_avs_enable_store_page(client, attr->index, buf, count); +} + +static SENSOR_DEVICE_ATTR_RW(avs0_enable, isl68137_avs_enable, 0); +static SENSOR_DEVICE_ATTR_RW(avs1_enable, isl68137_avs_enable, 1); + +static struct attribute *enable_attrs[] = { + &sensor_dev_attr_avs0_enable.dev_attr.attr, + &sensor_dev_attr_avs1_enable.dev_attr.attr, + NULL, +}; + +static const struct attribute_group enable_group = { + .attrs = enable_attrs, +}; + +static const struct attribute_group *attribute_groups[] = { + &enable_group, + NULL, +}; + +static struct pmbus_driver_info isl68137_info = { + .pages = 2, + .format[PSC_VOLTAGE_IN] = direct, + .format[PSC_VOLTAGE_OUT] = direct, + .format[PSC_CURRENT_IN] = direct, + .format[PSC_CURRENT_OUT] = direct, + .format[PSC_POWER] = direct, + .format[PSC_TEMPERATURE] = direct, + .m[PSC_VOLTAGE_IN] = 1, + .b[PSC_VOLTAGE_IN] = 0, + .R[PSC_VOLTAGE_IN] = 3, + .m[PSC_VOLTAGE_OUT] = 1, + .b[PSC_VOLTAGE_OUT] = 0, + .R[PSC_VOLTAGE_OUT] = 3, + .m[PSC_CURRENT_IN] = 1, + .b[PSC_CURRENT_IN] = 0, + .R[PSC_CURRENT_IN] = 2, + .m[PSC_CURRENT_OUT] = 1, + .b[PSC_CURRENT_OUT] = 0, + .R[PSC_CURRENT_OUT] = 1, + .m[PSC_POWER] = 1, + .b[PSC_POWER] = 0, + .R[PSC_POWER] = 0, + .m[PSC_TEMPERATURE] = 1, + .b[PSC_TEMPERATURE] = 0, + .R[PSC_TEMPERATURE] = 0, + .func[0] = PMBUS_HAVE_VIN | PMBUS_HAVE_IIN | PMBUS_HAVE_PIN + | PMBUS_HAVE_STATUS_INPUT | PMBUS_HAVE_TEMP | PMBUS_HAVE_TEMP2 + | PMBUS_HAVE_TEMP3 | PMBUS_HAVE_STATUS_TEMP + | PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT + | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT | PMBUS_HAVE_POUT, + .func[1] = PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT + | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT | PMBUS_HAVE_POUT, + .groups = attribute_groups, +}; + +static int isl68137_probe(struct i2c_client *client, + const struct i2c_device_id *id) +{ + return pmbus_do_probe(client, id, &isl68137_info); +} + +static const struct i2c_device_id isl68137_id[] = { + {"isl68137", 0}, + {} +}; + +MODULE_DEVICE_TABLE(i2c, isl68137_id); + +/* This is the driver that will be inserted */ +static struct i2c_driver isl68137_driver = { + .driver = { + .name = "isl68137", + }, + .probe = isl68137_probe, + .remove = pmbus_do_remove, + .id_table = isl68137_id, +}; + +module_i2c_driver(isl68137_driver); + +MODULE_AUTHOR("Maxim Sloyko "); +MODULE_DESCRIPTION("PMBus driver for Intersil ISL68137"); +MODULE_LICENSE("GPL"); -- cgit v1.2.3 From 89502a01979033a1c0c0c4d6d9aef07e59021005 Mon Sep 17 00:00:00 2001 From: Stephen Kitt Date: Mon, 15 Apr 2019 17:08:53 +0200 Subject: x86/mm: Fix the 56-bit addresses memory map in Documentation/x86/x86_64/mm.txt This fixes a PT typo, and the following 56-bit address-space addresses: * the hole extends from 0100000000000000 to feffffffffffffff * the KASAN shadow memory area stops at fffffbffffffffff (see kasan.h) Signed-off-by: Stephen Kitt Cc: Andy Lutomirski Cc: Borislav Petkov Cc: Brian Gerst Cc: Dave Hansen Cc: H. Peter Anvin Cc: Linus Torvalds Cc: Peter Zijlstra Cc: Rik van Riel Cc: Thomas Gleixner Cc: alex.popov@linux.com Cc: bhe@redhat.com Cc: corbet@lwn.net Cc: kirill.shutemov@linux.intel.com Cc: linux-doc@vger.kernel.org Link: http://lkml.kernel.org/r/20190415150853.10354-1-steve@sk2.org Signed-off-by: Ingo Molnar --- Documentation/x86/x86_64/mm.txt | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/x86/x86_64/mm.txt b/Documentation/x86/x86_64/mm.txt index 804f9426ed17..6cbe652d7a49 100644 --- a/Documentation/x86/x86_64/mm.txt +++ b/Documentation/x86/x86_64/mm.txt @@ -72,7 +72,7 @@ Complete virtual memory map with 5-level page tables Notes: - With 56-bit addresses, user-space memory gets expanded by a factor of 512x, - from 0.125 PB to 64 PB. All kernel mappings shift down to the -64 PT starting + from 0.125 PB to 64 PB. All kernel mappings shift down to the -64 PB starting offset and many of the regions expand to support the much larger physical memory supported. @@ -83,7 +83,7 @@ Notes: 0000000000000000 | 0 | 00ffffffffffffff | 64 PB | user-space virtual memory, different per mm __________________|____________|__________________|_________|___________________________________________________________ | | | | - 0000800000000000 | +64 PB | ffff7fffffffffff | ~16K PB | ... huge, still almost 64 bits wide hole of non-canonical + 0100000000000000 | +64 PB | feffffffffffffff | ~16K PB | ... huge, still almost 64 bits wide hole of non-canonical | | | | virtual memory addresses up to the -64 PB | | | | starting offset of kernel mappings. __________________|____________|__________________|_________|___________________________________________________________ @@ -99,7 +99,7 @@ ____________________________________________________________|___________________ ffd2000000000000 | -11.5 PB | ffd3ffffffffffff | 0.5 PB | ... unused hole ffd4000000000000 | -11 PB | ffd5ffffffffffff | 0.5 PB | virtual memory map (vmemmap_base) ffd6000000000000 | -10.5 PB | ffdeffffffffffff | 2.25 PB | ... unused hole - ffdf000000000000 | -8.25 PB | fffffdffffffffff | ~8 PB | KASAN shadow memory + ffdf000000000000 | -8.25 PB | fffffbffffffffff | ~8 PB | KASAN shadow memory __________________|____________|__________________|_________|____________________________________________________________ | | Identical layout to the 47-bit one from here on: -- cgit v1.2.3 From 7121f4c0304a8854cfa528d482444aff6b13b71f Mon Sep 17 00:00:00 2001 From: Fabien Parent Date: Sat, 23 Mar 2019 22:16:05 +0100 Subject: dt-bindings: wdog: mtk-wdt: add support for MT851 Add binding documentation of mtk-wdt for MT8516 SoC. Signed-off-by: Fabien Parent Acked-by: Guenter Roeck Acked-by: Rob Herring Signed-off-by: Matthias Brugger --- Documentation/devicetree/bindings/watchdog/mtk-wdt.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/watchdog/mtk-wdt.txt b/Documentation/devicetree/bindings/watchdog/mtk-wdt.txt index 8682d6a93e5b..fd380eb28df5 100644 --- a/Documentation/devicetree/bindings/watchdog/mtk-wdt.txt +++ b/Documentation/devicetree/bindings/watchdog/mtk-wdt.txt @@ -9,6 +9,7 @@ Required properties: "mediatek,mt7622-wdt", "mediatek,mt6589-wdt": for MT7622 "mediatek,mt7623-wdt", "mediatek,mt6589-wdt": for MT7623 "mediatek,mt7629-wdt", "mediatek,mt6589-wdt": for MT7629 + "mediatek,mt8516-wdt", "mediatek,mt6589-wdt": for MT8516 - reg : Specifies base physical address and size of the registers. -- cgit v1.2.3 From ef038a55dc06efeec2501479c038c0fb93d18e1d Mon Sep 17 00:00:00 2001 From: Fabien Parent Date: Sat, 23 Mar 2019 22:16:06 +0100 Subject: dt-bindings: timer: mtk-timer: add support for MT8516 Add binding documentation of mtk-timer for MT8516 SoC. Signed-off-by: Fabien Parent Acked-by: Rob Herring Acked-by: Daniel Lezcano Signed-off-by: Matthias Brugger --- Documentation/devicetree/bindings/timer/mediatek,mtk-timer.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/timer/mediatek,mtk-timer.txt b/Documentation/devicetree/bindings/timer/mediatek,mtk-timer.txt index ff7c567a7972..74c3eadad844 100644 --- a/Documentation/devicetree/bindings/timer/mediatek,mtk-timer.txt +++ b/Documentation/devicetree/bindings/timer/mediatek,mtk-timer.txt @@ -17,6 +17,7 @@ Required properties: * "mediatek,mt8127-timer" for MT8127 compatible timers (GPT) * "mediatek,mt8135-timer" for MT8135 compatible timers (GPT) * "mediatek,mt8173-timer" for MT8173 compatible timers (GPT) + * "mediatek,mt8516-timer" for MT8516 compatible timers (GPT) * "mediatek,mt6577-timer" for MT6577 and all above compatible timers (GPT) For those SoCs that use SYST -- cgit v1.2.3 From 61a640143f68e953efe2320c65c3784b8fbdcd42 Mon Sep 17 00:00:00 2001 From: Fabien Parent Date: Sat, 23 Mar 2019 22:16:08 +0100 Subject: dt-bindings: serial: mtk-uart: add support for MT8516 Add binding documentation of mtk-uart for MT8516 SoC. Signed-off-by: Fabien Parent Acked-by: Rob Herring Signed-off-by: Matthias Brugger --- Documentation/devicetree/bindings/serial/mtk-uart.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/serial/mtk-uart.txt b/Documentation/devicetree/bindings/serial/mtk-uart.txt index 4910f6316c3e..ca7e9dc83087 100644 --- a/Documentation/devicetree/bindings/serial/mtk-uart.txt +++ b/Documentation/devicetree/bindings/serial/mtk-uart.txt @@ -17,6 +17,7 @@ Required properties: * "mediatek,mt8127-uart" for MT8127 compatible UARTS * "mediatek,mt8135-uart" for MT8135 compatible UARTS * "mediatek,mt8173-uart" for MT8173 compatible UARTS + * "mediatek,mt8516-uart" for MT8516 compatible UARTS * "mediatek,mt6577-uart" for MT6577 and all of the above - reg: The base address of the UART register bank. -- cgit v1.2.3 From 6969706399cc1687206bc47a10eee3706f0c32fd Mon Sep 17 00:00:00 2001 From: Fabien Parent Date: Sat, 23 Mar 2019 22:16:09 +0100 Subject: dt-bindings: irq: mtk,sysirq: add support for MT8516 Add binding documentation of mediatek,sysirq for MT8516 SoC. Signed-off-by: Fabien Parent Acked-by: Rob Herring Signed-off-by: Matthias Brugger --- .../devicetree/bindings/interrupt-controller/mediatek,sysirq.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/interrupt-controller/mediatek,sysirq.txt b/Documentation/devicetree/bindings/interrupt-controller/mediatek,sysirq.txt index 9ef089400840..0e312fea2a5d 100644 --- a/Documentation/devicetree/bindings/interrupt-controller/mediatek,sysirq.txt +++ b/Documentation/devicetree/bindings/interrupt-controller/mediatek,sysirq.txt @@ -5,6 +5,7 @@ interrupt. Required properties: - compatible: should be + "mediatek,mt8516-sysirq", "mediatek,mt6577-sysirq": for MT8516 "mediatek,mt8183-sysirq", "mediatek,mt6577-sysirq": for MT8183 "mediatek,mt8173-sysirq", "mediatek,mt6577-sysirq": for MT8173 "mediatek,mt8135-sysirq", "mediatek,mt6577-sysirq": for MT8135 -- cgit v1.2.3 From 9e2b0e0be64227ba8f09008d32d75280595a5464 Mon Sep 17 00:00:00 2001 From: Nick Crews Date: Fri, 12 Apr 2019 12:14:43 -0600 Subject: platform/chrome: wilco_ec: Add h1_gpio status to debugfs As part of Chrome OS's FAFT (Fully Automated Firmware Testing) tests, we need to ensure that the H1 chip is properly setting some GPIO lines. The h1_gpio attribute exposes the state of the lines: - ENTRY_TO_FACT_MODE in BIT(0) - SPI_CHROME_SEL in BIT(1) There are two reasons that I am exposing this in debugfs, and not as a GPIO: 1. This is only useful for testing, so end users shouldn't ever care about this. In fact, if it passes the tests, then the value of h1_gpio will always be 2, so it would be really uninteresting for users. 2. This GPIO is not connected to, controlled by, or really even related to the AP. The GPIO runs between the EC and the H1 security chip. Changes in v4: - Use "0x02x\n" instead of "02x\n" for format string - Use DEFINE_DEBUGFS_ATTRIBUTE() - Add documentation Changes in v3: - Fix documentation to correspond with formatting change in v2. Changes in v2: - Zero out the unused fields in the request. - Format result as "%02x\n" instead of as a decimal. Signed-off-by: Nick Crews Signed-off-by: Enric Balletbo i Serra --- Documentation/ABI/testing/debugfs-wilco-ec | 13 +++++++++ drivers/platform/chrome/wilco_ec/debugfs.c | 47 ++++++++++++++++++++++++++++++ 2 files changed, 60 insertions(+) (limited to 'Documentation') diff --git a/Documentation/ABI/testing/debugfs-wilco-ec b/Documentation/ABI/testing/debugfs-wilco-ec index 7ff6b45be703..73a5a66ddca6 100644 --- a/Documentation/ABI/testing/debugfs-wilco-ec +++ b/Documentation/ABI/testing/debugfs-wilco-ec @@ -1,3 +1,16 @@ +What: /sys/kernel/debug/wilco_ec/h1_gpio +Date: April 2019 +KernelVersion: 5.2 +Description: + As part of Chrome OS's FAFT (Fully Automated Firmware Testing) + tests, we need to ensure that the H1 chip is properly setting + some GPIO lines. The h1_gpio attribute exposes the state + of the lines: + - ENTRY_TO_FACT_MODE in BIT(0) + - SPI_CHROME_SEL in BIT(1) + + Output will formatted with "0x%02x\n". + What: /sys/kernel/debug/wilco_ec/raw Date: January 2019 KernelVersion: 5.1 diff --git a/drivers/platform/chrome/wilco_ec/debugfs.c b/drivers/platform/chrome/wilco_ec/debugfs.c index 8d307378c1cb..f163476d080d 100644 --- a/drivers/platform/chrome/wilco_ec/debugfs.c +++ b/drivers/platform/chrome/wilco_ec/debugfs.c @@ -164,6 +164,51 @@ static const struct file_operations fops_raw = { .llseek = no_llseek, }; +#define CMD_KB_CHROME 0x88 +#define SUB_CMD_H1_GPIO 0x0A + +struct h1_gpio_status_request { + u8 cmd; /* Always CMD_KB_CHROME */ + u8 reserved; + u8 sub_cmd; /* Always SUB_CMD_H1_GPIO */ +} __packed; + +struct hi_gpio_status_response { + u8 status; /* 0 if allowed */ + u8 val; /* BIT(0)=ENTRY_TO_FACT_MODE, BIT(1)=SPI_CHROME_SEL */ +} __packed; + +static int h1_gpio_get(void *arg, u64 *val) +{ + struct wilco_ec_device *ec = arg; + struct h1_gpio_status_request rq; + struct hi_gpio_status_response rs; + struct wilco_ec_message msg; + int ret; + + memset(&rq, 0, sizeof(rq)); + rq.cmd = CMD_KB_CHROME; + rq.sub_cmd = SUB_CMD_H1_GPIO; + + memset(&msg, 0, sizeof(msg)); + msg.type = WILCO_EC_MSG_LEGACY; + msg.request_data = &rq; + msg.request_size = sizeof(rq); + msg.response_data = &rs; + msg.response_size = sizeof(rs); + ret = wilco_ec_mailbox(ec, &msg); + if (ret < 0) + return ret; + if (rs.status) + return -EIO; + + *val = rs.val; + + return 0; +} + +DEFINE_DEBUGFS_ATTRIBUTE(fops_h1_gpio, h1_gpio_get, NULL, "0x%02llx\n"); + /** * wilco_ec_debugfs_probe() - Create the debugfs node * @pdev: The platform device, probably created in core.c @@ -185,6 +230,8 @@ static int wilco_ec_debugfs_probe(struct platform_device *pdev) if (!debug_info->dir) return 0; debugfs_create_file("raw", 0644, debug_info->dir, NULL, &fops_raw); + debugfs_create_file("h1_gpio", 0444, debug_info->dir, ec, + &fops_h1_gpio); return 0; } -- cgit v1.2.3 From ead619de90583f6c191b6a844129df51dda8881f Mon Sep 17 00:00:00 2001 From: Thierry Reding Date: Mon, 1 Apr 2019 12:40:45 +0200 Subject: dt-bindings: usb: xhci-tegra: Add Tegra186 support Extend the bindings to cover the set of features found in Tegra186. Reviewed-by: Rob Herring Reviewed-by: JC Kuo Signed-off-by: Thierry Reding Signed-off-by: Greg Kroah-Hartman --- Documentation/devicetree/bindings/usb/nvidia,tegra124-xusb.txt | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/usb/nvidia,tegra124-xusb.txt b/Documentation/devicetree/bindings/usb/nvidia,tegra124-xusb.txt index 4156c3e181c5..5bfcc0b4d6b9 100644 --- a/Documentation/devicetree/bindings/usb/nvidia,tegra124-xusb.txt +++ b/Documentation/devicetree/bindings/usb/nvidia,tegra124-xusb.txt @@ -10,6 +10,7 @@ Required properties: - Tegra124: "nvidia,tegra124-xusb" - Tegra132: "nvidia,tegra132-xusb", "nvidia,tegra124-xusb" - Tegra210: "nvidia,tegra210-xusb" + - Tegra186: "nvidia,tegra186-xusb" - reg: Must contain the base and length of the xHCI host registers, XUSB FPCI registers and XUSB IPFS registers. - reg-names: Must contain the following entries: @@ -59,6 +60,8 @@ For Tegra210: - avdd-pll-uerefe-supply: PLLE reference PLL power supply. Must supply 1.05 V. - dvdd-pex-pll-supply: PCIe/USB3 PLL power supply. Must supply 1.05 V. - hvdd-pex-pll-e-supply: High-voltage PLLE power supply. Must supply 1.8 V. + +For Tegra210 and Tegra186: - power-domains: A list of PM domain specifiers that reference each power-domain used by the xHCI controller. This list must comprise of a specifier for the XUSBA and XUSBC power-domains. See ../power/power_domain.txt and @@ -78,6 +81,7 @@ Optional properties: - Tegra132: usb2-0, usb2-1, usb2-2, hsic-0, hsic-1, usb3-0, usb3-1 - Tegra210: usb2-0, usb2-1, usb2-2, usb2-3, hsic-0, usb3-0, usb3-1, usb3-2, usb3-3 + - Tegra186: usb2-0, usb2-1, usb2-2, hsic-0, usb3-0, usb3-1, usb3-2 Example: -------- -- cgit v1.2.3 From d80b5005c5dd113442454b469752f0f95ac15645 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Mon, 15 Apr 2019 23:56:01 -0300 Subject: docs: usb: convert documents to ReST Convert USB documents to ReST, in order to prepare for adding it to the kernel API book, as most of the stuff there are driver or subsystem-related. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Greg Kroah-Hartman --- Documentation/usb/WUSB-Design-overview.txt | 56 ++- Documentation/usb/acm.txt | 164 ++++---- Documentation/usb/authorization.txt | 75 ++-- Documentation/usb/chipidea.txt | 101 +++-- Documentation/usb/dwc3.txt | 12 +- Documentation/usb/ehci.txt | 42 +- Documentation/usb/functionfs.txt | 17 +- Documentation/usb/gadget-testing.txt | 611 +++++++++++++++++------------ Documentation/usb/gadget_configfs.txt | 306 ++++++++------- Documentation/usb/gadget_hid.txt | 175 +++++---- Documentation/usb/gadget_multi.txt | 43 +- Documentation/usb/gadget_printer.txt | 155 ++++---- Documentation/usb/gadget_serial.txt | 75 ++-- Documentation/usb/iuu_phoenix.txt | 34 +- Documentation/usb/mass-storage.txt | 19 +- Documentation/usb/misc_usbsevseg.txt | 9 +- Documentation/usb/mtouchusb.txt | 42 +- Documentation/usb/ohci.txt | 5 +- Documentation/usb/rio.txt | 83 ++-- Documentation/usb/usb-help.txt | 21 +- Documentation/usb/usb-serial.txt | 205 ++++++---- Documentation/usb/usbip_protocol.txt | 552 ++++++++++++++------------ Documentation/usb/usbmon.txt | 100 +++-- 23 files changed, 1663 insertions(+), 1239 deletions(-) (limited to 'Documentation') diff --git a/Documentation/usb/WUSB-Design-overview.txt b/Documentation/usb/WUSB-Design-overview.txt index fdb47637720e..dc5e21609bb5 100644 --- a/Documentation/usb/WUSB-Design-overview.txt +++ b/Documentation/usb/WUSB-Design-overview.txt @@ -1,7 +1,9 @@ - +================================ Linux UWB + Wireless USB + WiNET +================================ + + Copyright (C) 2005-2006 Intel Corporation - (C) 2005-2006 Intel Corporation Inaky Perez-Gonzalez This program is free software; you can redistribute it and/or @@ -29,6 +31,7 @@ drivers for the USB based UWB radio controllers defined in the Wireless USB 1.0 specification (including Wireless USB host controller and an Intel WiNET controller). +.. Contents 1. Introduction 1. HWA: Host Wire adapters, your Wireless USB dongle @@ -51,7 +54,8 @@ and an Intel WiNET controller). 4. Glossary - Introduction +Introduction +============ UWB is a wide-band communication protocol that is to serve also as the low-level protocol for others (much like TCP sits on IP). Currently @@ -93,7 +97,8 @@ The different logical parts of this driver are: do the actual WUSB. - HWA: Host Wire adapters, your Wireless USB dongle +HWA: Host Wire adapters, your Wireless USB dongle +------------------------------------------------- WUSB also defines a device called a Host Wire Adaptor (HWA), which in mere terms is a USB dongle that enables your PC to have UWB and Wireless @@ -125,7 +130,8 @@ The HWA itself is broken in two or three main interfaces: their type and kick into gear. - DWA: Device Wired Adaptor, a Wireless USB hub for wired devices +DWA: Device Wired Adaptor, a Wireless USB hub for wired devices +--------------------------------------------------------------- These are the complement to HWAs. They are a USB host for connecting wired devices, but it is connected to your PC connected via Wireless @@ -137,7 +143,8 @@ code with the HWA-RC driver; there is a bunch of factorization work that has been done to support that in upcoming releases. - WHCI: Wireless Host Controller Interface, the PCI WUSB host adapter +WHCI: Wireless Host Controller Interface, the PCI WUSB host adapter +------------------------------------------------------------------- This is your usual PCI device that implements WHCI. Similar in concept to EHCI, it allows your wireless USB devices (including DWAs) to connect @@ -148,7 +155,8 @@ There is still no driver support for this, but will be in upcoming releases. - The UWB stack +The UWB stack +============= The main mission of the UWB stack is to keep a tally of which devices are in radio proximity to allow drivers to connect to them. As well, it @@ -156,7 +164,8 @@ provides an API for controlling the local radio controllers (RCs from now on), such as to start/stop beaconing, scan, allocate bandwidth, etc. - Devices and hosts: the basic structure +Devices and hosts: the basic structure +-------------------------------------- The main building block here is the UWB device (struct uwb_dev). For each device that pops up in radio presence (ie: the UWB host receives a @@ -187,7 +196,8 @@ the USB connected HWA. Eventually, drivers/whci-rc.c will do the same for the PCI connected WHCI controller. - Host Controller life cycle +Host Controller life cycle +-------------------------- So let's say we connect a dongle to the system: it is detected and firmware uploaded if needed [for Intel's i1480 @@ -209,7 +219,8 @@ When a dongle is disconnected, /drivers/uwb/hwa-rc.c:hwarc_disconnect()/ takes time of tearing everything down safely (or not...). - On the air: beacons and enumerating the radio neighborhood +On the air: beacons and enumerating the radio neighborhood +---------------------------------------------------------- So assuming we have devices and we have agreed for a channel to connect on (let's say 9), we put the new RC to beacon: @@ -235,12 +246,14 @@ are received in some time, the device is considered gone and wiped out the beacon cache of dead devices]. - Device lists +Device lists +------------ All UWB devices are kept in the list of the struct bus_type uwb_bus_type. - Bandwidth allocation +Bandwidth allocation +-------------------- The UWB stack maintains a local copy of DRP availability through processing of incoming *DRP Availability Change* notifications. This @@ -260,7 +273,8 @@ completion. [Note: The bandwidth reservation work is in progress and subject to change.] - Wireless USB Host Controller drivers +Wireless USB Host Controller drivers +==================================== *WARNING* This section needs a lot of work! @@ -296,7 +310,8 @@ starts sending MMCs. Now it all depends on external stimuli. -*New device connection* +New device connection +--------------------- A new device pops up, it scans the radio looking for MMCs that give out the existence of Wireless USB channels. Once one (or more) are found, @@ -322,7 +337,8 @@ has seen the port status changes, as we have been toggling them. It will start enumerating and doing transfers through usb_hcd->urb_enqueue() to read descriptors and move our data. -*Device life cycle and keep alives* +Device life cycle and keep alives +--------------------------------- Every time there is a successful transfer to/from a device, we update a per-device activity timestamp. If not, every now and then we check and @@ -340,7 +356,8 @@ device list looking for whom needs refreshing. If the device wants to disconnect, it will either die (ugly) or send a /DN_Disconnect/ that will prompt a disconnection from the system. -*Sending and receiving data* +Sending and receiving data +-------------------------- Data is sent and received through /Remote Pipes/ (rpipes). An rpipe is /aimed/ at an endpoint in a WUSB device. This is the same for HWAs and @@ -394,7 +411,8 @@ finalize the transfer. For IN xfers, we only issue URBs for the segments we want to read and then wait for the xfer result data. -*URB mapping into xfers* +URB mapping into xfers +^^^^^^^^^^^^^^^^^^^^^^ This is done by hwahc_op_urb_[en|de]queue(). In enqueue() we aim an rpipe to the endpoint where we have to transmit, create a transfer @@ -407,7 +425,8 @@ and not yet done and when all that is done, the xfer callback will be called--this will call the URB callback. - Glossary +Glossary +======== *DWA* -- Device Wire Adapter @@ -436,4 +455,3 @@ the host. Design-overview.txt-1.8 (last edited 2006-11-04 12:22:24 by InakyPerezGonzalez) - diff --git a/Documentation/usb/acm.txt b/Documentation/usb/acm.txt index 903abca10517..e8bda98e9b51 100644 --- a/Documentation/usb/acm.txt +++ b/Documentation/usb/acm.txt @@ -1,127 +1,131 @@ - Linux ACM driver v0.16 - (c) 1999 Vojtech Pavlik - Sponsored by SuSE ----------------------------------------------------------------------------- +====================== +Linux ACM driver v0.16 +====================== + +Copyright (c) 1999 Vojtech Pavlik + +Sponsored by SuSE 0. Disclaimer ~~~~~~~~~~~~~ - This program is free software; you can redistribute it and/or modify it +This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. - This program is distributed in the hope that it will be useful, but +This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. - You should have received a copy of the GNU General Public License along +You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA - Should you need to contact me, the author, you can do so either by e-mail -- mail your message to , or by paper mail: Vojtech Pavlik, +Should you need to contact me, the author, you can do so either by e-mail - +mail your message to , or by paper mail: Vojtech Pavlik, Ucitelska 1576, Prague 8, 182 00 Czech Republic - For your convenience, the GNU General Public License version 2 is included +For your convenience, the GNU General Public License version 2 is included in the package: See the file COPYING. 1. Usage ~~~~~~~~ - The drivers/usb/class/cdc-acm.c drivers works with USB modems and USB ISDN terminal +The drivers/usb/class/cdc-acm.c drivers works with USB modems and USB ISDN terminal adapters that conform to the Universal Serial Bus Communication Device Class Abstract Control Model (USB CDC ACM) specification. - Many modems do, here is a list of those I know of: +Many modems do, here is a list of those I know of: - 3Com OfficeConnect 56k - 3Com Voice FaxModem Pro - 3Com Sportster - MultiTech MultiModem 56k - Zoom 2986L FaxModem - Compaq 56k FaxModem - ELSA Microlink 56k + - 3Com OfficeConnect 56k + - 3Com Voice FaxModem Pro + - 3Com Sportster + - MultiTech MultiModem 56k + - Zoom 2986L FaxModem + - Compaq 56k FaxModem + - ELSA Microlink 56k - I know of one ISDN TA that does work with the acm driver: +I know of one ISDN TA that does work with the acm driver: - 3Com USR ISDN Pro TA + - 3Com USR ISDN Pro TA - Some cell phones also connect via USB. I know the following phones work: +Some cell phones also connect via USB. I know the following phones work: - SonyEricsson K800i + - SonyEricsson K800i - Unfortunately many modems and most ISDN TAs use proprietary interfaces and +Unfortunately many modems and most ISDN TAs use proprietary interfaces and thus won't work with this drivers. Check for ACM compliance before buying. - To use the modems you need these modules loaded: +To use the modems you need these modules loaded:: usbcore.ko uhci-hcd.ko ohci-hcd.ko or ehci-hcd.ko cdc-acm.ko - After that, the modem[s] should be accessible. You should be able to use +After that, the modem[s] should be accessible. You should be able to use minicom, ppp and mgetty with them. 2. Verifying that it works ~~~~~~~~~~~~~~~~~~~~~~~~~~ - The first step would be to check /sys/kernel/debug/usb/devices, it should look -like this: - -T: Bus=01 Lev=00 Prnt=00 Port=00 Cnt=00 Dev#= 1 Spd=12 MxCh= 2 -B: Alloc= 0/900 us ( 0%), #Int= 0, #Iso= 0 -D: Ver= 1.00 Cls=09(hub ) Sub=00 Prot=00 MxPS= 8 #Cfgs= 1 -P: Vendor=0000 ProdID=0000 Rev= 0.00 -S: Product=USB UHCI Root Hub -S: SerialNumber=6800 -C:* #Ifs= 1 Cfg#= 1 Atr=40 MxPwr= 0mA -I: If#= 0 Alt= 0 #EPs= 1 Cls=09(hub ) Sub=00 Prot=00 Driver=hub -E: Ad=81(I) Atr=03(Int.) MxPS= 8 Ivl=255ms -T: Bus=01 Lev=01 Prnt=01 Port=01 Cnt=01 Dev#= 2 Spd=12 MxCh= 0 -D: Ver= 1.00 Cls=02(comm.) Sub=00 Prot=00 MxPS= 8 #Cfgs= 2 -P: Vendor=04c1 ProdID=008f Rev= 2.07 -S: Manufacturer=3Com Inc. -S: Product=3Com U.S. Robotics Pro ISDN TA -S: SerialNumber=UFT53A49BVT7 -C: #Ifs= 1 Cfg#= 1 Atr=60 MxPwr= 0mA -I: If#= 0 Alt= 0 #EPs= 3 Cls=ff(vend.) Sub=ff Prot=ff Driver=acm -E: Ad=85(I) Atr=02(Bulk) MxPS= 64 Ivl= 0ms -E: Ad=04(O) Atr=02(Bulk) MxPS= 64 Ivl= 0ms -E: Ad=81(I) Atr=03(Int.) MxPS= 16 Ivl=128ms -C:* #Ifs= 2 Cfg#= 2 Atr=60 MxPwr= 0mA -I: If#= 0 Alt= 0 #EPs= 1 Cls=02(comm.) Sub=02 Prot=01 Driver=acm -E: Ad=81(I) Atr=03(Int.) MxPS= 16 Ivl=128ms -I: If#= 1 Alt= 0 #EPs= 2 Cls=0a(data ) Sub=00 Prot=00 Driver=acm -E: Ad=85(I) Atr=02(Bulk) MxPS= 64 Ivl= 0ms -E: Ad=04(O) Atr=02(Bulk) MxPS= 64 Ivl= 0ms + +The first step would be to check /sys/kernel/debug/usb/devices, it should look +like this:: + + T: Bus=01 Lev=00 Prnt=00 Port=00 Cnt=00 Dev#= 1 Spd=12 MxCh= 2 + B: Alloc= 0/900 us ( 0%), #Int= 0, #Iso= 0 + D: Ver= 1.00 Cls=09(hub ) Sub=00 Prot=00 MxPS= 8 #Cfgs= 1 + P: Vendor=0000 ProdID=0000 Rev= 0.00 + S: Product=USB UHCI Root Hub + S: SerialNumber=6800 + C:* #Ifs= 1 Cfg#= 1 Atr=40 MxPwr= 0mA + I: If#= 0 Alt= 0 #EPs= 1 Cls=09(hub ) Sub=00 Prot=00 Driver=hub + E: Ad=81(I) Atr=03(Int.) MxPS= 8 Ivl=255ms + T: Bus=01 Lev=01 Prnt=01 Port=01 Cnt=01 Dev#= 2 Spd=12 MxCh= 0 + D: Ver= 1.00 Cls=02(comm.) Sub=00 Prot=00 MxPS= 8 #Cfgs= 2 + P: Vendor=04c1 ProdID=008f Rev= 2.07 + S: Manufacturer=3Com Inc. + S: Product=3Com U.S. Robotics Pro ISDN TA + S: SerialNumber=UFT53A49BVT7 + C: #Ifs= 1 Cfg#= 1 Atr=60 MxPwr= 0mA + I: If#= 0 Alt= 0 #EPs= 3 Cls=ff(vend.) Sub=ff Prot=ff Driver=acm + E: Ad=85(I) Atr=02(Bulk) MxPS= 64 Ivl= 0ms + E: Ad=04(O) Atr=02(Bulk) MxPS= 64 Ivl= 0ms + E: Ad=81(I) Atr=03(Int.) MxPS= 16 Ivl=128ms + C:* #Ifs= 2 Cfg#= 2 Atr=60 MxPwr= 0mA + I: If#= 0 Alt= 0 #EPs= 1 Cls=02(comm.) Sub=02 Prot=01 Driver=acm + E: Ad=81(I) Atr=03(Int.) MxPS= 16 Ivl=128ms + I: If#= 1 Alt= 0 #EPs= 2 Cls=0a(data ) Sub=00 Prot=00 Driver=acm + E: Ad=85(I) Atr=02(Bulk) MxPS= 64 Ivl= 0ms + E: Ad=04(O) Atr=02(Bulk) MxPS= 64 Ivl= 0ms The presence of these three lines (and the Cls= 'comm' and 'data' classes) is important, it means it's an ACM device. The Driver=acm means the acm driver is used for the device. If you see only Cls=ff(vend.) then you're out -of luck, you have a device with vendor specific-interface. - -D: Ver= 1.00 Cls=02(comm.) Sub=00 Prot=00 MxPS= 8 #Cfgs= 2 -I: If#= 0 Alt= 0 #EPs= 1 Cls=02(comm.) Sub=02 Prot=01 Driver=acm -I: If#= 1 Alt= 0 #EPs= 2 Cls=0a(data ) Sub=00 Prot=00 Driver=acm - -In the system log you should see: - -usb.c: USB new device connect, assigned device number 2 -usb.c: kmalloc IF c7691fa0, numif 1 -usb.c: kmalloc IF c7b5f3e0, numif 2 -usb.c: skipped 4 class/vendor specific interface descriptors -usb.c: new device strings: Mfr=1, Product=2, SerialNumber=3 -usb.c: USB device number 2 default language ID 0x409 -Manufacturer: 3Com Inc. -Product: 3Com U.S. Robotics Pro ISDN TA -SerialNumber: UFT53A49BVT7 -acm.c: probing config 1 -acm.c: probing config 2 -ttyACM0: USB ACM device -acm.c: acm_control_msg: rq: 0x22 val: 0x0 len: 0x0 result: 0 -acm.c: acm_control_msg: rq: 0x20 val: 0x0 len: 0x7 result: 7 -usb.c: acm driver claimed interface c7b5f3e0 -usb.c: acm driver claimed interface c7b5f3f8 -usb.c: acm driver claimed interface c7691fa0 +of luck, you have a device with vendor specific-interface:: + + D: Ver= 1.00 Cls=02(comm.) Sub=00 Prot=00 MxPS= 8 #Cfgs= 2 + I: If#= 0 Alt= 0 #EPs= 1 Cls=02(comm.) Sub=02 Prot=01 Driver=acm + I: If#= 1 Alt= 0 #EPs= 2 Cls=0a(data ) Sub=00 Prot=00 Driver=acm + +In the system log you should see:: + + usb.c: USB new device connect, assigned device number 2 + usb.c: kmalloc IF c7691fa0, numif 1 + usb.c: kmalloc IF c7b5f3e0, numif 2 + usb.c: skipped 4 class/vendor specific interface descriptors + usb.c: new device strings: Mfr=1, Product=2, SerialNumber=3 + usb.c: USB device number 2 default language ID 0x409 + Manufacturer: 3Com Inc. + Product: 3Com U.S. Robotics Pro ISDN TA + SerialNumber: UFT53A49BVT7 + acm.c: probing config 1 + acm.c: probing config 2 + ttyACM0: USB ACM device + acm.c: acm_control_msg: rq: 0x22 val: 0x0 len: 0x0 result: 0 + acm.c: acm_control_msg: rq: 0x20 val: 0x0 len: 0x7 result: 7 + usb.c: acm driver claimed interface c7b5f3e0 + usb.c: acm driver claimed interface c7b5f3f8 + usb.c: acm driver claimed interface c7691fa0 If all this seems to be OK, fire up minicom and set it to talk to the ttyACM device and try typing 'at'. If it responds with 'OK', then everything is diff --git a/Documentation/usb/authorization.txt b/Documentation/usb/authorization.txt index 9dd1dc7b1009..9e53909d04c2 100644 --- a/Documentation/usb/authorization.txt +++ b/Documentation/usb/authorization.txt @@ -1,7 +1,8 @@ - +============================================================== Authorizing (or not) your USB devices to connect to the system +============================================================== -(C) 2007 Inaky Perez-Gonzalez Intel Corporation +Copyright (C) 2007 Inaky Perez-Gonzalez Intel Corporation This feature allows you to control if a USB device can be used (or not) in a system. This feature will allow you to implement a lock-down @@ -12,24 +13,25 @@ its interfaces are immediately made available to the users. With this modification, only if root authorizes the device to be configured will then it be possible to use it. -Usage: +Usage +===== -Authorize a device to connect: +Authorize a device to connect:: -$ echo 1 > /sys/bus/usb/devices/DEVICE/authorized + $ echo 1 > /sys/bus/usb/devices/DEVICE/authorized -Deauthorize a device: +De-authorize a device:: -$ echo 0 > /sys/bus/usb/devices/DEVICE/authorized + $ echo 0 > /sys/bus/usb/devices/DEVICE/authorized Set new devices connected to hostX to be deauthorized by default (ie: -lock down): +lock down):: -$ echo 0 > /sys/bus/usb/devices/usbX/authorized_default + $ echo 0 > /sys/bus/usb/devices/usbX/authorized_default -Remove the lock down: +Remove the lock down:: -$ echo 1 > /sys/bus/usb/devices/usbX/authorized_default + $ echo 1 > /sys/bus/usb/devices/usbX/authorized_default By default, Wired USB devices are authorized by default to connect. Wireless USB hosts deauthorize by default all new connected @@ -40,21 +42,21 @@ USB ports. Example system lockdown (lame) ------------------------ +------------------------------ Imagine you want to implement a lockdown so only devices of type XYZ can be connected (for example, it is a kiosk machine with a visible -USB port): +USB port):: -boot up -rc.local -> + boot up + rc.local -> - for host in /sys/bus/usb/devices/usb* - do - echo 0 > $host/authorized_default - done + for host in /sys/bus/usb/devices/usb* + do + echo 0 > $host/authorized_default + done -Hookup an script to udev, for new USB devices +Hookup an script to udev, for new USB devices:: if device_is_my_type $DEV then @@ -67,10 +69,10 @@ checking if the class, type and protocol match something is the worse security verification you can make (or the best, for someone willing to break it). If you need something secure, use crypto and Certificate Authentication or stuff like that. Something simple for an storage key -could be: +could be:: -function device_is_my_type() -{ + function device_is_my_type() + { echo 1 > authorized # temporarily authorize it # FIXME: make sure none can mount it mount DEVICENODE /mntpoint @@ -83,7 +85,7 @@ function device_is_my_type() else echo 0 > authorized fi -} + } Of course, this is lame, you'd want to do a real certificate @@ -95,30 +97,35 @@ welcome. Interface authorization ----------------------- + There is a similar approach to allow or deny specific USB interfaces. That allows to block only a subset of an USB device. -Authorize an interface: -$ echo 1 > /sys/bus/usb/devices/INTERFACE/authorized +Authorize an interface:: -Deauthorize an interface: -$ echo 0 > /sys/bus/usb/devices/INTERFACE/authorized + $ echo 1 > /sys/bus/usb/devices/INTERFACE/authorized + +Deauthorize an interface:: + + $ echo 0 > /sys/bus/usb/devices/INTERFACE/authorized The default value for new interfaces on a particular USB bus can be changed, too. -Allow interfaces per default: -$ echo 1 > /sys/bus/usb/devices/usbX/interface_authorized_default +Allow interfaces per default:: + + $ echo 1 > /sys/bus/usb/devices/usbX/interface_authorized_default + +Deny interfaces per default:: -Deny interfaces per default: -$ echo 0 > /sys/bus/usb/devices/usbX/interface_authorized_default + $ echo 0 > /sys/bus/usb/devices/usbX/interface_authorized_default Per default the interface_authorized_default bit is 1. So all interfaces would authorized per default. Note: -If a deauthorized interface will be authorized so the driver probing must -be triggered manually by writing INTERFACE to /sys/bus/usb/drivers_probe + If a deauthorized interface will be authorized so the driver probing must + be triggered manually by writing INTERFACE to /sys/bus/usb/drivers_probe For drivers that need multiple interfaces all needed interfaces should be authorized first. After that the drivers should be probed. diff --git a/Documentation/usb/chipidea.txt b/Documentation/usb/chipidea.txt index d1eedc01b00a..68473abe2823 100644 --- a/Documentation/usb/chipidea.txt +++ b/Documentation/usb/chipidea.txt @@ -1,22 +1,37 @@ +============================================== +ChipIdea Highspeed Dual Role Controller Driver +============================================== + 1. How to test OTG FSM(HNP and SRP) ----------------------------------- + To show how to demo OTG HNP and SRP functions via sys input files with 2 Freescale i.MX6Q sabre SD boards. 1.1 How to enable OTG FSM ---------------------------------------- +------------------------- + 1.1.1 Select CONFIG_USB_OTG_FSM in menuconfig, rebuild kernel +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + Image and modules. If you want to check some internal variables for otg fsm, mount debugfs, there are 2 files -which can show otg fsm variables and some controller registers value: -cat /sys/kernel/debug/ci_hdrc.0/otg -cat /sys/kernel/debug/ci_hdrc.0/registers +which can show otg fsm variables and some controller registers value:: + + cat /sys/kernel/debug/ci_hdrc.0/otg + cat /sys/kernel/debug/ci_hdrc.0/registers + 1.1.2 Add below entries in your dts file for your controller node +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +:: + otg-rev = <0x0200>; adp-disable; 1.2 Test operations ------------------- + 1) Power up 2 Freescale i.MX6Q sabre SD boards with gadget class driver loaded (e.g. g_mass_storage). @@ -26,19 +41,24 @@ cat /sys/kernel/debug/ci_hdrc.0/registers The A-device(with micro A plug inserted) should enumerate B-device. 3) Role switch - On B-device: - echo 1 > /sys/bus/platform/devices/ci_hdrc.0/inputs/b_bus_req + + On B-device:: + + echo 1 > /sys/bus/platform/devices/ci_hdrc.0/inputs/b_bus_req B-device should take host role and enumerate A-device. 4) A-device switch back to host. - On B-device: - echo 0 > /sys/bus/platform/devices/ci_hdrc.0/inputs/b_bus_req + + On B-device:: + + echo 0 > /sys/bus/platform/devices/ci_hdrc.0/inputs/b_bus_req or, by introducing HNP polling, B-Host can know when A-peripheral wish to be host role, so this role switch also can be trigged in A-peripheral - side by answering the polling from B-Host, this can be done on A-device: - echo 1 > /sys/bus/platform/devices/ci_hdrc.0/inputs/a_bus_req + side by answering the polling from B-Host, this can be done on A-device:: + + echo 1 > /sys/bus/platform/devices/ci_hdrc.0/inputs/a_bus_req A-device should switch back to host and enumerate B-device. @@ -49,23 +69,31 @@ cat /sys/kernel/debug/ci_hdrc.0/registers A-device should NOT enumerate B-device. if A-device wants to use bus: - On A-device: - echo 0 > /sys/bus/platform/devices/ci_hdrc.0/inputs/a_bus_drop - echo 1 > /sys/bus/platform/devices/ci_hdrc.0/inputs/a_bus_req + + On A-device:: + + echo 0 > /sys/bus/platform/devices/ci_hdrc.0/inputs/a_bus_drop + echo 1 > /sys/bus/platform/devices/ci_hdrc.0/inputs/a_bus_req if B-device wants to use bus: - On B-device: - echo 1 > /sys/bus/platform/devices/ci_hdrc.0/inputs/b_bus_req + + On B-device:: + + echo 1 > /sys/bus/platform/devices/ci_hdrc.0/inputs/b_bus_req 7) A-device power down the bus. - On A-device: - echo 1 > /sys/bus/platform/devices/ci_hdrc.0/inputs/a_bus_drop + + On A-device:: + + echo 1 > /sys/bus/platform/devices/ci_hdrc.0/inputs/a_bus_drop A-device should disconnect with B-device and power down the bus. 8) B-device does data pulse for SRP. - On B-device: - echo 1 > /sys/bus/platform/devices/ci_hdrc.0/inputs/b_bus_req + + On B-device:: + + echo 1 > /sys/bus/platform/devices/ci_hdrc.0/inputs/b_bus_req A-device should resume usb bus and enumerate B-device. @@ -75,22 +103,31 @@ cat /sys/kernel/debug/ci_hdrc.0/registers July 27, 2012 Revision 2.0 version 1.1a" 2. How to enable USB as system wakeup source ------------------------------------ +-------------------------------------------- Below is the example for how to enable USB as system wakeup source at imx6 platform. -2.1 Enable core's wakeup -echo enabled > /sys/bus/platform/devices/ci_hdrc.0/power/wakeup -2.2 Enable glue layer's wakeup -echo enabled > /sys/bus/platform/devices/2184000.usb/power/wakeup -2.3 Enable PHY's wakeup (optional) -echo enabled > /sys/bus/platform/devices/20c9000.usbphy/power/wakeup -2.4 Enable roothub's wakeup -echo enabled > /sys/bus/usb/devices/usb1/power/wakeup -2.5 Enable related device's wakeup -echo enabled > /sys/bus/usb/devices/1-1/power/wakeup +2.1 Enable core's wakeup:: + + echo enabled > /sys/bus/platform/devices/ci_hdrc.0/power/wakeup + +2.2 Enable glue layer's wakeup:: + + echo enabled > /sys/bus/platform/devices/2184000.usb/power/wakeup + +2.3 Enable PHY's wakeup (optional):: + + echo enabled > /sys/bus/platform/devices/20c9000.usbphy/power/wakeup + +2.4 Enable roothub's wakeup:: + + echo enabled > /sys/bus/usb/devices/usb1/power/wakeup + +2.5 Enable related device's wakeup:: + + echo enabled > /sys/bus/usb/devices/1-1/power/wakeup If the system has only one usb port, and you want usb wakeup at this port, you -can use below script to enable usb wakeup. -for i in $(find /sys -name wakeup | grep usb);do echo enabled > $i;done; +can use below script to enable usb wakeup:: + for i in $(find /sys -name wakeup | grep usb);do echo enabled > $i;done; diff --git a/Documentation/usb/dwc3.txt b/Documentation/usb/dwc3.txt index 1d02c01d1c7c..f94a7ba16573 100644 --- a/Documentation/usb/dwc3.txt +++ b/Documentation/usb/dwc3.txt @@ -1,6 +1,11 @@ +=========== +DWC3 driver +=========== + + +TODO +~~~~ - TODO -~~~~~~ Please pick something while reading :) - Convert interrupt handler to per-ep-thread-irq @@ -9,6 +14,7 @@ Please pick something while reading :) until the command completes which is bad. Implementation idea: + - dwc core implements a demultiplexing irq chip for interrupts per endpoint. The interrupt numbers are allocated during probe and belong to the device. If MSI provides per-endpoint interrupt this dummy @@ -19,6 +25,7 @@ Please pick something while reading :) - dwc3_send_gadget_ep_cmd() will sleep in wait_for_completion_timeout() until the command completes. - the interrupt handler is split into the following pieces: + - primary handler of the device goes through every event and calls generic_handle_irq() for event it. On return from generic_handle_irq() in acknowledges the event @@ -40,6 +47,7 @@ Please pick something while reading :) for command completion. Latency: + There should be no increase in latency since the interrupt-thread has a high priority and will be run before an average task in user land (except the user changed priorities). diff --git a/Documentation/usb/ehci.txt b/Documentation/usb/ehci.txt index 160bd6c3ab7b..31f650e7c1b4 100644 --- a/Documentation/usb/ehci.txt +++ b/Documentation/usb/ehci.txt @@ -1,3 +1,7 @@ +=========== +EHCI driver +=========== + 27-Dec-2002 The EHCI driver is used to talk to high speed USB 2.0 devices using @@ -40,7 +44,8 @@ APIs exposed to USB device drivers. -FUNCTIONALITY +Functionality +============= This driver is regularly tested on x86 hardware, and has also been used on PPC hardware so big/little endianness issues should be gone. @@ -48,6 +53,7 @@ It's believed to do all the right PCI magic so that I/O works even on systems with interesting DMA mapping issues. Transfer Types +-------------- At this writing the driver should comfortably handle all control, bulk, and interrupt transfers, including requests to USB 1.1 devices through @@ -63,6 +69,7 @@ since EHCI represents these with a different data structure. So for now, most USB audio and video devices can't be connected to high speed buses. Driver Behavior +--------------- Transfers of all types can be queued. This means that control transfers from a driver on one interface (or through usbfs) won't interfere with @@ -83,14 +90,15 @@ limits on the number of periodic transactions that can be scheduled, and prevent use of polling intervals of less than one frame. -USE BY +Use by +====== Assuming you have an EHCI controller (on a PCI card or motherboard) -and have compiled this driver as a module, load this like: +and have compiled this driver as a module, load this like:: # modprobe ehci-hcd -and remove it by: +and remove it by:: # rmmod ehci-hcd @@ -112,13 +120,16 @@ If you're using this driver on a 2.5 kernel, and you've enabled USB debugging support, you'll see three files in the "sysfs" directory for any EHCI controller: - "async" dumps the asynchronous schedule, used for control + "async" + dumps the asynchronous schedule, used for control and bulk transfers. Shows each active qh and the qtds pending, usually one qtd per urb. (Look at it with usb-storage doing disk I/O; watch the request queues!) - "periodic" dumps the periodic schedule, used for interrupt + "periodic" + dumps the periodic schedule, used for interrupt and isochronous transfers. Doesn't show qtds. - "registers" show controller register state, and + "registers" + show controller register state, and The contents of those files can help identify driver problems. @@ -136,7 +147,8 @@ transaction translators are in use; some drivers have been seen to behave badly when they see different faults than OHCI or UHCI report. -PERFORMANCE +Performance +=========== USB 2.0 throughput is gated by two main factors: how fast the host controller can process requests, and how fast devices can respond to @@ -156,6 +168,7 @@ hardware and device driver software allow it. Periodic transfer modes approach the quoted 480 MBit/sec transfer rate. Hardware Performance +-------------------- At this writing, individual USB 2.0 devices tend to max out at around 20 MByte/sec transfer rates. This is of course subject to change; @@ -183,6 +196,7 @@ you issue a control or bulk request you can often expect to learn that it completed in less than 250 usec (depending on transfer size). Software Performance +-------------------- To get even 20 MByte/sec transfer rates, Linux-USB device drivers will need to keep the EHCI queue full. That means issuing large requests, @@ -206,9 +220,11 @@ mapping (which might apply an IOMMU) and IRQ reduction, all of which will help make high speed transfers run as fast as they can. -TBD: Interrupt and ISO transfer performance issues. Those periodic -transfers are fully scheduled, so the main issue is likely to be how -to trigger "high bandwidth" modes. +TBD: + Interrupt and ISO transfer performance issues. Those periodic + transfers are fully scheduled, so the main issue is likely to be how + to trigger "high bandwidth" modes. -TBD: More than standard 80% periodic bandwidth allocation is possible -through sysfs uframe_periodic_max parameter. Describe that. +TBD: + More than standard 80% periodic bandwidth allocation is possible + through sysfs uframe_periodic_max parameter. Describe that. diff --git a/Documentation/usb/functionfs.txt b/Documentation/usb/functionfs.txt index eaaaea019fc7..7fdc6d840ac5 100644 --- a/Documentation/usb/functionfs.txt +++ b/Documentation/usb/functionfs.txt @@ -1,4 +1,6 @@ -*How FunctionFS works* +==================== +How FunctionFS works +==================== From kernel point of view it is just a composite function with some unique behaviour. It may be added to an USB configuration only after @@ -38,13 +40,13 @@ when mounting. One can imagine a gadget that has an Ethernet, MTP and HID interfaces where the last two are implemented via FunctionFS. On user space -level it would look like this: +level it would look like this:: -$ insmod g_ffs.ko idVendor= iSerialNumber= functions=mtp,hid -$ mkdir /dev/ffs-mtp && mount -t functionfs mtp /dev/ffs-mtp -$ ( cd /dev/ffs-mtp && mtp-daemon ) & -$ mkdir /dev/ffs-hid && mount -t functionfs hid /dev/ffs-hid -$ ( cd /dev/ffs-hid && hid-daemon ) & + $ insmod g_ffs.ko idVendor= iSerialNumber= functions=mtp,hid + $ mkdir /dev/ffs-mtp && mount -t functionfs mtp /dev/ffs-mtp + $ ( cd /dev/ffs-mtp && mtp-daemon ) & + $ mkdir /dev/ffs-hid && mount -t functionfs hid /dev/ffs-hid + $ ( cd /dev/ffs-hid && hid-daemon ) & On kernel level the gadget checks ffs_data->dev_name to identify whether it's FunctionFS designed for MTP ("mtp") or HID ("hid"). @@ -64,4 +66,3 @@ have been written to their ep0's. Conversely, the gadget is unregistered after the first USB function closes its endpoints. - diff --git a/Documentation/usb/gadget-testing.txt b/Documentation/usb/gadget-testing.txt index 5908a21fddb6..7d7f2340af42 100644 --- a/Documentation/usb/gadget-testing.txt +++ b/Documentation/usb/gadget-testing.txt @@ -1,26 +1,32 @@ +============== +Gadget Testing +============== + This file summarizes information on basic testing of USB functions provided by gadgets. -1. ACM function -2. ECM function -3. ECM subset function -4. EEM function -5. FFS function -6. HID function -7. LOOPBACK function -8. MASS STORAGE function -9. MIDI function -10. NCM function -11. OBEX function -12. PHONET function -13. RNDIS function -14. SERIAL function -15. SOURCESINK function -16. UAC1 function (legacy implementation) -17. UAC2 function -18. UVC function -19. PRINTER function -20. UAC1 function (new API) +.. contents + + 1. ACM function + 2. ECM function + 3. ECM subset function + 4. EEM function + 5. FFS function + 6. HID function + 7. LOOPBACK function + 8. MASS STORAGE function + 9. MIDI function + 10. NCM function + 11. OBEX function + 12. PHONET function + 13. RNDIS function + 14. SERIAL function + 15. SOURCESINK function + 16. UAC1 function (legacy implementation) + 17. UAC2 function + 18. UVC function + 19. PRINTER function + 20. UAC1 function (new API) 1. ACM function @@ -44,13 +50,23 @@ There can be at most 4 ACM/generic serial/OBEX ports in the system. Testing the ACM function ------------------------ -On the host: cat > /dev/ttyACM -On the device : cat /dev/ttyGS +On the host:: + + cat > /dev/ttyACM + +On the device:: + + cat /dev/ttyGS then the other way round -On the device: cat > /dev/ttyGS -On the host: cat /dev/ttyACM +On the device:: + + cat > /dev/ttyGS + +On the host:: + + cat /dev/ttyACM 2. ECM function =============== @@ -63,13 +79,15 @@ Function-specific configfs interface The function name to use when creating the function directory is "ecm". The ECM function provides these attributes in its function directory: - ifname - network device interface name associated with this + =============== ================================================== + ifname network device interface name associated with this function instance - qmult - queue length multiplier for high and super speed - host_addr - MAC address of host's end of this + qmult queue length multiplier for high and super speed + host_addr MAC address of host's end of this Ethernet over USB link - dev_addr - MAC address of device's end of this + dev_addr MAC address of device's end of this Ethernet over USB link + =============== ================================================== and after creating the functions/ecm. they contain default values: qmult is 5, dev_addr and host_addr are randomly selected. @@ -82,8 +100,13 @@ Testing the ECM function Configure IP addresses of the device and the host. Then: -On the device: ping -On the host: ping +On the device:: + + ping + +On the host:: + + ping 3. ECM subset function ====================== @@ -96,13 +119,15 @@ Function-specific configfs interface The function name to use when creating the function directory is "geth". The ECM subset function provides these attributes in its function directory: - ifname - network device interface name associated with this + =============== ================================================== + ifname network device interface name associated with this function instance - qmult - queue length multiplier for high and super speed - host_addr - MAC address of host's end of this + qmult queue length multiplier for high and super speed + host_addr MAC address of host's end of this Ethernet over USB link - dev_addr - MAC address of device's end of this + dev_addr MAC address of device's end of this Ethernet over USB link + =============== ================================================== and after creating the functions/ecm. they contain default values: qmult is 5, dev_addr and host_addr are randomly selected. @@ -115,8 +140,13 @@ Testing the ECM subset function Configure IP addresses of the device and the host. Then: -On the device: ping -On the host: ping +On the device:: + + ping + +On the host:: + + ping 4. EEM function =============== @@ -129,13 +159,15 @@ Function-specific configfs interface The function name to use when creating the function directory is "eem". The EEM function provides these attributes in its function directory: - ifname - network device interface name associated with this + =============== ================================================== + ifname network device interface name associated with this function instance - qmult - queue length multiplier for high and super speed - host_addr - MAC address of host's end of this + qmult queue length multiplier for high and super speed + host_addr MAC address of host's end of this Ethernet over USB link - dev_addr - MAC address of device's end of this + dev_addr MAC address of device's end of this Ethernet over USB link + =============== ================================================== and after creating the functions/eem. they contain default values: qmult is 5, dev_addr and host_addr are randomly selected. @@ -148,8 +180,13 @@ Testing the EEM function Configure IP addresses of the device and the host. Then: -On the device: ping -On the host: ping +On the device:: + + ping + +On the host:: + + ping 5. FFS function =============== @@ -172,6 +209,7 @@ Testing the FFS function ------------------------ On the device: start the function's userspace daemon, enable the gadget + On the host: use the USB function provided by the device 6. HID function @@ -185,39 +223,43 @@ Function-specific configfs interface The function name to use when creating the function directory is "hid". The HID function provides these attributes in its function directory: - protocol - HID protocol to use - report_desc - data to be used in HID reports, except data + =============== =========================================== + protocol HID protocol to use + report_desc data to be used in HID reports, except data passed with /dev/hidg - report_length - HID report length - subclass - HID subclass to use + report_length HID report length + subclass HID subclass to use + =============== =========================================== For a keyboard the protocol and the subclass are 1, the report_length is 8, -while the report_desc is: +while the report_desc is:: -$ hd my_report_desc -00000000 05 01 09 06 a1 01 05 07 19 e0 29 e7 15 00 25 01 |..........)...%.| -00000010 75 01 95 08 81 02 95 01 75 08 81 03 95 05 75 01 |u.......u.....u.| -00000020 05 08 19 01 29 05 91 02 95 01 75 03 91 03 95 06 |....).....u.....| -00000030 75 08 15 00 25 65 05 07 19 00 29 65 81 00 c0 |u...%e....)e...| -0000003f + $ hd my_report_desc + 00000000 05 01 09 06 a1 01 05 07 19 e0 29 e7 15 00 25 01 |..........)...%.| + 00000010 75 01 95 08 81 02 95 01 75 08 81 03 95 05 75 01 |u.......u.....u.| + 00000020 05 08 19 01 29 05 91 02 95 01 75 03 91 03 95 06 |....).....u.....| + 00000030 75 08 15 00 25 65 05 07 19 00 29 65 81 00 c0 |u...%e....)e...| + 0000003f -Such a sequence of bytes can be stored to the attribute with echo: +Such a sequence of bytes can be stored to the attribute with echo:: -$ echo -ne \\x05\\x01\\x09\\x06\\xa1..... + $ echo -ne \\x05\\x01\\x09\\x06\\xa1..... Testing the HID function ------------------------ Device: + - create the gadget - connect the gadget to a host, preferably not the one used -to control the gadget + to control the gadget - run a program which writes to /dev/hidg, e.g. -a userspace program found in Documentation/usb/gadget_hid.txt: + a userspace program found in Documentation/usb/gadget_hid.txt:: -$ ./hid_gadget_test /dev/hidg0 keyboard + $ ./hid_gadget_test /dev/hidg0 keyboard Host: + - observe the keystrokes from the gadget 7. LOOPBACK function @@ -231,13 +273,16 @@ Function-specific configfs interface The function name to use when creating the function directory is "Loopback". The LOOPBACK function provides these attributes in its function directory: - qlen - depth of loopback queue - bulk_buflen - buffer length + =============== ======================= + qlen depth of loopback queue + bulk_buflen buffer length + =============== ======================= Testing the LOOPBACK function ----------------------------- device: run the gadget + host: test-usb (tools/usb/testusb.c) 8. MASS STORAGE function @@ -252,18 +297,20 @@ The function name to use when creating the function directory is "mass_storage". The MASS STORAGE function provides these attributes in its directory: files: - stall - Set to permit function to halt bulk endpoints. + =============== ============================================== + stall Set to permit function to halt bulk endpoints. Disabled on some USB devices known not to work correctly. You should set it to true. - num_buffers - Number of pipeline buffers. Valid numbers + num_buffers Number of pipeline buffers. Valid numbers are 2..4. Available only if CONFIG_USB_GADGET_DEBUG_FILES is set. + =============== ============================================== and a default lun.0 directory corresponding to SCSI LUN #0. -A new lun can be added with mkdir: +A new lun can be added with mkdir:: -$ mkdir functions/mass_storage.0/partition.5 + $ mkdir functions/mass_storage.0/partition.5 Lun numbering does not have to be continuous, except for lun #0 which is created by default. A maximum of 8 luns can be specified and they all must be @@ -273,18 +320,20 @@ although it is not mandatory. In each lun directory there are the following attribute files: - file - The path to the backing file for the LUN. + =============== ============================================== + file The path to the backing file for the LUN. Required if LUN is not marked as removable. - ro - Flag specifying access to the LUN shall be + ro Flag specifying access to the LUN shall be read-only. This is implied if CD-ROM emulation is enabled as well as when it was impossible to open "filename" in R/W mode. - removable - Flag specifying that LUN shall be indicated as + removable Flag specifying that LUN shall be indicated as being removable. - cdrom - Flag specifying that LUN shall be reported as + cdrom Flag specifying that LUN shall be reported as being a CD-ROM. - nofua - Flag specifying that FUA flag + nofua Flag specifying that FUA flag in SCSI WRITE(10,12) + =============== ============================================== Testing the MASS STORAGE function --------------------------------- @@ -304,12 +353,14 @@ Function-specific configfs interface The function name to use when creating the function directory is "midi". The MIDI function provides these attributes in its function directory: - buflen - MIDI buffer length - id - ID string for the USB MIDI adapter - in_ports - number of MIDI input ports - index - index value for the USB MIDI adapter - out_ports - number of MIDI output ports - qlen - USB read request queue length + =============== ==================================== + buflen MIDI buffer length + id ID string for the USB MIDI adapter + in_ports number of MIDI input ports + index index value for the USB MIDI adapter + out_ports number of MIDI output ports + qlen USB read request queue length + =============== ==================================== Testing the MIDI function ------------------------- @@ -317,60 +368,63 @@ Testing the MIDI function There are two cases: playing a mid from the gadget to the host and playing a mid from the host to the gadget. -1) Playing a mid from the gadget to the host -host) +1) Playing a mid from the gadget to the host: + +host:: -$ arecordmidi -l - Port Client name Port name - 14:0 Midi Through Midi Through Port-0 - 24:0 MIDI Gadget MIDI Gadget MIDI 1 -$ arecordmidi -p 24:0 from_gadget.mid + $ arecordmidi -l + Port Client name Port name + 14:0 Midi Through Midi Through Port-0 + 24:0 MIDI Gadget MIDI Gadget MIDI 1 + $ arecordmidi -p 24:0 from_gadget.mid -gadget) +gadget:: -$ aplaymidi -l - Port Client name Port name - 20:0 f_midi f_midi + $ aplaymidi -l + Port Client name Port name + 20:0 f_midi f_midi -$ aplaymidi -p 20:0 to_host.mid + $ aplaymidi -p 20:0 to_host.mid 2) Playing a mid from the host to the gadget -gadget) -$ arecordmidi -l - Port Client name Port name - 20:0 f_midi f_midi +gadget:: + + $ arecordmidi -l + Port Client name Port name + 20:0 f_midi f_midi -$ arecordmidi -p 20:0 from_host.mid + $ arecordmidi -p 20:0 from_host.mid -host) +host:: -$ aplaymidi -l - Port Client name Port name - 14:0 Midi Through Midi Through Port-0 - 24:0 MIDI Gadget MIDI Gadget MIDI 1 + $ aplaymidi -l + Port Client name Port name + 14:0 Midi Through Midi Through Port-0 + 24:0 MIDI Gadget MIDI Gadget MIDI 1 -$ aplaymidi -p24:0 to_gadget.mid + $ aplaymidi -p24:0 to_gadget.mid The from_gadget.mid should sound identical to the to_host.mid. + The from_host.id should sound identical to the to_gadget.mid. -MIDI files can be played to speakers/headphones with e.g. timidity installed +MIDI files can be played to speakers/headphones with e.g. timidity installed:: -$ aplaymidi -l - Port Client name Port name - 14:0 Midi Through Midi Through Port-0 - 24:0 MIDI Gadget MIDI Gadget MIDI 1 -128:0 TiMidity TiMidity port 0 -128:1 TiMidity TiMidity port 1 -128:2 TiMidity TiMidity port 2 -128:3 TiMidity TiMidity port 3 + $ aplaymidi -l + Port Client name Port name + 14:0 Midi Through Midi Through Port-0 + 24:0 MIDI Gadget MIDI Gadget MIDI 1 + 128:0 TiMidity TiMidity port 0 + 128:1 TiMidity TiMidity port 1 + 128:2 TiMidity TiMidity port 2 + 128:3 TiMidity TiMidity port 3 -$ aplaymidi -p 128:0 file.mid + $ aplaymidi -p 128:0 file.mid -MIDI ports can be logically connected using the aconnect utility, e.g.: +MIDI ports can be logically connected using the aconnect utility, e.g.:: -$ aconnect 24:0 128:0 # try it on the host + $ aconnect 24:0 128:0 # try it on the host After the gadget's MIDI port is connected to timidity's MIDI port, whatever is played at the gadget side with aplaymidi -l is audible @@ -387,13 +441,15 @@ Function-specific configfs interface The function name to use when creating the function directory is "ncm". The NCM function provides these attributes in its function directory: - ifname - network device interface name associated with this + =============== ================================================== + ifname network device interface name associated with this function instance - qmult - queue length multiplier for high and super speed - host_addr - MAC address of host's end of this + qmult queue length multiplier for high and super speed + host_addr MAC address of host's end of this Ethernet over USB link - dev_addr - MAC address of device's end of this + dev_addr MAC address of device's end of this Ethernet over USB link + =============== ================================================== and after creating the functions/ncm. they contain default values: qmult is 5, dev_addr and host_addr are randomly selected. @@ -406,8 +462,13 @@ Testing the NCM function Configure IP addresses of the device and the host. Then: -On the device: ping -On the host: ping +On the device:: + + ping + +On the host:: + + ping 11. OBEX function ================= @@ -429,13 +490,18 @@ There can be at most 4 ACM/generic serial/OBEX ports in the system. Testing the OBEX function ------------------------- -On device: seriald -f /dev/ttyGS -s 1024 -On host: serialc -v -p -i -a1 -s1024 \ - -t -r +On device:: + + seriald -f /dev/ttyGS -s 1024 + +On host:: + + serialc -v -p -i -a1 -s1024 \ + -t -r where seriald and serialc are Felipe's utilities found here: -https://github.com/felipebalbi/usb-tools.git master + https://github.com/felipebalbi/usb-tools.git master 12. PHONET function =================== @@ -448,8 +514,10 @@ Function-specific configfs interface The function name to use when creating the function directory is "phonet". The PHONET function provides just one attribute in its function directory: - ifname - network device interface name associated with this + =============== ================================================== + ifname network device interface name associated with this function instance + =============== ================================================== Testing the PHONET function --------------------------- @@ -464,41 +532,41 @@ These tools are required: git://git.gitorious.org/meego-cellular/phonet-utils.git -On the host: +On the host:: -$ ./phonet -a 0x10 -i usbpn0 -$ ./pnroute add 0x6c usbpn0 -$./pnroute add 0x10 usbpn0 -$ ifconfig usbpn0 up + $ ./phonet -a 0x10 -i usbpn0 + $ ./pnroute add 0x6c usbpn0 + $./pnroute add 0x10 usbpn0 + $ ifconfig usbpn0 up -On the device: +On the device:: -$ ./phonet -a 0x6c -i upnlink0 -$ ./pnroute add 0x10 upnlink0 -$ ifconfig upnlink0 up + $ ./phonet -a 0x6c -i upnlink0 + $ ./pnroute add 0x10 upnlink0 + $ ifconfig upnlink0 up -Then a test program can be used: +Then a test program can be used:: -http://www.spinics.net/lists/linux-usb/msg85690.html + http://www.spinics.net/lists/linux-usb/msg85690.html -On the device: +On the device:: -$ ./pnxmit -a 0x6c -r + $ ./pnxmit -a 0x6c -r -On the host: +On the host:: -$ ./pnxmit -a 0x10 -s 0x6c + $ ./pnxmit -a 0x10 -s 0x6c As a result some data should be sent from host to device. Then the other way round: -On the host: +On the host:: -$ ./pnxmit -a 0x10 -r + $ ./pnxmit -a 0x10 -r -On the device: +On the device:: -$ ./pnxmit -a 0x6c -s 0x10 + $ ./pnxmit -a 0x6c -s 0x10 13. RNDIS function ================== @@ -511,13 +579,15 @@ Function-specific configfs interface The function name to use when creating the function directory is "rndis". The RNDIS function provides these attributes in its function directory: - ifname - network device interface name associated with this + =============== ================================================== + ifname network device interface name associated with this function instance - qmult - queue length multiplier for high and super speed - host_addr - MAC address of host's end of this + qmult queue length multiplier for high and super speed + host_addr MAC address of host's end of this Ethernet over USB link - dev_addr - MAC address of device's end of this + dev_addr MAC address of device's end of this Ethernet over USB link + =============== ================================================== and after creating the functions/rndis. they contain default values: qmult is 5, dev_addr and host_addr are randomly selected. @@ -530,8 +600,13 @@ Testing the RNDIS function Configure IP addresses of the device and the host. Then: -On the device: ping -On the host: ping +On the device:: + + ping + +On the host:: + + ping 14. SERIAL function =================== @@ -553,15 +628,28 @@ There can be at most 4 ACM/generic serial/OBEX ports in the system. Testing the SERIAL function --------------------------- -On host: insmod usbserial - echo VID PID >/sys/bus/usb-serial/drivers/generic/new_id -On host: cat > /dev/ttyUSB -On target: cat /dev/ttyGS +On host:: + + insmod usbserial + echo VID PID >/sys/bus/usb-serial/drivers/generic/new_id + +On host:: + + cat > /dev/ttyUSB + +On target:: + + cat /dev/ttyGS then the other way round -On target: cat > /dev/ttyGS -On host: cat /dev/ttyUSB +On target:: + + cat > /dev/ttyGS + +On host:: + + cat /dev/ttyUSB 15. SOURCESINK function ======================= @@ -574,24 +662,27 @@ Function-specific configfs interface The function name to use when creating the function directory is "SourceSink". The SOURCESINK function provides these attributes in its function directory: - pattern - 0 (all zeros), 1 (mod63), 2 (none) - isoc_interval - 1..16 - isoc_maxpacket - 0 - 1023 (fs), 0 - 1024 (hs/ss) - isoc_mult - 0..2 (hs/ss only) - isoc_maxburst - 0..15 (ss only) - bulk_buflen - buffer length - bulk_qlen - depth of queue for bulk - iso_qlen - depth of queue for iso + =============== ================================== + pattern 0 (all zeros), 1 (mod63), 2 (none) + isoc_interval 1..16 + isoc_maxpacket 0 - 1023 (fs), 0 - 1024 (hs/ss) + isoc_mult 0..2 (hs/ss only) + isoc_maxburst 0..15 (ss only) + bulk_buflen buffer length + bulk_qlen depth of queue for bulk + iso_qlen depth of queue for iso + =============== ================================== Testing the SOURCESINK function ------------------------------- device: run the gadget + host: test-usb (tools/usb/testusb.c) 16. UAC1 function (legacy implementation) -================= +========================================= The function is provided by usb_f_uac1_legacy.ko module. @@ -602,12 +693,14 @@ The function name to use when creating the function directory is "uac1_legacy". The uac1 function provides these attributes in its function directory: - audio_buf_size - audio buffer size - fn_cap - capture pcm device file name - fn_cntl - control device file name - fn_play - playback pcm device file name - req_buf_size - ISO OUT endpoint request buffer size - req_count - ISO OUT endpoint request count + =============== ==================================== + audio_buf_size audio buffer size + fn_cap capture pcm device file name + fn_cntl control device file name + fn_play playback pcm device file name + req_buf_size ISO OUT endpoint request buffer size + req_count ISO OUT endpoint request count + =============== ==================================== The attributes have sane default values. @@ -615,7 +708,10 @@ Testing the UAC1 function ------------------------- device: run the gadget -host: aplay -l # should list our USB Audio Gadget + +host:: + + aplay -l # should list our USB Audio Gadget 17. UAC2 function ================= @@ -628,14 +724,16 @@ Function-specific configfs interface The function name to use when creating the function directory is "uac2". The uac2 function provides these attributes in its function directory: - c_chmask - capture channel mask - c_srate - capture sampling rate - c_ssize - capture sample size (bytes) - p_chmask - playback channel mask - p_srate - playback sampling rate - p_ssize - playback sample size (bytes) - req_number - the number of pre-allocated request for both capture - and playback + =============== ==================================================== + c_chmask capture channel mask + c_srate capture sampling rate + c_ssize capture sample size (bytes) + p_chmask playback channel mask + p_srate playback sampling rate + p_ssize playback sample size (bytes) + req_number the number of pre-allocated request for both capture + and playback + =============== ==================================================== The attributes have sane default values. @@ -648,14 +746,14 @@ host: aplay -l # should list our USB Audio Gadget This function does not require real hardware support, it just sends a stream of audio data to/from the host. In order to actually hear something at the device side, a command similar -to this must be used at the device side: +to this must be used at the device side:: -$ arecord -f dat -t wav -D hw:2,0 | aplay -D hw:0,0 & + $ arecord -f dat -t wav -D hw:2,0 | aplay -D hw:0,0 & -e.g.: +e.g.:: -$ arecord -f dat -t wav -D hw:CARD=UAC2Gadget,DEV=0 | \ -aplay -D default:CARD=OdroidU3 + $ arecord -f dat -t wav -D hw:CARD=UAC2Gadget,DEV=0 | \ + aplay -D default:CARD=OdroidU3 18. UVC function ================ @@ -668,66 +766,73 @@ Function-specific configfs interface The function name to use when creating the function directory is "uvc". The uvc function provides these attributes in its function directory: - streaming_interval - interval for polling endpoint for data transfers - streaming_maxburst - bMaxBurst for super speed companion descriptor - streaming_maxpacket - maximum packet size this endpoint is capable of - sending or receiving when this configuration is - selected + =================== ================================================ + streaming_interval interval for polling endpoint for data transfers + streaming_maxburst bMaxBurst for super speed companion descriptor + streaming_maxpacket maximum packet size this endpoint is capable of + sending or receiving when this configuration is + selected + =================== ================================================ There are also "control" and "streaming" subdirectories, each of which contain a number of their subdirectories. There are some sane defaults provided, but the user must provide the following: - control header - create in control/header, link from control/class/fs - and/or control/class/ss - streaming header - create in streaming/header, link from - streaming/class/fs and/or streaming/class/hs and/or - streaming/class/ss - format description - create in streaming/mjpeg and/or - streaming/uncompressed - frame description - create in streaming/mjpeg/ and/or in - streaming/uncompressed/ + ================== ==================================================== + control header create in control/header, link from control/class/fs + and/or control/class/ss + streaming header create in streaming/header, link from + streaming/class/fs and/or streaming/class/hs and/or + streaming/class/ss + format description create in streaming/mjpeg and/or + streaming/uncompressed + frame description create in streaming/mjpeg/ and/or in + streaming/uncompressed/ + ================== ==================================================== Each frame description contains frame interval specification, and each such specification consists of a number of lines with an inverval value -in each line. The rules stated above are best illustrated with an example: - -# mkdir functions/uvc.usb0/control/header/h -# cd functions/uvc.usb0/control/ -# ln -s header/h class/fs -# ln -s header/h class/ss -# mkdir -p functions/uvc.usb0/streaming/uncompressed/u/360p -# cat < functions/uvc.usb0/streaming/uncompressed/u/360p/dwFrameInterval -666666 -1000000 -5000000 -EOF -# cd $GADGET_CONFIGFS_ROOT -# mkdir functions/uvc.usb0/streaming/header/h -# cd functions/uvc.usb0/streaming/header/h -# ln -s ../../uncompressed/u -# cd ../../class/fs -# ln -s ../../header/h -# cd ../../class/hs -# ln -s ../../header/h -# cd ../../class/ss -# ln -s ../../header/h +in each line. The rules stated above are best illustrated with an example:: + + # mkdir functions/uvc.usb0/control/header/h + # cd functions/uvc.usb0/control/ + # ln -s header/h class/fs + # ln -s header/h class/ss + # mkdir -p functions/uvc.usb0/streaming/uncompressed/u/360p + # cat < functions/uvc.usb0/streaming/uncompressed/u/360p/dwFrameInterval + 666666 + 1000000 + 5000000 + EOF + # cd $GADGET_CONFIGFS_ROOT + # mkdir functions/uvc.usb0/streaming/header/h + # cd functions/uvc.usb0/streaming/header/h + # ln -s ../../uncompressed/u + # cd ../../class/fs + # ln -s ../../header/h + # cd ../../class/hs + # ln -s ../../header/h + # cd ../../class/ss + # ln -s ../../header/h Testing the UVC function ------------------------ -device: run the gadget, modprobe vivid +device: run the gadget, modprobe vivid:: -# uvc-gadget -u /dev/video -v /dev/video + # uvc-gadget -u /dev/video -v /dev/video where uvc-gadget is this program: -http://git.ideasonboard.org/uvc-gadget.git + http://git.ideasonboard.org/uvc-gadget.git with these patches: -http://www.spinics.net/lists/linux-usb/msg99220.html -host: luvcview -f yuv + http://www.spinics.net/lists/linux-usb/msg99220.html + +host:: + + luvcview -f yuv 19. PRINTER function ==================== @@ -740,16 +845,19 @@ Function-specific configfs interface The function name to use when creating the function directory is "printer". The printer function provides these attributes in its function directory: - pnp_string - Data to be passed to the host in pnp string - q_len - Number of requests per endpoint + ========== =========================================== + pnp_string Data to be passed to the host in pnp string + q_len Number of requests per endpoint + ========== =========================================== Testing the PRINTER function ---------------------------- The most basic testing: -device: run the gadget -# ls -l /devices/virtual/usb_printer_gadget/ +device: run the gadget:: + + # ls -l /devices/virtual/usb_printer_gadget/ should show g_printer. @@ -761,23 +869,28 @@ If udev is active, then e.g. /dev/usb/lp0 should appear. host->device transmission: -device: -# cat /dev/g_printer -host: -# cat > /dev/usb/lp0 +device:: -device->host transmission: + # cat /dev/g_printer -# cat > /dev/g_printer -host: -# cat /dev/usb/lp0 +host:: + + # cat > /dev/usb/lp0 + +device->host transmission:: + + # cat > /dev/g_printer + +host:: + + # cat /dev/usb/lp0 More advanced testing can be done with the prn_example described in Documentation/usb/gadget_printer.txt. 20. UAC1 function (virtual ALSA card, using u_audio API) -================= +======================================================== The function is provided by usb_f_uac1.ko module. It will create a virtual ALSA card and the audio streams are simply @@ -789,14 +902,16 @@ Function-specific configfs interface The function name to use when creating the function directory is "uac1". The uac1 function provides these attributes in its function directory: - c_chmask - capture channel mask - c_srate - capture sampling rate - c_ssize - capture sample size (bytes) - p_chmask - playback channel mask - p_srate - playback sampling rate - p_ssize - playback sample size (bytes) - req_number - the number of pre-allocated request for both capture - and playback + ========== ==================================================== + c_chmask capture channel mask + c_srate capture sampling rate + c_ssize capture sample size (bytes) + p_chmask playback channel mask + p_srate playback sampling rate + p_ssize playback sample size (bytes) + req_number the number of pre-allocated request for both capture + and playback + ========== ==================================================== The attributes have sane default values. @@ -809,11 +924,11 @@ host: aplay -l # should list our USB Audio Gadget This function does not require real hardware support, it just sends a stream of audio data to/from the host. In order to actually hear something at the device side, a command similar -to this must be used at the device side: +to this must be used at the device side:: -$ arecord -f dat -t wav -D hw:2,0 | aplay -D hw:0,0 & + $ arecord -f dat -t wav -D hw:2,0 | aplay -D hw:0,0 & -e.g.: +e.g.:: -$ arecord -f dat -t wav -D hw:CARD=UAC1Gadget,DEV=0 | \ -aplay -D default:CARD=OdroidU3 + $ arecord -f dat -t wav -D hw:CARD=UAC1Gadget,DEV=0 | \ + aplay -D default:CARD=OdroidU3 diff --git a/Documentation/usb/gadget_configfs.txt b/Documentation/usb/gadget_configfs.txt index b8cb38a98c19..54fb08baae22 100644 --- a/Documentation/usb/gadget_configfs.txt +++ b/Documentation/usb/gadget_configfs.txt @@ -1,11 +1,9 @@ +============================================ +Linux USB gadget configured through configfs +============================================ - - - Linux USB gadget configured through configfs - - - 25th April 2013 +25th April 2013 @@ -26,7 +24,7 @@ Linux provides a number of functions for gadgets to use. Creating a gadget means deciding what configurations there will be and which functions each configuration will provide. -Configfs (please see Documentation/filesystems/configfs/*) lends itself nicely +Configfs (please see `Documentation/filesystems/configfs/*`) lends itself nicely for the purpose of telling the kernel about the above mentioned decision. This document is about how to do it. @@ -51,44 +49,46 @@ Usage made available through configfs can be seen here: http://www.spinics.net/lists/linux-usb/msg76388.html) -$ modprobe libcomposite -$ mount none $CONFIGFS_HOME -t configfs +:: + + $ modprobe libcomposite + $ mount none $CONFIGFS_HOME -t configfs where CONFIGFS_HOME is the mount point for configfs 1. Creating the gadgets ----------------------- -For each gadget to be created its corresponding directory must be created: +For each gadget to be created its corresponding directory must be created:: -$ mkdir $CONFIGFS_HOME/usb_gadget/ + $ mkdir $CONFIGFS_HOME/usb_gadget/ -e.g.: +e.g.:: -$ mkdir $CONFIGFS_HOME/usb_gadget/g1 + $ mkdir $CONFIGFS_HOME/usb_gadget/g1 -... -... -... + ... + ... + ... -$ cd $CONFIGFS_HOME/usb_gadget/g1 + $ cd $CONFIGFS_HOME/usb_gadget/g1 -Each gadget needs to have its vendor id and product id specified: +Each gadget needs to have its vendor id and product id specified:: -$ echo > idVendor -$ echo > idProduct + $ echo > idVendor + $ echo > idProduct A gadget also needs its serial number, manufacturer and product strings. In order to have a place to store them, a strings subdirectory must be created -for each language, e.g.: +for each language, e.g.:: -$ mkdir strings/0x409 + $ mkdir strings/0x409 -Then the strings can be specified: +Then the strings can be specified:: -$ echo > strings/0x409/serialnumber -$ echo > strings/0x409/manufacturer -$ echo > strings/0x409/product + $ echo > strings/0x409/serialnumber + $ echo > strings/0x409/manufacturer + $ echo > strings/0x409/product 2. Creating the configurations ------------------------------ @@ -99,43 +99,43 @@ directories must be created: $ mkdir configs/. where can be any string which is legal in a filesystem and the - is the configuration's number, e.g.: + is the configuration's number, e.g.:: -$ mkdir configs/c.1 + $ mkdir configs/c.1 -... -... -... + ... + ... + ... Each configuration also needs its strings, so a subdirectory must be created -for each language, e.g.: +for each language, e.g.:: -$ mkdir configs/c.1/strings/0x409 + $ mkdir configs/c.1/strings/0x409 -Then the configuration string can be specified: +Then the configuration string can be specified:: -$ echo > configs/c.1/strings/0x409/configuration + $ echo > configs/c.1/strings/0x409/configuration -Some attributes can also be set for a configuration, e.g.: +Some attributes can also be set for a configuration, e.g.:: -$ echo 120 > configs/c.1/MaxPower + $ echo 120 > configs/c.1/MaxPower 3. Creating the functions ------------------------- The gadget will provide some functions, for each function its corresponding -directory must be created: +directory must be created:: -$ mkdir functions/. + $ mkdir functions/. where corresponds to one of allowed function names and instance name -is an arbitrary string allowed in a filesystem, e.g.: +is an arbitrary string allowed in a filesystem, e.g.:: -$ mkdir functions/ncm.usb0 # usb_f_ncm.ko gets loaded with request_module() + $ mkdir functions/ncm.usb0 # usb_f_ncm.ko gets loaded with request_module() -... -... -... + ... + ... + ... Each function provides its specific set of attributes, with either read-only or read-write access. Where applicable they need to be written to as @@ -149,17 +149,17 @@ At this moment a number of gadgets is created, each of which has a number of configurations specified and a number of functions available. What remains is specifying which function is available in which configuration (the same function can be used in multiple configurations). This is achieved with -creating symbolic links: +creating symbolic links:: -$ ln -s functions/. configs/. + $ ln -s functions/. configs/. -e.g.: +e.g.:: -$ ln -s functions/ncm.usb0 configs/c.1 + $ ln -s functions/ncm.usb0 configs/c.1 -... -... -... + ... + ... + ... 5. Enabling the gadget ---------------------- @@ -167,123 +167,127 @@ $ ln -s functions/ncm.usb0 configs/c.1 All the above steps serve the purpose of composing the gadget of configurations and functions. -An example directory structure might look like this: - -. -./strings -./strings/0x409 -./strings/0x409/serialnumber -./strings/0x409/product -./strings/0x409/manufacturer -./configs -./configs/c.1 -./configs/c.1/ncm.usb0 -> ../../../../usb_gadget/g1/functions/ncm.usb0 -./configs/c.1/strings -./configs/c.1/strings/0x409 -./configs/c.1/strings/0x409/configuration -./configs/c.1/bmAttributes -./configs/c.1/MaxPower -./functions -./functions/ncm.usb0 -./functions/ncm.usb0/ifname -./functions/ncm.usb0/qmult -./functions/ncm.usb0/host_addr -./functions/ncm.usb0/dev_addr -./UDC -./bcdUSB -./bcdDevice -./idProduct -./idVendor -./bMaxPacketSize0 -./bDeviceProtocol -./bDeviceSubClass -./bDeviceClass +An example directory structure might look like this:: + + . + ./strings + ./strings/0x409 + ./strings/0x409/serialnumber + ./strings/0x409/product + ./strings/0x409/manufacturer + ./configs + ./configs/c.1 + ./configs/c.1/ncm.usb0 -> ../../../../usb_gadget/g1/functions/ncm.usb0 + ./configs/c.1/strings + ./configs/c.1/strings/0x409 + ./configs/c.1/strings/0x409/configuration + ./configs/c.1/bmAttributes + ./configs/c.1/MaxPower + ./functions + ./functions/ncm.usb0 + ./functions/ncm.usb0/ifname + ./functions/ncm.usb0/qmult + ./functions/ncm.usb0/host_addr + ./functions/ncm.usb0/dev_addr + ./UDC + ./bcdUSB + ./bcdDevice + ./idProduct + ./idVendor + ./bMaxPacketSize0 + ./bDeviceProtocol + ./bDeviceSubClass + ./bDeviceClass Such a gadget must be finally enabled so that the USB host can enumerate it. -In order to enable the gadget it must be bound to a UDC (USB Device Controller). -$ echo > UDC +In order to enable the gadget it must be bound to a UDC (USB Device +Controller):: + + $ echo > UDC where is one of those found in /sys/class/udc/* -e.g.: +e.g.:: -$ echo s3c-hsotg > UDC + $ echo s3c-hsotg > UDC 6. Disabling the gadget ----------------------- -$ echo "" > UDC +:: + + $ echo "" > UDC 7. Cleaning up -------------- -Remove functions from configurations: +Remove functions from configurations:: -$ rm configs/./ + $ rm configs/./ where . specify the configuration and is -a symlink to a function being removed from the configuration, e.g.: +a symlink to a function being removed from the configuration, e.g.:: -$ rm configs/c.1/ncm.usb0 + $ rm configs/c.1/ncm.usb0 -... -... -... + ... + ... + ... -Remove strings directories in configurations +Remove strings directories in configurations: -$ rmdir configs/./strings/ + $ rmdir configs/./strings/ -e.g.: +e.g.:: -$ rmdir configs/c.1/strings/0x409 + $ rmdir configs/c.1/strings/0x409 -... -... -... + ... + ... + ... -and remove the configurations +and remove the configurations:: -$ rmdir configs/. + $ rmdir configs/. -e.g.: +e.g.:: -rmdir configs/c.1 + rmdir configs/c.1 -... -... -... + ... + ... + ... -Remove functions (function modules are not unloaded, though) +Remove functions (function modules are not unloaded, though): -$ rmdir functions/. + $ rmdir functions/. -e.g.: +e.g.:: -$ rmdir functions/ncm.usb0 + $ rmdir functions/ncm.usb0 -... -... -... + ... + ... + ... -Remove strings directories in the gadget +Remove strings directories in the gadget:: -$ rmdir strings/ + $ rmdir strings/ -e.g.: +e.g.:: -$ rmdir strings/0x409 + $ rmdir strings/0x409 -and finally remove the gadget: +and finally remove the gadget:: -$ cd .. -$ rmdir + $ cd .. + $ rmdir -e.g.: +e.g.:: -$ rmdir g1 + $ rmdir g1 @@ -305,16 +309,16 @@ configured elements. However, they are embedded in usage-specific larger structures. In the picture below there is a "cs" which contains a config_item and an "sa" which contains a configfs_attribute. -The filesystem view would be like this: +The filesystem view would be like this:: -./ -./cs (directory) - | - +--sa (file) - | - . - . - . + ./ + ./cs (directory) + | + +--sa (file) + | + . + . + . Whenever a user reads/writes the "sa" file, a function is called which accepts a struct config_item and a struct configfs_attribute. @@ -326,29 +330,31 @@ buffer), while the "store" is for modifying the file's contents (copy data from the buffer to the cs), but it is up to the implementer of the two functions to decide what they actually do. -typedef struct configured_structure cs; -typedef struct specific_attribute sa; - - sa - +----------------------------------+ - cs | (*show)(cs *, buffer); | -+-----------------+ | (*store)(cs *, buffer, length); | -| | | | -| +-------------+ | | +------------------+ | -| | struct |-|----|------>|struct | | -| | config_item | | | |configfs_attribute| | -| +-------------+ | | +------------------+ | -| | +----------------------------------+ -| data to be set | . -| | . -+-----------------+ . +:: + + typedef struct configured_structure cs; + typedef struct specific_attribute sa; + + sa + +----------------------------------+ + cs | (*show)(cs *, buffer); | + +-----------------+ | (*store)(cs *, buffer, length); | + | | | | + | +-------------+ | | +------------------+ | + | | struct |-|----|------>|struct | | + | | config_item | | | |configfs_attribute| | + | +-------------+ | | +------------------+ | + | | +----------------------------------+ + | data to be set | . + | | . + +-----------------+ . The file names are decided by the config item/group designer, while the directories in general can be named at will. A group can have a number of its default sub-groups created automatically. For more information on configfs please see -Documentation/filesystems/configfs/*. +`Documentation/filesystems/configfs/*`. The concepts described above translate to USB gadgets like this: diff --git a/Documentation/usb/gadget_hid.txt b/Documentation/usb/gadget_hid.txt index 7a0fb8e16e27..098d563040cc 100644 --- a/Documentation/usb/gadget_hid.txt +++ b/Documentation/usb/gadget_hid.txt @@ -1,28 +1,31 @@ - - Linux USB HID gadget driver +=========================== +Linux USB HID gadget driver +=========================== Introduction +============ - The HID Gadget driver provides emulation of USB Human Interface - Devices (HID). The basic HID handling is done in the kernel, - and HID reports can be sent/received through I/O on the - /dev/hidgX character devices. +The HID Gadget driver provides emulation of USB Human Interface +Devices (HID). The basic HID handling is done in the kernel, +and HID reports can be sent/received through I/O on the +/dev/hidgX character devices. - For more details about HID, see the developer page on - http://www.usb.org/developers/hidpage/ +For more details about HID, see the developer page on +http://www.usb.org/developers/hidpage/ Configuration +============= - g_hid is a platform driver, so to use it you need to add - struct platform_device(s) to your platform code defining the - HID function descriptors you want to use - E.G. something - like: +g_hid is a platform driver, so to use it you need to add +struct platform_device(s) to your platform code defining the +HID function descriptors you want to use - E.G. something +like:: -#include -#include + #include + #include -/* hid descriptor for a keyboard */ -static struct hidg_func_descriptor my_hid_data = { + /* hid descriptor for a keyboard */ + static struct hidg_func_descriptor my_hid_data = { .subclass = 0, /* No subclass */ .protocol = 1, /* Keyboard */ .report_length = 8, @@ -61,85 +64,87 @@ static struct hidg_func_descriptor my_hid_data = { 0x81, 0x00, /* INPUT (Data,Ary,Abs) */ 0xc0 /* END_COLLECTION */ } -}; + }; -static struct platform_device my_hid = { + static struct platform_device my_hid = { .name = "hidg", .id = 0, .num_resources = 0, .resource = 0, .dev.platform_data = &my_hid_data, -}; + }; - You can add as many HID functions as you want, only limited by - the amount of interrupt endpoints your gadget driver supports. +You can add as many HID functions as you want, only limited by +the amount of interrupt endpoints your gadget driver supports. Configuration with configfs +=========================== - Instead of adding fake platform devices and drivers in order to pass - some data to the kernel, if HID is a part of a gadget composed with - configfs the hidg_func_descriptor.report_desc is passed to the kernel - by writing the appropriate stream of bytes to a configfs attribute. +Instead of adding fake platform devices and drivers in order to pass +some data to the kernel, if HID is a part of a gadget composed with +configfs the hidg_func_descriptor.report_desc is passed to the kernel +by writing the appropriate stream of bytes to a configfs attribute. Send and receive HID reports +============================ - HID reports can be sent/received using read/write on the - /dev/hidgX character devices. See below for an example program - to do this. +HID reports can be sent/received using read/write on the +/dev/hidgX character devices. See below for an example program +to do this. - hid_gadget_test is a small interactive program to test the HID - gadget driver. To use, point it at a hidg device and set the - device type (keyboard / mouse / joystick) - E.G.: +hid_gadget_test is a small interactive program to test the HID +gadget driver. To use, point it at a hidg device and set the +device type (keyboard / mouse / joystick) - E.G.:: - # hid_gadget_test /dev/hidg0 keyboard + # hid_gadget_test /dev/hidg0 keyboard - You are now in the prompt of hid_gadget_test. You can type any - combination of options and values. Available options and - values are listed at program start. In keyboard mode you can - send up to six values. +You are now in the prompt of hid_gadget_test. You can type any +combination of options and values. Available options and +values are listed at program start. In keyboard mode you can +send up to six values. - For example type: g i s t r --left-shift +For example type: g i s t r --left-shift - Hit return and the corresponding report will be sent by the - HID gadget. +Hit return and the corresponding report will be sent by the +HID gadget. - Another interesting example is the caps lock test. Type - --caps-lock and hit return. A report is then sent by the - gadget and you should receive the host answer, corresponding - to the caps lock LED status. +Another interesting example is the caps lock test. Type +--caps-lock and hit return. A report is then sent by the +gadget and you should receive the host answer, corresponding +to the caps lock LED status:: - --caps-lock - recv report:2 + --caps-lock + recv report:2 - With this command: +With this command:: - # hid_gadget_test /dev/hidg1 mouse + # hid_gadget_test /dev/hidg1 mouse - You can test the mouse emulation. Values are two signed numbers. +You can test the mouse emulation. Values are two signed numbers. -Sample code +Sample code:: -/* hid_gadget_test */ + /* hid_gadget_test */ -#include -#include -#include -#include -#include -#include -#include -#include -#include + #include + #include + #include + #include + #include + #include + #include + #include + #include -#define BUF_LEN 512 + #define BUF_LEN 512 -struct options { + struct options { const char *opt; unsigned char val; -}; + }; -static struct options kmod[] = { + static struct options kmod[] = { {.opt = "--left-ctrl", .val = 0x01}, {.opt = "--right-ctrl", .val = 0x10}, {.opt = "--left-shift", .val = 0x02}, @@ -149,9 +154,9 @@ static struct options kmod[] = { {.opt = "--left-meta", .val = 0x08}, {.opt = "--right-meta", .val = 0x80}, {.opt = NULL} -}; + }; -static struct options kval[] = { + static struct options kval[] = { {.opt = "--return", .val = 0x28}, {.opt = "--esc", .val = 0x29}, {.opt = "--bckspc", .val = 0x2a}, @@ -183,10 +188,10 @@ static struct options kval[] = { {.opt = "--up", .val = 0x52}, {.opt = "--num-lock", .val = 0x53}, {.opt = NULL} -}; + }; -int keyboard_fill_report(char report[8], char buf[BUF_LEN], int *hold) -{ + int keyboard_fill_report(char report[8], char buf[BUF_LEN], int *hold) + { char *tok = strtok(buf, " "); int key = 0; int i = 0; @@ -229,17 +234,17 @@ int keyboard_fill_report(char report[8], char buf[BUF_LEN], int *hold) fprintf(stderr, "unknown option: %s\n", tok); } return 8; -} + } -static struct options mmod[] = { + static struct options mmod[] = { {.opt = "--b1", .val = 0x01}, {.opt = "--b2", .val = 0x02}, {.opt = "--b3", .val = 0x04}, {.opt = NULL} -}; + }; -int mouse_fill_report(char report[8], char buf[BUF_LEN], int *hold) -{ + int mouse_fill_report(char report[8], char buf[BUF_LEN], int *hold) + { char *tok = strtok(buf, " "); int mvt = 0; int i = 0; @@ -274,9 +279,9 @@ int mouse_fill_report(char report[8], char buf[BUF_LEN], int *hold) fprintf(stderr, "unknown option: %s\n", tok); } return 3; -} + } -static struct options jmod[] = { + static struct options jmod[] = { {.opt = "--b1", .val = 0x10}, {.opt = "--b2", .val = 0x20}, {.opt = "--b3", .val = 0x40}, @@ -287,10 +292,10 @@ static struct options jmod[] = { {.opt = "--hat4", .val = 0x03}, {.opt = "--hatneutral", .val = 0x04}, {.opt = NULL} -}; + }; -int joystick_fill_report(char report[8], char buf[BUF_LEN], int *hold) -{ + int joystick_fill_report(char report[8], char buf[BUF_LEN], int *hold) + { char *tok = strtok(buf, " "); int mvt = 0; int i = 0; @@ -326,10 +331,10 @@ int joystick_fill_report(char report[8], char buf[BUF_LEN], int *hold) fprintf(stderr, "unknown option: %s\n", tok); } return 4; -} + } -void print_options(char c) -{ + void print_options(char c) + { int i = 0; if (c == 'k') { @@ -358,10 +363,10 @@ void print_options(char c) " three signed numbers\n" "--quit to close\n"); } -} + } -int main(int argc, const char *argv[]) -{ + int main(int argc, const char *argv[]) + { const char *filename = NULL; int fd = 0; char buf[BUF_LEN]; @@ -449,4 +454,4 @@ int main(int argc, const char *argv[]) close(fd); return 0; -} + } diff --git a/Documentation/usb/gadget_multi.txt b/Documentation/usb/gadget_multi.txt index b3146dd7aa43..9806b55af301 100644 --- a/Documentation/usb/gadget_multi.txt +++ b/Documentation/usb/gadget_multi.txt @@ -1,6 +1,9 @@ - -*- org -*- +============================== +Multifunction Composite Gadget +============================== -* Overview +Overview +======== The Multifunction Composite Gadget (or g_multi) is a composite gadget that makes extensive use of the composite framework to provide @@ -17,13 +20,15 @@ have two configurations -- one with RNDIS and another with CDC ECM[3]. Please note that if you use non-standard configuration (that is enable CDC ECM) you may need to change vendor and/or product ID. -* Host drivers +Host drivers +============ To make use of the gadget one needs to make it work on host side -- without that there's no hope of achieving anything with the gadget. As one might expect, things one need to do very from system to system. -** Linux host drivers +Linux host drivers +------------------ Since the gadget uses standard composite framework and appears as such to Linux host it does not need any additional drivers on Linux host @@ -34,11 +39,13 @@ This is also true for two configuration set-up with RNDIS configuration being the first one. Linux host will use the second configuration with CDC ECM which should work better under Linux. -** Windows host drivers +Windows host drivers +-------------------- For the gadget to work under Windows two conditions have to be met: -*** Detecting as composite gadget +Detecting as composite gadget +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ First of all, Windows need to detect the gadget as an USB composite gadget which on its own have some conditions[4]. If they are met, @@ -53,7 +60,8 @@ The only thing to worry is that the gadget has to have a single configuration so a dual RNDIS and CDC ECM gadget won't work unless you create a proper INF -- and of course, if you do submit it! -*** Installing drivers for each function +Installing drivers for each function +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ The other, trickier thing is making Windows install drivers for each individual function. @@ -63,7 +71,8 @@ implementing USB Mass Storage class and selects appropriate driver. Things are harder with RDNIS and CDC ACM. -**** RNDIS +RNDIS +..... To make Windows select RNDIS drivers for the first function in the gadget, one needs to use the [[file:linux.inf]] file provided with this @@ -75,11 +84,13 @@ RNDIS was not the first interface. You do not need to worry abut it unless you are trying to develop your own gadget in which case watch out for this bug. -**** CDC ACM +CDC ACM +....... Similarly, [[file:linux-cdc-acm.inf]] is provided for CDC ACM. -**** Customising the gadget +Customising the gadget +...................... If you intend to hack the g_multi gadget be advised that rearranging functions will obviously change interface numbers for each of the @@ -97,14 +108,16 @@ things don't work as intended before realising Windows have cached some drivers information (changing USB port may sometimes help plus you might try using USBDeview[8] to remove the phantom device). -**** INF testing +INF testing +........... Provided INF files have been tested on Windows XP SP3, Windows Vista and Windows 7, all 32-bit versions. It should work on 64-bit versions as well. It most likely won't work on Windows prior to Windows XP SP2. -** Other systems +Other systems +------------- At this moment, drivers for any other systems have not been tested. Knowing how MacOS is based on BSD and BSD is an Open Source it is @@ -115,7 +128,8 @@ For more exotic systems I have even less to say... Any testing and drivers *are* *welcome*! -* Authors +Authors +======= This document has been written by Michal Nazarewicz ([[mailto:mina86@mina86.com]]). INF files have been hacked with @@ -124,7 +138,8 @@ Xiaofan Chen ([[mailto:xiaofanc@gmail.com]]) basing on the MS RNDIS template[9], Microchip's CDC ACM INF file and David Brownell's ([[mailto:dbrownell@users.sourceforge.net]]) original INF files. -* Footnotes +Footnotes +========= [1] Remote Network Driver Interface Specification, [[http://msdn.microsoft.com/en-us/library/ee484414.aspx]]. diff --git a/Documentation/usb/gadget_printer.txt b/Documentation/usb/gadget_printer.txt index ad995bf0db41..5e5516c69075 100644 --- a/Documentation/usb/gadget_printer.txt +++ b/Documentation/usb/gadget_printer.txt @@ -1,12 +1,14 @@ +=============================== +Linux USB Printer Gadget Driver +=============================== - Linux USB Printer Gadget Driver - 06/04/2007 +06/04/2007 - Copyright (C) 2007 Craig W. Nadler +Copyright (C) 2007 Craig W. Nadler -GENERAL +General ======= This driver may be used if you are writing printer firmware using Linux as @@ -29,52 +31,60 @@ user space firmware can read or write this status byte using a device file -HOWTO USE THIS DRIVER +Howto Use This Driver ===================== To load the USB device controller driver and the printer gadget driver. The -following example uses the Netchip 2280 USB device controller driver: +following example uses the Netchip 2280 USB device controller driver:: -modprobe net2280 -modprobe g_printer + modprobe net2280 + modprobe g_printer The follow command line parameter can be used when loading the printer gadget (ex: modprobe g_printer idVendor=0x0525 idProduct=0xa4a8 ): -idVendor - This is the Vendor ID used in the device descriptor. The default is +idVendor + This is the Vendor ID used in the device descriptor. The default is the Netchip vendor id 0x0525. YOU MUST CHANGE TO YOUR OWN VENDOR ID BEFORE RELEASING A PRODUCT. If you plan to release a product and don't already have a Vendor ID please see www.usb.org for details on how to get one. -idProduct - This is the Product ID used in the device descriptor. The default +idProduct + This is the Product ID used in the device descriptor. The default is 0xa4a8, you should change this to an ID that's not used by any of your other USB products if you have any. It would be a good idea to start numbering your products starting with say 0x0001. -bcdDevice - This is the version number of your product. It would be a good idea +bcdDevice + This is the version number of your product. It would be a good idea to put your firmware version here. -iManufacturer - A string containing the name of the Vendor. +iManufacturer + A string containing the name of the Vendor. -iProduct - A string containing the Product Name. +iProduct + A string containing the Product Name. -iSerialNum - A string containing the Serial Number. This should be changed for +iSerialNum + A string containing the Serial Number. This should be changed for each unit of your product. -iPNPstring - The PNP ID string used for this printer. You will want to set +iPNPstring + The PNP ID string used for this printer. You will want to set either on the command line or hard code the PNP ID string used for your printer product. -qlen - The number of 8k buffers to use per endpoint. The default is 10, you +qlen + The number of 8k buffers to use per endpoint. The default is 10, you should tune this for your product. You may also want to tune the size of each buffer for your product. -USING THE EXAMPLE CODE +Using The Example Code ====================== This example code talks to stdout, instead of a print engine. @@ -82,22 +92,23 @@ This example code talks to stdout, instead of a print engine. To compile the test code below: 1) save it to a file called prn_example.c -2) compile the code with the follow command: +2) compile the code with the follow command:: + gcc prn_example.c -o prn_example -To read printer data from the host to stdout: +To read printer data from the host to stdout:: # prn_example -read_data -To write printer data from a file (data_file) to the host: +To write printer data from a file (data_file) to the host:: # cat data_file | prn_example -write_data -To get the current printer status for the gadget driver: +To get the current printer status for the gadget driver::: # prn_example -get_status @@ -107,60 +118,62 @@ To get the current printer status for the gadget driver: Printer OK -To set printer to Selected/On-line: +To set printer to Selected/On-line:: # prn_example -selected -To set printer to Not Selected/Off-line: +To set printer to Not Selected/Off-line:: # prn_example -not_selected -To set paper status to paper out: +To set paper status to paper out:: # prn_example -paper_out -To set paper status to paper loaded: +To set paper status to paper loaded:: # prn_example -paper_loaded -To set error status to printer OK: +To set error status to printer OK:: # prn_example -no_error -To set error status to ERROR: +To set error status to ERROR:: # prn_example -error -EXAMPLE CODE +Example Code ============ +:: + -#include -#include -#include -#include -#include -#include + #include + #include + #include + #include + #include + #include -#define PRINTER_FILE "/dev/g_printer" -#define BUF_SIZE 512 + #define PRINTER_FILE "/dev/g_printer" + #define BUF_SIZE 512 -/* - * 'usage()' - Show program usage. - */ + /* + * 'usage()' - Show program usage. + */ -static void -usage(const char *option) /* I - Option string or NULL */ -{ + static void + usage(const char *option) /* I - Option string or NULL */ + { if (option) { fprintf(stderr,"prn_example: Unknown option \"%s\"!\n", option); @@ -186,12 +199,12 @@ usage(const char *option) /* I - Option string or NULL */ fputs("\n\n", stderr); exit(1); -} + } -static int -read_printer_data() -{ + static int + read_printer_data() + { struct pollfd fd[1]; /* Open device file for printer gadget. */ @@ -236,12 +249,12 @@ read_printer_data() close(fd[0].fd); return 0; -} + } -static int -write_printer_data() -{ + static int + write_printer_data() + { struct pollfd fd[1]; /* Open device file for printer gadget. */ @@ -295,12 +308,12 @@ write_printer_data() close(fd[0].fd); return 0; -} + } -static int -read_NB_printer_data() -{ + static int + read_NB_printer_data() + { int fd; static char buf[BUF_SIZE]; int bytes_read; @@ -329,12 +342,12 @@ read_NB_printer_data() close(fd); return 0; -} + } -static int -get_printer_status() -{ + static int + get_printer_status() + { int retval; int fd; @@ -357,12 +370,12 @@ get_printer_status() close(fd); return(retval); -} + } -static int -set_printer_status(unsigned char buf, int clear_printer_status_bit) -{ + static int + set_printer_status(unsigned char buf, int clear_printer_status_bit) + { int retval; int fd; @@ -397,12 +410,12 @@ set_printer_status(unsigned char buf, int clear_printer_status_bit) close(fd); return 0; -} + } -static int -display_printer_status() -{ + static int + display_printer_status() + { char printer_status; printer_status = get_printer_status(); @@ -429,12 +442,12 @@ display_printer_status() } return(0); -} + } -int -main(int argc, char *argv[]) -{ + int + main(int argc, char *argv[]) + { int i; /* Looping var */ int retval = 0; @@ -507,4 +520,4 @@ main(int argc, char *argv[]) } exit(retval); -} + } diff --git a/Documentation/usb/gadget_serial.txt b/Documentation/usb/gadget_serial.txt index d1def3186782..dce8bc1fb1f2 100644 --- a/Documentation/usb/gadget_serial.txt +++ b/Documentation/usb/gadget_serial.txt @@ -1,7 +1,10 @@ +=============================== +Linux Gadget Serial Driver v2.0 +=============================== - Linux Gadget Serial Driver v2.0 - 11/20/2004 - (updated 8-May-2008 for v2.3) +11/20/2004 + +(updated 8-May-2008 for v2.3) License and Disclaimer @@ -56,7 +59,7 @@ hardware; for example, a PDA, an embedded Linux system, or a PC with a USB development card. The gadget serial driver talks over USB to either a CDC ACM driver -or a generic USB serial driver running on a host PC. +or a generic USB serial driver running on a host PC:: Host -------------------------------------- @@ -112,11 +115,11 @@ configuring the kernel. Then rebuild and install the kernel or modules. Then you must load the gadget serial driver. To load it as an -ACM device (recommended for interoperability), do this: +ACM device (recommended for interoperability), do this:: modprobe g_serial -To load it as a vendor specific bulk in/out device, do this: +To load it as a vendor specific bulk in/out device, do this:: modprobe g_serial use_acm=0 @@ -127,7 +130,7 @@ desired. Your system should use mdev (from busybox) or udev to make the device nodes. After this gadget driver has been set up you should -then see a /dev/ttyGS0 node: +then see a /dev/ttyGS0 node:: # ls -l /dev/ttyGS0 | cat crw-rw---- 1 root root 253, 0 May 8 14:10 /dev/ttyGS0 @@ -187,24 +190,24 @@ support". Once the gadget serial driver is loaded and the USB device connected to the Linux host with a USB cable, the host system should recognize -the gadget serial device. For example, the command +the gadget serial device. For example, the command:: cat /sys/kernel/debug/usb/devices -should show something like this: - -T: Bus=01 Lev=01 Prnt=01 Port=01 Cnt=02 Dev#= 5 Spd=480 MxCh= 0 -D: Ver= 2.00 Cls=02(comm.) Sub=00 Prot=00 MxPS=64 #Cfgs= 1 -P: Vendor=0525 ProdID=a4a7 Rev= 2.01 -S: Manufacturer=Linux 2.6.8.1 with net2280 -S: Product=Gadget Serial -S: SerialNumber=0 -C:* #Ifs= 2 Cfg#= 2 Atr=c0 MxPwr= 2mA -I: If#= 0 Alt= 0 #EPs= 1 Cls=02(comm.) Sub=02 Prot=01 Driver=acm -E: Ad=83(I) Atr=03(Int.) MxPS= 8 Ivl=32ms -I: If#= 1 Alt= 0 #EPs= 2 Cls=0a(data ) Sub=00 Prot=00 Driver=acm -E: Ad=81(I) Atr=02(Bulk) MxPS= 512 Ivl=0ms -E: Ad=02(O) Atr=02(Bulk) MxPS= 512 Ivl=0ms +should show something like this::: + + T: Bus=01 Lev=01 Prnt=01 Port=01 Cnt=02 Dev#= 5 Spd=480 MxCh= 0 + D: Ver= 2.00 Cls=02(comm.) Sub=00 Prot=00 MxPS=64 #Cfgs= 1 + P: Vendor=0525 ProdID=a4a7 Rev= 2.01 + S: Manufacturer=Linux 2.6.8.1 with net2280 + S: Product=Gadget Serial + S: SerialNumber=0 + C:* #Ifs= 2 Cfg#= 2 Atr=c0 MxPwr= 2mA + I: If#= 0 Alt= 0 #EPs= 1 Cls=02(comm.) Sub=02 Prot=01 Driver=acm + E: Ad=83(I) Atr=03(Int.) MxPS= 8 Ivl=32ms + I: If#= 1 Alt= 0 #EPs= 2 Cls=0a(data ) Sub=00 Prot=00 Driver=acm + E: Ad=81(I) Atr=02(Bulk) MxPS= 512 Ivl=0ms + E: Ad=02(O) Atr=02(Bulk) MxPS= 512 Ivl=0ms If the host side Linux system is configured properly, the ACM driver should be loaded automatically. The command "lsmod" should show the @@ -219,29 +222,29 @@ Serial Converter support", and for the "USB Generic Serial Driver". Once the gadget serial driver is loaded and the USB device connected to the Linux host with a USB cable, the host system should recognize -the gadget serial device. For example, the command +the gadget serial device. For example, the command:: cat /sys/kernel/debug/usb/devices -should show something like this: +should show something like this::: -T: Bus=01 Lev=01 Prnt=01 Port=01 Cnt=02 Dev#= 6 Spd=480 MxCh= 0 -D: Ver= 2.00 Cls=ff(vend.) Sub=00 Prot=00 MxPS=64 #Cfgs= 1 -P: Vendor=0525 ProdID=a4a6 Rev= 2.01 -S: Manufacturer=Linux 2.6.8.1 with net2280 -S: Product=Gadget Serial -S: SerialNumber=0 -C:* #Ifs= 1 Cfg#= 1 Atr=c0 MxPwr= 2mA -I: If#= 0 Alt= 0 #EPs= 2 Cls=0a(data ) Sub=00 Prot=00 Driver=serial -E: Ad=81(I) Atr=02(Bulk) MxPS= 512 Ivl=0ms -E: Ad=02(O) Atr=02(Bulk) MxPS= 512 Ivl=0ms + T: Bus=01 Lev=01 Prnt=01 Port=01 Cnt=02 Dev#= 6 Spd=480 MxCh= 0 + D: Ver= 2.00 Cls=ff(vend.) Sub=00 Prot=00 MxPS=64 #Cfgs= 1 + P: Vendor=0525 ProdID=a4a6 Rev= 2.01 + S: Manufacturer=Linux 2.6.8.1 with net2280 + S: Product=Gadget Serial + S: SerialNumber=0 + C:* #Ifs= 1 Cfg#= 1 Atr=c0 MxPwr= 2mA + I: If#= 0 Alt= 0 #EPs= 2 Cls=0a(data ) Sub=00 Prot=00 Driver=serial + E: Ad=81(I) Atr=02(Bulk) MxPS= 512 Ivl=0ms + E: Ad=02(O) Atr=02(Bulk) MxPS= 512 Ivl=0ms You must load the usbserial driver and explicitly set its parameters -to configure it to recognize the gadget serial device, like this: +to configure it to recognize the gadget serial device, like this:: echo 0x0525 0xA4A6 >/sys/bus/usb-serial/drivers/generic/new_id -The legacy way is to use module parameters: +The legacy way is to use module parameters:: modprobe usbserial vendor=0x0525 product=0xA4A6 diff --git a/Documentation/usb/iuu_phoenix.txt b/Documentation/usb/iuu_phoenix.txt index e5f048067da4..b76268728450 100644 --- a/Documentation/usb/iuu_phoenix.txt +++ b/Documentation/usb/iuu_phoenix.txt @@ -1,5 +1,6 @@ +============================= Infinity Usb Unlimited Readme ------------------------------ +============================= Hi all, @@ -19,7 +20,8 @@ have his own device file(/dev/ttyUSB0,/dev/ttyUSB1,...) -How to tune the reader speed ? +How to tune the reader speed? +============================= A few parameters can be used at load time To use parameters, just unload the module if it is @@ -27,26 +29,33 @@ How to tune the reader speed ? In case of prebuilt module, use the command insmod iuu_phoenix param=value. - Example: + Example:: - modprobe iuu_phoenix clockmode=3 + modprobe iuu_phoenix clockmode=3 The parameters are: - parm: clockmode:1=3Mhz579,2=3Mhz680,3=6Mhz (int) - parm: boost:overclock boost percent 100 to 500 (int) - parm: cdmode:Card detect mode 0=none, 1=CD, 2=!CD, 3=DSR, 4=!DSR, 5=CTS, 6=!CTS, 7=RING, 8=!RING (int) - parm: xmas:xmas color enabled or not (bool) - parm: debug:Debug enabled or not (bool) +clockmode: + 1=3Mhz579,2=3Mhz680,3=6Mhz (int) +boost: + overclock boost percent 100 to 500 (int) +cdmode: + Card detect mode + 0=none, 1=CD, 2=!CD, 3=DSR, 4=!DSR, 5=CTS, 6=!CTS, 7=RING, 8=!RING (int) +xmas: + xmas color enabled or not (bool) +debug: + Debug enabled or not (bool) - clockmode will provide 3 different base settings commonly adopted by different software: - 1. 3Mhz579 + + 1. 3Mhz579 2. 3Mhz680 3. 6Mhz - boost provide a way to overclock the reader ( my favorite :-) ) - For example to have best performance than a simple clockmode=3, try this: + For example to have best performance than a simple clockmode=3, try this:: modprobe boost=195 @@ -66,7 +75,8 @@ How to tune the reader speed ? - debug will produce a lot of debugging messages... - Last notes: +Last notes +========== Don't worry about the serial settings, the serial emulation is an abstraction, so use any speed or parity setting will diff --git a/Documentation/usb/mass-storage.txt b/Documentation/usb/mass-storage.txt index e89803a5a960..d181b47c3cb6 100644 --- a/Documentation/usb/mass-storage.txt +++ b/Documentation/usb/mass-storage.txt @@ -1,4 +1,9 @@ -* Overview +========================= +Mass Storage Gadget (MSG) +========================= + +Overview +======== Mass Storage Gadget (or MSG) acts as a USB Mass Storage device, appearing to the host as a disk or a CD-ROM drive. It supports @@ -24,7 +29,8 @@ (which is no longer included in Linux). It will talk only briefly about how to use MSF within composite gadgets. -* Module parameters +Module parameters +================= The mass storage gadget accepts the following mass storage specific module parameters: @@ -146,7 +152,8 @@ - iProduct -- USB Product string (string) - iSerialNumber -- SerialNumber string (sting) -* sysfs entries +sysfs entries +============= For each logical unit, the gadget creates a directory in the sysfs hierarchy. Inside of it the following three files are created: @@ -177,7 +184,8 @@ Other then those, as usual, the values of module parameters can be read from /sys/module/g_mass_storage/parameters/* files. -* Other gadgets using mass storage function +Other gadgets using mass storage function +========================================= The Mass Storage Gadget uses the Mass Storage Function to handle mass storage protocol. As a composite function, MSF may be used by @@ -193,7 +201,8 @@ may take a look at mass_storage.c, acm_ms.c and multi.c (sorted by complexity). -* Relation to file storage gadget +Relation to file storage gadget +=============================== The Mass Storage Function and thus the Mass Storage Gadget has been based on the File Storage Gadget. The difference between the two is diff --git a/Documentation/usb/misc_usbsevseg.txt b/Documentation/usb/misc_usbsevseg.txt index 0f6be4f9930b..6274aee083ed 100644 --- a/Documentation/usb/misc_usbsevseg.txt +++ b/Documentation/usb/misc_usbsevseg.txt @@ -1,4 +1,7 @@ +============================= USB 7-Segment Numeric Display +============================= + Manufactured by Delcom Engineering Device Information @@ -13,9 +16,13 @@ Device Modes ------------ By default, the driver assumes the display is only 6 characters The mode for 6 characters is: + MSB 0x06; LSB 0x3f + For the 8 character display: + MSB 0x08; LSB 0xff + The device can accept "text" either in raw, hex, or ascii textmode. raw controls each segment manually, hex expects a value between 0-15 per character, @@ -42,5 +49,3 @@ Device Operation To set multiple decimals points sum up each power. For example, to set the 0th and 3rd decimal place echo 1001 > /sys/bus/usb/.../decimals - - diff --git a/Documentation/usb/mtouchusb.txt b/Documentation/usb/mtouchusb.txt index a91adb26ea7b..d1111b74bf75 100644 --- a/Documentation/usb/mtouchusb.txt +++ b/Documentation/usb/mtouchusb.txt @@ -1,19 +1,27 @@ -CHANGES +================ +mtouchusb driver +================ + +Changes +======= - 0.3 - Created based off of scanner & INSTALL from the original touchscreen driver on freecode (http://freecode.com/projects/3mtouchscreendriver) - Amended for linux-2.4.18, then 2.4.19 - 0.5 - Complete rewrite using Linux Input in 2.6.3 - Unfortunately no calibration support at this time + Unfortunately no calibration support at this time - 1.4 - Multiple changes to support the EXII 5000UC and house cleaning - Changed reset from standard USB dev reset to vendor reset - Changed data sent to host from compensated to raw coordinates - Eliminated vendor/product module params - Performed multiple successful tests with an EXII-5010UC + Changed reset from standard USB dev reset to vendor reset + Changed data sent to host from compensated to raw coordinates + Eliminated vendor/product module params + Performed multiple successful tests with an EXII-5010UC + +Supported Hardware +================== -SUPPORTED HARDWARE: +:: All controllers have the Vendor: 0x0596 & Product: 0x0001 @@ -29,9 +37,10 @@ SUPPORTED HARDWARE: USB Capacitive - Black Case EXII-5030UC USB Capacitive - No Case EXII-5050UC -DRIVER NOTES: +Driver Notes +============ -Installation is simple, you only need to add Linux Input, Linux USB, and the +Installation is simple, you only need to add Linux Input, Linux USB, and the driver to the kernel. The driver can also be optionally built as a module. This driver appears to be one of possible 2 Linux USB Input Touchscreen @@ -49,24 +58,27 @@ The controller screen resolution is now 0 to 16384 for both X and Y reporting the raw touch data. This is the same for the old and new capacitive USB controllers. -Perhaps at some point an abstract function will be placed into evdev so -generic functions like calibrations, resets, and vendor information can be +Perhaps at some point an abstract function will be placed into evdev so +generic functions like calibrations, resets, and vendor information can be requested from the userspace (And the drivers would handle the vendor specific tasks). -TODO: +TODO +==== Implement a control urb again to handle requests to and from the device such as calibration, etc once/if it becomes available. -DISCLAIMER: +Disclaimer +========== -I am not a MicroTouch/3M employee, nor have I ever been. 3M does not support +I am not a MicroTouch/3M employee, nor have I ever been. 3M does not support this driver! If you want touch drivers only supported within X, please go to: http://www.3m.com/3MTouchSystems/ -THANKS: +Thanks +====== A huge thank you to 3M Touch Systems for the EXII-5010UC controllers for testing! diff --git a/Documentation/usb/ohci.txt b/Documentation/usb/ohci.txt index 99320d9fa523..bb3c49719e6b 100644 --- a/Documentation/usb/ohci.txt +++ b/Documentation/usb/ohci.txt @@ -1,3 +1,7 @@ +==== +OHCI +==== + 23-Aug-2002 The "ohci-hcd" driver is a USB Host Controller Driver (HCD) that is derived @@ -29,4 +33,3 @@ work on while the OS is getting around to the relevant IRQ processing. - David Brownell - diff --git a/Documentation/usb/rio.txt b/Documentation/usb/rio.txt index aee715af7db7..ca9adcf56355 100644 --- a/Documentation/usb/rio.txt +++ b/Documentation/usb/rio.txt @@ -1,72 +1,80 @@ +============ +Diamonds Rio +============ + Copyright (C) 1999, 2000 Bruce Tenison + Portions Copyright (C) 1999, 2000 David Nelson + Thanks to David Nelson for guidance and the usage of the scanner.txt and scanner.c files to model our driver and this informative file. Mar. 2, 2000 -CHANGES +Changes +======= - Initial Revision -OVERVIEW +Overview +======== This README will address issues regarding how to configure the kernel -to access a RIO 500 mp3 player. +to access a RIO 500 mp3 player. Before I explain how to use this to access the Rio500 please be warned: -W A R N I N G: --------------- +.. warning:: -Please note that this software is still under development. The authors -are in no way responsible for any damage that may occur, no matter how -inconsequential. + Please note that this software is still under development. The authors + are in no way responsible for any damage that may occur, no matter how + inconsequential. It seems that the Rio has a problem when sending .mp3 with low batteries. I suggest when the batteries are low and you want to transfer stuff that you replace it with a fresh one. In my case, what happened is I lost two 16kb blocks (they are no longer usable to store information to it). But I don't -know if that's normal or not; it could simply be a problem with the flash +know if that's normal or not; it could simply be a problem with the flash memory. -In an extreme case, I left my Rio playing overnight and the batteries wore -down to nothing and appear to have corrupted the flash memory. My RIO -needed to be replaced as a result. Diamond tech support is aware of the -problem. Do NOT allow your batteries to wear down to nothing before -changing them. It appears RIO 500 firmware does not handle low battery -power well at all. +In an extreme case, I left my Rio playing overnight and the batteries wore +down to nothing and appear to have corrupted the flash memory. My RIO +needed to be replaced as a result. Diamond tech support is aware of the +problem. Do NOT allow your batteries to wear down to nothing before +changing them. It appears RIO 500 firmware does not handle low battery +power well at all. -On systems with OHCI controllers, the kernel OHCI code appears to have -power on problems with some chipsets. If you are having problems -connecting to your RIO 500, try turning it on first and then plugging it -into the USB cable. +On systems with OHCI controllers, the kernel OHCI code appears to have +power on problems with some chipsets. If you are having problems +connecting to your RIO 500, try turning it on first and then plugging it +into the USB cable. -Contact information: --------------------- +Contact Information +------------------- The main page for the project is hosted at sourceforge.net in the following URL: . You can also go to the project's sourceforge home page at: . There is also a mailing list: rio500-users@lists.sourceforge.net -Authors: +Authors ------- -Most of the code was written by Cesar Miquel . Keith +Most of the code was written by Cesar Miquel . Keith Clayton is incharge of the PPC port and making sure things work there. Bruce Tenison is adding support for .fon files and also does testing. The program will mostly sure be re-written and Pete Ikusz along with the rest will re-design it. I would -also like to thank Tri Nguyen who provided use +also like to thank Tri Nguyen who provided use with some important information regarding the communication with the Rio. -ADDITIONAL INFORMATION and Userspace tools +Additional Information and userspace tools -http://rio500.sourceforge.net/ + http://rio500.sourceforge.net/ -REQUIREMENTS +Requirements +============ A host with a USB port. Ideally, either a UHCI (Intel) or OHCI (Compaq and others) hardware port should work. @@ -80,11 +88,11 @@ A Linux kernel with RIO 500 support enabled. 'lspci' which is only needed to determine the type of USB hardware available in your machine. -CONFIGURATION +Configuration Using `lspci -v`, determine the type of USB hardware available. - If you see something like: + If you see something like:: USB Controller: ...... Flags: ..... @@ -92,7 +100,7 @@ Using `lspci -v`, determine the type of USB hardware available. Then you have a UHCI based controller. - If you see something like: + If you see something like:: USB Controller: ..... Flags: .... @@ -107,8 +115,9 @@ hardware (determined from the steps above), 'USB Diamond Rio500 support', and (you may need to execute `depmod -a` to update the module dependencies). -Add a device for the USB rio500: - `mknod /dev/usb/rio500 c 180 64` +Add a device for the USB rio500:: + + mknod /dev/usb/rio500 c 180 64 Set appropriate permissions for /dev/usb/rio500 (don't forget about group and world permissions). Both read and write permissions are @@ -116,12 +125,14 @@ required for proper operation. Load the appropriate modules (if compiled as modules): - OHCI: + OHCI:: + modprobe usbcore modprobe usb-ohci modprobe rio500 - UHCI: + UHCI:: + modprobe usbcore modprobe usb-uhci (or uhci) modprobe rio500 @@ -129,10 +140,10 @@ Load the appropriate modules (if compiled as modules): That's it. The Rio500 Utils at: http://rio500.sourceforge.net should be able to access the rio500. -BUGS +Bugs +==== If you encounter any problems feel free to drop me an email. Bruce Tenison btenison@dibbs.net - diff --git a/Documentation/usb/usb-help.txt b/Documentation/usb/usb-help.txt index 4273ca2b86ba..dc23ecd4d802 100644 --- a/Documentation/usb/usb-help.txt +++ b/Documentation/usb/usb-help.txt @@ -1,16 +1,17 @@ -usb-help.txt +============== +USB references +============== + 2008-Mar-7 For USB help other than the readme files that are located in -Documentation/usb/*, see the following: +`Documentation/usb/*`, see the following: -Linux-USB project: http://www.linux-usb.org - mirrors at http://usb.in.tum.de/linux-usb/ - and http://it.linux-usb.org -Linux USB Guide: http://linux-usb.sourceforge.net -Linux-USB device overview (working devices and drivers): - http://www.qbik.ch/usb/devices/ +- Linux-USB project: http://www.linux-usb.org + mirrors at http://usb.in.tum.de/linux-usb/ + and http://it.linux-usb.org +- Linux USB Guide: http://linux-usb.sourceforge.net +- Linux-USB device overview (working devices and drivers): + http://www.qbik.ch/usb/devices/ The Linux-USB mailing list is at linux-usb@vger.kernel.org - -### diff --git a/Documentation/usb/usb-serial.txt b/Documentation/usb/usb-serial.txt index ab100d6ee436..8fa7dbd3da9a 100644 --- a/Documentation/usb/usb-serial.txt +++ b/Documentation/usb/usb-serial.txt @@ -1,4 +1,9 @@ -INTRODUCTION +========== +USB serial +========== + +Introduction +============ The USB serial driver currently supports a number of different USB to serial converter products, as well as some devices that use a serial @@ -8,13 +13,15 @@ INTRODUCTION the different devices. -CONFIGURATION +Configuration +============= Currently the driver can handle up to 256 different serial interfaces at - one time. + one time. The major number that the driver uses is 188 so to use the driver, - create the following nodes: + create the following nodes:: + mknod /dev/ttyUSB0 c 188 0 mknod /dev/ttyUSB1 c 188 1 mknod /dev/ttyUSB2 c 188 2 @@ -28,12 +35,14 @@ CONFIGURATION When the device is connected and recognized by the driver, the driver will print to the system log, which node(s) the device has been bound to. - -SPECIFIC DEVICES SUPPORTED + +Specific Devices Supported +========================== ConnectTech WhiteHEAT 4 port converter +-------------------------------------- ConnectTech has been very forthcoming with information about their device, including providing a unit to test with. @@ -46,6 +55,7 @@ ConnectTech WhiteHEAT 4 port converter HandSpring Visor, Palm USB, and Clié USB driver +----------------------------------------------- This driver works with all HandSpring USB, Palm USB, and Sony Clié USB devices. @@ -62,7 +72,7 @@ HandSpring Visor, Palm USB, and Clié USB driver This goes against the current documentation for pilot-xfer and other packages, but is the only way that it will work due to the hardware in the device. - + When the device is connected, try talking to it on the second port (this is usually /dev/ttyUSB1 if you do not have any other usb-serial devices in the system.) The system log should tell you which port is @@ -78,10 +88,10 @@ HandSpring Visor, Palm USB, and Clié USB driver try resetting the device, first a hot reset, and then a cold reset if necessary. Some devices need this before they can talk to the USB port properly. - + Devices that are not compiled into the kernel can be specified with module parameters. e.g. modprobe visor vendor=0x54c product=0x66 - + There is a webpage and mailing lists for this portion of the driver at: http://sourceforge.net/projects/usbvisor/ @@ -90,6 +100,7 @@ HandSpring Visor, Palm USB, and Clié USB driver PocketPC PDA Driver +------------------- This driver can be used to connect to Compaq iPAQ, HP Jornada, Casio EM500 and other PDAs running Windows CE 3.0 or PocketPC 2002 using a USB @@ -135,12 +146,13 @@ PocketPC PDA Driver be used to flash the ROM, as well as the microP code.. so much for needing Toshiba's $350 serial cable for flashing!! :D NOTE: This has NOT been tested. Use at your own risk. - + For any questions or problems with the driver, please contact Ganesh Varadarajan Keyspan PDA Serial Adapter +-------------------------- Single port DB-9 serial adapter, pushed as a PDA adapter for iMacs (mostly sold in Macintosh catalogs, comes in a translucent white/green dongle). @@ -148,32 +160,37 @@ Keyspan PDA Serial Adapter This driver also works for the Xircom/Entrega single port serial adapter. Current status: + Things that work: - basic input/output (tested with 'cu') - blocking write when serial line can't keep up - changing baud rates (up to 115200) - getting/setting modem control pins (TIOCM{GET,SET,BIS,BIC}) - sending break (although duration looks suspect) + - basic input/output (tested with 'cu') + - blocking write when serial line can't keep up + - changing baud rates (up to 115200) + - getting/setting modem control pins (TIOCM{GET,SET,BIS,BIC}) + - sending break (although duration looks suspect) + Things that don't: - device strings (as logged by kernel) have trailing binary garbage - device ID isn't right, might collide with other Keyspan products - changing baud rates ought to flush tx/rx to avoid mangled half characters + - device strings (as logged by kernel) have trailing binary garbage + - device ID isn't right, might collide with other Keyspan products + - changing baud rates ought to flush tx/rx to avoid mangled half characters + Big Things on the todo list: - parity, 7 vs 8 bits per char, 1 or 2 stop bits - HW flow control - not all of the standard USB descriptors are handled: Get_Status, Set_Feature - O_NONBLOCK, select() + - parity, 7 vs 8 bits per char, 1 or 2 stop bits + - HW flow control + - not all of the standard USB descriptors are handled: + Get_Status, Set_Feature, O_NONBLOCK, select() For any questions or problems with this driver, please contact Brian - Warner at warner@lothar.com + Warner at warner@lothar.com Keyspan USA-series Serial Adapters +---------------------------------- - Single, Dual and Quad port adapters - driver uses Keyspan supplied + Single, Dual and Quad port adapters - driver uses Keyspan supplied firmware and is being developed with their support. - + Current status: + The USA-18X, USA-28X, USA-19, USA-19W and USA-49W are supported and have been pretty thoroughly tested at various baud rates with 8-N-1 character settings. Other character lengths and parity setups are @@ -182,32 +199,37 @@ Keyspan USA-series Serial Adapters The USA-28 isn't yet supported though doing so should be pretty straightforward. Contact the maintainer if you require this functionality. - + More information is available at: + http://www.carnationsoftware.com/carnation/Keyspan.html - + For any questions or problems with this driver, please contact Hugh Blemings at hugh@misc.nu FTDI Single Port Serial Driver +------------------------------ This is a single port DB-25 serial adapter. Devices supported include: - -TripNav TN-200 USB GPS - -Navis Engineering Bureau CH-4711 USB GPS + + - TripNav TN-200 USB GPS + - Navis Engineering Bureau CH-4711 USB GPS For any questions or problems with this driver, please contact Bill Ryder. ZyXEL omni.net lcd plus ISDN TA +------------------------------- This is an ISDN TA. Please report both successes and troubles to azummo@towertech.it Cypress M8 CY4601 Family Serial Driver +-------------------------------------- This driver was in most part developed by Neil "koyama" Whelchel. It has been improved since that previous form to support dynamic serial @@ -215,18 +237,19 @@ Cypress M8 CY4601 Family Serial Driver part stable and has been tested on an smp machine. (dual p2) Chipsets supported under CY4601 family: - + CY7C63723, CY7C63742, CY7C63743, CY7C64013 Devices supported: - -DeLorme's USB Earthmate GPS (SiRF Star II lp arch) - -Cypress HID->COM RS232 adapter - - Note: Cypress Semiconductor claims no affiliation with the + - DeLorme's USB Earthmate GPS (SiRF Star II lp arch) + - Cypress HID->COM RS232 adapter + + Note: + Cypress Semiconductor claims no affiliation with the hid->com device. - Most devices using chipsets under the CY4601 family should + Most devices using chipsets under the CY4601 family should work with the driver. As long as they stay true to the CY4601 usbserial specification. @@ -236,8 +259,9 @@ Cypress M8 CY4601 Family Serial Driver upon start init to this setting. usbserial core provides the rest of the termios settings, along with some custom termios so that the output is in proper format and parsable. - - The device can be put into sirf mode by issuing NMEA command: + + The device can be put into sirf mode by issuing NMEA command:: + $PSRF100,,,,,*CHECKSUM $PSRF100,0,9600,8,1,0*0C @@ -259,11 +283,14 @@ Cypress M8 CY4601 Family Serial Driver If you have any questions, problems, patches, feature requests, etc. you can contact me here via email: + dignome@gmail.com + (your problems/patches can alternately be submitted to usb-devel) Digi AccelePort Driver +---------------------- This driver supports the Digi AccelePort USB 2 and 4 devices, 2 port (plus a parallel port) and 4 port USB serial converters. The driver @@ -285,42 +312,49 @@ Digi AccelePort Driver Belkin USB Serial Adapter F5U103 +-------------------------------- Single port DB-9/PS-2 serial adapter from Belkin with firmware by eTEK Labs. The Peracom single port serial adapter also works with this driver, as well as the GoHubs adapter. Current status: + The following have been tested and work: - Baud rate 300-230400 - Data bits 5-8 - Stop bits 1-2 - Parity N,E,O,M,S - Handshake None, Software (XON/XOFF), Hardware (CTSRTS,CTSDTR)* - Break Set and clear - Line control Input/Output query and control ** - - * Hardware input flow control is only enabled for firmware + + - Baud rate 300-230400 + - Data bits 5-8 + - Stop bits 1-2 + - Parity N,E,O,M,S + - Handshake None, Software (XON/XOFF), Hardware (CTSRTS,CTSDTR) [1]_ + - Break Set and clear + - Line control Input/Output query and control [2]_ + + .. [1] + Hardware input flow control is only enabled for firmware levels above 2.06. Read source code comments describing Belkin firmware errata. Hardware output flow control is working for all firmware versions. - ** Queries of inputs (CTS,DSR,CD,RI) show the last + + .. [2] + Queries of inputs (CTS,DSR,CD,RI) show the last reported state. Queries of outputs (DTR,RTS) show the last requested state and may not reflect current state as set by automatic hardware flow control. TO DO List: - -- Add true modem control line query capability. Currently tracks the - states reported by the interrupt and the states requested. - -- Add error reporting back to application for UART error conditions. - -- Add support for flush ioctls. - -- Add everything else that is missing :) + - Add true modem control line query capability. Currently tracks the + states reported by the interrupt and the states requested. + - Add error reporting back to application for UART error conditions. + - Add support for flush ioctls. + - Add everything else that is missing :) For any questions or problems with this driver, please contact William Greathouse at wgreathouse@smva.com Empeg empeg-car Mark I/II Driver +-------------------------------- This is an experimental driver to provide connectivity support for the client synchronization tools for an Empeg empeg-car mp3 player. @@ -335,6 +369,7 @@ Empeg empeg-car Mark I/II Driver MCT USB Single Port Serial Adapter U232 +--------------------------------------- This driver is for the MCT USB-RS232 Converter (25 pin, Model No. U232-P25) from Magic Control Technology Corp. (there is also a 9 pin @@ -355,35 +390,39 @@ MCT USB Single Port Serial Adapter U232 Inside Out Networks Edgeport Driver +----------------------------------- This driver supports all devices made by Inside Out Networks, specifically the following models: - Edgeport/4 - Rapidport/4 - Edgeport/4t - Edgeport/2 - Edgeport/4i - Edgeport/2i - Edgeport/421 - Edgeport/21 - Edgeport/8 - Edgeport/8 Dual - Edgeport/2D8 - Edgeport/4D8 - Edgeport/8i - Edgeport/2 DIN - Edgeport/4 DIN - Edgeport/16 Dual + + - Edgeport/4 + - Rapidport/4 + - Edgeport/4t + - Edgeport/2 + - Edgeport/4i + - Edgeport/2i + - Edgeport/421 + - Edgeport/21 + - Edgeport/8 + - Edgeport/8 Dual + - Edgeport/2D8 + - Edgeport/4D8 + - Edgeport/8i + - Edgeport/2 DIN + - Edgeport/4 DIN + - Edgeport/16 Dual For any questions or problems with this driver, please contact Greg Kroah-Hartman at greg@kroah.com REINER SCT cyberJack pinpad/e-com USB chipcard reader - +----------------------------------------------------- + Interface to ISO 7816 compatible contactbased chipcards, e.g. GSM SIMs. - + Current status: + This is the kernel part of the driver for this USB card reader. There is also a user part for a CT-API driver available. A site for downloading is TBA. For now, you can request it from the @@ -394,6 +433,7 @@ REINER SCT cyberJack pinpad/e-com USB chipcard reader Prolific PL2303 Driver +---------------------- This driver supports any device that has the PL2303 chip from Prolific in it. This includes a number of single port USB to serial converters, @@ -403,11 +443,13 @@ Prolific PL2303 Driver For any questions or problems with this driver, please contact Greg Kroah-Hartman at greg@kroah.com - + KL5KUSB105 chipset / PalmConnect USB single-port adapter - +-------------------------------------------------------- + Current status: + The driver was put together by looking at the usb bus transactions done by Palm's driver under Windows, so a lot of functionality is still missing. Notably, serial ioctls are sometimes faked or not yet @@ -417,21 +459,25 @@ Current status: are supported, but handshaking (software or hardware) is not, which is why it is wise to cut down on the rate used is wise for large transfers until this is settled. - + See http://www.uuhaus.de/linux/palmconnect.html for up-to-date information on this driver. Winchiphead CH341 Driver +------------------------ This driver is for the Winchiphead CH341 USB-RS232 Converter. This chip also implements an IEEE 1284 parallel port, I2C and SPI, but that is not supported by the driver. The protocol was analyzed from the behaviour of the Windows driver, no datasheet is available at present. + The manufacturer's website: http://www.winchiphead.com/. + For any questions or problems with this driver, please contact frank@kingswood-consulting.co.uk. Moschip MCS7720, MCS7715 driver +------------------------------- These chips are present in devices sold by various manufacturers, such as Syba and Cables Unlimited. There may be others. The 7720 provides two serial @@ -449,20 +495,24 @@ Moschip MCS7720, MCS7715 driver don't have one of these devices, so I can't say for sure. Generic Serial driver +--------------------- If your device is not one of the above listed devices, compatible with the above models, you can try out the "generic" interface. This interface does not provide any type of control messages sent to the device, and does not support any kind of device flow control. All that is required of your device is that it has at least one bulk in endpoint, - or one bulk out endpoint. + or one bulk out endpoint. + + To enable the generic driver to recognize your device, provide:: - To enable the generic driver to recognize your device, provide echo >/sys/bus/usb-serial/drivers/generic/new_id + where the and is replaced with the hex representation of your device's vendor id and product id. If the driver is compiled as a module you can also provide one id when - loading the module + loading the module:: + insmod usbserial vendor=0x#### product=0x#### This driver has been successfully used to connect to the NetChip USB @@ -473,7 +523,8 @@ Generic Serial driver Kroah-Hartman at greg@kroah.com -CONTACT: +Contact +======= If anyone has any problems using these drivers, with any of the above specified products, please contact the specific driver's author listed diff --git a/Documentation/usb/usbip_protocol.txt b/Documentation/usb/usbip_protocol.txt index c7a0f4c7e7f1..988c832166cd 100644 --- a/Documentation/usb/usbip_protocol.txt +++ b/Documentation/usb/usbip_protocol.txt @@ -1,3 +1,7 @@ +=============== +USB/IP protocol +=============== + PRELIMINARY DRAFT, MAY CONTAIN MISTAKES! 28 Jun 2011 @@ -12,6 +16,8 @@ in one or more pieces at the low level transport layer). The server sends back the OP_REP_DEVLIST packet which lists the exported USB devices. Finally the TCP/IP connection is closed. +:: + virtual host controller usb host "client" "server" (imports USB devices) (exports USB devices) @@ -32,6 +38,8 @@ send two types of packets: the USBIP_CMD_SUBMIT to submit an URB, and USBIP_CMD_UNLINK to unlink a previously submitted URB. The answers of the server may be USBIP_RET_SUBMIT and USBIP_RET_UNLINK respectively. +:: + virtual host controller usb host "client" "server" (imports USB devices) (exports USB devices) @@ -88,270 +96,316 @@ The fields are in network (big endian) byte order meaning that the most signific byte (MSB) is stored at the lowest address. -OP_REQ_DEVLIST: Retrieve the list of exported USB devices. +OP_REQ_DEVLIST: + Retrieve the list of exported USB devices. - Offset | Length | Value | Description ------------+--------+------------+--------------------------------------------------- - 0 | 2 | 0x0100 | Binary-coded decimal USBIP version number: v1.0.0 ------------+--------+------------+--------------------------------------------------- - 2 | 2 | 0x8005 | Command code: Retrieve the list of exported USB - | | | devices. ------------+--------+------------+--------------------------------------------------- - 4 | 4 | 0x00000000 | Status: unused, shall be set to 0 ++-----------+--------+------------+---------------------------------------------------+ +| Offset | Length | Value | Description | ++===========+========+============+===================================================+ +| 0 | 2 | 0x0100 | Binary-coded decimal USBIP version number: v1.0.0 | ++-----------+--------+------------+---------------------------------------------------+ +| 2 | 2 | 0x8005 | Command code: Retrieve the list of exported USB | +| | | | devices. | ++-----------+--------+------------+---------------------------------------------------+ +| 4 | 4 | 0x00000000 | Status: unused, shall be set to 0 | ++-----------+--------+------------+---------------------------------------------------+ -OP_REP_DEVLIST: Reply with the list of exported USB devices. +OP_REP_DEVLIST: + Reply with the list of exported USB devices. - Offset | Length | Value | Description ------------+--------+------------+--------------------------------------------------- - 0 | 2 | 0x0100 | Binary-coded decimal USBIP version number: v1.0.0. ------------+--------+------------+--------------------------------------------------- - 2 | 2 | 0x0005 | Reply code: The list of exported USB devices. ------------+--------+------------+--------------------------------------------------- - 4 | 4 | 0x00000000 | Status: 0 for OK ------------+--------+------------+--------------------------------------------------- - 8 | 4 | n | Number of exported devices: 0 means no exported - | | | devices. ------------+--------+------------+--------------------------------------------------- - 0x0C | | | From now on the exported n devices are described, - | | | if any. If no devices are exported the message - | | | ends with the previous "number of exported - | | | devices" field. ------------+--------+------------+--------------------------------------------------- - | 256 | | path: Path of the device on the host exporting the - | | | USB device, string closed with zero byte, e.g. - | | | "/sys/devices/pci0000:00/0000:00:1d.1/usb3/3-2" - | | | The unused bytes shall be filled with zero - | | | bytes. ------------+--------+------------+--------------------------------------------------- - 0x10C | 32 | | busid: Bus ID of the exported device, string - | | | closed with zero byte, e.g. "3-2". The unused - | | | bytes shall be filled with zero bytes. ------------+--------+------------+--------------------------------------------------- - 0x12C | 4 | | busnum ------------+--------+------------+--------------------------------------------------- - 0x130 | 4 | | devnum ------------+--------+------------+--------------------------------------------------- - 0x134 | 4 | | speed ------------+--------+------------+--------------------------------------------------- - 0x138 | 2 | | idVendor ------------+--------+------------+--------------------------------------------------- - 0x13A | 2 | | idProduct ------------+--------+------------+--------------------------------------------------- - 0x13C | 2 | | bcdDevice ------------+--------+------------+--------------------------------------------------- - 0x13E | 1 | | bDeviceClass ------------+--------+------------+--------------------------------------------------- - 0x13F | 1 | | bDeviceSubClass ------------+--------+------------+--------------------------------------------------- - 0x140 | 1 | | bDeviceProtocol ------------+--------+------------+--------------------------------------------------- - 0x141 | 1 | | bConfigurationValue ------------+--------+------------+--------------------------------------------------- - 0x142 | 1 | | bNumConfigurations ------------+--------+------------+--------------------------------------------------- - 0x143 | 1 | | bNumInterfaces ------------+--------+------------+--------------------------------------------------- - 0x144 | | m_0 | From now on each interface is described, all - | | | together bNumInterfaces times, with the - | | | the following 4 fields: ------------+--------+------------+--------------------------------------------------- - | 1 | | bInterfaceClass ------------+--------+------------+--------------------------------------------------- - 0x145 | 1 | | bInterfaceSubClass ------------+--------+------------+--------------------------------------------------- - 0x146 | 1 | | bInterfaceProtocol ------------+--------+------------+--------------------------------------------------- - 0x147 | 1 | | padding byte for alignment, shall be set to zero ------------+--------+------------+--------------------------------------------------- - 0xC + | | | The second exported USB device starts at i=1 - i*0x138 + | | | with the busid field. - m_(i-1)*4 | | | ++-----------+--------+------------+---------------------------------------------------+ +| Offset | Length | Value | Description | ++===========+========+============+===================================================+ +| 0 | 2 | 0x0100 | Binary-coded decimal USBIP version number: v1.0.0.| ++-----------+--------+------------+---------------------------------------------------+ +| 2 | 2 | 0x0005 | Reply code: The list of exported USB devices. | ++-----------+--------+------------+---------------------------------------------------+ +| 4 | 4 | 0x00000000 | Status: 0 for OK | ++-----------+--------+------------+---------------------------------------------------+ +| 8 | 4 | n | Number of exported devices: 0 means no exported | +| | | | devices. | ++-----------+--------+------------+---------------------------------------------------+ +| 0x0C | | | From now on the exported n devices are described, | +| | | | if any. If no devices are exported the message | +| | | | ends with the previous "number of exported | +| | | | devices" field. | ++-----------+--------+------------+---------------------------------------------------+ +| | 256 | | path: Path of the device on the host exporting the| +| | | | USB device, string closed with zero byte, e.g. | +| | | | "/sys/devices/pci0000:00/0000:00:1d.1/usb3/3-2" | +| | | | The unused bytes shall be filled with zero | +| | | | bytes. | ++-----------+--------+------------+---------------------------------------------------+ +| 0x10C | 32 | | busid: Bus ID of the exported device, string | +| | | | closed with zero byte, e.g. "3-2". The unused | +| | | | bytes shall be filled with zero bytes. | ++-----------+--------+------------+---------------------------------------------------+ +| 0x12C | 4 | | busnum | ++-----------+--------+------------+---------------------------------------------------+ +| 0x130 | 4 | | devnum | ++-----------+--------+------------+---------------------------------------------------+ +| 0x134 | 4 | | speed | ++-----------+--------+------------+---------------------------------------------------+ +| 0x138 | 2 | | idVendor | ++-----------+--------+------------+---------------------------------------------------+ +| 0x13A | 2 | | idProduct | ++-----------+--------+------------+---------------------------------------------------+ +| 0x13C | 2 | | bcdDevice | ++-----------+--------+------------+---------------------------------------------------+ +| 0x13E | 1 | | bDeviceClass | ++-----------+--------+------------+---------------------------------------------------+ +| 0x13F | 1 | | bDeviceSubClass | ++-----------+--------+------------+---------------------------------------------------+ +| 0x140 | 1 | | bDeviceProtocol | ++-----------+--------+------------+---------------------------------------------------+ +| 0x141 | 1 | | bConfigurationValue | ++-----------+--------+------------+---------------------------------------------------+ +| 0x142 | 1 | | bNumConfigurations | ++-----------+--------+------------+---------------------------------------------------+ +| 0x143 | 1 | | bNumInterfaces | ++-----------+--------+------------+---------------------------------------------------+ +| 0x144 | | m_0 | From now on each interface is described, all | +| | | | together bNumInterfaces times, with the | +| | | | the following 4 fields: | ++-----------+--------+------------+---------------------------------------------------+ +| | 1 | | bInterfaceClass | ++-----------+--------+------------+---------------------------------------------------+ +| 0x145 | 1 | | bInterfaceSubClass | ++-----------+--------+------------+---------------------------------------------------+ +| 0x146 | 1 | | bInterfaceProtocol | ++-----------+--------+------------+---------------------------------------------------+ +| 0x147 | 1 | | padding byte for alignment, shall be set to zero | ++-----------+--------+------------+---------------------------------------------------+ +| 0xC + | | | The second exported USB device starts at i=1 | +| i*0x138 + | | | with the busid field. | +| m_(i-1)*4 | | | | ++-----------+--------+------------+---------------------------------------------------+ -OP_REQ_IMPORT: Request to import (attach) a remote USB device. +OP_REQ_IMPORT: + Request to import (attach) a remote USB device. - Offset | Length | Value | Description ------------+--------+------------+--------------------------------------------------- - 0 | 2 | 0x0100 | Binary-coded decimal USBIP version number: v1.0.0 ------------+--------+------------+--------------------------------------------------- - 2 | 2 | 0x8003 | Command code: import a remote USB device. ------------+--------+------------+--------------------------------------------------- - 4 | 4 | 0x00000000 | Status: unused, shall be set to 0 ------------+--------+------------+--------------------------------------------------- - 8 | 32 | | busid: the busid of the exported device on the - | | | remote host. The possible values are taken - | | | from the message field OP_REP_DEVLIST.busid. - | | | A string closed with zero, the unused bytes - | | | shall be filled with zeros. ------------+--------+------------+--------------------------------------------------- ++-----------+--------+------------+---------------------------------------------------+ +| Offset | Length | Value | Description | ++===========+========+============+===================================================+ +| 0 | 2 | 0x0100 | Binary-coded decimal USBIP version number: v1.0.0 | ++-----------+--------+------------+---------------------------------------------------+ +| 2 | 2 | 0x8003 | Command code: import a remote USB device. | ++-----------+--------+------------+---------------------------------------------------+ +| 4 | 4 | 0x00000000 | Status: unused, shall be set to 0 | ++-----------+--------+------------+---------------------------------------------------+ +| 8 | 32 | | busid: the busid of the exported device on the | +| | | | remote host. The possible values are taken | +| | | | from the message field OP_REP_DEVLIST.busid. | +| | | | A string closed with zero, the unused bytes | +| | | | shall be filled with zeros. | ++-----------+--------+------------+---------------------------------------------------+ -OP_REP_IMPORT: Reply to import (attach) a remote USB device. +OP_REP_IMPORT: + Reply to import (attach) a remote USB device. - Offset | Length | Value | Description ------------+--------+------------+--------------------------------------------------- - 0 | 2 | 0x0100 | Binary-coded decimal USBIP version number: v1.0.0 ------------+--------+------------+--------------------------------------------------- - 2 | 2 | 0x0003 | Reply code: Reply to import. ------------+--------+------------+--------------------------------------------------- - 4 | 4 | 0x00000000 | Status: 0 for OK - | | | 1 for error ------------+--------+------------+--------------------------------------------------- - 8 | | | From now on comes the details of the imported - | | | device, if the previous status field was OK (0), - | | | otherwise the reply ends with the status field. ------------+--------+------------+--------------------------------------------------- - | 256 | | path: Path of the device on the host exporting the - | | | USB device, string closed with zero byte, e.g. - | | | "/sys/devices/pci0000:00/0000:00:1d.1/usb3/3-2" - | | | The unused bytes shall be filled with zero - | | | bytes. ------------+--------+------------+--------------------------------------------------- - 0x108 | 32 | | busid: Bus ID of the exported device, string - | | | closed with zero byte, e.g. "3-2". The unused - | | | bytes shall be filled with zero bytes. ------------+--------+------------+--------------------------------------------------- - 0x128 | 4 | | busnum ------------+--------+------------+--------------------------------------------------- - 0x12C | 4 | | devnum ------------+--------+------------+--------------------------------------------------- - 0x130 | 4 | | speed ------------+--------+------------+--------------------------------------------------- - 0x134 | 2 | | idVendor ------------+--------+------------+--------------------------------------------------- - 0x136 | 2 | | idProduct ------------+--------+------------+--------------------------------------------------- - 0x138 | 2 | | bcdDevice ------------+--------+------------+--------------------------------------------------- - 0x139 | 1 | | bDeviceClass ------------+--------+------------+--------------------------------------------------- - 0x13A | 1 | | bDeviceSubClass ------------+--------+------------+--------------------------------------------------- - 0x13B | 1 | | bDeviceProtocol ------------+--------+------------+--------------------------------------------------- - 0x13C | 1 | | bConfigurationValue ------------+--------+------------+--------------------------------------------------- - 0x13D | 1 | | bNumConfigurations ------------+--------+------------+--------------------------------------------------- - 0x13E | 1 | | bNumInterfaces ++-----------+--------+------------+---------------------------------------------------+ +| Offset | Length | Value | Description | ++===========+========+============+===================================================+ +| 0 | 2 | 0x0100 | Binary-coded decimal USBIP version number: v1.0.0 | ++-----------+--------+------------+---------------------------------------------------+ +| 2 | 2 | 0x0003 | Reply code: Reply to import. | ++-----------+--------+------------+---------------------------------------------------+ +| 4 | 4 | 0x00000000 | Status: | +| | | | | +| | | | - 0 for OK | +| | | | - 1 for error | ++-----------+--------+------------+---------------------------------------------------+ +| 8 | | | From now on comes the details of the imported | +| | | | device, if the previous status field was OK (0), | +| | | | otherwise the reply ends with the status field. | ++-----------+--------+------------+---------------------------------------------------+ +| | 256 | | path: Path of the device on the host exporting the| +| | | | USB device, string closed with zero byte, e.g. | +| | | | "/sys/devices/pci0000:00/0000:00:1d.1/usb3/3-2" | +| | | | The unused bytes shall be filled with zero | +| | | | bytes. | ++-----------+--------+------------+---------------------------------------------------+ +| 0x108 | 32 | | busid: Bus ID of the exported device, string | +| | | | closed with zero byte, e.g. "3-2". The unused | +| | | | bytes shall be filled with zero bytes. | ++-----------+--------+------------+---------------------------------------------------+ +| 0x128 | 4 | | busnum | ++-----------+--------+------------+---------------------------------------------------+ +| 0x12C | 4 | | devnum | ++-----------+--------+------------+---------------------------------------------------+ +| 0x130 | 4 | | speed | ++-----------+--------+------------+---------------------------------------------------+ +| 0x134 | 2 | | idVendor | ++-----------+--------+------------+---------------------------------------------------+ +| 0x136 | 2 | | idProduct | ++-----------+--------+------------+---------------------------------------------------+ +| 0x138 | 2 | | bcdDevice | ++-----------+--------+------------+---------------------------------------------------+ +| 0x139 | 1 | | bDeviceClass | ++-----------+--------+------------+---------------------------------------------------+ +| 0x13A | 1 | | bDeviceSubClass | ++-----------+--------+------------+---------------------------------------------------+ +| 0x13B | 1 | | bDeviceProtocol | ++-----------+--------+------------+---------------------------------------------------+ +| 0x13C | 1 | | bConfigurationValue | ++-----------+--------+------------+---------------------------------------------------+ +| 0x13D | 1 | | bNumConfigurations | ++-----------+--------+------------+---------------------------------------------------+ +| 0x13E | 1 | | bNumInterfaces | ++-----------+--------+------------+---------------------------------------------------+ -USBIP_CMD_SUBMIT: Submit an URB +USBIP_CMD_SUBMIT: + Submit an URB - Offset | Length | Value | Description ------------+--------+------------+--------------------------------------------------- - 0 | 4 | 0x00000001 | command: Submit an URB ------------+--------+------------+--------------------------------------------------- - 4 | 4 | | seqnum: the sequence number of the URB to submit ------------+--------+------------+--------------------------------------------------- - 8 | 4 | | devid ------------+--------+------------+--------------------------------------------------- - 0xC | 4 | | direction: 0: USBIP_DIR_OUT - | | | 1: USBIP_DIR_IN ------------+--------+------------+--------------------------------------------------- - 0x10 | 4 | | ep: endpoint number, possible values are: 0...15 ------------+--------+------------+--------------------------------------------------- - 0x14 | 4 | | transfer_flags: possible values depend on the - | | | URB transfer type, see below ------------+--------+------------+--------------------------------------------------- - 0x18 | 4 | | transfer_buffer_length ------------+--------+------------+--------------------------------------------------- - 0x1C | 4 | | start_frame: specify the selected frame to - | | | transmit an ISO frame, ignored if URB_ISO_ASAP - | | | is specified at transfer_flags ------------+--------+------------+--------------------------------------------------- - 0x20 | 4 | | number_of_packets: number of ISO packets ------------+--------+------------+--------------------------------------------------- - 0x24 | 4 | | interval: maximum time for the request on the - | | | server-side host controller ------------+--------+------------+--------------------------------------------------- - 0x28 | 8 | | setup: data bytes for USB setup, filled with - | | | zeros if not used ------------+--------+------------+--------------------------------------------------- - 0x30 | | | URB data. For ISO transfers the padding between - | | | each ISO packets is not transmitted. ++-----------+--------+------------+---------------------------------------------------+ +| Offset | Length | Value | Description | ++===========+========+============+===================================================+ +| 0 | 4 | 0x00000001 | command: Submit an URB | ++-----------+--------+------------+---------------------------------------------------+ +| 4 | 4 | | seqnum: the sequence number of the URB to submit | ++-----------+--------+------------+---------------------------------------------------+ +| 8 | 4 | | devid | ++-----------+--------+------------+---------------------------------------------------+ +| 0xC | 4 | | direction: | +| | | | | +| | | | - 0: USBIP_DIR_OUT | +| | | | - 1: USBIP_DIR_IN | ++-----------+--------+------------+---------------------------------------------------+ +| 0x10 | 4 | | ep: endpoint number, possible values are: 0...15 | ++-----------+--------+------------+---------------------------------------------------+ +| 0x14 | 4 | | transfer_flags: possible values depend on the | +| | | | URB transfer type, see below | ++-----------+--------+------------+---------------------------------------------------+ +| 0x18 | 4 | | transfer_buffer_length | ++-----------+--------+------------+---------------------------------------------------+ +| 0x1C | 4 | | start_frame: specify the selected frame to | +| | | | transmit an ISO frame, ignored if URB_ISO_ASAP | +| | | | is specified at transfer_flags | ++-----------+--------+------------+---------------------------------------------------+ +| 0x20 | 4 | | number_of_packets: number of ISO packets | ++-----------+--------+------------+---------------------------------------------------+ +| 0x24 | 4 | | interval: maximum time for the request on the | +| | | | server-side host controller | ++-----------+--------+------------+---------------------------------------------------+ +| 0x28 | 8 | | setup: data bytes for USB setup, filled with | +| | | | zeros if not used | ++-----------+--------+------------+---------------------------------------------------+ +| 0x30 | | | URB data. For ISO transfers the padding between | +| | | | each ISO packets is not transmitted. | ++-----------+--------+------------+---------------------------------------------------+ - Allowed transfer_flags | value | control | interrupt | bulk | isochronous - -------------------------+------------+---------+-----------+----------+------------- - URB_SHORT_NOT_OK | 0x00000001 | only in | only in | only in | no - URB_ISO_ASAP | 0x00000002 | no | no | no | yes - URB_NO_TRANSFER_DMA_MAP | 0x00000004 | yes | yes | yes | yes - URB_ZERO_PACKET | 0x00000040 | no | no | only out | no - URB_NO_INTERRUPT | 0x00000080 | yes | yes | yes | yes - URB_FREE_BUFFER | 0x00000100 | yes | yes | yes | yes - URB_DIR_MASK | 0x00000200 | yes | yes | yes | yes + +-------------------------+------------+---------+-----------+----------+-------------+ + | Allowed transfer_flags | value | control | interrupt | bulk | isochronous | + +=========================+============+=========+===========+==========+=============+ + | URB_SHORT_NOT_OK | 0x00000001 | only in | only in | only in | no | + +-------------------------+------------+---------+-----------+----------+-------------+ + | URB_ISO_ASAP | 0x00000002 | no | no | no | yes | + +-------------------------+------------+---------+-----------+----------+-------------+ + | URB_NO_TRANSFER_DMA_MAP | 0x00000004 | yes | yes | yes | yes | + +-------------------------+------------+---------+-----------+----------+-------------+ + | URB_ZERO_PACKET | 0x00000040 | no | no | only out | no | + +-------------------------+------------+---------+-----------+----------+-------------+ + | URB_NO_INTERRUPT | 0x00000080 | yes | yes | yes | yes | + +-------------------------+------------+---------+-----------+----------+-------------+ + | URB_FREE_BUFFER | 0x00000100 | yes | yes | yes | yes | + +-------------------------+------------+---------+-----------+----------+-------------+ + | URB_DIR_MASK | 0x00000200 | yes | yes | yes | yes | + +-------------------------+------------+---------+-----------+----------+-------------+ -USBIP_RET_SUBMIT: Reply for submitting an URB +USBIP_RET_SUBMIT: + Reply for submitting an URB - Offset | Length | Value | Description ------------+--------+------------+--------------------------------------------------- - 0 | 4 | 0x00000003 | command ------------+--------+------------+--------------------------------------------------- - 4 | 4 | | seqnum: URB sequence number ------------+--------+------------+--------------------------------------------------- - 8 | 4 | | devid ------------+--------+------------+--------------------------------------------------- - 0xC | 4 | | direction: 0: USBIP_DIR_OUT - | | | 1: USBIP_DIR_IN ------------+--------+------------+--------------------------------------------------- - 0x10 | 4 | | ep: endpoint number ------------+--------+------------+--------------------------------------------------- - 0x14 | 4 | | status: zero for successful URB transaction, - | | | otherwise some kind of error happened. ------------+--------+------------+--------------------------------------------------- - 0x18 | 4 | n | actual_length: number of URB data bytes ------------+--------+------------+--------------------------------------------------- - 0x1C | 4 | | start_frame: for an ISO frame the actually - | | | selected frame for transmit. ------------+--------+------------+--------------------------------------------------- - 0x20 | 4 | | number_of_packets ------------+--------+------------+--------------------------------------------------- - 0x24 | 4 | | error_count ------------+--------+------------+--------------------------------------------------- - 0x28 | 8 | | setup: data bytes for USB setup, filled with - | | | zeros if not used ------------+--------+------------+--------------------------------------------------- - 0x30 | n | | URB data bytes. For ISO transfers the padding - | | | between each ISO packets is not transmitted. ++-----------+--------+------------+---------------------------------------------------+ +| Offset | Length | Value | Description | ++===========+========+============+===================================================+ +| 0 | 4 | 0x00000003 | command | ++-----------+--------+------------+---------------------------------------------------+ +| 4 | 4 | | seqnum: URB sequence number | ++-----------+--------+------------+---------------------------------------------------+ +| 8 | 4 | | devid | ++-----------+--------+------------+---------------------------------------------------+ +| 0xC | 4 | | direction: | +| | | | | +| | | | - 0: USBIP_DIR_OUT | +| | | | - 1: USBIP_DIR_IN | ++-----------+--------+------------+---------------------------------------------------+ +| 0x10 | 4 | | ep: endpoint number | ++-----------+--------+------------+---------------------------------------------------+ +| 0x14 | 4 | | status: zero for successful URB transaction, | +| | | | otherwise some kind of error happened. | ++-----------+--------+------------+---------------------------------------------------+ +| 0x18 | 4 | n | actual_length: number of URB data bytes | ++-----------+--------+------------+---------------------------------------------------+ +| 0x1C | 4 | | start_frame: for an ISO frame the actually | +| | | | selected frame for transmit. | ++-----------+--------+------------+---------------------------------------------------+ +| 0x20 | 4 | | number_of_packets | ++-----------+--------+------------+---------------------------------------------------+ +| 0x24 | 4 | | error_count | ++-----------+--------+------------+---------------------------------------------------+ +| 0x28 | 8 | | setup: data bytes for USB setup, filled with | +| | | | zeros if not used | ++-----------+--------+------------+---------------------------------------------------+ +| 0x30 | n | | URB data bytes. For ISO transfers the padding | +| | | | between each ISO packets is not transmitted. | ++-----------+--------+------------+---------------------------------------------------+ -USBIP_CMD_UNLINK: Unlink an URB +USBIP_CMD_UNLINK: + Unlink an URB - Offset | Length | Value | Description ------------+--------+------------+--------------------------------------------------- - 0 | 4 | 0x00000002 | command: URB unlink command ------------+--------+------------+--------------------------------------------------- - 4 | 4 | | seqnum: URB sequence number to unlink: FIXME: is this so? ------------+--------+------------+--------------------------------------------------- - 8 | 4 | | devid ------------+--------+------------+--------------------------------------------------- - 0xC | 4 | | direction: 0: USBIP_DIR_OUT - | | | 1: USBIP_DIR_IN ------------+--------+------------+--------------------------------------------------- - 0x10 | 4 | | ep: endpoint number: zero ------------+--------+------------+--------------------------------------------------- - 0x14 | 4 | | seqnum: the URB sequence number given previously - | | | at USBIP_CMD_SUBMIT.seqnum field ------------+--------+------------+--------------------------------------------------- - 0x30 | n | | URB data bytes. For ISO transfers the padding - | | | between each ISO packets is not transmitted. ++-----------+--------+------------+---------------------------------------------------+ +| Offset | Length | Value | Description | ++===========+========+============+===================================================+ +| 0 | 4 | 0x00000002 | command: URB unlink command | ++-----------+--------+------------+---------------------------------------------------+ +| 4 | 4 | | seqnum: URB sequence number to unlink: | +| | | | | +| | | | FIXME: | +| | | | is this so? | ++-----------+--------+------------+---------------------------------------------------+ +| 8 | 4 | | devid | ++-----------+--------+------------+---------------------------------------------------+ +| 0xC | 4 | | direction: | +| | | | | +| | | | - 0: USBIP_DIR_OUT | +| | | | - 1: USBIP_DIR_IN | ++-----------+--------+------------+---------------------------------------------------+ +| 0x10 | 4 | | ep: endpoint number: zero | ++-----------+--------+------------+---------------------------------------------------+ +| 0x14 | 4 | | seqnum: the URB sequence number given previously | +| | | | at USBIP_CMD_SUBMIT.seqnum field | ++-----------+--------+------------+---------------------------------------------------+ +| 0x30 | n | | URB data bytes. For ISO transfers the padding | +| | | | between each ISO packets is not transmitted. | ++-----------+--------+------------+---------------------------------------------------+ -USBIP_RET_UNLINK: Reply for URB unlink +USBIP_RET_UNLINK: + Reply for URB unlink - Offset | Length | Value | Description ------------+--------+------------+--------------------------------------------------- - 0 | 4 | 0x00000004 | command: reply for the URB unlink command ------------+--------+------------+--------------------------------------------------- - 4 | 4 | | seqnum: the unlinked URB sequence number ------------+--------+------------+--------------------------------------------------- - 8 | 4 | | devid ------------+--------+------------+--------------------------------------------------- - 0xC | 4 | | direction: 0: USBIP_DIR_OUT - | | | 1: USBIP_DIR_IN ------------+--------+------------+--------------------------------------------------- - 0x10 | 4 | | ep: endpoint number ------------+--------+------------+--------------------------------------------------- - 0x14 | 4 | | status: This is the value contained in the - | | | urb->status in the URB completition handler. - | | | FIXME: a better explanation needed. ------------+--------+------------+--------------------------------------------------- - 0x30 | n | | URB data bytes. For ISO transfers the padding - | | | between each ISO packets is not transmitted. ++-----------+--------+------------+---------------------------------------------------+ +| Offset | Length | Value | Description | ++===========+========+============+===================================================+ +| 0 | 4 | 0x00000004 | command: reply for the URB unlink command | ++-----------+--------+------------+---------------------------------------------------+ +| 4 | 4 | | seqnum: the unlinked URB sequence number | ++-----------+--------+------------+---------------------------------------------------+ +| 8 | 4 | | devid | ++-----------+--------+------------+---------------------------------------------------+ +| 0xC | 4 | | direction: | +| | | | | +| | | | - 0: USBIP_DIR_OUT | +| | | | - 1: USBIP_DIR_IN | ++-----------+--------+------------+---------------------------------------------------+ +| 0x10 | 4 | | ep: endpoint number | ++-----------+--------+------------+---------------------------------------------------+ +| 0x14 | 4 | | status: This is the value contained in the | +| | | | urb->status in the URB completition handler. | +| | | | | +| | | | FIXME: | +| | | | a better explanation needed. | ++-----------+--------+------------+---------------------------------------------------+ +| 0x30 | n | | URB data bytes. For ISO transfers the padding | +| | | | between each ISO packets is not transmitted. | ++-----------+--------+------------+---------------------------------------------------+ diff --git a/Documentation/usb/usbmon.txt b/Documentation/usb/usbmon.txt index 28425f736756..b0bd51080799 100644 --- a/Documentation/usb/usbmon.txt +++ b/Documentation/usb/usbmon.txt @@ -1,4 +1,9 @@ -* Introduction +====== +usbmon +====== + +Introduction +============ The name "usbmon" in lowercase refers to a facility in kernel which is used to collect traces of I/O on the USB bus. This function is analogous @@ -16,7 +21,8 @@ Two APIs are currently implemented: "text" and "binary". The binary API is available through a character device in /dev namespace and is an ABI. The text API is deprecated since 2.6.35, but available for convenience. -* How to use usbmon to collect raw text traces +How to use usbmon to collect raw text traces +============================================ Unlike the packet socket, usbmon has an interface which provides traces in a text format. This is used for two purposes. First, it serves as a @@ -26,38 +32,41 @@ are finalized. Second, humans can read it in case tools are not available. To collect a raw text trace, execute following steps. 1. Prepare +---------- Mount debugfs (it has to be enabled in your kernel configuration), and load the usbmon module (if built as module). The second step is skipped -if usbmon is built into the kernel. +if usbmon is built into the kernel:: -# mount -t debugfs none_debugs /sys/kernel/debug -# modprobe usbmon -# + # mount -t debugfs none_debugs /sys/kernel/debug + # modprobe usbmon + # -Verify that bus sockets are present. +Verify that bus sockets are present: -# ls /sys/kernel/debug/usb/usbmon -0s 0u 1s 1t 1u 2s 2t 2u 3s 3t 3u 4s 4t 4u -# + # ls /sys/kernel/debug/usb/usbmon + 0s 0u 1s 1t 1u 2s 2t 2u 3s 3t 3u 4s 4t 4u + # Now you can choose to either use the socket '0u' (to capture packets on all buses), and skip to step #3, or find the bus used by your device with step #2. This allows to filter away annoying devices that talk continuously. 2. Find which bus connects to the desired device +------------------------------------------------ Run "cat /sys/kernel/debug/usb/devices", and find the T-line which corresponds to the device. Usually you do it by looking for the vendor string. If you have many similar devices, unplug one and compare the two /sys/kernel/debug/usb/devices outputs. The T-line will have a bus number. -Example: -T: Bus=03 Lev=01 Prnt=01 Port=00 Cnt=01 Dev#= 2 Spd=12 MxCh= 0 -D: Ver= 1.10 Cls=00(>ifc ) Sub=00 Prot=00 MxPS= 8 #Cfgs= 1 -P: Vendor=0557 ProdID=2004 Rev= 1.00 -S: Manufacturer=ATEN -S: Product=UC100KM V2.00 +Example:: + + T: Bus=03 Lev=01 Prnt=01 Port=00 Cnt=01 Dev#= 2 Spd=12 MxCh= 0 + D: Ver= 1.10 Cls=00(>ifc ) Sub=00 Prot=00 MxPS= 8 #Cfgs= 1 + P: Vendor=0557 ProdID=2004 Rev= 1.00 + S: Manufacturer=ATEN + S: Product=UC100KM V2.00 "Bus=03" means it's bus 3. Alternatively, you can look at the output from "lsusb" and get the bus number from the appropriate line. Example: @@ -65,23 +74,28 @@ S: Product=UC100KM V2.00 Bus 003 Device 002: ID 0557:2004 ATEN UC100KM V2.00 3. Start 'cat' +-------------- + +:: -# cat /sys/kernel/debug/usb/usbmon/3u > /tmp/1.mon.out + # cat /sys/kernel/debug/usb/usbmon/3u > /tmp/1.mon.out -to listen on a single bus, otherwise, to listen on all buses, type: +to listen on a single bus, otherwise, to listen on all buses, type:: -# cat /sys/kernel/debug/usb/usbmon/0u > /tmp/1.mon.out + # cat /sys/kernel/debug/usb/usbmon/0u > /tmp/1.mon.out This process will read until it is killed. Naturally, the output can be redirected to a desirable location. This is preferred, because it is going to be quite long. 4. Perform the desired operation on the USB bus +----------------------------------------------- This is where you do something that creates the traffic: plug in a flash key, copy files, control a webcam, etc. 5. Kill cat +----------- Usually it's done with a keyboard interrupt (Control-C). @@ -89,7 +103,8 @@ At this point the output file (/tmp/1.mon.out in this example) can be saved, sent by e-mail, or inspected with a text editor. In the last case make sure that the file size is not excessive for your favourite editor. -* Raw text data format +Raw text data format +==================== Two formats are supported currently: the original, or '1t' format, and the '1u' format. The '1t' format is deprecated in kernel 2.6.21. The '1u' @@ -122,10 +137,14 @@ Here is the list of words, from left to right: - "Address" word (formerly a "pipe"). It consists of four fields, separated by colons: URB type and direction, Bus number, Device address, Endpoint number. Type and direction are encoded with two bytes in the following manner: + + == == ============================= Ci Co Control input and output Zi Zo Isochronous input and output Ii Io Interrupt input and output Bi Bo Bulk input and output + == == ============================= + Bus number, Device address, and Endpoint are decimal numbers, but they may have leading zeros, for the sake of human readers. @@ -178,24 +197,25 @@ Here is the list of words, from left to right: Examples: -An input control transfer to get a port status. +An input control transfer to get a port status:: -d5ea89a0 3575914555 S Ci:1:001:0 s a3 00 0000 0003 0004 4 < -d5ea89a0 3575914560 C Ci:1:001:0 0 4 = 01050000 + d5ea89a0 3575914555 S Ci:1:001:0 s a3 00 0000 0003 0004 4 < + d5ea89a0 3575914560 C Ci:1:001:0 0 4 = 01050000 An output bulk transfer to send a SCSI command 0x28 (READ_10) in a 31-byte -Bulk wrapper to a storage device at address 5: +Bulk wrapper to a storage device at address 5:: -dd65f0e8 4128379752 S Bo:1:005:2 -115 31 = 55534243 ad000000 00800000 80010a28 20000000 20000040 00000000 000000 -dd65f0e8 4128379808 C Bo:1:005:2 0 31 > + dd65f0e8 4128379752 S Bo:1:005:2 -115 31 = 55534243 ad000000 00800000 80010a28 20000000 20000040 00000000 000000 + dd65f0e8 4128379808 C Bo:1:005:2 0 31 > -* Raw binary format and API +Raw binary format and API +========================= The overall architecture of the API is about the same as the one above, only the events are delivered in binary format. Each event is sent in -the following structure (its name is made up, so that we can refer to it): +the following structure (its name is made up, so that we can refer to it):: -struct usbmon_packet { + struct usbmon_packet { u64 id; /* 0: URB ID - from submission to callback */ unsigned char type; /* 8: Same as text; extensible. */ unsigned char xfer_type; /* ISO (0), Intr, Control, Bulk (3) */ @@ -220,7 +240,7 @@ struct usbmon_packet { int start_frame; /* 52: For ISO */ unsigned int xfer_flags; /* 56: copy of URB's transfer_flags */ unsigned int ndesc; /* 60: Actual number of ISO descriptors */ -}; /* 64 total length */ + }; /* 64 total length */ These events can be received from a character device by reading with read(2), with an ioctl(2), or by accessing the buffer with mmap. However, read(2) @@ -244,12 +264,12 @@ no events are available. MON_IOCG_STATS, defined as _IOR(MON_IOC_MAGIC, 3, struct mon_bin_stats) -The argument is a pointer to the following structure: +The argument is a pointer to the following structure:: -struct mon_bin_stats { + struct mon_bin_stats { u32 queued; u32 dropped; -}; + }; The member "queued" refers to the number of events currently queued in the buffer (and not to the number of events processed since the last reset). @@ -273,13 +293,13 @@ This call returns the current size of the buffer in bytes. These calls wait for events to arrive if none were in the kernel buffer, then return the first event. The argument is a pointer to the following -structure: +structure:: -struct mon_get_arg { + struct mon_get_arg { struct usbmon_packet *hdr; void *data; size_t alloc; /* Length of data (can be zero) */ -}; + }; Before the call, hdr, data, and alloc should be filled. Upon return, the area pointed by hdr contains the next event structure, and the data buffer contains @@ -290,13 +310,13 @@ The MON_IOCX_GET copies 48 bytes to hdr area, MON_IOCX_GETX copies 64 bytes. MON_IOCX_MFETCH, defined as _IOWR(MON_IOC_MAGIC, 7, struct mon_mfetch_arg) This ioctl is primarily used when the application accesses the buffer -with mmap(2). Its argument is a pointer to the following structure: +with mmap(2). Its argument is a pointer to the following structure:: -struct mon_mfetch_arg { + struct mon_mfetch_arg { uint32_t *offvec; /* Vector of events fetched */ uint32_t nfetch; /* Number of events to fetch (out: fetched) */ uint32_t nflush; /* Number of events to flush */ -}; + }; The ioctl operates in 3 stages. @@ -329,7 +349,7 @@ be polled with select(2) and poll(2). But lseek(2) does not work. The basic idea is simple: To prepare, map the buffer by getting the current size, then using mmap(2). -Then, execute a loop similar to the one written in pseudo-code below: +Then, execute a loop similar to the one written in pseudo-code below:: struct mon_mfetch_arg fetch; struct usbmon_packet *hdr; -- cgit v1.2.3 From 14ec072a19ad7a7b45fd997ab0f730d3999eb59a Mon Sep 17 00:00:00 2001 From: Maxime Ripard Date: Tue, 16 Apr 2019 10:27:57 +0200 Subject: dt-bindings: usb: Convert USB HCD generic binding to YAML The USB HCD generic binding is used by many USB host bindings. In order to allow the DT validation to happen on those, let's create a YAML description for that generic binding that can be referenced later on. Signed-off-by: Maxime Ripard Acked-by: Chen-Yu Tsai Signed-off-by: Greg Kroah-Hartman --- Documentation/devicetree/bindings/usb/usb-hcd.txt | 9 -------- Documentation/devicetree/bindings/usb/usb-hcd.yaml | 25 ++++++++++++++++++++++ 2 files changed, 25 insertions(+), 9 deletions(-) delete mode 100644 Documentation/devicetree/bindings/usb/usb-hcd.txt create mode 100644 Documentation/devicetree/bindings/usb/usb-hcd.yaml (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/usb/usb-hcd.txt b/Documentation/devicetree/bindings/usb/usb-hcd.txt deleted file mode 100644 index 50529b838c9c..000000000000 --- a/Documentation/devicetree/bindings/usb/usb-hcd.txt +++ /dev/null @@ -1,9 +0,0 @@ -Generic USB HCD (Host Controller Device) Properties - -Optional properties: -- phys: a list of all USB PHYs on this HCD - -Example: - &usb1 { - phys = <&usb2_phy1>, <&usb3_phy1>; - }; diff --git a/Documentation/devicetree/bindings/usb/usb-hcd.yaml b/Documentation/devicetree/bindings/usb/usb-hcd.yaml new file mode 100644 index 000000000000..9c8c56d3a792 --- /dev/null +++ b/Documentation/devicetree/bindings/usb/usb-hcd.yaml @@ -0,0 +1,25 @@ +# SPDX-License-Identifier: GPL-2.0 +%YAML 1.2 +--- +$id: http://devicetree.org/schemas/usb/usb-hcd.yaml# +$schema: http://devicetree.org/meta-schemas/core.yaml# + +title: Generic USB Host Controller Device Tree Bindings + +maintainers: + - Greg Kroah-Hartman + +properties: + $nodename: + pattern: "^usb(@.*)?" + + phys: + $ref: /schemas/types.yaml#/definitions/phandle-array + description: + List of all the USB PHYs on this HCD + +examples: + - | + usb { + phys = <&usb2_phy1>, <&usb3_phy1>; + }; -- cgit v1.2.3 From c93bcace1098ff4be518649187a763004275b79b Mon Sep 17 00:00:00 2001 From: Maxime Ripard Date: Tue, 16 Apr 2019 10:27:58 +0200 Subject: dt-bindings: usb: Convert the generic OHCI binding to YAML The generic OHCI binding is used by many controllers that are using the OHCI spec. Convert that binding to a YAML description to enable the validation on all the nodes using that binding. Signed-off-by: Maxime Ripard Acked-by: Chen-Yu Tsai Signed-off-by: Greg Kroah-Hartman --- .../devicetree/bindings/usb/generic-ohci.yaml | 89 ++++++++++++++++++++++ Documentation/devicetree/bindings/usb/usb-ohci.txt | 35 --------- 2 files changed, 89 insertions(+), 35 deletions(-) create mode 100644 Documentation/devicetree/bindings/usb/generic-ohci.yaml delete mode 100644 Documentation/devicetree/bindings/usb/usb-ohci.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/usb/generic-ohci.yaml b/Documentation/devicetree/bindings/usb/generic-ohci.yaml new file mode 100644 index 000000000000..da5a14becbe5 --- /dev/null +++ b/Documentation/devicetree/bindings/usb/generic-ohci.yaml @@ -0,0 +1,89 @@ +# SPDX-License-Identifier: GPL-2.0 +%YAML 1.2 +--- +$id: http://devicetree.org/schemas/usb/generic-ohci.yaml# +$schema: http://devicetree.org/meta-schemas/core.yaml# + +title: USB OHCI Controller Device Tree Bindings + +allOf: + - $ref: "usb-hcd.yaml" + +maintainers: + - Greg Kroah-Hartman + +properties: + compatible: + contains: + const: generic-ohci + + reg: + maxItems: 1 + + interrupts: + maxItems: 1 + + resets: + minItems: 1 + maxItems: 2 + + clocks: + minItems: 1 + maxItems: 3 + description: | + In case the Renesas R-Car Gen3 SoCs: + - if a host only channel: first clock should be host. + - if a USB DRD channel: first clock should be host and second + one should be peripheral + + big-endian: + $ref: /schemas/types.yaml#/definitions/flag + description: + Set this flag for HCDs with big endian descriptors and big + endian registers. + + big-endian-desc: + $ref: /schemas/types.yaml#/definitions/flag + description: + Set this flag for HCDs with big endian descriptors. + + big-endian-regs: + $ref: /schemas/types.yaml#/definitions/flag + description: + Set this flag for HCDs with big endian registers. + + remote-wakeup-connected: + $ref: /schemas/types.yaml#/definitions/flag + description: + Remote wakeup is wired on the platform. + + no-big-frame-no: + $ref: /schemas/types.yaml#/definitions/flag + description: + Set if frame_no lives in bits [15:0] of HCCA + + num-ports: + $ref: /schemas/types.yaml#/definitions/uint32 + description: + Overrides the detected port count + + phys: true + +required: + - compatible + - reg + - interrupts + +additionalProperties: false + +examples: + - | + ohci0: usb@1c14400 { + compatible = "allwinner,sun4i-a10-ohci", "generic-ohci"; + reg = <0x01c14400 0x100>; + interrupts = <64>; + clocks = <&usb_clk 6>, <&ahb_gates 2>; + phys = <&usbphy 1>; + }; + +... diff --git a/Documentation/devicetree/bindings/usb/usb-ohci.txt b/Documentation/devicetree/bindings/usb/usb-ohci.txt deleted file mode 100644 index aaaa5255c972..000000000000 --- a/Documentation/devicetree/bindings/usb/usb-ohci.txt +++ /dev/null @@ -1,35 +0,0 @@ -USB OHCI controllers - -Required properties: -- compatible : "generic-ohci" -- reg : ohci controller register range (address and length) -- interrupts : ohci controller interrupt - -Optional properties: -- big-endian-regs : boolean, set this for hcds with big-endian registers -- big-endian-desc : boolean, set this for hcds with big-endian descriptors -- big-endian : boolean, for hcds with big-endian-regs + big-endian-desc -- no-big-frame-no : boolean, set if frame_no lives in bits [15:0] of HCCA -- remote-wakeup-connected: remote wakeup is wired on the platform -- num-ports : u32, to override the detected port count -- clocks : a list of phandle + clock specifier pairs. In case of Renesas - R-Car Gen3 SoCs: - - if a host only channel: first clock should be host. - - if a USB DRD channel: first clock should be host and second one - should be peripheral. -- phys : see usb-hcd.txt in the current directory -- resets : a list of phandle + reset specifier pairs - -additionally the properties from usb-hcd.txt (in the current directory) are -supported. - -Example: - - ohci0: usb@1c14400 { - compatible = "allwinner,sun4i-a10-ohci", "generic-ohci"; - reg = <0x01c14400 0x100>; - interrupts = <64>; - clocks = <&usb_clk 6>, <&ahb_gates 2>; - phys = <&usbphy 1>; - phy-names = "usb"; - }; -- cgit v1.2.3 From c3e2485d5f4f8c605c67c0c0ac237be45438edd1 Mon Sep 17 00:00:00 2001 From: Maxime Ripard Date: Tue, 16 Apr 2019 10:27:59 +0200 Subject: dt-bindings: usb: Convert the generic EHCI binding to YAML The generic EHCI binding is used by many controllers that are using the EHCI spec. Convert that binding to a YAML description to enable the validation on all the nodes using that binding. Signed-off-by: Maxime Ripard Acked-by: Chen-Yu Tsai Signed-off-by: Greg Kroah-Hartman --- .../devicetree/bindings/usb/generic-ehci.yaml | 95 ++++++++++++++++++++++ Documentation/devicetree/bindings/usb/usb-ehci.txt | 46 ----------- 2 files changed, 95 insertions(+), 46 deletions(-) create mode 100644 Documentation/devicetree/bindings/usb/generic-ehci.yaml delete mode 100644 Documentation/devicetree/bindings/usb/usb-ehci.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/usb/generic-ehci.yaml b/Documentation/devicetree/bindings/usb/generic-ehci.yaml new file mode 100644 index 000000000000..d3b4f6415920 --- /dev/null +++ b/Documentation/devicetree/bindings/usb/generic-ehci.yaml @@ -0,0 +1,95 @@ +# SPDX-License-Identifier: GPL-2.0 +%YAML 1.2 +--- +$id: http://devicetree.org/schemas/usb/generic-ehci.yaml# +$schema: http://devicetree.org/meta-schemas/core.yaml# + +title: USB EHCI Controller Device Tree Bindings + +allOf: + - $ref: "usb-hcd.yaml" + +maintainers: + - Greg Kroah-Hartman + +properties: + compatible: + contains: + const: generic-ehci + + reg: + maxItems: 1 + + interrupts: + maxItems: 1 + + resets: + minItems: 1 + maxItems: 4 + + clocks: + minItems: 1 + maxItems: 4 + description: | + In case the Renesas R-Car Gen3 SoCs: + - if a host only channel: first clock should be host. + - if a USB DRD channel: first clock should be host and second + one should be peripheral + + big-endian: + $ref: /schemas/types.yaml#/definitions/flag + description: + Set this flag for HCDs with big endian descriptors and big + endian registers. + + big-endian-desc: + $ref: /schemas/types.yaml#/definitions/flag + description: + Set this flag for HCDs with big endian descriptors. + + big-endian-regs: + $ref: /schemas/types.yaml#/definitions/flag + description: + Set this flag for HCDs with big endian registers. + + has-transaction-translator: + $ref: /schemas/types.yaml#/definitions/flag + description: + Set this flag if EHCI has a Transaction Translator built into + the root hub. + + needs-reset-on-resume: + $ref: /schemas/types.yaml#/definitions/flag + description: + Set this flag to force EHCI reset after resume. + + phys: true + +required: + - compatible + - reg + - interrupts + +additionalProperties: false + +examples: + - | + ehci@e0000300 { + compatible = "ibm,usb-ehci-440epx", "generic-ehci"; + interrupt-parent = <&UIC0>; + interrupts = <0x1a 4>; + reg = <0 0xe0000300 90 0 0xe0000390 70>; + big-endian; + }; + + - | + ehci0: usb@1c14000 { + compatible = "allwinner,sun4i-a10-ehci", "generic-ehci"; + reg = <0x01c14000 0x100>; + interrupts = <39>; + clocks = <&ahb_gates 1>; + phys = <&usbphy 1>; + phy-names = "usb"; + }; + +... diff --git a/Documentation/devicetree/bindings/usb/usb-ehci.txt b/Documentation/devicetree/bindings/usb/usb-ehci.txt deleted file mode 100644 index 406252d14c6b..000000000000 --- a/Documentation/devicetree/bindings/usb/usb-ehci.txt +++ /dev/null @@ -1,46 +0,0 @@ -USB EHCI controllers - -Required properties: - - compatible : should be "generic-ehci". - - reg : should contain at least address and length of the standard EHCI - register set for the device. Optional platform-dependent registers - (debug-port or other) can be also specified here, but only after - definition of standard EHCI registers. - - interrupts : one EHCI interrupt should be described here. - -Optional properties: - - big-endian-regs : boolean, set this for hcds with big-endian registers - - big-endian-desc : boolean, set this for hcds with big-endian descriptors - - big-endian : boolean, for hcds with big-endian-regs + big-endian-desc - - needs-reset-on-resume : boolean, set this to force EHCI reset after resume - - has-transaction-translator : boolean, set this if EHCI have a Transaction - Translator built into the root hub. - - clocks : a list of phandle + clock specifier pairs. In case of Renesas - R-Car Gen3 SoCs: - - if a host only channel: first clock should be host. - - if a USB DRD channel: first clock should be host and second one - should be peripheral. - - phys : see usb-hcd.txt in the current directory - - resets : phandle + reset specifier pair - -additionally the properties from usb-hcd.txt (in the current directory) are -supported. - -Example (Sequoia 440EPx): - ehci@e0000300 { - compatible = "ibm,usb-ehci-440epx", "usb-ehci"; - interrupt-parent = <&UIC0>; - interrupts = <1a 4>; - reg = <0 e0000300 90 0 e0000390 70>; - big-endian; - }; - -Example (Allwinner sun4i A10 SoC): - ehci0: usb@1c14000 { - compatible = "allwinner,sun4i-a10-ehci", "generic-ehci"; - reg = <0x01c14000 0x100>; - interrupts = <39>; - clocks = <&ahb_gates 1>; - phys = <&usbphy 1>; - phy-names = "usb"; - }; -- cgit v1.2.3 From 18073da76973f8ce75ee1d622f2a4d2d1b6121a8 Mon Sep 17 00:00:00 2001 From: Fabien Parent Date: Sat, 23 Mar 2019 22:16:10 +0100 Subject: dt-bindings: i2c: i2c-mtk: add support for MT8516 Add binding documentation of i2c-mtk for MT8516 SoC. Signed-off-by: Fabien Parent Acked-by: Rob Herring Acked-by: Matthias Brugger Signed-off-by: Wolfram Sang --- Documentation/devicetree/bindings/i2c/i2c-mtk.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/i2c/i2c-mtk.txt b/Documentation/devicetree/bindings/i2c/i2c-mtk.txt index b052f29e72f0..68f6d73a8b73 100644 --- a/Documentation/devicetree/bindings/i2c/i2c-mtk.txt +++ b/Documentation/devicetree/bindings/i2c/i2c-mtk.txt @@ -13,6 +13,7 @@ Required properties: "mediatek,mt7629-i2c", "mediatek,mt2712-i2c": for MediaTek MT7629 "mediatek,mt8173-i2c": for MediaTek MT8173 "mediatek,mt8183-i2c": for MediaTek MT8183 + "mediatek,mt8516-i2c", "mediatek,mt2712-i2c": for MediaTek MT8516 - reg: physical base address of the controller and dma base, length of memory mapped region. - interrupts: interrupt number to the cpu. -- cgit v1.2.3 From c110ae578ca0a10064dfbda3d786d6a733b9fe69 Mon Sep 17 00:00:00 2001 From: Paolo Bonzini Date: Thu, 28 Mar 2019 17:24:03 +0100 Subject: kvm: move KVM_CAP_NR_MEMSLOTS to common code All architectures except MIPS were defining it in the same way, and memory slots are handled entirely by common code so there is no point in keeping the definition per-architecture. Signed-off-by: Paolo Bonzini --- Documentation/virtual/kvm/api.txt | 5 ++--- arch/powerpc/kvm/powerpc.c | 3 --- arch/s390/kvm/kvm-s390.c | 3 --- arch/x86/kvm/x86.c | 3 --- virt/kvm/arm/arm.c | 3 --- virt/kvm/kvm_main.c | 2 ++ 6 files changed, 4 insertions(+), 15 deletions(-) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/api.txt b/Documentation/virtual/kvm/api.txt index 67068c47c591..b62ad0d94234 100644 --- a/Documentation/virtual/kvm/api.txt +++ b/Documentation/virtual/kvm/api.txt @@ -1117,9 +1117,8 @@ struct kvm_userspace_memory_region { This ioctl allows the user to create, modify or delete a guest physical memory slot. Bits 0-15 of "slot" specify the slot id and this value should be less than the maximum number of user memory slots supported per -VM. The maximum allowed slots can be queried using KVM_CAP_NR_MEMSLOTS, -if this capability is supported by the architecture. Slots may not -overlap in guest physical address space. +VM. The maximum allowed slots can be queried using KVM_CAP_NR_MEMSLOTS. +Slots may not overlap in guest physical address space. If KVM_CAP_MULTI_ADDRESS_SPACE is available, bits 16-31 of "slot" specifies the address space which is being modified. They must be diff --git a/arch/powerpc/kvm/powerpc.c b/arch/powerpc/kvm/powerpc.c index 8885377ec3e0..92910b7c5bcc 100644 --- a/arch/powerpc/kvm/powerpc.c +++ b/arch/powerpc/kvm/powerpc.c @@ -644,9 +644,6 @@ int kvm_vm_ioctl_check_extension(struct kvm *kvm, long ext) else r = num_online_cpus(); break; - case KVM_CAP_NR_MEMSLOTS: - r = KVM_USER_MEM_SLOTS; - break; case KVM_CAP_MAX_VCPUS: r = KVM_MAX_VCPUS; break; diff --git a/arch/s390/kvm/kvm-s390.c b/arch/s390/kvm/kvm-s390.c index 4638303ba6a8..28f35d2b06cb 100644 --- a/arch/s390/kvm/kvm-s390.c +++ b/arch/s390/kvm/kvm-s390.c @@ -513,9 +513,6 @@ int kvm_vm_ioctl_check_extension(struct kvm *kvm, long ext) else if (sclp.has_esca && sclp.has_64bscao) r = KVM_S390_ESCA_CPU_SLOTS; break; - case KVM_CAP_NR_MEMSLOTS: - r = KVM_USER_MEM_SLOTS; - break; case KVM_CAP_S390_COW: r = MACHINE_HAS_ESOP; break; diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c index 38440316a806..6c27d224f744 100644 --- a/arch/x86/kvm/x86.c +++ b/arch/x86/kvm/x86.c @@ -3093,9 +3093,6 @@ int kvm_vm_ioctl_check_extension(struct kvm *kvm, long ext) case KVM_CAP_MAX_VCPUS: r = KVM_MAX_VCPUS; break; - case KVM_CAP_NR_MEMSLOTS: - r = KVM_USER_MEM_SLOTS; - break; case KVM_CAP_PV_MMU: /* obsolete */ r = 0; break; diff --git a/virt/kvm/arm/arm.c b/virt/kvm/arm/arm.c index 99c37384ba7b..be4ec5f3ba5f 100644 --- a/virt/kvm/arm/arm.c +++ b/virt/kvm/arm/arm.c @@ -224,9 +224,6 @@ int kvm_vm_ioctl_check_extension(struct kvm *kvm, long ext) case KVM_CAP_MAX_VCPUS: r = KVM_MAX_VCPUS; break; - case KVM_CAP_NR_MEMSLOTS: - r = KVM_USER_MEM_SLOTS; - break; case KVM_CAP_MSI_DEVID: if (!kvm) r = -EINVAL; diff --git a/virt/kvm/kvm_main.c b/virt/kvm/kvm_main.c index dc8edc97ba85..684b67252cd5 100644 --- a/virt/kvm/kvm_main.c +++ b/virt/kvm/kvm_main.c @@ -3063,6 +3063,8 @@ static long kvm_vm_ioctl_check_extension_generic(struct kvm *kvm, long arg) #endif case KVM_CAP_MAX_VCPU_ID: return KVM_MAX_VCPU_ID; + case KVM_CAP_NR_MEMSLOTS: + return KVM_USER_MEM_SLOTS; default: break; } -- cgit v1.2.3 From 3df5ffd2e5dc11df9dd215c7005e681e44402584 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Mon, 15 Apr 2019 17:00:05 -0300 Subject: docs: trace: fix some Sphinx warnings There are some warnings produced when building trace. Fix them. Signed-off-by: Mauro Carvalho Chehab Acked-by: Steven Rostedt (VMware) Signed-off-by: Jonathan Corbet --- Documentation/trace/ftrace.rst | 1 + Documentation/trace/histogram.rst | 94 ++++++++++++++++++++------------------- 2 files changed, 49 insertions(+), 46 deletions(-) (limited to 'Documentation') diff --git a/Documentation/trace/ftrace.rst b/Documentation/trace/ftrace.rst index 7c5e6d6ab5d1..c3b9bd2fd512 100644 --- a/Documentation/trace/ftrace.rst +++ b/Documentation/trace/ftrace.rst @@ -1404,6 +1404,7 @@ trace has provided some very helpful debugging information. If we prefer function graph output instead of function, we can set display-graph option:: + with echo 1 > options/display-graph # tracer: irqsoff diff --git a/Documentation/trace/histogram.rst b/Documentation/trace/histogram.rst index 0ea59d45aef1..f95d94d19c22 100644 --- a/Documentation/trace/histogram.rst +++ b/Documentation/trace/histogram.rst @@ -2133,33 +2133,33 @@ The following commonly-used handler.action pairs are available: the end the event that triggered the snapshot (in this case you can verify the timestamps between the sched_waking and sched_switch events, which should match the time displayed in the - global maximum): - - # cat /sys/kernel/debug/tracing/snapshot - - <...>-2103 [005] d..3 309.873125: sched_switch: prev_comm=cyclictest prev_pid=2103 prev_prio=19 prev_state=D ==> next_comm=swapper/5 next_pid=0 next_prio=120 - -0 [005] d.h3 309.873611: sched_waking: comm=cyclictest pid=2102 prio=19 target_cpu=005 - -0 [005] dNh4 309.873613: sched_wakeup: comm=cyclictest pid=2102 prio=19 target_cpu=005 - -0 [005] d..3 309.873616: sched_switch: prev_comm=swapper/5 prev_pid=0 prev_prio=120 prev_state=S ==> next_comm=cyclictest next_pid=2102 next_prio=19 - <...>-2102 [005] d..3 309.873625: sched_switch: prev_comm=cyclictest prev_pid=2102 prev_prio=19 prev_state=D ==> next_comm=swapper/5 next_pid=0 next_prio=120 - -0 [005] d.h3 309.874624: sched_waking: comm=cyclictest pid=2102 prio=19 target_cpu=005 - -0 [005] dNh4 309.874626: sched_wakeup: comm=cyclictest pid=2102 prio=19 target_cpu=005 - -0 [005] dNh3 309.874628: sched_waking: comm=cyclictest pid=2103 prio=19 target_cpu=005 - -0 [005] dNh4 309.874630: sched_wakeup: comm=cyclictest pid=2103 prio=19 target_cpu=005 - -0 [005] d..3 309.874633: sched_switch: prev_comm=swapper/5 prev_pid=0 prev_prio=120 prev_state=S ==> next_comm=cyclictest next_pid=2102 next_prio=19 - -0 [004] d.h3 309.874757: sched_waking: comm=gnome-terminal- pid=1699 prio=120 target_cpu=004 - -0 [004] dNh4 309.874762: sched_wakeup: comm=gnome-terminal- pid=1699 prio=120 target_cpu=004 - -0 [004] d..3 309.874766: sched_switch: prev_comm=swapper/4 prev_pid=0 prev_prio=120 prev_state=S ==> next_comm=gnome-terminal- next_pid=1699 next_prio=120 - gnome-terminal--1699 [004] d.h2 309.874941: sched_stat_runtime: comm=gnome-terminal- pid=1699 runtime=180706 [ns] vruntime=1126870572 [ns] - -0 [003] d.s4 309.874956: sched_waking: comm=rcu_sched pid=9 prio=120 target_cpu=007 - -0 [003] d.s5 309.874960: sched_wake_idle_without_ipi: cpu=7 - -0 [003] d.s5 309.874961: sched_wakeup: comm=rcu_sched pid=9 prio=120 target_cpu=007 - -0 [007] d..3 309.874963: sched_switch: prev_comm=swapper/7 prev_pid=0 prev_prio=120 prev_state=S ==> next_comm=rcu_sched next_pid=9 next_prio=120 - rcu_sched-9 [007] d..3 309.874973: sched_stat_runtime: comm=rcu_sched pid=9 runtime=13646 [ns] vruntime=22531430286 [ns] - rcu_sched-9 [007] d..3 309.874978: sched_switch: prev_comm=rcu_sched prev_pid=9 prev_prio=120 prev_state=R+ ==> next_comm=swapper/7 next_pid=0 next_prio=120 - <...>-2102 [005] d..4 309.874994: sched_migrate_task: comm=cyclictest pid=2103 prio=19 orig_cpu=5 dest_cpu=1 - <...>-2102 [005] d..4 309.875185: sched_wake_idle_without_ipi: cpu=1 - -0 [001] d..3 309.875200: sched_switch: prev_comm=swapper/1 prev_pid=0 prev_prio=120 prev_state=S ==> next_comm=cyclictest next_pid=2103 next_prio=19 + global maximum):: + + # cat /sys/kernel/debug/tracing/snapshot + + <...>-2103 [005] d..3 309.873125: sched_switch: prev_comm=cyclictest prev_pid=2103 prev_prio=19 prev_state=D ==> next_comm=swapper/5 next_pid=0 next_prio=120 + -0 [005] d.h3 309.873611: sched_waking: comm=cyclictest pid=2102 prio=19 target_cpu=005 + -0 [005] dNh4 309.873613: sched_wakeup: comm=cyclictest pid=2102 prio=19 target_cpu=005 + -0 [005] d..3 309.873616: sched_switch: prev_comm=swapper/5 prev_pid=0 prev_prio=120 prev_state=S ==> next_comm=cyclictest next_pid=2102 next_prio=19 + <...>-2102 [005] d..3 309.873625: sched_switch: prev_comm=cyclictest prev_pid=2102 prev_prio=19 prev_state=D ==> next_comm=swapper/5 next_pid=0 next_prio=120 + -0 [005] d.h3 309.874624: sched_waking: comm=cyclictest pid=2102 prio=19 target_cpu=005 + -0 [005] dNh4 309.874626: sched_wakeup: comm=cyclictest pid=2102 prio=19 target_cpu=005 + -0 [005] dNh3 309.874628: sched_waking: comm=cyclictest pid=2103 prio=19 target_cpu=005 + -0 [005] dNh4 309.874630: sched_wakeup: comm=cyclictest pid=2103 prio=19 target_cpu=005 + -0 [005] d..3 309.874633: sched_switch: prev_comm=swapper/5 prev_pid=0 prev_prio=120 prev_state=S ==> next_comm=cyclictest next_pid=2102 next_prio=19 + -0 [004] d.h3 309.874757: sched_waking: comm=gnome-terminal- pid=1699 prio=120 target_cpu=004 + -0 [004] dNh4 309.874762: sched_wakeup: comm=gnome-terminal- pid=1699 prio=120 target_cpu=004 + -0 [004] d..3 309.874766: sched_switch: prev_comm=swapper/4 prev_pid=0 prev_prio=120 prev_state=S ==> next_comm=gnome-terminal- next_pid=1699 next_prio=120 + gnome-terminal--1699 [004] d.h2 309.874941: sched_stat_runtime: comm=gnome-terminal- pid=1699 runtime=180706 [ns] vruntime=1126870572 [ns] + -0 [003] d.s4 309.874956: sched_waking: comm=rcu_sched pid=9 prio=120 target_cpu=007 + -0 [003] d.s5 309.874960: sched_wake_idle_without_ipi: cpu=7 + -0 [003] d.s5 309.874961: sched_wakeup: comm=rcu_sched pid=9 prio=120 target_cpu=007 + -0 [007] d..3 309.874963: sched_switch: prev_comm=swapper/7 prev_pid=0 prev_prio=120 prev_state=S ==> next_comm=rcu_sched next_pid=9 next_prio=120 + rcu_sched-9 [007] d..3 309.874973: sched_stat_runtime: comm=rcu_sched pid=9 runtime=13646 [ns] vruntime=22531430286 [ns] + rcu_sched-9 [007] d..3 309.874978: sched_switch: prev_comm=rcu_sched prev_pid=9 prev_prio=120 prev_state=R+ ==> next_comm=swapper/7 next_pid=0 next_prio=120 + <...>-2102 [005] d..4 309.874994: sched_migrate_task: comm=cyclictest pid=2103 prio=19 orig_cpu=5 dest_cpu=1 + <...>-2102 [005] d..4 309.875185: sched_wake_idle_without_ipi: cpu=1 + -0 [001] d..3 309.875200: sched_switch: prev_comm=swapper/1 prev_pid=0 prev_prio=120 prev_state=S ==> next_comm=cyclictest next_pid=2103 next_prio=19 - onchange(var).save(field,.. .) @@ -2213,9 +2213,10 @@ The following commonly-used handler.action pairs are available: following the rest of the fields. If a snaphot was taken, there is also a message indicating that, - along with the value and event that triggered the snapshot: + along with the value and event that triggered the snapshot:: + + # cat /sys/kernel/debug/tracing/events/tcp/tcp_probe/hist - # cat /sys/kernel/debug/tracing/events/tcp/tcp_probe/hist { dport: 1521 } hitcount: 8 changed: 10 snd_wnd: 35456 srtt: 154262 rcv_wnd: 42112 @@ -2228,14 +2229,15 @@ The following commonly-used handler.action pairs are available: { dport: 443 } hitcount: 211 changed: 10 snd_wnd: 26960 srtt: 17379 rcv_wnd: 28800 - Snapshot taken (see tracing/snapshot). Details: + Snapshot taken (see tracing/snapshot). Details:: + triggering value { onchange($cwnd) }: 10 triggered by event with key: { dport: 80 } - Totals: - Hits: 414 - Entries: 4 - Dropped: 0 + Totals: + Hits: 414 + Entries: 4 + Dropped: 0 In the above case, the event that triggered the snapshot has the key with dport == 80. If you look at the bucket that has 80 as @@ -2245,18 +2247,18 @@ The following commonly-used handler.action pairs are available: the global snapshot). And finally, looking at the snapshot data should show at or near - the end the event that triggered the snapshot: - - # cat /sys/kernel/debug/tracing/snapshot - - gnome-shell-1261 [006] dN.3 49.823113: sched_stat_runtime: comm=gnome-shell pid=1261 runtime=49347 [ns] vruntime=1835730389 [ns] - kworker/u16:4-773 [003] d..3 49.823114: sched_switch: prev_comm=kworker/u16:4 prev_pid=773 prev_prio=120 prev_state=R+ ==> next_comm=kworker/3:2 next_pid=135 next_prio=120 - gnome-shell-1261 [006] d..3 49.823114: sched_switch: prev_comm=gnome-shell prev_pid=1261 prev_prio=120 prev_state=R+ ==> next_comm=kworker/6:2 next_pid=387 next_prio=120 - kworker/3:2-135 [003] d..3 49.823118: sched_stat_runtime: comm=kworker/3:2 pid=135 runtime=5339 [ns] vruntime=17815800388 [ns] - kworker/6:2-387 [006] d..3 49.823120: sched_stat_runtime: comm=kworker/6:2 pid=387 runtime=9594 [ns] vruntime=14589605367 [ns] - kworker/6:2-387 [006] d..3 49.823122: sched_switch: prev_comm=kworker/6:2 prev_pid=387 prev_prio=120 prev_state=R+ ==> next_comm=gnome-shell next_pid=1261 next_prio=120 - kworker/3:2-135 [003] d..3 49.823123: sched_switch: prev_comm=kworker/3:2 prev_pid=135 prev_prio=120 prev_state=T ==> next_comm=swapper/3 next_pid=0 next_prio=120 - -0 [004] ..s7 49.823798: tcp_probe: src=10.0.0.10:54326 dest=23.215.104.193:80 mark=0x0 length=32 snd_nxt=0xe3ae2ff5 snd_una=0xe3ae2ecd snd_cwnd=10 ssthresh=2147483647 snd_wnd=28960 srtt=19604 rcv_wnd=29312 + the end the event that triggered the snapshot:: + + # cat /sys/kernel/debug/tracing/snapshot + + gnome-shell-1261 [006] dN.3 49.823113: sched_stat_runtime: comm=gnome-shell pid=1261 runtime=49347 [ns] vruntime=1835730389 [ns] + kworker/u16:4-773 [003] d..3 49.823114: sched_switch: prev_comm=kworker/u16:4 prev_pid=773 prev_prio=120 prev_state=R+ ==> next_comm=kworker/3:2 next_pid=135 next_prio=120 + gnome-shell-1261 [006] d..3 49.823114: sched_switch: prev_comm=gnome-shell prev_pid=1261 prev_prio=120 prev_state=R+ ==> next_comm=kworker/6:2 next_pid=387 next_prio=120 + kworker/3:2-135 [003] d..3 49.823118: sched_stat_runtime: comm=kworker/3:2 pid=135 runtime=5339 [ns] vruntime=17815800388 [ns] + kworker/6:2-387 [006] d..3 49.823120: sched_stat_runtime: comm=kworker/6:2 pid=387 runtime=9594 [ns] vruntime=14589605367 [ns] + kworker/6:2-387 [006] d..3 49.823122: sched_switch: prev_comm=kworker/6:2 prev_pid=387 prev_prio=120 prev_state=R+ ==> next_comm=gnome-shell next_pid=1261 next_prio=120 + kworker/3:2-135 [003] d..3 49.823123: sched_switch: prev_comm=kworker/3:2 prev_pid=135 prev_prio=120 prev_state=T ==> next_comm=swapper/3 next_pid=0 next_prio=120 + -0 [004] ..s7 49.823798: tcp_probe: src=10.0.0.10:54326 dest=23.215.104.193:80 mark=0x0 length=32 snd_nxt=0xe3ae2ff5 snd_una=0xe3ae2ecd snd_cwnd=10 ssthresh=2147483647 snd_wnd=28960 srtt=19604 rcv_wnd=29312 3. User space creating a trigger -------------------------------- -- cgit v1.2.3 From aaba098fe6ce594ae6f963dc041be6307e499f19 Mon Sep 17 00:00:00 2001 From: Andrew Murray Date: Tue, 9 Apr 2019 10:52:40 +0100 Subject: arm64: HWCAP: add support for AT_HWCAP2 As we will exhaust the first 32 bits of AT_HWCAP let's start exposing AT_HWCAP2 to userspace to give us up to 64 caps. Whilst it's possible to use the remaining 32 bits of AT_HWCAP, we prefer to expand into AT_HWCAP2 in order to provide a consistent view to userspace between ILP32 and LP64. However internal to the kernel we prefer to continue to use the full space of elf_hwcap. To reduce complexity and allow for future expansion, we now represent hwcaps in the kernel as ordinals and use a KERNEL_HWCAP_ prefix. This allows us to support automatic feature based module loading for all our hwcaps. We introduce cpu_set_feature to set hwcaps which complements the existing cpu_have_feature helper. These helpers allow us to clean up existing direct uses of elf_hwcap and reduce any future effort required to move beyond 64 caps. For convenience we also introduce cpu_{have,set}_named_feature which makes use of the cpu_feature macro to allow providing a hwcap name without a {KERNEL_}HWCAP_ prefix. Signed-off-by: Andrew Murray [will: use const_ilog2() and tweak documentation] Signed-off-by: Will Deacon --- Documentation/arm64/elf_hwcaps.txt | 13 +++++-- arch/arm64/crypto/aes-ce-ccm-glue.c | 2 +- arch/arm64/crypto/aes-neonbs-glue.c | 2 +- arch/arm64/crypto/chacha-neon-glue.c | 2 +- arch/arm64/crypto/crct10dif-ce-glue.c | 4 +- arch/arm64/crypto/ghash-ce-glue.c | 8 ++-- arch/arm64/crypto/nhpoly1305-neon-glue.c | 2 +- arch/arm64/crypto/sha256-glue.c | 4 +- arch/arm64/include/asm/cpufeature.h | 22 ++++++----- arch/arm64/include/asm/hwcap.h | 52 ++++++++++++++++++++++++- arch/arm64/include/uapi/asm/hwcap.h | 2 +- arch/arm64/kernel/cpufeature.c | 66 ++++++++++++++++---------------- arch/arm64/kernel/cpuinfo.c | 2 +- arch/arm64/kernel/fpsimd.c | 4 +- drivers/clocksource/arm_arch_timer.c | 8 ++++ 15 files changed, 130 insertions(+), 63 deletions(-) (limited to 'Documentation') diff --git a/Documentation/arm64/elf_hwcaps.txt b/Documentation/arm64/elf_hwcaps.txt index 13d6691b37be..11805777031e 100644 --- a/Documentation/arm64/elf_hwcaps.txt +++ b/Documentation/arm64/elf_hwcaps.txt @@ -13,9 +13,9 @@ architected discovery mechanism available to userspace code at EL0. The kernel exposes the presence of these features to userspace through a set of flags called hwcaps, exposed in the auxilliary vector. -Userspace software can test for features by acquiring the AT_HWCAP entry -of the auxilliary vector, and testing whether the relevant flags are -set, e.g. +Userspace software can test for features by acquiring the AT_HWCAP or +AT_HWCAP2 entry of the auxiliary vector, and testing whether the relevant +flags are set, e.g. bool floating_point_is_present(void) { @@ -194,3 +194,10 @@ HWCAP_PACG Functionality implied by ID_AA64ISAR1_EL1.GPA == 0b0001 or ID_AA64ISAR1_EL1.GPI == 0b0001, as described by Documentation/arm64/pointer-authentication.txt. + + +4. Unused AT_HWCAP bits +----------------------- + +For interoperation with userspace, the kernel guarantees that bits 62 +and 63 of AT_HWCAP will always be returned as 0. diff --git a/arch/arm64/crypto/aes-ce-ccm-glue.c b/arch/arm64/crypto/aes-ce-ccm-glue.c index 5fc6f51908fd..036ea77f83bc 100644 --- a/arch/arm64/crypto/aes-ce-ccm-glue.c +++ b/arch/arm64/crypto/aes-ce-ccm-glue.c @@ -372,7 +372,7 @@ static struct aead_alg ccm_aes_alg = { static int __init aes_mod_init(void) { - if (!(elf_hwcap & HWCAP_AES)) + if (!cpu_have_named_feature(AES)) return -ENODEV; return crypto_register_aead(&ccm_aes_alg); } diff --git a/arch/arm64/crypto/aes-neonbs-glue.c b/arch/arm64/crypto/aes-neonbs-glue.c index e7a95a566462..bf1b321ff4c1 100644 --- a/arch/arm64/crypto/aes-neonbs-glue.c +++ b/arch/arm64/crypto/aes-neonbs-glue.c @@ -440,7 +440,7 @@ static int __init aes_init(void) int err; int i; - if (!(elf_hwcap & HWCAP_ASIMD)) + if (!cpu_have_named_feature(ASIMD)) return -ENODEV; err = crypto_register_skciphers(aes_algs, ARRAY_SIZE(aes_algs)); diff --git a/arch/arm64/crypto/chacha-neon-glue.c b/arch/arm64/crypto/chacha-neon-glue.c index bece1d85bd81..cb054f51c917 100644 --- a/arch/arm64/crypto/chacha-neon-glue.c +++ b/arch/arm64/crypto/chacha-neon-glue.c @@ -173,7 +173,7 @@ static struct skcipher_alg algs[] = { static int __init chacha_simd_mod_init(void) { - if (!(elf_hwcap & HWCAP_ASIMD)) + if (!cpu_have_named_feature(ASIMD)) return -ENODEV; return crypto_register_skciphers(algs, ARRAY_SIZE(algs)); diff --git a/arch/arm64/crypto/crct10dif-ce-glue.c b/arch/arm64/crypto/crct10dif-ce-glue.c index dd325829ee44..e81d5bd555c0 100644 --- a/arch/arm64/crypto/crct10dif-ce-glue.c +++ b/arch/arm64/crypto/crct10dif-ce-glue.c @@ -101,7 +101,7 @@ static struct shash_alg crc_t10dif_alg[] = {{ static int __init crc_t10dif_mod_init(void) { - if (elf_hwcap & HWCAP_PMULL) + if (cpu_have_named_feature(PMULL)) return crypto_register_shashes(crc_t10dif_alg, ARRAY_SIZE(crc_t10dif_alg)); else @@ -111,7 +111,7 @@ static int __init crc_t10dif_mod_init(void) static void __exit crc_t10dif_mod_exit(void) { - if (elf_hwcap & HWCAP_PMULL) + if (cpu_have_named_feature(PMULL)) crypto_unregister_shashes(crc_t10dif_alg, ARRAY_SIZE(crc_t10dif_alg)); else diff --git a/arch/arm64/crypto/ghash-ce-glue.c b/arch/arm64/crypto/ghash-ce-glue.c index 791ad422c427..4e69bb78ea89 100644 --- a/arch/arm64/crypto/ghash-ce-glue.c +++ b/arch/arm64/crypto/ghash-ce-glue.c @@ -704,10 +704,10 @@ static int __init ghash_ce_mod_init(void) { int ret; - if (!(elf_hwcap & HWCAP_ASIMD)) + if (!cpu_have_named_feature(ASIMD)) return -ENODEV; - if (elf_hwcap & HWCAP_PMULL) + if (cpu_have_named_feature(PMULL)) ret = crypto_register_shashes(ghash_alg, ARRAY_SIZE(ghash_alg)); else @@ -717,7 +717,7 @@ static int __init ghash_ce_mod_init(void) if (ret) return ret; - if (elf_hwcap & HWCAP_PMULL) { + if (cpu_have_named_feature(PMULL)) { ret = crypto_register_aead(&gcm_aes_alg); if (ret) crypto_unregister_shashes(ghash_alg, @@ -728,7 +728,7 @@ static int __init ghash_ce_mod_init(void) static void __exit ghash_ce_mod_exit(void) { - if (elf_hwcap & HWCAP_PMULL) + if (cpu_have_named_feature(PMULL)) crypto_unregister_shashes(ghash_alg, ARRAY_SIZE(ghash_alg)); else crypto_unregister_shash(ghash_alg); diff --git a/arch/arm64/crypto/nhpoly1305-neon-glue.c b/arch/arm64/crypto/nhpoly1305-neon-glue.c index 22cc32ac9448..38a589044b6c 100644 --- a/arch/arm64/crypto/nhpoly1305-neon-glue.c +++ b/arch/arm64/crypto/nhpoly1305-neon-glue.c @@ -56,7 +56,7 @@ static struct shash_alg nhpoly1305_alg = { static int __init nhpoly1305_mod_init(void) { - if (!(elf_hwcap & HWCAP_ASIMD)) + if (!cpu_have_named_feature(ASIMD)) return -ENODEV; return crypto_register_shash(&nhpoly1305_alg); diff --git a/arch/arm64/crypto/sha256-glue.c b/arch/arm64/crypto/sha256-glue.c index 4aedeaefd61f..0cccdb9cc2c0 100644 --- a/arch/arm64/crypto/sha256-glue.c +++ b/arch/arm64/crypto/sha256-glue.c @@ -173,7 +173,7 @@ static int __init sha256_mod_init(void) if (ret) return ret; - if (elf_hwcap & HWCAP_ASIMD) { + if (cpu_have_named_feature(ASIMD)) { ret = crypto_register_shashes(neon_algs, ARRAY_SIZE(neon_algs)); if (ret) crypto_unregister_shashes(algs, ARRAY_SIZE(algs)); @@ -183,7 +183,7 @@ static int __init sha256_mod_init(void) static void __exit sha256_mod_fini(void) { - if (elf_hwcap & HWCAP_ASIMD) + if (cpu_have_named_feature(ASIMD)) crypto_unregister_shashes(neon_algs, ARRAY_SIZE(neon_algs)); crypto_unregister_shashes(algs, ARRAY_SIZE(algs)); } diff --git a/arch/arm64/include/asm/cpufeature.h b/arch/arm64/include/asm/cpufeature.h index e505e1fbd2b9..347c17046668 100644 --- a/arch/arm64/include/asm/cpufeature.h +++ b/arch/arm64/include/asm/cpufeature.h @@ -14,15 +14,8 @@ #include #include -/* - * In the arm64 world (as in the ARM world), elf_hwcap is used both internally - * in the kernel and for user space to keep track of which optional features - * are supported by the current system. So let's map feature 'x' to HWCAP_x. - * Note that HWCAP_x constants are bit fields so we need to take the log. - */ - -#define MAX_CPU_FEATURES (8 * sizeof(elf_hwcap)) -#define cpu_feature(x) ilog2(HWCAP_ ## x) +#define MAX_CPU_FEATURES 64 +#define cpu_feature(x) KERNEL_HWCAP_ ## x #ifndef __ASSEMBLY__ @@ -400,10 +393,19 @@ extern DECLARE_BITMAP(boot_capabilities, ARM64_NPATCHABLE); bool this_cpu_has_cap(unsigned int cap); +static inline void cpu_set_feature(unsigned int num) +{ + WARN_ON(num >= MAX_CPU_FEATURES); + elf_hwcap |= BIT(num); +} +#define cpu_set_named_feature(name) cpu_set_feature(cpu_feature(name)) + static inline bool cpu_have_feature(unsigned int num) { - return elf_hwcap & (1UL << num); + WARN_ON(num >= MAX_CPU_FEATURES); + return elf_hwcap & BIT(num); } +#define cpu_have_named_feature(name) cpu_have_feature(cpu_feature(name)) /* System capability check for constant caps */ static inline bool __cpus_have_const_cap(int num) diff --git a/arch/arm64/include/asm/hwcap.h b/arch/arm64/include/asm/hwcap.h index 400b80b49595..af868cbe96f8 100644 --- a/arch/arm64/include/asm/hwcap.h +++ b/arch/arm64/include/asm/hwcap.h @@ -40,11 +40,61 @@ #define COMPAT_HWCAP2_CRC32 (1 << 4) #ifndef __ASSEMBLY__ +#include +#include + +/* + * For userspace we represent hwcaps as a collection of HWCAP{,2}_x bitfields + * as described in uapi/asm/hwcap.h. For the kernel we represent hwcaps as + * natural numbers (in a single range of size MAX_CPU_FEATURES) defined here + * with prefix KERNEL_HWCAP_ mapped to their HWCAP{,2}_x counterpart. + * + * Hwcaps should be set and tested within the kernel via the + * cpu_{set,have}_named_feature(feature) where feature is the unique suffix + * of KERNEL_HWCAP_{feature}. + */ +#define __khwcap_feature(x) const_ilog2(HWCAP_ ## x) +#define KERNEL_HWCAP_FP __khwcap_feature(FP) +#define KERNEL_HWCAP_ASIMD __khwcap_feature(ASIMD) +#define KERNEL_HWCAP_EVTSTRM __khwcap_feature(EVTSTRM) +#define KERNEL_HWCAP_AES __khwcap_feature(AES) +#define KERNEL_HWCAP_PMULL __khwcap_feature(PMULL) +#define KERNEL_HWCAP_SHA1 __khwcap_feature(SHA1) +#define KERNEL_HWCAP_SHA2 __khwcap_feature(SHA2) +#define KERNEL_HWCAP_CRC32 __khwcap_feature(CRC32) +#define KERNEL_HWCAP_ATOMICS __khwcap_feature(ATOMICS) +#define KERNEL_HWCAP_FPHP __khwcap_feature(FPHP) +#define KERNEL_HWCAP_ASIMDHP __khwcap_feature(ASIMDHP) +#define KERNEL_HWCAP_CPUID __khwcap_feature(CPUID) +#define KERNEL_HWCAP_ASIMDRDM __khwcap_feature(ASIMDRDM) +#define KERNEL_HWCAP_JSCVT __khwcap_feature(JSCVT) +#define KERNEL_HWCAP_FCMA __khwcap_feature(FCMA) +#define KERNEL_HWCAP_LRCPC __khwcap_feature(LRCPC) +#define KERNEL_HWCAP_DCPOP __khwcap_feature(DCPOP) +#define KERNEL_HWCAP_SHA3 __khwcap_feature(SHA3) +#define KERNEL_HWCAP_SM3 __khwcap_feature(SM3) +#define KERNEL_HWCAP_SM4 __khwcap_feature(SM4) +#define KERNEL_HWCAP_ASIMDDP __khwcap_feature(ASIMDDP) +#define KERNEL_HWCAP_SHA512 __khwcap_feature(SHA512) +#define KERNEL_HWCAP_SVE __khwcap_feature(SVE) +#define KERNEL_HWCAP_ASIMDFHM __khwcap_feature(ASIMDFHM) +#define KERNEL_HWCAP_DIT __khwcap_feature(DIT) +#define KERNEL_HWCAP_USCAT __khwcap_feature(USCAT) +#define KERNEL_HWCAP_ILRCPC __khwcap_feature(ILRCPC) +#define KERNEL_HWCAP_FLAGM __khwcap_feature(FLAGM) +#define KERNEL_HWCAP_SSBS __khwcap_feature(SSBS) +#define KERNEL_HWCAP_SB __khwcap_feature(SB) +#define KERNEL_HWCAP_PACA __khwcap_feature(PACA) +#define KERNEL_HWCAP_PACG __khwcap_feature(PACG) + +#define __khwcap2_feature(x) (const_ilog2(HWCAP2_ ## x) + 32) + /* * This yields a mask that user programs can use to figure out what * instruction set this cpu supports. */ -#define ELF_HWCAP (elf_hwcap) +#define ELF_HWCAP lower_32_bits(elf_hwcap) +#define ELF_HWCAP2 upper_32_bits(elf_hwcap) #ifdef CONFIG_COMPAT #define COMPAT_ELF_HWCAP (compat_elf_hwcap) diff --git a/arch/arm64/include/uapi/asm/hwcap.h b/arch/arm64/include/uapi/asm/hwcap.h index 5f0750c2199c..453b45af80b7 100644 --- a/arch/arm64/include/uapi/asm/hwcap.h +++ b/arch/arm64/include/uapi/asm/hwcap.h @@ -18,7 +18,7 @@ #define _UAPI__ASM_HWCAP_H /* - * HWCAP flags - for elf_hwcap (in kernel) and AT_HWCAP + * HWCAP flags - for AT_HWCAP */ #define HWCAP_FP (1 << 0) #define HWCAP_ASIMD (1 << 1) diff --git a/arch/arm64/kernel/cpufeature.c b/arch/arm64/kernel/cpufeature.c index 4061de10cea6..986ceeacd19f 100644 --- a/arch/arm64/kernel/cpufeature.c +++ b/arch/arm64/kernel/cpufeature.c @@ -1571,39 +1571,39 @@ static const struct arm64_cpu_capabilities ptr_auth_hwcap_gen_matches[] = { #endif static const struct arm64_cpu_capabilities arm64_elf_hwcaps[] = { - HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_AES_SHIFT, FTR_UNSIGNED, 2, CAP_HWCAP, HWCAP_PMULL), - HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_AES_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, HWCAP_AES), - HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_SHA1_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, HWCAP_SHA1), - HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_SHA2_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, HWCAP_SHA2), - HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_SHA2_SHIFT, FTR_UNSIGNED, 2, CAP_HWCAP, HWCAP_SHA512), - HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_CRC32_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, HWCAP_CRC32), - HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_ATOMICS_SHIFT, FTR_UNSIGNED, 2, CAP_HWCAP, HWCAP_ATOMICS), - HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_RDM_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, HWCAP_ASIMDRDM), - HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_SHA3_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, HWCAP_SHA3), - HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_SM3_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, HWCAP_SM3), - HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_SM4_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, HWCAP_SM4), - HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_DP_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, HWCAP_ASIMDDP), - HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_FHM_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, HWCAP_ASIMDFHM), - HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_TS_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, HWCAP_FLAGM), - HWCAP_CAP(SYS_ID_AA64PFR0_EL1, ID_AA64PFR0_FP_SHIFT, FTR_SIGNED, 0, CAP_HWCAP, HWCAP_FP), - HWCAP_CAP(SYS_ID_AA64PFR0_EL1, ID_AA64PFR0_FP_SHIFT, FTR_SIGNED, 1, CAP_HWCAP, HWCAP_FPHP), - HWCAP_CAP(SYS_ID_AA64PFR0_EL1, ID_AA64PFR0_ASIMD_SHIFT, FTR_SIGNED, 0, CAP_HWCAP, HWCAP_ASIMD), - HWCAP_CAP(SYS_ID_AA64PFR0_EL1, ID_AA64PFR0_ASIMD_SHIFT, FTR_SIGNED, 1, CAP_HWCAP, HWCAP_ASIMDHP), - HWCAP_CAP(SYS_ID_AA64PFR0_EL1, ID_AA64PFR0_DIT_SHIFT, FTR_SIGNED, 1, CAP_HWCAP, HWCAP_DIT), - HWCAP_CAP(SYS_ID_AA64ISAR1_EL1, ID_AA64ISAR1_DPB_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, HWCAP_DCPOP), - HWCAP_CAP(SYS_ID_AA64ISAR1_EL1, ID_AA64ISAR1_JSCVT_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, HWCAP_JSCVT), - HWCAP_CAP(SYS_ID_AA64ISAR1_EL1, ID_AA64ISAR1_FCMA_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, HWCAP_FCMA), - HWCAP_CAP(SYS_ID_AA64ISAR1_EL1, ID_AA64ISAR1_LRCPC_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, HWCAP_LRCPC), - HWCAP_CAP(SYS_ID_AA64ISAR1_EL1, ID_AA64ISAR1_LRCPC_SHIFT, FTR_UNSIGNED, 2, CAP_HWCAP, HWCAP_ILRCPC), - HWCAP_CAP(SYS_ID_AA64ISAR1_EL1, ID_AA64ISAR1_SB_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, HWCAP_SB), - HWCAP_CAP(SYS_ID_AA64MMFR2_EL1, ID_AA64MMFR2_AT_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, HWCAP_USCAT), + HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_AES_SHIFT, FTR_UNSIGNED, 2, CAP_HWCAP, KERNEL_HWCAP_PMULL), + HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_AES_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_AES), + HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_SHA1_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_SHA1), + HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_SHA2_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_SHA2), + HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_SHA2_SHIFT, FTR_UNSIGNED, 2, CAP_HWCAP, KERNEL_HWCAP_SHA512), + HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_CRC32_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_CRC32), + HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_ATOMICS_SHIFT, FTR_UNSIGNED, 2, CAP_HWCAP, KERNEL_HWCAP_ATOMICS), + HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_RDM_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_ASIMDRDM), + HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_SHA3_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_SHA3), + HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_SM3_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_SM3), + HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_SM4_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_SM4), + HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_DP_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_ASIMDDP), + HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_FHM_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_ASIMDFHM), + HWCAP_CAP(SYS_ID_AA64ISAR0_EL1, ID_AA64ISAR0_TS_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_FLAGM), + HWCAP_CAP(SYS_ID_AA64PFR0_EL1, ID_AA64PFR0_FP_SHIFT, FTR_SIGNED, 0, CAP_HWCAP, KERNEL_HWCAP_FP), + HWCAP_CAP(SYS_ID_AA64PFR0_EL1, ID_AA64PFR0_FP_SHIFT, FTR_SIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_FPHP), + HWCAP_CAP(SYS_ID_AA64PFR0_EL1, ID_AA64PFR0_ASIMD_SHIFT, FTR_SIGNED, 0, CAP_HWCAP, KERNEL_HWCAP_ASIMD), + HWCAP_CAP(SYS_ID_AA64PFR0_EL1, ID_AA64PFR0_ASIMD_SHIFT, FTR_SIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_ASIMDHP), + HWCAP_CAP(SYS_ID_AA64PFR0_EL1, ID_AA64PFR0_DIT_SHIFT, FTR_SIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_DIT), + HWCAP_CAP(SYS_ID_AA64ISAR1_EL1, ID_AA64ISAR1_DPB_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_DCPOP), + HWCAP_CAP(SYS_ID_AA64ISAR1_EL1, ID_AA64ISAR1_JSCVT_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_JSCVT), + HWCAP_CAP(SYS_ID_AA64ISAR1_EL1, ID_AA64ISAR1_FCMA_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_FCMA), + HWCAP_CAP(SYS_ID_AA64ISAR1_EL1, ID_AA64ISAR1_LRCPC_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_LRCPC), + HWCAP_CAP(SYS_ID_AA64ISAR1_EL1, ID_AA64ISAR1_LRCPC_SHIFT, FTR_UNSIGNED, 2, CAP_HWCAP, KERNEL_HWCAP_ILRCPC), + HWCAP_CAP(SYS_ID_AA64ISAR1_EL1, ID_AA64ISAR1_SB_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_SB), + HWCAP_CAP(SYS_ID_AA64MMFR2_EL1, ID_AA64MMFR2_AT_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_USCAT), #ifdef CONFIG_ARM64_SVE - HWCAP_CAP(SYS_ID_AA64PFR0_EL1, ID_AA64PFR0_SVE_SHIFT, FTR_UNSIGNED, ID_AA64PFR0_SVE, CAP_HWCAP, HWCAP_SVE), + HWCAP_CAP(SYS_ID_AA64PFR0_EL1, ID_AA64PFR0_SVE_SHIFT, FTR_UNSIGNED, ID_AA64PFR0_SVE, CAP_HWCAP, KERNEL_HWCAP_SVE), #endif - HWCAP_CAP(SYS_ID_AA64PFR1_EL1, ID_AA64PFR1_SSBS_SHIFT, FTR_UNSIGNED, ID_AA64PFR1_SSBS_PSTATE_INSNS, CAP_HWCAP, HWCAP_SSBS), + HWCAP_CAP(SYS_ID_AA64PFR1_EL1, ID_AA64PFR1_SSBS_SHIFT, FTR_UNSIGNED, ID_AA64PFR1_SSBS_PSTATE_INSNS, CAP_HWCAP, KERNEL_HWCAP_SSBS), #ifdef CONFIG_ARM64_PTR_AUTH - HWCAP_MULTI_CAP(ptr_auth_hwcap_addr_matches, CAP_HWCAP, HWCAP_PACA), - HWCAP_MULTI_CAP(ptr_auth_hwcap_gen_matches, CAP_HWCAP, HWCAP_PACG), + HWCAP_MULTI_CAP(ptr_auth_hwcap_addr_matches, CAP_HWCAP, KERNEL_HWCAP_PACA), + HWCAP_MULTI_CAP(ptr_auth_hwcap_gen_matches, CAP_HWCAP, KERNEL_HWCAP_PACG), #endif {}, }; @@ -1623,7 +1623,7 @@ static void __init cap_set_elf_hwcap(const struct arm64_cpu_capabilities *cap) { switch (cap->hwcap_type) { case CAP_HWCAP: - elf_hwcap |= cap->hwcap; + cpu_set_feature(cap->hwcap); break; #ifdef CONFIG_COMPAT case CAP_COMPAT_HWCAP: @@ -1646,7 +1646,7 @@ static bool cpus_have_elf_hwcap(const struct arm64_cpu_capabilities *cap) switch (cap->hwcap_type) { case CAP_HWCAP: - rc = (elf_hwcap & cap->hwcap) != 0; + rc = cpu_have_feature(cap->hwcap); break; #ifdef CONFIG_COMPAT case CAP_COMPAT_HWCAP: @@ -1667,7 +1667,7 @@ static bool cpus_have_elf_hwcap(const struct arm64_cpu_capabilities *cap) static void __init setup_elf_hwcaps(const struct arm64_cpu_capabilities *hwcaps) { /* We support emulation of accesses to CPU ID feature registers */ - elf_hwcap |= HWCAP_CPUID; + cpu_set_named_feature(CPUID); for (; hwcaps->matches; hwcaps++) if (hwcaps->matches(hwcaps, cpucap_default_scope(hwcaps))) cap_set_elf_hwcap(hwcaps); diff --git a/arch/arm64/kernel/cpuinfo.c b/arch/arm64/kernel/cpuinfo.c index ca0685f33900..810db95f293f 100644 --- a/arch/arm64/kernel/cpuinfo.c +++ b/arch/arm64/kernel/cpuinfo.c @@ -167,7 +167,7 @@ static int c_show(struct seq_file *m, void *v) #endif /* CONFIG_COMPAT */ } else { for (j = 0; hwcap_str[j]; j++) - if (elf_hwcap & (1 << j)) + if (cpu_have_feature(j)) seq_printf(m, " %s", hwcap_str[j]); } seq_puts(m, "\n"); diff --git a/arch/arm64/kernel/fpsimd.c b/arch/arm64/kernel/fpsimd.c index 5ebe73b69961..735cf1f8b109 100644 --- a/arch/arm64/kernel/fpsimd.c +++ b/arch/arm64/kernel/fpsimd.c @@ -1258,14 +1258,14 @@ static inline void fpsimd_hotplug_init(void) { } */ static int __init fpsimd_init(void) { - if (elf_hwcap & HWCAP_FP) { + if (cpu_have_named_feature(FP)) { fpsimd_pm_init(); fpsimd_hotplug_init(); } else { pr_notice("Floating-point is not implemented\n"); } - if (!(elf_hwcap & HWCAP_ASIMD)) + if (!cpu_have_named_feature(ASIMD)) pr_notice("Advanced SIMD is not implemented\n"); return sve_sysctl_init(); diff --git a/drivers/clocksource/arm_arch_timer.c b/drivers/clocksource/arm_arch_timer.c index aa4ec53281ce..6cc8aff83805 100644 --- a/drivers/clocksource/arm_arch_timer.c +++ b/drivers/clocksource/arm_arch_timer.c @@ -833,7 +833,11 @@ static void arch_timer_evtstrm_enable(int divider) cntkctl |= (divider << ARCH_TIMER_EVT_TRIGGER_SHIFT) | ARCH_TIMER_VIRT_EVT_EN; arch_timer_set_cntkctl(cntkctl); +#ifdef CONFIG_ARM64 + cpu_set_named_feature(EVTSTRM); +#else elf_hwcap |= HWCAP_EVTSTRM; +#endif #ifdef CONFIG_COMPAT compat_elf_hwcap |= COMPAT_HWCAP_EVTSTRM; #endif @@ -1055,7 +1059,11 @@ static int arch_timer_cpu_pm_notify(struct notifier_block *self, } else if (action == CPU_PM_ENTER_FAILED || action == CPU_PM_EXIT) { arch_timer_set_cntkctl(__this_cpu_read(saved_cntkctl)); +#ifdef CONFIG_ARM64 + if (cpu_have_named_feature(EVTSTRM)) +#else if (elf_hwcap & HWCAP_EVTSTRM) +#endif cpumask_set_cpu(smp_processor_id(), &evtstrm_available); } return NOTIFY_OK; -- cgit v1.2.3 From 671db581815faf17cbedd7fcbc48823a247d90b1 Mon Sep 17 00:00:00 2001 From: Andrew Murray Date: Tue, 9 Apr 2019 10:52:43 +0100 Subject: arm64: Expose DC CVADP to userspace ARMv8.5 builds upon the ARMv8.2 DC CVAP instruction by introducing a DC CVADP instruction which cleans the data cache to the point of deep persistence. Let's expose this support via the arm64 ELF hwcaps. Signed-off-by: Andrew Murray Reviewed-by: Dave Martin Signed-off-by: Will Deacon --- Documentation/arm64/elf_hwcaps.txt | 4 ++++ arch/arm64/include/asm/hwcap.h | 1 + arch/arm64/include/uapi/asm/hwcap.h | 5 +++++ arch/arm64/kernel/cpufeature.c | 1 + arch/arm64/kernel/cpuinfo.c | 1 + 5 files changed, 12 insertions(+) (limited to 'Documentation') diff --git a/Documentation/arm64/elf_hwcaps.txt b/Documentation/arm64/elf_hwcaps.txt index 11805777031e..55431fd2a67a 100644 --- a/Documentation/arm64/elf_hwcaps.txt +++ b/Documentation/arm64/elf_hwcaps.txt @@ -135,6 +135,10 @@ HWCAP_DCPOP Functionality implied by ID_AA64ISAR1_EL1.DPB == 0b0001. +HWCAP2_DCPODP + + Functionality implied by ID_AA64ISAR1_EL1.DPB == 0b0010. + HWCAP_SHA3 Functionality implied by ID_AA64ISAR0_EL1.SHA3 == 0b0001. diff --git a/arch/arm64/include/asm/hwcap.h b/arch/arm64/include/asm/hwcap.h index a843b6efce5b..f78c86c64e68 100644 --- a/arch/arm64/include/asm/hwcap.h +++ b/arch/arm64/include/asm/hwcap.h @@ -88,6 +88,7 @@ #define KERNEL_HWCAP_PACG __khwcap_feature(PACG) #define __khwcap2_feature(x) (const_ilog2(HWCAP2_ ## x) + 32) +#define KERNEL_HWCAP_DCPODP __khwcap2_feature(DCPODP) /* * This yields a mask that user programs can use to figure out what diff --git a/arch/arm64/include/uapi/asm/hwcap.h b/arch/arm64/include/uapi/asm/hwcap.h index 453b45af80b7..d64af3913a9e 100644 --- a/arch/arm64/include/uapi/asm/hwcap.h +++ b/arch/arm64/include/uapi/asm/hwcap.h @@ -53,4 +53,9 @@ #define HWCAP_PACA (1 << 30) #define HWCAP_PACG (1UL << 31) +/* + * HWCAP2 flags - for AT_HWCAP2 + */ +#define HWCAP2_DCPODP (1 << 0) + #endif /* _UAPI__ASM_HWCAP_H */ diff --git a/arch/arm64/kernel/cpufeature.c b/arch/arm64/kernel/cpufeature.c index a655d1bb1186..f8b682a3a9f4 100644 --- a/arch/arm64/kernel/cpufeature.c +++ b/arch/arm64/kernel/cpufeature.c @@ -1591,6 +1591,7 @@ static const struct arm64_cpu_capabilities arm64_elf_hwcaps[] = { HWCAP_CAP(SYS_ID_AA64PFR0_EL1, ID_AA64PFR0_ASIMD_SHIFT, FTR_SIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_ASIMDHP), HWCAP_CAP(SYS_ID_AA64PFR0_EL1, ID_AA64PFR0_DIT_SHIFT, FTR_SIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_DIT), HWCAP_CAP(SYS_ID_AA64ISAR1_EL1, ID_AA64ISAR1_DPB_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_DCPOP), + HWCAP_CAP(SYS_ID_AA64ISAR1_EL1, ID_AA64ISAR1_DPB_SHIFT, FTR_UNSIGNED, 2, CAP_HWCAP, KERNEL_HWCAP_DCPODP), HWCAP_CAP(SYS_ID_AA64ISAR1_EL1, ID_AA64ISAR1_JSCVT_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_JSCVT), HWCAP_CAP(SYS_ID_AA64ISAR1_EL1, ID_AA64ISAR1_FCMA_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_FCMA), HWCAP_CAP(SYS_ID_AA64ISAR1_EL1, ID_AA64ISAR1_LRCPC_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_LRCPC), diff --git a/arch/arm64/kernel/cpuinfo.c b/arch/arm64/kernel/cpuinfo.c index 810db95f293f..093ca53ce1d1 100644 --- a/arch/arm64/kernel/cpuinfo.c +++ b/arch/arm64/kernel/cpuinfo.c @@ -85,6 +85,7 @@ static const char *const hwcap_str[] = { "sb", "paca", "pacg", + "dcpodp", NULL }; -- cgit v1.2.3 From 5c090abf945bf5fd496c861f371410888be8f4de Mon Sep 17 00:00:00 2001 From: Nicolin Chen Date: Tue, 16 Apr 2019 12:41:31 -0700 Subject: hwmon: (ina3221) Add averaging mode support The CONFIG register has a 3-bit averaging mode field for users to setup the number of samples that are collected and averaged together. This is very useful to filter noise from sensor data. This patch adds a 'samples' sysfs node using hwmon_chip_samples of hwmon core, and updates wait time calculation by taking this samples value into account. Signed-off-by: Nicolin Chen Signed-off-by: Guenter Roeck --- Documentation/hwmon/ina3221 | 3 ++ drivers/hwmon/ina3221.c | 67 ++++++++++++++++++++++++++++++++++++++++++++- 2 files changed, 69 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/hwmon/ina3221 b/Documentation/hwmon/ina3221 index 4b82cbfb551c..ed3f22769d4b 100644 --- a/Documentation/hwmon/ina3221 +++ b/Documentation/hwmon/ina3221 @@ -35,3 +35,6 @@ curr[123]_max Warning alert current(mA) setting, activates the average is above this value. curr[123]_max_alarm Warning alert current limit exceeded in[456]_input Shunt voltage(uV) for channels 1, 2, and 3 respectively +samples Number of samples using in the averaging mode. + Supports the list of number of samples: + 1, 4, 16, 64, 128, 256, 512, 1024 diff --git a/drivers/hwmon/ina3221.c b/drivers/hwmon/ina3221.c index e6f43df0435c..74d39d212931 100644 --- a/drivers/hwmon/ina3221.c +++ b/drivers/hwmon/ina3221.c @@ -22,6 +22,7 @@ #include #include #include +#include #define INA3221_DRIVER_NAME "ina3221" @@ -51,6 +52,9 @@ #define INA3221_CONFIG_VBUS_CT_SHIFT 6 #define INA3221_CONFIG_VBUS_CT_MASK GENMASK(8, 6) #define INA3221_CONFIG_VBUS_CT(x) (((x) & GENMASK(8, 6)) >> 6) +#define INA3221_CONFIG_AVG_SHIFT 9 +#define INA3221_CONFIG_AVG_MASK GENMASK(11, 9) +#define INA3221_CONFIG_AVG(x) (((x) & GENMASK(11, 9)) >> 9) #define INA3221_CONFIG_CHs_EN_MASK GENMASK(14, 12) #define INA3221_CONFIG_CHx_EN(x) BIT(14 - (x)) @@ -135,17 +139,24 @@ static const u16 ina3221_conv_time[] = { 140, 204, 332, 588, 1100, 2116, 4156, 8244, }; +/* Lookup table for number of samples using in averaging mode */ +static const int ina3221_avg_samples[] = { + 1, 4, 16, 64, 128, 256, 512, 1024, +}; + static inline int ina3221_wait_for_data(struct ina3221_data *ina) { u32 channels = hweight16(ina->reg_config & INA3221_CONFIG_CHs_EN_MASK); u32 vbus_ct_idx = INA3221_CONFIG_VBUS_CT(ina->reg_config); u32 vsh_ct_idx = INA3221_CONFIG_VSH_CT(ina->reg_config); + u32 samples_idx = INA3221_CONFIG_AVG(ina->reg_config); + u32 samples = ina3221_avg_samples[samples_idx]; u32 vbus_ct = ina3221_conv_time[vbus_ct_idx]; u32 vsh_ct = ina3221_conv_time[vsh_ct_idx]; u32 wait, cvrf; /* Calculate total conversion time */ - wait = channels * (vbus_ct + vsh_ct); + wait = channels * (vbus_ct + vsh_ct) * samples; /* Polling the CVRF bit to make sure read data is ready */ return regmap_field_read_poll_timeout(ina->fields[F_CVRF], @@ -176,6 +187,21 @@ static const u8 ina3221_in_reg[] = { INA3221_SHUNT3, }; +static int ina3221_read_chip(struct device *dev, u32 attr, long *val) +{ + struct ina3221_data *ina = dev_get_drvdata(dev); + int regval; + + switch (attr) { + case hwmon_chip_samples: + regval = INA3221_CONFIG_AVG(ina->reg_config); + *val = ina3221_avg_samples[regval]; + return 0; + default: + return -EOPNOTSUPP; + } +} + static int ina3221_read_in(struct device *dev, u32 attr, int channel, long *val) { const bool is_shunt = channel > INA3221_CHANNEL3; @@ -279,6 +305,30 @@ static int ina3221_read_curr(struct device *dev, u32 attr, } } +static int ina3221_write_chip(struct device *dev, u32 attr, long val) +{ + struct ina3221_data *ina = dev_get_drvdata(dev); + int ret, idx; + + switch (attr) { + case hwmon_chip_samples: + idx = find_closest(val, ina3221_avg_samples, + ARRAY_SIZE(ina3221_avg_samples)); + + ret = regmap_update_bits(ina->regmap, INA3221_CONFIG, + INA3221_CONFIG_AVG_MASK, + idx << INA3221_CONFIG_AVG_SHIFT); + if (ret) + return ret; + + /* Update reg_config accordingly */ + return regmap_read(ina->regmap, INA3221_CONFIG, + &ina->reg_config); + default: + return -EOPNOTSUPP; + } +} + static int ina3221_write_curr(struct device *dev, u32 attr, int channel, long val) { @@ -361,6 +411,9 @@ static int ina3221_read(struct device *dev, enum hwmon_sensor_types type, mutex_lock(&ina->lock); switch (type) { + case hwmon_chip: + ret = ina3221_read_chip(dev, attr, val); + break; case hwmon_in: /* 0-align channel ID */ ret = ina3221_read_in(dev, attr, channel - 1, val); @@ -387,6 +440,9 @@ static int ina3221_write(struct device *dev, enum hwmon_sensor_types type, mutex_lock(&ina->lock); switch (type) { + case hwmon_chip: + ret = ina3221_write_chip(dev, attr, val); + break; case hwmon_in: /* 0-align channel ID */ ret = ina3221_write_enable(dev, channel - 1, val); @@ -423,6 +479,13 @@ static umode_t ina3221_is_visible(const void *drvdata, const struct ina3221_input *input = NULL; switch (type) { + case hwmon_chip: + switch (attr) { + case hwmon_chip_samples: + return 0644; + default: + return 0; + } case hwmon_in: /* Ignore in0_ */ if (channel == 0) @@ -463,6 +526,8 @@ static umode_t ina3221_is_visible(const void *drvdata, HWMON_C_MAX | HWMON_C_MAX_ALARM) static const struct hwmon_channel_info *ina3221_info[] = { + HWMON_CHANNEL_INFO(chip, + HWMON_C_SAMPLES), HWMON_CHANNEL_INFO(in, /* 0: dummy, skipped in is_visible */ HWMON_I_INPUT, -- cgit v1.2.3 From 2b8d59296cff37a73dc72a0667c148b0e57ae64f Mon Sep 17 00:00:00 2001 From: Thierry Reding Date: Thu, 21 Feb 2019 16:46:30 +0100 Subject: dt-bindings: phy: tegra: Add Tegra186 support Extend the bindings to cover the set of features found in Tegra186. Note that, technically, there are four more supplies connected to the XUSB pad controller (DVDD_PEX, DVDD_PEX_PLL, HVDD_PEX and HVDD_PEX_PLL), but the power sequencing requirements of Tegra186 require these to be under the control of the PMIC. Reviewed-by: JC Kuo Signed-off-by: Thierry Reding Reviewed-by: Rob Herring Signed-off-by: Kishon Vijay Abraham I --- .../devicetree/bindings/phy/nvidia,tegra124-xusb-padctl.txt | 9 +++++++++ 1 file changed, 9 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/phy/nvidia,tegra124-xusb-padctl.txt b/Documentation/devicetree/bindings/phy/nvidia,tegra124-xusb-padctl.txt index 3742c152c467..daedb15f322e 100644 --- a/Documentation/devicetree/bindings/phy/nvidia,tegra124-xusb-padctl.txt +++ b/Documentation/devicetree/bindings/phy/nvidia,tegra124-xusb-padctl.txt @@ -36,11 +36,20 @@ Required properties: - Tegra124: "nvidia,tegra124-xusb-padctl" - Tegra132: "nvidia,tegra132-xusb-padctl", "nvidia,tegra124-xusb-padctl" - Tegra210: "nvidia,tegra210-xusb-padctl" + - Tegra186: "nvidia,tegra186-xusb-padctl" - reg: Physical base address and length of the controller's registers. - resets: Must contain an entry for each entry in reset-names. - reset-names: Must include the following entries: - "padctl" +For Tegra186: +- avdd-pll-erefeut-supply: UPHY brick and reference clock as well as UTMI PHY + power supply. Must supply 1.8 V. +- avdd-usb-supply: USB I/Os, VBUS, ID, REXT, D+/D- power supply. Must supply + 3.3 V. +- vclamp-usb-supply: Bias rail for USB pad. Must supply 1.8 V. +- vddio-hsic-supply: HSIC PHY power supply. Must supply 1.2 V. + Pad nodes: ========== -- cgit v1.2.3 From 30417ab2a3d78781d45cace7fa0317ad9a044f11 Mon Sep 17 00:00:00 2001 From: Srinath Mannam Date: Tue, 19 Mar 2019 14:45:42 +0530 Subject: dt-bindings: phy: Add Stingray USB PHY binding document Add DT binding document for Stingray USB PHY. Signed-off-by: Srinath Mannam Reviewed-by: Rob Herring Signed-off-by: Kishon Vijay Abraham I --- .../bindings/phy/brcm,stingray-usb-phy.txt | 32 ++++++++++++++++++++++ 1 file changed, 32 insertions(+) create mode 100644 Documentation/devicetree/bindings/phy/brcm,stingray-usb-phy.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/phy/brcm,stingray-usb-phy.txt b/Documentation/devicetree/bindings/phy/brcm,stingray-usb-phy.txt new file mode 100644 index 000000000000..4ba298966af9 --- /dev/null +++ b/Documentation/devicetree/bindings/phy/brcm,stingray-usb-phy.txt @@ -0,0 +1,32 @@ +Broadcom Stingray USB PHY + +Required properties: + - compatible : should be one of the listed compatibles + - "brcm,sr-usb-combo-phy" is combo PHY has two PHYs, one SS and one HS. + - "brcm,sr-usb-hs-phy" is a single HS PHY. + - reg: offset and length of the PHY blocks registers + - #phy-cells: + - Must be 1 for brcm,sr-usb-combo-phy as it expects one argument to indicate + the PHY number of two PHYs. 0 for HS PHY and 1 for SS PHY. + - Must be 0 for brcm,sr-usb-hs-phy. + +Refer to phy/phy-bindings.txt for the generic PHY binding properties + +Example: + usbphy0: usb-phy@0 { + compatible = "brcm,sr-usb-combo-phy"; + reg = <0x00000000 0x100>; + #phy-cells = <1>; + }; + + usbphy1: usb-phy@10000 { + compatible = "brcm,sr-usb-combo-phy"; + reg = <0x00010000 0x100>, + #phy-cells = <1>; + }; + + usbphy2: usb-phy@20000 { + compatible = "brcm,sr-usb-hs-phy"; + reg = <0x00020000 0x100>, + #phy-cells = <0>; + }; -- cgit v1.2.3 From 7609db4e846b26bab1c259fb025c56f4c262a21a Mon Sep 17 00:00:00 2001 From: Neil Armstrong Date: Mon, 25 Mar 2019 10:39:36 +0100 Subject: dt-bindings: phy: Add Amlogic G12A USB2 PHY Bindings Add the Amlogic G12A Family USB2 OTG PHY Bindings The PHY can work in host or peripheral modes depending on it's position. Configuration of the mode is part of the USBCTRL registers which are outside of the PHY registers. Signed-off-by: Neil Armstrong Reviewed-by: Martin Blumenstingl Reviewed-by: Rob Herring Signed-off-by: Kishon Vijay Abraham I --- .../bindings/phy/meson-g12a-usb2-phy.txt | 22 ++++++++++++++++++++++ 1 file changed, 22 insertions(+) create mode 100644 Documentation/devicetree/bindings/phy/meson-g12a-usb2-phy.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/phy/meson-g12a-usb2-phy.txt b/Documentation/devicetree/bindings/phy/meson-g12a-usb2-phy.txt new file mode 100644 index 000000000000..a6ebc3dea159 --- /dev/null +++ b/Documentation/devicetree/bindings/phy/meson-g12a-usb2-phy.txt @@ -0,0 +1,22 @@ +* Amlogic G12A USB2 PHY binding + +Required properties: +- compatible: Should be "amlogic,meson-g12a-usb2-phy" +- reg: The base address and length of the registers +- #phys-cells: must be 0 (see phy-bindings.txt in this directory) +- clocks: a phandle to the clock of this PHY +- clock-names: must be "xtal" +- resets: a phandle to the reset line of this PHY +- reset-names: must be "phy" +- phy-supply: see phy-bindings.txt in this directory + +Example: + usb2_phy0: phy@36000 { + compatible = "amlogic,g12a-usb2-phy"; + reg = <0x0 0x36000 0x0 0x2000>; + clocks = <&xtal>; + clock-names = "xtal"; + resets = <&reset RESET_USB_PHY21>; + reset-names = "phy"; + #phy-cells = <0>; + }; -- cgit v1.2.3 From ab6dbeb24d1a93425b2d1d91b17a7bce79dba41b Mon Sep 17 00:00:00 2001 From: Neil Armstrong Date: Mon, 25 Mar 2019 10:39:37 +0100 Subject: dt-bindings: phy: Add Amlogic G12A USB3+PCIE Combo PHY Bindings Add the Amlogic G12A Family USB3 + PCIE Combo PHY Bindings. This PHY can provide exclusively USB3 or PCIE support on shared I/Os. Signed-off-by: Neil Armstrong Reviewed-by: Martin Blumenstingl Reviewed-by: Rob Herring Signed-off-by: Kishon Vijay Abraham I --- .../bindings/phy/meson-g12a-usb3-pcie-phy.txt | 22 ++++++++++++++++++++++ 1 file changed, 22 insertions(+) create mode 100644 Documentation/devicetree/bindings/phy/meson-g12a-usb3-pcie-phy.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/phy/meson-g12a-usb3-pcie-phy.txt b/Documentation/devicetree/bindings/phy/meson-g12a-usb3-pcie-phy.txt new file mode 100644 index 000000000000..7cfc17e2df31 --- /dev/null +++ b/Documentation/devicetree/bindings/phy/meson-g12a-usb3-pcie-phy.txt @@ -0,0 +1,22 @@ +* Amlogic G12A USB3 + PCIE Combo PHY binding + +Required properties: +- compatible: Should be "amlogic,meson-g12a-usb3-pcie-phy" +- #phys-cells: must be 1. The cell number is used to select the phy mode + as defined in between PHY_TYPE_USB3 and PHY_TYPE_PCIE +- reg: The base address and length of the registers +- clocks: a phandle to the 100MHz reference clock of this PHY +- clock-names: must be "ref_clk" +- resets: phandle to the reset lines for the PHY control +- reset-names: must be "phy" + +Example: + usb3_pcie_phy: phy@46000 { + compatible = "amlogic,g12a-usb3-pcie-phy"; + reg = <0x0 0x46000 0x0 0x2000>; + clocks = <&clkc CLKID_PCIE_PLL>; + clock-names = "ref_clk"; + resets = <&reset RESET_PCIE_PHY>; + reset-names = "phy"; + #phy-cells = <1>; + }; -- cgit v1.2.3 From 8de4acd397ab96bf3487c6a765fd2b76e2863909 Mon Sep 17 00:00:00 2001 From: Evan Green Date: Thu, 21 Mar 2019 10:17:53 -0700 Subject: dt-bindings: ufs: Add #reset-cells for Qualcomm controllers Enable Qualcomm UFS controllers to expose the PHY reset via a reset controller. Signed-off-by: Evan Green Reviewed-by: Rob Herring Reviewed-by: Stephen Boyd Signed-off-by: Kishon Vijay Abraham I --- Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt | 3 +++ 1 file changed, 3 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt b/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt index 5111e9130bc3..f647c09bc62a 100644 --- a/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt +++ b/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt @@ -50,6 +50,8 @@ Optional properties: -lanes-per-direction : number of lanes available per direction - either 1 or 2. Note that it is assume same number of lanes is used both directions at once. If not specified, default is 2 lanes per direction. +- #reset-cells : Must be <1> for Qualcomm UFS controllers that expose + PHY reset from the UFS controller. - resets : reset node register - reset-names : describe reset node register, the "rst" corresponds to reset the whole UFS IP. @@ -79,4 +81,5 @@ Example: reset-names = "rst"; phys = <&ufsphy1>; phy-names = "ufsphy"; + #reset-cells = <1>; }; -- cgit v1.2.3 From 95cee0b4e30a09a411a17e9a3bc6b72ed92063da Mon Sep 17 00:00:00 2001 From: Evan Green Date: Thu, 21 Mar 2019 10:17:54 -0700 Subject: dt-bindings: phy-qcom-qmp: Add UFS PHY reset Add a required reset to the SDM845 UFS phy to express the PHY reset bit inside the UFS controller register space. Before this change, this reset was not expressed in the DT, and the driver utilized two different callbacks (phy_init and phy_poweron) to implement a two-phase initialization procedure that involved deasserting this reset between init and poweron. This abused the two callbacks and diluted their purpose. That scheme does not work as regulators cannot be turned off in phy_poweroff because they were turned on in init, rather than poweron. The net result is that regulators are left on in suspend that shouldn't be. This new scheme gives the UFS reset to the PHY, so that it can fully initialize itself in a single callback. We can then turn regulators on during poweron and off during poweroff. Signed-off-by: Evan Green Reviewed-by: Rob Herring Reviewed-by: Stephen Boyd Signed-off-by: Kishon Vijay Abraham I --- Documentation/devicetree/bindings/phy/qcom-qmp-phy.txt | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/phy/qcom-qmp-phy.txt b/Documentation/devicetree/bindings/phy/qcom-qmp-phy.txt index 5d181fc3cc18..4a78ba8b85bc 100644 --- a/Documentation/devicetree/bindings/phy/qcom-qmp-phy.txt +++ b/Documentation/devicetree/bindings/phy/qcom-qmp-phy.txt @@ -59,7 +59,8 @@ Required properties: one for each entry in reset-names. - reset-names: "phy" for reset of phy block, "common" for phy common block reset, - "cfg" for phy's ahb cfg block reset. + "cfg" for phy's ahb cfg block reset, + "ufsphy" for the PHY reset in the UFS controller. For "qcom,ipq8074-qmp-pcie-phy" must contain: "phy", "common". @@ -74,7 +75,8 @@ Required properties: "phy", "common". For "qcom,sdm845-qmp-usb3-uni-phy" must contain: "phy", "common". - For "qcom,sdm845-qmp-ufs-phy": no resets are listed. + For "qcom,sdm845-qmp-ufs-phy": must contain: + "ufsphy". - vdda-phy-supply: Phandle to a regulator supply to PHY core block. - vdda-pll-supply: Phandle to 1.8V regulator supply to PHY refclk pll block. -- cgit v1.2.3 From 70b894deb78a7deed9157863a17f9e85a4ba87b3 Mon Sep 17 00:00:00 2001 From: Evan Green Date: Thu, 21 Mar 2019 10:17:55 -0700 Subject: dt-bindings: phy: qcom-ufs: Add resets property Add a resets property to the PHY that represents the PHY reset register in the UFS controller itself. This better describes the complete specification of the PHY, and allows the PHY to perform its initialization in a single function, rather than relying on back-channel sequencing of initialization through the PHY framework. Signed-off-by: Evan Green Reviewed-by: Rob Herring Reviewed-by: Stephen Boyd Signed-off-by: Kishon Vijay Abraham I --- Documentation/devicetree/bindings/ufs/ufs-qcom.txt | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/ufs/ufs-qcom.txt b/Documentation/devicetree/bindings/ufs/ufs-qcom.txt index 21d9a93db2e9..fd59f93e9556 100644 --- a/Documentation/devicetree/bindings/ufs/ufs-qcom.txt +++ b/Documentation/devicetree/bindings/ufs/ufs-qcom.txt @@ -29,6 +29,7 @@ Optional properties: - vdda-pll-max-microamp : specifies max. load that can be drawn from pll supply - vddp-ref-clk-supply : phandle to UFS device ref_clk pad power supply - vddp-ref-clk-max-microamp : specifies max. load that can be drawn from this supply +- resets : specifies the PHY reset in the UFS controller Example: @@ -51,9 +52,11 @@ Example: <&clock_gcc clk_ufs_phy_ldo>, <&clock_gcc clk_gcc_ufs_tx_cfg_clk>, <&clock_gcc clk_gcc_ufs_rx_cfg_clk>; + resets = <&ufshc 0>; }; - ufshc@fc598000 { + ufshc: ufshc@fc598000 { + #reset-cells = <1>; ... phys = <&ufsphy1>; phy-names = "ufsphy"; -- cgit v1.2.3 From 2c1a4b0cbeb47c0376aa53df2b2a3a79670ca6aa Mon Sep 17 00:00:00 2001 From: Christoph Muellner Date: Fri, 22 Mar 2019 12:34:51 +0100 Subject: dt-bindings: phy: Add a new property drive-impedance-ohm for RK's emmc PHY This patch documents the new proprty drive-impedance-ohm for Rockchip's eMMC PHY node. Signed-off-by: Christoph Muellner Signed-off-by: Philipp Tomsich Signed-off-by: Kishon Vijay Abraham I --- Documentation/devicetree/bindings/phy/rockchip-emmc-phy.txt | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/phy/rockchip-emmc-phy.txt b/Documentation/devicetree/bindings/phy/rockchip-emmc-phy.txt index e3ea55763b0a..e728786f21e0 100644 --- a/Documentation/devicetree/bindings/phy/rockchip-emmc-phy.txt +++ b/Documentation/devicetree/bindings/phy/rockchip-emmc-phy.txt @@ -7,12 +7,15 @@ Required properties: - reg: PHY register address offset and length in "general register files" -Optional clocks using the clock bindings (see ../clock/clock-bindings.txt), -specified by name: +Optional properties: - clock-names: Should contain "emmcclk". Although this is listed as optional (because most boards can get basic functionality without having access to it), it is strongly suggested. + See ../clock/clock-bindings.txt for details. - clocks: Should have a phandle to the card clock exported by the SDHCI driver. + - drive-impedance-ohm: Specifies the drive impedance in Ohm. + Possible values are 33, 40, 50, 66 and 100. + If not set, the default value of 50 will be applied. Example: @@ -29,6 +32,7 @@ grf: syscon@ff770000 { reg = <0xf780 0x20>; clocks = <&sdhci>; clock-names = "emmcclk"; + drive-impedance-ohm = <50>; #phy-cells = <0>; }; }; -- cgit v1.2.3 From fd7bd3b6bebdf889802db67b8c48b67aa20f4a2b Mon Sep 17 00:00:00 2001 From: Stanley Chu Date: Sat, 16 Mar 2019 13:04:44 +0800 Subject: dt-bindings: phy: Add document for phy-mtk-ufs Add UFS M-PHY node document for MediaTek SoC chips. Signed-off-by: Stanley Chu Reviewed-by: Rob Herring Signed-off-by: Kishon Vijay Abraham I --- .../devicetree/bindings/phy/phy-mtk-ufs.txt | 38 ++++++++++++++++++++++ 1 file changed, 38 insertions(+) create mode 100644 Documentation/devicetree/bindings/phy/phy-mtk-ufs.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/phy/phy-mtk-ufs.txt b/Documentation/devicetree/bindings/phy/phy-mtk-ufs.txt new file mode 100644 index 000000000000..5789029a1d42 --- /dev/null +++ b/Documentation/devicetree/bindings/phy/phy-mtk-ufs.txt @@ -0,0 +1,38 @@ +MediaTek Universal Flash Storage (UFS) M-PHY binding +-------------------------------------------------------- + +UFS M-PHY nodes are defined to describe on-chip UFS M-PHY hardware macro. +Each UFS M-PHY node should have its own node. + +To bind UFS M-PHY with UFS host controller, the controller node should +contain a phandle reference to UFS M-PHY node. + +Required properties for UFS M-PHY nodes: +- compatible : Compatible list, contains the following controller: + "mediatek,mt8183-ufsphy" for ufs phy + persent on MT81xx chipsets. +- reg : Address and length of the UFS M-PHY register set. +- #phy-cells : This property shall be set to 0. +- clocks : List of phandle and clock specifier pairs. +- clock-names : List of clock input name strings sorted in the same + order as the clocks property. Following clocks are + mandatory. + "unipro": Unipro core control clock. + "mp": M-PHY core control clock. + +Example: + + ufsphy: phy@11fa0000 { + compatible = "mediatek,mt8183-ufsphy"; + reg = <0 0x11fa0000 0 0xc000>; + #phy-cells = <0>; + + clocks = <&infracfg_ao INFRACFG_AO_UNIPRO_SCK_CG>, + <&infracfg_ao INFRACFG_AO_UFS_MP_SAP_BCLK_CG>; + clock-names = "unipro", "mp"; + }; + + ufshci@11270000 { + ... + phys = <&ufsphy>; + }; -- cgit v1.2.3 From f56511d0080ce33a17f7192a3f43d65e614da5cf Mon Sep 17 00:00:00 2001 From: Biju Das Date: Wed, 10 Apr 2019 15:48:38 +0100 Subject: dt-bindings: phy: rcar-gen2: Add r8a77470 support Add USB PHY support for r8a77470 SoC. Renesas RZ/G1C (R8A77470) USB PHY is similar to the R-Car Gen2 family, but has the below feature compared to other RZ/G1 and R-Car Gen2/3 SoCs It has a shared pll reset for usbphy0/usbphy1 and this register reside in usbphy0 block. Signed-off-by: Biju Das Reviewed-by: Rob Herring Reviewed-by: Yoshihiro Shimoda Signed-off-by: Kishon Vijay Abraham I --- .../devicetree/bindings/phy/rcar-gen2-phy.txt | 57 ++++++++++++++++++++-- 1 file changed, 53 insertions(+), 4 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/phy/rcar-gen2-phy.txt b/Documentation/devicetree/bindings/phy/rcar-gen2-phy.txt index 4f0879a0ca12..ac96d6481bb8 100644 --- a/Documentation/devicetree/bindings/phy/rcar-gen2-phy.txt +++ b/Documentation/devicetree/bindings/phy/rcar-gen2-phy.txt @@ -7,6 +7,7 @@ Required properties: - compatible: "renesas,usb-phy-r8a7743" if the device is a part of R8A7743 SoC. "renesas,usb-phy-r8a7744" if the device is a part of R8A7744 SoC. "renesas,usb-phy-r8a7745" if the device is a part of R8A7745 SoC. + "renesas,usb-phy-r8a77470" if the device is a part of R8A77470 SoC. "renesas,usb-phy-r8a7790" if the device is a part of R8A7790 SoC. "renesas,usb-phy-r8a7791" if the device is a part of R8A7791 SoC. "renesas,usb-phy-r8a7794" if the device is a part of R8A7794 SoC. @@ -30,7 +31,7 @@ channels. These subnodes must contain the following properties: - #phy-cells: see phy-bindings.txt in the same directory, must be <1>. The phandle's argument in the PHY specifier is the USB controller selector for -the USB channel; see the selector meanings below: +the USB channel other than r8a77470 SoC; see the selector meanings below: +-----------+---------------+---------------+ |\ Selector | | | @@ -41,6 +42,16 @@ the USB channel; see the selector meanings below: | 2 | PCI EHCI/OHCI | xHCI | +-----------+---------------+---------------+ +For r8a77470 SoC;see the selector meaning below: + ++-----------+---------------+---------------+ +|\ Selector | | | ++ --------- + 0 | 1 | +| Channel \| | | ++-----------+---------------+---------------+ +| 0 | EHCI/OHCI | HS-USB | ++-----------+---------------+---------------+ + Example (Lager board): usb-phy@e6590100 { @@ -48,15 +59,53 @@ Example (Lager board): reg = <0 0xe6590100 0 0x100>; #address-cells = <1>; #size-cells = <0>; - clocks = <&mstp7_clks R8A7790_CLK_HSUSB>; + clocks = <&cpg CPG_MOD 704>; clock-names = "usbhs"; + power-domains = <&sysc R8A7790_PD_ALWAYS_ON>; + resets = <&cpg 704>; - usb-channel@0 { + usb0: usb-channel@0 { reg = <0>; #phy-cells = <1>; }; - usb-channel@2 { + usb2: usb-channel@2 { reg = <2>; #phy-cells = <1>; }; }; + +Example (iWave RZ/G1C sbc): + + usbphy0: usb-phy0@e6590100 { + compatible = "renesas,usb-phy-r8a77470", + "renesas,rcar-gen2-usb-phy"; + reg = <0 0xe6590100 0 0x100>; + #address-cells = <1>; + #size-cells = <0>; + clocks = <&cpg CPG_MOD 704>; + clock-names = "usbhs"; + power-domains = <&sysc R8A77470_PD_ALWAYS_ON>; + resets = <&cpg 704>; + + usb0: usb-channel@0 { + reg = <0>; + #phy-cells = <1>; + }; + }; + + usbphy1: usb-phy@e6598100 { + compatible = "renesas,usb-phy-r8a77470", + "renesas,rcar-gen2-usb-phy"; + reg = <0 0xe6598100 0 0x100>; + #address-cells = <1>; + #size-cells = <0>; + clocks = <&cpg CPG_MOD 706>; + clock-names = "usbhs"; + power-domains = <&sysc R8A77470_PD_ALWAYS_ON>; + resets = <&cpg 706>; + + usb1: usb-channel@0 { + reg = <0>; + #phy-cells = <1>; + }; + }; -- cgit v1.2.3 From d6c4aee8d1218d5cd73ce5e6f27ac68ad8b9430b Mon Sep 17 00:00:00 2001 From: Biju Das Date: Wed, 10 Apr 2019 15:48:40 +0100 Subject: dt-bindings: rcar-gen3-phy-usb2: Add r8a77470 support Document RZ/G1C (R8A77470) SoC bindings. For RZ/G1C, this driver is used to enable interrupt generation and initializing timing registers which is part of phy_init code. Signed-off-by: Biju Das Reviewed-by: Rob Herring Reviewed-by: Yoshihiro Shimoda Signed-off-by: Kishon Vijay Abraham I --- Documentation/devicetree/bindings/phy/rcar-gen3-phy-usb2.txt | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/phy/rcar-gen3-phy-usb2.txt b/Documentation/devicetree/bindings/phy/rcar-gen3-phy-usb2.txt index ad9c290d8f15..23894dbbf903 100644 --- a/Documentation/devicetree/bindings/phy/rcar-gen3-phy-usb2.txt +++ b/Documentation/devicetree/bindings/phy/rcar-gen3-phy-usb2.txt @@ -1,10 +1,12 @@ * Renesas R-Car generation 3 USB 2.0 PHY This file provides information on what the device node for the R-Car generation -3 and RZ/G2 USB 2.0 PHY contain. +3, RZ/G1C and RZ/G2 USB 2.0 PHY contain. Required properties: -- compatible: "renesas,usb2-phy-r8a774a1" if the device is a part of an R8A774A1 +- compatible: "renesas,usb2-phy-r8a77470" if the device is a part of an R8A77470 + SoC. + "renesas,usb2-phy-r8a774a1" if the device is a part of an R8A774A1 SoC. "renesas,usb2-phy-r8a774c0" if the device is a part of an R8A774C0 SoC. -- cgit v1.2.3 From 233da2c9ec22dcc885987acf1c8ccb88e8835022 Mon Sep 17 00:00:00 2001 From: Yoshihiro Shimoda Date: Thu, 11 Apr 2019 19:27:34 +0900 Subject: dt-bindings: phy: rcar-gen3-phy-usb2: Revise #phy-cells property To have the detailed property on each PHY specifier, this patch revises the #phy-cells property. Signed-off-by: Yoshihiro Shimoda Signed-off-by: Kishon Vijay Abraham I --- Documentation/devicetree/bindings/phy/rcar-gen3-phy-usb2.txt | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/phy/rcar-gen3-phy-usb2.txt b/Documentation/devicetree/bindings/phy/rcar-gen3-phy-usb2.txt index 23894dbbf903..d46188f450bf 100644 --- a/Documentation/devicetree/bindings/phy/rcar-gen3-phy-usb2.txt +++ b/Documentation/devicetree/bindings/phy/rcar-gen3-phy-usb2.txt @@ -29,7 +29,13 @@ Required properties: - reg: offset and length of the partial USB 2.0 Host register block. - clocks: clock phandle and specifier pair(s). -- #phy-cells: see phy-bindings.txt in the same directory, must be <0>. +- #phy-cells: see phy-bindings.txt in the same directory, must be <1> (and + using <0> is deprecated). + +The phandle's argument in the PHY specifier is the INT_STATUS bit of controller: +- 1 = USBH_INTA (OHCI) +- 2 = USBH_INTB (EHCI) +- 3 = UCOM_INT (OTG and BC) Optional properties: To use a USB channel where USB 2.0 Host and HSUSB (USB 2.0 Peripheral) are -- cgit v1.2.3 From 4e0ae876f77bc01a7e77724dea57b4b82bd53244 Mon Sep 17 00:00:00 2001 From: Kishon Vijay Abraham I Date: Fri, 5 Apr 2019 16:38:32 +0530 Subject: dt-bindings: phy: ti: Add dt binding documentation for SERDES in AM654x SoC MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit AM654x has two SERDES instances. Each instance has three input clocks (left input, externel reference clock and right input) and two output clocks (left output and right output) in addition to a PLL mux clock which the SERDES uses for Clock Multiplier Unit (CMU refclock). The PLL mux clock can select from one of the three input clocks. The right output can select between left input and external reference clock while the left output can select between the right input and external reference clock. The left and right input reference clock of SERDES0 and SERDES1 respectively are connected to the SoC clock. In the case of two lane SERDES personality card, the left input of SERDES1 is connected to the right output of SERDES0 in a chained fashion. See section "Reference Clock Distribution" of AM65x Sitara Processors TRM (SPRUID7 – April 2018) for more details. Add dt-binding documentation in order to represent all these different configurations in device tree. Signed-off-by: Kishon Vijay Abraham I --- .../bindings/phy/ti,phy-am654-serdes.txt | 82 ++++++++++++++++++++++ include/dt-bindings/phy/phy-am654-serdes.h | 13 ++++ 2 files changed, 95 insertions(+) create mode 100644 Documentation/devicetree/bindings/phy/ti,phy-am654-serdes.txt create mode 100644 include/dt-bindings/phy/phy-am654-serdes.h (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/phy/ti,phy-am654-serdes.txt b/Documentation/devicetree/bindings/phy/ti,phy-am654-serdes.txt new file mode 100644 index 000000000000..64b286d2d398 --- /dev/null +++ b/Documentation/devicetree/bindings/phy/ti,phy-am654-serdes.txt @@ -0,0 +1,82 @@ +TI AM654 SERDES + +Required properties: + - compatible: Should be "ti,phy-am654-serdes" + - reg : Address and length of the register set for the device. + - #phy-cells: determine the number of cells that should be given in the + phandle while referencing this phy. Should be "2". The 1st cell + corresponds to the phy type (should be one of the types specified in + include/dt-bindings/phy/phy.h) and the 2nd cell should be the serdes + lane function. + If SERDES0 is referenced 2nd cell should be: + 0 - USB3 + 1 - PCIe0 Lane0 + 2 - ICSS2 SGMII Lane0 + If SERDES1 is referenced 2nd cell should be: + 0 - PCIe1 Lane0 + 1 - PCIe0 Lane1 + 2 - ICSS2 SGMII Lane1 + - power-domains: As documented by the generic PM domain bindings in + Documentation/devicetree/bindings/power/power_domain.txt. + - clocks: List of clock-specifiers representing the input to the SERDES. + Should have 3 items representing the left input clock, external + reference clock and right input clock in that order. + - clock-output-names: List of clock names for each of the clock outputs of + SERDES. Should have 3 items for CMU reference clock, + left output clock and right output clock in that order. + - assigned-clocks: As defined in + Documentation/devicetree/bindings/clock/clock-bindings.txt + - assigned-clock-parents: As defined in + Documentation/devicetree/bindings/clock/clock-bindings.txt + - #clock-cells: Should be <1> to choose between the 3 output clocks. + Defined in Documentation/devicetree/bindings/clock/clock-bindings.txt + + The following macros are defined in dt-bindings/phy/phy-am654-serdes.h + for selecting the correct reference clock. This can be used while + specifying the clocks created by SERDES. + => AM654_SERDES_CMU_REFCLK + => AM654_SERDES_LO_REFCLK + => AM654_SERDES_RO_REFCLK + + - mux-controls: Phandle to the multiplexer that is used to select the lane + function. See #phy-cells above to see the multiplex values. + +Example: + +Example for SERDES0 is given below. It has 3 clock inputs; +left input reference clock as indicated by <&k3_clks 153 4>, external +reference clock as indicated by <&k3_clks 153 1> and right input +reference clock as indicated by <&serdes1 AM654_SERDES_LO_REFCLK>. (The +right input of SERDES0 is connected to the left output of SERDES1). + +SERDES0 registers 3 clock outputs as indicated in clock-output-names. The +first refers to the CMU reference clock, second refers to the left output +reference clock and the third refers to the right output reference clock. + +The assigned-clocks and assigned-clock-parents is used here to set the +parent of left input reference clock to MAINHSDIV_CLKOUT4 and parent of +CMU reference clock to left input reference clock. + +serdes0: serdes@900000 { + compatible = "ti,phy-am654-serdes"; + reg = <0x0 0x900000 0x0 0x2000>; + reg-names = "serdes"; + #phy-cells = <2>; + power-domains = <&k3_pds 153>; + clocks = <&k3_clks 153 4>, <&k3_clks 153 1>, + <&serdes1 AM654_SERDES_LO_REFCLK>; + clock-output-names = "serdes0_cmu_refclk", "serdes0_lo_refclk", + "serdes0_ro_refclk"; + assigned-clocks = <&k3_clks 153 4>, <&serdes0 AM654_SERDES_CMU_REFCLK>; + assigned-clock-parents = <&k3_clks 153 8>, <&k3_clks 153 4>; + ti,serdes-clk = <&serdes0_clk>; + mux-controls = <&serdes_mux 0>; + #clock-cells = <1>; +}; + +Example for PCIe consumer node using the SERDES PHY specifier is given below. +&pcie0_rc { + num-lanes = <2>; + phys = <&serdes0 PHY_TYPE_PCIE 1>, <&serdes1 PHY_TYPE_PCIE 1>; + phy-names = "pcie-phy0", "pcie-phy1"; +}; diff --git a/include/dt-bindings/phy/phy-am654-serdes.h b/include/dt-bindings/phy/phy-am654-serdes.h new file mode 100644 index 000000000000..e8d901729ed9 --- /dev/null +++ b/include/dt-bindings/phy/phy-am654-serdes.h @@ -0,0 +1,13 @@ +/* SPDX-License-Identifier: GPL-2.0 */ +/* + * This header provides constants for AM654 SERDES. + */ + +#ifndef _DT_BINDINGS_AM654_SERDES +#define _DT_BINDINGS_AM654_SERDES + +#define AM654_SERDES_CMU_REFCLK 0 +#define AM654_SERDES_LO_REFCLK 1 +#define AM654_SERDES_RO_REFCLK 2 + +#endif /* _DT_BINDINGS_AM654_SERDES */ -- cgit v1.2.3 From 20a980e957bf10d78a74f3446a80ce29723c55c8 Mon Sep 17 00:00:00 2001 From: Sven Van Asbroeck Date: Tue, 16 Apr 2019 11:56:15 -0400 Subject: dt-bindings: anybus-controller: document devicetree binding This patch adds devicetree binding documentation for the Arcx anybus controller. Reviewed-by: Rob Herring Signed-off-by: Sven Van Asbroeck Signed-off-by: Greg Kroah-Hartman --- .../bindings/fieldbus/arcx,anybus-controller.txt | 71 ++++++++++++++++++++++ 1 file changed, 71 insertions(+) create mode 100644 Documentation/devicetree/bindings/fieldbus/arcx,anybus-controller.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/fieldbus/arcx,anybus-controller.txt b/Documentation/devicetree/bindings/fieldbus/arcx,anybus-controller.txt new file mode 100644 index 000000000000..b1f9474f36d5 --- /dev/null +++ b/Documentation/devicetree/bindings/fieldbus/arcx,anybus-controller.txt @@ -0,0 +1,71 @@ +* Arcx Anybus-S controller + +This chip communicates with the SoC over a parallel bus. It is +expected that its Device Tree node is specified as the child of a node +corresponding to the parallel bus used for communication. + +Required properties: +-------------------- + + - compatible : The following chip-specific string: + "arcx,anybus-controller" + + - reg : three areas: + index 0: bus memory area where the cpld registers are located. + index 1: bus memory area of the first host's dual-port ram. + index 2: bus memory area of the second host's dual-port ram. + + - reset-gpios : the GPIO pin connected to the reset line of the controller. + + - interrupts : two interrupts: + index 0: interrupt connected to the first host + index 1: interrupt connected to the second host + Generic interrupt client node bindings are described in + interrupt-controller/interrupts.txt + +Optional: use of subnodes +------------------------- + +The card connected to a host may need additional properties. These can be +specified in subnodes to the controller node. + +The subnodes are identified by the standard 'reg' property. Which information +exactly can be specified depends on the bindings for the function driver +for the subnode. + +Required controller node properties when using subnodes: +- #address-cells: should be one. +- #size-cells: should be zero. + +Required subnode properties: +- reg: Must contain the host index of the card this subnode describes: + <0> for the first host on the controller + <1> for the second host on the controller + Note that only a single card can be plugged into a host, so the host + index uniquely describes the card location. + +Example of usage: +----------------- + +This example places the bridge on top of the i.MX WEIM parallel bus, see: +Documentation/devicetree/bindings/bus/imx-weim.txt + +&weim { + controller@0,0 { + compatible = "arcx,anybus-controller"; + reg = <0 0 0x100>, <0 0x400000 0x800>, <1 0x400000 0x800>; + reset-gpios = <&gpio5 2 GPIO_ACTIVE_HIGH>; + interrupt-parent = <&gpio1>; + interrupts = <1 IRQ_TYPE_LEVEL_LOW>, <5 IRQ_TYPE_LEVEL_LOW>; + /* fsl,weim-cs-timing is a i.MX WEIM bus specific property */ + fsl,weim-cs-timing = <0x024400b1 0x00001010 0x20081100 + 0x00000000 0xa0000240 0x00000000>; + /* optional subnode for a card plugged into the first host */ + #address-cells = <1>; + #size-cells = <0>; + card@0 { + reg = <0>; + /* card specific properties go here */ + }; + }; +}; -- cgit v1.2.3 From d564d73f22649fdb70d18cfbe03925bd9f47ec26 Mon Sep 17 00:00:00 2001 From: Sven Van Asbroeck Date: Tue, 16 Apr 2019 11:56:16 -0400 Subject: dt-bindings: Add vendor prefix for arcx / Archronix MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit arcx Inc. is an engineering company which provides advanced embedded systems and consulting services. Archronix is a technology design and product engineering firm specializing in hardware control systems and enabling software. Clients include OEM's in the transportation, aerospace, medical and commercial sectors. Websites: http://www.arcx.com/ http://www.archronix.com/ Reviewed-by: Rob Herring Reviewed-by: Andreas Färber Signed-off-by: Sven Van Asbroeck Signed-off-by: Greg Kroah-Hartman --- Documentation/devicetree/bindings/vendor-prefixes.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/vendor-prefixes.txt b/Documentation/devicetree/bindings/vendor-prefixes.txt index 93753f447c20..686771d056c7 100644 --- a/Documentation/devicetree/bindings/vendor-prefixes.txt +++ b/Documentation/devicetree/bindings/vendor-prefixes.txt @@ -36,6 +36,7 @@ aptina Aptina Imaging arasan Arasan Chip Systems archermind ArcherMind Technology (Nanjing) Co., Ltd. arctic Arctic Sand +arcx arcx Inc. / Archronix Inc. aries Aries Embedded GmbH arm ARM Ltd. armadeus ARMadeus Systems SARL -- cgit v1.2.3 From 8f34c5b5afce91d171bb0802631197484cb69b8b Mon Sep 17 00:00:00 2001 From: Thomas Gleixner Date: Sun, 14 Apr 2019 17:59:45 +0200 Subject: x86/exceptions: Make IST index zero based The defines for the exception stack (IST) array in the TSS are using the SDM convention IST1 - IST7. That causes all sorts of code to subtract 1 for array indices related to IST. That's confusing at best and does not provide any value. Make the indices zero based and fixup the usage sites. The only code which needs to adjust the 0 based index is the interrupt descriptor setup which needs to add 1 now. Signed-off-by: Thomas Gleixner Signed-off-by: Borislav Petkov Reviewed-by: Sean Christopherson Cc: Andy Lutomirski Cc: Baoquan He Cc: "Chang S. Bae" Cc: Dave Hansen Cc: Dominik Brodowski Cc: Dou Liyang Cc: "H. Peter Anvin" Cc: Ingo Molnar Cc: Jonathan Corbet Cc: Josh Poimboeuf Cc: "Kirill A. Shutemov" Cc: Konrad Rzeszutek Wilk Cc: linux-doc@vger.kernel.org Cc: Nicolai Stange Cc: Peter Zijlstra Cc: Qian Cai Cc: x86-ml Link: https://lkml.kernel.org/r/20190414160144.331772825@linutronix.de --- Documentation/x86/kernel-stacks | 8 ++++---- arch/x86/entry/entry_64.S | 4 ++-- arch/x86/include/asm/page_64_types.h | 13 ++++++++----- arch/x86/kernel/cpu/common.c | 4 ++-- arch/x86/kernel/dumpstack_64.c | 14 +++++++------- arch/x86/kernel/idt.c | 15 +++++++++------ arch/x86/kernel/irq_64.c | 2 +- arch/x86/mm/fault.c | 2 +- 8 files changed, 34 insertions(+), 28 deletions(-) (limited to 'Documentation') diff --git a/Documentation/x86/kernel-stacks b/Documentation/x86/kernel-stacks index 9a0aa4d3a866..1b04596caea9 100644 --- a/Documentation/x86/kernel-stacks +++ b/Documentation/x86/kernel-stacks @@ -59,7 +59,7 @@ If that assumption is ever broken then the stacks will become corrupt. The currently assigned IST stacks are :- -* DOUBLEFAULT_STACK. EXCEPTION_STKSZ (PAGE_SIZE). +* ESTACK_DF. EXCEPTION_STKSZ (PAGE_SIZE). Used for interrupt 8 - Double Fault Exception (#DF). @@ -68,7 +68,7 @@ The currently assigned IST stacks are :- Using a separate stack allows the kernel to recover from it well enough in many cases to still output an oops. -* NMI_STACK. EXCEPTION_STKSZ (PAGE_SIZE). +* ESTACK_NMI. EXCEPTION_STKSZ (PAGE_SIZE). Used for non-maskable interrupts (NMI). @@ -76,7 +76,7 @@ The currently assigned IST stacks are :- middle of switching stacks. Using IST for NMI events avoids making assumptions about the previous state of the kernel stack. -* DEBUG_STACK. DEBUG_STKSZ +* ESTACK_DB. DEBUG_STKSZ Used for hardware debug interrupts (interrupt 1) and for software debug interrupts (INT3). @@ -86,7 +86,7 @@ The currently assigned IST stacks are :- avoids making assumptions about the previous state of the kernel stack. -* MCE_STACK. EXCEPTION_STKSZ (PAGE_SIZE). +* ESTACK_MCE. EXCEPTION_STKSZ (PAGE_SIZE). Used for interrupt 18 - Machine Check Exception (#MC). diff --git a/arch/x86/entry/entry_64.S b/arch/x86/entry/entry_64.S index 1f0efdb7b629..fd0a50452cb3 100644 --- a/arch/x86/entry/entry_64.S +++ b/arch/x86/entry/entry_64.S @@ -841,7 +841,7 @@ apicinterrupt IRQ_WORK_VECTOR irq_work_interrupt smp_irq_work_interrupt /* * Exception entry points. */ -#define CPU_TSS_IST(x) PER_CPU_VAR(cpu_tss_rw) + (TSS_ist + ((x) - 1) * 8) +#define CPU_TSS_IST(x) PER_CPU_VAR(cpu_tss_rw) + (TSS_ist + (x) * 8) /** * idtentry - Generate an IDT entry stub @@ -1129,7 +1129,7 @@ apicinterrupt3 HYPERV_STIMER0_VECTOR \ hv_stimer0_callback_vector hv_stimer0_vector_handler #endif /* CONFIG_HYPERV */ -idtentry debug do_debug has_error_code=0 paranoid=1 shift_ist=DEBUG_STACK +idtentry debug do_debug has_error_code=0 paranoid=1 shift_ist=ESTACK_DB idtentry int3 do_int3 has_error_code=0 idtentry stack_segment do_stack_segment has_error_code=1 diff --git a/arch/x86/include/asm/page_64_types.h b/arch/x86/include/asm/page_64_types.h index bcd8c0518604..6ab2c54c1bf9 100644 --- a/arch/x86/include/asm/page_64_types.h +++ b/arch/x86/include/asm/page_64_types.h @@ -24,11 +24,14 @@ #define IRQ_STACK_ORDER (2 + KASAN_STACK_ORDER) #define IRQ_STACK_SIZE (PAGE_SIZE << IRQ_STACK_ORDER) -#define DOUBLEFAULT_STACK 1 -#define NMI_STACK 2 -#define DEBUG_STACK 3 -#define MCE_STACK 4 -#define N_EXCEPTION_STACKS 4 /* hw limit: 7 */ +/* + * The index for the tss.ist[] array. The hardware limit is 7 entries. + */ +#define ESTACK_DF 0 +#define ESTACK_NMI 1 +#define ESTACK_DB 2 +#define ESTACK_MCE 3 +#define N_EXCEPTION_STACKS 4 /* * Set __PAGE_OFFSET to the most negative possible address + diff --git a/arch/x86/kernel/cpu/common.c b/arch/x86/kernel/cpu/common.c index cb28e98a0659..0e4cb718fc4a 100644 --- a/arch/x86/kernel/cpu/common.c +++ b/arch/x86/kernel/cpu/common.c @@ -516,7 +516,7 @@ DEFINE_PER_CPU(struct cpu_entry_area *, cpu_entry_area); */ static const unsigned int exception_stack_sizes[N_EXCEPTION_STACKS] = { [0 ... N_EXCEPTION_STACKS - 1] = EXCEPTION_STKSZ, - [DEBUG_STACK - 1] = DEBUG_STKSZ + [ESTACK_DB] = DEBUG_STKSZ }; #endif @@ -1760,7 +1760,7 @@ void cpu_init(void) estacks += exception_stack_sizes[v]; oist->ist[v] = t->x86_tss.ist[v] = (unsigned long)estacks; - if (v == DEBUG_STACK-1) + if (v == ESTACK_DB) per_cpu(debug_stack_addr, cpu) = (unsigned long)estacks; } } diff --git a/arch/x86/kernel/dumpstack_64.c b/arch/x86/kernel/dumpstack_64.c index 90f0fa88cbb3..455b47ef9250 100644 --- a/arch/x86/kernel/dumpstack_64.c +++ b/arch/x86/kernel/dumpstack_64.c @@ -18,16 +18,16 @@ #include -static char *exception_stack_names[N_EXCEPTION_STACKS] = { - [ DOUBLEFAULT_STACK-1 ] = "#DF", - [ NMI_STACK-1 ] = "NMI", - [ DEBUG_STACK-1 ] = "#DB", - [ MCE_STACK-1 ] = "#MC", +static const char *exception_stack_names[N_EXCEPTION_STACKS] = { + [ ESTACK_DF ] = "#DF", + [ ESTACK_NMI ] = "NMI", + [ ESTACK_DB ] = "#DB", + [ ESTACK_MCE ] = "#MC", }; -static unsigned long exception_stack_sizes[N_EXCEPTION_STACKS] = { +static const unsigned long exception_stack_sizes[N_EXCEPTION_STACKS] = { [0 ... N_EXCEPTION_STACKS - 1] = EXCEPTION_STKSZ, - [DEBUG_STACK - 1] = DEBUG_STKSZ + [ESTACK_DB] = DEBUG_STKSZ }; const char *stack_type_name(enum stack_type type) diff --git a/arch/x86/kernel/idt.c b/arch/x86/kernel/idt.c index 2877606e97de..2188f734ec61 100644 --- a/arch/x86/kernel/idt.c +++ b/arch/x86/kernel/idt.c @@ -41,9 +41,12 @@ struct idt_data { #define SYSG(_vector, _addr) \ G(_vector, _addr, DEFAULT_STACK, GATE_INTERRUPT, DPL3, __KERNEL_CS) -/* Interrupt gate with interrupt stack */ +/* + * Interrupt gate with interrupt stack. The _ist index is the index in + * the tss.ist[] array, but for the descriptor it needs to start at 1. + */ #define ISTG(_vector, _addr, _ist) \ - G(_vector, _addr, _ist, GATE_INTERRUPT, DPL0, __KERNEL_CS) + G(_vector, _addr, _ist + 1, GATE_INTERRUPT, DPL0, __KERNEL_CS) /* Task gate */ #define TSKG(_vector, _gdt) \ @@ -180,11 +183,11 @@ gate_desc debug_idt_table[IDT_ENTRIES] __page_aligned_bss; * cpu_init() when the TSS has been initialized. */ static const __initconst struct idt_data ist_idts[] = { - ISTG(X86_TRAP_DB, debug, DEBUG_STACK), - ISTG(X86_TRAP_NMI, nmi, NMI_STACK), - ISTG(X86_TRAP_DF, double_fault, DOUBLEFAULT_STACK), + ISTG(X86_TRAP_DB, debug, ESTACK_DB), + ISTG(X86_TRAP_NMI, nmi, ESTACK_NMI), + ISTG(X86_TRAP_DF, double_fault, ESTACK_DF), #ifdef CONFIG_X86_MCE - ISTG(X86_TRAP_MC, &machine_check, MCE_STACK), + ISTG(X86_TRAP_MC, &machine_check, ESTACK_MCE), #endif }; diff --git a/arch/x86/kernel/irq_64.c b/arch/x86/kernel/irq_64.c index cf200466d5c8..182e8b245e06 100644 --- a/arch/x86/kernel/irq_64.c +++ b/arch/x86/kernel/irq_64.c @@ -61,7 +61,7 @@ static inline void stack_overflow_check(struct pt_regs *regs) return; oist = this_cpu_ptr(&orig_ist); - estack_top = (u64)oist->ist[DEBUG_STACK]; + estack_top = (u64)oist->ist[ESTACK_DB]; estack_bottom = estack_top - DEBUG_STKSZ + STACK_MARGIN; if (regs->sp >= estack_bottom && regs->sp <= estack_top) return; diff --git a/arch/x86/mm/fault.c b/arch/x86/mm/fault.c index 667f1da36208..0524e1d74f24 100644 --- a/arch/x86/mm/fault.c +++ b/arch/x86/mm/fault.c @@ -793,7 +793,7 @@ no_context(struct pt_regs *regs, unsigned long error_code, if (is_vmalloc_addr((void *)address) && (((unsigned long)tsk->stack - 1 - address < PAGE_SIZE) || address - ((unsigned long)tsk->stack + THREAD_SIZE) < PAGE_SIZE)) { - unsigned long stack = this_cpu_read(orig_ist.ist[DOUBLEFAULT_STACK]) - sizeof(void *); + unsigned long stack = this_cpu_read(orig_ist.ist[ESTACK_DF]) - sizeof(void *); /* * We're likely to be running with very little stack space * left. It's plausible that we'd hit this condition but -- cgit v1.2.3 From 2a594d4ccf3f10f80b77d71bd3dad10813ac0137 Mon Sep 17 00:00:00 2001 From: Thomas Gleixner Date: Sun, 14 Apr 2019 17:59:57 +0200 Subject: x86/exceptions: Split debug IST stack The debug IST stack is actually two separate debug stacks to handle #DB recursion. This is required because the CPU starts always at top of stack on exception entry, which means on #DB recursion the second #DB would overwrite the stack of the first. The low level entry code therefore adjusts the top of stack on entry so a secondary #DB starts from a different stack page. But the stack pages are adjacent without a guard page between them. Split the debug stack into 3 stacks which are separated by guard pages. The 3rd stack is never mapped into the cpu_entry_area and is only there to catch triple #DB nesting: --- top of DB_stack <- Initial stack --- end of DB_stack guard page --- top of DB1_stack <- Top of stack after entering first #DB --- end of DB1_stack guard page --- top of DB2_stack <- Top of stack after entering second #DB --- end of DB2_stack guard page If DB2 would not act as the final guard hole, a second #DB would point the top of #DB stack to the stack below #DB1 which would be valid and not catch the not so desired triple nesting. The backing store does not allocate any memory for DB2 and its guard page as it is not going to be mapped into the cpu_entry_area. - Adjust the low level entry code so it adjusts top of #DB with the offset between the stacks instead of exception stack size. - Make the dumpstack code aware of the new stacks. - Adjust the in_debug_stack() implementation and move it into the NMI code where it belongs. As this is NMI hotpath code, it just checks the full area between top of DB_stack and bottom of DB1_stack without checking for the guard page. That's correct because the NMI cannot hit a stackpointer pointing to the guard page between DB and DB1 stack. Even if it would, then the NMI operation still is unaffected, but the resume of the debug exception on the topmost DB stack will crash by touching the guard page. [ bp: Make exception_stack_names static const char * const ] Suggested-by: Andy Lutomirski Signed-off-by: Thomas Gleixner Signed-off-by: Borislav Petkov Reviewed-by: Sean Christopherson Cc: Andy Lutomirski Cc: Baoquan He Cc: "Chang S. Bae" Cc: Dave Hansen Cc: Dominik Brodowski Cc: "H. Peter Anvin" Cc: Ingo Molnar Cc: Joerg Roedel Cc: Jonathan Corbet Cc: Josh Poimboeuf Cc: Juergen Gross Cc: "Kirill A. Shutemov" Cc: Konrad Rzeszutek Wilk Cc: linux-doc@vger.kernel.org Cc: Masahiro Yamada Cc: Peter Zijlstra Cc: Qian Cai Cc: Sean Christopherson Cc: x86-ml Link: https://lkml.kernel.org/r/20190414160145.439944544@linutronix.de --- Documentation/x86/kernel-stacks | 7 ++++++- arch/x86/entry/entry_64.S | 8 ++++---- arch/x86/include/asm/cpu_entry_area.h | 14 ++++++++++---- arch/x86/include/asm/debugreg.h | 2 -- arch/x86/include/asm/page_64_types.h | 3 --- arch/x86/kernel/asm-offsets_64.c | 2 ++ arch/x86/kernel/cpu/common.c | 11 ----------- arch/x86/kernel/dumpstack_64.c | 12 ++++++++---- arch/x86/kernel/nmi.c | 20 +++++++++++++++++++- arch/x86/mm/cpu_entry_area.c | 4 +++- 10 files changed, 52 insertions(+), 31 deletions(-) (limited to 'Documentation') diff --git a/Documentation/x86/kernel-stacks b/Documentation/x86/kernel-stacks index 1b04596caea9..d1bfb0b95ee0 100644 --- a/Documentation/x86/kernel-stacks +++ b/Documentation/x86/kernel-stacks @@ -76,7 +76,7 @@ The currently assigned IST stacks are :- middle of switching stacks. Using IST for NMI events avoids making assumptions about the previous state of the kernel stack. -* ESTACK_DB. DEBUG_STKSZ +* ESTACK_DB. EXCEPTION_STKSZ (PAGE_SIZE). Used for hardware debug interrupts (interrupt 1) and for software debug interrupts (INT3). @@ -86,6 +86,11 @@ The currently assigned IST stacks are :- avoids making assumptions about the previous state of the kernel stack. + To handle nested #DB correctly there exist two instances of DB stacks. On + #DB entry the IST stackpointer for #DB is switched to the second instance + so a nested #DB starts from a clean stack. The nested #DB switches + the IST stackpointer to a guard hole to catch triple nesting. + * ESTACK_MCE. EXCEPTION_STKSZ (PAGE_SIZE). Used for interrupt 18 - Machine Check Exception (#MC). diff --git a/arch/x86/entry/entry_64.S b/arch/x86/entry/entry_64.S index 5c0348504a4b..ee649f1f279e 100644 --- a/arch/x86/entry/entry_64.S +++ b/arch/x86/entry/entry_64.S @@ -879,7 +879,7 @@ apicinterrupt IRQ_WORK_VECTOR irq_work_interrupt smp_irq_work_interrupt * @paranoid == 2 is special: the stub will never switch stacks. This is for * #DF: if the thread stack is somehow unusable, we'll still get a useful OOPS. */ -.macro idtentry sym do_sym has_error_code:req paranoid=0 shift_ist=-1 +.macro idtentry sym do_sym has_error_code:req paranoid=0 shift_ist=-1 ist_offset=0 ENTRY(\sym) UNWIND_HINT_IRET_REGS offset=\has_error_code*8 @@ -925,13 +925,13 @@ ENTRY(\sym) .endif .if \shift_ist != -1 - subq $EXCEPTION_STKSZ, CPU_TSS_IST(\shift_ist) + subq $\ist_offset, CPU_TSS_IST(\shift_ist) .endif call \do_sym .if \shift_ist != -1 - addq $EXCEPTION_STKSZ, CPU_TSS_IST(\shift_ist) + addq $\ist_offset, CPU_TSS_IST(\shift_ist) .endif /* these procedures expect "no swapgs" flag in ebx */ @@ -1129,7 +1129,7 @@ apicinterrupt3 HYPERV_STIMER0_VECTOR \ hv_stimer0_callback_vector hv_stimer0_vector_handler #endif /* CONFIG_HYPERV */ -idtentry debug do_debug has_error_code=0 paranoid=1 shift_ist=IST_INDEX_DB +idtentry debug do_debug has_error_code=0 paranoid=1 shift_ist=IST_INDEX_DB ist_offset=DB_STACK_OFFSET idtentry int3 do_int3 has_error_code=0 idtentry stack_segment do_stack_segment has_error_code=1 diff --git a/arch/x86/include/asm/cpu_entry_area.h b/arch/x86/include/asm/cpu_entry_area.h index 9c96406e6d2b..cff3f3f3bfe0 100644 --- a/arch/x86/include/asm/cpu_entry_area.h +++ b/arch/x86/include/asm/cpu_entry_area.h @@ -10,25 +10,29 @@ #ifdef CONFIG_X86_64 /* Macro to enforce the same ordering and stack sizes */ -#define ESTACKS_MEMBERS(guardsize) \ +#define ESTACKS_MEMBERS(guardsize, db2_holesize)\ char DF_stack_guard[guardsize]; \ char DF_stack[EXCEPTION_STKSZ]; \ char NMI_stack_guard[guardsize]; \ char NMI_stack[EXCEPTION_STKSZ]; \ + char DB2_stack_guard[guardsize]; \ + char DB2_stack[db2_holesize]; \ + char DB1_stack_guard[guardsize]; \ + char DB1_stack[EXCEPTION_STKSZ]; \ char DB_stack_guard[guardsize]; \ - char DB_stack[DEBUG_STKSZ]; \ + char DB_stack[EXCEPTION_STKSZ]; \ char MCE_stack_guard[guardsize]; \ char MCE_stack[EXCEPTION_STKSZ]; \ char IST_top_guard[guardsize]; \ /* The exception stacks' physical storage. No guard pages required */ struct exception_stacks { - ESTACKS_MEMBERS(0) + ESTACKS_MEMBERS(0, 0) }; /* The effective cpu entry area mapping with guard pages. */ struct cea_exception_stacks { - ESTACKS_MEMBERS(PAGE_SIZE) + ESTACKS_MEMBERS(PAGE_SIZE, EXCEPTION_STKSZ) }; /* @@ -37,6 +41,8 @@ struct cea_exception_stacks { enum exception_stack_ordering { ESTACK_DF, ESTACK_NMI, + ESTACK_DB2, + ESTACK_DB1, ESTACK_DB, ESTACK_MCE, N_EXCEPTION_STACKS diff --git a/arch/x86/include/asm/debugreg.h b/arch/x86/include/asm/debugreg.h index 9e5ca30738e5..1a8609a15856 100644 --- a/arch/x86/include/asm/debugreg.h +++ b/arch/x86/include/asm/debugreg.h @@ -104,11 +104,9 @@ static inline void debug_stack_usage_dec(void) { __this_cpu_dec(debug_stack_usage); } -int is_debug_stack(unsigned long addr); void debug_stack_set_zero(void); void debug_stack_reset(void); #else /* !X86_64 */ -static inline int is_debug_stack(unsigned long addr) { return 0; } static inline void debug_stack_set_zero(void) { } static inline void debug_stack_reset(void) { } static inline void debug_stack_usage_inc(void) { } diff --git a/arch/x86/include/asm/page_64_types.h b/arch/x86/include/asm/page_64_types.h index 056de887b220..793c14c372cb 100644 --- a/arch/x86/include/asm/page_64_types.h +++ b/arch/x86/include/asm/page_64_types.h @@ -18,9 +18,6 @@ #define EXCEPTION_STACK_ORDER (0 + KASAN_STACK_ORDER) #define EXCEPTION_STKSZ (PAGE_SIZE << EXCEPTION_STACK_ORDER) -#define DEBUG_STACK_ORDER (EXCEPTION_STACK_ORDER + 1) -#define DEBUG_STKSZ (PAGE_SIZE << DEBUG_STACK_ORDER) - #define IRQ_STACK_ORDER (2 + KASAN_STACK_ORDER) #define IRQ_STACK_SIZE (PAGE_SIZE << IRQ_STACK_ORDER) diff --git a/arch/x86/kernel/asm-offsets_64.c b/arch/x86/kernel/asm-offsets_64.c index ddced33184b5..f5281567e28e 100644 --- a/arch/x86/kernel/asm-offsets_64.c +++ b/arch/x86/kernel/asm-offsets_64.c @@ -68,6 +68,8 @@ int main(void) #undef ENTRY OFFSET(TSS_ist, tss_struct, x86_tss.ist); + DEFINE(DB_STACK_OFFSET, offsetof(struct cea_exception_stacks, DB_stack) - + offsetof(struct cea_exception_stacks, DB1_stack)); BLANK(); #ifdef CONFIG_STACKPROTECTOR diff --git a/arch/x86/kernel/cpu/common.c b/arch/x86/kernel/cpu/common.c index 143aceaf9a9a..88cab45707a9 100644 --- a/arch/x86/kernel/cpu/common.c +++ b/arch/x86/kernel/cpu/common.c @@ -1549,17 +1549,7 @@ void syscall_init(void) X86_EFLAGS_IOPL|X86_EFLAGS_AC|X86_EFLAGS_NT); } -static DEFINE_PER_CPU(unsigned long, debug_stack_addr); DEFINE_PER_CPU(int, debug_stack_usage); - -int is_debug_stack(unsigned long addr) -{ - return __this_cpu_read(debug_stack_usage) || - (addr <= __this_cpu_read(debug_stack_addr) && - addr > (__this_cpu_read(debug_stack_addr) - DEBUG_STKSZ)); -} -NOKPROBE_SYMBOL(is_debug_stack); - DEFINE_PER_CPU(u32, debug_idt_ctr); void debug_stack_set_zero(void) @@ -1735,7 +1725,6 @@ void cpu_init(void) t->x86_tss.ist[IST_INDEX_NMI] = __this_cpu_ist_top_va(NMI); t->x86_tss.ist[IST_INDEX_DB] = __this_cpu_ist_top_va(DB); t->x86_tss.ist[IST_INDEX_MCE] = __this_cpu_ist_top_va(MCE); - per_cpu(debug_stack_addr, cpu) = t->x86_tss.ist[IST_INDEX_DB]; } t->x86_tss.io_bitmap_base = IO_BITMAP_OFFSET; diff --git a/arch/x86/kernel/dumpstack_64.c b/arch/x86/kernel/dumpstack_64.c index f6fbd0438f9e..fca97bd3d8ae 100644 --- a/arch/x86/kernel/dumpstack_64.c +++ b/arch/x86/kernel/dumpstack_64.c @@ -19,16 +19,18 @@ #include #include -static const char *exception_stack_names[N_EXCEPTION_STACKS] = { +static const char * const exception_stack_names[] = { [ ESTACK_DF ] = "#DF", [ ESTACK_NMI ] = "NMI", + [ ESTACK_DB2 ] = "#DB2", + [ ESTACK_DB1 ] = "#DB1", [ ESTACK_DB ] = "#DB", [ ESTACK_MCE ] = "#MC", }; const char *stack_type_name(enum stack_type type) { - BUILD_BUG_ON(N_EXCEPTION_STACKS != 4); + BUILD_BUG_ON(N_EXCEPTION_STACKS != 6); if (type == STACK_TYPE_IRQ) return "IRQ"; @@ -58,9 +60,11 @@ struct estack_layout { .end = offsetof(struct cea_exception_stacks, x## _stack_guard) \ } -static const struct estack_layout layout[N_EXCEPTION_STACKS] = { +static const struct estack_layout layout[] = { [ ESTACK_DF ] = ESTACK_ENTRY(DF), [ ESTACK_NMI ] = ESTACK_ENTRY(NMI), + [ ESTACK_DB2 ] = { .begin = 0, .end = 0}, + [ ESTACK_DB1 ] = ESTACK_ENTRY(DB1), [ ESTACK_DB ] = ESTACK_ENTRY(DB), [ ESTACK_MCE ] = ESTACK_ENTRY(MCE), }; @@ -71,7 +75,7 @@ static bool in_exception_stack(unsigned long *stack, struct stack_info *info) struct pt_regs *regs; unsigned int k; - BUILD_BUG_ON(N_EXCEPTION_STACKS != 4); + BUILD_BUG_ON(N_EXCEPTION_STACKS != 6); estacks = (unsigned long)__this_cpu_read(cea_exception_stacks); diff --git a/arch/x86/kernel/nmi.c b/arch/x86/kernel/nmi.c index 18bc9b51ac9b..3755d0310026 100644 --- a/arch/x86/kernel/nmi.c +++ b/arch/x86/kernel/nmi.c @@ -21,13 +21,14 @@ #include #include #include +#include #include #if defined(CONFIG_EDAC) #include #endif -#include +#include #include #include #include @@ -487,6 +488,23 @@ static DEFINE_PER_CPU(unsigned long, nmi_cr2); * switch back to the original IDT. */ static DEFINE_PER_CPU(int, update_debug_stack); + +static bool notrace is_debug_stack(unsigned long addr) +{ + struct cea_exception_stacks *cs = __this_cpu_read(cea_exception_stacks); + unsigned long top = CEA_ESTACK_TOP(cs, DB); + unsigned long bot = CEA_ESTACK_BOT(cs, DB1); + + if (__this_cpu_read(debug_stack_usage)) + return true; + /* + * Note, this covers the guard page between DB and DB1 as well to + * avoid two checks. But by all means @addr can never point into + * the guard page. + */ + return addr >= bot && addr < top; +} +NOKPROBE_SYMBOL(is_debug_stack); #endif dotraplinkage notrace void diff --git a/arch/x86/mm/cpu_entry_area.c b/arch/x86/mm/cpu_entry_area.c index a00d0d059c8a..752ad11d6868 100644 --- a/arch/x86/mm/cpu_entry_area.c +++ b/arch/x86/mm/cpu_entry_area.c @@ -98,10 +98,12 @@ static void __init percpu_setup_exception_stacks(unsigned int cpu) /* * The exceptions stack mappings in the per cpu area are protected - * by guard pages so each stack must be mapped separately. + * by guard pages so each stack must be mapped separately. DB2 is + * not mapped; it just exists to catch triple nesting of #DB. */ cea_map_stack(DF); cea_map_stack(NMI); + cea_map_stack(DB1); cea_map_stack(DB); cea_map_stack(MCE); } -- cgit v1.2.3 From f8e8cfda6569859c339ffacbb93e02d9cdb08574 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 17 Apr 2019 06:46:09 -0300 Subject: docs: hwmon: k10temp: convert to ReST format Convert k10temp to ReST format, in order to allow it to be parsed by Sphinx. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Guenter Roeck --- Documentation/hwmon/k10temp | 37 ++++++++++++++++++++++++++++++++++++- 1 file changed, 36 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/hwmon/k10temp b/Documentation/hwmon/k10temp index 254d2f55345a..12a86ba17de9 100644 --- a/Documentation/hwmon/k10temp +++ b/Documentation/hwmon/k10temp @@ -2,42 +2,77 @@ Kernel driver k10temp ===================== Supported chips: + * AMD Family 10h processors: + Socket F: Quad-Core/Six-Core/Embedded Opteron (but see below) + Socket AM2+: Quad-Core Opteron, Phenom (II) X3/X4, Athlon X2 (but see below) + Socket AM3: Quad-Core Opteron, Athlon/Phenom II X2/X3/X4, Sempron II + Socket S1G3: Athlon II, Sempron, Turion II + * AMD Family 11h processors: + Socket S1G2: Athlon (X2), Sempron (X2), Turion X2 (Ultra) + * AMD Family 12h processors: "Llano" (E2/A4/A6/A8-Series) + * AMD Family 14h processors: "Brazos" (C/E/G/Z-Series) + * AMD Family 15h processors: "Bulldozer" (FX-Series), "Trinity", "Kaveri", "Carrizo" + * AMD Family 16h processors: "Kabini", "Mullins" Prefix: 'k10temp' + Addresses scanned: PCI space + Datasheets: + BIOS and Kernel Developer's Guide (BKDG) For AMD Family 10h Processors: + http://support.amd.com/us/Processor_TechDocs/31116.pdf + BIOS and Kernel Developer's Guide (BKDG) for AMD Family 11h Processors: + http://support.amd.com/us/Processor_TechDocs/41256.pdf + BIOS and Kernel Developer's Guide (BKDG) for AMD Family 12h Processors: + http://support.amd.com/us/Processor_TechDocs/41131.pdf + BIOS and Kernel Developer's Guide (BKDG) for AMD Family 14h Models 00h-0Fh Processors: + http://support.amd.com/us/Processor_TechDocs/43170.pdf + Revision Guide for AMD Family 10h Processors: + http://support.amd.com/us/Processor_TechDocs/41322.pdf + Revision Guide for AMD Family 11h Processors: + http://support.amd.com/us/Processor_TechDocs/41788.pdf + Revision Guide for AMD Family 12h Processors: + http://support.amd.com/us/Processor_TechDocs/44739.pdf + Revision Guide for AMD Family 14h Models 00h-0Fh Processors: + http://support.amd.com/us/Processor_TechDocs/47534.pdf + AMD Family 11h Processor Power and Thermal Data Sheet for Notebooks: + http://support.amd.com/us/Processor_TechDocs/43373.pdf + AMD Family 10h Server and Workstation Processor Power and Thermal Data Sheet: + http://support.amd.com/us/Processor_TechDocs/43374.pdf + AMD Family 10h Desktop Processor Power and Thermal Data Sheet: + http://support.amd.com/us/Processor_TechDocs/43375.pdf Author: Clemens Ladisch @@ -60,7 +95,7 @@ are using an AM3 processor on an AM2+ mainboard, you can safely use the There is one temperature measurement value, available as temp1_input in sysfs. It is measured in degrees Celsius with a resolution of 1/8th degree. -Please note that it is defined as a relative value; to quote the AMD manual: +Please note that it is defined as a relative value; to quote the AMD manual:: Tctl is the processor temperature control value, used by the platform to control cooling systems. Tctl is a non-physical temperature on an -- cgit v1.2.3 From a449dff630eb9a78d38c7db39428db8a9079b9ea Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 17 Apr 2019 06:46:10 -0300 Subject: docs: hwmon: vexpress: convert to ReST format Convert vexpress to ReST format, in order to allow it to be parsed by Sphinx. Signed-off-by: Mauro Carvalho Chehab Acked-by: Liviu Dudau Signed-off-by: Guenter Roeck --- Documentation/hwmon/vexpress | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/hwmon/vexpress b/Documentation/hwmon/vexpress index 557d6d5ad90d..8c861c8151ac 100644 --- a/Documentation/hwmon/vexpress +++ b/Documentation/hwmon/vexpress @@ -2,14 +2,21 @@ Kernel driver vexpress ====================== Supported systems: + * ARM Ltd. Versatile Express platform + Prefix: 'vexpress' + Datasheets: + * "Hardware Description" sections of the Technical Reference Manuals - for the Versatile Express boards: - http://infocenter.arm.com/help/topic/com.arm.doc.subset.boards.express/index.html + for the Versatile Express boards: + + - http://infocenter.arm.com/help/topic/com.arm.doc.subset.boards.express/index.html + * Section "4.4.14. System Configuration registers" of the V2M-P1 TRM: - http://infocenter.arm.com/help/index.jsp?topic=/com.arm.doc.dui0447-/index.html + + - http://infocenter.arm.com/help/index.jsp?topic=/com.arm.doc.dui0447-/index.html Author: Pawel Moll -- cgit v1.2.3 From de6f291746075c1c6759747105cbca667f5abb8f Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 17 Apr 2019 06:46:11 -0300 Subject: docs: hwmon: menf21bmc: convert to ReST format Convert menf21bmc to ReST format, in order to allow it to be parsed by Sphinx. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Guenter Roeck --- Documentation/hwmon/menf21bmc | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'Documentation') diff --git a/Documentation/hwmon/menf21bmc b/Documentation/hwmon/menf21bmc index 2a273a065c5e..1f0c6b2235ab 100644 --- a/Documentation/hwmon/menf21bmc +++ b/Documentation/hwmon/menf21bmc @@ -2,8 +2,11 @@ Kernel driver menf21bmc_hwmon ============================= Supported chips: + * MEN 14F021P00 + Prefix: 'menf21bmc_hwmon' + Adresses scanned: - Author: Andreas Werner @@ -34,6 +37,7 @@ Sysfs entries The following attributes are supported. All attributes are read only The Limits are read once by the driver. +=============== ========================== in0_input +3.3V input voltage in1_input +5.0V input voltage in2_input +12.0V input voltage @@ -48,3 +52,4 @@ in1_label "MON_5V" in2_label "MON_12V" in3_label "5V_STANDBY" in4_label "VBAT" +=============== ========================== -- cgit v1.2.3 From 42c027a5b7ba04224080ff46b6ef44658ad7554e Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 17 Apr 2019 06:46:12 -0300 Subject: docs: hwmon: sch5627: convert to ReST format Convert sch5627 to ReST format, in order to allow it to be parsed by Sphinx. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Guenter Roeck --- Documentation/hwmon/sch5627 | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'Documentation') diff --git a/Documentation/hwmon/sch5627 b/Documentation/hwmon/sch5627 index 0551d266c51c..187682e99114 100644 --- a/Documentation/hwmon/sch5627 +++ b/Documentation/hwmon/sch5627 @@ -2,9 +2,13 @@ Kernel driver sch5627 ===================== Supported chips: + * SMSC SCH5627 + Prefix: 'sch5627' + Addresses scanned: none, address read from Super I/O config space + Datasheet: Application Note available upon request Author: Hans de Goede -- cgit v1.2.3 From 92e395d7b1738f39cfa9f18b9bd77df8f4b7bc50 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 17 Apr 2019 06:46:13 -0300 Subject: docs: hwmon: emc2103: convert to ReST format Convert emc2103 to ReST format, in order to allow it to be parsed by Sphinx. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Guenter Roeck --- Documentation/hwmon/emc2103 | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/hwmon/emc2103 b/Documentation/hwmon/emc2103 index a12b2c127140..6a6ca6d1b34e 100644 --- a/Documentation/hwmon/emc2103 +++ b/Documentation/hwmon/emc2103 @@ -2,13 +2,17 @@ Kernel driver emc2103 ====================== Supported chips: + * SMSC EMC2103 + Addresses scanned: I2C 0x2e + Prefix: 'emc2103' + Datasheet: Not public Authors: - Steve Glendinning + Steve Glendinning Description ----------- -- cgit v1.2.3 From a9fc881b9bac7c4ae1e8569ba93e8600ce1a1c09 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 17 Apr 2019 06:46:14 -0300 Subject: docs: hwmon: pc87360: convert to ReST format Convert pc87360 to ReST format, in order to allow it to be parsed by Sphinx. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Guenter Roeck --- Documentation/hwmon/pc87360 | 38 ++++++++++++++++++++++++++------------ 1 file changed, 26 insertions(+), 12 deletions(-) (limited to 'Documentation') diff --git a/Documentation/hwmon/pc87360 b/Documentation/hwmon/pc87360 index d5f5cf16ce59..4bad07bce54b 100644 --- a/Documentation/hwmon/pc87360 +++ b/Documentation/hwmon/pc87360 @@ -2,14 +2,19 @@ Kernel driver pc87360 ===================== Supported chips: + * National Semiconductor PC87360, PC87363, PC87364, PC87365 and PC87366 + Prefixes: 'pc87360', 'pc87363', 'pc87364', 'pc87365', 'pc87366' + Addresses scanned: none, address read from Super I/O config space + Datasheets: No longer available Authors: Jean Delvare Thanks to Sandeep Mehta, Tonko de Rooy and Daniel Ceregatti for testing. + Thanks to Rudolf Marek for helping me investigate conversion issues. @@ -17,11 +22,13 @@ Module Parameters ----------------- * init int - Chip initialization level: - 0: None - *1: Forcibly enable internal voltage and temperature channels, except in9 - 2: Forcibly enable all voltage and temperature channels, except in9 - 3: Forcibly enable all voltage and temperature channels, including in9 + Chip initialization level: + + - 0: None + - **1**: Forcibly enable internal voltage and temperature channels, + except in9 + - 2: Forcibly enable all voltage and temperature channels, except in9 + - 3: Forcibly enable all voltage and temperature channels, including in9 Note that this parameter has no effect for the PC87360, PC87363 and PC87364 chips. @@ -43,13 +50,15 @@ hardware monitoring chipsets, not only controlling and monitoring three fans, but also monitoring eleven voltage inputs and two (PC87365) or up to four (PC87366) temperatures. + =========== ======= ======= ======= ======= ===== Chip #vin #fan #pwm #temp devid - + =========== ======= ======= ======= ======= ===== PC87360 - 2 2 - 0xE1 PC87363 - 2 2 - 0xE8 PC87364 - 3 3 - 0xE4 PC87365 11 3 3 2 0xE5 PC87366 11 3 3 3-4 0xE9 + =========== ======= ======= ======= ======= ===== The driver assumes that no more than one chip is present, and one of the standard Super I/O addresses is used (0x2E/0x2F or 0x4E/0x4F) @@ -68,18 +77,23 @@ have to care no more. For reference, here are a few values about clock dividers: - slowest accuracy highest - measurable around 3000 accurate + =========== =============== =============== =========== + slowest accuracy highest + measurable around 3000 accurate divider speed (RPM) RPM (RPM) speed (RPM) - 1 1882 18 6928 - 2 941 37 4898 - 4 470 74 3464 - 8 235 150 2449 + =========== =============== =============== =========== + 1 1882 18 6928 + 2 941 37 4898 + 4 470 74 3464 + 8 235 150 2449 + =========== =============== =============== =========== For the curious, here is how the values above were computed: + * slowest measurable speed: clock/(255*divider) * accuracy around 3000 RPM: 3000^2/clock * highest accurate speed: sqrt(clock*100) + The clock speed for the PC87360 family is 480 kHz. I arbitrarily chose 100 RPM as the lowest acceptable accuracy. -- cgit v1.2.3 From b413e3fa7fb05a8eea42473456b863c3b2a5511d Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 17 Apr 2019 06:46:15 -0300 Subject: docs: hwmon: fam15h_power: convert to ReST format Convert fam15h_power to ReST format, in order to allow it to be parsed by Sphinx. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Guenter Roeck --- Documentation/hwmon/fam15h_power | 85 +++++++++++++++++++++++++++------------- 1 file changed, 57 insertions(+), 28 deletions(-) (limited to 'Documentation') diff --git a/Documentation/hwmon/fam15h_power b/Documentation/hwmon/fam15h_power index fb594c281c46..fdde632c93a3 100644 --- a/Documentation/hwmon/fam15h_power +++ b/Documentation/hwmon/fam15h_power @@ -2,15 +2,20 @@ Kernel driver fam15h_power ========================== Supported chips: + * AMD Family 15h Processors + * AMD Family 16h Processors Prefix: 'fam15h_power' + Addresses scanned: PCI space + Datasheets: - BIOS and Kernel Developer's Guide (BKDG) For AMD Family 15h Processors - BIOS and Kernel Developer's Guide (BKDG) For AMD Family 16h Processors - AMD64 Architecture Programmer's Manual Volume 2: System Programming + + - BIOS and Kernel Developer's Guide (BKDG) For AMD Family 15h Processors + - BIOS and Kernel Developer's Guide (BKDG) For AMD Family 16h Processors + - AMD64 Architecture Programmer's Manual Volume 2: System Programming Author: Andreas Herrmann @@ -31,14 +36,19 @@ For AMD Family 15h and 16h processors the following power values can be calculated using different processor northbridge function registers: -* BasePwrWatts: Specifies in watts the maximum amount of power - consumed by the processor for NB and logic external to the core. -* ProcessorPwrWatts: Specifies in watts the maximum amount of power - the processor can support. -* CurrPwrWatts: Specifies in watts the current amount of power being - consumed by the processor. +* BasePwrWatts: + Specifies in watts the maximum amount of power + consumed by the processor for NB and logic external to the core. + +* ProcessorPwrWatts: + Specifies in watts the maximum amount of power + the processor can support. +* CurrPwrWatts: + Specifies in watts the current amount of power being + consumed by the processor. This driver provides ProcessorPwrWatts and CurrPwrWatts: + * power1_crit (ProcessorPwrWatts) * power1_input (CurrPwrWatts) @@ -53,35 +63,53 @@ calculate the average power consumed by a processor during a measurement interval Tm. The feature of accumulated power mechanism is indicated by CPUID Fn8000_0007_EDX[12]. -* Tsample: compute unit power accumulator sample period -* Tref: the PTSC counter period -* PTSC: performance timestamp counter -* N: the ratio of compute unit power accumulator sample period to the - PTSC period -* Jmax: max compute unit accumulated power which is indicated by - MaxCpuSwPwrAcc MSR C001007b -* Jx/Jy: compute unit accumulated power which is indicated by - CpuSwPwrAcc MSR C001007a -* Tx/Ty: the value of performance timestamp counter which is indicated - by CU_PTSC MSR C0010280 -* PwrCPUave: CPU average power +* Tsample: + compute unit power accumulator sample period + +* Tref: + the PTSC counter period + +* PTSC: + performance timestamp counter + +* N: + the ratio of compute unit power accumulator sample period to the + PTSC period + +* Jmax: + max compute unit accumulated power which is indicated by + MaxCpuSwPwrAcc MSR C001007b + +* Jx/Jy: + compute unit accumulated power which is indicated by + CpuSwPwrAcc MSR C001007a +* Tx/Ty: + the value of performance timestamp counter which is indicated + by CU_PTSC MSR C0010280 + +* PwrCPUave: + CPU average power i. Determine the ratio of Tsample to Tref by executing CPUID Fn8000_0007. + N = value of CPUID Fn8000_0007_ECX[CpuPwrSampleTimeRatio[15:0]]. ii. Read the full range of the cumulative energy value from the new -MSR MaxCpuSwPwrAcc. + MSR MaxCpuSwPwrAcc. + Jmax = value returned. + iii. At time x, SW reads CpuSwPwrAcc MSR and samples the PTSC. - Jx = value read from CpuSwPwrAcc and Tx = value read from -PTSC. + + Jx = value read from CpuSwPwrAcc and Tx = value read from PTSC. iv. At time y, SW reads CpuSwPwrAcc MSR and samples the PTSC. - Jy = value read from CpuSwPwrAcc and Ty = value read from -PTSC. + + Jy = value read from CpuSwPwrAcc and Ty = value read from PTSC. v. Calculate the average power consumption for a compute unit over -time period (y-x). Unit of result is uWatt. + time period (y-x). Unit of result is uWatt:: + if (Jy < Jx) // Rollover has occurred Jdelta = (Jy + Jmax) - Jx else @@ -90,13 +118,14 @@ time period (y-x). Unit of result is uWatt. This driver provides PwrCPUave and interval(default is 10 millisecond and maximum is 1 second): + * power1_average (PwrCPUave) * power1_average_interval (Interval) The power1_average_interval can be updated at /etc/sensors3.conf file as below: -chip "fam15h_power-*" +chip `fam15h_power-*` set power1_average_interval 0.01 Then save it with "sensors -s". -- cgit v1.2.3 From ce09cfb600d373f338809379de5de40fedf9532c Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 17 Apr 2019 06:46:16 -0300 Subject: docs: hwmon: w83791d: convert to ReST format Convert w83791d to ReST format, in order to allow it to be parsed by Sphinx. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Guenter Roeck --- Documentation/hwmon/w83791d | 123 +++++++++++++++++++++++++------------------- 1 file changed, 71 insertions(+), 52 deletions(-) (limited to 'Documentation') diff --git a/Documentation/hwmon/w83791d b/Documentation/hwmon/w83791d index f4021a285460..a91f9e5fb0c6 100644 --- a/Documentation/hwmon/w83791d +++ b/Documentation/hwmon/w83791d @@ -2,9 +2,13 @@ Kernel driver w83791d ===================== Supported chips: + * Winbond W83791D + Prefix: 'w83791d' + Addresses scanned: I2C 0x2c - 0x2f + Datasheet: http://www.winbond-usa.com/products/winbond_products/pdfs/PCIC/W83791D_W83791Gb.pdf Author: Charles Spirakis @@ -12,39 +16,46 @@ Author: Charles Spirakis This driver was derived from the w83781d.c and w83792d.c source files. Credits: + w83781d.c: - Frodo Looijaard , - Philip Edelbrock , - and Mark Studebaker + + - Frodo Looijaard , + - Philip Edelbrock , + - Mark Studebaker + w83792d.c: - Shane Huang (Winbond), - Rudolf Marek + + - Shane Huang (Winbond), + - Rudolf Marek Additional contributors: - Sven Anders - Marc Hulsman + + - Sven Anders + - Marc Hulsman Module Parameters ----------------- * init boolean - (default 0) - Use 'init=1' to have the driver do extra software initializations. - The default behavior is to do the minimum initialization possible - and depend on the BIOS to properly setup the chip. If you know you - have a w83791d and you're having problems, try init=1 before trying - reset=1. + (default 0) + + Use 'init=1' to have the driver do extra software initializations. + The default behavior is to do the minimum initialization possible + and depend on the BIOS to properly setup the chip. If you know you + have a w83791d and you're having problems, try init=1 before trying + reset=1. * reset boolean - (default 0) - Use 'reset=1' to reset the chip (via index 0x40, bit 7). The default - behavior is no chip reset to preserve BIOS settings. + (default 0) + + Use 'reset=1' to reset the chip (via index 0x40, bit 7). The default + behavior is no chip reset to preserve BIOS settings. * force_subclients=bus,caddr,saddr,saddr - This is used to force the i2c addresses for subclients of - a certain chip. Example usage is `force_subclients=0,0x2f,0x4a,0x4b' - to force the subclients of chip 0x2f on bus 0 to i2c addresses - 0x4a and 0x4b. + This is used to force the i2c addresses for subclients of + a certain chip. Example usage is `force_subclients=0,0x2f,0x4a,0x4b` + to force the subclients of chip 0x2f on bus 0 to i2c addresses + 0x4a and 0x4b. Description @@ -91,11 +102,11 @@ This file is used for both legacy and new code. The sysfs interface to the beep bitmask has migrated from the original legacy method of a single sysfs beep_mask file to a newer method using multiple -*_beep files as described in .../Documentation/hwmon/sysfs-interface. +`*_beep` files as described in `Documentation/hwmon/sysfs-interface`. A similar change has occurred for the bitmap corresponding to the alarms. The original legacy method used a single sysfs alarms file containing a bitmap -of triggered alarms. The newer method uses multiple sysfs *_alarm files +of triggered alarms. The newer method uses multiple sysfs `*_alarm` files (again following the pattern described in sysfs-interface). Since both methods read and write the underlying hardware, they can be used @@ -116,46 +127,54 @@ User mode code requesting values more often will receive cached values. The sysfs-interface is documented in the 'sysfs-interface' file. Only chip-specific options are documented here. -pwm[1-3]_enable - this file controls mode of fan/temperature control for +======================= ======================================================= +pwm[1-3]_enable this file controls mode of fan/temperature control for fan 1-3. Fan/PWM 4-5 only support manual mode. - * 1 Manual mode - * 2 Thermal Cruise mode - * 3 Fan Speed Cruise mode (no further support) -temp[1-3]_target - defines the target temperature for Thermal Cruise mode. + * 1 Manual mode + * 2 Thermal Cruise mode + * 3 Fan Speed Cruise mode (no further support) + +temp[1-3]_target defines the target temperature for Thermal Cruise mode. Unit: millidegree Celsius RW -temp[1-3]_tolerance - temperature tolerance for Thermal Cruise mode. +temp[1-3]_tolerance temperature tolerance for Thermal Cruise mode. Specifies an interval around the target temperature in which the fan speed is not changed. Unit: millidegree Celsius RW +======================= ======================================================= Alarms bitmap vs. beep_mask bitmask ------------------------------------- +----------------------------------- + For legacy code using the alarms and beep_mask files: -in0 (VCORE) : alarms: 0x000001 beep_mask: 0x000001 -in1 (VINR0) : alarms: 0x000002 beep_mask: 0x002000 <== mismatch -in2 (+3.3VIN): alarms: 0x000004 beep_mask: 0x000004 -in3 (5VDD) : alarms: 0x000008 beep_mask: 0x000008 -in4 (+12VIN) : alarms: 0x000100 beep_mask: 0x000100 -in5 (-12VIN) : alarms: 0x000200 beep_mask: 0x000200 -in6 (-5VIN) : alarms: 0x000400 beep_mask: 0x000400 -in7 (VSB) : alarms: 0x080000 beep_mask: 0x010000 <== mismatch -in8 (VBAT) : alarms: 0x100000 beep_mask: 0x020000 <== mismatch -in9 (VINR1) : alarms: 0x004000 beep_mask: 0x004000 -temp1 : alarms: 0x000010 beep_mask: 0x000010 -temp2 : alarms: 0x000020 beep_mask: 0x000020 -temp3 : alarms: 0x002000 beep_mask: 0x000002 <== mismatch -fan1 : alarms: 0x000040 beep_mask: 0x000040 -fan2 : alarms: 0x000080 beep_mask: 0x000080 -fan3 : alarms: 0x000800 beep_mask: 0x000800 -fan4 : alarms: 0x200000 beep_mask: 0x200000 -fan5 : alarms: 0x400000 beep_mask: 0x400000 -tart1 : alarms: 0x010000 beep_mask: 0x040000 <== mismatch -tart2 : alarms: 0x020000 beep_mask: 0x080000 <== mismatch -tart3 : alarms: 0x040000 beep_mask: 0x100000 <== mismatch -case_open : alarms: 0x001000 beep_mask: 0x001000 -global_enable: alarms: -------- beep_mask: 0x800000 (modified via beep_enable) +============= ======== ========= ========================== +Signal Alarms beep_mask Obs +============= ======== ========= ========================== +in0 (VCORE) 0x000001 0x000001 +in1 (VINR0) 0x000002 0x002000 <== mismatch +in2 (+3.3VIN) 0x000004 0x000004 +in3 (5VDD) 0x000008 0x000008 +in4 (+12VIN) 0x000100 0x000100 +in5 (-12VIN) 0x000200 0x000200 +in6 (-5VIN) 0x000400 0x000400 +in7 (VSB) 0x080000 0x010000 <== mismatch +in8 (VBAT) 0x100000 0x020000 <== mismatch +in9 (VINR1) 0x004000 0x004000 +temp1 0x000010 0x000010 +temp2 0x000020 0x000020 +temp3 0x002000 0x000002 <== mismatch +fan1 0x000040 0x000040 +fan2 0x000080 0x000080 +fan3 0x000800 0x000800 +fan4 0x200000 0x200000 +fan5 0x400000 0x400000 +tart1 0x010000 0x040000 <== mismatch +tart2 0x020000 0x080000 <== mismatch +tart3 0x040000 0x100000 <== mismatch +case_open 0x001000 0x001000 +global_enable - 0x800000 (modified via beep_enable) +============= ======== ========= ========================== -- cgit v1.2.3 From 270efaa46c2e354a13d03ce08a5e29596ce50a86 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 17 Apr 2019 06:46:17 -0300 Subject: docs: hwmon: coretemp: convert to ReST format Convert coretemp to ReST format, in order to allow it to be parsed by Sphinx. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Guenter Roeck --- Documentation/hwmon/coretemp | 46 +++++++++++++++++++++++++++++--------------- 1 file changed, 30 insertions(+), 16 deletions(-) (limited to 'Documentation') diff --git a/Documentation/hwmon/coretemp b/Documentation/hwmon/coretemp index fec5a9bf755f..c609329e3bc4 100644 --- a/Documentation/hwmon/coretemp +++ b/Documentation/hwmon/coretemp @@ -3,20 +3,29 @@ Kernel driver coretemp Supported chips: * All Intel Core family + Prefix: 'coretemp' - CPUID: family 0x6, models 0xe (Pentium M DC), 0xf (Core 2 DC 65nm), - 0x16 (Core 2 SC 65nm), 0x17 (Penryn 45nm), - 0x1a (Nehalem), 0x1c (Atom), 0x1e (Lynnfield), - 0x26 (Tunnel Creek Atom), 0x27 (Medfield Atom), - 0x36 (Cedar Trail Atom) - Datasheet: Intel 64 and IA-32 Architectures Software Developer's Manual - Volume 3A: System Programming Guide - http://softwarecommunity.intel.com/Wiki/Mobility/720.htm + + CPUID: family 0x6, models + + - 0xe (Pentium M DC), 0xf (Core 2 DC 65nm), + - 0x16 (Core 2 SC 65nm), 0x17 (Penryn 45nm), + - 0x1a (Nehalem), 0x1c (Atom), 0x1e (Lynnfield), + - 0x26 (Tunnel Creek Atom), 0x27 (Medfield Atom), + - 0x36 (Cedar Trail Atom) + + Datasheet: + + Intel 64 and IA-32 Architectures Software Developer's Manual + Volume 3A: System Programming Guide + + http://softwarecommunity.intel.com/Wiki/Mobility/720.htm Author: Rudolf Marek Description ----------- + This driver permits reading the DTS (Digital Temperature Sensor) embedded inside Intel CPUs. This driver can read both the per-core and per-package temperature using the appropriate sensors. The per-package sensor is new; @@ -35,14 +44,17 @@ may be raised, if the temperature grows enough (more than TjMax) to trigger the Out-Of-Spec bit. Following table summarizes the exported sysfs files: All Sysfs entries are named with their core_id (represented here by 'X'). -tempX_input - Core temperature (in millidegrees Celsius). -tempX_max - All cooling devices should be turned on (on Core2). -tempX_crit - Maximum junction temperature (in millidegrees Celsius). -tempX_crit_alarm - Set when Out-of-spec bit is set, never clears. - Correct CPU operation is no longer guaranteed. -tempX_label - Contains string "Core X", where X is processor - number. For Package temp, this will be "Physical id Y", - where Y is the package number. + +================= ======================================================== +tempX_input Core temperature (in millidegrees Celsius). +tempX_max All cooling devices should be turned on (on Core2). +tempX_crit Maximum junction temperature (in millidegrees Celsius). +tempX_crit_alarm Set when Out-of-spec bit is set, never clears. + Correct CPU operation is no longer guaranteed. +tempX_label Contains string "Core X", where X is processor + number. For Package temp, this will be "Physical id Y", + where Y is the package number. +================= ======================================================== On CPU models which support it, TjMax is read from a model-specific register. On other models, it is set to an arbitrary value based on weak heuristics. @@ -52,6 +64,7 @@ as a module parameter (tjmax). Appendix A. Known TjMax lists (TBD): Some information comes from ark.intel.com +=============== =============================================== ================ Process Processor TjMax(C) 22nm Core i5/i7 Processors @@ -179,3 +192,4 @@ Process Processor TjMax(C) 65nm Celeron Processors T1700/1600 100 560/550/540/530 100 +=============== =============================================== ================ -- cgit v1.2.3 From 9e929c6745da58ab64d2d462ba46b661c03d2060 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 17 Apr 2019 06:46:18 -0300 Subject: docs: hwmon: aspeed-pwm-tacho: convert to ReST format Convert aspeed-pwm-tacho to ReST format, in order to allow it to be parsed by Sphinx. Signed-off-by: Mauro Carvalho Chehab Acked-by: Andrew Jeffery Signed-off-by: Guenter Roeck --- Documentation/hwmon/aspeed-pwm-tacho | 2 ++ 1 file changed, 2 insertions(+) (limited to 'Documentation') diff --git a/Documentation/hwmon/aspeed-pwm-tacho b/Documentation/hwmon/aspeed-pwm-tacho index 7cfb34977460..6dcec845fbc7 100644 --- a/Documentation/hwmon/aspeed-pwm-tacho +++ b/Documentation/hwmon/aspeed-pwm-tacho @@ -15,8 +15,10 @@ controller supports up to 16 tachometer inputs. The driver provides the following sensor accesses in sysfs: +=============== ======= ===================================================== fanX_input ro provide current fan rotation value in RPM as reported by the fan to the device. pwmX rw get or set PWM fan control value. This is an integer value between 0(off) and 255(full speed). +=============== ======= ===================================================== -- cgit v1.2.3 From a4710b72190a5ee1953ffba60cdbdced52a28466 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 17 Apr 2019 06:46:19 -0300 Subject: docs: hwmon: ibmpowernv: convert to ReST format Convert ibmpowernv to ReST format, in order to allow it to be parsed by Sphinx. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Guenter Roeck --- Documentation/hwmon/ibmpowernv | 31 +++++++++++++++++++------------ 1 file changed, 19 insertions(+), 12 deletions(-) (limited to 'Documentation') diff --git a/Documentation/hwmon/ibmpowernv b/Documentation/hwmon/ibmpowernv index 56468258711f..5d642bc3dec0 100644 --- a/Documentation/hwmon/ibmpowernv +++ b/Documentation/hwmon/ibmpowernv @@ -2,6 +2,7 @@ Kernel Driver IBMPOWERNV ======================== Supported systems: + * Any recent IBM P servers based on POWERNV platform Author: Neelesh Gupta @@ -29,10 +30,11 @@ CONFIG_SENSORS_IBMPOWERNV. It can also be built as module 'ibmpowernv'. Sysfs attributes ---------------- +======================= ======================================================= fanX_input Measured RPM value. fanX_min Threshold RPM for alert generation. -fanX_fault 0: No fail condition - 1: Failing fan +fanX_fault - 0: No fail condition + - 1: Failing fan tempX_input Measured ambient temperature. tempX_max Threshold ambient temperature for alert generation. @@ -42,20 +44,22 @@ tempX_enable Enable/disable all temperature sensors belonging to the sub-group. In POWER9, this attribute corresponds to each OCC. Using this attribute each OCC can be asked to disable/enable all of its temperature sensors. - 1: Enable - 0: Disable + + - 1: Enable + - 0: Disable inX_input Measured power supply voltage (millivolt) -inX_fault 0: No fail condition. - 1: Failing power supply. +inX_fault - 0: No fail condition. + - 1: Failing power supply. inX_highest Historical maximum voltage inX_lowest Historical minimum voltage inX_enable Enable/disable all voltage sensors belonging to the sub-group. In POWER9, this attribute corresponds to each OCC. Using this attribute each OCC can be asked to disable/enable all of its voltage sensors. - 1: Enable - 0: Disable + + - 1: Enable + - 0: Disable powerX_input Power consumption (microWatt) powerX_input_highest Historical maximum power @@ -64,8 +68,9 @@ powerX_enable Enable/disable all power sensors belonging to the sub-group. In POWER9, this attribute corresponds to each OCC. Using this attribute each OCC can be asked to disable/enable all of its power sensors. - 1: Enable - 0: Disable + + - 1: Enable + - 0: Disable currX_input Measured current (milliampere) currX_highest Historical maximum current @@ -74,7 +79,9 @@ currX_enable Enable/disable all current sensors belonging to the sub-group. In POWER9, this attribute corresponds to each OCC. Using this attribute each OCC can be asked to disable/enable all of its current sensors. - 1: Enable - 0: Disable + + - 1: Enable + - 0: Disable energyX_input Cumulative energy (microJoule) +======================= ======================================================= -- cgit v1.2.3 From 1288cfe0437e3affee6cccc68e288eb6492c1f8b Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 17 Apr 2019 06:46:20 -0300 Subject: docs: hwmon: asc7621: convert to ReST format Convert asc7621 to ReST format, in order to allow it to be parsed by Sphinx. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Guenter Roeck --- Documentation/hwmon/asc7621 | 146 ++++++++++++++++++++++++++------------------ 1 file changed, 88 insertions(+), 58 deletions(-) (limited to 'Documentation') diff --git a/Documentation/hwmon/asc7621 b/Documentation/hwmon/asc7621 index 7287be7e1f21..b5a9fad0f172 100644 --- a/Documentation/hwmon/asc7621 +++ b/Documentation/hwmon/asc7621 @@ -1,10 +1,15 @@ +===================== Kernel driver asc7621 -================== +===================== Supported chips: + Andigilog aSC7621 and aSC7621a + Prefix: 'asc7621' + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + Datasheet: http://www.fairview5.com/linux/asc7621/asc7621.pdf Author: @@ -73,8 +78,10 @@ Finally, we have added a tach disable function that turns off the tach measurement system for individual tachs in order to save power. That is in register 75h. --- +-------------------------------------------------------------------------- + aSC7621 Product Description +=========================== The aSC7621 has a two wire digital interface compatible with SMBus 2.0. Using a 10-bit ADC, the aSC7621 measures the temperature of two remote diode @@ -102,6 +109,8 @@ System voltages of VCCP, 2.5V, 3.3V, 5.0V, and 12V motherboard power are monitored efficiently with internal scaling resistors. Features +-------- + - Supports PECI interface and monitors internal and remote thermal diodes - 2-wire, SMBus 2.0 compliant, serial interface - 10-bit ADC @@ -110,7 +119,7 @@ Features - Noise filtering of temperature reading for fan speed control - 0.25C digital temperature sensor resolution - 3 PWM fan speed control outputs for 2-, 3- or 4-wire fans and up to 4 fan - tachometer inputs + tachometer inputs - Enhanced measured temperature to Temperature Zone assignment. - Provides high and low PWM frequency ranges - 3 GPIO pins for custom use @@ -123,17 +132,20 @@ Except where noted below, the sysfs entries created by this driver follow the standards defined in "sysfs-interface". temp1_source + = =============================================== 0 (default) peci_legacy = 0, Remote 1 Temperature - peci_legacy = 1, PECI Processor Temperature 0 + peci_legacy = 1, PECI Processor Temperature 0 1 Remote 1 Temperature 2 Remote 2 Temperature 3 Internal Temperature 4 PECI Processor Temperature 0 5 PECI Processor Temperature 1 6 PECI Processor Temperature 2 - 7 PECI Processor Temperature 3 + 7 PECI Processor Temperature 3 + = =============================================== temp2_source + = =============================================== 0 (default) Internal Temperature 1 Remote 1 Temperature 2 Remote 2 Temperature @@ -142,8 +154,10 @@ temp2_source 5 PECI Processor Temperature 1 6 PECI Processor Temperature 2 7 PECI Processor Temperature 3 + = =============================================== temp3_source + = =============================================== 0 (default) Remote 2 Temperature 1 Remote 1 Temperature 2 Remote 2 Temperature @@ -152,10 +166,12 @@ temp3_source 5 PECI Processor Temperature 1 6 PECI Processor Temperature 2 7 PECI Processor Temperature 3 + = =============================================== temp4_source + = =============================================== 0 (default) peci_legacy = 0, PECI Processor Temperature 0 - peci_legacy = 1, Remote 1 Temperature + peci_legacy = 1, Remote 1 Temperature 1 Remote 1 Temperature 2 Remote 2 Temperature 3 Internal Temperature @@ -163,58 +179,65 @@ temp4_source 5 PECI Processor Temperature 1 6 PECI Processor Temperature 2 7 PECI Processor Temperature 3 + = =============================================== -temp[1-4]_smoothing_enable -temp[1-4]_smoothing_time +temp[1-4]_smoothing_enable / temp[1-4]_smoothing_time Smooths spikes in temp readings caused by noise. Valid values in milliseconds are: - 35000 - 17600 - 11800 - 7000 - 4400 - 3000 - 1600 - 800 + + * 35000 + * 17600 + * 11800 + * 7000 + * 4400 + * 3000 + * 1600 + * 800 temp[1-4]_crit When the corresponding zone temperature reaches this value, ALL pwm outputs will got to 100%. -temp[5-8]_input -temp[5-8]_enable +temp[5-8]_input / temp[5-8]_enable The aSC7621 can also read temperatures provided by the processor via the PECI bus. Usually these are "core" temps and are relative to the point where the automatic thermal control circuit starts throttling. This means that these are usually negative numbers. pwm[1-3]_enable + =============== ======================================================== 0 Fan off. 1 Fan on manual control. 2 Fan on automatic control and will run at the minimum pwm - if the temperature for the zone is below the minimum. - 3 Fan on automatic control but will be off if the temperature - for the zone is below the minimum. - 4-254 Ignored. + if the temperature for the zone is below the minimum. + 3 Fan on automatic control but will be off if the + temperature for the zone is below the minimum. + 4-254 Ignored. 255 Fan on full. + =============== ======================================================== pwm[1-3]_auto_channels Bitmap as described in sysctl-interface with the following exceptions... + Only the following combination of zones (and their corresponding masks) are valid: - 1 - 2 - 3 - 2,3 - 1,2,3 - 4 - 1,2,3,4 - Special values: - 0 Disabled. - 16 Fan on manual control. - 31 Fan on full. + * 1 + * 2 + * 3 + * 2,3 + * 1,2,3 + * 4 + * 1,2,3,4 + + * Special values: + + == ====================== + 0 Disabled. + 16 Fan on manual control. + 31 Fan on full. + == ====================== pwm[1-3]_invert @@ -226,22 +249,22 @@ pwm[1-3]_freq PWM frequency in Hz Valid values in Hz are: - 10 - 15 - 23 - 30 (default) - 38 - 47 - 62 - 94 - 23000 - 24000 - 25000 - 26000 - 27000 - 28000 - 29000 - 30000 + * 10 + * 15 + * 23 + * 30 (default) + * 38 + * 47 + * 62 + * 94 + * 23000 + * 24000 + * 25000 + * 26000 + * 27000 + * 28000 + * 29000 + * 30000 Setting any other value will be ignored. @@ -251,17 +274,17 @@ peci_enable peci_avg Input filter average time. - 0 0 Sec. (no Smoothing) (default) - 1 0.25 Sec. - 2 0.5 Sec. - 3 1.0 Sec. - 4 2.0 Sec. - 5 4.0 Sec. - 6 8.0 Sec. - 7 0.0 Sec. + * 0 0 Sec. (no Smoothing) (default) + * 1 0.25 Sec. + * 2 0.5 Sec. + * 3 1.0 Sec. + * 4 2.0 Sec. + * 5 4.0 Sec. + * 6 8.0 Sec. + * 7 0.0 Sec. peci_legacy - + = ============================================ 0 Standard Mode (default) Remote Diode 1 reading is associated with Temperature Zone 1, PECI is associated with @@ -270,10 +293,12 @@ peci_legacy 1 Legacy Mode PECI is associated with Temperature Zone 1, Remote Diode 1 is associated with Zone 4 + = ============================================ peci_diode Diode filter + = ==================== 0 0.25 Sec. 1 1.1 Sec. 2 2.4 Sec. (default) @@ -282,15 +307,20 @@ peci_diode 5 6.8 Sec. 6 10.2 Sec. 7 16.4 Sec. + = ==================== peci_4domain Four domain enable + = =============================================== 0 1 or 2 Domains for enabled processors (default) 1 3 or 4 Domains for enabled processors + = =============================================== peci_domain Domain + = ================================================== 0 Processor contains a single domain (0) (default) 1 Processor contains two domains (0,1) + = ================================================== -- cgit v1.2.3 From 33ffc74ffa3d7ae9946524dfeaea6f4b251909a5 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 17 Apr 2019 06:46:21 -0300 Subject: docs: hwmon: ads1015: convert to ReST format Convert ads1015 to ReST format, in order to allow it to be parsed by Sphinx. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Guenter Roeck --- Documentation/hwmon/ads1015 | 74 +++++++++++++++++++++++++++------------------ 1 file changed, 44 insertions(+), 30 deletions(-) (limited to 'Documentation') diff --git a/Documentation/hwmon/ads1015 b/Documentation/hwmon/ads1015 index 02d2a459385f..e0951c4e57bb 100644 --- a/Documentation/hwmon/ads1015 +++ b/Documentation/hwmon/ads1015 @@ -2,17 +2,25 @@ Kernel driver ads1015 ===================== Supported chips: + * Texas Instruments ADS1015 + Prefix: 'ads1015' - Datasheet: Publicly available at the Texas Instruments website : - http://focus.ti.com/lit/ds/symlink/ads1015.pdf + + Datasheet: Publicly available at the Texas Instruments website: + + http://focus.ti.com/lit/ds/symlink/ads1015.pdf + * Texas Instruments ADS1115 + Prefix: 'ads1115' - Datasheet: Publicly available at the Texas Instruments website : - http://focus.ti.com/lit/ds/symlink/ads1115.pdf + + Datasheet: Publicly available at the Texas Instruments website: + + http://focus.ti.com/lit/ds/symlink/ads1115.pdf Authors: - Dirk Eibach, Guntermann & Drunck GmbH + Dirk Eibach, Guntermann & Drunck GmbH Description ----------- @@ -24,14 +32,15 @@ This device is a 12/16-bit A-D converter with 4 inputs. The inputs can be used single ended or in certain differential combinations. The inputs can be made available by 8 sysfs input files in0_input - in7_input: -in0: Voltage over AIN0 and AIN1. -in1: Voltage over AIN0 and AIN3. -in2: Voltage over AIN1 and AIN3. -in3: Voltage over AIN2 and AIN3. -in4: Voltage over AIN0 and GND. -in5: Voltage over AIN1 and GND. -in6: Voltage over AIN2 and GND. -in7: Voltage over AIN3 and GND. + + - in0: Voltage over AIN0 and AIN1. + - in1: Voltage over AIN0 and AIN3. + - in2: Voltage over AIN1 and AIN3. + - in3: Voltage over AIN2 and AIN3. + - in4: Voltage over AIN0 and GND. + - in5: Voltage over AIN1 and GND. + - in6: Voltage over AIN2 and GND. + - in7: Voltage over AIN3 and GND. Which inputs are available can be configured using platform data or devicetree. @@ -42,29 +51,34 @@ Platform Data In linux/platform_data/ads1015.h platform data is defined, channel_data contains configuration data for the used input combinations: + - pga is the programmable gain amplifier (values are full scale) - 0: +/- 6.144 V - 1: +/- 4.096 V - 2: +/- 2.048 V - 3: +/- 1.024 V - 4: +/- 0.512 V - 5: +/- 0.256 V + + - 0: +/- 6.144 V + - 1: +/- 4.096 V + - 2: +/- 2.048 V + - 3: +/- 1.024 V + - 4: +/- 0.512 V + - 5: +/- 0.256 V + - data_rate in samples per second - 0: 128 - 1: 250 - 2: 490 - 3: 920 - 4: 1600 - 5: 2400 - 6: 3300 - -Example: -struct ads1015_platform_data data = { + + - 0: 128 + - 1: 250 + - 2: 490 + - 3: 920 + - 4: 1600 + - 5: 2400 + - 6: 3300 + +Example:: + + struct ads1015_platform_data data = { .channel_data = { [2] = { .enabled = true, .pga = 1, .data_rate = 0 }, [4] = { .enabled = true, .pga = 4, .data_rate = 5 }, } -}; + }; In this case only in2_input (FS +/- 4.096 V, 128 SPS) and in4_input (FS +/- 0.512 V, 2400 SPS) would be created. -- cgit v1.2.3 From cdc39b091b9d756d62edb74d23a62bd6dba0453d Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 17 Apr 2019 06:46:22 -0300 Subject: docs: hwmon: dme1737, vt1211: convert to ReST format Convert dme1737 and vt1211 to ReST format, in order to allow them to be parsed by Sphinx. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Guenter Roeck --- Documentation/hwmon/dme1737 | 88 +++++++++++++++++++++++++++++++-------------- Documentation/hwmon/vt1211 | 84 ++++++++++++++++++++++++++----------------- 2 files changed, 114 insertions(+), 58 deletions(-) (limited to 'Documentation') diff --git a/Documentation/hwmon/dme1737 b/Documentation/hwmon/dme1737 index 4d2935145a1c..82fcbc6b2b43 100644 --- a/Documentation/hwmon/dme1737 +++ b/Documentation/hwmon/dme1737 @@ -2,21 +2,37 @@ Kernel driver dme1737 ===================== Supported chips: + * SMSC DME1737 and compatibles (like Asus A8000) + Prefix: 'dme1737' + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + Datasheet: Provided by SMSC upon request and under NDA + * SMSC SCH3112, SCH3114, SCH3116 + Prefix: 'sch311x' + Addresses scanned: none, address read from Super-I/O config space + Datasheet: Available on the Internet + * SMSC SCH5027 + Prefix: 'sch5027' + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + Datasheet: Provided by SMSC upon request and under NDA + * SMSC SCH5127 + Prefix: 'sch5127' + Addresses scanned: none, address read from Super-I/O config space + Datasheet: Provided by SMSC upon request and under NDA Authors: @@ -26,11 +42,14 @@ Authors: Module Parameters ----------------- -* force_start: bool Enables the monitoring of voltage, fan and temp inputs +* force_start: bool + Enables the monitoring of voltage, fan and temp inputs and PWM output control functions. Using this parameter shouldn't be required since the BIOS usually takes care of this. -* probe_all_addr: bool Include non-standard LPC addresses 0x162e and 0x164e + +* probe_all_addr: bool + Include non-standard LPC addresses 0x162e and 0x164e when probing for ISA devices. This is required for the following boards: - VIA EPIA SN18000 @@ -70,7 +89,8 @@ scaling resistors. The values returned by the driver therefore reflect true millivolts and don't need scaling. The voltage inputs are mapped as follows (the last column indicates the input ranges): -DME1737, A8000: +DME1737, A8000:: + in0: +5VTR (+5V standby) 0V - 6.64V in1: Vccp (processor core) 0V - 3V in2: VCC (internal +3.3V) 0V - 4.38V @@ -79,7 +99,8 @@ DME1737, A8000: in5: VTR (+3.3V standby) 0V - 4.38V in6: Vbat (+3.0V) 0V - 4.38V -SCH311x: +SCH311x:: + in0: +2.5V 0V - 3.32V in1: Vccp (processor core) 0V - 2V in2: VCC (internal +3.3V) 0V - 4.38V @@ -88,7 +109,8 @@ SCH311x: in5: VTR (+3.3V standby) 0V - 4.38V in6: Vbat (+3.0V) 0V - 4.38V -SCH5027: +SCH5027:: + in0: +5VTR (+5V standby) 0V - 6.64V in1: Vccp (processor core) 0V - 3V in2: VCC (internal +3.3V) 0V - 4.38V @@ -97,7 +119,8 @@ SCH5027: in5: VTR (+3.3V standby) 0V - 4.38V in6: Vbat (+3.0V) 0V - 4.38V -SCH5127: +SCH5127:: + in0: +2.5 0V - 3.32V in1: Vccp (processor core) 0V - 3V in2: VCC (internal +3.3V) 0V - 4.38V @@ -119,7 +142,7 @@ Celsius. The chip also features offsets for all 3 temperature inputs which - when programmed - get added to the input readings. The chip does all the scaling by itself and the driver therefore reports true temperatures that don't need any user-space adjustments. The temperature inputs are mapped as follows -(the last column indicates the input ranges): +(the last column indicates the input ranges):: temp1: Remote diode 1 (3904 type) temperature -127C - +127C temp2: DME1737 internal temperature -127C - +127C @@ -171,6 +194,7 @@ pwm[1-3]_auto_pwm_min, respectively. The thermal thresholds of the zones are programmed via zone[1-3]_auto_point[1-3]_temp and zone[1-3]_auto_point1_temp_hyst: + =============================== ======================================= pwm[1-3]_auto_point2_pwm full-speed duty-cycle (255, i.e., 100%) pwm[1-3]_auto_point1_pwm low-speed duty-cycle pwm[1-3]_auto_pwm_min min-speed duty-cycle @@ -179,6 +203,7 @@ zone[1-3]_auto_point1_temp_hyst: zone[1-3]_auto_point2_temp full-speed temp zone[1-3]_auto_point1_temp low-speed temp zone[1-3]_auto_point1_temp_hyst min-speed temp + =============================== ======================================= The chip adjusts the output duty-cycle linearly in the range of auto_point1_pwm to auto_point2_pwm if the temperature of the associated zone is between @@ -192,17 +217,21 @@ all PWM outputs are set to 100% duty-cycle. Following is another representation of how the chip sets the output duty-cycle based on the temperature of the associated thermal zone: - Duty-Cycle Duty-Cycle - Temperature Rising Temp Falling Temp - ----------- ----------- ------------ + =============== =============== ================= + Temperature Duty-Cycle Duty-Cycle + Rising Temp Falling Temp + =============== =============== ================= full-speed full-speed full-speed - < linearly adjusted duty-cycle > + - < linearly - + adjusted + duty-cycle > low-speed low-speed low-speed - min-speed low-speed + - min-speed low-speed min-speed min-speed min-speed - min-speed min-speed + - min-speed min-speed + =============== =============== ================= Sysfs Attributes @@ -211,8 +240,9 @@ Sysfs Attributes Following is a list of all sysfs attributes that the driver provides, their permissions and a short description: +=============================== ======= ======================================= Name Perm Description ----- ---- ----------- +=============================== ======= ======================================= cpu0_vid RO CPU core reference voltage in millivolts. vrm RW Voltage regulator module version @@ -242,9 +272,10 @@ temp[1-3]_fault RO Temp input fault. Returns 1 if the chip zone[1-3]_auto_channels_temp RO Temperature zone to temperature input mapping. This attribute is a bitfield and supports the following values: - 1: temp1 - 2: temp2 - 4: temp3 + + - 1: temp1 + - 2: temp2 + - 4: temp3 zone[1-3]_auto_point1_temp_hyst RW Auto PWM temp point1 hysteresis. The output of the corresponding PWM is set to the pwm_auto_min value if the temp @@ -275,9 +306,10 @@ pmw[1-3,5-6] RO/RW Duty-cycle of PWM output. Supported manual mode. pwm[1-3]_enable RW Enable of PWM outputs 1-3. Supported values are: - 0: turned off (output @ 100%) - 1: manual mode - 2: automatic mode + + - 0: turned off (output @ 100%) + - 1: manual mode + - 2: automatic mode pwm[5-6]_enable RO Enable of PWM outputs 5-6. Always returns 1 since these 2 outputs are hard-wired to manual mode. @@ -294,11 +326,12 @@ pmw[1-3]_ramp_rate RW Ramp rate of PWM output. Determines how pwm[1-3]_auto_channels_zone RW PWM output to temperature zone mapping. This attribute is a bitfield and supports the following values: - 1: zone1 - 2: zone2 - 4: zone3 - 6: highest of zone[2-3] - 7: highest of zone[1-3] + + - 1: zone1 + - 2: zone2 + - 4: zone3 + - 6: highest of zone[2-3] + - 7: highest of zone[1-3] pwm[1-3]_auto_pwm_min RW Auto PWM min pwm. Minimum PWM duty- cycle. Supported values are 0 or auto_point1_pwm. @@ -307,12 +340,14 @@ pwm[1-3]_auto_point1_pwm RW Auto PWM pwm point. Auto_point1 is the pwm[1-3]_auto_point2_pwm RO Auto PWM pwm point. Auto_point2 is the full-speed duty-cycle which is hard- wired to 255 (100% duty-cycle). +=============================== ======= ======================================= Chip Differences ---------------- +======================= ======= ======= ======= ======= Feature dme1737 sch311x sch5027 sch5127 -------------------------------------------------------- +======================= ======= ======= ======= ======= temp[1-3]_offset yes yes vid yes zone3 yes yes yes @@ -326,3 +361,4 @@ pwm5 opt opt fan6 opt opt pwm6 opt opt in7 yes +======================= ======= ======= ======= ======= diff --git a/Documentation/hwmon/vt1211 b/Documentation/hwmon/vt1211 index 77fa633b97a8..ddbcde7dd642 100644 --- a/Documentation/hwmon/vt1211 +++ b/Documentation/hwmon/vt1211 @@ -2,9 +2,13 @@ Kernel driver vt1211 ==================== Supported chips: + * VIA VT1211 + Prefix: 'vt1211' + Addresses scanned: none, address read from Super-I/O config space + Datasheet: Provided by VIA upon request and under NDA Authors: Juerg Haefliger @@ -19,14 +23,17 @@ technical support. Module Parameters ----------------- -* uch_config: int Override the BIOS default universal channel (UCH) + +* uch_config: int + Override the BIOS default universal channel (UCH) configuration for channels 1-5. Legal values are in the range of 0-31. Bit 0 maps to UCH1, bit 1 maps to UCH2 and so on. Setting a bit to 1 enables the thermal input of that particular UCH and setting a bit to 0 enables the voltage input. -* int_mode: int Override the BIOS default temperature interrupt mode. +* int_mode: int + Override the BIOS default temperature interrupt mode. The only possible value is 0 which forces interrupt mode 0. In this mode, any pending interrupt is cleared when the status register is read but is regenerated as @@ -55,8 +62,9 @@ connected to the PWM outputs of the VT1211 :-(). The following table shows the relationship between the vt1211 inputs and the sysfs nodes. +=============== ============== =========== ================================ Sensor Voltage Mode Temp Mode Default Use (from the datasheet) ------- ------------ --------- -------------------------------- +=============== ============== =========== ================================ Reading 1 temp1 Intel thermal diode Reading 3 temp2 Internal thermal diode UCH1/Reading2 in0 temp3 NTC type thermistor @@ -65,6 +73,7 @@ UCH3 in2 temp5 VccP (processor core) UCH4 in3 temp6 +5V UCH5 in4 temp7 +12V +3.3V in5 Internal VCC (+3.3V) +=============== ============== =========== ================================ Voltage Monitoring @@ -82,19 +91,22 @@ follows. And this is of course totally dependent on the actual board implementation :-) You will have to find documentation for your own motherboard and edit sensors.conf accordingly. - Expected +============= ====== ====== ========= ============ + Expected Voltage R1 R2 Divider Raw Value ------------------------------------------------ +============= ====== ====== ========= ============ +2.5V 2K 10K 1.2 2083 mV -VccP --- --- 1.0 1400 mV (1) +VccP --- --- 1.0 1400 mV [1]_ +5V 14K 10K 2.4 2083 mV +12V 47K 10K 5.7 2105 mV -+3.3V (int) 2K 3.4K 1.588 3300 mV (2) ++3.3V (int) 2K 3.4K 1.588 3300 mV [2]_ +3.3V (ext) 6.8K 10K 1.68 1964 mV +============= ====== ====== ========= ============ + +.. [1] Depending on the CPU (1.4V is for a VIA C3 Nehemiah). -(1) Depending on the CPU (1.4V is for a VIA C3 Nehemiah). -(2) R1 and R2 for 3.3V (int) are internal to the VT1211 chip and the driver - performs the scaling and returns the properly scaled voltage value. +.. [2] R1 and R2 for 3.3V (int) are internal to the VT1211 chip and the driver + performs the scaling and returns the properly scaled voltage value. Each measured voltage has an associated low and high limit which triggers an alarm when crossed. @@ -124,35 +136,37 @@ compute temp1 (@-Offset)/Gain, (@*Gain)+Offset According to the VIA VT1211 BIOS porting guide, the following gain and offset values should be used: +=============== ======== =========== Diode Type Offset Gain ----------- ------ ---- +=============== ======== =========== Intel CPU 88.638 0.9528 - 65.000 0.9686 *) + 65.000 0.9686 [3]_ VIA C3 Ezra 83.869 0.9528 VIA C3 Ezra-T 73.869 0.9528 +=============== ======== =========== -*) This is the formula from the lm_sensors 2.10.0 sensors.conf file. I don't -know where it comes from or how it was derived, it's just listed here for -completeness. +.. [3] This is the formula from the lm_sensors 2.10.0 sensors.conf file. I don't + know where it comes from or how it was derived, it's just listed here for + completeness. Temp3-temp7 support NTC thermistors. For these channels, the driver returns the voltages as seen at the individual pins of UCH1-UCH5. The voltage at the pin (Vpin) is formed by a voltage divider made of the thermistor (Rth) and a -scaling resistor (Rs): +scaling resistor (Rs):: -Vpin = 2200 * Rth / (Rs + Rth) (2200 is the ADC max limit of 2200 mV) + Vpin = 2200 * Rth / (Rs + Rth) (2200 is the ADC max limit of 2200 mV) The equation for the thermistor is as follows (google it if you want to know -more about it): +more about it):: -Rth = Ro * exp(B * (1 / T - 1 / To)) (To is 298.15K (25C) and Ro is the - nominal resistance at 25C) + Rth = Ro * exp(B * (1 / T - 1 / To)) (To is 298.15K (25C) and Ro is the + nominal resistance at 25C) Mingling the above two equations and assuming Rs = Ro and B = 3435 yields the -following formula for sensors.conf: +following formula for sensors.conf:: -compute tempx 1 / (1 / 298.15 - (` (2200 / @ - 1)) / 3435) - 273.15, - 2200 / (1 + (^ (3435 / 298.15 - 3435 / (273.15 + @)))) + compute tempx 1 / (1 / 298.15 - (` (2200 / @ - 1)) / 3435) - 273.15, + 2200 / (1 + (^ (3435 / 298.15 - 3435 / (273.15 + @)))) Fan Speed Control @@ -176,31 +190,37 @@ registers in the VT1211 and programming one set is sufficient (actually only the first set pwm1_auto_point[1-4]_temp is writable, the second set is read-only). +========================== ========================================= PWM Auto Point PWM Output Duty-Cycle ------------------------------------------------- +========================== ========================================= pwm[1-2]_auto_point4_pwm full speed duty-cycle (hard-wired to 255) pwm[1-2]_auto_point3_pwm high speed duty-cycle pwm[1-2]_auto_point2_pwm low speed duty-cycle pwm[1-2]_auto_point1_pwm off duty-cycle (hard-wired to 0) +========================== ========================================= +========================== ================= Temp Auto Point Thermal Threshold ---------------------------------------------- +========================== ================= pwm[1-2]_auto_point4_temp full speed temp pwm[1-2]_auto_point3_temp high speed temp pwm[1-2]_auto_point2_temp low speed temp pwm[1-2]_auto_point1_temp off temp +========================== ================= Long story short, the controller implements the following algorithm to set the PWM output duty-cycle based on the input temperature: -Thermal Threshold Output Duty-Cycle - (Rising Temp) (Falling Temp) ----------------------------------------------------------- - full speed duty-cycle full speed duty-cycle +=================== ======================= ======================== +Thermal Threshold Output Duty-Cycle Output Duty-Cycle + (Rising Temp) (Falling Temp) +=================== ======================= ======================== +- full speed duty-cycle full speed duty-cycle full speed temp - high speed duty-cycle full speed duty-cycle +- high speed duty-cycle full speed duty-cycle high speed temp - low speed duty-cycle high speed duty-cycle +- low speed duty-cycle high speed duty-cycle low speed temp - off duty-cycle low speed duty-cycle +- off duty-cycle low speed duty-cycle off temp +=================== ======================= ======================== -- cgit v1.2.3 From 4f1158b355a888bc612b8f37d2f9aad7032e55a3 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 17 Apr 2019 06:46:23 -0300 Subject: docs: hwmon: wm831x, wm8350: convert to ReST format Convert wm831x and wm8350 to ReST format, in order to allow them to be parsed by Sphinx. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Guenter Roeck --- Documentation/hwmon/wm831x | 9 ++++++--- Documentation/hwmon/wm8350 | 10 +++++++--- 2 files changed, 13 insertions(+), 6 deletions(-) (limited to 'Documentation') diff --git a/Documentation/hwmon/wm831x b/Documentation/hwmon/wm831x index 11446757c8c8..c56fb35a2fb3 100644 --- a/Documentation/hwmon/wm831x +++ b/Documentation/hwmon/wm831x @@ -3,11 +3,14 @@ Kernel driver wm831x-hwmon Supported chips: * Wolfson Microelectronics WM831x PMICs + Prefix: 'wm831x' + Datasheet: - http://www.wolfsonmicro.com/products/WM8310 - http://www.wolfsonmicro.com/products/WM8311 - http://www.wolfsonmicro.com/products/WM8312 + + - http://www.wolfsonmicro.com/products/WM8310 + - http://www.wolfsonmicro.com/products/WM8311 + - http://www.wolfsonmicro.com/products/WM8312 Authors: Mark Brown diff --git a/Documentation/hwmon/wm8350 b/Documentation/hwmon/wm8350 index 98f923bd2e92..cec044ca5900 100644 --- a/Documentation/hwmon/wm8350 +++ b/Documentation/hwmon/wm8350 @@ -2,12 +2,16 @@ Kernel driver wm8350-hwmon ========================== Supported chips: + * Wolfson Microelectronics WM835x PMICs + Prefix: 'wm8350' + Datasheet: - http://www.wolfsonmicro.com/products/WM8350 - http://www.wolfsonmicro.com/products/WM8351 - http://www.wolfsonmicro.com/products/WM8352 + + - http://www.wolfsonmicro.com/products/WM8350 + - http://www.wolfsonmicro.com/products/WM8351 + - http://www.wolfsonmicro.com/products/WM8352 Authors: Mark Brown -- cgit v1.2.3 From 08fae079ea750eec86a5ca7844c0a0a914e70fc2 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 17 Apr 2019 06:46:24 -0300 Subject: docs: hwmon: da9052, da9055: convert to ReST format Convert da9052 and da9055 to ReST format, in order to allow them to be parsed by Sphinx. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Guenter Roeck --- Documentation/hwmon/da9052 | 41 +++++++++++++++++++++++++++++------------ Documentation/hwmon/da9055 | 20 +++++++++++++++----- 2 files changed, 44 insertions(+), 17 deletions(-) (limited to 'Documentation') diff --git a/Documentation/hwmon/da9052 b/Documentation/hwmon/da9052 index 5bc51346b689..c1c0f1f08904 100644 --- a/Documentation/hwmon/da9052 +++ b/Documentation/hwmon/da9052 @@ -1,6 +1,12 @@ +Kernel driver da9052 +==================== + Supported chips: + * Dialog Semiconductors DA9052-BC and DA9053-AA/Bx PMICs + Prefix: 'da9052' + Datasheet: Datasheet is not publicly available. Authors: David Dajun Chen @@ -15,17 +21,20 @@ different inputs. The track and hold circuit ensures stable input voltages at the input of the ADC during the conversion. The ADC is used to measure the following inputs: -Channel 0: VDDOUT - measurement of the system voltage -Channel 1: ICH - internal battery charger current measurement -Channel 2: TBAT - output from the battery NTC -Channel 3: VBAT - measurement of the battery voltage -Channel 4: ADC_IN4 - high impedance input (0 - 2.5V) -Channel 5: ADC_IN5 - high impedance input (0 - 2.5V) -Channel 6: ADC_IN6 - high impedance input (0 - 2.5V) -Channel 7: XY - TSI interface to measure the X and Y voltage of the touch - screen resistive potentiometers -Channel 8: Internal Tjunc. - sense (internal temp. sensor) -Channel 9: VBBAT - measurement of the backup battery voltage + +========= =================================================================== +Channel 0 VDDOUT - measurement of the system voltage +Channel 1 ICH - internal battery charger current measurement +Channel 2 TBAT - output from the battery NTC +Channel 3 VBAT - measurement of the battery voltage +Channel 4 ADC_IN4 - high impedance input (0 - 2.5V) +Channel 5 ADC_IN5 - high impedance input (0 - 2.5V) +Channel 6 ADC_IN6 - high impedance input (0 - 2.5V) +Channel 7 XY - TSI interface to measure the X and Y voltage of the touch + screen resistive potentiometers +Channel 8 Internal Tjunc. - sense (internal temp. sensor) +Channel 9 VBBAT - measurement of the backup battery voltage +========= =================================================================== By using sysfs attributes we can measure the system voltage VDDOUT, the battery charging current ICH, battery temperature TBAT, battery junction temperature @@ -37,12 +46,15 @@ Voltage Monitoring Voltages are sampled by a 10 bit ADC. The battery voltage is calculated as: + Milli volt = ((ADC value * 1000) / 512) + 2500 The backup battery voltage is calculated as: + Milli volt = (ADC value * 2500) / 512; The voltages on ADC channels 4, 5 and 6 are calculated as: + Milli volt = (ADC value * 2500) / 1023 Temperature Monitoring @@ -52,10 +64,15 @@ Temperatures are sampled by a 10 bit ADC. Junction and battery temperatures are monitored by the ADC channels. The junction temperature is calculated: + Degrees celsius = 1.708 * (TJUNC_RES - T_OFFSET) - 108.8 + The junction temperature attribute is supported by the driver. The battery temperature is calculated: - Degree Celsius = 1 / (t1 + 1/298)- 273 + + Degree Celsius = 1 / (t1 + 1/298) - 273 + where t1 = (1/B)* ln(( ADCval * 2.5)/(R25*ITBAT*255)) + Default values of R25, B, ITBAT are 10e3, 3380 and 50e-6 respectively. diff --git a/Documentation/hwmon/da9055 b/Documentation/hwmon/da9055 index 855c3f536e00..beae271a3312 100644 --- a/Documentation/hwmon/da9055 +++ b/Documentation/hwmon/da9055 @@ -1,6 +1,11 @@ +Kernel driver da9055 +==================== + Supported chips: * Dialog Semiconductors DA9055 PMIC + Prefix: 'da9055' + Datasheet: Datasheet is not publicly available. Authors: David Dajun Chen @@ -15,11 +20,12 @@ different inputs. The track and hold circuit ensures stable input voltages at the input of the ADC during the conversion. The ADC is used to measure the following inputs: -Channel 0: VDDOUT - measurement of the system voltage -Channel 1: ADC_IN1 - high impedance input (0 - 2.5V) -Channel 2: ADC_IN2 - high impedance input (0 - 2.5V) -Channel 3: ADC_IN3 - high impedance input (0 - 2.5V) -Channel 4: Internal Tjunc. - sense (internal temp. sensor) + +- Channel 0: VDDOUT - measurement of the system voltage +- Channel 1: ADC_IN1 - high impedance input (0 - 2.5V) +- Channel 2: ADC_IN2 - high impedance input (0 - 2.5V) +- Channel 3: ADC_IN3 - high impedance input (0 - 2.5V) +- Channel 4: Internal Tjunc. - sense (internal temp. sensor) By using sysfs attributes we can measure the system voltage VDDOUT, chip junction temperature and auxiliary channels voltages. @@ -31,9 +37,11 @@ Voltages are sampled in a AUTO mode it can be manually sampled too and results are stored in a 10 bit ADC. The system voltage is calculated as: + Milli volt = ((ADC value * 1000) / 85) + 2500 The voltages on ADC channels 1, 2 and 3 are calculated as: + Milli volt = (ADC value * 1000) / 102 Temperature Monitoring @@ -43,5 +51,7 @@ Temperatures are sampled by a 10 bit ADC. Junction temperatures are monitored by the ADC channels. The junction temperature is calculated: + Degrees celsius = -0.4084 * (ADC_RES - T_OFFSET) + 307.6332 + The junction temperature attribute is supported by the driver. -- cgit v1.2.3 From 0d9256262f92d26ebd29ee469bd07761a9835739 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 17 Apr 2019 06:46:25 -0300 Subject: docs: hwmon: k8temp, w83793: convert to ReST format Convert k8temp and w83793 to ReST format, in order to allow them to be parsed by Sphinx. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Guenter Roeck --- Documentation/hwmon/k8temp | 17 ++++-- Documentation/hwmon/w83793 | 129 ++++++++++++++++++++++++--------------------- 2 files changed, 80 insertions(+), 66 deletions(-) (limited to 'Documentation') diff --git a/Documentation/hwmon/k8temp b/Documentation/hwmon/k8temp index 716dc24c7237..72da12aa17e5 100644 --- a/Documentation/hwmon/k8temp +++ b/Documentation/hwmon/k8temp @@ -2,12 +2,17 @@ Kernel driver k8temp ==================== Supported chips: + * AMD Athlon64/FX or Opteron CPUs + Prefix: 'k8temp' + Addresses scanned: PCI space + Datasheet: http://support.amd.com/us/Processor_TechDocs/32559.pdf Author: Rudolf Marek + Contact: Rudolf Marek Description @@ -27,10 +32,12 @@ implemented sensors. Mapping of /sys files is as follows: -temp1_input - temperature of Core 0 and "place" 0 -temp2_input - temperature of Core 0 and "place" 1 -temp3_input - temperature of Core 1 and "place" 0 -temp4_input - temperature of Core 1 and "place" 1 +============= =================================== +temp1_input temperature of Core 0 and "place" 0 +temp2_input temperature of Core 0 and "place" 1 +temp3_input temperature of Core 1 and "place" 0 +temp4_input temperature of Core 1 and "place" 1 +============= =================================== Temperatures are measured in degrees Celsius and measurement resolution is 1 degree C. It is expected that future CPU will have better resolution. The @@ -48,7 +55,7 @@ computed temperature called TControl, which must be lower than TControlMax. The relationship is following: -temp1_input - TjOffset*2 < TControlMax, + temp1_input - TjOffset*2 < TControlMax, TjOffset is not yet exported by the driver, TControlMax is usually 70 degrees C. The rule of the thumb -> CPU temperature should not cross diff --git a/Documentation/hwmon/w83793 b/Documentation/hwmon/w83793 index 6cc5f639b721..83bb40c48645 100644 --- a/Documentation/hwmon/w83793 +++ b/Documentation/hwmon/w83793 @@ -2,29 +2,34 @@ Kernel driver w83793 ==================== Supported chips: + * Winbond W83793G/W83793R + Prefix: 'w83793' + Addresses scanned: I2C 0x2c - 0x2f + Datasheet: Still not published Authors: - Yuan Mu (Winbond Electronics) - Rudolf Marek + - Yuan Mu (Winbond Electronics) + - Rudolf Marek Module parameters ----------------- * reset int - (default 0) - This parameter is not recommended, it will lose motherboard specific - settings. Use 'reset=1' to reset the chip when loading this module. + (default 0) + + This parameter is not recommended, it will lose motherboard specific + settings. Use 'reset=1' to reset the chip when loading this module. * force_subclients=bus,caddr,saddr1,saddr2 - This is used to force the i2c addresses for subclients of - a certain chip. Typical usage is `force_subclients=0,0x2f,0x4a,0x4b' - to force the subclients of chip 0x2f on bus 0 to i2c addresses - 0x4a and 0x4b. + This is used to force the i2c addresses for subclients of + a certain chip. Typical usage is `force_subclients=0,0x2f,0x4a,0x4b` + to force the subclients of chip 0x2f on bus 0 to i2c addresses + 0x4a and 0x4b. Description @@ -33,70 +38,72 @@ Description This driver implements support for Winbond W83793G/W83793R chips. * Exported features - This driver exports 10 voltage sensors, up to 12 fan tachometer inputs, - 6 remote temperatures, up to 8 sets of PWM fan controls, SmartFan - (automatic fan speed control) on all temperature/PWM combinations, 2 - sets of 6-pin CPU VID input. + This driver exports 10 voltage sensors, up to 12 fan tachometer inputs, + 6 remote temperatures, up to 8 sets of PWM fan controls, SmartFan + (automatic fan speed control) on all temperature/PWM combinations, 2 + sets of 6-pin CPU VID input. * Sensor resolutions - If your motherboard maker used the reference design, the resolution of - voltage0-2 is 2mV, resolution of voltage3/4/5 is 16mV, 8mV for voltage6, - 24mV for voltage7/8. Temp1-4 have a 0.25 degree Celsius resolution, - temp5-6 have a 1 degree Celsiis resolution. + If your motherboard maker used the reference design, the resolution of + voltage0-2 is 2mV, resolution of voltage3/4/5 is 16mV, 8mV for voltage6, + 24mV for voltage7/8. Temp1-4 have a 0.25 degree Celsius resolution, + temp5-6 have a 1 degree Celsiis resolution. * Temperature sensor types - Temp1-4 have 2 possible types. It can be read from (and written to) - temp[1-4]_type. - - If the value is 3, it starts monitoring using a remote termal diode - (default). - - If the value is 6, it starts monitoring using the temperature sensor - in Intel CPU and get result by PECI. - Temp5-6 can be connected to external thermistors (value of - temp[5-6]_type is 4). + Temp1-4 have 2 possible types. It can be read from (and written to) + temp[1-4]_type. + + - If the value is 3, it starts monitoring using a remote termal diode + (default). + - If the value is 6, it starts monitoring using the temperature sensor + in Intel CPU and get result by PECI. + + Temp5-6 can be connected to external thermistors (value of + temp[5-6]_type is 4). * Alarm mechanism - For voltage sensors, an alarm triggers if the measured value is below - the low voltage limit or over the high voltage limit. - For temperature sensors, an alarm triggers if the measured value goes - above the high temperature limit, and wears off only after the measured - value drops below the hysteresis value. - For fan sensors, an alarm triggers if the measured value is below the - low speed limit. + For voltage sensors, an alarm triggers if the measured value is below + the low voltage limit or over the high voltage limit. + For temperature sensors, an alarm triggers if the measured value goes + above the high temperature limit, and wears off only after the measured + value drops below the hysteresis value. + For fan sensors, an alarm triggers if the measured value is below the + low speed limit. * SmartFan/PWM control - If you want to set a pwm fan to manual mode, you just need to make sure it - is not controlled by any temp channel, for example, you want to set fan1 - to manual mode, you need to check the value of temp[1-6]_fan_map, make - sure bit 0 is cleared in the 6 values. And then set the pwm1 value to - control the fan. - - Each temperature channel can control all the 8 PWM outputs (by setting the - corresponding bit in tempX_fan_map), you can set the temperature channel - mode using temp[1-6]_pwm_enable, 2 is Thermal Cruise mode and 3 - is the SmartFanII mode. Temperature channels will try to speed up or - slow down all controlled fans, this means one fan can receive different - PWM value requests from different temperature channels, but the chip - will always pick the safest (max) PWM value for each fan. - - In Thermal Cruise mode, the chip attempts to keep the temperature at a - predefined value, within a tolerance margin. So if tempX_input > - thermal_cruiseX + toleranceX, the chip will increase the PWM value, - if tempX_input < thermal_cruiseX - toleranceX, the chip will decrease - the PWM value. If the temperature is within the tolerance range, the PWM - value is left unchanged. - - SmartFanII works differently, you have to define up to 7 PWM, temperature - trip points, defining a PWM/temperature curve which the chip will follow. - While not fundamentally different from the Thermal Cruise mode, the - implementation is quite different, giving you a finer-grained control. + If you want to set a pwm fan to manual mode, you just need to make sure it + is not controlled by any temp channel, for example, you want to set fan1 + to manual mode, you need to check the value of temp[1-6]_fan_map, make + sure bit 0 is cleared in the 6 values. And then set the pwm1 value to + control the fan. + + Each temperature channel can control all the 8 PWM outputs (by setting the + corresponding bit in tempX_fan_map), you can set the temperature channel + mode using temp[1-6]_pwm_enable, 2 is Thermal Cruise mode and 3 + is the SmartFanII mode. Temperature channels will try to speed up or + slow down all controlled fans, this means one fan can receive different + PWM value requests from different temperature channels, but the chip + will always pick the safest (max) PWM value for each fan. + + In Thermal Cruise mode, the chip attempts to keep the temperature at a + predefined value, within a tolerance margin. So if tempX_input > + thermal_cruiseX + toleranceX, the chip will increase the PWM value, + if tempX_input < thermal_cruiseX - toleranceX, the chip will decrease + the PWM value. If the temperature is within the tolerance range, the PWM + value is left unchanged. + + SmartFanII works differently, you have to define up to 7 PWM, temperature + trip points, defining a PWM/temperature curve which the chip will follow. + While not fundamentally different from the Thermal Cruise mode, the + implementation is quite different, giving you a finer-grained control. * Chassis - If the case open alarm triggers, it will stay in this state unless cleared - by writing 0 to the sysfs file "intrusion0_alarm". + If the case open alarm triggers, it will stay in this state unless cleared + by writing 0 to the sysfs file "intrusion0_alarm". * VID and VRM - The VRM version is detected automatically, don't modify the it unless you - *do* know the cpu VRM version and it's not properly detected. + The VRM version is detected automatically, don't modify the it unless you + *do* know the cpu VRM version and it's not properly detected. Notes -- cgit v1.2.3 From 1f234ff1621787860cfcca6aa8fb626519405a72 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 17 Apr 2019 06:46:26 -0300 Subject: docs: hwmon: pmbus files: convert to ReST format Convert pmbus files to ReST format, in order to allow them to be parsed by Sphinx. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Guenter Roeck --- Documentation/hwmon/adm1275 | 26 ++++ Documentation/hwmon/ibm-cffps | 3 + Documentation/hwmon/ir35221 | 11 +- Documentation/hwmon/lm25066 | 30 +++++ Documentation/hwmon/ltc2978 | 267 +++++++++++++++++++++++++++++++---------- Documentation/hwmon/ltc3815 | 12 +- Documentation/hwmon/max16064 | 15 ++- Documentation/hwmon/max20751 | 7 ++ Documentation/hwmon/max31785 | 6 + Documentation/hwmon/max34440 | 88 +++++++++++--- Documentation/hwmon/max8688 | 18 ++- Documentation/hwmon/pmbus | 90 ++++++++++---- Documentation/hwmon/pmbus-core | 173 +++++++++++++++----------- Documentation/hwmon/tps40422 | 23 ++-- Documentation/hwmon/ucd9000 | 31 +++-- Documentation/hwmon/ucd9200 | 42 ++++--- Documentation/hwmon/zl6100 | 69 +++++++++-- 17 files changed, 684 insertions(+), 227 deletions(-) (limited to 'Documentation') diff --git a/Documentation/hwmon/adm1275 b/Documentation/hwmon/adm1275 index 5e277b0d91ce..5c5860011d6e 100644 --- a/Documentation/hwmon/adm1275 +++ b/Documentation/hwmon/adm1275 @@ -2,29 +2,53 @@ Kernel driver adm1275 ===================== Supported chips: + * Analog Devices ADM1075 + Prefix: 'adm1075' + Addresses scanned: - + Datasheet: www.analog.com/static/imported-files/data_sheets/ADM1075.pdf + * Analog Devices ADM1272 + Prefix: 'adm1272' + Addresses scanned: - + Datasheet: www.analog.com/static/imported-files/data_sheets/ADM1272.pdf + * Analog Devices ADM1275 + Prefix: 'adm1275' + Addresses scanned: - + Datasheet: www.analog.com/static/imported-files/data_sheets/ADM1275.pdf + * Analog Devices ADM1276 + Prefix: 'adm1276' + Addresses scanned: - + Datasheet: www.analog.com/static/imported-files/data_sheets/ADM1276.pdf + * Analog Devices ADM1278 + Prefix: 'adm1278' + Addresses scanned: - + Datasheet: www.analog.com/static/imported-files/data_sheets/ADM1278.pdf + * Analog Devices ADM1293/ADM1294 + Prefix: 'adm1293', 'adm1294' + Addresses scanned: - + Datasheet: http://www.analog.com/media/en/technical-documentation/data-sheets/ADM1293_1294.pdf Author: Guenter Roeck @@ -75,6 +99,7 @@ Sysfs entries The following attributes are supported. Limits are read-write, history reset attributes are write-only, all other attributes are read-only. +======================= ======================================================= inX_label "vin1" or "vout1" depending on chip variant and configuration. On ADM1075, ADM1293, and ADM1294, vout1 reports the voltage on the VAUX pin. @@ -120,3 +145,4 @@ temp1_reset_history Write any value to reset history. Temperature attributes are supported on ADM1272 and ADM1278. +======================= ======================================================= diff --git a/Documentation/hwmon/ibm-cffps b/Documentation/hwmon/ibm-cffps index e05ecd8ecfcf..52e74e39463a 100644 --- a/Documentation/hwmon/ibm-cffps +++ b/Documentation/hwmon/ibm-cffps @@ -2,6 +2,7 @@ Kernel driver ibm-cffps ======================= Supported chips: + * IBM Common Form Factor power supply Author: Eddie James @@ -24,6 +25,7 @@ Sysfs entries The following attributes are supported: +======================= ====================================================== curr1_alarm Output current over-current alarm. curr1_input Measured output current in mA. curr1_label "iout1" @@ -52,3 +54,4 @@ temp2_alarm Secondary rectifier temp over-temperature alarm. temp2_input Measured secondary rectifier temp in millidegrees C. temp3_alarm ORing FET temperature over-temperature alarm. temp3_input Measured ORing FET temperature in millidegrees C. +======================= ====================================================== diff --git a/Documentation/hwmon/ir35221 b/Documentation/hwmon/ir35221 index 3e82f3d93f44..a83922e5ccb5 100644 --- a/Documentation/hwmon/ir35221 +++ b/Documentation/hwmon/ir35221 @@ -3,8 +3,11 @@ Kernel driver ir35221 Supported chips: * Infineon IR35221 + Prefix: 'ir35221' + Addresses scanned: - + Datasheet: Datasheet is not publicly available. Author: Samuel Mendoza-Jonas @@ -23,15 +26,16 @@ This driver does not probe for PMBus devices. You will have to instantiate devices explicitly. Example: the following commands will load the driver for an IR35221 -at address 0x70 on I2C bus #4: +at address 0x70 on I2C bus #4:: -# modprobe ir35221 -# echo ir35221 0x70 > /sys/bus/i2c/devices/i2c-4/new_device + # modprobe ir35221 + # echo ir35221 0x70 > /sys/bus/i2c/devices/i2c-4/new_device Sysfs attributes ---------------- +======================= ======================================================= curr1_label "iin" curr1_input Measured input current curr1_max Maximum current @@ -85,3 +89,4 @@ temp[1-2]_highest Highest temperature temp[1-2]_lowest Lowest temperature temp[1-2]_max Maximum temperature temp[1-2]_max_alarm Chip temperature high alarm +======================= ======================================================= diff --git a/Documentation/hwmon/lm25066 b/Documentation/hwmon/lm25066 index 51b32aa203a8..60b7f2722931 100644 --- a/Documentation/hwmon/lm25066 +++ b/Documentation/hwmon/lm25066 @@ -2,34 +2,62 @@ Kernel driver lm25066 ===================== Supported chips: + * TI LM25056 + Prefix: 'lm25056' + Addresses scanned: - + Datasheets: + http://www.ti.com/lit/gpn/lm25056 + http://www.ti.com/lit/gpn/lm25056a + * National Semiconductor LM25066 + Prefix: 'lm25066' + Addresses scanned: - + Datasheets: + http://www.national.com/pf/LM/LM25066.html + http://www.national.com/pf/LM/LM25066A.html + * National Semiconductor LM5064 + Prefix: 'lm5064' + Addresses scanned: - + Datasheet: + http://www.national.com/pf/LM/LM5064.html + * National Semiconductor LM5066 + Prefix: 'lm5066' + Addresses scanned: - + Datasheet: + http://www.national.com/pf/LM/LM5066.html + * Texas Instruments LM5066I + Prefix: 'lm5066i' + Addresses scanned: - + Datasheet: + http://www.ti.com/product/LM5066I + Author: Guenter Roeck @@ -64,6 +92,7 @@ Sysfs entries The following attributes are supported. Limits are read-write; all other attributes are read-only. +======================= ======================================================= in1_label "vin" in1_input Measured input voltage. in1_average Average measured input voltage. @@ -105,3 +134,4 @@ temp1_max Maximum temperature. temp1_crit Critical high temperature. temp1_max_alarm Chip temperature high alarm. temp1_crit_alarm Chip temperature critical high alarm. +======================= ======================================================= diff --git a/Documentation/hwmon/ltc2978 b/Documentation/hwmon/ltc2978 index dfb2caa401d9..01a24fd6d5fe 100644 --- a/Documentation/hwmon/ltc2978 +++ b/Documentation/hwmon/ltc2978 @@ -2,85 +2,143 @@ Kernel driver ltc2978 ===================== Supported chips: + * Linear Technology LTC2974 + Prefix: 'ltc2974' + Addresses scanned: - + Datasheet: http://www.linear.com/product/ltc2974 + * Linear Technology LTC2975 + Prefix: 'ltc2975' + Addresses scanned: - + Datasheet: http://www.linear.com/product/ltc2975 + * Linear Technology LTC2977 + Prefix: 'ltc2977' + Addresses scanned: - + Datasheet: http://www.linear.com/product/ltc2977 + * Linear Technology LTC2978, LTC2978A + Prefix: 'ltc2978' + Addresses scanned: - + Datasheet: http://www.linear.com/product/ltc2978 - http://www.linear.com/product/ltc2978a + + http://www.linear.com/product/ltc2978a + * Linear Technology LTC2980 + Prefix: 'ltc2980' + Addresses scanned: - + Datasheet: http://www.linear.com/product/ltc2980 + * Linear Technology LTC3880 + Prefix: 'ltc3880' + Addresses scanned: - + Datasheet: http://www.linear.com/product/ltc3880 + * Linear Technology LTC3882 + Prefix: 'ltc3882' + Addresses scanned: - + Datasheet: http://www.linear.com/product/ltc3882 + * Linear Technology LTC3883 + Prefix: 'ltc3883' + Addresses scanned: - + Datasheet: http://www.linear.com/product/ltc3883 + * Linear Technology LTC3886 + Prefix: 'ltc3886' + Addresses scanned: - + Datasheet: http://www.linear.com/product/ltc3886 + * Linear Technology LTC3887 + Prefix: 'ltc3887' + Addresses scanned: - + Datasheet: http://www.linear.com/product/ltc3887 + * Linear Technology LTM2987 + Prefix: 'ltm2987' + Addresses scanned: - + Datasheet: http://www.linear.com/product/ltm2987 + * Linear Technology LTM4675 + Prefix: 'ltm4675' + Addresses scanned: - + Datasheet: http://www.linear.com/product/ltm4675 + * Linear Technology LTM4676 + Prefix: 'ltm4676' + Addresses scanned: - + Datasheet: http://www.linear.com/product/ltm4676 + * Analog Devices LTM4686 + Prefix: 'ltm4686' + Addresses scanned: - + Datasheet: http://www.analog.com/ltm4686 + Author: Guenter Roeck Description ----------- -LTC2974 and LTC2975 are quad digital power supply managers. -LTC2978 is an octal power supply monitor. -LTC2977 is a pin compatible replacement for LTC2978. -LTC2980 is a 16-channel Power System Manager, consisting of two LTC2977 -in a single die. The chip is instantiated and reported as two separate chips -on two different I2C bus addresses. -LTC3880, LTC3882, LTC3886, and LTC3887 are dual output poly-phase step-down -DC/DC controllers. -LTC3883 is a single phase step-down DC/DC controller. -LTM2987 is a 16-channel Power System Manager with two LTC2977 plus -additional components on a single die. The chip is instantiated and reported -as two separate chips on two different I2C bus addresses. -LTM4675 is a dual 9A or single 18A μModule regulator -LTM4676 is a dual 13A or single 26A uModule regulator. -LTM4686 is a dual 10A or single 20A uModule regulator. +- LTC2974 and LTC2975 are quad digital power supply managers. +- LTC2978 is an octal power supply monitor. +- LTC2977 is a pin compatible replacement for LTC2978. +- LTC2980 is a 16-channel Power System Manager, consisting of two LTC2977 +- in a single die. The chip is instantiated and reported as two separate chips +- on two different I2C bus addresses. +- LTC3880, LTC3882, LTC3886, and LTC3887 are dual output poly-phase step-down +- DC/DC controllers. +- LTC3883 is a single phase step-down DC/DC controller. +- LTM2987 is a 16-channel Power System Manager with two LTC2977 plus +- additional components on a single die. The chip is instantiated and reported +- as two separate chips on two different I2C bus addresses. +- LTM4675 is a dual 9A or single 18A μModule regulator +- LTM4676 is a dual 13A or single 26A uModule regulator. +- LTM4686 is a dual 10A or single 20A uModule regulator. Usage Notes @@ -90,127 +148,208 @@ This driver does not probe for PMBus devices. You will have to instantiate devices explicitly. Example: the following commands will load the driver for an LTC2978 at address -0x60 on I2C bus #1: +0x60 on I2C bus #1:: -# modprobe ltc2978 -# echo ltc2978 0x60 > /sys/bus/i2c/devices/i2c-1/new_device + # modprobe ltc2978 + # echo ltc2978 0x60 > /sys/bus/i2c/devices/i2c-1/new_device Sysfs attributes ---------------- +======================= ======================================================== in1_label "vin" + in1_input Measured input voltage. + in1_min Minimum input voltage. + in1_max Maximum input voltage. + LTC2974, LTC2975, LTC2977, LTC2980, LTC2978, and LTM2987 only. + in1_lcrit Critical minimum input voltage. + LTC2974, LTC2975, LTC2977, LTC2980, LTC2978, and LTM2987 only. + in1_crit Critical maximum input voltage. + in1_min_alarm Input voltage low alarm. + in1_max_alarm Input voltage high alarm. + LTC2974, LTC2975, LTC2977, LTC2980, LTC2978, and LTM2987 only. in1_lcrit_alarm Input voltage critical low alarm. + LTC2974, LTC2975, LTC2977, LTC2980, LTC2978, and LTM2987 only. in1_crit_alarm Input voltage critical high alarm. + in1_lowest Lowest input voltage. + LTC2974, LTC2975, LTC2977, LTC2980, LTC2978, and LTM2987 only. in1_highest Highest input voltage. + in1_reset_history Reset input voltage history. in[N]_label "vout[1-8]". - LTC2974, LTC2975: N=2-5 - LTC2977, LTC2980, LTM2987: N=2-9 - LTC2978: N=2-9 - LTC3880, LTC3882, LTC23886 LTC3887, LTM4675, LTM4676: - N=2-3 - LTC3883: N=2 + + - LTC2974, LTC2975: N=2-5 + - LTC2977, LTC2980, LTM2987: N=2-9 + - LTC2978: N=2-9 + - LTC3880, LTC3882, LTC23886 LTC3887, LTM4675, LTM4676: + N=2-3 + - LTC3883: N=2 + in[N]_input Measured output voltage. + in[N]_min Minimum output voltage. + in[N]_max Maximum output voltage. + in[N]_lcrit Critical minimum output voltage. + in[N]_crit Critical maximum output voltage. + in[N]_min_alarm Output voltage low alarm. + in[N]_max_alarm Output voltage high alarm. + in[N]_lcrit_alarm Output voltage critical low alarm. + in[N]_crit_alarm Output voltage critical high alarm. -in[N]_lowest Lowest output voltage. LTC2974, LTC2975, - and LTC2978 only. + +in[N]_lowest Lowest output voltage. + + + LTC2974, LTC2975,and LTC2978 only. + in[N]_highest Highest output voltage. + in[N]_reset_history Reset output voltage history. temp[N]_input Measured temperature. - On LTC2974 and LTC2975, temp[1-4] report external - temperatures, and temp5 reports the chip temperature. - On LTC2977, LTC2980, LTC2978, and LTM2987, only one - temperature measurement is supported and reports - the chip temperature. - On LTC3880, LTC3882, LTC3887, LTM4675, and LTM4676, - temp1 and temp2 report external temperatures, and temp3 - reports the chip temperature. - On LTC3883, temp1 reports an external temperature, - and temp2 reports the chip temperature. -temp[N]_min Mimimum temperature. LTC2974, LCT2977, LTM2980, LTC2978, - and LTM2987 only. + + - On LTC2974 and LTC2975, temp[1-4] report external + temperatures, and temp5 reports the chip temperature. + - On LTC2977, LTC2980, LTC2978, and LTM2987, only one + temperature measurement is supported and reports + the chip temperature. + - On LTC3880, LTC3882, LTC3887, LTM4675, and LTM4676, + temp1 and temp2 report external temperatures, and + temp3 reports the chip temperature. + - On LTC3883, temp1 reports an external temperature, + and temp2 reports the chip temperature. + +temp[N]_min Mimimum temperature. + + LTC2974, LCT2977, LTM2980, LTC2978, and LTM2987 only. + temp[N]_max Maximum temperature. + temp[N]_lcrit Critical low temperature. + temp[N]_crit Critical high temperature. + temp[N]_min_alarm Temperature low alarm. + LTC2974, LTC2975, LTC2977, LTM2980, LTC2978, and LTM2987 only. + temp[N]_max_alarm Temperature high alarm. + + temp[N]_lcrit_alarm Temperature critical low alarm. + temp[N]_crit_alarm Temperature critical high alarm. + temp[N]_lowest Lowest measured temperature. - LTC2974, LTC2975, LTC2977, LTM2980, LTC2978, and - LTM2987 only. - Not supported for chip temperature sensor on LTC2974 and - LTC2975. -temp[N]_highest Highest measured temperature. Not supported for chip - temperature sensor on LTC2974 and LTC2975. -temp[N]_reset_history Reset temperature history. Not supported for chip - temperature sensor on LTC2974 and LTC2975. + + - LTC2974, LTC2975, LTC2977, LTM2980, LTC2978, and + LTM2987 only. + - Not supported for chip temperature sensor on LTC2974 + and LTC2975. + +temp[N]_highest Highest measured temperature. + + Not supported for chip temperature sensor on + LTC2974 and LTC2975. + +temp[N]_reset_history Reset temperature history. + + Not supported for chip temperature sensor on + LTC2974 and LTC2975. power1_label "pin". LTC3883 and LTC3886 only. + power1_input Measured input power. power[N]_label "pout[1-4]". - LTC2974, LTC2975: N=1-4 - LTC2977, LTC2980, LTM2987: Not supported - LTC2978: Not supported - LTC3880, LTC3882, LTC3886, LTC3887, LTM4675, LTM4676: - N=1-2 - LTC3883: N=2 + + - LTC2974, LTC2975: N=1-4 + - LTC2977, LTC2980, LTM2987: Not supported + - LTC2978: Not supported + - LTC3880, LTC3882, LTC3886, LTC3887, LTM4675, LTM4676: + N=1-2 + - LTC3883: N=2 + power[N]_input Measured output power. -curr1_label "iin". LTC3880, LTC3883, LTC3886, LTC3887, LTM4675, +curr1_label "iin". + + LTC3880, LTC3883, LTC3886, LTC3887, LTM4675, and LTM4676 only. + curr1_input Measured input current. + curr1_max Maximum input current. + curr1_max_alarm Input current high alarm. -curr1_highest Highest input current. LTC3883 and LTC3886 only. -curr1_reset_history Reset input current history. LTC3883 and LTC3886 only. + +curr1_highest Highest input current. + + LTC3883 and LTC3886 only. + +curr1_reset_history Reset input current history. + + LTC3883 and LTC3886 only. curr[N]_label "iout[1-4]". - LTC2974, LTC2975: N=1-4 - LTC2977, LTC2980, LTM2987: not supported - LTC2978: not supported - LTC3880, LTC3882, LTC3886, LTC3887, LTM4675, LTM4676: - N=2-3 - LTC3883: N=2 + + - LTC2974, LTC2975: N=1-4 + - LTC2977, LTC2980, LTM2987: not supported + - LTC2978: not supported + - LTC3880, LTC3882, LTC3886, LTC3887, LTM4675, LTM4676: + N=2-3 + - LTC3883: N=2 + curr[N]_input Measured output current. + curr[N]_max Maximum output current. + curr[N]_crit Critical high output current. -curr[N]_lcrit Critical low output current. LTC2974 and LTC2975 only. + +curr[N]_lcrit Critical low output current. + + LTC2974 and LTC2975 only. + curr[N]_max_alarm Output current high alarm. + curr[N]_crit_alarm Output current critical high alarm. + curr[N]_lcrit_alarm Output current critical low alarm. + + LTC2974 and LTC2975 only. + +curr[N]_lowest Lowest output current. + LTC2974 and LTC2975 only. -curr[N]_lowest Lowest output current. LTC2974 and LTC2975 only. + curr[N]_highest Highest output current. + curr[N]_reset_history Reset output current history. +======================= ======================================================== diff --git a/Documentation/hwmon/ltc3815 b/Documentation/hwmon/ltc3815 index eb7db2d13587..fb0135fc1925 100644 --- a/Documentation/hwmon/ltc3815 +++ b/Documentation/hwmon/ltc3815 @@ -2,9 +2,13 @@ Kernel driver ltc3815 ===================== Supported chips: + * Linear Technology LTC3815 + Prefix: 'ltc3815' + Addresses scanned: - + Datasheet: http://www.linear.com/product/ltc3815 Author: Guenter Roeck @@ -23,15 +27,16 @@ This driver does not probe for PMBus devices. You will have to instantiate devices explicitly. Example: the following commands will load the driver for an LTC3815 -at address 0x20 on I2C bus #1: +at address 0x20 on I2C bus #1:: -# modprobe ltc3815 -# echo ltc3815 0x20 > /sys/bus/i2c/devices/i2c-1/new_device + # modprobe ltc3815 + # echo ltc3815 0x20 > /sys/bus/i2c/devices/i2c-1/new_device Sysfs attributes ---------------- +======================= ======================================================= in1_label "vin" in1_input Measured input voltage. in1_alarm Input voltage alarm. @@ -59,3 +64,4 @@ curr2_input Measured output current. curr2_alarm Output current alarm. curr2_highest Highest output current. curr2_reset_history Reset output current history. +======================= ======================================================= diff --git a/Documentation/hwmon/max16064 b/Documentation/hwmon/max16064 index 265370f5cb82..61ec679dc477 100644 --- a/Documentation/hwmon/max16064 +++ b/Documentation/hwmon/max16064 @@ -2,9 +2,13 @@ Kernel driver max16064 ====================== Supported chips: + * Maxim MAX16064 + Prefix: 'max16064' + Addresses scanned: - + Datasheet: http://datasheets.maxim-ic.com/en/ds/MAX16064.pdf Author: Guenter Roeck @@ -40,16 +44,20 @@ Sysfs entries The following attributes are supported. Limits are read-write; all other attributes are read-only. +======================= ======================================================== in[1-4]_label "vout[1-4]" in[1-4]_input Measured voltage. From READ_VOUT register. in[1-4]_min Minimum Voltage. From VOUT_UV_WARN_LIMIT register. in[1-4]_max Maximum voltage. From VOUT_OV_WARN_LIMIT register. in[1-4]_lcrit Critical minimum Voltage. VOUT_UV_FAULT_LIMIT register. -in[1-4]_crit Critical maximum voltage. From VOUT_OV_FAULT_LIMIT register. +in[1-4]_crit Critical maximum voltage. From VOUT_OV_FAULT_LIMIT + register. in[1-4]_min_alarm Voltage low alarm. From VOLTAGE_UV_WARNING status. in[1-4]_max_alarm Voltage high alarm. From VOLTAGE_OV_WARNING status. -in[1-4]_lcrit_alarm Voltage critical low alarm. From VOLTAGE_UV_FAULT status. -in[1-4]_crit_alarm Voltage critical high alarm. From VOLTAGE_OV_FAULT status. +in[1-4]_lcrit_alarm Voltage critical low alarm. From VOLTAGE_UV_FAULT + status. +in[1-4]_crit_alarm Voltage critical high alarm. From VOLTAGE_OV_FAULT + status. in[1-4]_highest Historical maximum voltage. in[1-4]_reset_history Write any value to reset history. @@ -64,3 +72,4 @@ temp1_crit_alarm Chip temperature critical high alarm. Set by comparing status is set. temp1_highest Historical maximum temperature. temp1_reset_history Write any value to reset history. +======================= ======================================================== diff --git a/Documentation/hwmon/max20751 b/Documentation/hwmon/max20751 index f9fa25ebb521..d546695900ef 100644 --- a/Documentation/hwmon/max20751 +++ b/Documentation/hwmon/max20751 @@ -2,10 +2,15 @@ Kernel driver max20751 ====================== Supported chips: + * maxim MAX20751 + Prefix: 'max20751' + Addresses scanned: - + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX20751.pdf + Application note: http://pdfserv.maximintegrated.com/en/an/AN5941.pdf Author: Guenter Roeck @@ -40,6 +45,7 @@ Sysfs entries The following attributes are supported. +======================= ======================================================= in1_label "vin1" in1_input Measured voltage. in1_min Minimum input voltage. @@ -75,3 +81,4 @@ temp1_crit_alarm Chip temperature critical high alarm. power1_input Output power. power1_label "pout1" +======================= ======================================================= diff --git a/Documentation/hwmon/max31785 b/Documentation/hwmon/max31785 index 270c5f865261..c8c6756d0ee1 100644 --- a/Documentation/hwmon/max31785 +++ b/Documentation/hwmon/max31785 @@ -2,9 +2,13 @@ Kernel driver max31785 ====================== Supported chips: + * Maxim MAX31785, MAX31785A + Prefix: 'max31785' or 'max31785a' + Addresses scanned: - + Datasheet: https://datasheets.maximintegrated.com/en/ds/MAX31785.pdf Author: Andrew Jeffery @@ -30,6 +34,7 @@ devices explicitly. Sysfs attributes ---------------- +======================= ======================================================= fan[1-4]_alarm Fan alarm. fan[1-4]_fault Fan fault. fan[1-8]_input Fan RPM. On the MAX31785A, inputs 5-8 correspond to the @@ -58,3 +63,4 @@ temp[1-11]_crit_alarm Chip temperature critical high alarm temp[1-11]_input Measured temperature temp[1-11]_max Maximum temperature temp[1-11]_max_alarm Chip temperature high alarm +======================= ======================================================= diff --git a/Documentation/hwmon/max34440 b/Documentation/hwmon/max34440 index b2de8fa49273..639838ef29fd 100644 --- a/Documentation/hwmon/max34440 +++ b/Documentation/hwmon/max34440 @@ -2,34 +2,63 @@ Kernel driver max34440 ====================== Supported chips: + * Maxim MAX34440 + Prefixes: 'max34440' + Addresses scanned: - + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX34440.pdf + * Maxim MAX34441 + PMBus 5-Channel Power-Supply Manager and Intelligent Fan Controller + Prefixes: 'max34441' + Addresses scanned: - + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX34441.pdf + * Maxim MAX34446 + PMBus Power-Supply Data Logger + Prefixes: 'max34446' + Addresses scanned: - + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX34446.pdf + * Maxim MAX34451 + PMBus 16-Channel V/I Monitor and 12-Channel Sequencer/Marginer + Prefixes: 'max34451' + Addresses scanned: - + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX34451.pdf + * Maxim MAX34460 + PMBus 12-Channel Voltage Monitor & Sequencer + Prefix: 'max34460' + Addresses scanned: - + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX34460.pdf + * Maxim MAX34461 + PMBus 16-Channel Voltage Monitor & Sequencer + Prefix: 'max34461' + Addresses scanned: - + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX34461.pdf Author: Guenter Roeck @@ -77,42 +106,67 @@ Sysfs entries The following attributes are supported. Limits are read-write; all other attributes are read-only. +In +~~ + +======================= ======================================================= in[1-6]_label "vout[1-6]". in[1-6]_input Measured voltage. From READ_VOUT register. in[1-6]_min Minimum Voltage. From VOUT_UV_WARN_LIMIT register. in[1-6]_max Maximum voltage. From VOUT_OV_WARN_LIMIT register. in[1-6]_lcrit Critical minimum Voltage. VOUT_UV_FAULT_LIMIT register. -in[1-6]_crit Critical maximum voltage. From VOUT_OV_FAULT_LIMIT register. +in[1-6]_crit Critical maximum voltage. From VOUT_OV_FAULT_LIMIT + register. in[1-6]_min_alarm Voltage low alarm. From VOLTAGE_UV_WARNING status. in[1-6]_max_alarm Voltage high alarm. From VOLTAGE_OV_WARNING status. -in[1-6]_lcrit_alarm Voltage critical low alarm. From VOLTAGE_UV_FAULT status. -in[1-6]_crit_alarm Voltage critical high alarm. From VOLTAGE_OV_FAULT status. +in[1-6]_lcrit_alarm Voltage critical low alarm. From VOLTAGE_UV_FAULT + status. +in[1-6]_crit_alarm Voltage critical high alarm. From VOLTAGE_OV_FAULT + status. in[1-6]_lowest Historical minimum voltage. in[1-6]_highest Historical maximum voltage. in[1-6]_reset_history Write any value to reset history. +======================= ======================================================= + +.. note:: MAX34446 only supports in[1-4]. - MAX34446 only supports in[1-4]. +Curr +~~~~ +======================= ======================================================== curr[1-6]_label "iout[1-6]". curr[1-6]_input Measured current. From READ_IOUT register. curr[1-6]_max Maximum current. From IOUT_OC_WARN_LIMIT register. -curr[1-6]_crit Critical maximum current. From IOUT_OC_FAULT_LIMIT register. +curr[1-6]_crit Critical maximum current. From IOUT_OC_FAULT_LIMIT + register. curr[1-6]_max_alarm Current high alarm. From IOUT_OC_WARNING status. curr[1-6]_crit_alarm Current critical high alarm. From IOUT_OC_FAULT status. curr[1-4]_average Historical average current (MAX34446/34451 only). curr[1-6]_highest Historical maximum current. curr[1-6]_reset_history Write any value to reset history. +======================= ======================================================== + +.. note:: + + - in6 and curr6 attributes only exist for MAX34440. + - MAX34446 only supports curr[1-4]. - in6 and curr6 attributes only exist for MAX34440. - MAX34446 only supports curr[1-4]. +Power +~~~~~ +======================= ======================================================== power[1,3]_label "pout[1,3]" power[1,3]_input Measured power. power[1,3]_average Historical average power. power[1,3]_highest Historical maximum power. +======================= ======================================================== - Power attributes only exist for MAX34446. +.. note:: Power attributes only exist for MAX34446. +Temp +~~~~ + +======================= ======================================================== temp[1-8]_input Measured temperatures. From READ_TEMPERATURE_1 register. temp1 is the chip's internal temperature. temp2..temp5 are remote I2C temperature sensors. For MAX34441, temp6 @@ -125,11 +179,17 @@ temp[1-8]_crit_alarm Temperature critical high alarm. temp[1-8]_average Historical average temperature (MAX34446 only). temp[1-8]_highest Historical maximum temperature. temp[1-8]_reset_history Write any value to reset history. +======================= ======================================================== + + +.. note:: + - temp7 and temp8 attributes only exist for MAX34440. + - MAX34446 only supports temp[1-3]. + - temp7 and temp8 attributes only exist for MAX34440. - MAX34446 only supports temp[1-3]. +.. note:: -MAX34451 supports attribute groups in[1-16] (or curr[1-16] based on input pins) -and temp[1-5]. -MAX34460 supports attribute groups in[1-12] and temp[1-5]. -MAX34461 supports attribute groups in[1-16] and temp[1-5]. + - MAX34451 supports attribute groups in[1-16] (or curr[1-16] based on + input pins) and temp[1-5]. + - MAX34460 supports attribute groups in[1-12] and temp[1-5]. + - MAX34461 supports attribute groups in[1-16] and temp[1-5]. diff --git a/Documentation/hwmon/max8688 b/Documentation/hwmon/max8688 index ca233bec7a8a..43da139234c1 100644 --- a/Documentation/hwmon/max8688 +++ b/Documentation/hwmon/max8688 @@ -2,9 +2,13 @@ Kernel driver max8688 ===================== Supported chips: + * Maxim MAX8688 + Prefix: 'max8688' + Addresses scanned: - + Datasheet: http://datasheets.maxim-ic.com/en/ds/MAX8688.pdf Author: Guenter Roeck @@ -40,23 +44,28 @@ Sysfs entries The following attributes are supported. Limits are read-write; all other attributes are read-only. +======================= ======================================================== in1_label "vout1" in1_input Measured voltage. From READ_VOUT register. in1_min Minimum Voltage. From VOUT_UV_WARN_LIMIT register. in1_max Maximum voltage. From VOUT_OV_WARN_LIMIT register. in1_lcrit Critical minimum Voltage. VOUT_UV_FAULT_LIMIT register. -in1_crit Critical maximum voltage. From VOUT_OV_FAULT_LIMIT register. +in1_crit Critical maximum voltage. From VOUT_OV_FAULT_LIMIT + register. in1_min_alarm Voltage low alarm. From VOLTAGE_UV_WARNING status. in1_max_alarm Voltage high alarm. From VOLTAGE_OV_WARNING status. -in1_lcrit_alarm Voltage critical low alarm. From VOLTAGE_UV_FAULT status. -in1_crit_alarm Voltage critical high alarm. From VOLTAGE_OV_FAULT status. +in1_lcrit_alarm Voltage critical low alarm. From VOLTAGE_UV_FAULT + status. +in1_crit_alarm Voltage critical high alarm. From VOLTAGE_OV_FAULT + status. in1_highest Historical maximum voltage. in1_reset_history Write any value to reset history. curr1_label "iout1" curr1_input Measured current. From READ_IOUT register. curr1_max Maximum current. From IOUT_OC_WARN_LIMIT register. -curr1_crit Critical maximum current. From IOUT_OC_FAULT_LIMIT register. +curr1_crit Critical maximum current. From IOUT_OC_FAULT_LIMIT + register. curr1_max_alarm Current high alarm. From IOUT_OC_WARN_LIMIT register. curr1_crit_alarm Current critical high alarm. From IOUT_OC_FAULT status. curr1_highest Historical maximum current. @@ -73,3 +82,4 @@ temp1_crit_alarm Chip temperature critical high alarm. Set by comparing status is set. temp1_highest Historical maximum temperature. temp1_reset_history Write any value to reset history. +======================= ======================================================== diff --git a/Documentation/hwmon/pmbus b/Documentation/hwmon/pmbus index dfd9c65996c0..abfb9dd4857d 100644 --- a/Documentation/hwmon/pmbus +++ b/Documentation/hwmon/pmbus @@ -1,42 +1,77 @@ Kernel driver pmbus -==================== +=================== Supported chips: + * Ericsson BMR453, BMR454 + Prefixes: 'bmr453', 'bmr454' + Addresses scanned: - + Datasheet: + http://archive.ericsson.net/service/internet/picov/get?DocNo=28701-EN/LZT146395 + * ON Semiconductor ADP4000, NCP4200, NCP4208 + Prefixes: 'adp4000', 'ncp4200', 'ncp4208' + Addresses scanned: - + Datasheets: + http://www.onsemi.com/pub_link/Collateral/ADP4000-D.PDF + http://www.onsemi.com/pub_link/Collateral/NCP4200-D.PDF + http://www.onsemi.com/pub_link/Collateral/JUNE%202009-%20REV.%200.PDF + * Lineage Power + Prefixes: 'mdt040', 'pdt003', 'pdt006', 'pdt012', 'udt020' + Addresses scanned: - + Datasheets: + http://www.lineagepower.com/oem/pdf/PDT003A0X.pdf + http://www.lineagepower.com/oem/pdf/PDT006A0X.pdf + http://www.lineagepower.com/oem/pdf/PDT012A0X.pdf + http://www.lineagepower.com/oem/pdf/UDT020A0X.pdf + http://www.lineagepower.com/oem/pdf/MDT040A0X.pdf + * Texas Instruments TPS40400, TPS544B20, TPS544B25, TPS544C20, TPS544C25 + Prefixes: 'tps40400', 'tps544b20', 'tps544b25', 'tps544c20', 'tps544c25' + Addresses scanned: - + Datasheets: + http://www.ti.com/lit/gpn/tps40400 + http://www.ti.com/lit/gpn/tps544b20 + http://www.ti.com/lit/gpn/tps544b25 + http://www.ti.com/lit/gpn/tps544c20 + http://www.ti.com/lit/gpn/tps544c25 + * Generic PMBus devices + Prefix: 'pmbus' + Addresses scanned: - + Datasheet: n.a. + Author: Guenter Roeck @@ -62,9 +97,10 @@ supported by all chips), and since there is no well defined address range for PMBus devices. You will have to instantiate the devices explicitly. Example: the following will load the driver for an LTC2978 at address 0x60 -on I2C bus #1: -$ modprobe pmbus -$ echo ltc2978 0x60 > /sys/bus/i2c/devices/i2c-1/new_device +on I2C bus #1:: + + $ modprobe pmbus + $ echo ltc2978 0x60 > /sys/bus/i2c/devices/i2c-1/new_device Platform data support @@ -72,9 +108,9 @@ Platform data support Support for additional PMBus chips can be added by defining chip parameters in a new chip specific driver file. For example, (untested) code to add support for -Emerson DS1200 power modules might look as follows. +Emerson DS1200 power modules might look as follows:: -static struct pmbus_driver_info ds1200_info = { + static struct pmbus_driver_info ds1200_info = { .pages = 1, /* Note: All other sensors are in linear mode */ .direct[PSC_VOLTAGE_OUT] = true, @@ -95,45 +131,45 @@ static struct pmbus_driver_info ds1200_info = { | PMBUS_HAVE_PIN | PMBUS_HAVE_POUT | PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP | PMBUS_HAVE_FAN12 | PMBUS_HAVE_STATUS_FAN12, -}; + }; -static int ds1200_probe(struct i2c_client *client, - const struct i2c_device_id *id) -{ + static int ds1200_probe(struct i2c_client *client, + const struct i2c_device_id *id) + { return pmbus_do_probe(client, id, &ds1200_info); -} + } -static int ds1200_remove(struct i2c_client *client) -{ + static int ds1200_remove(struct i2c_client *client) + { return pmbus_do_remove(client); -} + } -static const struct i2c_device_id ds1200_id[] = { + static const struct i2c_device_id ds1200_id[] = { {"ds1200", 0}, {} -}; + }; -MODULE_DEVICE_TABLE(i2c, ds1200_id); + MODULE_DEVICE_TABLE(i2c, ds1200_id); -/* This is the driver that will be inserted */ -static struct i2c_driver ds1200_driver = { + /* This is the driver that will be inserted */ + static struct i2c_driver ds1200_driver = { .driver = { .name = "ds1200", }, .probe = ds1200_probe, .remove = ds1200_remove, .id_table = ds1200_id, -}; + }; -static int __init ds1200_init(void) -{ + static int __init ds1200_init(void) + { return i2c_add_driver(&ds1200_driver); -} + } -static void __exit ds1200_exit(void) -{ + static void __exit ds1200_exit(void) + { i2c_del_driver(&ds1200_driver); -} + } Sysfs entries @@ -148,6 +184,7 @@ a given sysfs entry. The following attributes are supported. Limits are read-write; all other attributes are read-only. +======================= ======================================================== inX_input Measured voltage. From READ_VIN or READ_VOUT register. inX_min Minimum Voltage. From VIN_UV_WARN_LIMIT or VOUT_UV_WARN_LIMIT register. @@ -214,3 +251,4 @@ tempX_lcrit_alarm Chip temperature critical low alarm. Set by comparing tempX_crit_alarm Chip temperature critical high alarm. Set by comparing READ_TEMPERATURE_X with OT_FAULT_LIMIT if TEMP_OT_FAULT status is set. +======================= ======================================================== diff --git a/Documentation/hwmon/pmbus-core b/Documentation/hwmon/pmbus-core index 8ed10e9ddfb5..92515c446fe3 100644 --- a/Documentation/hwmon/pmbus-core +++ b/Documentation/hwmon/pmbus-core @@ -1,3 +1,4 @@ +================================== PMBus core driver and internal API ================================== @@ -120,24 +121,24 @@ Specifically, it provides the following information. non-standard PMBus commands to standard commands, or to augment standard command return values with device specific information. - API functions - ------------- +API functions +============= - Functions provided by chip driver - --------------------------------- +Functions provided by chip driver +--------------------------------- - All functions return the command return value (read) or zero (write) if - successful. A return value of -ENODATA indicates that there is no manufacturer - specific command, but that a standard PMBus command may exist. Any other - negative return value indicates that the commands does not exist for this - chip, and that no attempt should be made to read or write the standard - command. +All functions return the command return value (read) or zero (write) if +successful. A return value of -ENODATA indicates that there is no manufacturer +specific command, but that a standard PMBus command may exist. Any other +negative return value indicates that the commands does not exist for this +chip, and that no attempt should be made to read or write the standard +command. - As mentioned above, an exception to this rule applies to virtual commands, - which _must_ be handled in driver specific code. See "Virtual PMBus Commands" - above for more details. +As mentioned above, an exception to this rule applies to virtual commands, +which *must* be handled in driver specific code. See "Virtual PMBus Commands" +above for more details. - Command execution in the core PMBus driver code is as follows. +Command execution in the core PMBus driver code is as follows:: if (chip_access_function) { status = chip_access_function(); @@ -148,128 +149,160 @@ Specifically, it provides the following information. return -EINVAL; return generic_access(); - Chip drivers may provide pointers to the following functions in struct - pmbus_driver_info. All functions are optional. +Chip drivers may provide pointers to the following functions in struct +pmbus_driver_info. All functions are optional. + +:: int (*read_byte_data)(struct i2c_client *client, int page, int reg); - Read byte from page , register . - may be -1, which means "current page". +Read byte from page , register . + may be -1, which means "current page". + + +:: int (*read_word_data)(struct i2c_client *client, int page, int reg); - Read word from page , register . +Read word from page , register . + +:: int (*write_word_data)(struct i2c_client *client, int page, int reg, - u16 word); + u16 word); - Write word to page , register . +Write word to page , register . + +:: int (*write_byte)(struct i2c_client *client, int page, u8 value); - Write byte to page , register . - may be -1, which means "current page". +Write byte to page , register . + may be -1, which means "current page". + +:: int (*identify)(struct i2c_client *client, struct pmbus_driver_info *info); - Determine supported PMBus functionality. This function is only necessary - if a chip driver supports multiple chips, and the chip functionality is not - pre-determined. It is currently only used by the generic pmbus driver - (pmbus.c). +Determine supported PMBus functionality. This function is only necessary +if a chip driver supports multiple chips, and the chip functionality is not +pre-determined. It is currently only used by the generic pmbus driver +(pmbus.c). + +Functions exported by core driver +--------------------------------- - Functions exported by core driver - --------------------------------- +Chip drivers are expected to use the following functions to read or write +PMBus registers. Chip drivers may also use direct I2C commands. If direct I2C +commands are used, the chip driver code must not directly modify the current +page, since the selected page is cached in the core driver and the core driver +will assume that it is selected. Using pmbus_set_page() to select a new page +is mandatory. - Chip drivers are expected to use the following functions to read or write - PMBus registers. Chip drivers may also use direct I2C commands. If direct I2C - commands are used, the chip driver code must not directly modify the current - page, since the selected page is cached in the core driver and the core driver - will assume that it is selected. Using pmbus_set_page() to select a new page - is mandatory. +:: int pmbus_set_page(struct i2c_client *client, u8 page); - Set PMBus page register to for subsequent commands. +Set PMBus page register to for subsequent commands. + +:: int pmbus_read_word_data(struct i2c_client *client, u8 page, u8 reg); - Read word data from , . Similar to i2c_smbus_read_word_data(), but - selects page first. +Read word data from , . Similar to i2c_smbus_read_word_data(), but +selects page first. + +:: int pmbus_write_word_data(struct i2c_client *client, u8 page, u8 reg, u16 word); - Write word data to , . Similar to i2c_smbus_write_word_data(), but - selects page first. +Write word data to , . Similar to i2c_smbus_write_word_data(), but +selects page first. + +:: int pmbus_read_byte_data(struct i2c_client *client, int page, u8 reg); - Read byte data from , . Similar to i2c_smbus_read_byte_data(), but - selects page first. may be -1, which means "current page". +Read byte data from , . Similar to i2c_smbus_read_byte_data(), but +selects page first. may be -1, which means "current page". + +:: int pmbus_write_byte(struct i2c_client *client, int page, u8 value); - Write byte data to , . Similar to i2c_smbus_write_byte(), but - selects page first. may be -1, which means "current page". +Write byte data to , . Similar to i2c_smbus_write_byte(), but +selects page first. may be -1, which means "current page". + +:: void pmbus_clear_faults(struct i2c_client *client); - Execute PMBus "Clear Fault" command on all chip pages. - This function calls the device specific write_byte function if defined. - Therefore, it must _not_ be called from that function. +Execute PMBus "Clear Fault" command on all chip pages. +This function calls the device specific write_byte function if defined. +Therefore, it must _not_ be called from that function. + +:: bool pmbus_check_byte_register(struct i2c_client *client, int page, int reg); - Check if byte register exists. Return true if the register exists, false - otherwise. - This function calls the device specific write_byte function if defined to - obtain the chip status. Therefore, it must _not_ be called from that function. +Check if byte register exists. Return true if the register exists, false +otherwise. +This function calls the device specific write_byte function if defined to +obtain the chip status. Therefore, it must _not_ be called from that function. + +:: bool pmbus_check_word_register(struct i2c_client *client, int page, int reg); - Check if word register exists. Return true if the register exists, false - otherwise. - This function calls the device specific write_byte function if defined to - obtain the chip status. Therefore, it must _not_ be called from that function. +Check if word register exists. Return true if the register exists, false +otherwise. +This function calls the device specific write_byte function if defined to +obtain the chip status. Therefore, it must _not_ be called from that function. + +:: int pmbus_do_probe(struct i2c_client *client, const struct i2c_device_id *id, - struct pmbus_driver_info *info); + struct pmbus_driver_info *info); + +Execute probe function. Similar to standard probe function for other drivers, +with the pointer to struct pmbus_driver_info as additional argument. Calls +identify function if supported. Must only be called from device probe +function. - Execute probe function. Similar to standard probe function for other drivers, - with the pointer to struct pmbus_driver_info as additional argument. Calls - identify function if supported. Must only be called from device probe - function. +:: void pmbus_do_remove(struct i2c_client *client); - Execute driver remove function. Similar to standard driver remove function. +Execute driver remove function. Similar to standard driver remove function. + +:: const struct pmbus_driver_info *pmbus_get_driver_info(struct i2c_client *client); - Return pointer to struct pmbus_driver_info as passed to pmbus_do_probe(). +Return pointer to struct pmbus_driver_info as passed to pmbus_do_probe(). PMBus driver platform data ========================== PMBus platform data is defined in include/linux/pmbus.h. Platform data -currently only provides a flag field with a single bit used. +currently only provides a flag field with a single bit used:: -#define PMBUS_SKIP_STATUS_CHECK (1 << 0) + #define PMBUS_SKIP_STATUS_CHECK (1 << 0) -struct pmbus_platform_data { - u32 flags; /* Device specific flags */ -}; + struct pmbus_platform_data { + u32 flags; /* Device specific flags */ + }; Flags ----- PMBUS_SKIP_STATUS_CHECK - -During register detection, skip checking the status register for -communication or command errors. + During register detection, skip checking the status register for + communication or command errors. Some PMBus chips respond with valid data when trying to read an unsupported register. For such chips, checking the status register is mandatory when diff --git a/Documentation/hwmon/tps40422 b/Documentation/hwmon/tps40422 index 24bb0688d515..359751eb5ed4 100644 --- a/Documentation/hwmon/tps40422 +++ b/Documentation/hwmon/tps40422 @@ -2,9 +2,13 @@ Kernel driver tps40422 ====================== Supported chips: + * TI TPS40422 + Prefix: 'tps40422' + Addresses scanned: - + Datasheet: http://www.ti.com/lit/gpn/tps40422 Author: Zhu Laiwen @@ -39,6 +43,7 @@ Sysfs entries The following attributes are supported. +======================= ======================================================= in[1-2]_label "vout[1-2]" in[1-2]_input Measured voltage. From READ_VOUT register. in[1-2]_alarm voltage alarm. @@ -46,19 +51,23 @@ in[1-2]_alarm voltage alarm. curr[1-2]_input Measured current. From READ_IOUT register. curr[1-2]_label "iout[1-2]" curr1_max Maximum current. From IOUT_OC_WARN_LIMIT register. -curr1_crit Critical maximum current. From IOUT_OC_FAULT_LIMIT register. +curr1_crit Critical maximum current. From IOUT_OC_FAULT_LIMIT + register. curr1_max_alarm Current high alarm. From IOUT_OC_WARN_LIMIT status. curr1_crit_alarm Current critical high alarm. From IOUT_OC_FAULT status. curr2_alarm Current high alarm. From IOUT_OC_WARNING status. -temp1_input Measured temperature. From READ_TEMPERATURE_2 register on page 0. +temp1_input Measured temperature. From READ_TEMPERATURE_2 register + on page 0. temp1_max Maximum temperature. From OT_WARN_LIMIT register. temp1_crit Critical high temperature. From OT_FAULT_LIMIT register. temp1_max_alarm Chip temperature high alarm. Set by comparing - READ_TEMPERATURE_2 on page 0 with OT_WARN_LIMIT if TEMP_OT_WARNING - status is set. + READ_TEMPERATURE_2 on page 0 with OT_WARN_LIMIT if + TEMP_OT_WARNING status is set. temp1_crit_alarm Chip temperature critical high alarm. Set by comparing - READ_TEMPERATURE_2 on page 0 with OT_FAULT_LIMIT if TEMP_OT_FAULT - status is set. -temp2_input Measured temperature. From READ_TEMPERATURE_2 register on page 1. + READ_TEMPERATURE_2 on page 0 with OT_FAULT_LIMIT if + TEMP_OT_FAULT status is set. +temp2_input Measured temperature. From READ_TEMPERATURE_2 register + on page 1. temp2_alarm Chip temperature alarm on page 1. +======================= ======================================================= diff --git a/Documentation/hwmon/ucd9000 b/Documentation/hwmon/ucd9000 index 262e713e60ff..d69061b7312c 100644 --- a/Documentation/hwmon/ucd9000 +++ b/Documentation/hwmon/ucd9000 @@ -2,15 +2,20 @@ Kernel driver ucd9000 ===================== Supported chips: + * TI UCD90120, UCD90124, UCD90160, UCD9090, and UCD90910 + Prefixes: 'ucd90120', 'ucd90124', 'ucd90160', 'ucd9090', 'ucd90910' + Addresses scanned: - + Datasheets: - http://focus.ti.com/lit/ds/symlink/ucd90120.pdf - http://focus.ti.com/lit/ds/symlink/ucd90124.pdf - http://focus.ti.com/lit/ds/symlink/ucd90160.pdf - http://focus.ti.com/lit/ds/symlink/ucd9090.pdf - http://focus.ti.com/lit/ds/symlink/ucd90910.pdf + + - http://focus.ti.com/lit/ds/symlink/ucd90120.pdf + - http://focus.ti.com/lit/ds/symlink/ucd90124.pdf + - http://focus.ti.com/lit/ds/symlink/ucd90160.pdf + - http://focus.ti.com/lit/ds/symlink/ucd9090.pdf + - http://focus.ti.com/lit/ds/symlink/ucd90910.pdf Author: Guenter Roeck @@ -76,23 +81,28 @@ Sysfs entries The following attributes are supported. Limits are read-write; all other attributes are read-only. +======================= ======================================================== in[1-12]_label "vout[1-12]". in[1-12]_input Measured voltage. From READ_VOUT register. in[1-12]_min Minimum Voltage. From VOUT_UV_WARN_LIMIT register. in[1-12]_max Maximum voltage. From VOUT_OV_WARN_LIMIT register. in[1-12]_lcrit Critical minimum Voltage. VOUT_UV_FAULT_LIMIT register. -in[1-12]_crit Critical maximum voltage. From VOUT_OV_FAULT_LIMIT register. +in[1-12]_crit Critical maximum voltage. From VOUT_OV_FAULT_LIMIT + register. in[1-12]_min_alarm Voltage low alarm. From VOLTAGE_UV_WARNING status. in[1-12]_max_alarm Voltage high alarm. From VOLTAGE_OV_WARNING status. -in[1-12]_lcrit_alarm Voltage critical low alarm. From VOLTAGE_UV_FAULT status. -in[1-12]_crit_alarm Voltage critical high alarm. From VOLTAGE_OV_FAULT status. +in[1-12]_lcrit_alarm Voltage critical low alarm. From VOLTAGE_UV_FAULT + status. +in[1-12]_crit_alarm Voltage critical high alarm. From VOLTAGE_OV_FAULT + status. curr[1-12]_label "iout[1-12]". curr[1-12]_input Measured current. From READ_IOUT register. curr[1-12]_max Maximum current. From IOUT_OC_WARN_LIMIT register. -curr[1-12]_lcrit Critical minimum output current. From IOUT_UC_FAULT_LIMIT +curr[1-12]_lcrit Critical minimum output current. From + IOUT_UC_FAULT_LIMIT register. +curr[1-12]_crit Critical maximum current. From IOUT_OC_FAULT_LIMIT register. -curr[1-12]_crit Critical maximum current. From IOUT_OC_FAULT_LIMIT register. curr[1-12]_max_alarm Current high alarm. From IOUT_OC_WARNING status. curr[1-12]_crit_alarm Current critical high alarm. From IOUT_OC_FAULT status. @@ -116,3 +126,4 @@ fan[1-4]_fault Fan fault. created only for enabled fans. Note that even though UCD90910 supports up to 10 fans, only up to four fans are currently supported. +======================= ======================================================== diff --git a/Documentation/hwmon/ucd9200 b/Documentation/hwmon/ucd9200 index 1e8060e631bd..44eda4a579b6 100644 --- a/Documentation/hwmon/ucd9200 +++ b/Documentation/hwmon/ucd9200 @@ -2,18 +2,23 @@ Kernel driver ucd9200 ===================== Supported chips: + * TI UCD9220, UCD9222, UCD9224, UCD9240, UCD9244, UCD9246, and UCD9248 + Prefixes: 'ucd9220', 'ucd9222', 'ucd9224', 'ucd9240', 'ucd9244', 'ucd9246', - 'ucd9248' + 'ucd9248' + Addresses scanned: - + Datasheets: - http://focus.ti.com/lit/ds/symlink/ucd9220.pdf - http://focus.ti.com/lit/ds/symlink/ucd9222.pdf - http://focus.ti.com/lit/ds/symlink/ucd9224.pdf - http://focus.ti.com/lit/ds/symlink/ucd9240.pdf - http://focus.ti.com/lit/ds/symlink/ucd9244.pdf - http://focus.ti.com/lit/ds/symlink/ucd9246.pdf - http://focus.ti.com/lit/ds/symlink/ucd9248.pdf + + - http://focus.ti.com/lit/ds/symlink/ucd9220.pdf + - http://focus.ti.com/lit/ds/symlink/ucd9222.pdf + - http://focus.ti.com/lit/ds/symlink/ucd9224.pdf + - http://focus.ti.com/lit/ds/symlink/ucd9240.pdf + - http://focus.ti.com/lit/ds/symlink/ucd9244.pdf + - http://focus.ti.com/lit/ds/symlink/ucd9246.pdf + - http://focus.ti.com/lit/ds/symlink/ucd9248.pdf Author: Guenter Roeck @@ -52,12 +57,14 @@ Sysfs entries The following attributes are supported. Limits are read-write; all other attributes are read-only. +======================= ======================================================== in1_label "vin". in1_input Measured voltage. From READ_VIN register. in1_min Minimum Voltage. From VIN_UV_WARN_LIMIT register. in1_max Maximum voltage. From VIN_OV_WARN_LIMIT register. in1_lcrit Critical minimum Voltage. VIN_UV_FAULT_LIMIT register. -in1_crit Critical maximum voltage. From VIN_OV_FAULT_LIMIT register. +in1_crit Critical maximum voltage. From VIN_OV_FAULT_LIMIT + register. in1_min_alarm Voltage low alarm. From VIN_UV_WARNING status. in1_max_alarm Voltage high alarm. From VIN_OV_WARNING status. in1_lcrit_alarm Voltage critical low alarm. From VIN_UV_FAULT status. @@ -68,11 +75,14 @@ in[2-5]_input Measured voltage. From READ_VOUT register. in[2-5]_min Minimum Voltage. From VOUT_UV_WARN_LIMIT register. in[2-5]_max Maximum voltage. From VOUT_OV_WARN_LIMIT register. in[2-5]_lcrit Critical minimum Voltage. VOUT_UV_FAULT_LIMIT register. -in[2-5]_crit Critical maximum voltage. From VOUT_OV_FAULT_LIMIT register. +in[2-5]_crit Critical maximum voltage. From VOUT_OV_FAULT_LIMIT + register. in[2-5]_min_alarm Voltage low alarm. From VOLTAGE_UV_WARNING status. in[2-5]_max_alarm Voltage high alarm. From VOLTAGE_OV_WARNING status. -in[2-5]_lcrit_alarm Voltage critical low alarm. From VOLTAGE_UV_FAULT status. -in[2-5]_crit_alarm Voltage critical high alarm. From VOLTAGE_OV_FAULT status. +in[2-5]_lcrit_alarm Voltage critical low alarm. From VOLTAGE_UV_FAULT + status. +in[2-5]_crit_alarm Voltage critical high alarm. From VOLTAGE_OV_FAULT + status. curr1_label "iin". curr1_input Measured current. From READ_IIN register. @@ -80,9 +90,10 @@ curr1_input Measured current. From READ_IIN register. curr[2-5]_label "iout[1-4]". curr[2-5]_input Measured current. From READ_IOUT register. curr[2-5]_max Maximum current. From IOUT_OC_WARN_LIMIT register. -curr[2-5]_lcrit Critical minimum output current. From IOUT_UC_FAULT_LIMIT +curr[2-5]_lcrit Critical minimum output current. From + IOUT_UC_FAULT_LIMIT register. +curr[2-5]_crit Critical maximum current. From IOUT_OC_FAULT_LIMIT register. -curr[2-5]_crit Critical maximum current. From IOUT_OC_FAULT_LIMIT register. curr[2-5]_max_alarm Current high alarm. From IOUT_OC_WARNING status. curr[2-5]_crit_alarm Current critical high alarm. From IOUT_OC_FAULT status. @@ -97,7 +108,7 @@ power[2-5]_label "pout[1-4]" rails. See chip datasheets for details. temp[1-5]_input Measured temperatures. From READ_TEMPERATURE_1 and - READ_TEMPERATURE_2 registers. + READ_TEMPERATURE_2 registers. temp1 is the chip internal temperature. temp[2-5] are rail temperatures. temp[2-5] attributes are only created for enabled rails. See chip datasheets for @@ -110,3 +121,4 @@ temp[1-5]_crit_alarm Temperature critical high alarm. fan1_input Fan RPM. ucd9240 only. fan1_alarm Fan alarm. ucd9240 only. fan1_fault Fan fault. ucd9240 only. +======================= ======================================================== diff --git a/Documentation/hwmon/zl6100 b/Documentation/hwmon/zl6100 index 477a94b131ae..4029970bace4 100644 --- a/Documentation/hwmon/zl6100 +++ b/Documentation/hwmon/zl6100 @@ -2,57 +2,106 @@ Kernel driver zl6100 ==================== Supported chips: + * Intersil / Zilker Labs ZL2004 + Prefix: 'zl2004' + Addresses scanned: - + Datasheet: http://www.intersil.com/data/fn/fn6847.pdf + * Intersil / Zilker Labs ZL2005 + Prefix: 'zl2005' + Addresses scanned: - + Datasheet: http://www.intersil.com/data/fn/fn6848.pdf + * Intersil / Zilker Labs ZL2006 + Prefix: 'zl2006' + Addresses scanned: - + Datasheet: http://www.intersil.com/data/fn/fn6850.pdf + * Intersil / Zilker Labs ZL2008 + Prefix: 'zl2008' + Addresses scanned: - + Datasheet: http://www.intersil.com/data/fn/fn6859.pdf + * Intersil / Zilker Labs ZL2105 + Prefix: 'zl2105' + Addresses scanned: - + Datasheet: http://www.intersil.com/data/fn/fn6851.pdf + * Intersil / Zilker Labs ZL2106 + Prefix: 'zl2106' + Addresses scanned: - + Datasheet: http://www.intersil.com/data/fn/fn6852.pdf + * Intersil / Zilker Labs ZL6100 + Prefix: 'zl6100' + Addresses scanned: - + Datasheet: http://www.intersil.com/data/fn/fn6876.pdf + * Intersil / Zilker Labs ZL6105 + Prefix: 'zl6105' + Addresses scanned: - + Datasheet: http://www.intersil.com/data/fn/fn6906.pdf + * Intersil / Zilker Labs ZL9101M + Prefix: 'zl9101' + Addresses scanned: - + Datasheet: http://www.intersil.com/data/fn/fn7669.pdf + * Intersil / Zilker Labs ZL9117M + Prefix: 'zl9117' + Addresses scanned: - + Datasheet: http://www.intersil.com/data/fn/fn7914.pdf + * Ericsson BMR450, BMR451 + Prefix: 'bmr450', 'bmr451' + Addresses scanned: - + Datasheet: + http://archive.ericsson.net/service/internet/picov/get?DocNo=28701-EN/LZT146401 + * Ericsson BMR462, BMR463, BMR464 + Prefixes: 'bmr462', 'bmr463', 'bmr464' + Addresses scanned: - + Datasheet: -http://archive.ericsson.net/service/internet/picov/get?DocNo=28701-EN/LZT146256 + http://archive.ericsson.net/service/internet/picov/get?DocNo=28701-EN/LZT146256 Author: Guenter Roeck @@ -75,13 +124,15 @@ This driver does not auto-detect devices. You will have to instantiate the devices explicitly. Please see Documentation/i2c/instantiating-devices for details. -WARNING: Do not access chip registers using the i2cdump command, and do not use -any of the i2ctools commands on a command register used to save and restore -configuration data (0x11, 0x12, 0x15, 0x16, and 0xf4). The chips supported by -this driver interpret any access to those command registers (including read -commands) as request to execute the command in question. Unless write accesses -to those registers are protected, this may result in power loss, board resets, -and/or Flash corruption. Worst case, your board may turn into a brick. +.. warning:: + + Do not access chip registers using the i2cdump command, and do not use + any of the i2ctools commands on a command register used to save and restore + configuration data (0x11, 0x12, 0x15, 0x16, and 0xf4). The chips supported by + this driver interpret any access to those command registers (including read + commands) as request to execute the command in question. Unless write accesses + to those registers are protected, this may result in power loss, board resets, + and/or Flash corruption. Worst case, your board may turn into a brick. Platform data support @@ -110,6 +161,7 @@ Sysfs entries The following attributes are supported. Limits are read-write; all other attributes are read-only. +======================= ======================================================== in1_label "vin" in1_input Measured input voltage. in1_min Minimum input voltage. @@ -158,3 +210,4 @@ temp[12]_min_alarm Chip temperature low alarm. temp[12]_max_alarm Chip temperature high alarm. temp[12]_lcrit_alarm Chip temperature critical low alarm. temp[12]_crit_alarm Chip temperature critical high alarm. +======================= ======================================================== -- cgit v1.2.3 From b32570a4f0919569bcba13a5419ea97ca5c1d3cf Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 17 Apr 2019 06:46:27 -0300 Subject: docs: hwmon: misc files: convert to ReST format Convert other files maintained by Guenter to ReST format, in order to allow them to be parsed by Sphinx. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Guenter Roeck --- Documentation/hwmon/ina209 | 18 ++++--- Documentation/hwmon/ina2xx | 39 ++++++++++++--- Documentation/hwmon/jc42 | 55 +++++++++++++++++++-- Documentation/hwmon/lm95234 | 11 ++++- Documentation/hwmon/ltc4261 | 16 ++++-- Documentation/hwmon/max16065 | 24 ++++++++- Documentation/hwmon/max6697 | 33 +++++++++++++ Documentation/hwmon/nct6775 | 114 ++++++++++++++++++++++++++++++++++--------- Documentation/hwmon/smm665 | 42 +++++++++++++--- Documentation/hwmon/tmp401 | 30 +++++++++++- 10 files changed, 328 insertions(+), 54 deletions(-) (limited to 'Documentation') diff --git a/Documentation/hwmon/ina209 b/Documentation/hwmon/ina209 index 672501de4509..64322075a145 100644 --- a/Documentation/hwmon/ina209 +++ b/Documentation/hwmon/ina209 @@ -1,16 +1,21 @@ Kernel driver ina209 -===================== +==================== Supported chips: + * Burr-Brown / Texas Instruments INA209 + Prefix: 'ina209' + Addresses scanned: - + Datasheet: - http://www.ti.com/lit/gpn/ina209 + http://www.ti.com/lit/gpn/ina209 -Author: Paul Hays -Author: Ira W. Snyder -Author: Guenter Roeck +Author: + - Paul Hays + - Ira W. Snyder + - Guenter Roeck Description @@ -31,7 +36,7 @@ the I2C bus. See the datasheet for details. This tries to expose most monitoring features of the hardware via sysfs. It does not support every feature of this chip. - +======================= ======================================================= in0_input shunt voltage (mV) in0_input_highest shunt voltage historical maximum reading (mV) in0_input_lowest shunt voltage historical minimum reading (mV) @@ -70,6 +75,7 @@ curr1_input current measurement (mA) update_interval data conversion time; affects number of samples used to average results for shunt and bus voltages. +======================= ======================================================= General Remarks --------------- diff --git a/Documentation/hwmon/ina2xx b/Documentation/hwmon/ina2xx index 0f36c021192d..95badf9c396f 100644 --- a/Documentation/hwmon/ina2xx +++ b/Documentation/hwmon/ina2xx @@ -2,35 +2,56 @@ Kernel driver ina2xx ==================== Supported chips: + * Texas Instruments INA219 + + Prefix: 'ina219' Addresses: I2C 0x40 - 0x4f + Datasheet: Publicly available at the Texas Instruments website - http://www.ti.com/ + + http://www.ti.com/ * Texas Instruments INA220 + Prefix: 'ina220' + Addresses: I2C 0x40 - 0x4f + Datasheet: Publicly available at the Texas Instruments website - http://www.ti.com/ + + http://www.ti.com/ * Texas Instruments INA226 + Prefix: 'ina226' + Addresses: I2C 0x40 - 0x4f + Datasheet: Publicly available at the Texas Instruments website - http://www.ti.com/ + + http://www.ti.com/ * Texas Instruments INA230 + Prefix: 'ina230' + Addresses: I2C 0x40 - 0x4f + Datasheet: Publicly available at the Texas Instruments website - http://www.ti.com/ + + http://www.ti.com/ * Texas Instruments INA231 + Prefix: 'ina231' + Addresses: I2C 0x40 - 0x4f + Datasheet: Publicly available at the Texas Instruments website - http://www.ti.com/ + + http://www.ti.com/ Author: Lothar Felten @@ -64,16 +85,20 @@ lower limit of the update_interval is 2 ms, the upper limit is 2253 ms. The actual programmed interval may vary from the desired value. General sysfs entries -------------- +--------------------- +======================= =============================== in0_input Shunt voltage(mV) channel in1_input Bus voltage(mV) channel curr1_input Current(mA) measurement channel power1_input Power(uW) measurement channel shunt_resistor Shunt resistance(uOhm) channel +======================= =============================== Sysfs entries for ina226, ina230 and ina231 only -------------- +------------------------------------------------ +======================= ==================================================== update_interval data conversion time; affects number of samples used to average results for shunt and bus voltages. +======================= ==================================================== diff --git a/Documentation/hwmon/jc42 b/Documentation/hwmon/jc42 index b4b671f22453..5b14b49bb6f7 100644 --- a/Documentation/hwmon/jc42 +++ b/Documentation/hwmon/jc42 @@ -2,53 +2,100 @@ Kernel driver jc42 ================== Supported chips: + * Analog Devices ADT7408 + Datasheets: + http://www.analog.com/static/imported-files/data_sheets/ADT7408.pdf + * Atmel AT30TS00, AT30TS002A/B, AT30TSE004A + Datasheets: + http://www.atmel.com/Images/doc8585.pdf + http://www.atmel.com/Images/doc8711.pdf + http://www.atmel.com/Images/Atmel-8852-SEEPROM-AT30TSE002A-Datasheet.pdf + http://www.atmel.com/Images/Atmel-8868-DTS-AT30TSE004A-Datasheet.pdf + * IDT TSE2002B3, TSE2002GB2, TSE2004GB2, TS3000B3, TS3000GB0, TS3000GB2, + TS3001GB2 + Datasheets: + Available from IDT web site + * Maxim MAX6604 + Datasheets: + http://datasheets.maxim-ic.com/en/ds/MAX6604.pdf + * Microchip MCP9804, MCP9805, MCP9808, MCP98242, MCP98243, MCP98244, MCP9843 + Datasheets: + http://ww1.microchip.com/downloads/en/DeviceDoc/22203C.pdf + http://ww1.microchip.com/downloads/en/DeviceDoc/21977b.pdf + http://ww1.microchip.com/downloads/en/DeviceDoc/25095A.pdf + http://ww1.microchip.com/downloads/en/DeviceDoc/21996a.pdf + http://ww1.microchip.com/downloads/en/DeviceDoc/22153c.pdf + http://ww1.microchip.com/downloads/en/DeviceDoc/22327A.pdf + * NXP Semiconductors SE97, SE97B, SE98, SE98A + Datasheets: + http://www.nxp.com/documents/data_sheet/SE97.pdf + http://www.nxp.com/documents/data_sheet/SE97B.pdf + http://www.nxp.com/documents/data_sheet/SE98.pdf + http://www.nxp.com/documents/data_sheet/SE98A.pdf + * ON Semiconductor CAT34TS02, CAT6095 + Datasheet: + http://www.onsemi.com/pub_link/Collateral/CAT34TS02-D.PDF + http://www.onsemi.com/pub/Collateral/CAT6095-D.PDF + * ST Microelectronics STTS424, STTS424E02, STTS2002, STTS2004, STTS3000 + Datasheets: + http://www.st.com/web/en/resource/technical/document/datasheet/CD00157556.pdf + http://www.st.com/web/en/resource/technical/document/datasheet/CD00157558.pdf + http://www.st.com/web/en/resource/technical/document/datasheet/CD00266638.pdf + http://www.st.com/web/en/resource/technical/document/datasheet/CD00225278.pdf + http://www.st.com/web/en/resource/technical/document/datasheet/DM00076709.pdf + * JEDEC JC 42.4 compliant temperature sensor chips + Datasheet: + http://www.jedec.org/sites/default/files/docs/4_01_04R19.pdf + Common for all chips: + Prefix: 'jc42' + Addresses scanned: I2C 0x18 - 0x1f Author: @@ -67,10 +114,10 @@ The driver auto-detects the chips listed above, but can be manually instantiated to support other JC 42.4 compliant chips. Example: the following will load the driver for a generic JC 42.4 compliant -temperature sensor at address 0x18 on I2C bus #1: +temperature sensor at address 0x18 on I2C bus #1:: -# modprobe jc42 -# echo jc42 0x18 > /sys/bus/i2c/devices/i2c-1/new_device + # modprobe jc42 + # echo jc42 0x18 > /sys/bus/i2c/devices/i2c-1/new_device A JC 42.4 compliant chip supports a single temperature sensor. Minimum, maximum, and critical temperature can be configured. There are alarms for high, low, @@ -90,6 +137,7 @@ cannot be changed. Sysfs entries ------------- +======================= =========================================== temp1_input Temperature (RO) temp1_min Minimum temperature (RO or RW) temp1_max Maximum temperature (RO or RW) @@ -101,3 +149,4 @@ temp1_max_hyst Maximum hysteresis temperature (RO) temp1_min_alarm Temperature low alarm temp1_max_alarm Temperature high alarm temp1_crit_alarm Temperature critical alarm +======================= =========================================== diff --git a/Documentation/hwmon/lm95234 b/Documentation/hwmon/lm95234 index 32b777ef224c..e4c14bea5efd 100644 --- a/Documentation/hwmon/lm95234 +++ b/Documentation/hwmon/lm95234 @@ -2,15 +2,22 @@ Kernel driver lm95234 ===================== Supported chips: + * National Semiconductor / Texas Instruments LM95233 + Addresses scanned: I2C 0x18, 0x2a, 0x2b + Datasheet: Publicly available at the Texas Instruments website - http://www.ti.com/product/lm95233 + + http://www.ti.com/product/lm95233 + * National Semiconductor / Texas Instruments LM95234 + Addresses scanned: I2C 0x18, 0x4d, 0x4e + Datasheet: Publicly available at the Texas Instruments website - http://www.ti.com/product/lm95234 + http://www.ti.com/product/lm95234 Author: Guenter Roeck diff --git a/Documentation/hwmon/ltc4261 b/Documentation/hwmon/ltc4261 index 9378a75c6134..c80233f8082e 100644 --- a/Documentation/hwmon/ltc4261 +++ b/Documentation/hwmon/ltc4261 @@ -2,11 +2,16 @@ Kernel driver ltc4261 ===================== Supported chips: + * Linear Technology LTC4261 + Prefix: 'ltc4261' + Addresses scanned: - + Datasheet: - http://cds.linear.com/docs/Datasheet/42612fb.pdf + + http://cds.linear.com/docs/Datasheet/42612fb.pdf Author: Guenter Roeck @@ -26,9 +31,10 @@ which can be safely used to identify the chip. You will have to instantiate the devices explicitly. Example: the following will load the driver for an LTC4261 at address 0x10 -on I2C bus #1: -$ modprobe ltc4261 -$ echo ltc4261 0x10 > /sys/bus/i2c/devices/i2c-1/new_device +on I2C bus #1:: + + $ modprobe ltc4261 + $ echo ltc4261 0x10 > /sys/bus/i2c/devices/i2c-1/new_device Sysfs entries @@ -51,6 +57,7 @@ the proximity of the ADIN2 pin to the OV pin. ADIN2 is, however, not available on all chip variants. To ensure that the alarm condition is reported to the user, report it with both voltage sensors. +======================= ============================= in1_input ADIN2 voltage (mV) in1_min_alarm ADIN/ADIN2 Undervoltage alarm in1_max_alarm ADIN/ADIN2 Overvoltage alarm @@ -61,3 +68,4 @@ in2_max_alarm ADIN/ADIN2 Overvoltage alarm curr1_input SENSE current (mA) curr1_alarm SENSE overcurrent alarm +======================= ============================= diff --git a/Documentation/hwmon/max16065 b/Documentation/hwmon/max16065 index 208a29e43010..fa5c852a178c 100644 --- a/Documentation/hwmon/max16065 +++ b/Documentation/hwmon/max16065 @@ -1,28 +1,48 @@ Kernel driver max16065 ====================== + Supported chips: + * Maxim MAX16065, MAX16066 + Prefixes: 'max16065', 'max16066' + Addresses scanned: - + Datasheet: + http://datasheets.maxim-ic.com/en/ds/MAX16065-MAX16066.pdf + * Maxim MAX16067 + Prefix: 'max16067' + Addresses scanned: - + Datasheet: + http://datasheets.maxim-ic.com/en/ds/MAX16067.pdf + * Maxim MAX16068 + Prefix: 'max16068' + Addresses scanned: - + Datasheet: + http://datasheets.maxim-ic.com/en/ds/MAX16068.pdf + * Maxim MAX16070/MAX16071 + Prefixes: 'max16070', 'max16071' + Addresses scanned: - + Datasheet: - http://datasheets.maxim-ic.com/en/ds/MAX16070-MAX16071.pdf + http://datasheets.maxim-ic.com/en/ds/MAX16070-MAX16071.pdf Author: Guenter Roeck @@ -73,6 +93,7 @@ turn into a brick. Sysfs entries ------------- +======================= ======================================================== in[0-11]_input Input voltage measurements. in12_input Voltage on CSP (Current Sense Positive) pin. @@ -103,3 +124,4 @@ curr1_input Current sense input; only if the chip supports current curr1_alarm Overcurrent alarm; only if the chip supports current sensing and if current sensing is enabled. +======================= ======================================================== diff --git a/Documentation/hwmon/max6697 b/Documentation/hwmon/max6697 index 6594177ededa..ffc5a7d8d33b 100644 --- a/Documentation/hwmon/max6697 +++ b/Documentation/hwmon/max6697 @@ -2,38 +2,69 @@ Kernel driver max6697 ===================== Supported chips: + * Maxim MAX6581 + Prefix: 'max6581' + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6581.pdf + * Maxim MAX6602 + Prefix: 'max6602' + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6602.pdf + * Maxim MAX6622 + Prefix: 'max6622' + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6622.pdf + * Maxim MAX6636 + Prefix: 'max6636' + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6636.pdf + * Maxim MAX6689 + Prefix: 'max6689' + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6689.pdf + * Maxim MAX6693 + Prefix: 'max6693' + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6693.pdf + * Maxim MAX6694 + Prefix: 'max6694' + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6694.pdf + * Maxim MAX6697 + Prefix: 'max6697' + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6697.pdf + * Maxim MAX6698 + Prefix: 'max6698' + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6698.pdf + * Maxim MAX6699 + Prefix: 'max6699' + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6699.pdf Author: + Guenter Roeck Description @@ -50,9 +81,11 @@ The driver provides the following sysfs attributes. temp1 is the local (chip) temperature, temp[2..n] are remote temperatures. The actually supported per-channel attributes are chip type and channel dependent. +================ == ========================================================== tempX_input RO temperature tempX_max RW temperature maximum threshold tempX_max_alarm RO temperature maximum threshold alarm tempX_crit RW temperature critical threshold tempX_crit_alarm RO temperature critical threshold alarm tempX_fault RO temperature diode fault (remote sensors only) +================ == ========================================================== diff --git a/Documentation/hwmon/nct6775 b/Documentation/hwmon/nct6775 index bd59834d310f..1d0315c40952 100644 --- a/Documentation/hwmon/nct6775 +++ b/Documentation/hwmon/nct6775 @@ -1,52 +1,90 @@ -Note -==== - -This driver supersedes the NCT6775F and NCT6776F support in the W83627EHF -driver. - Kernel driver NCT6775 ===================== +.. note:: + + This driver supersedes the NCT6775F and NCT6776F support in the W83627EHF + driver. + Supported chips: + * Nuvoton NCT6102D/NCT6104D/NCT6106D + Prefix: 'nct6106' + Addresses scanned: ISA address retrieved from Super I/O registers + Datasheet: Available from the Nuvoton web site + * Nuvoton NCT5572D/NCT6771F/NCT6772F/NCT6775F/W83677HG-I + Prefix: 'nct6775' + Addresses scanned: ISA address retrieved from Super I/O registers + Datasheet: Available from Nuvoton upon request + * Nuvoton NCT5573D/NCT5577D/NCT6776D/NCT6776F + Prefix: 'nct6776' + Addresses scanned: ISA address retrieved from Super I/O registers + Datasheet: Available from Nuvoton upon request + * Nuvoton NCT5532D/NCT6779D + Prefix: 'nct6779' + Addresses scanned: ISA address retrieved from Super I/O registers + Datasheet: Available from Nuvoton upon request + * Nuvoton NCT6791D + Prefix: 'nct6791' + Addresses scanned: ISA address retrieved from Super I/O registers + Datasheet: Available from Nuvoton upon request + * Nuvoton NCT6792D + Prefix: 'nct6792' + Addresses scanned: ISA address retrieved from Super I/O registers + Datasheet: Available from Nuvoton upon request + * Nuvoton NCT6793D + Prefix: 'nct6793' + Addresses scanned: ISA address retrieved from Super I/O registers + Datasheet: Available from Nuvoton upon request + * Nuvoton NCT6795D + Prefix: 'nct6795' + Addresses scanned: ISA address retrieved from Super I/O registers + Datasheet: Available from Nuvoton upon request + * Nuvoton NCT6796D + Prefix: 'nct6796' + Addresses scanned: ISA address retrieved from Super I/O registers + Datasheet: Available from Nuvoton upon request + + Authors: - Guenter Roeck + + Guenter Roeck Description ----------- @@ -96,10 +134,14 @@ The mode works for fan1-fan5. sysfs attributes ---------------- -pwm[1-7] - this file stores PWM duty cycle or DC value (fan speed) in range: +pwm[1-7] + - this file stores PWM duty cycle or DC value (fan speed) in range: + 0 (lowest speed) to 255 (full) -pwm[1-7]_enable - this file controls mode of fan/temperature control: +pwm[1-7]_enable + - this file controls mode of fan/temperature control: + * 0 Fan control disabled (fans set to maximum speed) * 1 Manual mode, write to pwm[0-5] any value 0-255 * 2 "Thermal Cruise" mode @@ -107,15 +149,19 @@ pwm[1-7]_enable - this file controls mode of fan/temperature control: * 4 "Smart Fan III" mode (NCT6775F only) * 5 "Smart Fan IV" mode -pwm[1-7]_mode - controls if output is PWM or DC level - * 0 DC output - * 1 PWM output +pwm[1-7]_mode + - controls if output is PWM or DC level + + * 0 DC output + * 1 PWM output Common fan control attributes ----------------------------- -pwm[1-7]_temp_sel Temperature source. Value is temperature sensor index. +pwm[1-7]_temp_sel + Temperature source. Value is temperature sensor index. For example, select '1' for temp1_input. + pwm[1-7]_weight_temp_sel Secondary temperature source. Value is temperature sensor index. For example, select '1' for temp1_input. @@ -126,13 +172,16 @@ following attributes. pwm[1-7]_weight_duty_step Duty step size. + pwm[1-7]_weight_temp_step Temperature step size. With each step over temp_step_base, the value of weight_duty_step is added to the current pwm value. + pwm[1-7]_weight_temp_step_base Temperature at which secondary temperature control kicks in. + pwm[1-7]_weight_temp_step_tol Temperature step tolerance. @@ -141,24 +190,35 @@ Thermal Cruise mode (2) If the temperature is in the range defined by: -pwm[1-7]_target_temp Target temperature, unit millidegree Celsius +pwm[1-7]_target_temp + Target temperature, unit millidegree Celsius (range 0 - 127000) + pwm[1-7]_temp_tolerance Target temperature tolerance, unit millidegree Celsius -there are no changes to fan speed. Once the temperature leaves the interval, fan +There are no changes to fan speed. Once the temperature leaves the interval, fan speed increases (if temperature is higher that desired) or decreases (if temperature is lower than desired), using the following limits and time intervals. -pwm[1-7]_start fan pwm start value (range 1 - 255), to start fan +pwm[1-7]_start + fan pwm start value (range 1 - 255), to start fan when the temperature is above defined range. -pwm[1-7]_floor lowest fan pwm (range 0 - 255) if temperature is below + +pwm[1-7]_floor + lowest fan pwm (range 0 - 255) if temperature is below the defined range. If set to 0, the fan is expected to stop if the temperature is below the defined range. -pwm[1-7]_step_up_time milliseconds before fan speed is increased -pwm[1-7]_step_down_time milliseconds before fan speed is decreased -pwm[1-7]_stop_time how many milliseconds must elapse to switch + +pwm[1-7]_step_up_time + milliseconds before fan speed is increased + +pwm[1-7]_step_down_time + milliseconds before fan speed is decreased + +pwm[1-7]_stop_time + how many milliseconds must elapse to switch corresponding fan off (when the temperature was below defined range). @@ -167,7 +227,9 @@ Speed Cruise mode (3) This modes tries to keep the fan speed constant. -fan[1-7]_target Target fan speed +fan[1-7]_target + Target fan speed + fan[1-7]_tolerance Target speed tolerance @@ -188,16 +250,22 @@ critical temperature mode, in which the fans should run at full speed. pwm[1-7]_auto_point[1-7]_pwm pwm value to be set if temperature reaches matching temperature range. + pwm[1-7]_auto_point[1-7]_temp Temperature over which the matching pwm is enabled. + pwm[1-7]_temp_tolerance Temperature tolerance, unit millidegree Celsius + pwm[1-7]_crit_temp_tolerance Temperature tolerance for critical temperature, unit millidegree Celsius -pwm[1-7]_step_up_time milliseconds before fan speed is increased -pwm[1-7]_step_down_time milliseconds before fan speed is decreased +pwm[1-7]_step_up_time + milliseconds before fan speed is increased + +pwm[1-7]_step_down_time + milliseconds before fan speed is decreased Usage Notes ----------- diff --git a/Documentation/hwmon/smm665 b/Documentation/hwmon/smm665 index a341eeedab75..a0e27f62b57b 100644 --- a/Documentation/hwmon/smm665 +++ b/Documentation/hwmon/smm665 @@ -2,31 +2,57 @@ Kernel driver smm665 ==================== Supported chips: + * Summit Microelectronics SMM465 + Prefix: 'smm465' + Addresses scanned: - + Datasheet: + http://www.summitmicro.com/prod_select/summary/SMM465/SMM465DS.pdf + * Summit Microelectronics SMM665, SMM665B + Prefix: 'smm665' + Addresses scanned: - + Datasheet: + http://www.summitmicro.com/prod_select/summary/SMM665/SMM665B_2089_20.pdf + * Summit Microelectronics SMM665C + Prefix: 'smm665c' + Addresses scanned: - + Datasheet: + http://www.summitmicro.com/prod_select/summary/SMM665C/SMM665C_2125.pdf + * Summit Microelectronics SMM764 + Prefix: 'smm764' + Addresses scanned: - + Datasheet: + http://www.summitmicro.com/prod_select/summary/SMM764/SMM764_2098.pdf + * Summit Microelectronics SMM766, SMM766B + Prefix: 'smm766' + Addresses scanned: - + Datasheets: + http://www.summitmicro.com/prod_select/summary/SMM766/SMM766_2086.pdf + http://www.summitmicro.com/prod_select/summary/SMM766B/SMM766B_2122.pdf Author: Guenter Roeck @@ -36,9 +62,10 @@ Module Parameters ----------------- * vref: int - Default: 1250 (mV) - Reference voltage on VREF_ADC pin in mV. It should not be necessary to set - this parameter unless a non-default reference voltage is used. + Default: 1250 (mV) + + Reference voltage on VREF_ADC pin in mV. It should not be necessary to set + this parameter unless a non-default reference voltage is used. Description @@ -64,9 +91,10 @@ the devices explicitly. When instantiating the device, you have to specify its configuration register address. Example: the following will load the driver for an SMM665 at address 0x57 -on I2C bus #1: -$ modprobe smm665 -$ echo smm665 0x57 > /sys/bus/i2c/devices/i2c-1/new_device +on I2C bus #1:: + + $ modprobe smm665 + $ echo smm665 0x57 > /sys/bus/i2c/devices/i2c-1/new_device Sysfs entries @@ -84,6 +112,7 @@ max otherwise. For details please see the SMM665 datasheet. For SMM465 and SMM764, values for Channel E and F are reported but undefined. +======================= ======================================================= in1_input 12V input voltage (mV) in2_input 3.3V (VDD) input voltage (mV) in3_input Channel A voltage (mV) @@ -155,3 +184,4 @@ temp1_min Mimimum chip temperature temp1_max Maximum chip temperature temp1_crit Critical chip temperature temp1_crit_alarm Temperature critical alarm +======================= ======================================================= diff --git a/Documentation/hwmon/tmp401 b/Documentation/hwmon/tmp401 index 2d9ca42213cf..bd865bbdb38d 100644 --- a/Documentation/hwmon/tmp401 +++ b/Documentation/hwmon/tmp401 @@ -2,33 +2,59 @@ Kernel driver tmp401 ==================== Supported chips: + * Texas Instruments TMP401 + Prefix: 'tmp401' + Addresses scanned: I2C 0x4c + Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp401.html + * Texas Instruments TMP411 + Prefix: 'tmp411' + Addresses scanned: I2C 0x4c, 0x4d, 0x4e + Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp411.html + * Texas Instruments TMP431 + Prefix: 'tmp431' + Addresses scanned: I2C 0x4c, 0x4d + Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp431.html + * Texas Instruments TMP432 + Prefix: 'tmp432' + Addresses scanned: I2C 0x4c, 0x4d + Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp432.html + * Texas Instruments TMP435 + Prefix: 'tmp435' + Addresses scanned: I2C 0x48 - 0x4f + Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp435.html + * Texas Instruments TMP461 + Prefix: 'tmp461' + Datasheet: http://www.ti.com/product/tmp461 + + Authors: - Hans de Goede - Andre Prendel + + - Hans de Goede + - Andre Prendel Description ----------- -- cgit v1.2.3 From b04f2f7d387b3160883c2a1f5e2285483a791e82 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 17 Apr 2019 06:46:28 -0300 Subject: docs: hwmon: convert remaining files to ReST format Convert all other hwmon files to ReST format, in order to allow them to be parsed by Sphinx. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Guenter Roeck --- Documentation/hwmon/ab8500 | 8 +- Documentation/hwmon/abituguru | 97 ++-- Documentation/hwmon/abituguru-datasheet | 160 ++++--- Documentation/hwmon/abituguru3 | 36 +- Documentation/hwmon/abx500 | 8 +- Documentation/hwmon/acpi_power_meter | 23 +- Documentation/hwmon/ad7314 | 9 + Documentation/hwmon/adc128d818 | 7 +- Documentation/hwmon/adm1021 | 44 +- Documentation/hwmon/adm1025 | 13 +- Documentation/hwmon/adm1026 | 24 +- Documentation/hwmon/adm1031 | 16 +- Documentation/hwmon/adm9240 | 50 ++- Documentation/hwmon/ads7828 | 29 +- Documentation/hwmon/adt7410 | 49 ++- Documentation/hwmon/adt7411 | 20 +- Documentation/hwmon/adt7462 | 10 +- Documentation/hwmon/adt7470 | 8 +- Documentation/hwmon/adt7475 | 38 +- Documentation/hwmon/amc6821 | 19 +- Documentation/hwmon/asb100 | 54 +-- Documentation/hwmon/ds1621 | 156 ++++--- Documentation/hwmon/ds620 | 12 +- Documentation/hwmon/emc1403 | 33 +- Documentation/hwmon/emc6w201 | 5 + Documentation/hwmon/f71805f | 36 +- Documentation/hwmon/f71882fg | 56 ++- Documentation/hwmon/ftsteutates | 14 +- Documentation/hwmon/g760a | 4 + Documentation/hwmon/g762 | 49 ++- Documentation/hwmon/gl518sm | 21 +- Documentation/hwmon/hih6130 | 14 +- Documentation/hwmon/hwmon-kernel-api.txt | 346 ++++++++------- Documentation/hwmon/ibmaem | 10 +- Documentation/hwmon/ina3221 | 21 +- Documentation/hwmon/it87 | 102 ++++- Documentation/hwmon/lineage-pem | 16 +- Documentation/hwmon/lm63 | 24 +- Documentation/hwmon/lm70 | 13 +- Documentation/hwmon/lm73 | 16 +- Documentation/hwmon/lm75 | 96 +++- Documentation/hwmon/lm77 | 9 +- Documentation/hwmon/lm78 | 20 +- Documentation/hwmon/lm80 | 19 +- Documentation/hwmon/lm83 | 16 +- Documentation/hwmon/lm85 | 97 +++- Documentation/hwmon/lm87 | 23 +- Documentation/hwmon/lm90 | 174 ++++++-- Documentation/hwmon/lm92 | 17 +- Documentation/hwmon/lm93 | 157 +++---- Documentation/hwmon/lm95245 | 13 +- Documentation/hwmon/ltc2945 | 16 +- Documentation/hwmon/ltc2990 | 23 +- Documentation/hwmon/ltc4151 | 16 +- Documentation/hwmon/ltc4215 | 16 +- Documentation/hwmon/ltc4245 | 17 +- Documentation/hwmon/ltc4260 | 16 +- Documentation/hwmon/max1619 | 11 +- Documentation/hwmon/max1668 | 14 +- Documentation/hwmon/max197 | 36 +- Documentation/hwmon/max31722 | 12 + Documentation/hwmon/max31790 | 6 + Documentation/hwmon/max6639 | 16 +- Documentation/hwmon/max6642 | 10 +- Documentation/hwmon/max6650 | 16 +- Documentation/hwmon/mc13783-adc | 27 +- Documentation/hwmon/mcp3021 | 15 +- Documentation/hwmon/mlxreg-fan | 60 +-- Documentation/hwmon/nct6683 | 11 +- Documentation/hwmon/nct7802 | 11 +- Documentation/hwmon/nct7904 | 9 +- Documentation/hwmon/npcm750-pwm-fan | 4 + Documentation/hwmon/nsa320 | 15 +- Documentation/hwmon/ntc_thermistor | 123 +++--- Documentation/hwmon/occ | 93 ++-- Documentation/hwmon/pc87427 | 4 + Documentation/hwmon/pcf8591 | 52 ++- Documentation/hwmon/powr1220 | 12 +- Documentation/hwmon/raspberrypi-hwmon | 3 + Documentation/hwmon/sch5636 | 3 + Documentation/hwmon/scpi-hwmon | 7 +- Documentation/hwmon/sht15 | 28 +- Documentation/hwmon/sht21 | 24 +- Documentation/hwmon/sht3x | 42 +- Documentation/hwmon/shtc1 | 19 +- Documentation/hwmon/sis5595 | 40 +- Documentation/hwmon/smsc47b397 | 162 ++++--- Documentation/hwmon/smsc47m1 | 43 +- Documentation/hwmon/smsc47m192 | 97 ++-- Documentation/hwmon/submitting-patches | 15 +- Documentation/hwmon/sysfs-interface | 731 +++++++++++++++++++++---------- Documentation/hwmon/tc654 | 9 +- Documentation/hwmon/tc74 | 3 + Documentation/hwmon/thmc50 | 38 +- Documentation/hwmon/tmp102 | 5 + Documentation/hwmon/tmp103 | 5 + Documentation/hwmon/tmp108 | 5 + Documentation/hwmon/tmp421 | 26 +- Documentation/hwmon/twl4030-madc-hwmon | 8 +- Documentation/hwmon/userspace-tools | 3 + Documentation/hwmon/via686a | 30 +- Documentation/hwmon/w83627ehf | 162 ++++--- Documentation/hwmon/w83627hf | 65 +-- Documentation/hwmon/w83773g | 12 +- Documentation/hwmon/w83781d | 330 ++++++++------ Documentation/hwmon/w83792d | 112 +++-- Documentation/hwmon/w83795 | 223 +++++----- Documentation/hwmon/w83l785ts | 9 +- Documentation/hwmon/w83l786ng | 42 +- Documentation/hwmon/xgene-hwmon | 24 +- 110 files changed, 3551 insertions(+), 1746 deletions(-) (limited to 'Documentation') diff --git a/Documentation/hwmon/ab8500 b/Documentation/hwmon/ab8500 index cf169c8ef4e3..d87c61151239 100644 --- a/Documentation/hwmon/ab8500 +++ b/Documentation/hwmon/ab8500 @@ -2,14 +2,18 @@ Kernel driver ab8500 ==================== Supported chips: + * ST-Ericsson AB8500 + Prefix: 'ab8500' + Addresses scanned: - + Datasheet: http://www.stericsson.com/developers/documentation.jsp Authors: - Martin Persson - Hongbo Zhang + - Martin Persson + - Hongbo Zhang Description ----------- diff --git a/Documentation/hwmon/abituguru b/Documentation/hwmon/abituguru index 44013d23b3f0..d8243c827de9 100644 --- a/Documentation/hwmon/abituguru +++ b/Documentation/hwmon/abituguru @@ -2,69 +2,85 @@ Kernel driver abituguru ======================= Supported chips: + * Abit uGuru revision 1 & 2 (Hardware Monitor part only) + Prefix: 'abituguru' + Addresses scanned: ISA 0x0E0 + Datasheet: Not available, this driver is based on reverse engineering. - A "Datasheet" has been written based on the reverse engineering it - should be available in the same dir as this file under the name - abituguru-datasheet. + A "Datasheet" has been written based on the reverse engineering it + should be available in the same dir as this file under the name + abituguru-datasheet. + Note: The uGuru is a microcontroller with onboard firmware which programs it to behave as a hwmon IC. There are many different revisions of the firmware and thus effectivly many different revisions of the uGuru. Below is an incomplete list with which revisions are used for which Motherboards: - uGuru 1.00 ~ 1.24 (AI7, KV8-MAX3, AN7) (1) - uGuru 2.0.0.0 ~ 2.0.4.2 (KV8-PRO) - uGuru 2.1.0.0 ~ 2.1.2.8 (AS8, AV8, AA8, AG8, AA8XE, AX8) - uGuru 2.2.0.0 ~ 2.2.0.6 (AA8 Fatal1ty) - uGuru 2.3.0.0 ~ 2.3.0.9 (AN8) - uGuru 3.0.0.0 ~ 3.0.x.x (AW8, AL8, AT8, NI8 SLI, AT8 32X, AN8 32X, - AW9D-MAX) (2) - 1) For revisions 2 and 3 uGuru's the driver can autodetect the - sensortype (Volt or Temp) for bank1 sensors, for revision 1 uGuru's - this does not always work. For these uGuru's the autodetection can - be overridden with the bank1_types module param. For all 3 known - revison 1 motherboards the correct use of this param is: - bank1_types=1,1,0,0,0,0,0,2,0,0,0,0,2,0,0,1 - You may also need to specify the fan_sensors option for these boards - fan_sensors=5 - 2) There is a separate abituguru3 driver for these motherboards, - the abituguru (without the 3 !) driver will not work on these - motherboards (and visa versa)! + + - uGuru 1.00 ~ 1.24 (AI7, KV8-MAX3, AN7) [1]_ + - uGuru 2.0.0.0 ~ 2.0.4.2 (KV8-PRO) + - uGuru 2.1.0.0 ~ 2.1.2.8 (AS8, AV8, AA8, AG8, AA8XE, AX8) + - uGuru 2.2.0.0 ~ 2.2.0.6 (AA8 Fatal1ty) + - uGuru 2.3.0.0 ~ 2.3.0.9 (AN8) + - uGuru 3.0.0.0 ~ 3.0.x.x (AW8, AL8, AT8, NI8 SLI, AT8 32X, AN8 32X, + AW9D-MAX) [2]_ + +.. [1] For revisions 2 and 3 uGuru's the driver can autodetect the + sensortype (Volt or Temp) for bank1 sensors, for revision 1 uGuru's + this does not always work. For these uGuru's the autodetection can + be overridden with the bank1_types module param. For all 3 known + revison 1 motherboards the correct use of this param is: + bank1_types=1,1,0,0,0,0,0,2,0,0,0,0,2,0,0,1 + You may also need to specify the fan_sensors option for these boards + fan_sensors=5 + +.. [2] There is a separate abituguru3 driver for these motherboards, + the abituguru (without the 3 !) driver will not work on these + motherboards (and visa versa)! Authors: - Hans de Goede , - (Initial reverse engineering done by Olle Sandberg - ) + - Hans de Goede , + - (Initial reverse engineering done by Olle Sandberg + ) Module Parameters ----------------- -* force: bool Force detection. Note this parameter only causes the +* force: bool + Force detection. Note this parameter only causes the detection to be skipped, and thus the insmod to succeed. If the uGuru can't be read the actual hwmon driver will not load and thus no hwmon device will get registered. -* bank1_types: int[] Bank1 sensortype autodetection override: - -1 autodetect (default) - 0 volt sensor - 1 temp sensor - 2 not connected -* fan_sensors: int Tell the driver how many fan speed sensors there are +* bank1_types: int[] + Bank1 sensortype autodetection override: + + * -1 autodetect (default) + * 0 volt sensor + * 1 temp sensor + * 2 not connected +* fan_sensors: int + Tell the driver how many fan speed sensors there are on your motherboard. Default: 0 (autodetect). -* pwms: int Tell the driver how many fan speed controls (fan +* pwms: int + Tell the driver how many fan speed controls (fan pwms) your motherboard has. Default: 0 (autodetect). -* verbose: int How verbose should the driver be? (0-3): - 0 normal output - 1 + verbose error reporting - 2 + sensors type probing info (default) - 3 + retryable error reporting +* verbose: int + How verbose should the driver be? (0-3): + + * 0 normal output + * 1 + verbose error reporting + * 2 + sensors type probing info (default) + * 3 + retryable error reporting + Default: 2 (the driver is still in the testing phase) -Notice if you need any of the first three options above please insmod the +Notice: if you need any of the first three options above please insmod the driver with verbose set to 3 and mail me the output of: dmesg | grep abituguru @@ -90,3 +106,8 @@ Known Issues ------------ The voltage and frequency control parts of the Abit uGuru are not supported. + +.. toctree:: + :maxdepth: 1 + + abituguru-datasheet.rst diff --git a/Documentation/hwmon/abituguru-datasheet b/Documentation/hwmon/abituguru-datasheet index 86c0b1251c81..6d5253e2223b 100644 --- a/Documentation/hwmon/abituguru-datasheet +++ b/Documentation/hwmon/abituguru-datasheet @@ -1,3 +1,4 @@ +=============== uGuru datasheet =============== @@ -168,34 +169,35 @@ This bank contains 0 sensors, iow the sensor address is ignored (but must be written) just use 0. Bank 0x20 contains 3 bytes: Byte 0: -This byte holds the alarm flags for sensor 0-7 of Sensor Bank1, with bit 0 -corresponding to sensor 0, 1 to 1, etc. + This byte holds the alarm flags for sensor 0-7 of Sensor Bank1, with bit 0 + corresponding to sensor 0, 1 to 1, etc. Byte 1: -This byte holds the alarm flags for sensor 8-15 of Sensor Bank1, with bit 0 -corresponding to sensor 8, 1 to 9, etc. + This byte holds the alarm flags for sensor 8-15 of Sensor Bank1, with bit 0 + corresponding to sensor 8, 1 to 9, etc. Byte 2: -This byte holds the alarm flags for sensor 0-5 of Sensor Bank2, with bit 0 -corresponding to sensor 0, 1 to 1, etc. + This byte holds the alarm flags for sensor 0-5 of Sensor Bank2, with bit 0 + corresponding to sensor 0, 1 to 1, etc. Bank 0x21 Sensor Bank1 Values / Readings (R) -------------------------------------------- This bank contains 16 sensors, for each sensor it contains 1 byte. So far the following sensors are known to be available on all motherboards: -Sensor 0 CPU temp -Sensor 1 SYS temp -Sensor 3 CPU core volt -Sensor 4 DDR volt -Sensor 10 DDR Vtt volt -Sensor 15 PWM temp + +- Sensor 0 CPU temp +- Sensor 1 SYS temp +- Sensor 3 CPU core volt +- Sensor 4 DDR volt +- Sensor 10 DDR Vtt volt +- Sensor 15 PWM temp Byte 0: -This byte holds the reading from the sensor. Sensors in Bank1 can be both -volt and temp sensors, this is motherboard specific. The uGuru however does -seem to know (be programmed with) what kindoff sensor is attached see Sensor -Bank1 Settings description. + This byte holds the reading from the sensor. Sensors in Bank1 can be both + volt and temp sensors, this is motherboard specific. The uGuru however does + seem to know (be programmed with) what kindoff sensor is attached see Sensor + Bank1 Settings description. Volt sensors use a linear scale, a reading 0 corresponds with 0 volt and a reading of 255 with 3494 mV. The sensors for higher voltages however are @@ -207,96 +209,118 @@ Temp sensors also use a linear scale, a reading of 0 corresponds with 0 degree Celsius and a reading of 255 with a reading of 255 degrees Celsius. -Bank 0x22 Sensor Bank1 Settings (R) -Bank 0x23 Sensor Bank1 Settings (W) ------------------------------------ +Bank 0x22 Sensor Bank1 Settings (R) and Bank 0x23 Sensor Bank1 Settings (W) +--------------------------------------------------------------------------- -This bank contains 16 sensors, for each sensor it contains 3 bytes. Each +Those banks contain 16 sensors, for each sensor it contains 3 bytes. Each set of 3 bytes contains the settings for the sensor with the same sensor address in Bank 0x21 . Byte 0: -Alarm behaviour for the selected sensor. A 1 enables the described behaviour. -Bit 0: Give an alarm if measured temp is over the warning threshold (RW) * -Bit 1: Give an alarm if measured volt is over the max threshold (RW) ** -Bit 2: Give an alarm if measured volt is under the min threshold (RW) ** -Bit 3: Beep if alarm (RW) -Bit 4: 1 if alarm cause measured temp is over the warning threshold (R) -Bit 5: 1 if alarm cause measured volt is over the max threshold (R) -Bit 6: 1 if alarm cause measured volt is under the min threshold (R) -Bit 7: Volt sensor: Shutdown if alarm persist for more than 4 seconds (RW) - Temp sensor: Shutdown if temp is over the shutdown threshold (RW) - -* This bit is only honored/used by the uGuru if a temp sensor is connected -** This bit is only honored/used by the uGuru if a volt sensor is connected -Note with some trickery this can be used to find out what kinda sensor is -detected see the Linux kernel driver for an example with many comments on -how todo this. + Alarm behaviour for the selected sensor. A 1 enables the described + behaviour. + +Bit 0: + Give an alarm if measured temp is over the warning threshold (RW) [1]_ + +Bit 1: + Give an alarm if measured volt is over the max threshold (RW) [2]_ + +Bit 2: + Give an alarm if measured volt is under the min threshold (RW) [2]_ + +Bit 3: + Beep if alarm (RW) + +Bit 4: + 1 if alarm cause measured temp is over the warning threshold (R) + +Bit 5: + 1 if alarm cause measured volt is over the max threshold (R) + +Bit 6: + 1 if alarm cause measured volt is under the min threshold (R) + +Bit 7: + - Volt sensor: Shutdown if alarm persist for more than 4 seconds (RW) + - Temp sensor: Shutdown if temp is over the shutdown threshold (RW) + +.. [1] This bit is only honored/used by the uGuru if a temp sensor is connected + +.. [2] This bit is only honored/used by the uGuru if a volt sensor is connected + Note with some trickery this can be used to find out what kinda sensor + is detected see the Linux kernel driver for an example with many + comments on how todo this. Byte 1: -Temp sensor: warning threshold (scale as bank 0x21) -Volt sensor: min threshold (scale as bank 0x21) + - Temp sensor: warning threshold (scale as bank 0x21) + - Volt sensor: min threshold (scale as bank 0x21) Byte 2: -Temp sensor: shutdown threshold (scale as bank 0x21) -Volt sensor: max threshold (scale as bank 0x21) + - Temp sensor: shutdown threshold (scale as bank 0x21) + - Volt sensor: max threshold (scale as bank 0x21) -Bank 0x24 PWM outputs for FAN's (R) -Bank 0x25 PWM outputs for FAN's (W) ------------------------------------ +Bank 0x24 PWM outputs for FAN's (R) and Bank 0x25 PWM outputs for FAN's (W) +--------------------------------------------------------------------------- -This bank contains 3 "sensors", for each sensor it contains 5 bytes. -Sensor 0 usually controls the CPU fan -Sensor 1 usually controls the NB (or chipset for single chip) fan -Sensor 2 usually controls the System fan +Those banks contain 3 "sensors", for each sensor it contains 5 bytes. + - Sensor 0 usually controls the CPU fan + - Sensor 1 usually controls the NB (or chipset for single chip) fan + - Sensor 2 usually controls the System fan Byte 0: -Flag 0x80 to enable control, Fan runs at 100% when disabled. -low nibble (temp)sensor address at bank 0x21 used for control. + Flag 0x80 to enable control, Fan runs at 100% when disabled. + low nibble (temp)sensor address at bank 0x21 used for control. Byte 1: -0-255 = 0-12v (linear), specify voltage at which fan will rotate when under -low threshold temp (specified in byte 3) + 0-255 = 0-12v (linear), specify voltage at which fan will rotate when under + low threshold temp (specified in byte 3) Byte 2: -0-255 = 0-12v (linear), specify voltage at which fan will rotate when above -high threshold temp (specified in byte 4) + 0-255 = 0-12v (linear), specify voltage at which fan will rotate when above + high threshold temp (specified in byte 4) Byte 3: -Low threshold temp (scale as bank 0x21) + Low threshold temp (scale as bank 0x21) byte 4: -High threshold temp (scale as bank 0x21) + High threshold temp (scale as bank 0x21) Bank 0x26 Sensors Bank2 Values / Readings (R) --------------------------------------------- This bank contains 6 sensors (AFAIK), for each sensor it contains 1 byte. + So far the following sensors are known to be available on all motherboards: -Sensor 0: CPU fan speed -Sensor 1: NB (or chipset for single chip) fan speed -Sensor 2: SYS fan speed + - Sensor 0: CPU fan speed + - Sensor 1: NB (or chipset for single chip) fan speed + - Sensor 2: SYS fan speed Byte 0: -This byte holds the reading from the sensor. 0-255 = 0-15300 (linear) + This byte holds the reading from the sensor. 0-255 = 0-15300 (linear) -Bank 0x27 Sensors Bank2 Settings (R) -Bank 0x28 Sensors Bank2 Settings (W) ------------------------------------- +Bank 0x27 Sensors Bank2 Settings (R) and Bank 0x28 Sensors Bank2 Settings (W) +----------------------------------------------------------------------------- -This bank contains 6 sensors (AFAIK), for each sensor it contains 2 bytes. +Those banks contain 6 sensors (AFAIK), for each sensor it contains 2 bytes. Byte 0: -Alarm behaviour for the selected sensor. A 1 enables the described behaviour. -Bit 0: Give an alarm if measured rpm is under the min threshold (RW) -Bit 3: Beep if alarm (RW) -Bit 7: Shutdown if alarm persist for more than 4 seconds (RW) + Alarm behaviour for the selected sensor. A 1 enables the described behaviour. + +Bit 0: + Give an alarm if measured rpm is under the min threshold (RW) + +Bit 3: + Beep if alarm (RW) + +Bit 7: + Shutdown if alarm persist for more than 4 seconds (RW) Byte 1: -min threshold (scale as bank 0x26) + min threshold (scale as bank 0x26) Warning for the adventurous diff --git a/Documentation/hwmon/abituguru3 b/Documentation/hwmon/abituguru3 index a6ccfe4bb6aa..514f11f41e8b 100644 --- a/Documentation/hwmon/abituguru3 +++ b/Documentation/hwmon/abituguru3 @@ -3,41 +3,51 @@ Kernel driver abituguru3 Supported chips: * Abit uGuru revision 3 (Hardware Monitor part, reading only) + Prefix: 'abituguru3' + Addresses scanned: ISA 0x0E0 + Datasheet: Not available, this driver is based on reverse engineering. + Note: The uGuru is a microcontroller with onboard firmware which programs it to behave as a hwmon IC. There are many different revisions of the firmware and thus effectivly many different revisions of the uGuru. Below is an incomplete list with which revisions are used for which Motherboards: - uGuru 1.00 ~ 1.24 (AI7, KV8-MAX3, AN7) - uGuru 2.0.0.0 ~ 2.0.4.2 (KV8-PRO) - uGuru 2.1.0.0 ~ 2.1.2.8 (AS8, AV8, AA8, AG8, AA8XE, AX8) - uGuru 2.3.0.0 ~ 2.3.0.9 (AN8) - uGuru 3.0.0.0 ~ 3.0.x.x (AW8, AL8, AT8, NI8 SLI, AT8 32X, AN8 32X, - AW9D-MAX) + + - uGuru 1.00 ~ 1.24 (AI7, KV8-MAX3, AN7) + - uGuru 2.0.0.0 ~ 2.0.4.2 (KV8-PRO) + - uGuru 2.1.0.0 ~ 2.1.2.8 (AS8, AV8, AA8, AG8, AA8XE, AX8) + - uGuru 2.3.0.0 ~ 2.3.0.9 (AN8) + - uGuru 3.0.0.0 ~ 3.0.x.x (AW8, AL8, AT8, NI8 SLI, AT8 32X, AN8 32X, + AW9D-MAX) + The abituguru3 driver is only for revison 3.0.x.x motherboards, this driver will not work on older motherboards. For older motherboards use the abituguru (without the 3 !) driver. Authors: - Hans de Goede , - (Initial reverse engineering done by Louis Kruger) + - Hans de Goede , + - (Initial reverse engineering done by Louis Kruger) Module Parameters ----------------- -* force: bool Force detection. Note this parameter only causes the +* force: bool + Force detection. Note this parameter only causes the detection to be skipped, and thus the insmod to succeed. If the uGuru can't be read the actual hwmon driver will not load and thus no hwmon device will get registered. -* verbose: bool Should the driver be verbose? - 0/off/false normal output - 1/on/true + verbose error reporting (default) +* verbose: bool + Should the driver be verbose? + + * 0/off/false normal output + * 1/on/true + verbose error reporting (default) + Default: 1 (the driver is still in the testing phase) Description @@ -62,4 +72,4 @@ neither is writing any of the sensor settings and writing / reading the fanspeed control registers (FanEQ) If you encounter any problems please mail me and -include the output of: "dmesg | grep abituguru" +include the output of: `dmesg | grep abituguru` diff --git a/Documentation/hwmon/abx500 b/Documentation/hwmon/abx500 index 319a058cec7c..3d88b2ce0f00 100644 --- a/Documentation/hwmon/abx500 +++ b/Documentation/hwmon/abx500 @@ -2,14 +2,18 @@ Kernel driver abx500 ==================== Supported chips: + * ST-Ericsson ABx500 series + Prefix: 'abx500' + Addresses scanned: - + Datasheet: http://www.stericsson.com/developers/documentation.jsp Authors: - Martin Persson - Hongbo Zhang + Martin Persson + Hongbo Zhang Description ----------- diff --git a/Documentation/hwmon/acpi_power_meter b/Documentation/hwmon/acpi_power_meter index c80399a00c50..7665ca6ba957 100644 --- a/Documentation/hwmon/acpi_power_meter +++ b/Documentation/hwmon/acpi_power_meter @@ -4,8 +4,11 @@ Kernel driver power_meter This driver talks to ACPI 4.0 power meters. Supported systems: + * Any recent system with ACPI 4.0. + Prefix: 'power_meter' + Datasheet: http://acpi.info/, section 10.4. Author: Darrick J. Wong @@ -23,21 +26,21 @@ of Documentation/hwmon/sysfs-interface. Special Features ---------------- -The power[1-*]_is_battery knob indicates if the power supply is a battery. -Both power[1-*]_average_{min,max} must be set before the trip points will work. +The `power[1-*]_is_battery` knob indicates if the power supply is a battery. +Both `power[1-*]_average_{min,max}` must be set before the trip points will work. When both of them are set, an ACPI event will be broadcast on the ACPI netlink socket and a poll notification will be sent to the appropriate -power[1-*]_average sysfs file. +`power[1-*]_average` sysfs file. -The power[1-*]_{model_number, serial_number, oem_info} fields display arbitrary -strings that ACPI provides with the meter. The measures/ directory contains -symlinks to the devices that this meter measures. +The `power[1-*]_{model_number, serial_number, oem_info}` fields display +arbitrary strings that ACPI provides with the meter. The measures/ directory +contains symlinks to the devices that this meter measures. Some computers have the ability to enforce a power cap in hardware. If this is -the case, the power[1-*]_cap and related sysfs files will appear. When the +the case, the `power[1-*]_cap` and related sysfs files will appear. When the average power consumption exceeds the cap, an ACPI event will be broadcast on the netlink event socket and a poll notification will be sent to the -appropriate power[1-*]_alarm file to indicate that capping has begun, and the +appropriate `power[1-*]_alarm` file to indicate that capping has begun, and the hardware has taken action to reduce power consumption. Most likely this will result in reduced performance. @@ -46,6 +49,6 @@ all cases the ACPI event will be broadcast on the ACPI netlink event socket as well as sent as a poll notification to a sysfs file. The events are as follows: -power[1-*]_cap will be notified if the firmware changes the power cap. -power[1-*]_interval will be notified if the firmware changes the averaging +`power[1-*]_cap` will be notified if the firmware changes the power cap. +`power[1-*]_interval` will be notified if the firmware changes the averaging interval. diff --git a/Documentation/hwmon/ad7314 b/Documentation/hwmon/ad7314 index 1912549c7467..bf389736bcd1 100644 --- a/Documentation/hwmon/ad7314 +++ b/Documentation/hwmon/ad7314 @@ -2,14 +2,23 @@ Kernel driver ad7314 ==================== Supported chips: + * Analog Devices AD7314 + Prefix: 'ad7314' + Datasheet: Publicly available at Analog Devices website. + * Analog Devices ADT7301 + Prefix: 'adt7301' + Datasheet: Publicly available at Analog Devices website. + * Analog Devices ADT7302 + Prefix: 'adt7302' + Datasheet: Publicly available at Analog Devices website. Description diff --git a/Documentation/hwmon/adc128d818 b/Documentation/hwmon/adc128d818 index 39c95004dabc..6753468932ab 100644 --- a/Documentation/hwmon/adc128d818 +++ b/Documentation/hwmon/adc128d818 @@ -2,11 +2,14 @@ Kernel driver adc128d818 ======================== Supported chips: + * Texas Instruments ADC818D818 + Prefix: 'adc818d818' + Addresses scanned: I2C 0x1d, 0x1e, 0x1f, 0x2d, 0x2e, 0x2f - Datasheet: Publicly available at the TI website - http://www.ti.com/ + + Datasheet: Publicly available at the TI website http://www.ti.com/ Author: Guenter Roeck diff --git a/Documentation/hwmon/adm1021 b/Documentation/hwmon/adm1021 index 02ad96cf9b2b..6cbb0f75fe00 100644 --- a/Documentation/hwmon/adm1021 +++ b/Documentation/hwmon/adm1021 @@ -2,51 +2,91 @@ Kernel driver adm1021 ===================== Supported chips: + * Analog Devices ADM1021 + Prefix: 'adm1021' + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + Datasheet: Publicly available at the Analog Devices website + * Analog Devices ADM1021A/ADM1023 + Prefix: 'adm1023' + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + Datasheet: Publicly available at the Analog Devices website + * Genesys Logic GL523SM + Prefix: 'gl523sm' + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + Datasheet: + * Maxim MAX1617 + Prefix: 'max1617' + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + Datasheet: Publicly available at the Maxim website + * Maxim MAX1617A + Prefix: 'max1617a' + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + Datasheet: Publicly available at the Maxim website + * National Semiconductor LM84 + Prefix: 'lm84' + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + Datasheet: Publicly available at the National Semiconductor website + * Philips NE1617 + Prefix: 'max1617' (probably detected as a max1617) + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + Datasheet: Publicly available at the Philips website + * Philips NE1617A + Prefix: 'max1617' (probably detected as a max1617) + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + Datasheet: Publicly available at the Philips website + * TI THMC10 + Prefix: 'thmc10' + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + Datasheet: Publicly available at the TI website + * Onsemi MC1066 + Prefix: 'mc1066' + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + Datasheet: Publicly available at the Onsemi website Authors: - Frodo Looijaard , - Philip Edelbrock + - Frodo Looijaard , + - Philip Edelbrock Module Parameters ----------------- diff --git a/Documentation/hwmon/adm1025 b/Documentation/hwmon/adm1025 index 99f05049c68a..283e65e348a5 100644 --- a/Documentation/hwmon/adm1025 +++ b/Documentation/hwmon/adm1025 @@ -2,23 +2,32 @@ Kernel driver adm1025 ===================== Supported chips: + * Analog Devices ADM1025, ADM1025A + Prefix: 'adm1025' + Addresses scanned: I2C 0x2c - 0x2e + Datasheet: Publicly available at the Analog Devices website + * Philips NE1619 + Prefix: 'ne1619' + Addresses scanned: I2C 0x2c - 0x2d + Datasheet: Publicly available at the Philips website The NE1619 presents some differences with the original ADM1025: + * Only two possible addresses (0x2c - 0x2d). * No temperature offset register, but we don't use it anyway. * No INT mode for pin 16. We don't play with it anyway. Authors: - Chen-Yuan Wu , - Jean Delvare + - Chen-Yuan Wu , + - Jean Delvare Description ----------- diff --git a/Documentation/hwmon/adm1026 b/Documentation/hwmon/adm1026 index d8fabe0c23ac..35d63e6498a3 100644 --- a/Documentation/hwmon/adm1026 +++ b/Documentation/hwmon/adm1026 @@ -3,28 +3,36 @@ Kernel driver adm1026 Supported chips: * Analog Devices ADM1026 + Prefix: 'adm1026' + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + Datasheet: Publicly available at the Analog Devices website - http://www.onsemi.com/PowerSolutions/product.do?id=ADM1026 + + http://www.onsemi.com/PowerSolutions/product.do?id=ADM1026 Authors: - Philip Pokorny for Penguin Computing - Justin Thiessen + - Philip Pokorny for Penguin Computing + - Justin Thiessen Module Parameters ----------------- * gpio_input: int array (min = 1, max = 17) - List of GPIO pins (0-16) to program as inputs + List of GPIO pins (0-16) to program as inputs + * gpio_output: int array (min = 1, max = 17) - List of GPIO pins (0-16) to program as outputs + List of GPIO pins (0-16) to program as outputs + * gpio_inverted: int array (min = 1, max = 17) - List of GPIO pins (0-16) to program as inverted + List of GPIO pins (0-16) to program as inverted + * gpio_normal: int array (min = 1, max = 17) - List of GPIO pins (0-16) to program as normal/non-inverted + List of GPIO pins (0-16) to program as normal/non-inverted + * gpio_fan: int array (min = 1, max = 8) - List of GPIO pins (0-7) to program as fan tachs + List of GPIO pins (0-7) to program as fan tachs Description diff --git a/Documentation/hwmon/adm1031 b/Documentation/hwmon/adm1031 index a143117c99cb..a677c3ab5574 100644 --- a/Documentation/hwmon/adm1031 +++ b/Documentation/hwmon/adm1031 @@ -3,20 +3,28 @@ Kernel driver adm1031 Supported chips: * Analog Devices ADM1030 + Prefix: 'adm1030' + Addresses scanned: I2C 0x2c to 0x2e + Datasheet: Publicly available at the Analog Devices website - http://www.analog.com/en/prod/0%2C2877%2CADM1030%2C00.html + + http://www.analog.com/en/prod/0%2C2877%2CADM1030%2C00.html * Analog Devices ADM1031 + Prefix: 'adm1031' + Addresses scanned: I2C 0x2c to 0x2e + Datasheet: Publicly available at the Analog Devices website - http://www.analog.com/en/prod/0%2C2877%2CADM1031%2C00.html + + http://www.analog.com/en/prod/0%2C2877%2CADM1031%2C00.html Authors: - Alexandre d'Alton - Jean Delvare + - Alexandre d'Alton + - Jean Delvare Description ----------- diff --git a/Documentation/hwmon/adm9240 b/Documentation/hwmon/adm9240 index 9b174fc700cc..91063b0f4c6f 100644 --- a/Documentation/hwmon/adm9240 +++ b/Documentation/hwmon/adm9240 @@ -2,30 +2,43 @@ Kernel driver adm9240 ===================== Supported chips: + * Analog Devices ADM9240 + Prefix: 'adm9240' + Addresses scanned: I2C 0x2c - 0x2f + Datasheet: Publicly available at the Analog Devices website - http://www.analog.com/UploadedFiles/Data_Sheets/79857778ADM9240_0.pdf + + http://www.analog.com/UploadedFiles/Data_Sheets/79857778ADM9240_0.pdf * Dallas Semiconductor DS1780 + Prefix: 'ds1780' + Addresses scanned: I2C 0x2c - 0x2f + Datasheet: Publicly available at the Dallas Semiconductor (Maxim) website - http://pdfserv.maxim-ic.com/en/ds/DS1780.pdf + + http://pdfserv.maxim-ic.com/en/ds/DS1780.pdf * National Semiconductor LM81 + Prefix: 'lm81' + Addresses scanned: I2C 0x2c - 0x2f + Datasheet: Publicly available at the National Semiconductor website - http://www.national.com/ds.cgi/LM/LM81.pdf + + http://www.national.com/ds.cgi/LM/LM81.pdf Authors: - Frodo Looijaard , - Philip Edelbrock , - Michiel Rook , - Grant Coady with guidance - from Jean Delvare + - Frodo Looijaard , + - Philip Edelbrock , + - Michiel Rook , + - Grant Coady with guidance + from Jean Delvare Interface --------- @@ -87,11 +100,13 @@ rpm = (22500 * 60) / (count * divider) Automatic fan clock divider * User sets 0 to fan_min limit + - low speed alarm is disabled - fan clock divider not changed - auto fan clock adjuster enabled for valid fan speed reading * User sets fan_min limit too low + - low speed alarm is enabled - fan clock divider set to max - fan_min set to register value 254 which corresponds @@ -101,18 +116,20 @@ Automatic fan clock divider - auto fan clock adjuster disabled * User sets reasonable fan speed + - low speed alarm is enabled - fan clock divider set to suit fan_min - auto fan clock adjuster enabled: adjusts fan_min * User sets unreasonably high low fan speed limit + - resolution of the low speed limit may be reduced - alarm will be asserted - auto fan clock adjuster enabled: adjusts fan_min - * fan speed may be displayed as zero until the auto fan clock divider - adjuster brings fan speed clock divider back into chip measurement - range, this will occur within a few measurement cycles. + * fan speed may be displayed as zero until the auto fan clock divider + adjuster brings fan speed clock divider back into chip measurement + range, this will occur within a few measurement cycles. Analog Output ------------- @@ -122,16 +139,21 @@ power up or reset. This doesn't do much on the test Intel SE440BX-2. Voltage Monitor +^^^^^^^^^^^^^^^ + Voltage (IN) measurement is internally scaled: + === =========== =========== ========= ========== nr label nominal maximum resolution - mV mV mV + mV mV mV + === =========== =========== ========= ========== 0 +2.5V 2500 3320 13.0 1 Vccp1 2700 3600 14.1 2 +3.3V 3300 4380 17.2 3 +5V 5000 6640 26.0 4 +12V 12000 15940 62.5 5 Vccp2 2700 3600 14.1 + === =========== =========== ========= ========== The reading is an unsigned 8-bit value, nominal voltage measurement is represented by a reading of 192, being 3/4 of the measurement range. @@ -159,8 +181,9 @@ Clear the CI latch by writing value 0 to the sysfs intrusion0_alarm file. Alarm flags reported as 16-bit word + === ============= ========================== bit label comment - --- ------------- -------------------------- + === ============= ========================== 0 +2.5 V_Error high or low limit exceeded 1 VCCP_Error high or low limit exceeded 2 +3.3 V_Error high or low limit exceeded @@ -171,6 +194,7 @@ Alarm flags reported as 16-bit word 8 +12 V_Error high or low limit exceeded 9 VCCP2_Error high or low limit exceeded 12 Chassis_Error CI pin went high + === ============= ========================== Remaining bits are reserved and thus undefined. It is important to note that alarm bits may be cleared on read, user-space may latch alarms and diff --git a/Documentation/hwmon/ads7828 b/Documentation/hwmon/ads7828 index f6e263e0f607..b830b490cfe4 100644 --- a/Documentation/hwmon/ads7828 +++ b/Documentation/hwmon/ads7828 @@ -2,20 +2,27 @@ Kernel driver ads7828 ===================== Supported chips: + * Texas Instruments/Burr-Brown ADS7828 + Prefix: 'ads7828' + Datasheet: Publicly available at the Texas Instruments website: - http://focus.ti.com/lit/ds/symlink/ads7828.pdf + + http://focus.ti.com/lit/ds/symlink/ads7828.pdf * Texas Instruments ADS7830 + Prefix: 'ads7830' + Datasheet: Publicly available at the Texas Instruments website: - http://focus.ti.com/lit/ds/symlink/ads7830.pdf + + http://focus.ti.com/lit/ds/symlink/ads7830.pdf Authors: - Steve Hardy - Vivien Didelot - Guillaume Roguez + - Steve Hardy + - Vivien Didelot + - Guillaume Roguez Platform data ------------- @@ -24,16 +31,16 @@ The ads7828 driver accepts an optional ads7828_platform_data structure (defined in include/linux/platform_data/ads7828.h). The structure fields are: * diff_input: (bool) Differential operation - set to true for differential mode, false for default single ended mode. + set to true for differential mode, false for default single ended mode. * ext_vref: (bool) External reference - set to true if it operates with an external reference, false for default - internal reference. + set to true if it operates with an external reference, false for default + internal reference. * vref_mv: (unsigned int) Voltage reference - if using an external reference, set this to the reference voltage in mV, - otherwise it will default to the internal value (2500mV). This value will be - bounded with limits accepted by the chip, described in the datasheet. + if using an external reference, set this to the reference voltage in mV, + otherwise it will default to the internal value (2500mV). This value will be + bounded with limits accepted by the chip, described in the datasheet. If no structure is provided, the configuration defaults to single ended operation and internal voltage reference (2.5V). diff --git a/Documentation/hwmon/adt7410 b/Documentation/hwmon/adt7410 index 9817941e5f19..24caaa83c8ec 100644 --- a/Documentation/hwmon/adt7410 +++ b/Documentation/hwmon/adt7410 @@ -2,26 +2,45 @@ Kernel driver adt7410 ===================== Supported chips: + * Analog Devices ADT7410 + Prefix: 'adt7410' + Addresses scanned: None + Datasheet: Publicly available at the Analog Devices website - http://www.analog.com/static/imported-files/data_sheets/ADT7410.pdf + + http://www.analog.com/static/imported-files/data_sheets/ADT7410.pdf * Analog Devices ADT7420 + Prefix: 'adt7420' + Addresses scanned: None + Datasheet: Publicly available at the Analog Devices website - http://www.analog.com/static/imported-files/data_sheets/ADT7420.pdf + + http://www.analog.com/static/imported-files/data_sheets/ADT7420.pdf + * Analog Devices ADT7310 + Prefix: 'adt7310' + Addresses scanned: None + Datasheet: Publicly available at the Analog Devices website - http://www.analog.com/static/imported-files/data_sheets/ADT7310.pdf + + http://www.analog.com/static/imported-files/data_sheets/ADT7310.pdf + * Analog Devices ADT7320 + Prefix: 'adt7320' + Addresses scanned: None + Datasheet: Publicly available at the Analog Devices website - http://www.analog.com/static/imported-files/data_sheets/ADT7320.pdf + + http://www.analog.com/static/imported-files/data_sheets/ADT7320.pdf Author: Hartmut Knaack @@ -61,13 +80,15 @@ The device is set to 16 bit resolution and comparator mode. sysfs-Interface --------------- -temp#_input - temperature input -temp#_min - temperature minimum setpoint -temp#_max - temperature maximum setpoint -temp#_crit - critical temperature setpoint -temp#_min_hyst - hysteresis for temperature minimum (read-only) -temp#_max_hyst - hysteresis for temperature maximum (read/write) -temp#_crit_hyst - hysteresis for critical temperature (read-only) -temp#_min_alarm - temperature minimum alarm flag -temp#_max_alarm - temperature maximum alarm flag -temp#_crit_alarm - critical temperature alarm flag +======================== ==================================================== +temp#_input temperature input +temp#_min temperature minimum setpoint +temp#_max temperature maximum setpoint +temp#_crit critical temperature setpoint +temp#_min_hyst hysteresis for temperature minimum (read-only) +temp#_max_hyst hysteresis for temperature maximum (read/write) +temp#_crit_hyst hysteresis for critical temperature (read-only) +temp#_min_alarm temperature minimum alarm flag +temp#_max_alarm temperature maximum alarm flag +temp#_crit_alarm critical temperature alarm flag +======================== ==================================================== diff --git a/Documentation/hwmon/adt7411 b/Documentation/hwmon/adt7411 index 1632960f9745..57ad16fb216a 100644 --- a/Documentation/hwmon/adt7411 +++ b/Documentation/hwmon/adt7411 @@ -2,9 +2,13 @@ Kernel driver adt7411 ===================== Supported chips: + * Analog Devices ADT7411 + Prefix: 'adt7411' + Addresses scanned: 0x48, 0x4a, 0x4b + Datasheet: Publicly available at the Analog Devices website Author: Wolfram Sang (based on adt7470 by Darrick J. Wong) @@ -26,15 +30,19 @@ Check the datasheet for details. sysfs-Interface --------------- -in0_input - vdd voltage input -in[1-8]_input - analog 1-8 input -temp1_input - temperature input +================ ================= +in0_input vdd voltage input +in[1-8]_input analog 1-8 input +temp1_input temperature input +================ ================= Besides standard interfaces, this driver adds (0 = off, 1 = on): - adc_ref_vdd - Use vdd as reference instead of 2.25 V - fast_sampling - Sample at 22.5 kHz instead of 1.4 kHz, but drop filters - no_average - Turn off averaging over 16 samples + ============== ======================================================= + adc_ref_vdd Use vdd as reference instead of 2.25 V + fast_sampling Sample at 22.5 kHz instead of 1.4 kHz, but drop filters + no_average Turn off averaging over 16 samples + ============== ======================================================= Notes ----- diff --git a/Documentation/hwmon/adt7462 b/Documentation/hwmon/adt7462 index ec660b328275..a7a831118d32 100644 --- a/Documentation/hwmon/adt7462 +++ b/Documentation/hwmon/adt7462 @@ -1,10 +1,14 @@ Kernel driver adt7462 -====================== +===================== Supported chips: + * Analog Devices ADT7462 + Prefix: 'adt7462' + Addresses scanned: I2C 0x58, 0x5C + Datasheet: Publicly available at the Analog Devices website Author: Darrick J. Wong @@ -57,8 +61,8 @@ Besides standard interfaces driver adds the following: * pwm#_auto_point1_pwm and temp#_auto_point1_temp and * pwm#_auto_point2_pwm and temp#_auto_point2_temp - -point1: Set the pwm speed at a lower temperature bound. -point2: Set the pwm speed at a higher temperature bound. + - point1: Set the pwm speed at a lower temperature bound. + - point2: Set the pwm speed at a higher temperature bound. The ADT7462 will scale the pwm between the lower and higher pwm speed when the temperature is between the two temperature boundaries. PWM values range diff --git a/Documentation/hwmon/adt7470 b/Documentation/hwmon/adt7470 index fe68e18a0c8d..d225f816e992 100644 --- a/Documentation/hwmon/adt7470 +++ b/Documentation/hwmon/adt7470 @@ -2,9 +2,13 @@ Kernel driver adt7470 ===================== Supported chips: + * Analog Devices ADT7470 + Prefix: 'adt7470' + Addresses scanned: I2C 0x2C, 0x2E, 0x2F + Datasheet: Publicly available at the Analog Devices website Author: Darrick J. Wong @@ -56,8 +60,8 @@ Besides standard interfaces driver adds the following: * pwm#_auto_point1_pwm and pwm#_auto_point1_temp and * pwm#_auto_point2_pwm and pwm#_auto_point2_temp - -point1: Set the pwm speed at a lower temperature bound. -point2: Set the pwm speed at a higher temperature bound. + - point1: Set the pwm speed at a lower temperature bound. + - point2: Set the pwm speed at a higher temperature bound. The ADT7470 will scale the pwm between the lower and higher pwm speed when the temperature is between the two temperature boundaries. PWM values range diff --git a/Documentation/hwmon/adt7475 b/Documentation/hwmon/adt7475 index 01b46b290532..ef3ea1ea9bc1 100644 --- a/Documentation/hwmon/adt7475 +++ b/Documentation/hwmon/adt7475 @@ -2,28 +2,44 @@ Kernel driver adt7475 ===================== Supported chips: + * Analog Devices ADT7473 + Prefix: 'adt7473' + Addresses scanned: I2C 0x2C, 0x2D, 0x2E + Datasheet: Publicly available at the On Semiconductors website + * Analog Devices ADT7475 + Prefix: 'adt7475' + Addresses scanned: I2C 0x2E + Datasheet: Publicly available at the On Semiconductors website + * Analog Devices ADT7476 + Prefix: 'adt7476' + Addresses scanned: I2C 0x2C, 0x2D, 0x2E + Datasheet: Publicly available at the On Semiconductors website + * Analog Devices ADT7490 + Prefix: 'adt7490' + Addresses scanned: I2C 0x2C, 0x2D, 0x2E + Datasheet: Publicly available at the On Semiconductors website Authors: - Jordan Crouse - Hans de Goede - Darrick J. Wong (documentation) - Jean Delvare + - Jordan Crouse + - Hans de Goede + - Darrick J. Wong (documentation) + - Jean Delvare Description @@ -82,14 +98,16 @@ ADT7490: Sysfs Mapping ------------- - ADT7490 ADT7476 ADT7475 ADT7473 - ------- ------- ------- ------- +==== =========== =========== ========= ========== +in ADT7490 ADT7476 ADT7475 ADT7473 +==== =========== =========== ========= ========== in0 2.5VIN (22) 2.5VIN (22) - - in1 VCCP (23) VCCP (23) VCCP (14) VCCP (14) in2 VCC (4) VCC (4) VCC (4) VCC (3) in3 5VIN (20) 5VIN (20) in4 12VIN (21) 12VIN (21) in5 VTT (8) +==== =========== =========== ========= ========== Special Features ---------------- @@ -107,8 +125,8 @@ Fan Speed Control The driver exposes two trip points per PWM channel. -point1: Set the PWM speed at the lower temperature bound -point2: Set the PWM speed at the higher temperature bound +- point1: Set the PWM speed at the lower temperature bound +- point2: Set the PWM speed at the higher temperature bound The ADT747x will scale the PWM linearly between the lower and higher PWM speed when the temperature is between the two temperature boundaries. @@ -123,12 +141,12 @@ the PWM control exceeds temp#_max. At Tmin - hysteresis the PWM output can either be off (0% duty cycle) or at the minimum (i.e. auto_point1_pwm). This behaviour can be configured using the -pwm[1-*]_stall_disable sysfs attribute. A value of 0 means the fans will shut +`pwm[1-*]_stall_disable sysfs attribute`. A value of 0 means the fans will shut off. A value of 1 means the fans will run at auto_point1_pwm. The responsiveness of the ADT747x to temperature changes can be configured. This allows smoothing of the fan speed transition. To set the transition time -set the value in ms in the temp[1-*]_smoothing sysfs attribute. +set the value in ms in the `temp[1-*]_smoothing` sysfs attribute. Notes ----- diff --git a/Documentation/hwmon/amc6821 b/Documentation/hwmon/amc6821 index ced8359c50f8..d10eabcbc0f3 100644 --- a/Documentation/hwmon/amc6821 +++ b/Documentation/hwmon/amc6821 @@ -2,9 +2,13 @@ Kernel driver amc6821 ===================== Supported chips: + Texas Instruments AMC6821 + Prefix: 'amc6821' + Addresses scanned: 0x18, 0x19, 0x1a, 0x2c, 0x2d, 0x2e, 0x4c, 0x4d, 0x4e + Datasheet: http://focus.ti.com/docs/prod/folders/print/amc6821.html Authors: @@ -21,10 +25,11 @@ The pwm can be controlled either from software or automatically. The driver provides the following sensor accesses in sysfs: +======================= == =============================================== temp1_input ro on-chip temperature temp1_min rw " temp1_max rw " -temp1_crit rw " +temp1_crit rw " temp1_min_alarm ro " temp1_max_alarm ro " temp1_crit_alarm ro " @@ -32,16 +37,16 @@ temp1_crit_alarm ro " temp2_input ro remote temperature temp2_min rw " temp2_max rw " -temp2_crit rw " +temp2_crit rw " temp2_min_alarm ro " temp2_max_alarm ro " temp2_crit_alarm ro " temp2_fault ro " -fan1_input ro tachometer speed +fan1_input ro tachometer speed fan1_min rw " fan1_max rw " -fan1_fault ro " +fan1_fault ro " fan1_div rw Fan divisor can be either 2 or 4. pwm1 rw pwm1 @@ -87,6 +92,7 @@ temp2_auto_point3_temp rw Above this temperature fan runs at maximum values which depend on temp2_auto_point2_temp and pwm1_auto_point2_pwm. Read it out after writing to get actual value. +======================= == =============================================== Module parameters @@ -97,6 +103,7 @@ load the module with: init=0. If your board BIOS doesn't initialize the chip, or you want different settings, you can set the following parameters: -init=1, -pwminv: 0 default pwm output, 1 inverts pwm output. + +- init=1, +- pwminv: 0 default pwm output, 1 inverts pwm output. diff --git a/Documentation/hwmon/asb100 b/Documentation/hwmon/asb100 index ab7365e139be..311d9f7b6926 100644 --- a/Documentation/hwmon/asb100 +++ b/Documentation/hwmon/asb100 @@ -2,9 +2,13 @@ Kernel driver asb100 ==================== Supported Chips: + * Asus ASB100 and ASB100-A "Bach" + Prefix: 'asb100' + Addresses scanned: I2C 0x2d + Datasheet: none released Author: Mark M. Hoffman @@ -41,32 +45,30 @@ processor itself. It is a value in volts. Alarms: (TODO question marks indicate may or may not work) -0x0001 => in0 (?) -0x0002 => in1 (?) -0x0004 => in2 -0x0008 => in3 -0x0010 => temp1 (1) -0x0020 => temp2 -0x0040 => fan1 -0x0080 => fan2 -0x0100 => in4 -0x0200 => in5 (?) (2) -0x0400 => in6 (?) (2) -0x0800 => fan3 -0x1000 => chassis switch -0x2000 => temp3 - -Alarm Notes: - -(1) This alarm will only trigger if the hysteresis value is 127C. -I.e. it behaves the same as w83781d. - -(2) The min and max registers for these values appear to -be read-only or otherwise stuck at 0x00. +- 0x0001 => in0 (?) +- 0x0002 => in1 (?) +- 0x0004 => in2 +- 0x0008 => in3 +- 0x0010 => temp1 [1]_ +- 0x0020 => temp2 +- 0x0040 => fan1 +- 0x0080 => fan2 +- 0x0100 => in4 +- 0x0200 => in5 (?) [2]_ +- 0x0400 => in6 (?) [2]_ +- 0x0800 => fan3 +- 0x1000 => chassis switch +- 0x2000 => temp3 + +.. [1] This alarm will only trigger if the hysteresis value is 127C. + I.e. it behaves the same as w83781d. + +.. [2] The min and max registers for these values appear to + be read-only or otherwise stuck at 0x00. TODO: -* Experiment with fan divisors > 8. -* Experiment with temp. sensor types. -* Are there really 13 voltage inputs? Probably not... -* Cleanups, no doubt... + * Experiment with fan divisors > 8. + * Experiment with temp. sensor types. + * Are there really 13 voltage inputs? Probably not... + * Cleanups, no doubt... diff --git a/Documentation/hwmon/ds1621 b/Documentation/hwmon/ds1621 index fa3407997795..552b37e9dd34 100644 --- a/Documentation/hwmon/ds1621 +++ b/Documentation/hwmon/ds1621 @@ -2,42 +2,61 @@ Kernel driver ds1621 ==================== Supported chips: + * Dallas Semiconductor / Maxim Integrated DS1621 + Prefix: 'ds1621' + Addresses scanned: none + Datasheet: Publicly available from www.maximintegrated.com * Dallas Semiconductor DS1625 + Prefix: 'ds1625' + Addresses scanned: none + Datasheet: Publicly available from www.datasheetarchive.com * Maxim Integrated DS1631 + Prefix: 'ds1631' + Addresses scanned: none + Datasheet: Publicly available from www.maximintegrated.com * Maxim Integrated DS1721 + Prefix: 'ds1721' + Addresses scanned: none + Datasheet: Publicly available from www.maximintegrated.com * Maxim Integrated DS1731 + Prefix: 'ds1731' + Addresses scanned: none + Datasheet: Publicly available from www.maximintegrated.com Authors: - Christian W. Zuckschwerdt - valuable contributions by Jan M. Sendler - ported to 2.6 by Aurelien Jarno - with the help of Jean Delvare + - Christian W. Zuckschwerdt + - valuable contributions by Jan M. Sendler + - ported to 2.6 by Aurelien Jarno + with the help of Jean Delvare Module Parameters ------------------ * polarity int - Output's polarity: 0 = active high, 1 = active low + Output's polarity: + + * 0 = active high, + * 1 = active low Description ----------- @@ -87,28 +106,31 @@ are used internally, however, these flags do get set and cleared as the actual temperature crosses the min or max settings (which by default are set to 75 and 80 degrees respectively). -Temperature Conversion: ------------------------ -DS1621 - 750ms (older devices may take up to 1000ms) -DS1625 - 500ms -DS1631 - 93ms..750ms for 9..12 bits resolution, respectively. -DS1721 - 93ms..750ms for 9..12 bits resolution, respectively. -DS1731 - 93ms..750ms for 9..12 bits resolution, respectively. +Temperature Conversion +---------------------- + +- DS1621 - 750ms (older devices may take up to 1000ms) +- DS1625 - 500ms +- DS1631 - 93ms..750ms for 9..12 bits resolution, respectively. +- DS1721 - 93ms..750ms for 9..12 bits resolution, respectively. +- DS1731 - 93ms..750ms for 9..12 bits resolution, respectively. Note: On the DS1621, internal access to non-volatile registers may last for 10ms or less (unverified on the other devices). -Temperature Accuracy: ---------------------- -DS1621: +/- 0.5 degree Celsius (from 0 to +70 degrees) -DS1625: +/- 0.5 degree Celsius (from 0 to +70 degrees) -DS1631: +/- 0.5 degree Celsius (from 0 to +70 degrees) -DS1721: +/- 1.0 degree Celsius (from -10 to +85 degrees) -DS1731: +/- 1.0 degree Celsius (from -10 to +85 degrees) +Temperature Accuracy +-------------------- -Note: -Please refer to the device datasheets for accuracy at other temperatures. +- DS1621: +/- 0.5 degree Celsius (from 0 to +70 degrees) +- DS1625: +/- 0.5 degree Celsius (from 0 to +70 degrees) +- DS1631: +/- 0.5 degree Celsius (from 0 to +70 degrees) +- DS1721: +/- 1.0 degree Celsius (from -10 to +85 degrees) +- DS1731: +/- 1.0 degree Celsius (from -10 to +85 degrees) + +.. Note:: + + Please refer to the device datasheets for accuracy at other temperatures. Temperature Resolution: ----------------------- @@ -117,60 +139,67 @@ support, which is achieved via the R0 and R1 config register bits, where: R0..R1 ------ - 0 0 => 9 bits, 0.5 degrees Celsius - 1 0 => 10 bits, 0.25 degrees Celsius - 0 1 => 11 bits, 0.125 degrees Celsius - 1 1 => 12 bits, 0.0625 degrees Celsius -Note: -At initial device power-on, the default resolution is set to 12-bits. +== == =============================== +R0 R1 +== == =============================== + 0 0 9 bits, 0.5 degrees Celsius + 1 0 10 bits, 0.25 degrees Celsius + 0 1 11 bits, 0.125 degrees Celsius + 1 1 12 bits, 0.0625 degrees Celsius +== == =============================== + +.. Note:: + + At initial device power-on, the default resolution is set to 12-bits. The resolution mode for the DS1631, DS1721, or DS1731 can be changed from userspace, via the device 'update_interval' sysfs attribute. This attribute will normalize the range of input values to the device maximum resolution values defined in the datasheet as follows: +============= ================== =============== Resolution Conversion Time Input Range (C/LSB) (msec) (msec) ------------------------------------------------- +============= ================== =============== 0.5 93.75 0....94 0.25 187.5 95...187 0.125 375 188..375 0.0625 750 376..infinity ------------------------------------------------- +============= ================== =============== The following examples show how the 'update_interval' attribute can be -used to change the conversion time: - -$ cat update_interval -750 -$ cat temp1_input -22062 -$ -$ echo 300 > update_interval -$ cat update_interval -375 -$ cat temp1_input -22125 -$ -$ echo 150 > update_interval -$ cat update_interval -188 -$ cat temp1_input -22250 -$ -$ echo 1 > update_interval -$ cat update_interval -94 -$ cat temp1_input -22000 -$ -$ echo 1000 > update_interval -$ cat update_interval -750 -$ cat temp1_input -22062 -$ +used to change the conversion time:: + + $ cat update_interval + 750 + $ cat temp1_input + 22062 + $ + $ echo 300 > update_interval + $ cat update_interval + 375 + $ cat temp1_input + 22125 + $ + $ echo 150 > update_interval + $ cat update_interval + 188 + $ cat temp1_input + 22250 + $ + $ echo 1 > update_interval + $ cat update_interval + 94 + $ cat temp1_input + 22000 + $ + $ echo 1000 > update_interval + $ cat update_interval + 750 + $ cat temp1_input + 22062 + $ As shown, the ds1621 driver automatically adjusts the 'update_interval' user input, via a step function. Reading back the 'update_interval' value @@ -182,6 +211,7 @@ via the following function: g(x) = 0.5 * [minimum_conversion_time/x] where: - -> 'x' = the output from 'update_interval' - -> 'g(x)' = the resolution in degrees C per LSB. - -> 93.75ms = minimum conversion time + + - 'x' = the output from 'update_interval' + - 'g(x)' = the resolution in degrees C per LSB. + - 93.75ms = minimum conversion time diff --git a/Documentation/hwmon/ds620 b/Documentation/hwmon/ds620 index 1fbe3cd916cc..2d686b17b547 100644 --- a/Documentation/hwmon/ds620 +++ b/Documentation/hwmon/ds620 @@ -2,15 +2,19 @@ Kernel driver ds620 =================== Supported chips: + * Dallas Semiconductor DS620 + Prefix: 'ds620' + Datasheet: Publicly available at the Dallas Semiconductor website - http://www.dalsemi.com/ + + http://www.dalsemi.com/ Authors: - Roland Stigge - based on ds1621.c by - Christian W. Zuckschwerdt + Roland Stigge + based on ds1621.c by + Christian W. Zuckschwerdt Description ----------- diff --git a/Documentation/hwmon/emc1403 b/Documentation/hwmon/emc1403 index a869b0ef6a9d..3a4913b63ef3 100644 --- a/Documentation/hwmon/emc1403 +++ b/Documentation/hwmon/emc1403 @@ -2,28 +2,48 @@ Kernel driver emc1403 ===================== Supported chips: + * SMSC / Microchip EMC1402, EMC1412 + Addresses scanned: I2C 0x18, 0x1c, 0x29, 0x4c, 0x4d, 0x5c + Prefix: 'emc1402' + Datasheets: - http://ww1.microchip.com/downloads/en/DeviceDoc/1412.pdf - http://ww1.microchip.com/downloads/en/DeviceDoc/1402.pdf + + - http://ww1.microchip.com/downloads/en/DeviceDoc/1412.pdf + - http://ww1.microchip.com/downloads/en/DeviceDoc/1402.pdf + * SMSC / Microchip EMC1403, EMC1404, EMC1413, EMC1414 + Addresses scanned: I2C 0x18, 0x29, 0x4c, 0x4d + Prefix: 'emc1403', 'emc1404' + Datasheets: - http://ww1.microchip.com/downloads/en/DeviceDoc/1403_1404.pdf - http://ww1.microchip.com/downloads/en/DeviceDoc/1413_1414.pdf + + - http://ww1.microchip.com/downloads/en/DeviceDoc/1403_1404.pdf + - http://ww1.microchip.com/downloads/en/DeviceDoc/1413_1414.pdf + * SMSC / Microchip EMC1422 + Addresses scanned: I2C 0x4c + Prefix: 'emc1422' + Datasheet: - http://ww1.microchip.com/downloads/en/DeviceDoc/1422.pdf + + - http://ww1.microchip.com/downloads/en/DeviceDoc/1422.pdf + * SMSC / Microchip EMC1423, EMC1424 + Addresses scanned: I2C 0x4c + Prefix: 'emc1423', 'emc1424' + Datasheet: - http://ww1.microchip.com/downloads/en/DeviceDoc/1423_1424.pdf + + - http://ww1.microchip.com/downloads/en/DeviceDoc/1423_1424.pdf Author: Kalhan Trisal @@ -38,5 +42,6 @@ Known Systems With EMC6W201 The EMC6W201 is a rare device, only found on a few systems, made in 2005 and 2006. Known systems with this device: + * Dell Precision 670 workstation * Gigabyte 2CEWH mainboard diff --git a/Documentation/hwmon/f71805f b/Documentation/hwmon/f71805f index 48a356084bc6..1efe5e5d337c 100644 --- a/Documentation/hwmon/f71805f +++ b/Documentation/hwmon/f71805f @@ -2,17 +2,29 @@ Kernel driver f71805f ===================== Supported chips: + * Fintek F71805F/FG + Prefix: 'f71805f' + Addresses scanned: none, address read from Super I/O config space + Datasheet: Available from the Fintek website + * Fintek F71806F/FG + Prefix: 'f71872f' + Addresses scanned: none, address read from Super I/O config space + Datasheet: Available from the Fintek website + * Fintek F71872F/FG + Prefix: 'f71872f' + Addresses scanned: none, address read from Super I/O config space + Datasheet: Available from the Fintek website Author: Jean Delvare @@ -64,24 +76,26 @@ you can only set the limits in steps of 32 mV (before scaling). The wirings and resistor values suggested by Fintek are as follow: - pin expected - name use R1 R2 divider raw val. - +======= ======= =========== ==== ======= ============ ============== +in pin expected + name use R1 R2 divider raw val. +======= ======= =========== ==== ======= ============ ============== in0 VCC VCC3.3V int. int. 2.00 1.65 V in1 VIN1 VTT1.2V 10K - 1.00 1.20 V -in2 VIN2 VRAM 100K 100K 2.00 ~1.25 V (1) -in3 VIN3 VCHIPSET 47K 100K 1.47 2.24 V (2) +in2 VIN2 VRAM 100K 100K 2.00 ~1.25 V [1]_ +in3 VIN3 VCHIPSET 47K 100K 1.47 2.24 V [2]_ in4 VIN4 VCC5V 200K 47K 5.25 0.95 V in5 VIN5 +12V 200K 20K 11.00 1.05 V in6 VIN6 VCC1.5V 10K - 1.00 1.50 V -in7 VIN7 VCORE 10K - 1.00 ~1.40 V (1) +in7 VIN7 VCORE 10K - 1.00 ~1.40 V [1]_ in8 VIN8 VSB5V 200K 47K 1.00 0.95 V -in10 VSB VSB3.3V int. int. 2.00 1.65 V (3) -in9 VBAT VBATTERY int. int. 2.00 1.50 V (3) +in10 VSB VSB3.3V int. int. 2.00 1.65 V [3]_ +in9 VBAT VBATTERY int. int. 2.00 1.50 V [3]_ +======= ======= =========== ==== ======= ============ ============== -(1) Depends on your hardware setup. -(2) Obviously not correct, swapping R1 and R2 would make more sense. -(3) F71872F/FG only. +.. [1] Depends on your hardware setup. +.. [2] Obviously not correct, swapping R1 and R2 would make more sense. +.. [3] F71872F/FG only. These values can be used as hints at best, as motherboard manufacturers are free to use a completely different setup. As a matter of fact, the diff --git a/Documentation/hwmon/f71882fg b/Documentation/hwmon/f71882fg index 4c3cb8377d74..5c0b7b0db150 100644 --- a/Documentation/hwmon/f71882fg +++ b/Documentation/hwmon/f71882fg @@ -2,60 +2,114 @@ Kernel driver f71882fg ====================== Supported chips: + * Fintek F71808E + Prefix: 'f71808e' + Addresses scanned: none, address read from Super I/O config space + Datasheet: Not public + * Fintek F71808A + Prefix: 'f71808a' + Addresses scanned: none, address read from Super I/O config space + Datasheet: Not public + * Fintek F71858FG + Prefix: 'f71858fg' + Addresses scanned: none, address read from Super I/O config space + Datasheet: Available from the Fintek website + * Fintek F71862FG and F71863FG + Prefix: 'f71862fg' + Addresses scanned: none, address read from Super I/O config space + Datasheet: Available from the Fintek website + * Fintek F71869F and F71869E + Prefix: 'f71869' + Addresses scanned: none, address read from Super I/O config space + Datasheet: Available from the Fintek website + * Fintek F71869A + Prefix: 'f71869a' + Addresses scanned: none, address read from Super I/O config space + Datasheet: Not public + * Fintek F71882FG and F71883FG + Prefix: 'f71882fg' + Addresses scanned: none, address read from Super I/O config space + Datasheet: Available from the Fintek website + * Fintek F71889FG + Prefix: 'f71889fg' + Addresses scanned: none, address read from Super I/O config space + Datasheet: Available from the Fintek website + * Fintek F71889ED + Prefix: 'f71889ed' + Addresses scanned: none, address read from Super I/O config space + Datasheet: Should become available on the Fintek website soon + * Fintek F71889A + Prefix: 'f71889a' + Addresses scanned: none, address read from Super I/O config space + Datasheet: Should become available on the Fintek website soon + * Fintek F8000 + Prefix: 'f8000' + Addresses scanned: none, address read from Super I/O config space + Datasheet: Not public + * Fintek F81801U + Prefix: 'f71889fg' + Addresses scanned: none, address read from Super I/O config space + Datasheet: Not public - Note: This is the 64-pin variant of the F71889FG, they have the + + Note: + This is the 64-pin variant of the F71889FG, they have the same device ID and are fully compatible as far as hardware monitoring is concerned. + * Fintek F81865F + Prefix: 'f81865f' + Addresses scanned: none, address read from Super I/O config space + Datasheet: Available from the Fintek website Author: Hans de Goede diff --git a/Documentation/hwmon/ftsteutates b/Documentation/hwmon/ftsteutates index af54db92391b..58a2483d8d0d 100644 --- a/Documentation/hwmon/ftsteutates +++ b/Documentation/hwmon/ftsteutates @@ -1,9 +1,12 @@ Kernel driver ftsteutates -===================== +========================= Supported chips: + * FTS Teutates + Prefix: 'ftsteutates' + Addresses scanned: I2C 0x73 (7-Bit) Author: Thilo Cestonaro @@ -11,6 +14,7 @@ Author: Thilo Cestonaro Description ----------- + The BMC Teutates is the Eleventh generation of Superior System monitoring and thermal management solution. It is builds on the basic functionality of the BMC Theseus and contains several new features and @@ -19,9 +23,11 @@ enhancements. It can monitor up to 4 voltages, 16 temperatures and implemented in this driver. To clear a temperature or fan alarm, execute the following command with the -correct path to the alarm file: +correct path to the alarm file:: + echo 0 >XXXX_alarm Specification of the chip can be found here: -ftp://ftp.ts.fujitsu.com/pub/Mainboard-OEM-Sales/Services/Software&Tools/Linux_SystemMonitoring&Watchdog&GPIO/BMC-Teutates_Specification_V1.21.pdf -ftp://ftp.ts.fujitsu.com/pub/Mainboard-OEM-Sales/Services/Software&Tools/Linux_SystemMonitoring&Watchdog&GPIO/Fujitsu_mainboards-1-Sensors_HowTo-en-US.pdf + +- ftp://ftp.ts.fujitsu.com/pub/Mainboard-OEM-Sales/Services/Software&Tools/Linux_SystemMonitoring&Watchdog&GPIO/BMC-Teutates_Specification_V1.21.pdf +- ftp://ftp.ts.fujitsu.com/pub/Mainboard-OEM-Sales/Services/Software&Tools/Linux_SystemMonitoring&Watchdog&GPIO/Fujitsu_mainboards-1-Sensors_HowTo-en-US.pdf diff --git a/Documentation/hwmon/g760a b/Documentation/hwmon/g760a index cfc894537061..d82952cc8319 100644 --- a/Documentation/hwmon/g760a +++ b/Documentation/hwmon/g760a @@ -2,9 +2,13 @@ Kernel driver g760a =================== Supported chips: + * Global Mixed-mode Technology Inc. G760A + Prefix: 'g760a' + Datasheet: Publicly available at the GMT website + http://www.gmt.com.tw/product/datasheet/EDS-760A.pdf Author: Herbert Valerio Riedel diff --git a/Documentation/hwmon/g762 b/Documentation/hwmon/g762 index 923db9c5b5bc..54574e26df21 100644 --- a/Documentation/hwmon/g762 +++ b/Documentation/hwmon/g762 @@ -21,34 +21,43 @@ documented in Documentation/devicetree/bindings/hwmon/g762.txt or using a specific platform_data structure in board initialization file (see include/linux/platform_data/g762.h). - fan1_target: set desired fan speed. This only makes sense in closed-loop - fan speed control (i.e. when pwm1_enable is set to 2). + fan1_target: + set desired fan speed. This only makes sense in closed-loop + fan speed control (i.e. when pwm1_enable is set to 2). - fan1_input: provide current fan rotation value in RPM as reported by - the fan to the device. + fan1_input: + provide current fan rotation value in RPM as reported by + the fan to the device. - fan1_div: fan clock divisor. Supported value are 1, 2, 4 and 8. + fan1_div: + fan clock divisor. Supported value are 1, 2, 4 and 8. - fan1_pulses: number of pulses per fan revolution. Supported values - are 2 and 4. + fan1_pulses: + number of pulses per fan revolution. Supported values + are 2 and 4. - fan1_fault: reports fan failure, i.e. no transition on fan gear pin for - about 0.7s (if the fan is not voluntarily set off). + fan1_fault: + reports fan failure, i.e. no transition on fan gear pin for + about 0.7s (if the fan is not voluntarily set off). - fan1_alarm: in closed-loop control mode, if fan RPM value is 25% out - of the programmed value for over 6 seconds 'fan1_alarm' is - set to 1. + fan1_alarm: + in closed-loop control mode, if fan RPM value is 25% out + of the programmed value for over 6 seconds 'fan1_alarm' is + set to 1. - pwm1_enable: set current fan speed control mode i.e. 1 for manual fan - speed control (open-loop) via pwm1 described below, 2 for - automatic fan speed control (closed-loop) via fan1_target - above. + pwm1_enable: + set current fan speed control mode i.e. 1 for manual fan + speed control (open-loop) via pwm1 described below, 2 for + automatic fan speed control (closed-loop) via fan1_target + above. - pwm1_mode: set or get fan driving mode: 1 for PWM mode, 0 for DC mode. + pwm1_mode: + set or get fan driving mode: 1 for PWM mode, 0 for DC mode. - pwm1: get or set PWM fan control value in open-loop mode. This is an - integer value between 0 and 255. 0 stops the fan, 255 makes - it run at full speed. + pwm1: + get or set PWM fan control value in open-loop mode. This is an + integer value between 0 and 255. 0 stops the fan, 255 makes + it run at full speed. Both in PWM mode ('pwm1_mode' set to 1) and DC mode ('pwm1_mode' set to 0), when current fan speed control mode is open-loop ('pwm1_enable' set to 1), diff --git a/Documentation/hwmon/gl518sm b/Documentation/hwmon/gl518sm index 494bb55b6e72..bf1e0b5e824b 100644 --- a/Documentation/hwmon/gl518sm +++ b/Documentation/hwmon/gl518sm @@ -2,27 +2,34 @@ Kernel driver gl518sm ===================== Supported chips: + * Genesys Logic GL518SM release 0x00 + Prefix: 'gl518sm' + Addresses scanned: I2C 0x2c and 0x2d + * Genesys Logic GL518SM release 0x80 + Prefix: 'gl518sm' + Addresses scanned: I2C 0x2c and 0x2d + Datasheet: http://www.genesyslogic.com/ Authors: - Frodo Looijaard , - Kyösti Mälkki - Hong-Gunn Chew - Jean Delvare + - Frodo Looijaard , + - Kyösti Mälkki + - Hong-Gunn Chew + - Jean Delvare Description ----------- -IMPORTANT: +.. important:: -For the revision 0x00 chip, the in0, in1, and in2 values (+5V, +3V, -and +12V) CANNOT be read. This is a limitation of the chip, not the driver. + For the revision 0x00 chip, the in0, in1, and in2 values (+5V, +3V, + and +12V) CANNOT be read. This is a limitation of the chip, not the driver. This driver supports the Genesys Logic GL518SM chip. There are at least two revision of this chip, which we call revision 0x00 and 0x80. Revision diff --git a/Documentation/hwmon/hih6130 b/Documentation/hwmon/hih6130 index 73dae918ea7b..649bd4be4fc2 100644 --- a/Documentation/hwmon/hih6130 +++ b/Documentation/hwmon/hih6130 @@ -2,11 +2,16 @@ Kernel driver hih6130 ===================== Supported chips: + * Honeywell HIH-6130 / HIH-6131 + Prefix: 'hih6130' + Addresses scanned: none + Datasheet: Publicly available at the Honeywell website - http://sensing.honeywell.com/index.php?ci_id=3106&la_id=1&defId=44872 + + http://sensing.honeywell.com/index.php?ci_id=3106&la_id=1&defId=44872 Author: Iain Paton @@ -28,8 +33,11 @@ instantiate I2C devices. sysfs-Interface --------------- -temp1_input - temperature input -humidity1_input - humidity input +temp1_input + temperature input + +humidity1_input + humidity input Notes ----- diff --git a/Documentation/hwmon/hwmon-kernel-api.txt b/Documentation/hwmon/hwmon-kernel-api.txt index f8e2ab5c21b9..b347b959fcda 100644 --- a/Documentation/hwmon/hwmon-kernel-api.txt +++ b/Documentation/hwmon/hwmon-kernel-api.txt @@ -1,5 +1,5 @@ -The Linux Hardware Monitoring kernel API. -========================================= +The Linux Hardware Monitoring kernel API +======================================== Guenter Roeck @@ -21,33 +21,34 @@ The API ------- Each hardware monitoring driver must #include and, in most cases, . linux/hwmon.h declares the following -register/unregister functions: - -struct device * -hwmon_device_register_with_groups(struct device *dev, const char *name, - void *drvdata, - const struct attribute_group **groups); - -struct device * -devm_hwmon_device_register_with_groups(struct device *dev, - const char *name, void *drvdata, - const struct attribute_group **groups); - -struct device * -hwmon_device_register_with_info(struct device *dev, - const char *name, void *drvdata, - const struct hwmon_chip_info *info, - const struct attribute_group **extra_groups); - -struct device * -devm_hwmon_device_register_with_info(struct device *dev, - const char *name, - void *drvdata, - const struct hwmon_chip_info *info, - const struct attribute_group **extra_groups); - -void hwmon_device_unregister(struct device *dev); -void devm_hwmon_device_unregister(struct device *dev); +register/unregister functions:: + + struct device * + hwmon_device_register_with_groups(struct device *dev, const char *name, + void *drvdata, + const struct attribute_group **groups); + + struct device * + devm_hwmon_device_register_with_groups(struct device *dev, + const char *name, void *drvdata, + const struct attribute_group **groups); + + struct device * + hwmon_device_register_with_info(struct device *dev, + const char *name, void *drvdata, + const struct hwmon_chip_info *info, + const struct attribute_group **extra_groups); + + struct device * + devm_hwmon_device_register_with_info(struct device *dev, + const char *name, + void *drvdata, + const struct hwmon_chip_info *info, + const struct attribute_group **extra_groups); + + void hwmon_device_unregister(struct device *dev); + + void devm_hwmon_device_unregister(struct device *dev); hwmon_device_register_with_groups registers a hardware monitoring device. The first parameter of this function is a pointer to the parent device. @@ -100,78 +101,89 @@ Using devm_hwmon_device_register_with_info() hwmon_device_register_with_info() registers a hardware monitoring device. The parameters to this function are -struct device *dev Pointer to parent device -const char *name Device name -void *drvdata Driver private data -const struct hwmon_chip_info *info - Pointer to chip description. -const struct attribute_group **extra_groups - Null-terminated list of additional non-standard - sysfs attribute groups. +=============================================== =============================================== +`struct device *dev` Pointer to parent device +`const char *name` Device name +`void *drvdata` Driver private data +`const struct hwmon_chip_info *info` Pointer to chip description. +`const struct attribute_group **extra_groups` Null-terminated list of additional non-standard + sysfs attribute groups. +=============================================== =============================================== This function returns a pointer to the created hardware monitoring device on success and a negative error code for failure. -The hwmon_chip_info structure looks as follows. +The hwmon_chip_info structure looks as follows:: -struct hwmon_chip_info { - const struct hwmon_ops *ops; - const struct hwmon_channel_info **info; -}; + struct hwmon_chip_info { + const struct hwmon_ops *ops; + const struct hwmon_channel_info **info; + }; It contains the following fields: -* ops: Pointer to device operations. -* info: NULL-terminated list of device channel descriptors. +* ops: + Pointer to device operations. +* info: + NULL-terminated list of device channel descriptors. -The list of hwmon operations is defined as: +The list of hwmon operations is defined as:: -struct hwmon_ops { + struct hwmon_ops { umode_t (*is_visible)(const void *, enum hwmon_sensor_types type, u32 attr, int); int (*read)(struct device *, enum hwmon_sensor_types type, u32 attr, int, long *); int (*write)(struct device *, enum hwmon_sensor_types type, u32 attr, int, long); -}; + }; It defines the following operations. -* is_visible: Pointer to a function to return the file mode for each supported - attribute. This function is mandatory. +* is_visible: + Pointer to a function to return the file mode for each supported + attribute. This function is mandatory. -* read: Pointer to a function for reading a value from the chip. This function - is optional, but must be provided if any readable attributes exist. +* read: + Pointer to a function for reading a value from the chip. This function + is optional, but must be provided if any readable attributes exist. -* write: Pointer to a function for writing a value to the chip. This function is - optional, but must be provided if any writeable attributes exist. +* write: + Pointer to a function for writing a value to the chip. This function is + optional, but must be provided if any writeable attributes exist. Each sensor channel is described with struct hwmon_channel_info, which is -defined as follows. +defined as follows:: -struct hwmon_channel_info { - enum hwmon_sensor_types type; - u32 *config; -}; + struct hwmon_channel_info { + enum hwmon_sensor_types type; + u32 *config; + }; It contains following fields: -* type: The hardware monitoring sensor type. - Supported sensor types are - * hwmon_chip A virtual sensor type, used to describe attributes - * which are not bound to a specific input or output - * hwmon_temp Temperature sensor - * hwmon_in Voltage sensor - * hwmon_curr Current sensor - * hwmon_power Power sensor - * hwmon_energy Energy sensor - * hwmon_humidity Humidity sensor - * hwmon_fan Fan speed sensor - * hwmon_pwm PWM control - -* config: Pointer to a 0-terminated list of configuration values for each - sensor of the given type. Each value is a combination of bit values - describing the attributes supposed by a single sensor. +* type: + The hardware monitoring sensor type. + + Supported sensor types are + + ================== ================================================== + hwmon_chip A virtual sensor type, used to describe attributes + which are not bound to a specific input or output + hwmon_temp Temperature sensor + hwmon_in Voltage sensor + hwmon_curr Current sensor + hwmon_power Power sensor + hwmon_energy Energy sensor + hwmon_humidity Humidity sensor + hwmon_fan Fan speed sensor + hwmon_pwm PWM control + ================== ================================================== + +* config: + Pointer to a 0-terminated list of configuration values for each + sensor of the given type. Each value is a combination of bit values + describing the attributes supposed by a single sensor. As an example, here is the complete description file for a LM75 compatible sensor chip. The chip has a single temperature sensor. The driver wants to @@ -179,61 +191,62 @@ register with the thermal subsystem (HWMON_C_REGISTER_TZ), and it supports the update_interval attribute (HWMON_C_UPDATE_INTERVAL). The chip supports reading the temperature (HWMON_T_INPUT), it has a maximum temperature register (HWMON_T_MAX) as well as a maximum temperature hysteresis register -(HWMON_T_MAX_HYST). - -static const u32 lm75_chip_config[] = { - HWMON_C_REGISTER_TZ | HWMON_C_UPDATE_INTERVAL, - 0 -}; - -static const struct hwmon_channel_info lm75_chip = { - .type = hwmon_chip, - .config = lm75_chip_config, -}; - -static const u32 lm75_temp_config[] = { - HWMON_T_INPUT | HWMON_T_MAX | HWMON_T_MAX_HYST, - 0 -}; - -static const struct hwmon_channel_info lm75_temp = { - .type = hwmon_temp, - .config = lm75_temp_config, -}; - -static const struct hwmon_channel_info *lm75_info[] = { - &lm75_chip, - &lm75_temp, - NULL -}; - -The HWMON_CHANNEL_INFO() macro can and should be used when possible. -With this macro, the above example can be simplified to - -static const struct hwmon_channel_info *lm75_info[] = { - HWMON_CHANNEL_INFO(chip, - HWMON_C_REGISTER_TZ | HWMON_C_UPDATE_INTERVAL), - HWMON_CHANNEL_INFO(temp, - HWMON_T_INPUT | HWMON_T_MAX | HWMON_T_MAX_HYST), - NULL -}; - -The remaining declarations are as follows. - -static const struct hwmon_ops lm75_hwmon_ops = { - .is_visible = lm75_is_visible, - .read = lm75_read, - .write = lm75_write, -}; - -static const struct hwmon_chip_info lm75_chip_info = { - .ops = &lm75_hwmon_ops, - .info = lm75_info, -}; +(HWMON_T_MAX_HYST):: + + static const u32 lm75_chip_config[] = { + HWMON_C_REGISTER_TZ | HWMON_C_UPDATE_INTERVAL, + 0 + }; + + static const struct hwmon_channel_info lm75_chip = { + .type = hwmon_chip, + .config = lm75_chip_config, + }; + + static const u32 lm75_temp_config[] = { + HWMON_T_INPUT | HWMON_T_MAX | HWMON_T_MAX_HYST, + 0 + }; + + static const struct hwmon_channel_info lm75_temp = { + .type = hwmon_temp, + .config = lm75_temp_config, + }; + + static const struct hwmon_channel_info *lm75_info[] = { + &lm75_chip, + &lm75_temp, + NULL + }; + + The HWMON_CHANNEL_INFO() macro can and should be used when possible. + With this macro, the above example can be simplified to + + static const struct hwmon_channel_info *lm75_info[] = { + HWMON_CHANNEL_INFO(chip, + HWMON_C_REGISTER_TZ | HWMON_C_UPDATE_INTERVAL), + HWMON_CHANNEL_INFO(temp, + HWMON_T_INPUT | HWMON_T_MAX | HWMON_T_MAX_HYST), + NULL + }; + + The remaining declarations are as follows. + + static const struct hwmon_ops lm75_hwmon_ops = { + .is_visible = lm75_is_visible, + .read = lm75_read, + .write = lm75_write, + }; + + static const struct hwmon_chip_info lm75_chip_info = { + .ops = &lm75_hwmon_ops, + .info = lm75_info, + }; A complete list of bit values indicating individual attribute support is defined in include/linux/hwmon.h. Definition prefixes are as follows. +=============== ================================================= HWMON_C_xxxx Chip attributes, for use with hwmon_chip. HWMON_T_xxxx Temperature attributes, for use with hwmon_temp. HWMON_I_xxxx Voltage attributes, for use with hwmon_in. @@ -244,57 +257,76 @@ HWMON_E_xxxx Energy attributes, for use with hwmon_energy. HWMON_H_xxxx Humidity attributes, for use with hwmon_humidity. HWMON_F_xxxx Fan speed attributes, for use with hwmon_fan. HWMON_PWM_xxxx PWM control attributes, for use with hwmon_pwm. +=============== ================================================= Driver callback functions ------------------------- Each driver provides is_visible, read, and write functions. Parameters -and return values for those functions are as follows. +and return values for those functions are as follows:: -umode_t is_visible_func(const void *data, enum hwmon_sensor_types type, - u32 attr, int channel) + umode_t is_visible_func(const void *data, enum hwmon_sensor_types type, + u32 attr, int channel) Parameters: - data: Pointer to device private data structure. - type: The sensor type. - attr: Attribute identifier associated with a specific attribute. + data: + Pointer to device private data structure. + type: + The sensor type. + attr: + Attribute identifier associated with a specific attribute. For example, the attribute value for HWMON_T_INPUT would be hwmon_temp_input. For complete mappings of bit fields to attribute values please see include/linux/hwmon.h. - channel:The sensor channel number. + channel: + The sensor channel number. Return value: The file mode for this attribute. Typically, this will be 0 (the attribute will not be created), S_IRUGO, or 'S_IRUGO | S_IWUSR'. -int read_func(struct device *dev, enum hwmon_sensor_types type, - u32 attr, int channel, long *val) +:: + + int read_func(struct device *dev, enum hwmon_sensor_types type, + u32 attr, int channel, long *val) Parameters: - dev: Pointer to the hardware monitoring device. - type: The sensor type. - attr: Attribute identifier associated with a specific attribute. + dev: + Pointer to the hardware monitoring device. + type: + The sensor type. + attr: + Attribute identifier associated with a specific attribute. For example, the attribute value for HWMON_T_INPUT would be hwmon_temp_input. For complete mappings please see include/linux/hwmon.h. - channel:The sensor channel number. - val: Pointer to attribute value. + channel: + The sensor channel number. + val: + Pointer to attribute value. Return value: 0 on success, a negative error number otherwise. -int write_func(struct device *dev, enum hwmon_sensor_types type, - u32 attr, int channel, long val) +:: + + int write_func(struct device *dev, enum hwmon_sensor_types type, + u32 attr, int channel, long val) Parameters: - dev: Pointer to the hardware monitoring device. - type: The sensor type. - attr: Attribute identifier associated with a specific attribute. + dev: + Pointer to the hardware monitoring device. + type: + The sensor type. + attr: + Attribute identifier associated with a specific attribute. For example, the attribute value for HWMON_T_INPUT would be hwmon_temp_input. For complete mappings please see include/linux/hwmon.h. - channel:The sensor channel number. - val: The value to write to the chip. + channel: + The sensor channel number. + val: + The value to write to the chip. Return value: 0 on success, a negative error number otherwise. @@ -330,25 +362,25 @@ Standard functions, similar to DEVICE_ATTR_{RW,RO,WO}, have _show and _store appended to the provided function name. SENSOR_DEVICE_ATTR and its variants define a struct sensor_device_attribute -variable. This structure has the following fields. +variable. This structure has the following fields:: -struct sensor_device_attribute { - struct device_attribute dev_attr; - int index; -}; + struct sensor_device_attribute { + struct device_attribute dev_attr; + int index; + }; You can use to_sensor_dev_attr to get the pointer to this structure from the attribute read or write function. Its parameter is the device to which the attribute is attached. SENSOR_DEVICE_ATTR_2 and its variants define a struct sensor_device_attribute_2 -variable, which is defined as follows. +variable, which is defined as follows:: -struct sensor_device_attribute_2 { - struct device_attribute dev_attr; - u8 index; - u8 nr; -}; + struct sensor_device_attribute_2 { + struct device_attribute dev_attr; + u8 index; + u8 nr; + }; Use to_sensor_dev_attr_2 to get the pointer to this structure. Its parameter is the device to which the attribute is attached. diff --git a/Documentation/hwmon/ibmaem b/Documentation/hwmon/ibmaem index 1e0d59e000b4..f07a14a1c2f5 100644 --- a/Documentation/hwmon/ibmaem +++ b/Documentation/hwmon/ibmaem @@ -1,15 +1,21 @@ Kernel driver ibmaem -====================== +==================== This driver talks to the IBM Systems Director Active Energy Manager, known henceforth as AEM. Supported systems: + * Any recent IBM System X server with AEM support. + This includes the x3350, x3550, x3650, x3655, x3755, x3850 M2, - x3950 M2, and certain HC10/HS2x/LS2x/QS2x blades. The IPMI host interface + x3950 M2, and certain HC10/HS2x/LS2x/QS2x blades. + + The IPMI host interface driver ("ipmi-si") needs to be loaded for this driver to do anything. + Prefix: 'ibmaem' + Datasheet: Not available Author: Darrick J. Wong diff --git a/Documentation/hwmon/ina3221 b/Documentation/hwmon/ina3221 index ed3f22769d4b..1e34abb38b59 100644 --- a/Documentation/hwmon/ina3221 +++ b/Documentation/hwmon/ina3221 @@ -2,11 +2,16 @@ Kernel driver ina3221 ===================== Supported chips: + * Texas Instruments INA3221 + Prefix: 'ina3221' + Addresses: I2C 0x40 - 0x43 + Datasheet: Publicly available at the Texas Instruments website - http://www.ti.com/ + + http://www.ti.com/ Author: Andrew F. Davis @@ -21,20 +26,24 @@ and power are calculated host-side from these. Sysfs entries ------------- +======================= ======================================================= in[123]_label Voltage channel labels in[123]_enable Voltage channel enable controls in[123]_input Bus voltage(mV) channels curr[123]_input Current(mA) measurement channels shunt[123]_resistor Shunt resistance(uOhm) channels curr[123]_crit Critical alert current(mA) setting, activates the - corresponding alarm when the respective current - is above this value + corresponding alarm when the respective current + is above this value curr[123]_crit_alarm Critical alert current limit exceeded curr[123]_max Warning alert current(mA) setting, activates the - corresponding alarm when the respective current - average is above this value. + corresponding alarm when the respective current + average is above this value. curr[123]_max_alarm Warning alert current limit exceeded in[456]_input Shunt voltage(uV) for channels 1, 2, and 3 respectively samples Number of samples using in the averaging mode. - Supports the list of number of samples: + + Supports the list of number of samples: + 1, 4, 16, 64, 128, 256, 512, 1024 +======================= ======================================================= diff --git a/Documentation/hwmon/it87 b/Documentation/hwmon/it87 index fff6f6bf55bc..2d83f23bee93 100644 --- a/Documentation/hwmon/it87 +++ b/Documentation/hwmon/it87 @@ -2,105 +2,179 @@ Kernel driver it87 ================== Supported chips: + * IT8603E/IT8623E + Prefix: 'it8603' + Addresses scanned: from Super I/O config space (8 I/O ports) + Datasheet: Not publicly available + * IT8620E + Prefix: 'it8620' + Addresses scanned: from Super I/O config space (8 I/O ports) + * IT8628E + Prefix: 'it8628' + Addresses scanned: from Super I/O config space (8 I/O ports) + Datasheet: Not publicly available + * IT8705F + Prefix: 'it87' + Addresses scanned: from Super I/O config space (8 I/O ports) + Datasheet: Once publicly available at the ITE website, but no longer + * IT8712F + Prefix: 'it8712' + Addresses scanned: from Super I/O config space (8 I/O ports) + Datasheet: Once publicly available at the ITE website, but no longer + * IT8716F/IT8726F + Prefix: 'it8716' + Addresses scanned: from Super I/O config space (8 I/O ports) + Datasheet: Once publicly available at the ITE website, but no longer + * IT8718F + Prefix: 'it8718' + Addresses scanned: from Super I/O config space (8 I/O ports) + Datasheet: Once publicly available at the ITE website, but no longer + * IT8720F + Prefix: 'it8720' + Addresses scanned: from Super I/O config space (8 I/O ports) + Datasheet: Not publicly available + * IT8721F/IT8758E + Prefix: 'it8721' + Addresses scanned: from Super I/O config space (8 I/O ports) + Datasheet: Not publicly available + * IT8728F + Prefix: 'it8728' + Addresses scanned: from Super I/O config space (8 I/O ports) + Datasheet: Not publicly available + * IT8732F + Prefix: 'it8732' + Addresses scanned: from Super I/O config space (8 I/O ports) + Datasheet: Not publicly available + * IT8771E + Prefix: 'it8771' + Addresses scanned: from Super I/O config space (8 I/O ports) + Datasheet: Not publicly available + * IT8772E + Prefix: 'it8772' + Addresses scanned: from Super I/O config space (8 I/O ports) + Datasheet: Not publicly available + * IT8781F + Prefix: 'it8781' + Addresses scanned: from Super I/O config space (8 I/O ports) + Datasheet: Not publicly available + * IT8782F + Prefix: 'it8782' + Addresses scanned: from Super I/O config space (8 I/O ports) + Datasheet: Not publicly available + * IT8783E/F + Prefix: 'it8783' + Addresses scanned: from Super I/O config space (8 I/O ports) + Datasheet: Not publicly available + * IT8786E + Prefix: 'it8786' + Addresses scanned: from Super I/O config space (8 I/O ports) + Datasheet: Not publicly available + * IT8790E + Prefix: 'it8790' + Addresses scanned: from Super I/O config space (8 I/O ports) + Datasheet: Not publicly available + * SiS950 [clone of IT8705F] + Prefix: 'it87' + Addresses scanned: from Super I/O config space (8 I/O ports) + Datasheet: No longer be available + Authors: - Christophe Gauthron - Jean Delvare + - Christophe Gauthron + - Jean Delvare Module Parameters ----------------- * update_vbat: int - - 0 if vbat should report power on value, 1 if vbat should be updated after - each read. Default is 0. On some boards the battery voltage is provided - by either the battery or the onboard power supply. Only the first reading - at power on will be the actual battery voltage (which the chip does - automatically). On other boards the battery voltage is always fed to - the chip so can be read at any time. Excessive reading may decrease - battery life but no information is given in the datasheet. + 0 if vbat should report power on value, 1 if vbat should be updated after + each read. Default is 0. On some boards the battery voltage is provided + by either the battery or the onboard power supply. Only the first reading + at power on will be the actual battery voltage (which the chip does + automatically). On other boards the battery voltage is always fed to + the chip so can be read at any time. Excessive reading may decrease + battery life but no information is given in the datasheet. * fix_pwm_polarity int - - Force PWM polarity to active high (DANGEROUS). Some chips are - misconfigured by BIOS - PWM values would be inverted. This option tries - to fix this. Please contact your BIOS manufacturer and ask him for fix. + Force PWM polarity to active high (DANGEROUS). Some chips are + misconfigured by BIOS - PWM values would be inverted. This option tries + to fix this. Please contact your BIOS manufacturer and ask him for fix. Hardware Interfaces diff --git a/Documentation/hwmon/lineage-pem b/Documentation/hwmon/lineage-pem index 83b2ddc160c8..10c271dc20e8 100644 --- a/Documentation/hwmon/lineage-pem +++ b/Documentation/hwmon/lineage-pem @@ -2,11 +2,16 @@ Kernel driver lineage-pem ========================= Supported devices: + * Lineage Compact Power Line Power Entry Modules + Prefix: 'lineage-pem' + Addresses scanned: - + Documentation: - http://www.lineagepower.com/oem/pdf/CPLI2C.pdf + + http://www.lineagepower.com/oem/pdf/CPLI2C.pdf Author: Guenter Roeck @@ -31,9 +36,10 @@ which can be safely used to identify the chip. You will have to instantiate the devices explicitly. Example: the following will load the driver for a Lineage PEM at address 0x40 -on I2C bus #1: -$ modprobe lineage-pem -$ echo lineage-pem 0x40 > /sys/bus/i2c/devices/i2c-1/new_device +on I2C bus #1:: + + $ modprobe lineage-pem + $ echo lineage-pem 0x40 > /sys/bus/i2c/devices/i2c-1/new_device All Lineage CPL power entry modules have a built-in I2C bus master selector (PCA9541). To ensure device access, this driver should only be used as client @@ -51,6 +57,7 @@ Input voltage, input current, input power, and fan speed measurement is only supported on newer devices. The driver detects if those attributes are supported, and only creates respective sysfs entries if they are. +======================= =============================== in1_input Output voltage (mV) in1_min_alarm Output undervoltage alarm in1_max_alarm Output overvoltage alarm @@ -75,3 +82,4 @@ temp1_crit temp1_alarm temp1_crit_alarm temp1_fault +======================= =============================== diff --git a/Documentation/hwmon/lm63 b/Documentation/hwmon/lm63 index 4a00461512a6..f478132b0408 100644 --- a/Documentation/hwmon/lm63 +++ b/Documentation/hwmon/lm63 @@ -2,26 +2,43 @@ Kernel driver lm63 ================== Supported chips: + * National Semiconductor LM63 + Prefix: 'lm63' + Addresses scanned: I2C 0x4c + Datasheet: Publicly available at the National Semiconductor website - http://www.national.com/pf/LM/LM63.html + + http://www.national.com/pf/LM/LM63.html + * National Semiconductor LM64 + Prefix: 'lm64' + Addresses scanned: I2C 0x18 and 0x4e + Datasheet: Publicly available at the National Semiconductor website - http://www.national.com/pf/LM/LM64.html + + http://www.national.com/pf/LM/LM64.html + * National Semiconductor LM96163 + Prefix: 'lm96163' + Addresses scanned: I2C 0x4c + Datasheet: Publicly available at the National Semiconductor website - http://www.national.com/pf/LM/LM96163.html + + http://www.national.com/pf/LM/LM96163.html + Author: Jean Delvare Thanks go to Tyan and especially Alex Buckingham for setting up a remote access to their S4882 test platform for this driver. + http://www.tyan.com/ Description @@ -32,6 +49,7 @@ and control. The LM63 is basically an LM86 with fan speed monitoring and control capabilities added. It misses some of the LM86 features though: + - No low limit for local temperature. - No critical limit for local temperature. - Critical limit for remote temperature can be changed only once. We diff --git a/Documentation/hwmon/lm70 b/Documentation/hwmon/lm70 index c3a1f2ea017d..f259bc1fcd91 100644 --- a/Documentation/hwmon/lm70 +++ b/Documentation/hwmon/lm70 @@ -2,19 +2,30 @@ Kernel driver lm70 ================== Supported chips: + * National Semiconductor LM70 + Datasheet: http://www.national.com/pf/LM/LM70.html + * Texas Instruments TMP121/TMP123 + Information: http://focus.ti.com/docs/prod/folders/print/tmp121.html + * Texas Instruments TMP122/TMP124 + Information: http://www.ti.com/product/tmp122 + * National Semiconductor LM71 + Datasheet: http://www.ti.com/product/LM71 + * National Semiconductor LM74 + Datasheet: http://www.ti.com/product/LM74 + Author: - Kaiwan N Billimoria + Kaiwan N Billimoria Description ----------- diff --git a/Documentation/hwmon/lm73 b/Documentation/hwmon/lm73 index 8af059dcb642..1d6a46844e85 100644 --- a/Documentation/hwmon/lm73 +++ b/Documentation/hwmon/lm73 @@ -2,13 +2,20 @@ Kernel driver lm73 ================== Supported chips: + * Texas Instruments LM73 + Prefix: 'lm73' + Addresses scanned: I2C 0x48, 0x49, 0x4a, 0x4c, 0x4d, and 0x4e + Datasheet: Publicly available at the Texas Instruments website - http://www.ti.com/product/lm73 + + http://www.ti.com/product/lm73 + Author: Guillaume Ligneul + Documentation: Chris Verges @@ -29,17 +36,18 @@ conversion time via the 'update_interval' sysfs attribute for the device. This attribute will normalize ranges of input values to the maximum times defined for the resolution in the datasheet. + ============= ============= ============ Resolution Conv. Time Input Range (C/LSB) (msec) (msec) - -------------------------------------- + ============= ============= ============ 0.25 14 0..14 0.125 28 15..28 0.0625 56 29..56 0.03125 112 57..infinity - -------------------------------------- + ============= ============= ============ The following examples show how the 'update_interval' attribute can be -used to change the conversion time: +used to change the conversion time:: $ echo 0 > update_interval $ cat update_interval diff --git a/Documentation/hwmon/lm75 b/Documentation/hwmon/lm75 index 010583608f12..6fd4d2df5420 100644 --- a/Documentation/hwmon/lm75 +++ b/Documentation/hwmon/lm75 @@ -2,68 +2,130 @@ Kernel driver lm75 ================== Supported chips: + * National Semiconductor LM75 + Prefix: 'lm75' + Addresses scanned: I2C 0x48 - 0x4f + Datasheet: Publicly available at the National Semiconductor website - http://www.national.com/ + + http://www.national.com/ + * National Semiconductor LM75A + Prefix: 'lm75a' + Addresses scanned: I2C 0x48 - 0x4f + Datasheet: Publicly available at the National Semiconductor website - http://www.national.com/ + + http://www.national.com/ + * Dallas Semiconductor (now Maxim) DS75, DS1775, DS7505 + Prefixes: 'ds75', 'ds1775', 'ds7505' + Addresses scanned: none + Datasheet: Publicly available at the Maxim website - http://www.maximintegrated.com/ + + http://www.maximintegrated.com/ + * Maxim MAX6625, MAX6626, MAX31725, MAX31726 + Prefixes: 'max6625', 'max6626', 'max31725', 'max31726' + Addresses scanned: none + Datasheet: Publicly available at the Maxim website - http://www.maxim-ic.com/ + + http://www.maxim-ic.com/ + * Microchip (TelCom) TCN75 + Prefix: 'tcn75' + Addresses scanned: none + Datasheet: Publicly available at the Microchip website - http://www.microchip.com/ + + http://www.microchip.com/ + * Microchip MCP9800, MCP9801, MCP9802, MCP9803 + Prefix: 'mcp980x' + Addresses scanned: none + Datasheet: Publicly available at the Microchip website - http://www.microchip.com/ + + http://www.microchip.com/ + * Analog Devices ADT75 + Prefix: 'adt75' + Addresses scanned: none + Datasheet: Publicly available at the Analog Devices website - http://www.analog.com/adt75 + + http://www.analog.com/adt75 + * ST Microelectronics STDS75 + Prefix: 'stds75' + Addresses scanned: none + Datasheet: Publicly available at the ST website - http://www.st.com/internet/analog/product/121769.jsp + + http://www.st.com/internet/analog/product/121769.jsp + * ST Microelectronics STLM75 + Prefix: 'stlm75' + Addresses scanned: none + Datasheet: Publicly available at the ST website + https://www.st.com/resource/en/datasheet/stlm75.pdf + * Texas Instruments TMP100, TMP101, TMP105, TMP112, TMP75, TMP75C, TMP175, TMP275 + Prefixes: 'tmp100', 'tmp101', 'tmp105', 'tmp112', 'tmp175', 'tmp75', 'tmp75c', 'tmp275' + Addresses scanned: none + Datasheet: Publicly available at the Texas Instruments website - http://www.ti.com/product/tmp100 - http://www.ti.com/product/tmp101 - http://www.ti.com/product/tmp105 - http://www.ti.com/product/tmp112 - http://www.ti.com/product/tmp75 - http://www.ti.com/product/tmp75c - http://www.ti.com/product/tmp175 - http://www.ti.com/product/tmp275 + + http://www.ti.com/product/tmp100 + + http://www.ti.com/product/tmp101 + + http://www.ti.com/product/tmp105 + + http://www.ti.com/product/tmp112 + + http://www.ti.com/product/tmp75 + + http://www.ti.com/product/tmp75c + + http://www.ti.com/product/tmp175 + + http://www.ti.com/product/tmp275 + * NXP LM75B + Prefix: 'lm75b' + Addresses scanned: none + Datasheet: Publicly available at the NXP website - http://www.nxp.com/documents/data_sheet/LM75B.pdf + + http://www.nxp.com/documents/data_sheet/LM75B.pdf Author: Frodo Looijaard diff --git a/Documentation/hwmon/lm77 b/Documentation/hwmon/lm77 index bfc915fe3639..4ed3fe6b999a 100644 --- a/Documentation/hwmon/lm77 +++ b/Documentation/hwmon/lm77 @@ -2,11 +2,17 @@ Kernel driver lm77 ================== Supported chips: + * National Semiconductor LM77 + Prefix: 'lm77' + Addresses scanned: I2C 0x48 - 0x4b + Datasheet: Publicly available at the National Semiconductor website - http://www.national.com/ + + http://www.national.com/ + Author: Andras BALI @@ -25,6 +31,7 @@ register on the chip, which means that the relative difference between the limit and its hysteresis is always the same for all 3 limits. This implementation detail implies the following: + * When setting a limit, its hysteresis will automatically follow, the difference staying unchanged. For example, if the old critical limit was 80 degrees C, and the hysteresis was 75 degrees C, and you change diff --git a/Documentation/hwmon/lm78 b/Documentation/hwmon/lm78 index 4dd47731789f..cb7a4832f35e 100644 --- a/Documentation/hwmon/lm78 +++ b/Documentation/hwmon/lm78 @@ -2,19 +2,31 @@ Kernel driver lm78 ================== Supported chips: + * National Semiconductor LM78 / LM78-J + Prefix: 'lm78' + Addresses scanned: I2C 0x28 - 0x2f, ISA 0x290 (8 I/O ports) + Datasheet: Publicly available at the National Semiconductor website - http://www.national.com/ + + http://www.national.com/ + * National Semiconductor LM79 + Prefix: 'lm79' + Addresses scanned: I2C 0x28 - 0x2f, ISA 0x290 (8 I/O ports) + Datasheet: Publicly available at the National Semiconductor website - http://www.national.com/ -Authors: Frodo Looijaard - Jean Delvare + http://www.national.com/ + + +Authors: + - Frodo Looijaard + - Jean Delvare Description ----------- diff --git a/Documentation/hwmon/lm80 b/Documentation/hwmon/lm80 index a60b43efc32b..c53186abd82e 100644 --- a/Documentation/hwmon/lm80 +++ b/Documentation/hwmon/lm80 @@ -2,20 +2,31 @@ Kernel driver lm80 ================== Supported chips: + * National Semiconductor LM80 + Prefix: 'lm80' + Addresses scanned: I2C 0x28 - 0x2f + Datasheet: Publicly available at the National Semiconductor website - http://www.national.com/ + + http://www.national.com/ + * National Semiconductor LM96080 + Prefix: 'lm96080' + Addresses scanned: I2C 0x28 - 0x2f + Datasheet: Publicly available at the National Semiconductor website - http://www.national.com/ + + http://www.national.com/ + Authors: - Frodo Looijaard , - Philip Edelbrock + - Frodo Looijaard , + - Philip Edelbrock Description ----------- diff --git a/Documentation/hwmon/lm83 b/Documentation/hwmon/lm83 index 50be5cb26de9..ecf83819960e 100644 --- a/Documentation/hwmon/lm83 +++ b/Documentation/hwmon/lm83 @@ -2,16 +2,24 @@ Kernel driver lm83 ================== Supported chips: + * National Semiconductor LM83 + Prefix: 'lm83' + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + Datasheet: Publicly available at the National Semiconductor website - http://www.national.com/pf/LM/LM83.html + + http://www.national.com/pf/LM/LM83.html + * National Semiconductor LM82 + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + Datasheet: Publicly available at the National Semiconductor website - http://www.national.com/pf/LM/LM82.html + http://www.national.com/pf/LM/LM82.html Author: Jean Delvare @@ -34,13 +42,17 @@ fact that any of these motherboards do actually have an LM83, please contact us. Note that the LM90 can easily be misdetected as a LM83. Confirmed motherboards: + === ===== SBS P014 SBS PSL09 + === ===== Unconfirmed motherboards: + =========== ========== Gigabyte GA-8IK1100 Iwill MPX2 Soltek SL-75DRV5 + =========== ========== The LM82 is confirmed to have been found on most AMD Geode reference designs and test platforms. diff --git a/Documentation/hwmon/lm85 b/Documentation/hwmon/lm85 index 2329c383efe4..faa92f54431c 100644 --- a/Documentation/hwmon/lm85 +++ b/Documentation/hwmon/lm85 @@ -2,49 +2,85 @@ Kernel driver lm85 ================== Supported chips: + * National Semiconductor LM85 (B and C versions) + Prefix: 'lm85b' or 'lm85c' + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + Datasheet: http://www.national.com/pf/LM/LM85.html + * Texas Instruments LM96000 + Prefix: 'lm9600' + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + Datasheet: http://www.ti.com/lit/ds/symlink/lm96000.pdf + * Analog Devices ADM1027 + Prefix: 'adm1027' + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + Datasheet: http://www.onsemi.com/PowerSolutions/product.do?id=ADM1027 + * Analog Devices ADT7463 + Prefix: 'adt7463' + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + Datasheet: http://www.onsemi.com/PowerSolutions/product.do?id=ADT7463 + * Analog Devices ADT7468 + Prefix: 'adt7468' + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + Datasheet: http://www.onsemi.com/PowerSolutions/product.do?id=ADT7468 + * SMSC EMC6D100, SMSC EMC6D101 + Prefix: 'emc6d100' + Addresses scanned: I2C 0x2c, 0x2d, 0x2e - Datasheet: http://www.smsc.com/media/Downloads_Public/discontinued/6d100.pdf + + Datasheet: http://www.smsc.com/media/Downloads_Public/discontinued/6d100.pdf + * SMSC EMC6D102 + Prefix: 'emc6d102' + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + Datasheet: http://www.smsc.com/main/catalog/emc6d102.html + * SMSC EMC6D103 + Prefix: 'emc6d103' + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + Datasheet: http://www.smsc.com/main/catalog/emc6d103.html + * SMSC EMC6D103S + Prefix: 'emc6d103s' + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + Datasheet: http://www.smsc.com/main/catalog/emc6d103s.html Authors: - Philip Pokorny , - Frodo Looijaard , - Richard Barrington , - Margit Schubert-While , - Justin Thiessen + - Philip Pokorny , + - Frodo Looijaard , + - Richard Barrington , + - Margit Schubert-While , + - Justin Thiessen Description ----------- @@ -177,38 +213,50 @@ Each temperature sensor is associated with a Zone. There are three sensors and therefore three zones (# 1, 2 and 3). Each zone has the following temperature configuration points: -* temp#_auto_temp_off - temperature below which fans should be off or spinning very low. -* temp#_auto_temp_min - temperature over which fans start to spin. -* temp#_auto_temp_max - temperature when fans spin at full speed. -* temp#_auto_temp_crit - temperature when all fans will run full speed. +* temp#_auto_temp_off + - temperature below which fans should be off or spinning very low. +* temp#_auto_temp_min + - temperature over which fans start to spin. +* temp#_auto_temp_max + - temperature when fans spin at full speed. +* temp#_auto_temp_crit + - temperature when all fans will run full speed. -* PWM Control +PWM Control +^^^^^^^^^^^ There are three PWM outputs. The LM85 datasheet suggests that the pwm3 output control both fan3 and fan4. Each PWM can be individually configured and assigned to a zone for its control value. Each PWM can be configured individually according to the following options. -* pwm#_auto_pwm_min - this specifies the PWM value for temp#_auto_temp_off - temperature. (PWM value from 0 to 255) +* pwm#_auto_pwm_min + - this specifies the PWM value for temp#_auto_temp_off + temperature. (PWM value from 0 to 255) + +* pwm#_auto_pwm_minctl + - this flags selects for temp#_auto_temp_off temperature + the behaviour of fans. Write 1 to let fans spinning at + pwm#_auto_pwm_min or write 0 to let them off. -* pwm#_auto_pwm_minctl - this flags selects for temp#_auto_temp_off temperature - the behaviour of fans. Write 1 to let fans spinning at - pwm#_auto_pwm_min or write 0 to let them off. +.. note:: -NOTE: It has been reported that there is a bug in the LM85 that causes the flag -to be associated with the zones not the PWMs. This contradicts all the -published documentation. Setting pwm#_min_ctl in this case actually affects all -PWMs controlled by zone '#'. + It has been reported that there is a bug in the LM85 that causes + the flag to be associated with the zones not the PWMs. This + contradicts all the published documentation. Setting pwm#_min_ctl + in this case actually affects all PWMs controlled by zone '#'. -* PWM Controlling Zone selection +PWM Controlling Zone selection +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -* pwm#_auto_channels - controls zone that is associated with PWM +* pwm#_auto_channels + - controls zone that is associated with PWM Configuration choices: - Value Meaning - ------ ------------------------------------------------ +========== ============================================= +Value Meaning +========== ============================================= 1 Controlled by Zone 1 2 Controlled by Zone 2 3 Controlled by Zone 3 @@ -217,6 +265,7 @@ Configuration choices: 0 PWM always 0% (off) -1 PWM always 100% (full on) -2 Manual control (write to 'pwm#' to set) +========== ============================================= The National LM85's have two vendor specific configuration features. Tach. mode and Spinup Control. For more details on these, diff --git a/Documentation/hwmon/lm87 b/Documentation/hwmon/lm87 index a2339fd9acb9..72fcb577ef2a 100644 --- a/Documentation/hwmon/lm87 +++ b/Documentation/hwmon/lm87 @@ -2,23 +2,32 @@ Kernel driver lm87 ================== Supported chips: + * National Semiconductor LM87 + Prefix: 'lm87' + Addresses scanned: I2C 0x2c - 0x2e + Datasheet: http://www.national.com/pf/LM/LM87.html + * Analog Devices ADM1024 + Prefix: 'adm1024' + Addresses scanned: I2C 0x2c - 0x2e + Datasheet: http://www.analog.com/en/prod/0,2877,ADM1024,00.html + Authors: - Frodo Looijaard , - Philip Edelbrock , - Mark Studebaker , - Stephen Rousset , - Dan Eaton , - Jean Delvare , - Original 2.6 port Jeff Oliver + - Frodo Looijaard , + - Philip Edelbrock , + - Mark Studebaker , + - Stephen Rousset , + - Dan Eaton , + - Jean Delvare , + - Original 2.6 port Jeff Oliver Description ----------- diff --git a/Documentation/hwmon/lm90 b/Documentation/hwmon/lm90 index 8122675d30f6..953315987c06 100644 --- a/Documentation/hwmon/lm90 +++ b/Documentation/hwmon/lm90 @@ -2,132 +2,256 @@ Kernel driver lm90 ================== Supported chips: + * National Semiconductor LM90 + Prefix: 'lm90' + Addresses scanned: I2C 0x4c + Datasheet: Publicly available at the National Semiconductor website - http://www.national.com/pf/LM/LM90.html + + http://www.national.com/pf/LM/LM90.html + * National Semiconductor LM89 + Prefix: 'lm89' (no auto-detection) + Addresses scanned: I2C 0x4c and 0x4d + Datasheet: Publicly available at the National Semiconductor website - http://www.national.com/mpf/LM/LM89.html + + http://www.national.com/mpf/LM/LM89.html + * National Semiconductor LM99 + Prefix: 'lm99' + Addresses scanned: I2C 0x4c and 0x4d + Datasheet: Publicly available at the National Semiconductor website - http://www.national.com/pf/LM/LM99.html + + http://www.national.com/pf/LM/LM99.html + * National Semiconductor LM86 + Prefix: 'lm86' + Addresses scanned: I2C 0x4c + Datasheet: Publicly available at the National Semiconductor website - http://www.national.com/mpf/LM/LM86.html + + http://www.national.com/mpf/LM/LM86.html + * Analog Devices ADM1032 + Prefix: 'adm1032' + Addresses scanned: I2C 0x4c and 0x4d + Datasheet: Publicly available at the ON Semiconductor website - http://www.onsemi.com/PowerSolutions/product.do?id=ADM1032 + + http://www.onsemi.com/PowerSolutions/product.do?id=ADM1032 + * Analog Devices ADT7461 + Prefix: 'adt7461' + Addresses scanned: I2C 0x4c and 0x4d + Datasheet: Publicly available at the ON Semiconductor website - http://www.onsemi.com/PowerSolutions/product.do?id=ADT7461 + + http://www.onsemi.com/PowerSolutions/product.do?id=ADT7461 + * Analog Devices ADT7461A + Prefix: 'adt7461a' + Addresses scanned: I2C 0x4c and 0x4d + Datasheet: Publicly available at the ON Semiconductor website - http://www.onsemi.com/PowerSolutions/product.do?id=ADT7461A + + http://www.onsemi.com/PowerSolutions/product.do?id=ADT7461A + * ON Semiconductor NCT1008 + Prefix: 'nct1008' + Addresses scanned: I2C 0x4c and 0x4d + Datasheet: Publicly available at the ON Semiconductor website - http://www.onsemi.com/PowerSolutions/product.do?id=NCT1008 + + http://www.onsemi.com/PowerSolutions/product.do?id=NCT1008 + * Maxim MAX6646 + Prefix: 'max6646' + Addresses scanned: I2C 0x4d + Datasheet: Publicly available at the Maxim website - http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3497 + + http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3497 + * Maxim MAX6647 + Prefix: 'max6646' + Addresses scanned: I2C 0x4e + Datasheet: Publicly available at the Maxim website - http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3497 + + http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3497 + * Maxim MAX6648 + Prefix: 'max6646' + Addresses scanned: I2C 0x4c + Datasheet: Publicly available at the Maxim website - http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3500 + + http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3500 + * Maxim MAX6649 + Prefix: 'max6646' + Addresses scanned: I2C 0x4c + Datasheet: Publicly available at the Maxim website - http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3497 + + http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3497 + * Maxim MAX6657 + Prefix: 'max6657' + Addresses scanned: I2C 0x4c + Datasheet: Publicly available at the Maxim website - http://www.maxim-ic.com/quick_view2.cfm/qv_pk/2578 + + http://www.maxim-ic.com/quick_view2.cfm/qv_pk/2578 + * Maxim MAX6658 + Prefix: 'max6657' + Addresses scanned: I2C 0x4c + Datasheet: Publicly available at the Maxim website - http://www.maxim-ic.com/quick_view2.cfm/qv_pk/2578 + + http://www.maxim-ic.com/quick_view2.cfm/qv_pk/2578 + * Maxim MAX6659 + Prefix: 'max6659' + Addresses scanned: I2C 0x4c, 0x4d, 0x4e + Datasheet: Publicly available at the Maxim website - http://www.maxim-ic.com/quick_view2.cfm/qv_pk/2578 + + http://www.maxim-ic.com/quick_view2.cfm/qv_pk/2578 + * Maxim MAX6680 + Prefix: 'max6680' + Addresses scanned: I2C 0x18, 0x19, 0x1a, 0x29, 0x2a, 0x2b, - 0x4c, 0x4d and 0x4e + + 0x4c, 0x4d and 0x4e + Datasheet: Publicly available at the Maxim website - http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3370 + + http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3370 + * Maxim MAX6681 + Prefix: 'max6680' + Addresses scanned: I2C 0x18, 0x19, 0x1a, 0x29, 0x2a, 0x2b, - 0x4c, 0x4d and 0x4e + + 0x4c, 0x4d and 0x4e + Datasheet: Publicly available at the Maxim website - http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3370 + + http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3370 + * Maxim MAX6692 + Prefix: 'max6646' + Addresses scanned: I2C 0x4c + Datasheet: Publicly available at the Maxim website - http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3500 + + http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3500 + * Maxim MAX6695 + Prefix: 'max6695' + Addresses scanned: I2C 0x18 + Datasheet: Publicly available at the Maxim website - http://www.maxim-ic.com/datasheet/index.mvp/id/4199 + + http://www.maxim-ic.com/datasheet/index.mvp/id/4199 + * Maxim MAX6696 + Prefix: 'max6695' + Addresses scanned: I2C 0x18, 0x19, 0x1a, 0x29, 0x2a, 0x2b, - 0x4c, 0x4d and 0x4e + + 0x4c, 0x4d and 0x4e + Datasheet: Publicly available at the Maxim website - http://www.maxim-ic.com/datasheet/index.mvp/id/4199 + + http://www.maxim-ic.com/datasheet/index.mvp/id/4199 + * Winbond/Nuvoton W83L771W/G + Prefix: 'w83l771' + Addresses scanned: I2C 0x4c + Datasheet: No longer available + * Winbond/Nuvoton W83L771AWG/ASG + Prefix: 'w83l771' + Addresses scanned: I2C 0x4c + Datasheet: Not publicly available, can be requested from Nuvoton + * Philips/NXP SA56004X + Prefix: 'sa56004' + Addresses scanned: I2C 0x48 through 0x4F + Datasheet: Publicly available at NXP website - http://ics.nxp.com/products/interface/datasheet/sa56004x.pdf + + http://ics.nxp.com/products/interface/datasheet/sa56004x.pdf + * GMT G781 + Prefix: 'g781' + Addresses scanned: I2C 0x4c, 0x4d + Datasheet: Not publicly available from GMT + * Texas Instruments TMP451 + Prefix: 'tmp451' + Addresses scanned: I2C 0x4c + Datasheet: Publicly available at TI website - http://www.ti.com/litv/pdf/sbos686 + http://www.ti.com/litv/pdf/sbos686 Author: Jean Delvare diff --git a/Documentation/hwmon/lm92 b/Documentation/hwmon/lm92 index cfa99a353b8c..c131b923ed36 100644 --- a/Documentation/hwmon/lm92 +++ b/Documentation/hwmon/lm92 @@ -2,22 +2,35 @@ Kernel driver lm92 ================== Supported chips: + * National Semiconductor LM92 + Prefix: 'lm92' + Addresses scanned: I2C 0x48 - 0x4b + Datasheet: http://www.national.com/pf/LM/LM92.html + * National Semiconductor LM76 + Prefix: 'lm92' + Addresses scanned: none, force parameter needed + Datasheet: http://www.national.com/pf/LM/LM76.html + * Maxim MAX6633/MAX6634/MAX6635 + Prefix: 'max6635' + Addresses scanned: none, force parameter needed + Datasheet: http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3074 + Authors: - Abraham van der Merwe - Jean Delvare + - Abraham van der Merwe + - Jean Delvare Description diff --git a/Documentation/hwmon/lm93 b/Documentation/hwmon/lm93 index f3b2ad2ceb01..49d199b45b67 100644 --- a/Documentation/hwmon/lm93 +++ b/Documentation/hwmon/lm93 @@ -2,20 +2,29 @@ Kernel driver lm93 ================== Supported chips: + * National Semiconductor LM93 + Prefix 'lm93' + Addresses scanned: I2C 0x2c-0x2e + Datasheet: http://www.national.com/ds.cgi/LM/LM93.pdf + * National Semiconductor LM94 + Prefix 'lm94' + Addresses scanned: I2C 0x2c-0x2e + Datasheet: http://www.national.com/ds.cgi/LM/LM94.pdf + Authors: - Mark M. Hoffman - Ported to 2.6 by Eric J. Bowersox - Adapted to 2.6.20 by Carsten Emde - Modified for mainline integration by Hans J. Koch + - Mark M. Hoffman + - Ported to 2.6 by Eric J. Bowersox + - Adapted to 2.6.20 by Carsten Emde + - Modified for mainline integration by Hans J. Koch Module Parameters ----------------- @@ -67,7 +76,8 @@ LM94 are not supported. User Interface -------------- -#PROCHOT: +#PROCHOT +^^^^^^^^ The LM93 can monitor two #PROCHOT signals. The results are found in the sysfs files prochot1, prochot2, prochot1_avg, prochot2_avg, prochot1_max, @@ -86,7 +96,8 @@ prochot2_interval. The values in these files specify the intervals for list will cause the driver to use the next largest interval. The available intervals are (in seconds): -#PROCHOT intervals: 0.73, 1.46, 2.9, 5.8, 11.7, 23.3, 46.6, 93.2, 186, 372 +#PROCHOT intervals: + 0.73, 1.46, 2.9, 5.8, 11.7, 23.3, 46.6, 93.2, 186, 372 It is possible to configure the LM93 to logically short the two #PROCHOT signals. I.e. when #P1_PROCHOT is asserted, the LM93 will automatically @@ -105,16 +116,15 @@ contains a value controlling the duty cycle for the PWM signal used when the override function is enabled. This value ranges from 0 to 15, with 0 indicating minimum duty cycle and 15 indicating maximum. -#VRD_HOT: +#VRD_HOT +^^^^^^^^ The LM93 can monitor two #VRD_HOT signals. The results are found in the sysfs files vrdhot1 and vrdhot2. There is one value per file: a boolean for which 1 indicates #VRD_HOT is asserted and 0 indicates it is negated. These files are read-only. -Smart Tach Mode: - -(from the datasheet) +Smart Tach Mode (from the datasheet):: If a fan is driven using a low-side drive PWM, the tachometer output of the fan is corrupted. The LM93 includes smart tachometer @@ -127,7 +137,8 @@ the fan tachometer with a pwm) to the sysfs file fan_smart_tach. A zero will disable the function for that fan. Note that Smart tach mode cannot be enabled if the PWM output frequency is 22500 Hz (see below). -Manual PWM: +Manual PWM +^^^^^^^^^^ The LM93 has a fixed or override mode for the two PWM outputs (although, there are still some conditions that will override even this mode - see section @@ -141,7 +152,8 @@ will cause the driver to use the next largest value. Also note: when manual PWM mode is disabled, the value of pwm1 and pwm2 indicates the current duty cycle chosen by the h/w. -PWM Output Frequency: +PWM Output Frequency +^^^^^^^^^^^^^^^^^^^^ The LM93 supports several different frequencies for the PWM output channels. The sysfs files pwm1_freq and pwm2_freq are used to select the frequency. The @@ -149,9 +161,11 @@ frequency values are constrained by the hardware. Selecting a value which is not available will cause the driver to use the next largest value. Also note that this parameter has implications for the Smart Tach Mode (see above). -PWM Output Frequencies (in Hz): 12, 36, 48, 60, 72, 84, 96, 22500 (default) +PWM Output Frequencies (in Hz): + 12, 36, 48, 60, 72, 84, 96, 22500 (default) -Automatic PWM: +Automatic PWM +^^^^^^^^^^^^^ The LM93 is capable of complex automatic fan control, with many different points of configuration. To start, each PWM output can be bound to any @@ -163,14 +177,16 @@ The eight control sources are: temp1-temp4 (aka "zones" in the datasheet), in the sysfs files pwm_auto_channels, where a "1" enables the binding, and a "0" disables it. The h/w default is 0x0f (all temperatures bound). - 0x01 - Temp 1 - 0x02 - Temp 2 - 0x04 - Temp 3 - 0x08 - Temp 4 - 0x10 - #PROCHOT 1 - 0x20 - #PROCHOT 2 - 0x40 - #VRDHOT 1 - 0x80 - #VRDHOT 2 + ====== =========== + 0x01 Temp 1 + 0x02 Temp 2 + 0x04 Temp 3 + 0x08 Temp 4 + 0x10 #PROCHOT 1 + 0x20 #PROCHOT 2 + 0x40 #VRDHOT 1 + 0x80 #VRDHOT 2 + ====== =========== The function y = f(x) takes a source temperature x to a PWM output y. This function of the LM93 is derived from a base temperature and a table of 12 @@ -180,7 +196,9 @@ degrees C, with the value of offset for temperature value being contained in the file temp_auto_offset. E.g. if the base temperature is 40C: + ========== ======================= =============== ======= offset # temp_auto_offset range pwm + ========== ======================= =============== ======= 1 0 - 25.00% 2 0 - 28.57% 3 1 40C - 41C 32.14% @@ -193,7 +211,8 @@ is 40C: 10 2 54C - 56C 57.14% 11 2 56C - 58C 71.43% 12 2 58C - 60C 85.71% - > 60C 100.00% + - - > 60C 100.00% + ========== ======================= =============== ======= Valid offsets are in the range 0C <= x <= 7.5C in 0.5C increments. @@ -213,7 +232,8 @@ temp_auto_pwm_min. Note, there are only two minimums: one each for temp[12] and temp[34]. Therefore, any change to e.g. temp1_auto_pwm_min will also affect temp2_auto_pwm_min. -PWM Spin-Up Cycle: +PWM Spin-Up Cycle +^^^^^^^^^^^^^^^^^ A spin-up cycle occurs when a PWM output is commanded from 0% duty cycle to some value > 0%. The LM93 supports a minimum duty cycle during spin-up. These @@ -225,10 +245,11 @@ the spin-up time in seconds. The available spin-up times are constrained by the hardware. Selecting a value which is not available will cause the driver to use the next largest value. -Spin-up Durations: 0 (disabled, h/w default), 0.1, 0.25, 0.4, 0.7, 1.0, - 2.0, 4.0 +Spin-up Durations: + 0 (disabled, h/w default), 0.1, 0.25, 0.4, 0.7, 1.0, 2.0, 4.0 -#PROCHOT and #VRDHOT PWM Ramping: +#PROCHOT and #VRDHOT PWM Ramping +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ If the #PROCHOT or #VRDHOT signals are asserted while bound to a PWM output channel, the LM93 will ramp the PWM output up to 100% duty cycle in discrete @@ -237,9 +258,11 @@ one value each in seconds: pwm_auto_prochot_ramp and pwm_auto_vrdhot_ramp. The available ramp times are constrained by the hardware. Selecting a value which is not available will cause the driver to use the next largest value. -Ramp Times: 0 (disabled, h/w default) to 0.75 in 0.05 second intervals +Ramp Times: + 0 (disabled, h/w default) to 0.75 in 0.05 second intervals -Fan Boost: +Fan Boost +^^^^^^^^^ For each temperature channel, there is a boost temperature: if the channel exceeds this limit, the LM93 will immediately drive both PWM outputs to 100%. @@ -249,7 +272,8 @@ limit is reached, the temperature channel must drop below this value before the boost function is disabled. This temperature is also expressed in degrees C in the sysfs files temp_auto_boost_hyst. -GPIO Pins: +GPIO Pins +^^^^^^^^^ The LM93 can monitor the logic level of four dedicated GPIO pins as well as the four tach input pins. GPIO0-GPIO3 correspond to (fan) tach 1-4, respectively. @@ -260,50 +284,29 @@ LSB is GPIO0, and the MSB is GPIO7. LM93 Unique sysfs Files ----------------------- - file description - ------------------------------------------------------------- - - prochot current #PROCHOT % - - prochot_avg moving average #PROCHOT % - - prochot_max limit #PROCHOT % - - prochot_short enable or disable logical #PROCHOT pin short - - prochot_override force #PROCHOT assertion as PWM - - prochot_override_duty_cycle - duty cycle for the PWM signal used when - #PROCHOT is overridden - - prochot_interval #PROCHOT PWM sampling interval - - vrdhot 0 means negated, 1 means asserted - - fan_smart_tach enable or disable smart tach mode - - pwm_auto_channels select control sources for PWM outputs - - pwm_auto_spinup_min minimum duty cycle during spin-up - - pwm_auto_spinup_time duration of spin-up - - pwm_auto_prochot_ramp ramp time per step when #PROCHOT asserted - - pwm_auto_vrdhot_ramp ramp time per step when #VRDHOT asserted - - temp_auto_base temperature channel base - - temp_auto_offset[1-12] - temperature channel offsets - - temp_auto_offset_hyst - temperature channel offset hysteresis - - temp_auto_boost temperature channel boost (PWMs to 100%) limit - - temp_auto_boost_hyst temperature channel boost hysteresis - - gpio input state of 8 GPIO pins; read-only - +=========================== =============================================== +file description +=========================== =============================================== +prochot current #PROCHOT % +prochot_avg moving average #PROCHOT % +prochot_max limit #PROCHOT % +prochot_short enable or disable logical #PROCHOT pin short +prochot_override force #PROCHOT assertion as PWM +prochot_override_duty_cycle duty cycle for the PWM signal used when + #PROCHOT is overridden +prochot_interval #PROCHOT PWM sampling interval +vrdhot 0 means negated, 1 means asserted +fan_smart_tach enable or disable smart tach mode +pwm_auto_channels select control sources for PWM outputs +pwm_auto_spinup_min minimum duty cycle during spin-up +pwm_auto_spinup_time duration of spin-up +pwm_auto_prochot_ramp ramp time per step when #PROCHOT asserted +pwm_auto_vrdhot_ramp ramp time per step when #VRDHOT asserted +temp_auto_base temperature channel base +temp_auto_offset[1-12] temperature channel offsets +temp_auto_offset_hyst temperature channel offset hysteresis +temp_auto_boost temperature channel boost (PWMs to 100%) + limit +temp_auto_boost_hyst temperature channel boost hysteresis +gpio input state of 8 GPIO pins; read-only +=========================== =============================================== diff --git a/Documentation/hwmon/lm95245 b/Documentation/hwmon/lm95245 index d755901f58c4..566d1dc8c5a6 100644 --- a/Documentation/hwmon/lm95245 +++ b/Documentation/hwmon/lm95245 @@ -1,16 +1,23 @@ Kernel driver lm95245 -================== +===================== Supported chips: + * TI LM95235 + Addresses scanned: I2C 0x18, 0x29, 0x4c + Datasheet: Publicly available at the TI website - http://www.ti.com/lit/ds/symlink/lm95235.pdf + + http://www.ti.com/lit/ds/symlink/lm95235.pdf + * TI / National Semiconductor LM95245 + Addresses scanned: I2C 0x18, 0x19, 0x29, 0x4c, 0x4d + Datasheet: Publicly available at the TI website - http://www.ti.com/lit/ds/symlink/lm95245.pdf + http://www.ti.com/lit/ds/symlink/lm95245.pdf Author: Alexander Stein diff --git a/Documentation/hwmon/ltc2945 b/Documentation/hwmon/ltc2945 index f8d0f7f19adb..20c884985367 100644 --- a/Documentation/hwmon/ltc2945 +++ b/Documentation/hwmon/ltc2945 @@ -2,11 +2,16 @@ Kernel driver ltc2945 ===================== Supported chips: + * Linear Technology LTC2945 + Prefix: 'ltc2945' + Addresses scanned: - + Datasheet: - http://cds.linear.com/docs/en/datasheet/2945fa.pdf + + http://cds.linear.com/docs/en/datasheet/2945fa.pdf Author: Guenter Roeck @@ -26,9 +31,10 @@ which can be safely used to identify the chip. You will have to instantiate the devices explicitly. Example: the following will load the driver for an LTC2945 at address 0x10 -on I2C bus #1: -$ modprobe ltc2945 -$ echo ltc2945 0x10 > /sys/bus/i2c/devices/i2c-1/new_device +on I2C bus #1:: + + $ modprobe ltc2945 + $ echo ltc2945 0x10 > /sys/bus/i2c/devices/i2c-1/new_device Sysfs entries @@ -45,6 +51,7 @@ Current Sense register. The reported value assumes that a 1 mOhm sense resistor is installed. If a different sense resistor is installed, calculate the real current by dividing the reported value by the sense resistor value in mOhm. +======================= ======================================================== in1_input VIN voltage (mV). Voltage is measured either at SENSE+ or VDD pin depending on chip configuration. in1_min Undervoltage threshold @@ -82,3 +89,4 @@ power1_input_highest Historical maximum power use power1_reset_history Write 1 to reset power1 history power1_min_alarm Low power alarm power1_max_alarm High power alarm +======================= ======================================================== diff --git a/Documentation/hwmon/ltc2990 b/Documentation/hwmon/ltc2990 index 3ed68f676c0f..e0a369e679d3 100644 --- a/Documentation/hwmon/ltc2990 +++ b/Documentation/hwmon/ltc2990 @@ -1,14 +1,23 @@ Kernel driver ltc2990 ===================== + Supported chips: + * Linear Technology LTC2990 + Prefix: 'ltc2990' + Addresses scanned: - + Datasheet: http://www.linear.com/product/ltc2990 -Author: Mike Looijmans - Tom Levens + + +Author: + + - Mike Looijmans + - Tom Levens Description @@ -31,17 +40,21 @@ devices explicitly. Sysfs attributes ---------------- +============= ================================================== in0_input Voltage at Vcc pin in millivolt (range 2.5V to 5V) -temp1_input Internal chip temperature in millidegrees Celcius +temp1_input Internal chip temperature in millidegrees Celsius +============= ================================================== A subset of the following attributes are visible, depending on the measurement mode of the chip. +============= ========================================================== in[1-4]_input Voltage at V[1-4] pin in millivolt -temp2_input External temperature sensor TR1 in millidegrees Celcius -temp3_input External temperature sensor TR2 in millidegrees Celcius +temp2_input External temperature sensor TR1 in millidegrees Celsius +temp3_input External temperature sensor TR2 in millidegrees Celsius curr1_input Current in mA across V1-V2 assuming a 1mOhm sense resistor curr2_input Current in mA across V3-V4 assuming a 1mOhm sense resistor +============= ========================================================== The "curr*_input" measurements actually report the voltage drop across the input pins in microvolts. This is equivalent to the current through a 1mOhm diff --git a/Documentation/hwmon/ltc4151 b/Documentation/hwmon/ltc4151 index 43c667e6677a..c39229b19624 100644 --- a/Documentation/hwmon/ltc4151 +++ b/Documentation/hwmon/ltc4151 @@ -2,11 +2,16 @@ Kernel driver ltc4151 ===================== Supported chips: + * Linear Technology LTC4151 + Prefix: 'ltc4151' + Addresses scanned: - + Datasheet: - http://www.linear.com/docs/Datasheet/4151fc.pdf + + http://www.linear.com/docs/Datasheet/4151fc.pdf Author: Per Dalen @@ -25,9 +30,10 @@ which can be safely used to identify the chip. You will have to instantiate the devices explicitly. Example: the following will load the driver for an LTC4151 at address 0x6f -on I2C bus #0: -# modprobe ltc4151 -# echo ltc4151 0x6f > /sys/bus/i2c/devices/i2c-0/new_device +on I2C bus #0:: + + # modprobe ltc4151 + # echo ltc4151 0x6f > /sys/bus/i2c/devices/i2c-0/new_device Sysfs entries @@ -40,8 +46,10 @@ Current reading provided by this driver is reported as obtained from the Current Sense register. The reported value assumes that a 1 mOhm sense resistor is installed. +======================= ================== in1_input VDIN voltage (mV) in2_input ADIN voltage (mV) curr1_input SENSE current (mA) +======================= ================== diff --git a/Documentation/hwmon/ltc4215 b/Documentation/hwmon/ltc4215 index c196a1846259..8d5044d99bab 100644 --- a/Documentation/hwmon/ltc4215 +++ b/Documentation/hwmon/ltc4215 @@ -2,11 +2,16 @@ Kernel driver ltc4215 ===================== Supported chips: + * Linear Technology LTC4215 + Prefix: 'ltc4215' + Addresses scanned: 0x44 + Datasheet: - http://www.linear.com/pc/downloadDocument.do?navId=H0,C1,C1003,C1006,C1163,P17572,D12697 + + http://www.linear.com/pc/downloadDocument.do?navId=H0,C1,C1003,C1006,C1163,P17572,D12697 Author: Ira W. Snyder @@ -26,9 +31,10 @@ of the possible addresses are unfriendly to probing. You will have to instantiate the devices explicitly. Example: the following will load the driver for an LTC4215 at address 0x44 -on I2C bus #0: -$ modprobe ltc4215 -$ echo ltc4215 0x44 > /sys/bus/i2c/devices/i2c-0/new_device +on I2C bus #0:: + + $ modprobe ltc4215 + $ echo ltc4215 0x44 > /sys/bus/i2c/devices/i2c-0/new_device Sysfs entries @@ -38,6 +44,7 @@ The LTC4215 has built-in limits for overvoltage, undervoltage, and undercurrent warnings. This makes it very likely that the reference circuit will be used. +======================= ========================= in1_input input voltage in2_input output voltage @@ -49,3 +56,4 @@ curr1_max_alarm overcurrent alarm power1_input power usage power1_alarm power bad alarm +======================= ========================= diff --git a/Documentation/hwmon/ltc4245 b/Documentation/hwmon/ltc4245 index 4ca7a9da09f9..3dafd08a4e87 100644 --- a/Documentation/hwmon/ltc4245 +++ b/Documentation/hwmon/ltc4245 @@ -2,11 +2,16 @@ Kernel driver ltc4245 ===================== Supported chips: + * Linear Technology LTC4245 + Prefix: 'ltc4245' + Addresses scanned: 0x20-0x3f + Datasheet: - http://www.linear.com/pc/downloadDocument.do?navId=H0,C1,C1003,C1006,C1140,P19392,D13517 + + http://www.linear.com/pc/downloadDocument.do?navId=H0,C1,C1003,C1006,C1140,P19392,D13517 Author: Ira W. Snyder @@ -27,9 +32,10 @@ of the possible addresses are unfriendly to probing. You will have to instantiate the devices explicitly. Example: the following will load the driver for an LTC4245 at address 0x23 -on I2C bus #1: -$ modprobe ltc4245 -$ echo ltc4245 0x23 > /sys/bus/i2c/devices/i2c-1/new_device +on I2C bus #1:: + + $ modprobe ltc4245 + $ echo ltc4245 0x23 > /sys/bus/i2c/devices/i2c-1/new_device Sysfs entries @@ -42,6 +48,7 @@ This driver uses the values in the datasheet to change the register values into the values specified in the sysfs-interface document. The current readings rely on the sense resistors listed in Table 2: "Sense Resistor Values". +======================= ======================================================= in1_input 12v input voltage (mV) in2_input 5v input voltage (mV) in3_input 3v input voltage (mV) @@ -80,6 +87,7 @@ power1_input 12v power usage (mW) power2_input 5v power usage (mW) power3_input 3v power usage (mW) power4_input Vee (-12v) power usage (mW) +======================= ======================================================= Note 1 @@ -96,6 +104,7 @@ slowly, -EAGAIN will be returned when you read the sysfs attribute containing the sensor reading. The LTC4245 chip can be configured to sample all GPIO pins with two methods: + 1) platform data -- see include/linux/platform_data/ltc4245.h 2) OF device tree -- add the "ltc4245,use-extra-gpios" property to each chip diff --git a/Documentation/hwmon/ltc4260 b/Documentation/hwmon/ltc4260 index c4ff4ad998b2..4c335b6a51d1 100644 --- a/Documentation/hwmon/ltc4260 +++ b/Documentation/hwmon/ltc4260 @@ -2,11 +2,16 @@ Kernel driver ltc4260 ===================== Supported chips: + * Linear Technology LTC4260 + Prefix: 'ltc4260' + Addresses scanned: - + Datasheet: - http://cds.linear.com/docs/en/datasheet/4260fc.pdf + + http://cds.linear.com/docs/en/datasheet/4260fc.pdf Author: Guenter Roeck @@ -26,9 +31,10 @@ which can be safely used to identify the chip. You will have to instantiate the devices explicitly. Example: the following will load the driver for an LTC4260 at address 0x10 -on I2C bus #1: -$ modprobe ltc4260 -$ echo ltc4260 0x10 > /sys/bus/i2c/devices/i2c-1/new_device +on I2C bus #1:: + + $ modprobe ltc4260 + $ echo ltc4260 0x10 > /sys/bus/i2c/devices/i2c-1/new_device Sysfs entries @@ -45,6 +51,7 @@ Current Sense register. The reported value assumes that a 1 mOhm sense resistor is installed. If a different sense resistor is installed, calculate the real current by dividing the reported value by the sense resistor value in mOhm. +======================= ======================= in1_input SOURCE voltage (mV) in1_min_alarm Undervoltage alarm in1_max_alarm Overvoltage alarm @@ -54,3 +61,4 @@ in2_alarm Power bad alarm curr1_input SENSE current (mA) curr1_alarm SENSE overcurrent alarm +======================= ======================= diff --git a/Documentation/hwmon/max1619 b/Documentation/hwmon/max1619 index 518bae3a80c4..4b3762c4eceb 100644 --- a/Documentation/hwmon/max1619 +++ b/Documentation/hwmon/max1619 @@ -2,15 +2,20 @@ Kernel driver max1619 ===================== Supported chips: + * Maxim MAX1619 + Prefix: 'max1619' + Addresses scanned: I2C 0x18-0x1a, 0x29-0x2b, 0x4c-0x4e + Datasheet: Publicly available at the Maxim website - http://pdfserv.maxim-ic.com/en/ds/MAX1619.pdf + + http://pdfserv.maxim-ic.com/en/ds/MAX1619.pdf Authors: - Oleksij Rempel , - Jean Delvare + - Oleksij Rempel , + - Jean Delvare Description ----------- diff --git a/Documentation/hwmon/max1668 b/Documentation/hwmon/max1668 index 8f9d570dbfec..417f17d750e6 100644 --- a/Documentation/hwmon/max1668 +++ b/Documentation/hwmon/max1668 @@ -2,12 +2,17 @@ Kernel driver max1668 ===================== Supported chips: + * Maxim MAX1668, MAX1805 and MAX1989 + Prefix: 'max1668' + Addresses scanned: I2C 0x18, 0x19, 0x1a, 0x29, 0x2a, 0x2b, 0x4c, 0x4d, 0x4e + Datasheet: http://datasheets.maxim-ic.com/en/ds/MAX1668-MAX1989.pdf Author: + David George Description @@ -23,8 +28,9 @@ two ICs. The driver is able to distinguish between the devices and creates sysfs entries as follows: -MAX1805, MAX1668 and MAX1989: +- MAX1805, MAX1668 and MAX1989: +=============== == ============================================================ temp1_input ro local (ambient) temperature temp1_max rw local temperature maximum threshold for alarm temp1_max_alarm ro local temperature maximum threshold alarm @@ -40,8 +46,11 @@ temp3_max rw remote temperature 2 maximum threshold for alarm temp3_max_alarm ro remote temperature 2 maximum threshold alarm temp3_min rw remote temperature 2 minimum threshold for alarm temp3_min_alarm ro remote temperature 2 minimum threshold alarm +=============== == ============================================================ + +- MAX1668 and MAX1989 only: -MAX1668 and MAX1989 only: +=============== == ============================================================ temp4_input ro remote temperature 3 temp4_max rw remote temperature 3 maximum threshold for alarm temp4_max_alarm ro remote temperature 3 maximum threshold alarm @@ -52,6 +61,7 @@ temp5_max rw remote temperature 4 maximum threshold for alarm temp5_max_alarm ro remote temperature 4 maximum threshold alarm temp5_min rw remote temperature 4 minimum threshold for alarm temp5_min_alarm ro remote temperature 4 minimum threshold alarm +=============== == ============================================================ Module Parameters ----------------- diff --git a/Documentation/hwmon/max197 b/Documentation/hwmon/max197 index 8d89b9009df8..02fe19bc3428 100644 --- a/Documentation/hwmon/max197 +++ b/Documentation/hwmon/max197 @@ -1,16 +1,22 @@ -Maxim MAX197 driver -=================== +Kernel driver max197 +==================== Author: + * Vivien Didelot Supported chips: + * Maxim MAX197 + Prefix: 'max197' + Datasheet: http://datasheets.maxim-ic.com/en/ds/MAX197.pdf * Maxim MAX199 + Prefix: 'max199' + Datasheet: http://datasheets.maxim-ic.com/en/ds/MAX199.pdf Description @@ -26,7 +32,7 @@ Platform data ------------- The MAX197 platform data (defined in linux/platform_data/max197.h) should be -filled with a pointer to a conversion function, defined like: +filled with a pointer to a conversion function, defined like:: int convert(u8 ctrl); @@ -36,25 +42,29 @@ or a negative error code otherwise. Control byte format: +======= ========== ============================================ Bit Name Description 7,6 PD1,PD0 Clock and Power-Down modes 5 ACQMOD Internal or External Controlled Acquisition 4 RNG Full-scale voltage magnitude at the input 3 BIP Unipolar or Bipolar conversion mode 2,1,0 A2,A1,A0 Channel +======= ========== ============================================ Sysfs interface --------------- -* in[0-7]_input: The conversion value for the corresponding channel. - RO + ============== ============================================================== + in[0-7]_input The conversion value for the corresponding channel. + RO -* in[0-7]_min: The lower limit (in mV) for the corresponding channel. - For the MAX197, it will be adjusted to -10000, -5000, or 0. - For the MAX199, it will be adjusted to -4000, -2000, or 0. - RW + in[0-7]_min The lower limit (in mV) for the corresponding channel. + For the MAX197, it will be adjusted to -10000, -5000, or 0. + For the MAX199, it will be adjusted to -4000, -2000, or 0. + RW -* in[0-7]_max: The higher limit (in mV) for the corresponding channel. - For the MAX197, it will be adjusted to 0, 5000, or 10000. - For the MAX199, it will be adjusted to 0, 2000, or 4000. - RW + in[0-7]_max The higher limit (in mV) for the corresponding channel. + For the MAX197, it will be adjusted to 0, 5000, or 10000. + For the MAX199, it will be adjusted to 0, 2000, or 4000. + RW + ============== ============================================================== diff --git a/Documentation/hwmon/max31722 b/Documentation/hwmon/max31722 index 090da84538c8..0ab15c00b226 100644 --- a/Documentation/hwmon/max31722 +++ b/Documentation/hwmon/max31722 @@ -2,15 +2,25 @@ Kernel driver max31722 ====================== Supported chips: + * Maxim Integrated MAX31722 + Prefix: 'max31722' + ACPI ID: MAX31722 + Addresses scanned: - + Datasheet: https://datasheets.maximintegrated.com/en/ds/MAX31722-MAX31723.pdf + * Maxim Integrated MAX31723 + Prefix: 'max31723' + ACPI ID: MAX31723 + Addresses scanned: - + Datasheet: https://datasheets.maximintegrated.com/en/ds/MAX31722-MAX31723.pdf Author: Tiberiu Breana @@ -31,4 +41,6 @@ Sysfs entries The following attribute is supported: +======================= ======================================================= temp1_input Measured temperature. Read-only. +======================= ======================================================= diff --git a/Documentation/hwmon/max31790 b/Documentation/hwmon/max31790 index 855e62430da9..84c62a12ef3a 100644 --- a/Documentation/hwmon/max31790 +++ b/Documentation/hwmon/max31790 @@ -2,9 +2,13 @@ Kernel driver max31790 ====================== Supported chips: + * Maxim MAX31790 + Prefix: 'max31790' + Addresses scanned: - + Datasheet: http://pdfserv.maximintegrated.com/en/ds/MAX31790.pdf Author: Il Han @@ -30,8 +34,10 @@ also be configured to serve as tachometer inputs. Sysfs entries ------------- +================== === ======================================================= fan[1-12]_input RO fan tachometer speed in RPM fan[1-12]_fault RO fan experienced fault fan[1-6]_target RW desired fan speed in RPM pwm[1-6]_enable RW regulator mode, 0=disabled, 1=manual mode, 2=rpm mode pwm[1-6] RW fan target duty cycle (0-255) +================== === ======================================================= diff --git a/Documentation/hwmon/max6639 b/Documentation/hwmon/max6639 index dc49f8be7167..3da54225f83c 100644 --- a/Documentation/hwmon/max6639 +++ b/Documentation/hwmon/max6639 @@ -2,14 +2,18 @@ Kernel driver max6639 ===================== Supported chips: + * Maxim MAX6639 + Prefix: 'max6639' + Addresses scanned: I2C 0x2c, 0x2e, 0x2f + Datasheet: http://pdfserv.maxim-ic.com/en/ds/MAX6639.pdf Authors: - He Changqing - Roland Stigge + - He Changqing + - Roland Stigge Description ----------- @@ -21,19 +25,20 @@ diode-connected transistors. The following device attributes are implemented via sysfs: +====================== ==== =================================================== Attribute R/W Contents ----------------------------------------------------------------------------- +====================== ==== =================================================== temp1_input R Temperature channel 1 input (0..150 C) temp2_input R Temperature channel 2 input (0..150 C) temp1_fault R Temperature channel 1 diode fault temp2_fault R Temperature channel 2 diode fault temp1_max RW Set THERM temperature for input 1 - (in C, see datasheet) + (in C, see datasheet) temp2_max RW Set THERM temperature for input 2 temp1_crit RW Set ALERT temperature for input 1 temp2_crit RW Set ALERT temperature for input 2 temp1_emergency RW Set OT temperature for input 1 - (in C, see datasheet) + (in C, see datasheet) temp2_emergency RW Set OT temperature for input 2 pwm1 RW Fan 1 target duty cycle (0..255) pwm2 RW Fan 2 target duty cycle (0..255) @@ -47,3 +52,4 @@ temp1_crit_alarm R Alarm on ALERT temperature on channel 1 temp2_crit_alarm R Alarm on ALERT temperature on channel 2 temp1_emergency_alarm R Alarm on OT temperature on channel 1 temp2_emergency_alarm R Alarm on OT temperature on channel 2 +====================== ==== =================================================== diff --git a/Documentation/hwmon/max6642 b/Documentation/hwmon/max6642 index afbd3e4942e2..7e5b7d4f9492 100644 --- a/Documentation/hwmon/max6642 +++ b/Documentation/hwmon/max6642 @@ -2,14 +2,20 @@ Kernel driver max6642 ===================== Supported chips: + * Maxim MAX6642 + Prefix: 'max6642' + Addresses scanned: I2C 0x48-0x4f + Datasheet: Publicly available at the Maxim website - http://datasheets.maxim-ic.com/en/ds/MAX6642.pdf + + http://datasheets.maxim-ic.com/en/ds/MAX6642.pdf Authors: - Per Dalen + + Per Dalen Description ----------- diff --git a/Documentation/hwmon/max6650 b/Documentation/hwmon/max6650 index dff1d296a48b..74dc3f0caaa2 100644 --- a/Documentation/hwmon/max6650 +++ b/Documentation/hwmon/max6650 @@ -2,19 +2,27 @@ Kernel driver max6650 ===================== Supported chips: + * Maxim MAX6650 + Prefix: 'max6650' + Addresses scanned: none + Datasheet: http://pdfserv.maxim-ic.com/en/ds/MAX6650-MAX6651.pdf + * Maxim MAX6651 + Prefix: 'max6651' + Addresses scanned: none + Datasheet: http://pdfserv.maxim-ic.com/en/ds/MAX6650-MAX6651.pdf Authors: - Hans J. Koch - John Morris - Claus Gindhart + - Hans J. Koch + - John Morris + - Claus Gindhart Description ----------- @@ -28,6 +36,7 @@ The driver is not able to distinguish between the 2 devices. The driver provides the following sensor accesses in sysfs: +=============== ======= ======================================================= fan1_input ro fan tachometer speed in RPM fan2_input ro " fan3_input ro " @@ -40,6 +49,7 @@ pwm1 rw relative speed (0-255), 255=max. speed. fan1_div rw sets the speed range the inputs can handle. Legal values are 1, 2, 4, and 8. Use lower values for faster fans. +=============== ======= ======================================================= Usage notes ----------- diff --git a/Documentation/hwmon/mc13783-adc b/Documentation/hwmon/mc13783-adc index 05ccc9f159f1..cae70350ba2f 100644 --- a/Documentation/hwmon/mc13783-adc +++ b/Documentation/hwmon/mc13783-adc @@ -2,16 +2,25 @@ Kernel driver mc13783-adc ========================= Supported chips: + * Freescale MC13783 + Prefix: 'mc13783' + Datasheet: https://www.nxp.com/docs/en/data-sheet/MC13783.pdf + * Freescale MC13892 + Prefix: 'mc13892' + Datasheet: https://www.nxp.com/docs/en/data-sheet/MC13892.pdf + + Authors: - Sascha Hauer - Luotao Fu + + - Sascha Hauer + - Luotao Fu Description ----------- @@ -30,9 +39,11 @@ the General Purpose inputs and touchscreen. See the following tables for the meaning of the different channels and their chip internal scaling: -MC13783: +- MC13783: + +======= =============================================== =============== ======= Channel Signal Input Range Scaling -------------------------------------------------------------------------------- +======= =============================================== =============== ======= 0 Battery Voltage (BATT) 2.50 - 4.65V -2.40V 1 Battery Current (BATT - BATTISNS) -50 - 50 mV x20 2 Application Supply (BP) 2.50 - 4.65V -2.40V @@ -52,10 +63,13 @@ Channel Signal Input Range Scaling 13 General Purpose TSX2 / Touchscreen X-plate 2 0 - 2.30V No 14 General Purpose TSY1 / Touchscreen Y-plate 1 0 - 2.30V No 15 General Purpose TSY2 / Touchscreen Y-plate 2 0 - 2.30V No +======= =============================================== =============== ======= + +- MC13892: -MC13892: +======= =============================================== =============== ======= Channel Signal Input Range Scaling -------------------------------------------------------------------------------- +======= =============================================== =============== ======= 0 Battery Voltage (BATT) 0 - 4.8V /2 1 Battery Current (BATT - BATTISNSCC) -60 - 60 mV x20 2 Application Supply (BPSNS) 0 - 4.8V /2 @@ -72,3 +86,4 @@ Channel Signal Input Range Scaling 13 General Purpose TSX2 / Touchscreen X-plate 2 0 - 2.4V No 14 General Purpose TSY1 / Touchscreen Y-plate 1 0 - 2.4V No 15 General Purpose TSY2 / Touchscreen Y-plate 2 0 - 2.4V No +======= =============================================== =============== ======= diff --git a/Documentation/hwmon/mcp3021 b/Documentation/hwmon/mcp3021 index 74a6b72adf5f..83f4bda2f269 100644 --- a/Documentation/hwmon/mcp3021 +++ b/Documentation/hwmon/mcp3021 @@ -1,17 +1,26 @@ Kernel driver MCP3021 -====================== +===================== Supported chips: + * Microchip Technology MCP3021 + Prefix: 'mcp3021' + Datasheet: http://ww1.microchip.com/downloads/en/DeviceDoc/21805a.pdf + * Microchip Technology MCP3221 + Prefix: 'mcp3221' + Datasheet: http://ww1.microchip.com/downloads/en/DeviceDoc/21732c.pdf + + Authors: - Mingkai Hu - Sven Schuchmann + + - Mingkai Hu + - Sven Schuchmann Description ----------- diff --git a/Documentation/hwmon/mlxreg-fan b/Documentation/hwmon/mlxreg-fan index fc531c6978d4..c92b8e885f7e 100644 --- a/Documentation/hwmon/mlxreg-fan +++ b/Documentation/hwmon/mlxreg-fan @@ -2,32 +2,38 @@ Kernel driver mlxreg-fan ======================== Provides FAN control for the next Mellanox systems: -QMB700, equipped with 40x200GbE InfiniBand ports; -MSN3700, equipped with 32x200GbE or 16x400GbE Ethernet ports; -MSN3410, equipped with 6x400GbE plus 48x50GbE Ethernet ports; -MSN3800, equipped with 64x1000GbE Ethernet ports; + +- QMB700, equipped with 40x200GbE InfiniBand ports; +- MSN3700, equipped with 32x200GbE or 16x400GbE Ethernet ports; +- MSN3410, equipped with 6x400GbE plus 48x50GbE Ethernet ports; +- MSN3800, equipped with 64x1000GbE Ethernet ports; + +Author: Vadim Pasternak + These are the Top of the Rack systems, equipped with Mellanox switch board with Mellanox Quantum or Spectrume-2 devices. FAN controller is implemented by the programmable device logic. The default registers offsets set within the programmable device is as following: -- pwm1 0xe3 -- fan1 (tacho1) 0xe4 -- fan2 (tacho2) 0xe5 -- fan3 (tacho3) 0xe6 -- fan4 (tacho4) 0xe7 -- fan5 (tacho5) 0xe8 -- fan6 (tacho6) 0xe9 -- fan7 (tacho7) 0xea -- fan8 (tacho8) 0xeb -- fan9 (tacho9) 0xec -- fan10 (tacho10) 0xed -- fan11 (tacho11) 0xee -- fan12 (tacho12) 0xef -This setup can be re-programmed with other registers. -Author: Vadim Pasternak +======================= ==== +pwm1 0xe3 +fan1 (tacho1) 0xe4 +fan2 (tacho2) 0xe5 +fan3 (tacho3) 0xe6 +fan4 (tacho4) 0xe7 +fan5 (tacho5) 0xe8 +fan6 (tacho6) 0xe9 +fan7 (tacho7) 0xea +fan8 (tacho8) 0xeb +fan9 (tacho9) 0xec +fan10 (tacho10) 0xed +fan11 (tacho11) 0xee +fan12 (tacho12) 0xef +======================= ==== + +This setup can be re-programmed with other registers. Description ----------- @@ -48,13 +54,17 @@ thermal's sysfs interfaces. /sys files in hwmon subsystem ----------------------------- -fan[1-12]_fault - RO files for tachometers TACH1-TACH12 fault indication -fan[1-12]_input - RO files for tachometers TACH1-TACH12 input (in RPM) -pwm1 - RW file for fan[1-12] target duty cycle (0..255) +================= == =================================================== +fan[1-12]_fault RO files for tachometers TACH1-TACH12 fault indication +fan[1-12]_input RO files for tachometers TACH1-TACH12 input (in RPM) +pwm1 RW file for fan[1-12] target duty cycle (0..255) +================= == =================================================== /sys files in thermal subsystem ------------------------------- -cur_state - RW file for current cooling state of the cooling device - (0..max_state) -max_state - RO file for maximum cooling state of the cooling device +================= == ==================================================== +cur_state RW file for current cooling state of the cooling device + (0..max_state) +max_state RO file for maximum cooling state of the cooling device +================= == ==================================================== diff --git a/Documentation/hwmon/nct6683 b/Documentation/hwmon/nct6683 index c1301d4300cd..efbf7e9703ec 100644 --- a/Documentation/hwmon/nct6683 +++ b/Documentation/hwmon/nct6683 @@ -2,13 +2,18 @@ Kernel driver nct6683 ===================== Supported chips: + * Nuvoton NCT6683D + Prefix: 'nct6683' + Addresses scanned: ISA address retrieved from Super I/O registers + Datasheet: Available from Nuvoton upon request Authors: - Guenter Roeck + + Guenter Roeck Description ----------- @@ -50,8 +55,10 @@ Tested Boards and Firmware Versions The driver has been reported to work with the following boards and firmware versions. +=============== =============================================== Board Firmware version ---------------------------------------------------------------- +=============== =============================================== Intel DH87RL NCT6683D EC firmware version 1.0 build 04/03/13 Intel DH87MC NCT6683D EC firmware version 1.0 build 04/03/13 Intel DB85FL NCT6683D EC firmware version 1.0 build 04/03/13 +=============== =============================================== diff --git a/Documentation/hwmon/nct7802 b/Documentation/hwmon/nct7802 index 5438deb6be02..8b7365a7cb32 100644 --- a/Documentation/hwmon/nct7802 +++ b/Documentation/hwmon/nct7802 @@ -2,13 +2,18 @@ Kernel driver nct7802 ===================== Supported chips: + * Nuvoton NCT7802Y + Prefix: 'nct7802' + Addresses scanned: I2C 0x28..0x2f + Datasheet: Available from Nuvoton web site Authors: - Guenter Roeck + + Guenter Roeck Description ----------- @@ -25,7 +30,9 @@ Tested Boards and BIOS Versions The driver has been reported to work with the following boards and BIOS versions. +======================= =============================================== Board BIOS version ---------------------------------------------------------------- +======================= =============================================== Kontron COMe-bSC2 CHR2E934.001.GGO Kontron COMe-bIP2 CCR2E212 +======================= =============================================== diff --git a/Documentation/hwmon/nct7904 b/Documentation/hwmon/nct7904 index 57fffe33ebfc..5b2f111582ff 100644 --- a/Documentation/hwmon/nct7904 +++ b/Documentation/hwmon/nct7904 @@ -1,11 +1,16 @@ Kernel driver nct7904 -==================== +===================== Supported chip: + * Nuvoton NCT7904D + Prefix: nct7904 + Addresses: I2C 0x2d, 0x2e + Datasheet: Publicly available at Nuvoton website + http://www.nuvoton.com/ Author: Vadim V. Vlasov @@ -25,6 +30,7 @@ Sysfs entries Currently, the driver supports only the following features: +======================= ======================================================= in[1-20]_input Input voltage measurements (mV) fan[1-12]_input Fan tachometer measurements (rpm) @@ -40,6 +46,7 @@ pwm[1-4]_enable R/W, 1/2 for manual or SmartFan mode previously configured by BIOS (or configuration EEPROM) pwm[1-4] R/O in SmartFan mode, R/W in manual control mode +======================= ======================================================= The driver checks sensor control registers and does not export the sensors that are not enabled. Anyway, a sensor that is enabled may actually be not diff --git a/Documentation/hwmon/npcm750-pwm-fan b/Documentation/hwmon/npcm750-pwm-fan index 6156ef7398e6..c67af08b6773 100644 --- a/Documentation/hwmon/npcm750-pwm-fan +++ b/Documentation/hwmon/npcm750-pwm-fan @@ -2,9 +2,11 @@ Kernel driver npcm750-pwm-fan ============================= Supported chips: + NUVOTON NPCM750/730/715/705 Authors: + Description: @@ -15,8 +17,10 @@ controller supports up to 16 tachometer inputs. The driver provides the following sensor accesses in sysfs: +=============== ======= ===================================================== fanX_input ro provide current fan rotation value in RPM as reported by the fan to the device. pwmX rw get or set PWM fan control value. This is an integer value between 0(off) and 255(full speed). +=============== ======= ===================================================== diff --git a/Documentation/hwmon/nsa320 b/Documentation/hwmon/nsa320 index fdbd6947799b..4fe75fd2f937 100644 --- a/Documentation/hwmon/nsa320 +++ b/Documentation/hwmon/nsa320 @@ -2,14 +2,23 @@ Kernel driver nsa320_hwmon ========================== Supported chips: + * Holtek HT46R065 microcontroller with onboard firmware that configures + it to act as a hardware monitor. + Prefix: 'nsa320' + Addresses scanned: none + Datasheet: Not available, driver was reverse engineered based upon the + Zyxel kernel source + + Author: + Adam Baker Description @@ -31,8 +40,10 @@ tenths of a degree. sysfs-Interface --------------- -temp1_input - temperature input -fan1_input - fan speed +============= ================= +temp1_input temperature input +fan1_input fan speed +============= ================= Notes ----- diff --git a/Documentation/hwmon/ntc_thermistor b/Documentation/hwmon/ntc_thermistor index 8b9ff23edc32..d0e7f91726b9 100644 --- a/Documentation/hwmon/ntc_thermistor +++ b/Documentation/hwmon/ntc_thermistor @@ -1,22 +1,29 @@ Kernel driver ntc_thermistor -================= +============================ Supported thermistors from Murata: + * Murata NTC Thermistors NCP15WB473, NCP18WB473, NCP21WB473, NCP03WB473, NCP15WL333, NCP03WF104, NCP15XH103 + Prefixes: 'ncp15wb473', 'ncp18wb473', 'ncp21wb473', 'ncp03wb473', 'ncp15wl333', 'ncp03wf104', 'ncp15xh103' + Datasheet: Publicly available at Murata Supported thermistors from EPCOS: + * EPCOS NTC Thermistors B57330V2103 + Prefixes: b57330v2103 + Datasheet: Publicly available at EPCOS Other NTC thermistors can be supported simply by adding compensation tables; e.g., NCP15WL333 support is added by the table ncpXXwl333. Authors: + MyungJoo Ham Description @@ -29,57 +36,60 @@ compensation table to get the temperature input. The NTC driver provides lookup tables with a linear approximation function and four circuit models with an option not to use any of the four models. +Using the following convention:: + + $ resistor + [TH] the thermistor + The four circuit models provided are: - $: resister, [TH]: the thermistor - - 1. connect = NTC_CONNECTED_POSITIVE, pullup_ohm > 0 - - [pullup_uV] - | | - [TH] $ (pullup_ohm) - | | - +----+-----------------------[read_uV] - | - $ (pulldown_ohm) - | - --- (ground) - - 2. connect = NTC_CONNECTED_POSITIVE, pullup_ohm = 0 (not-connected) - - [pullup_uV] - | - [TH] - | - +----------------------------[read_uV] - | - $ (pulldown_ohm) - | - --- (ground) - - 3. connect = NTC_CONNECTED_GROUND, pulldown_ohm > 0 - - [pullup_uV] - | - $ (pullup_ohm) - | - +----+-----------------------[read_uV] - | | - [TH] $ (pulldown_ohm) - | | - -------- (ground) - - 4. connect = NTC_CONNECTED_GROUND, pulldown_ohm = 0 (not-connected) - - [pullup_uV] - | - $ (pullup_ohm) - | - +----------------------------[read_uV] - | - [TH] - | - --- (ground) +1. connect = NTC_CONNECTED_POSITIVE, pullup_ohm > 0:: + + [pullup_uV] + | | + [TH] $ (pullup_ohm) + | | + +----+-----------------------[read_uV] + | + $ (pulldown_ohm) + | + -+- (ground) + +2. connect = NTC_CONNECTED_POSITIVE, pullup_ohm = 0 (not-connected):: + + [pullup_uV] + | + [TH] + | + +----------------------------[read_uV] + | + $ (pulldown_ohm) + | + -+- (ground) + +3. connect = NTC_CONNECTED_GROUND, pulldown_ohm > 0:: + + [pullup_uV] + | + $ (pullup_ohm) + | + +----+-----------------------[read_uV] + | | + [TH] $ (pulldown_ohm) + | | + -+----+- (ground) + +4. connect = NTC_CONNECTED_GROUND, pulldown_ohm = 0 (not-connected):: + + [pullup_uV] + | + $ (pullup_ohm) + | + +----------------------------[read_uV] + | + [TH] + | + -+- (ground) When one of the four circuit models is used, read_uV, pullup_uV, pullup_ohm, pulldown_ohm, and connect should be provided. When none of the four models @@ -88,13 +98,14 @@ provide read_ohm and _not_ provide the others. Sysfs Interface --------------- -name the mandatory global attribute, the thermistor name. -temp1_type always 4 (thermistor) - RO +=============== == ============================================================= +name the mandatory global attribute, the thermistor name. +=============== == ============================================================= +temp1_type RO always 4 (thermistor) -temp1_input measure the temperature and provide the measured value. - (reading this file initiates the reading procedure.) - RO +temp1_input RO measure the temperature and provide the measured value. + (reading this file initiates the reading procedure.) +=============== == ============================================================= Note that each NTC thermistor has only _one_ thermistor; thus, only temp1 exists. diff --git a/Documentation/hwmon/occ b/Documentation/hwmon/occ index e787596e03fe..bf41c162d70e 100644 --- a/Documentation/hwmon/occ +++ b/Documentation/hwmon/occ @@ -2,6 +2,7 @@ Kernel driver occ-hwmon ======================= Supported chips: + * POWER8 * POWER9 @@ -37,53 +38,87 @@ Some entries are only present with certain OCC sensor versions or only on certain OCCs in the system. The version number is not exported to the user but can be inferred. -temp[1-n]_label OCC sensor ID. +temp[1-n]_label + OCC sensor ID. + [with temperature sensor version 1] - temp[1-n]_input Measured temperature of the component in millidegrees + + temp[1-n]_input + Measured temperature of the component in millidegrees Celsius. + [with temperature sensor version >= 2] - temp[1-n]_type The FRU (Field Replaceable Unit) type + + temp[1-n]_type + The FRU (Field Replaceable Unit) type (represented by an integer) for the component that this sensor measures. - temp[1-n]_fault Temperature sensor fault boolean; 1 to indicate + temp[1-n]_fault + Temperature sensor fault boolean; 1 to indicate that a fault is present or 0 to indicate that no fault is present. + [with type == 3 (FRU type is VRM)] - temp[1-n]_alarm VRM temperature alarm boolean; 1 to indicate + + temp[1-n]_alarm + VRM temperature alarm boolean; 1 to indicate alarm, 0 to indicate no alarm + [else] - temp[1-n]_input Measured temperature of the component in - millidegrees Celsius. -freq[1-n]_label OCC sensor ID. -freq[1-n]_input Measured frequency of the component in MHz. + temp[1-n]_input + Measured temperature of the component in + millidegrees Celsius. -power[1-n]_input Latest measured power reading of the component in +freq[1-n]_label + OCC sensor ID. +freq[1-n]_input + Measured frequency of the component in MHz. +power[1-n]_input + Latest measured power reading of the component in microwatts. -power[1-n]_average Average power of the component in microwatts. -power[1-n]_average_interval The amount of time over which the power average +power[1-n]_average + Average power of the component in microwatts. +power[1-n]_average_interval + The amount of time over which the power average was taken in microseconds. + [with power sensor version < 2] - power[1-n]_label OCC sensor ID. + + power[1-n]_label + OCC sensor ID. + [with power sensor version >= 2] - power[1-n]_label OCC sensor ID + function ID + channel in the form + + power[1-n]_label + OCC sensor ID + function ID + channel in the form of a string, delimited by underscores, i.e. "0_15_1". Both the function ID and channel are integers that further identify the power sensor. + [with power sensor version 0xa0] - power[1-n]_label OCC sensor ID + sensor type in the form of a string, + + power[1-n]_label + OCC sensor ID + sensor type in the form of a string, delimited by an underscore, i.e. "0_system". Sensor type will be one of "system", "proc", "vdd" or "vdn". For this sensor version, OCC sensor ID will be the same for all power sensors. + [present only on "master" OCC; represents the whole system power; only one of - this type of power sensor will be present] - power[1-n]_label "system" - power[1-n]_input Latest system output power in microwatts. - power[1-n]_cap Current system power cap in microwatts. - power[1-n]_cap_not_redundant System power cap in microwatts when - there is not redundant power. - power[1-n]_cap_max Maximum power cap that the OCC can enforce in +this type of power sensor will be present] + + power[1-n]_label + "system" + power[1-n]_input + Latest system output power in microwatts. + power[1-n]_cap + Current system power cap in microwatts. + power[1-n]_cap_not_redundant + System power cap in microwatts when + there is not redundant power. + power[1-n]_cap_max + Maximum power cap that the OCC can enforce in microwatts. power[1-n]_cap_min Minimum power cap that the OCC can enforce in microwatts. @@ -94,8 +129,11 @@ power[1-n]_average_interval The amount of time over which the power average ignored, i.e. requesting a power cap of 500900000 microwatts will result in a power cap request of 500 watts. + [with caps sensor version > 1] - power[1-n]_cap_user_source Indicates how the user power cap was + + power[1-n]_cap_user_source + Indicates how the user power cap was set. This is an integer that maps to system or firmware components that can set the user power cap. @@ -104,9 +142,12 @@ The following "extn" sensors are exported as a way for the OCC to provide data that doesn't fit anywhere else. The meaning of these sensors is entirely dependent on their data, and cannot be statically defined. -extn[1-n]_label ASCII ID or OCC sensor ID. -extn[1-n]_flags This is one byte hexadecimal value. Bit 7 indicates the +extn[1-n]_label + ASCII ID or OCC sensor ID. +extn[1-n]_flags + This is one byte hexadecimal value. Bit 7 indicates the type of the label attribute; 1 for sensor ID, 0 for ASCII ID. Other bits are reserved. -extn[1-n]_input 6 bytes of hexadecimal data, with a meaning defined by +extn[1-n]_input + 6 bytes of hexadecimal data, with a meaning defined by the sensor ID. diff --git a/Documentation/hwmon/pc87427 b/Documentation/hwmon/pc87427 index c313eb66e08a..22d8f62d851f 100644 --- a/Documentation/hwmon/pc87427 +++ b/Documentation/hwmon/pc87427 @@ -2,9 +2,13 @@ Kernel driver pc87427 ===================== Supported chips: + * National Semiconductor PC87427 + Prefix: 'pc87427' + Addresses scanned: none, address read from Super I/O config space + Datasheet: No longer available Author: Jean Delvare diff --git a/Documentation/hwmon/pcf8591 b/Documentation/hwmon/pcf8591 index 447c0702c0ec..e98bd542a441 100644 --- a/Documentation/hwmon/pcf8591 +++ b/Documentation/hwmon/pcf8591 @@ -2,16 +2,21 @@ Kernel driver pcf8591 ===================== Supported chips: + * Philips/NXP PCF8591 + Prefix: 'pcf8591' + Addresses scanned: none + Datasheet: Publicly available at the NXP website - http://www.nxp.com/pip/PCF8591_6.html + + http://www.nxp.com/pip/PCF8591_6.html Authors: - Aurelien Jarno - valuable contributions by Jan M. Sendler , - Jean Delvare + - Aurelien Jarno + - valuable contributions by Jan M. Sendler , + - Jean Delvare Description @@ -22,24 +27,25 @@ analog output) for the I2C bus produced by Philips Semiconductors (now NXP). It is designed to provide a byte I2C interface to up to 4 separate devices. The PCF8591 has 4 analog inputs programmable as single-ended or -differential inputs : +differential inputs: + - mode 0 : four single ended inputs - Pins AIN0 to AIN3 are single ended inputs for channels 0 to 3 + Pins AIN0 to AIN3 are single ended inputs for channels 0 to 3 - mode 1 : three differential inputs - Pins AIN3 is the common negative differential input - Pins AIN0 to AIN2 are positive differential inputs for channels 0 to 2 + Pins AIN3 is the common negative differential input + Pins AIN0 to AIN2 are positive differential inputs for channels 0 to 2 - mode 2 : single ended and differential mixed - Pins AIN0 and AIN1 are single ended inputs for channels 0 and 1 - Pins AIN2 is the positive differential input for channel 3 - Pins AIN3 is the negative differential input for channel 3 + Pins AIN0 and AIN1 are single ended inputs for channels 0 and 1 + Pins AIN2 is the positive differential input for channel 3 + Pins AIN3 is the negative differential input for channel 3 - mode 3 : two differential inputs - Pins AIN0 is the positive differential input for channel 0 - Pins AIN1 is the negative differential input for channel 0 - Pins AIN2 is the positive differential input for channel 1 - Pins AIN3 is the negative differential input for channel 1 + Pins AIN0 is the positive differential input for channel 0 + Pins AIN1 is the negative differential input for channel 0 + Pins AIN2 is the positive differential input for channel 1 + Pins AIN3 is the negative differential input for channel 1 See the datasheet for details. @@ -49,10 +55,11 @@ Module parameters * input_mode int Analog input mode: - 0 = four single ended inputs - 1 = three differential inputs - 2 = single ended and differential mixed - 3 = two differential inputs + + - 0 = four single ended inputs + - 1 = three differential inputs + - 2 = single ended and differential mixed + - 3 = two differential inputs Accessing PCF8591 via /sys interface @@ -67,11 +74,12 @@ for details. Directories are being created for each instantiated PCF8591: /sys/bus/i2c/devices/<0>-<1>/ -where <0> is the bus the chip is connected to (e. g. i2c-0) -and <1> the chip address ([48..4f]) + where <0> is the bus the chip is connected to (e. g. i2c-0) + and <1> the chip address ([48..4f]) Inside these directories, there are such files: -in0_input, in1_input, in2_input, in3_input, out0_enable, out0_output, name + + in0_input, in1_input, in2_input, in3_input, out0_enable, out0_output, name Name contains chip name. diff --git a/Documentation/hwmon/powr1220 b/Documentation/hwmon/powr1220 index 21e44f71ae6e..a7fc258da0a8 100644 --- a/Documentation/hwmon/powr1220 +++ b/Documentation/hwmon/powr1220 @@ -1,12 +1,17 @@ Kernel driver powr1220 -================== +====================== Supported chips: + * Lattice POWR1220AT8 + Prefix: 'powr1220' + Addresses scanned: none + Datasheet: Publicly available at the Lattice website - http://www.latticesemi.com/ + + http://www.latticesemi.com/ Author: Scott Kanowitz @@ -26,7 +31,9 @@ value over the low measurement range maximum of 2 V. The input naming convention is as follows: +============== ======== driver name pin name +============== ======== in0 VMON1 in1 VMON2 in2 VMON3 @@ -41,5 +48,6 @@ in10 VMON11 in11 VMON12 in12 VCCA in13 VCCINP +============== ======== The ADC readings are updated on request with a minimum period of 1s. diff --git a/Documentation/hwmon/raspberrypi-hwmon b/Documentation/hwmon/raspberrypi-hwmon index 3c92e2cb52d6..8038ade36490 100644 --- a/Documentation/hwmon/raspberrypi-hwmon +++ b/Documentation/hwmon/raspberrypi-hwmon @@ -2,6 +2,7 @@ Kernel driver raspberrypi-hwmon =============================== Supported boards: + * Raspberry Pi A+ (via GPIO on SoC) * Raspberry Pi B+ (via GPIO on SoC) * Raspberry Pi 2 B (via GPIO on SoC) @@ -19,4 +20,6 @@ undervoltage conditions. Sysfs entries ------------- +======================= ================== in0_lcrit_alarm Undervoltage alarm +======================= ================== diff --git a/Documentation/hwmon/sch5636 b/Documentation/hwmon/sch5636 index 7b0a01da0717..4aaee3672f13 100644 --- a/Documentation/hwmon/sch5636 +++ b/Documentation/hwmon/sch5636 @@ -2,8 +2,11 @@ Kernel driver sch5636 ===================== Supported chips: + * SMSC SCH5636 + Prefix: 'sch5636' + Addresses scanned: none, address read from Super I/O config space Author: Hans de Goede diff --git a/Documentation/hwmon/scpi-hwmon b/Documentation/hwmon/scpi-hwmon index 4cfcdf2d5eab..eee7022b44db 100644 --- a/Documentation/hwmon/scpi-hwmon +++ b/Documentation/hwmon/scpi-hwmon @@ -2,8 +2,11 @@ Kernel driver scpi-hwmon ======================== Supported chips: + * Chips based on ARM System Control Processor Interface + Addresses scanned: - + Datasheet: http://infocenter.arm.com/help/index.jsp?topic=/com.arm.doc.dui0922b/index.html Author: Punit Agrawal @@ -14,7 +17,7 @@ Description This driver supports hardware monitoring for SoC's based on the ARM System Control Processor (SCP) implementing the System Control Processor Interface (SCPI). The following sensor types are supported -by the SCP - +by the SCP: * temperature * voltage @@ -30,4 +33,4 @@ Usage Notes The driver relies on device tree node to indicate the presence of SCPI support in the kernel. See Documentation/devicetree/bindings/arm/arm,scpi.txt for details of the -devicetree node. \ No newline at end of file +devicetree node. diff --git a/Documentation/hwmon/sht15 b/Documentation/hwmon/sht15 index 5e3207c3b177..485abe037f6c 100644 --- a/Documentation/hwmon/sht15 +++ b/Documentation/hwmon/sht15 @@ -2,29 +2,37 @@ Kernel driver sht15 =================== Authors: + * Wouter Horre * Jonathan Cameron * Vivien Didelot * Jerome Oufella Supported chips: + * Sensirion SHT10 + Prefix: 'sht10' * Sensirion SHT11 + Prefix: 'sht11' * Sensirion SHT15 + Prefix: 'sht15' * Sensirion SHT71 + Prefix: 'sht71' * Sensirion SHT75 + Prefix: 'sht75' Datasheet: Publicly available at the Sensirion website -http://www.sensirion.ch/en/pdf/product_information/Datasheet-humidity-sensor-SHT1x.pdf + + http://www.sensirion.ch/en/pdf/product_information/Datasheet-humidity-sensor-SHT1x.pdf Description ----------- @@ -63,11 +71,13 @@ Platform data Sysfs interface --------------- -* temp1_input: temperature input -* humidity1_input: humidity input -* heater_enable: write 1 in this attribute to enable the on-chip heater, - 0 to disable it. Be careful not to enable the heater - for too long. -* temp1_fault: if 1, this means that the voltage is low (below 2.47V) and - measurement may be invalid. -* humidity1_fault: same as temp1_fault. +================== ========================================================== +temp1_input temperature input +humidity1_input humidity input +heater_enable write 1 in this attribute to enable the on-chip heater, + 0 to disable it. Be careful not to enable the heater + for too long. +temp1_fault if 1, this means that the voltage is low (below 2.47V) and + measurement may be invalid. +humidity1_fault same as temp1_fault. +================== ========================================================== diff --git a/Documentation/hwmon/sht21 b/Documentation/hwmon/sht21 index 8b3cdda541c1..f1f5da030108 100644 --- a/Documentation/hwmon/sht21 +++ b/Documentation/hwmon/sht21 @@ -2,19 +2,33 @@ Kernel driver sht21 =================== Supported chips: + * Sensirion SHT21 + Prefix: 'sht21' + Addresses scanned: none + Datasheet: Publicly available at the Sensirion website + http://www.sensirion.com/file/datasheet_sht21 + + * Sensirion SHT25 + Prefix: 'sht25' + Addresses scanned: none + Datasheet: Publicly available at the Sensirion website + http://www.sensirion.com/file/datasheet_sht25 + + Author: + Urs Fleisch Description @@ -33,9 +47,13 @@ in the board setup code. sysfs-Interface --------------- -temp1_input - temperature input -humidity1_input - humidity input -eic - Electronic Identification Code +temp1_input + - temperature input + +humidity1_input + - humidity input +eic + - Electronic Identification Code Notes ----- diff --git a/Documentation/hwmon/sht3x b/Documentation/hwmon/sht3x index d9daa6ab1e8e..978a7117e4b2 100644 --- a/Documentation/hwmon/sht3x +++ b/Documentation/hwmon/sht3x @@ -2,14 +2,19 @@ Kernel driver sht3x =================== Supported chips: + * Sensirion SHT3x-DIS + Prefix: 'sht3x' + Addresses scanned: none + Datasheet: https://www.sensirion.com/file/datasheet_sht3x_digital Author: - David Frey - Pascal Sachs + + - David Frey + - Pascal Sachs Description ----------- @@ -24,6 +29,7 @@ addresses 0x44 or 0x45, depending on the wiring. See Documentation/i2c/instantiating-devices for methods to instantiate the device. There are two options configurable by means of sht3x_platform_data: + 1. blocking (pull the I2C clock line down while performing the measurement) or non-blocking mode. Blocking mode will guarantee the fastest result but the I2C bus will be busy during that time. By default, non-blocking mode @@ -35,12 +41,15 @@ There are two options configurable by means of sht3x_platform_data: The sht3x sensor supports a single shot mode as well as 5 periodic measure modes, which can be controlled with the update_interval sysfs interface. The allowed update_interval in milliseconds are as follows: - * 0 single shot mode - * 2000 0.5 Hz periodic measurement - * 1000 1 Hz periodic measurement - * 500 2 Hz periodic measurement - * 250 4 Hz periodic measurement - * 100 10 Hz periodic measurement + + ===== ======= ==================== + 0 single shot mode + 2000 0.5 Hz periodic measurement + 1000 1 Hz periodic measurement + 500 2 Hz periodic measurement + 250 4 Hz periodic measurement + 100 10 Hz periodic measurement + ===== ======= ==================== In the periodic measure mode, the sensor automatically triggers a measurement with the configured update interval on the chip. When a temperature or humidity @@ -53,6 +62,7 @@ low. sysfs-Interface --------------- +=================== ============================================================ temp1_input: temperature input humidity1_input: humidity input temp1_max: temperature max value @@ -64,13 +74,15 @@ temp1_min_hyst: temperature hysteresis value for min limit humidity1_min: humidity min value humidity1_min_hyst: humidity hysteresis value for min limit temp1_alarm: alarm flag is set to 1 if the temperature is outside the - configured limits. Alarm only works in periodic measure mode + configured limits. Alarm only works in periodic measure mode humidity1_alarm: alarm flag is set to 1 if the humidity is outside the - configured limits. Alarm only works in periodic measure mode + configured limits. Alarm only works in periodic measure mode heater_enable: heater enable, heating element removes excess humidity from - sensor - 0: turned off - 1: turned on + sensor: + + - 0: turned off + - 1: turned on update_interval: update interval, 0 for single shot, interval in msec - for periodic measurement. If the interval is not supported - by the sensor, the next faster interval is chosen + for periodic measurement. If the interval is not supported + by the sensor, the next faster interval is chosen +=================== ============================================================ diff --git a/Documentation/hwmon/shtc1 b/Documentation/hwmon/shtc1 index 6b1e05458f0f..aa116332ba26 100644 --- a/Documentation/hwmon/shtc1 +++ b/Documentation/hwmon/shtc1 @@ -2,17 +2,29 @@ Kernel driver shtc1 =================== Supported chips: + * Sensirion SHTC1 + Prefix: 'shtc1' + Addresses scanned: none + Datasheet: http://www.sensirion.com/file/datasheet_shtc1 + + * Sensirion SHTW1 + Prefix: 'shtw1' + Addresses scanned: none + Datasheet: Not publicly available + + Author: + Johannes Winkelmann Description @@ -28,6 +40,7 @@ address 0x70. See Documentation/i2c/instantiating-devices for methods to instantiate the device. There are two options configurable by means of shtc1_platform_data: + 1. blocking (pull the I2C clock line down while performing the measurement) or non-blocking mode. Blocking mode will guarantee the fastest result but the I2C bus will be busy during that time. By default, non-blocking mode @@ -39,5 +52,7 @@ There are two options configurable by means of shtc1_platform_data: sysfs-Interface --------------- -temp1_input - temperature input -humidity1_input - humidity input +temp1_input + - temperature input +humidity1_input + - humidity input diff --git a/Documentation/hwmon/sis5595 b/Documentation/hwmon/sis5595 index 4f8877a34f37..5acba6b0c0db 100644 --- a/Documentation/hwmon/sis5595 +++ b/Documentation/hwmon/sis5595 @@ -2,49 +2,67 @@ Kernel driver sis5595 ===================== Supported chips: + * Silicon Integrated Systems Corp. SiS5595 Southbridge Hardware Monitor + Prefix: 'sis5595' + Addresses scanned: ISA in PCI-space encoded address + Datasheet: Publicly available at the Silicon Integrated Systems Corp. site. + + Authors: - Kyösti Mälkki , - Mark D. Studebaker , - Aurelien Jarno 2.6 port + + - Kyösti Mälkki , + - Mark D. Studebaker , + - Aurelien Jarno 2.6 port SiS southbridge has a LM78-like chip integrated on the same IC. This driver is a customized copy of lm78.c Supports following revisions: + + =============== =============== ============== Version PCI ID PCI Revision + =============== =============== ============== 1 1039/0008 AF or less 2 1039/0008 B0 or greater + =============== =============== ============== Note: these chips contain a 0008 device which is incompatible with the - 5595. We recognize these by the presence of the listed - "blacklist" PCI ID and refuse to load. + 5595. We recognize these by the presence of the listed + "blacklist" PCI ID and refuse to load. + =================== =============== ================ NOT SUPPORTED PCI ID BLACKLIST PCI ID - 540 0008 0540 - 550 0008 0550 + =================== =============== ================ + 540 0008 0540 + 550 0008 0550 5513 0008 5511 5581 0008 5597 5582 0008 5597 5597 0008 5597 - 630 0008 0630 - 645 0008 0645 - 730 0008 0730 - 735 0008 0735 + 630 0008 0630 + 645 0008 0645 + 730 0008 0730 + 735 0008 0735 + =================== =============== ================ Module Parameters ----------------- + +======================= ===================================================== force_addr=0xaddr Set the I/O base address. Useful for boards that don't set the address in the BIOS. Does not do a PCI force; the device must still be present in lspci. Don't use this unless the driver complains that the base address is not set. + Example: 'modprobe sis5595 force_addr=0x290' +======================= ===================================================== Description diff --git a/Documentation/hwmon/smsc47b397 b/Documentation/hwmon/smsc47b397 index 3a43b6948924..600194cf1804 100644 --- a/Documentation/hwmon/smsc47b397 +++ b/Documentation/hwmon/smsc47b397 @@ -2,29 +2,38 @@ Kernel driver smsc47b397 ======================== Supported chips: + * SMSC LPC47B397-NC + * SMSC SCH5307-NS + * SMSC SCH5317 + Prefix: 'smsc47b397' + Addresses scanned: none, address read from Super I/O config space + Datasheet: In this file -Authors: Mark M. Hoffman - Utilitek Systems, Inc. +Authors: + + - Mark M. Hoffman + - Utilitek Systems, Inc. November 23, 2004 -The following specification describes the SMSC LPC47B397-NC[1] sensor chip +The following specification describes the SMSC LPC47B397-NC [1]_ sensor chip (for which there is no public datasheet available). This document was provided by Craig Kelly (In-Store Broadcast Network) and edited/corrected by Mark M. Hoffman . -[1] And SMSC SCH5307-NS and SCH5317, which have different device IDs but are -otherwise compatible. +.. [1] And SMSC SCH5307-NS and SCH5317, which have different device IDs but are + otherwise compatible. -* * * * * +------------------------------------------------------------------------- -Methods for detecting the HP SIO and reading the thermal data on a dc7100. +Methods for detecting the HP SIO and reading the thermal data on a dc7100 +------------------------------------------------------------------------- The thermal information on the dc7100 is contained in the SIO Hardware Monitor (HWM). The information is accessed through an index/data pair. The index/data @@ -35,18 +44,22 @@ and 0x61 (LSB). Currently we are using 0x480 for the HWM Base Address and Reading temperature information. The temperature information is located in the following registers: + +=============== ======= ======================================================= Temp1 0x25 (Currently, this reflects the CPU temp on all systems). Temp2 0x26 Temp3 0x27 Temp4 0x80 +=============== ======= ======================================================= Programming Example -The following is an example of how to read the HWM temperature registers: -MOV DX,480H -MOV AX,25H -OUT DX,AL -MOV DX,481H -IN AL,DX +The following is an example of how to read the HWM temperature registers:: + + MOV DX,480H + MOV AX,25H + OUT DX,AL + MOV DX,481H + IN AL,DX AL contains the data in hex, the temperature in Celsius is the decimal equivalent. @@ -55,25 +68,32 @@ Ex: If AL contains 0x2A, the temperature is 42 degrees C. Reading tach information. The fan speed information is located in the following registers: + +=============== ======= ======= ================================= LSB MSB Tach1 0x28 0x29 (Currently, this reflects the CPU fan speed on all systems). Tach2 0x2A 0x2B Tach3 0x2C 0x2D Tach4 0x2E 0x2F +=============== ======= ======= ================================= -Important!!! -Reading the tach LSB locks the tach MSB. -The LSB Must be read first. +.. Important:: + + Reading the tach LSB locks the tach MSB. + The LSB Must be read first. + +How to convert the tach reading to RPM +-------------------------------------- -How to convert the tach reading to RPM. The tach reading (TCount) is given by: (Tach MSB * 256) + (Tach LSB) The SIO counts the number of 90kHz (11.111us) pulses per revolution. RPM = 60/(TCount * 11.111us) -Example: -Reg 0x28 = 0x9B -Reg 0x29 = 0x08 +Example:: + + Reg 0x28 = 0x9B + Reg 0x29 = 0x08 TCount = 0x89B = 2203 @@ -81,21 +101,28 @@ RPM = 60 / (2203 * 11.11111 E-6) = 2451 RPM Obtaining the SIO version. -CONFIGURATION SEQUENCE +Configuration Sequence +---------------------- + To program the configuration registers, the following sequence must be followed: 1. Enter Configuration Mode 2. Configure the Configuration Registers 3. Exit Configuration Mode. Enter Configuration Mode +^^^^^^^^^^^^^^^^^^^^^^^^ + To place the chip into the Configuration State The config key (0x55) is written to the CONFIG PORT (0x2E). Configuration Mode +^^^^^^^^^^^^^^^^^^ + In configuration mode, the INDEX PORT is located at the CONFIG PORT address and the DATA PORT is at INDEX PORT address + 1. The desired configuration registers are accessed in two steps: + a. Write the index of the Logical Device Number Configuration Register (i.e., 0x07) to the INDEX PORT and then write the number of the desired logical device to the DATA PORT. @@ -104,30 +131,35 @@ b. Write the address of the desired configuration register within the logical device to the INDEX PORT and then write or read the config- uration register through the DATA PORT. -Note: If accessing the Global Configuration Registers, step (a) is not required. +Note: + If accessing the Global Configuration Registers, step (a) is not required. Exit Configuration Mode +^^^^^^^^^^^^^^^^^^^^^^^ + To exit the Configuration State the write 0xAA to the CONFIG PORT (0x2E). The chip returns to the RUN State. (This is important). Programming Example -The following is an example of how to read the SIO Device ID located at 0x20 - -; ENTER CONFIGURATION MODE -MOV DX,02EH -MOV AX,055H -OUT DX,AL -; GLOBAL CONFIGURATION REGISTER -MOV DX,02EH -MOV AL,20H -OUT DX,AL -; READ THE DATA -MOV DX,02FH -IN AL,DX -; EXIT CONFIGURATION MODE -MOV DX,02EH -MOV AX,0AAH -OUT DX,AL +^^^^^^^^^^^^^^^^^^^ + +The following is an example of how to read the SIO Device ID located at 0x20: + + ; ENTER CONFIGURATION MODE + MOV DX,02EH + MOV AX,055H + OUT DX,AL + ; GLOBAL CONFIGURATION REGISTER + MOV DX,02EH + MOV AL,20H + OUT DX,AL + ; READ THE DATA + MOV DX,02FH + IN AL,DX + ; EXIT CONFIGURATION MODE + MOV DX,02EH + MOV AX,0AAH + OUT DX,AL The registers of interest for identifying the SIO on the dc7100 are Device ID (0x20) and Device Rev (0x21). @@ -135,29 +167,31 @@ The registers of interest for identifying the SIO on the dc7100 are Device ID The Device ID will read 0x6F (0x81 for SCH5307-NS, and 0x85 for SCH5317) The Device Rev currently reads 0x01 -Obtaining the HWM Base Address. +Obtaining the HWM Base Address +------------------------------ + The following is an example of how to read the HWM Base Address located in -Logical Device 8. - -; ENTER CONFIGURATION MODE -MOV DX,02EH -MOV AX,055H -OUT DX,AL -; CONFIGURE REGISTER CRE0, -; LOGICAL DEVICE 8 -MOV DX,02EH -MOV AL,07H -OUT DX,AL ;Point to LD# Config Reg -MOV DX,02FH -MOV AL, 08H -OUT DX,AL;Point to Logical Device 8 -; -MOV DX,02EH -MOV AL,60H -OUT DX,AL ; Point to HWM Base Addr MSB -MOV DX,02FH -IN AL,DX ; Get MSB of HWM Base Addr -; EXIT CONFIGURATION MODE -MOV DX,02EH -MOV AX,0AAH -OUT DX,AL +Logical Device 8:: + + ; ENTER CONFIGURATION MODE + MOV DX,02EH + MOV AX,055H + OUT DX,AL + ; CONFIGURE REGISTER CRE0, + ; LOGICAL DEVICE 8 + MOV DX,02EH + MOV AL,07H + OUT DX,AL ;Point to LD# Config Reg + MOV DX,02FH + MOV AL, 08H + OUT DX,AL;Point to Logical Device 8 + ; + MOV DX,02EH + MOV AL,60H + OUT DX,AL ; Point to HWM Base Addr MSB + MOV DX,02FH + IN AL,DX ; Get MSB of HWM Base Addr + ; EXIT CONFIGURATION MODE + MOV DX,02EH + MOV AX,0AAH + OUT DX,AL diff --git a/Documentation/hwmon/smsc47m1 b/Documentation/hwmon/smsc47m1 index 10a24b420686..c54eabd5eb57 100644 --- a/Documentation/hwmon/smsc47m1 +++ b/Documentation/hwmon/smsc47m1 @@ -2,30 +2,53 @@ Kernel driver smsc47m1 ====================== Supported chips: + * SMSC LPC47B27x, LPC47M112, LPC47M10x, LPC47M13x, LPC47M14x, + LPC47M15x and LPC47M192 + Addresses scanned: none, address read from Super I/O config space + Prefix: 'smsc47m1' + Datasheets: - http://www.smsc.com/media/Downloads_Public/Data_Sheets/47b272.pdf - http://www.smsc.com/media/Downloads_Public/Data_Sheets/47m10x.pdf - http://www.smsc.com/media/Downloads_Public/Data_Sheets/47m112.pdf - http://www.smsc.com/ + + http://www.smsc.com/media/Downloads_Public/Data_Sheets/47b272.pdf + + http://www.smsc.com/media/Downloads_Public/Data_Sheets/47m10x.pdf + + http://www.smsc.com/media/Downloads_Public/Data_Sheets/47m112.pdf + + http://www.smsc.com/ + * SMSC LPC47M292 + Addresses scanned: none, address read from Super I/O config space + Prefix: 'smsc47m2' + Datasheet: Not public + * SMSC LPC47M997 + Addresses scanned: none, address read from Super I/O config space + Prefix: 'smsc47m1' + Datasheet: none + + Authors: - Mark D. Studebaker , - With assistance from Bruce Allen , and his - fan.c program: http://www.lsc-group.phys.uwm.edu/%7Eballen/driver/ - Gabriele Gorla , - Jean Delvare + + - Mark D. Studebaker , + - With assistance from Bruce Allen , and his + fan.c program: + + - http://www.lsc-group.phys.uwm.edu/%7Eballen/driver/ + + - Gabriele Gorla , + - Jean Delvare Description ----------- @@ -57,7 +80,7 @@ hardware registers are read whenever any data is read (unless it is less than 1.5 seconds since the last update). This means that you can easily miss once-only alarms. +------------------------------------------------------------------ -********************** The lm_sensors project gratefully acknowledges the support of Intel in the development of this driver. diff --git a/Documentation/hwmon/smsc47m192 b/Documentation/hwmon/smsc47m192 index 6d54ecb7b3f8..a2e86ab67918 100644 --- a/Documentation/hwmon/smsc47m192 +++ b/Documentation/hwmon/smsc47m192 @@ -2,17 +2,28 @@ Kernel driver smsc47m192 ======================== Supported chips: + * SMSC LPC47M192, LPC47M15x, LPC47M292 and LPC47M997 + Prefix: 'smsc47m192' + Addresses scanned: I2C 0x2c - 0x2d + Datasheet: The datasheet for LPC47M192 is publicly available from - http://www.smsc.com/ - The LPC47M15x, LPC47M292 and LPC47M997 are compatible for - hardware monitoring. -Author: Hartmut Rick - Special thanks to Jean Delvare for careful checking - of the code and many helpful comments and suggestions. + http://www.smsc.com/ + + The LPC47M15x, LPC47M292 and LPC47M997 are compatible for + + hardware monitoring. + + + +Author: + - Hartmut Rick + + - Special thanks to Jean Delvare for careful checking + of the code and many helpful comments and suggestions. Description @@ -52,52 +63,54 @@ Reading them more often repeats the same values. sysfs interface --------------- -in0_input - +2.5V voltage input -in1_input - CPU voltage input (nominal 2.25V) -in2_input - +3.3V voltage input -in3_input - +5V voltage input -in4_input - +12V voltage input (may be missing if used as VID4) -in5_input - Vcc voltage input (nominal 3.3V) - This is the supply voltage of the sensor chip itself. -in6_input - +1.5V voltage input -in7_input - +1.8V voltage input +===================== ========================================================== +in0_input +2.5V voltage input +in1_input CPU voltage input (nominal 2.25V) +in2_input +3.3V voltage input +in3_input +5V voltage input +in4_input +12V voltage input (may be missing if used as VID4) +in5_input Vcc voltage input (nominal 3.3V) + This is the supply voltage of the sensor chip itself. +in6_input +1.5V voltage input +in7_input +1.8V voltage input in[0-7]_min, -in[0-7]_max - lower and upper alarm thresholds for in[0-7]_input reading +in[0-7]_max lower and upper alarm thresholds for in[0-7]_input reading - All voltages are read and written in mV. + All voltages are read and written in mV. -in[0-7]_alarm - alarm flags for voltage inputs - These files read '1' in case of alarm, '0' otherwise. +in[0-7]_alarm alarm flags for voltage inputs + These files read '1' in case of alarm, '0' otherwise. -temp1_input - chip temperature measured by on-chip diode -temp[2-3]_input - temperature measured by external diodes (one of these would - typically be wired to the diode inside the CPU) +temp1_input chip temperature measured by on-chip diode +temp[2-3]_input temperature measured by external diodes (one of these + would typically be wired to the diode inside the CPU) temp[1-3]_min, -temp[1-3]_max - lower and upper alarm thresholds for temperatures +temp[1-3]_max lower and upper alarm thresholds for temperatures -temp[1-3]_offset - temperature offset registers - The chip adds the offsets stored in these registers to - the corresponding temperature readings. - Note that temp1 and temp2 offsets share the same register, - they cannot both be different from zero at the same time. - Writing a non-zero number to one of them will reset the other - offset to zero. +temp[1-3]_offset temperature offset registers + The chip adds the offsets stored in these registers to + the corresponding temperature readings. + Note that temp1 and temp2 offsets share the same register, + they cannot both be different from zero at the same time. + Writing a non-zero number to one of them will reset the other + offset to zero. - All temperatures and offsets are read and written in - units of 0.001 degC. + All temperatures and offsets are read and written in + units of 0.001 degC. -temp[1-3]_alarm - alarm flags for temperature inputs, '1' in case of alarm, - '0' otherwise. -temp[2-3]_input_fault - diode fault flags for temperature inputs 2 and 3. - A fault is detected if the two pins for the corresponding - sensor are open or shorted, or any of the two is shorted - to ground or Vcc. '1' indicates a diode fault. +temp[1-3]_alarm alarm flags for temperature inputs, '1' in case of alarm, + '0' otherwise. +temp[2-3]_input_fault diode fault flags for temperature inputs 2 and 3. + A fault is detected if the two pins for the corresponding + sensor are open or shorted, or any of the two is shorted + to ground or Vcc. '1' indicates a diode fault. -cpu0_vid - CPU voltage as received from the CPU +cpu0_vid CPU voltage as received from the CPU -vrm - CPU VID standard used for decoding CPU voltage +vrm CPU VID standard used for decoding CPU voltage +===================== ========================================================== - The *_min, *_max, *_offset and vrm files can be read and - written, all others are read-only. +The `*_min`, `*_max`, `*_offset` and `vrm` files can be read and written, +all others are read-only. diff --git a/Documentation/hwmon/submitting-patches b/Documentation/hwmon/submitting-patches index f88221b46153..12540b7d9b50 100644 --- a/Documentation/hwmon/submitting-patches +++ b/Documentation/hwmon/submitting-patches @@ -1,5 +1,5 @@ - How to Get Your Patch Accepted Into the Hwmon Subsystem - ------------------------------------------------------- +How to Get Your Patch Accepted Into the Hwmon Subsystem +======================================================= This text is a collection of suggestions for people writing patches or drivers for the hwmon subsystem. Following these suggestions will greatly @@ -9,11 +9,12 @@ increase the chances of your change being accepted. 1. General ---------- -* It should be unnecessary to mention, but please read and follow - Documentation/process/submit-checklist.rst - Documentation/process/submitting-drivers.rst - Documentation/process/submitting-patches.rst - Documentation/process/coding-style.rst +* It should be unnecessary to mention, but please read and follow: + + - Documentation/process/submit-checklist.rst + - Documentation/process/submitting-drivers.rst + - Documentation/process/submitting-patches.rst + - Documentation/process/coding-style.rst * Please run your patch through 'checkpatch --strict'. There should be no errors, no warnings, and few if any check messages. If there are any diff --git a/Documentation/hwmon/sysfs-interface b/Documentation/hwmon/sysfs-interface index 7b91706d01c8..fd590633bb14 100644 --- a/Documentation/hwmon/sysfs-interface +++ b/Documentation/hwmon/sysfs-interface @@ -1,5 +1,5 @@ Naming and data format standards for sysfs files ------------------------------------------------- +================================================ The libsensors library offers an interface to the raw sensors data through the sysfs interface. Since lm-sensors 3.0.0, libsensors is @@ -32,7 +32,7 @@ this reason, it is still not recommended to bypass the library. Each chip gets its own directory in the sysfs /sys/devices tree. To find all sensor chips, it is easier to follow the device symlinks from -/sys/class/hwmon/hwmon*. +`/sys/class/hwmon/hwmon*`. Up to lm-sensors 3.0.0, libsensors looks for hardware monitoring attributes in the "physical" device directory. Since lm-sensors 3.0.1, attributes found @@ -67,11 +67,13 @@ are interpreted as 0! For more on how written strings are interpreted see the ------------------------------------------------------------------------- -[0-*] denotes any positive number starting from 0 -[1-*] denotes any positive number starting from 1 +======= =========================================== +`[0-*]` denotes any positive number starting from 0 +`[1-*]` denotes any positive number starting from 1 RO read only value WO write only value RW read/write value +======= =========================================== Read/write values may be read-only for some chips, depending on the hardware implementation. @@ -80,57 +82,82 @@ All entries (except name) are optional, and should only be created in a given driver if the chip has the feature. -********************* -* Global attributes * -********************* +***************** +Global attributes +***************** -name The chip name. +`name` + The chip name. This should be a short, lowercase string, not containing whitespace, dashes, or the wildcard character '*'. This attribute represents the chip name. It is the only mandatory attribute. I2C devices get this attribute created automatically. + RO -update_interval The interval at which the chip will update readings. +`update_interval` + The interval at which the chip will update readings. Unit: millisecond + RW + Some devices have a variable update rate or interval. This attribute can be used to change it to the desired value. -************ -* Voltages * -************ +******** +Voltages +******** + +`in[0-*]_min` + Voltage min value. -in[0-*]_min Voltage min value. Unit: millivolt + RW - -in[0-*]_lcrit Voltage critical min value. + +`in[0-*]_lcrit` + Voltage critical min value. + Unit: millivolt + RW + If voltage drops to or below this limit, the system may take drastic action such as power down or reset. At the very least, it should report a fault. -in[0-*]_max Voltage max value. +`in[0-*]_max` + Voltage max value. + Unit: millivolt + RW - -in[0-*]_crit Voltage critical max value. + +`in[0-*]_crit` + Voltage critical max value. + Unit: millivolt + RW + If voltage reaches or exceeds this limit, the system may take drastic action such as power down or reset. At the very least, it should report a fault. -in[0-*]_input Voltage input value. +`in[0-*]_input` + Voltage input value. + Unit: millivolt + RO + Voltage measured on the chip pin. + Actual voltage depends on the scaling resistors on the motherboard, as recommended in the chip datasheet. + This varies by chip and by motherboard. Because of this variation, values are generally NOT scaled by the chip driver, and must be done by the application. @@ -140,166 +167,232 @@ in[0-*]_input Voltage input value. thumb: drivers should report the voltage values at the "pins" of the chip. -in[0-*]_average +`in[0-*]_average` Average voltage + Unit: millivolt + RO -in[0-*]_lowest +`in[0-*]_lowest` Historical minimum voltage + Unit: millivolt + RO -in[0-*]_highest +`in[0-*]_highest` Historical maximum voltage + Unit: millivolt + RO -in[0-*]_reset_history +`in[0-*]_reset_history` Reset inX_lowest and inX_highest + WO -in_reset_history +`in_reset_history` Reset inX_lowest and inX_highest for all sensors + WO -in[0-*]_label Suggested voltage channel label. +`in[0-*]_label` + Suggested voltage channel label. + Text string + Should only be created if the driver has hints about what this voltage channel is being used for, and user-space doesn't. In all other cases, the label is provided by user-space. + RO -in[0-*]_enable +`in[0-*]_enable` Enable or disable the sensors. + When disabled the sensor read will return -ENODATA. - 1: Enable - 0: Disable + + - 1: Enable + - 0: Disable + RW -cpu[0-*]_vid CPU core reference voltage. +`cpu[0-*]_vid` + CPU core reference voltage. + Unit: millivolt + RO + Not always correct. -vrm Voltage Regulator Module version number. +`vrm` + Voltage Regulator Module version number. + RW (but changing it should no more be necessary) + Originally the VRM standard version multiplied by 10, but now an arbitrary number, as not all standards have a version number. + Affects the way the driver calculates the CPU core reference voltage from the vid pins. Also see the Alarms section for status flags associated with voltages. -******** -* Fans * -******** +**** +Fans +**** + +`fan[1-*]_min` + Fan minimum value -fan[1-*]_min Fan minimum value Unit: revolution/min (RPM) + RW -fan[1-*]_max Fan maximum value +`fan[1-*]_max` + Fan maximum value + Unit: revolution/min (RPM) + Only rarely supported by the hardware. RW -fan[1-*]_input Fan input value. +`fan[1-*]_input` + Fan input value. + Unit: revolution/min (RPM) + RO -fan[1-*]_div Fan divisor. +`fan[1-*]_div` + Fan divisor. + Integer value in powers of two (1, 2, 4, 8, 16, 32, 64, 128). + RW + Some chips only support values 1, 2, 4 and 8. Note that this is actually an internal clock divisor, which affects the measurable speed range, not the read value. -fan[1-*]_pulses Number of tachometer pulses per fan revolution. +`fan[1-*]_pulses` + Number of tachometer pulses per fan revolution. + Integer value, typically between 1 and 4. + RW + This value is a characteristic of the fan connected to the device's input, so it has to be set in accordance with the fan model. + Should only be created if the chip has a register to configure the number of pulses. In the absence of such a register (and thus attribute) the value assumed by all devices is 2 pulses per fan revolution. -fan[1-*]_target +`fan[1-*]_target` Desired fan speed + Unit: revolution/min (RPM) + RW + Only makes sense if the chip supports closed-loop fan speed control based on the measured fan speed. -fan[1-*]_label Suggested fan channel label. +`fan[1-*]_label` + Suggested fan channel label. + Text string + Should only be created if the driver has hints about what this fan channel is being used for, and user-space doesn't. In all other cases, the label is provided by user-space. + RO -fan[1-*]_enable +`fan[1-*]_enable` Enable or disable the sensors. + When disabled the sensor read will return -ENODATA. - 1: Enable - 0: Disable + + - 1: Enable + - 0: Disable + RW Also see the Alarms section for status flags associated with fans. -******* -* PWM * -******* +*** +PWM +*** + +`pwm[1-*]` + Pulse width modulation fan control. -pwm[1-*] Pulse width modulation fan control. Integer value in the range 0 to 255 + RW + 255 is max or 100%. -pwm[1-*]_enable +`pwm[1-*]_enable` Fan speed control method: - 0: no fan speed control (i.e. fan at full speed) - 1: manual fan speed control enabled (using pwm[1-*]) - 2+: automatic fan speed control enabled + + - 0: no fan speed control (i.e. fan at full speed) + - 1: manual fan speed control enabled (using `pwm[1-*]`) + - 2+: automatic fan speed control enabled + Check individual chip documentation files for automatic mode details. + RW -pwm[1-*]_mode 0: DC mode (direct current) - 1: PWM mode (pulse-width modulation) +`pwm[1-*]_mode` + - 0: DC mode (direct current) + - 1: PWM mode (pulse-width modulation) + RW -pwm[1-*]_freq Base PWM frequency in Hz. +`pwm[1-*]_freq` + Base PWM frequency in Hz. + Only possibly available when pwmN_mode is PWM, but not always present even then. + RW -pwm[1-*]_auto_channels_temp +`pwm[1-*]_auto_channels_temp` Select which temperature channels affect this PWM output in - auto mode. Bitfield, 1 is temp1, 2 is temp2, 4 is temp3 etc... + auto mode. + + Bitfield, 1 is temp1, 2 is temp2, 4 is temp3 etc... Which values are possible depend on the chip used. + RW -pwm[1-*]_auto_point[1-*]_pwm -pwm[1-*]_auto_point[1-*]_temp -pwm[1-*]_auto_point[1-*]_temp_hyst - Define the PWM vs temperature curve. Number of trip points is - chip-dependent. Use this for chips which associate trip points - to PWM output channels. +`pwm[1-*]_auto_point[1-*]_pwm` / `pwm[1-*]_auto_point[1-*]_temp` / `pwm[1-*]_auto_point[1-*]_temp_hyst` + Define the PWM vs temperature curve. + + Number of trip points is chip-dependent. Use this for chips + which associate trip points to PWM output channels. + RW -temp[1-*]_auto_point[1-*]_pwm -temp[1-*]_auto_point[1-*]_temp -temp[1-*]_auto_point[1-*]_temp_hyst - Define the PWM vs temperature curve. Number of trip points is - chip-dependent. Use this for chips which associate trip points - to temperature channels. +`temp[1-*]_auto_point[1-*]_pwm` / `temp[1-*]_auto_point[1-*]_temp` / `temp[1-*]_auto_point[1-*]_temp_hyst` + Define the PWM vs temperature curve. + + Number of trip points is chip-dependent. Use this for chips + which associate trip points to temperature channels. + RW There is a third case where trip points are associated to both PWM output @@ -312,122 +405,173 @@ The actual result is up to the chip, but in general the highest candidate value (fastest fan speed) wins. -**************** -* Temperatures * -**************** +************ +Temperatures +************ + +`temp[1-*]_type` + Sensor type selection. -temp[1-*]_type Sensor type selection. Integers 1 to 6 + RW - 1: CPU embedded diode - 2: 3904 transistor - 3: thermal diode - 4: thermistor - 5: AMD AMDSI - 6: Intel PECI + + - 1: CPU embedded diode + - 2: 3904 transistor + - 3: thermal diode + - 4: thermistor + - 5: AMD AMDSI + - 6: Intel PECI + Not all types are supported by all chips -temp[1-*]_max Temperature max value. +`temp[1-*]_max` + Temperature max value. + Unit: millidegree Celsius (or millivolt, see below) + RW -temp[1-*]_min Temperature min value. +`temp[1-*]_min` + Temperature min value. + Unit: millidegree Celsius + RW -temp[1-*]_max_hyst +`temp[1-*]_max_hyst` Temperature hysteresis value for max limit. + Unit: millidegree Celsius + Must be reported as an absolute temperature, NOT a delta from the max value. + RW -temp[1-*]_min_hyst +`temp[1-*]_min_hyst` Temperature hysteresis value for min limit. Unit: millidegree Celsius + Must be reported as an absolute temperature, NOT a delta from the min value. + RW -temp[1-*]_input Temperature input value. +`temp[1-*]_input` + Temperature input value. + Unit: millidegree Celsius + RO -temp[1-*]_crit Temperature critical max value, typically greater than +`temp[1-*]_crit` + Temperature critical max value, typically greater than corresponding temp_max values. + Unit: millidegree Celsius + RW -temp[1-*]_crit_hyst +`temp[1-*]_crit_hyst` Temperature hysteresis value for critical limit. + Unit: millidegree Celsius + Must be reported as an absolute temperature, NOT a delta from the critical value. + RW -temp[1-*]_emergency +`temp[1-*]_emergency` Temperature emergency max value, for chips supporting more than two upper temperature limits. Must be equal or greater than corresponding temp_crit values. + Unit: millidegree Celsius + RW -temp[1-*]_emergency_hyst +`temp[1-*]_emergency_hyst` Temperature hysteresis value for emergency limit. + Unit: millidegree Celsius + Must be reported as an absolute temperature, NOT a delta from the emergency value. + RW -temp[1-*]_lcrit Temperature critical min value, typically lower than +`temp[1-*]_lcrit` + Temperature critical min value, typically lower than corresponding temp_min values. + Unit: millidegree Celsius + RW -temp[1-*]_lcrit_hyst +`temp[1-*]_lcrit_hyst` Temperature hysteresis value for critical min limit. + Unit: millidegree Celsius + Must be reported as an absolute temperature, NOT a delta from the critical min value. + RW -temp[1-*]_offset +`temp[1-*]_offset` Temperature offset which is added to the temperature reading by the chip. + Unit: millidegree Celsius + Read/Write value. -temp[1-*]_label Suggested temperature channel label. +`temp[1-*]_label` + Suggested temperature channel label. + Text string + Should only be created if the driver has hints about what this temperature channel is being used for, and user-space doesn't. In all other cases, the label is provided by user-space. + RO -temp[1-*]_lowest +`temp[1-*]_lowest` Historical minimum temperature + Unit: millidegree Celsius + RO -temp[1-*]_highest +`temp[1-*]_highest` Historical maximum temperature + Unit: millidegree Celsius + RO -temp[1-*]_reset_history +`temp[1-*]_reset_history` Reset temp_lowest and temp_highest + WO -temp_reset_history +`temp_reset_history` Reset temp_lowest and temp_highest for all sensors + WO -temp[1-*]_enable +`temp[1-*]_enable` Enable or disable the sensors. + When disabled the sensor read will return -ENODATA. - 1: Enable - 0: Disable + + - 1: Enable + - 0: Disable + RW Some chips measure temperature using external thermistors and an ADC, and @@ -442,201 +586,300 @@ channels by the driver. Also see the Alarms section for status flags associated with temperatures. -************ -* Currents * -************ +******** +Currents +******** + +`curr[1-*]_max` + Current max value -curr[1-*]_max Current max value Unit: milliampere + RW -curr[1-*]_min Current min value. +`curr[1-*]_min` + Current min value. + Unit: milliampere + RW -curr[1-*]_lcrit Current critical low value +`curr[1-*]_lcrit` + Current critical low value + Unit: milliampere + RW -curr[1-*]_crit Current critical high value. +`curr[1-*]_crit` + Current critical high value. + Unit: milliampere + RW -curr[1-*]_input Current input value +`curr[1-*]_input` + Current input value + Unit: milliampere + RO -curr[1-*]_average +`curr[1-*]_average` Average current use + Unit: milliampere + RO -curr[1-*]_lowest +`curr[1-*]_lowest` Historical minimum current + Unit: milliampere + RO -curr[1-*]_highest +`curr[1-*]_highest` Historical maximum current Unit: milliampere RO -curr[1-*]_reset_history +`curr[1-*]_reset_history` Reset currX_lowest and currX_highest + WO -curr_reset_history +`curr_reset_history` Reset currX_lowest and currX_highest for all sensors + WO -curr[1-*]_enable +`curr[1-*]_enable` Enable or disable the sensors. + When disabled the sensor read will return -ENODATA. - 1: Enable - 0: Disable + + - 1: Enable + - 0: Disable + RW Also see the Alarms section for status flags associated with currents. -********* -* Power * -********* +***** +Power +***** + +`power[1-*]_average` + Average power use -power[1-*]_average Average power use Unit: microWatt + RO -power[1-*]_average_interval Power use averaging interval. A poll +`power[1-*]_average_interval` + Power use averaging interval. A poll notification is sent to this file if the hardware changes the averaging interval. + Unit: milliseconds + RW -power[1-*]_average_interval_max Maximum power use averaging interval +`power[1-*]_average_interval_max` + Maximum power use averaging interval + Unit: milliseconds + RO -power[1-*]_average_interval_min Minimum power use averaging interval +`power[1-*]_average_interval_min` + Minimum power use averaging interval + Unit: milliseconds + RO -power[1-*]_average_highest Historical average maximum power use +`power[1-*]_average_highest` + Historical average maximum power use + Unit: microWatt + RO -power[1-*]_average_lowest Historical average minimum power use +`power[1-*]_average_lowest` + Historical average minimum power use + Unit: microWatt + RO -power[1-*]_average_max A poll notification is sent to - power[1-*]_average when power use +`power[1-*]_average_max` + A poll notification is sent to + `power[1-*]_average` when power use rises above this value. + Unit: microWatt + RW -power[1-*]_average_min A poll notification is sent to - power[1-*]_average when power use +`power[1-*]_average_min` + A poll notification is sent to + `power[1-*]_average` when power use sinks below this value. + Unit: microWatt + RW -power[1-*]_input Instantaneous power use +`power[1-*]_input` + Instantaneous power use + Unit: microWatt + RO -power[1-*]_input_highest Historical maximum power use +`power[1-*]_input_highest` + Historical maximum power use + Unit: microWatt + RO -power[1-*]_input_lowest Historical minimum power use +`power[1-*]_input_lowest` + Historical minimum power use + Unit: microWatt + RO -power[1-*]_reset_history Reset input_highest, input_lowest, +`power[1-*]_reset_history` + Reset input_highest, input_lowest, average_highest and average_lowest. + WO -power[1-*]_accuracy Accuracy of the power meter. +`power[1-*]_accuracy` + Accuracy of the power meter. + Unit: Percent + RO -power[1-*]_cap If power use rises above this limit, the +`power[1-*]_cap` + If power use rises above this limit, the system should take action to reduce power use. A poll notification is sent to this file if the - cap is changed by the hardware. The *_cap + cap is changed by the hardware. The `*_cap` files only appear if the cap is known to be enforced by hardware. + Unit: microWatt + RW -power[1-*]_cap_hyst Margin of hysteresis built around capping and +`power[1-*]_cap_hyst` + Margin of hysteresis built around capping and notification. + Unit: microWatt + RW -power[1-*]_cap_max Maximum cap that can be set. +`power[1-*]_cap_max` + Maximum cap that can be set. + Unit: microWatt + RO -power[1-*]_cap_min Minimum cap that can be set. +`power[1-*]_cap_min` + Minimum cap that can be set. + Unit: microWatt + RO -power[1-*]_max Maximum power. +`power[1-*]_max` + Maximum power. + Unit: microWatt + RW -power[1-*]_crit Critical maximum power. +`power[1-*]_crit` + Critical maximum power. + If power rises to or above this limit, the system is expected take drastic action to reduce power consumption, such as a system shutdown or a forced powerdown of some devices. + Unit: microWatt + RW -power[1-*]_enable Enable or disable the sensors. +`power[1-*]_enable` + Enable or disable the sensors. + When disabled the sensor read will return -ENODATA. - 1: Enable - 0: Disable + + - 1: Enable + - 0: Disable + RW Also see the Alarms section for status flags associated with power readings. -********** -* Energy * -********** +****** +Energy +****** + +`energy[1-*]_input` + Cumulative energy use -energy[1-*]_input Cumulative energy use Unit: microJoule + RO -energy[1-*]_enable Enable or disable the sensors. +`energy[1-*]_enable` + Enable or disable the sensors. + When disabled the sensor read will return -ENODATA. - 1: Enable - 0: Disable + + - 1: Enable + - 0: Disable + RW -************ -* Humidity * -************ +******** +Humidity +******** + +`humidity[1-*]_input` + Humidity -humidity[1-*]_input Humidity Unit: milli-percent (per cent mille, pcm) + RO -humidity[1-*]_enable Enable or disable the sensors +`humidity[1-*]_enable` + Enable or disable the sensors + When disabled the sensor read will return -ENODATA. - 1: Enable - 0: Disable + + - 1: Enable + - 0: Disable + RW -********** -* Alarms * -********** +****** +Alarms +****** Each channel or limit may have an associated alarm file, containing a boolean value. 1 means than an alarm condition exists, 0 means no alarm. @@ -645,67 +888,67 @@ Usually a given chip will either use channel-related alarms, or limit-related alarms, not both. The driver should just reflect the hardware implementation. -in[0-*]_alarm -curr[1-*]_alarm -power[1-*]_alarm -fan[1-*]_alarm -temp[1-*]_alarm - Channel alarm - 0: no alarm - 1: alarm - RO - -OR - -in[0-*]_min_alarm -in[0-*]_max_alarm -in[0-*]_lcrit_alarm -in[0-*]_crit_alarm -curr[1-*]_min_alarm -curr[1-*]_max_alarm -curr[1-*]_lcrit_alarm -curr[1-*]_crit_alarm -power[1-*]_cap_alarm -power[1-*]_max_alarm -power[1-*]_crit_alarm -fan[1-*]_min_alarm -fan[1-*]_max_alarm -temp[1-*]_min_alarm -temp[1-*]_max_alarm -temp[1-*]_lcrit_alarm -temp[1-*]_crit_alarm -temp[1-*]_emergency_alarm - Limit alarm - 0: no alarm - 1: alarm - RO ++-------------------------------+-----------------------+ +| **`in[0-*]_alarm`, | Channel alarm | +| `curr[1-*]_alarm`, | | +| `power[1-*]_alarm`, | - 0: no alarm | +| `fan[1-*]_alarm`, | - 1: alarm | +| `temp[1-*]_alarm`** | | +| | RO | ++-------------------------------+-----------------------+ + +**OR** + ++-------------------------------+-----------------------+ +| **`in[0-*]_min_alarm`, | Limit alarm | +| `in[0-*]_max_alarm`, | | +| `in[0-*]_lcrit_alarm`, | - 0: no alarm | +| `in[0-*]_crit_alarm`, | - 1: alarm | +| `curr[1-*]_min_alarm`, | | +| `curr[1-*]_max_alarm`, | RO | +| `curr[1-*]_lcrit_alarm`, | | +| `curr[1-*]_crit_alarm`, | | +| `power[1-*]_cap_alarm`, | | +| `power[1-*]_max_alarm`, | | +| `power[1-*]_crit_alarm`, | | +| `fan[1-*]_min_alarm`, | | +| `fan[1-*]_max_alarm`, | | +| `temp[1-*]_min_alarm`, | | +| `temp[1-*]_max_alarm`, | | +| `temp[1-*]_lcrit_alarm`, | | +| `temp[1-*]_crit_alarm`, | | +| `temp[1-*]_emergency_alarm`** | | ++-------------------------------+-----------------------+ Each input channel may have an associated fault file. This can be used to notify open diodes, unconnected fans etc. where the hardware supports it. When this boolean has value 1, the measurement for that channel should not be trusted. -fan[1-*]_fault -temp[1-*]_fault +`fan[1-*]_fault` / `temp[1-*]_fault` Input fault condition - 0: no fault occurred - 1: fault condition + + - 0: no fault occurred + - 1: fault condition + RO Some chips also offer the possibility to get beeped when an alarm occurs: -beep_enable Master beep enable - 0: no beeps - 1: beeps +`beep_enable` + Master beep enable + + - 0: no beeps + - 1: beeps + RW -in[0-*]_beep -curr[1-*]_beep -fan[1-*]_beep -temp[1-*]_beep +`in[0-*]_beep`, `curr[1-*]_beep`, `fan[1-*]_beep`, `temp[1-*]_beep`, Channel beep - 0: disable - 1: enable + + - 0: disable + - 1: enable + RW In theory, a chip could provide per-limit beep masking, but no such chip @@ -715,74 +958,90 @@ Old drivers provided a different, non-standard interface to alarms and beeps. These interface files are deprecated, but will be kept around for compatibility reasons: -alarms Alarm bitmask. +`alarms` + Alarm bitmask. + RO + Integer representation of one to four bytes. + A '1' bit means an alarm. + Chips should be programmed for 'comparator' mode so that the alarm will 'come back' after you read the register if it is still valid. + Generally a direct representation of a chip's internal alarm registers; there is no standard for the position of individual bits. For this reason, the use of this interface file for new drivers is discouraged. Use - individual *_alarm and *_fault files instead. + `individual *_alarm` and `*_fault` files instead. Bits are defined in kernel/include/sensors.h. -beep_mask Bitmask for beep. +`beep_mask` + Bitmask for beep. Same format as 'alarms' with the same bit locations, use discouraged for the same reason. Use individual - *_beep files instead. + `*_beep` files instead. RW -*********************** -* Intrusion detection * -*********************** +******************* +Intrusion detection +******************* -intrusion[0-*]_alarm +`intrusion[0-*]_alarm` Chassis intrusion detection - 0: OK - 1: intrusion detected + + - 0: OK + - 1: intrusion detected + RW + Contrary to regular alarm flags which clear themselves automatically when read, this one sticks until cleared by the user. This is done by writing 0 to the file. Writing other values is unsupported. -intrusion[0-*]_beep +`intrusion[0-*]_beep` Chassis intrusion beep + 0: disable 1: enable + RW -******************************** -* Average sample configuration * -******************************** +**************************** +Average sample configuration +**************************** Devices allowing for reading {in,power,curr,temp}_average values may export attributes for controlling number of samples used to compute average. -samples Sets number of average samples for all types of measurements. - RW - -in_samples -power_samples -curr_samples -temp_samples Sets number of average samples for specific type of measurements. - Note that on some devices it won't be possible to set all of them - to different values so changing one might also change some others. - RW - ++--------------+---------------------------------------------------------------+ +| samples | Sets number of average samples for all types of measurements. | +| | | +| | RW | ++--------------+---------------------------------------------------------------+ +| in_samples | Sets number of average samples for specific type of | +| power_samples| measurements. | +| curr_samples | | +| temp_samples | Note that on some devices it won't be possible to set all of | +| | them to different values so changing one might also change | +| | some others. | +| | | +| | RW | ++--------------+---------------------------------------------------------------+ sysfs attribute writes interpretation ------------------------------------- hwmon sysfs attributes always contain numbers, so the first thing to do is to convert the input to a number, there are 2 ways todo this depending whether -the number can be negative or not: -unsigned long u = simple_strtoul(buf, NULL, 10); -long s = simple_strtol(buf, NULL, 10); +the number can be negative or not:: + + unsigned long u = simple_strtoul(buf, NULL, 10); + long s = simple_strtol(buf, NULL, 10); With buf being the buffer with the user input being passed by the kernel. Notice that we do not use the second argument of strto[u]l, and thus cannot @@ -807,13 +1066,13 @@ limits using clamp_val(value, min_limit, max_limit). If it is not continuous like for example a tempX_type, then when an invalid value is written, -EINVAL should be returned. -Example1, temp1_max, register is a signed 8 bit value (-128 - 127 degrees): +Example1, temp1_max, register is a signed 8 bit value (-128 - 127 degrees):: long v = simple_strtol(buf, NULL, 10) / 1000; v = clamp_val(v, -128, 127); /* write v to register */ -Example2, fan divider setting, valid values 2, 4 and 8: +Example2, fan divider setting, valid values 2, 4 and 8:: unsigned long v = simple_strtoul(buf, NULL, 10); diff --git a/Documentation/hwmon/tc654 b/Documentation/hwmon/tc654 index 47636a8077b4..ce546ee6dfed 100644 --- a/Documentation/hwmon/tc654 +++ b/Documentation/hwmon/tc654 @@ -2,13 +2,16 @@ Kernel driver tc654 =================== Supported chips: + * Microchip TC654 and TC655 + Prefix: 'tc654' - Datasheet: http://ww1.microchip.com/downloads/en/DeviceDoc/20001734C.pdf + Datasheet: http://ww1.m + icrochip.com/downloads/en/DeviceDoc/20001734C.pdf Authors: - Chris Packham - Masahiko Iwamoto + - Chris Packham + - Masahiko Iwamoto Description ----------- diff --git a/Documentation/hwmon/tc74 b/Documentation/hwmon/tc74 index 43027aad5f8e..f1764211c129 100644 --- a/Documentation/hwmon/tc74 +++ b/Documentation/hwmon/tc74 @@ -2,8 +2,11 @@ Kernel driver tc74 ==================== Supported chips: + * Microchip TC74 + Prefix: 'tc74' + Datasheet: Publicly available at Microchip website. Description diff --git a/Documentation/hwmon/thmc50 b/Documentation/hwmon/thmc50 index 8a7772ade8d0..6dba1b59b20c 100644 --- a/Documentation/hwmon/thmc50 +++ b/Documentation/hwmon/thmc50 @@ -2,30 +2,41 @@ Kernel driver thmc50 ===================== Supported chips: + * Analog Devices ADM1022 + Prefix: 'adm1022' + Addresses scanned: I2C 0x2c - 0x2e + Datasheet: http://www.analog.com/en/prod/0,2877,ADM1022,00.html + * Texas Instruments THMC50 + Prefix: 'thmc50' + Addresses scanned: I2C 0x2c - 0x2e - Datasheet: http://www.ti.com/ + + Datasheet: http://www.ti.com/ + Author: Krzysztof Helt This driver was derived from the 2.4 kernel thmc50.c source file. Credits: + thmc50.c (2.4 kernel): - Frodo Looijaard - Philip Edelbrock + + - Frodo Looijaard + - Philip Edelbrock Module Parameters ----------------- * adm1022_temp3: short array - List of adapter,address pairs to force chips into ADM1022 mode with - second remote temperature. This does not work for original THMC50 chips. + List of adapter,address pairs to force chips into ADM1022 mode with + second remote temperature. This does not work for original THMC50 chips. Description ----------- @@ -59,12 +70,17 @@ Driver Features The driver provides up to three temperatures: -temp1 -- internal -temp2 -- remote -temp3 -- 2nd remote only for ADM1022 - -pwm1 -- fan speed (0 = stop, 255 = full) -pwm1_mode -- always 0 (DC mode) +temp1 + - internal +temp2 + - remote +temp3 + - 2nd remote only for ADM1022 + +pwm1 + - fan speed (0 = stop, 255 = full) +pwm1_mode + - always 0 (DC mode) The value of 0 for pwm1 also forces FAN_OFF signal from the chip, so it stops fans even if the value 0 into the ANALOG_OUT register does not. diff --git a/Documentation/hwmon/tmp102 b/Documentation/hwmon/tmp102 index 8454a7763122..5e34821df4ab 100644 --- a/Documentation/hwmon/tmp102 +++ b/Documentation/hwmon/tmp102 @@ -2,12 +2,17 @@ Kernel driver tmp102 ==================== Supported chips: + * Texas Instruments TMP102 + Prefix: 'tmp102' + Addresses scanned: none + Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp102.html Author: + Steven King Description diff --git a/Documentation/hwmon/tmp103 b/Documentation/hwmon/tmp103 index ec00a15645ba..7682a795e38c 100644 --- a/Documentation/hwmon/tmp103 +++ b/Documentation/hwmon/tmp103 @@ -2,12 +2,17 @@ Kernel driver tmp103 ==================== Supported chips: + * Texas Instruments TMP103 + Prefix: 'tmp103' + Addresses scanned: none + Product info and datasheet: http://www.ti.com/product/tmp103 Author: + Heiko Schocher Description diff --git a/Documentation/hwmon/tmp108 b/Documentation/hwmon/tmp108 index 25802df23010..7e08b7ef1e2f 100644 --- a/Documentation/hwmon/tmp108 +++ b/Documentation/hwmon/tmp108 @@ -2,12 +2,17 @@ Kernel driver tmp108 ==================== Supported chips: + * Texas Instruments TMP108 + Prefix: 'tmp108' + Addresses scanned: none + Datasheet: http://www.ti.com/product/tmp108 Author: + John Muir Description diff --git a/Documentation/hwmon/tmp421 b/Documentation/hwmon/tmp421 index 9e6fe5549ca1..1ba926a3605c 100644 --- a/Documentation/hwmon/tmp421 +++ b/Documentation/hwmon/tmp421 @@ -2,28 +2,49 @@ Kernel driver tmp421 ==================== Supported chips: + * Texas Instruments TMP421 + Prefix: 'tmp421' + Addresses scanned: I2C 0x2a, 0x4c, 0x4d, 0x4e and 0x4f + Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp421.html + * Texas Instruments TMP422 + Prefix: 'tmp422' + Addresses scanned: I2C 0x4c, 0x4d, 0x4e and 0x4f + Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp421.html + * Texas Instruments TMP423 + Prefix: 'tmp423' + Addresses scanned: I2C 0x4c and 0x4d + Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp421.html + * Texas Instruments TMP441 + Prefix: 'tmp441' + Addresses scanned: I2C 0x2a, 0x4c, 0x4d, 0x4e and 0x4f + Datasheet: http://www.ti.com/product/tmp441 + * Texas Instruments TMP442 + Prefix: 'tmp442' + Addresses scanned: I2C 0x4c and 0x4d + Datasheet: http://www.ti.com/product/tmp442 Authors: + Andre Prendel Description @@ -40,5 +61,6 @@ for both the local and remote channels is 0.0625 degree C. The chips support only temperature measurement. The driver exports the temperature values via the following sysfs files: -temp[1-4]_input -temp[2-4]_fault +**temp[1-4]_input** + +**temp[2-4]_fault** diff --git a/Documentation/hwmon/twl4030-madc-hwmon b/Documentation/hwmon/twl4030-madc-hwmon index c3a3a5be10ad..22c885383b11 100644 --- a/Documentation/hwmon/twl4030-madc-hwmon +++ b/Documentation/hwmon/twl4030-madc-hwmon @@ -1,8 +1,10 @@ Kernel driver twl4030-madc -========================= +========================== Supported chips: + * Texas Instruments TWL4030 + Prefix: 'twl4030-madc' @@ -19,8 +21,9 @@ channels which can be used in different modes. See this table for the meaning of the different channels +======= ========================================================== Channel Signal ------------------------------------------- +======= ========================================================== 0 Battery type(BTYPE) 1 BCI: Battery temperature (BTEMP) 2 GP analog input @@ -37,6 +40,7 @@ Channel Signal 13 Reserved 14 Reserved 15 VRUSB Supply/Speaker left/Speaker right polarization level +======= ========================================================== The Sysfs nodes will represent the voltage in the units of mV, diff --git a/Documentation/hwmon/userspace-tools b/Documentation/hwmon/userspace-tools index 9865aeedc58f..bf3797c8e734 100644 --- a/Documentation/hwmon/userspace-tools +++ b/Documentation/hwmon/userspace-tools @@ -1,3 +1,6 @@ +Userspace tools +=============== + Introduction ------------ diff --git a/Documentation/hwmon/via686a b/Documentation/hwmon/via686a index e5f90ab5c48d..a343c35df740 100644 --- a/Documentation/hwmon/via686a +++ b/Documentation/hwmon/via686a @@ -2,29 +2,35 @@ Kernel driver via686a ===================== Supported chips: + * Via VT82C686A, VT82C686B Southbridge Integrated Hardware Monitor + Prefix: 'via686a' + Addresses scanned: ISA in PCI-space encoded address + Datasheet: On request through web form (http://www.via.com.tw/en/resources/download-center/) Authors: - Kyösti Mälkki , - Mark D. Studebaker - Bob Dougherty - (Some conversion-factor data were contributed by - Jonathan Teh Soon Yew - and Alex van Kaam .) + - Kyösti Mälkki , + - Mark D. Studebaker + - Bob Dougherty + - (Some conversion-factor data were contributed by + - Jonathan Teh Soon Yew + - and Alex van Kaam .) Module Parameters ----------------- +======================= ======================================================= force_addr=0xaddr Set the I/O base address. Useful for boards that - don't set the address in the BIOS. Look for a BIOS - upgrade before resorting to this. Does not do a - PCI force; the via686a must still be present in lspci. - Don't use this unless the driver complains that the - base address is not set. - Example: 'modprobe via686a force_addr=0x6000' + don't set the address in the BIOS. Look for a BIOS + upgrade before resorting to this. Does not do a + PCI force; the via686a must still be present in lspci. + Don't use this unless the driver complains that the + base address is not set. + Example: 'modprobe via686a force_addr=0x6000' +======================= ======================================================= Description ----------- diff --git a/Documentation/hwmon/w83627ehf b/Documentation/hwmon/w83627ehf index 735c42a85ead..74d19ef11e1f 100644 --- a/Documentation/hwmon/w83627ehf +++ b/Documentation/hwmon/w83627ehf @@ -2,45 +2,79 @@ Kernel driver w83627ehf ======================= Supported chips: + * Winbond W83627EHF/EHG (ISA access ONLY) + Prefix: 'w83627ehf' + Addresses scanned: ISA address retrieved from Super I/O registers + Datasheet: not available + * Winbond W83627DHG + Prefix: 'w83627dhg' + Addresses scanned: ISA address retrieved from Super I/O registers + Datasheet: not available + * Winbond W83627DHG-P + Prefix: 'w83627dhg' + Addresses scanned: ISA address retrieved from Super I/O registers + Datasheet: not available + * Winbond W83627UHG + Prefix: 'w83627uhg' + Addresses scanned: ISA address retrieved from Super I/O registers + Datasheet: available from www.nuvoton.com + * Winbond W83667HG + Prefix: 'w83667hg' + Addresses scanned: ISA address retrieved from Super I/O registers + Datasheet: not available + * Winbond W83667HG-B + Prefix: 'w83667hg' + Addresses scanned: ISA address retrieved from Super I/O registers + Datasheet: Available from Nuvoton upon request + * Nuvoton NCT6775F/W83667HG-I + Prefix: 'nct6775' + Addresses scanned: ISA address retrieved from Super I/O registers + Datasheet: Available from Nuvoton upon request + * Nuvoton NCT6776F + Prefix: 'nct6776' + Addresses scanned: ISA address retrieved from Super I/O registers + Datasheet: Available from Nuvoton upon request + Authors: - Jean Delvare - Yuan Mu (Winbond) - Rudolf Marek - David Hubbard - Gong Jun + + - Jean Delvare + - Yuan Mu (Winbond) + - Rudolf Marek + - David Hubbard + - Gong Jun Description ----------- @@ -85,25 +119,30 @@ predefined temperature range. If the temperature goes out of range, fan is driven slower/faster to reach the predefined range again. The mode works for fan1-fan4. Mapping of temperatures to pwm outputs is as -follows: +follows:: -temp1 -> pwm1 -temp2 -> pwm2 -temp3 -> pwm3 (not on 627UHG) -prog -> pwm4 (not on 667HG and 667HG-B; the programmable setting is not - supported by the driver) + temp1 -> pwm1 + temp2 -> pwm2 + temp3 -> pwm3 (not on 627UHG) + prog -> pwm4 (not on 667HG and 667HG-B; the programmable setting is not + supported by the driver) /sys files ---------- -name - this is a standard hwmon device entry, it contains the name of - the device (see the prefix in the list of supported devices at - the top of this file) +name + this is a standard hwmon device entry, it contains the name of + the device (see the prefix in the list of supported devices at + the top of this file) + +pwm[1-4] + this file stores PWM duty cycle or DC value (fan speed) in range: -pwm[1-4] - this file stores PWM duty cycle or DC value (fan speed) in range: 0 (stop) to 255 (full) -pwm[1-4]_enable - this file controls mode of fan/temperature control: +pwm[1-4]_enable + this file controls mode of fan/temperature control: + * 1 Manual mode, write to pwm file any value 0-255 (full speed) * 2 "Thermal Cruise" mode * 3 "Fan Speed Cruise" mode @@ -121,33 +160,43 @@ pwm[1-4]_enable - this file controls mode of fan/temperature control: returned when reading pwm attributes is unrelated to SmartFan IV operation. -pwm[1-4]_mode - controls if output is PWM or DC level - * 0 DC output (0 - 12v) - * 1 PWM output +pwm[1-4]_mode + controls if output is PWM or DC level + + * 0 DC output (0 - 12v) + * 1 PWM output Thermal Cruise mode ------------------- If the temperature is in the range defined by: -pwm[1-4]_target - set target temperature, unit millidegree Celsius - (range 0 - 127000) -pwm[1-4]_tolerance - tolerance, unit millidegree Celsius (range 0 - 15000) +pwm[1-4]_target + set target temperature, unit millidegree Celsius + (range 0 - 127000) +pwm[1-4]_tolerance + tolerance, unit millidegree Celsius (range 0 - 15000) there are no changes to fan speed. Once the temperature leaves the interval, fan speed increases (temp is higher) or decreases if lower than desired. There are defined steps and times, but not exported by the driver yet. -pwm[1-4]_min_output - minimum fan speed (range 1 - 255), when the temperature - is below defined range. -pwm[1-4]_stop_time - how many milliseconds [ms] must elapse to switch - corresponding fan off. (when the temperature was below - defined range). -pwm[1-4]_start_output-minimum fan speed (range 1 - 255) when spinning up -pwm[1-4]_step_output- rate of fan speed change (1 - 255) -pwm[1-4]_stop_output- minimum fan speed (range 1 - 255) when spinning down -pwm[1-4]_max_output - maximum fan speed (range 1 - 255), when the temperature - is above defined range. +pwm[1-4]_min_output + minimum fan speed (range 1 - 255), when the temperature + is below defined range. +pwm[1-4]_stop_time + how many milliseconds [ms] must elapse to switch + corresponding fan off. (when the temperature was below + defined range). +pwm[1-4]_start_output + minimum fan speed (range 1 - 255) when spinning up +pwm[1-4]_step_output + rate of fan speed change (1 - 255) +pwm[1-4]_stop_output + minimum fan speed (range 1 - 255) when spinning down +pwm[1-4]_max_output + maximum fan speed (range 1 - 255), when the temperature + is above defined range. Note: last six functions are influenced by other control bits, not yet exported by the driver, so a change might not have any effect. @@ -161,26 +210,35 @@ different power-on default values, but BIOS should already be loading appropriate defaults. Note that bank selection must be performed as is currently done in the driver for all register addresses. -0x49: only on DHG, selects temperature source for AUX fan, CPU fan0 -0x4a: not completely documented for the EHF and the DHG documentation assigns - different behavior to bits 7 and 6, including extending the temperature - input selection to SmartFan I, not just SmartFan III. Testing on the EHF - will reveal whether they are compatible or not. - -0x58: Chip ID: 0xa1=EHF 0xc1=DHG -0x5e: only on DHG, has bits to enable "current mode" temperature detection and - critical temperature protection -0x45b: only on EHF, bit 3, vin4 alarm (EHF supports 10 inputs, only 9 on DHG) -0x552: only on EHF, vin4 -0x558: only on EHF, vin4 high limit -0x559: only on EHF, vin4 low limit -0x6b: only on DHG, SYS fan critical temperature -0x6c: only on DHG, CPU fan0 critical temperature -0x6d: only on DHG, AUX fan critical temperature -0x6e: only on DHG, CPU fan1 critical temperature - -0x50-0x55 and 0x650-0x657 are marked "Test Register" for the EHF, but "Reserved - Register" for the DHG +========================= ===================================================== +Register(s) Meaning +========================= ===================================================== +0x49 only on DHG, selects temperature source for AUX fan, + CPU fan0 +0x4a not completely documented for the EHF and the DHG + documentation assigns different behavior to bits 7 + and 6, including extending the temperature input + selection to SmartFan I, not just SmartFan III. + Testing on the EHF will reveal whether they are + compatible or not. +0x58 Chip ID: 0xa1=EHF 0xc1=DHG +0x5e only on DHG, has bits to enable "current mode" + temperature detection and critical temperature + protection +0x45b only on EHF, bit 3, vin4 alarm (EHF supports 10 + inputs, only 9 on DHG) +0x552 only on EHF, vin4 +0x558 only on EHF, vin4 high limit +0x559 only on EHF, vin4 low limit +0x6b only on DHG, SYS fan critical temperature +0x6c only on DHG, CPU fan0 critical temperature +0x6d only on DHG, AUX fan critical temperature +0x6e only on DHG, CPU fan1 critical temperature +0x50-0x55 and 0x650-0x657 marked as: + + - "Test Register" for the EHF + - "Reserved Register" for the DHG +========================= ===================================================== The DHG also supports PECI, where the DHG queries Intel CPU temperatures, and the ICH8 southbridge gets that data via PECI from the DHG, so that the diff --git a/Documentation/hwmon/w83627hf b/Documentation/hwmon/w83627hf index 8432e1118173..d1406c28dee7 100644 --- a/Documentation/hwmon/w83627hf +++ b/Documentation/hwmon/w83627hf @@ -20,10 +20,10 @@ Supported chips: Datasheet: Provided by Winbond on request(http://www.winbond.com/hq/enu) Authors: - Frodo Looijaard , - Philip Edelbrock , - Mark Studebaker , - Bernhard C. Schrenk + Frodo Looijaard , + Philip Edelbrock , + Mark Studebaker , + Bernhard C. Schrenk Module Parameters ----------------- @@ -52,8 +52,8 @@ If you really want i2c accesses for these Super I/O chips, use the w83781d driver. However this is not the preferred method now that this ISA driver has been developed. -The w83627_HF_ uses pins 110-106 as VID0-VID4. The w83627_THF_ uses the -same pins as GPIO[0:4]. Technically, the w83627_THF_ does not support a +The `w83627_HF_` uses pins 110-106 as VID0-VID4. The `w83627_THF_` uses the +same pins as GPIO[0:4]. Technically, the `w83627_THF_` does not support a VID reading. However the two chips have the identical 128 pin package. So, it is possible or even likely for a w83627thf to have the VID signals routed to these pins despite their not being labeled for that purpose. Therefore, @@ -75,19 +75,23 @@ module parameter is gone for technical reasons. If you need this feature, you can obtain the same result by using the isaset tool (part of lm-sensors) before loading the driver: -# Enter the Super I/O config space -isaset -y -f 0x2e 0x87 -isaset -y -f 0x2e 0x87 +# Enter the Super I/O config space:: -# Select the hwmon logical device -isaset -y 0x2e 0x2f 0x07 0x0b + isaset -y -f 0x2e 0x87 + isaset -y -f 0x2e 0x87 -# Set the base I/O address (to 0x290 in this example) -isaset -y 0x2e 0x2f 0x60 0x02 -isaset -y 0x2e 0x2f 0x61 0x90 +# Select the hwmon logical device:: -# Exit the Super-I/O config space -isaset -y -f 0x2e 0xaa + isaset -y 0x2e 0x2f 0x07 0x0b + +# Set the base I/O address (to 0x290 in this example):: + + isaset -y 0x2e 0x2f 0x60 0x02 + isaset -y 0x2e 0x2f 0x61 0x90 + +# Exit the Super-I/O config space:: + + isaset -y -f 0x2e 0xaa The above sequence assumes a Super-I/O config space at 0x2e/0x2f, but 0x4e/0x4f is also possible. @@ -97,18 +101,23 @@ Voltage pin mapping Here is a summary of the voltage pin mapping for the W83627THF. This can be useful to convert data provided by board manufacturers into -working libsensors configuration statements. - - W83627THF | - Pin | Name | Register | Sysfs attribute ------------------------------------------------------ - 100 | CPUVCORE | 20h | in0 - 99 | VIN0 | 21h | in1 - 98 | VIN1 | 22h | in2 - 97 | VIN2 | 24h | in4 - 114 | AVCC | 23h | in3 - 61 | 5VSB | 50h (bank 5) | in7 - 74 | VBAT | 51h (bank 5) | in8 +working libsensors configuration statements: + + +- W83627THF + + + ======== =============== =============== =============== + Pin Name Register Sysfs attribute + ======== =============== =============== =============== + 100 CPUVCORE 20h in0 + 99 VIN0 21h in1 + 98 VIN1 22h in2 + 97 VIN2 24h in4 + 114 AVCC 23h in3 + 61 5VSB 50h (bank 5) in7 + 74 VBAT 51h (bank 5) in8 + ======== =============== =============== =============== For other supported devices, you'll have to take the hard path and look up the information in the datasheet yourself (and then add it diff --git a/Documentation/hwmon/w83773g b/Documentation/hwmon/w83773g index 4cc6c0b8257f..cabaed391414 100644 --- a/Documentation/hwmon/w83773g +++ b/Documentation/hwmon/w83773g @@ -1,13 +1,18 @@ Kernel driver w83773g -==================== +===================== Supported chips: + * Nuvoton W83773G + Prefix: 'w83773g' + Addresses scanned: I2C 0x4c and 0x4d + Datasheet: https://www.nuvoton.com/resource-files/W83773G_SG_DatasheetV1_2.pdf Authors: + Lei YU Description @@ -27,7 +32,4 @@ Resolution for both the local and remote channels is 0.125 degree C. The chip supports only temperature measurement. The driver exports the temperature values via the following sysfs files: -temp[1-3]_input -temp[2-3]_fault -temp[2-3]_offset -update_interval +**temp[1-3]_input, temp[2-3]_fault, temp[2-3]_offset, update_interval** diff --git a/Documentation/hwmon/w83781d b/Documentation/hwmon/w83781d index 129b0a3b555b..f36d33dfb704 100644 --- a/Documentation/hwmon/w83781d +++ b/Documentation/hwmon/w83781d @@ -2,44 +2,64 @@ Kernel driver w83781d ===================== Supported chips: + * Winbond W83781D + Prefix: 'w83781d' + Addresses scanned: I2C 0x28 - 0x2f, ISA 0x290 (8 I/O ports) + Datasheet: http://www.winbond-usa.com/products/winbond_products/pdfs/PCIC/w83781d.pdf + * Winbond W83782D + Prefix: 'w83782d' + Addresses scanned: I2C 0x28 - 0x2f, ISA 0x290 (8 I/O ports) + Datasheet: http://www.winbond.com + * Winbond W83783S + Prefix: 'w83783s' + Addresses scanned: I2C 0x2d + Datasheet: http://www.winbond-usa.com/products/winbond_products/pdfs/PCIC/w83783s.pdf + * Asus AS99127F + Prefix: 'as99127f' + Addresses scanned: I2C 0x28 - 0x2f + Datasheet: Unavailable from Asus + + Authors: - Frodo Looijaard , - Philip Edelbrock , - Mark Studebaker + + - Frodo Looijaard , + - Philip Edelbrock , + - Mark Studebaker Module parameters ----------------- * init int - (default 1) - Use 'init=0' to bypass initializing the chip. - Try this if your computer crashes when you load the module. + (default 1) + + Use 'init=0' to bypass initializing the chip. + Try this if your computer crashes when you load the module. * reset int - (default 0) - The driver used to reset the chip on load, but does no more. Use - 'reset=1' to restore the old behavior. Report if you need to do this. + (default 0) + The driver used to reset the chip on load, but does no more. Use + 'reset=1' to restore the old behavior. Report if you need to do this. force_subclients=bus,caddr,saddr,saddr This is used to force the i2c addresses for subclients of - a certain chip. Typical usage is `force_subclients=0,0x2d,0x4a,0x4b' + a certain chip. Typical usage is `force_subclients=0,0x2d,0x4a,0x4b` to force the subclients of chip 0x2d on bus 0 to i2c addresses 0x4a and 0x4b. This parameter is useful for certain Tyan boards. @@ -54,12 +74,19 @@ There is quite some difference between these chips, but they are similar enough that it was sensible to put them together in one driver. The Asus chips are similar to an I2C-only W83782D. -Chip #vin #fanin #pwm #temp wchipid vendid i2c ISA -as99127f 7 3 0 3 0x31 0x12c3 yes no -as99127f rev.2 (type_name = as99127f) 0x31 0x5ca3 yes no -w83781d 7 3 0 3 0x10-1 0x5ca3 yes yes -w83782d 9 3 2-4 3 0x30 0x5ca3 yes yes -w83783s 5-6 3 2 1-2 0x40 0x5ca3 yes no ++----------+---------+--------+-------+-------+---------+--------+------+-----+ +| Chip | #vin | #fanin | #pwm | #temp | wchipid | vendid | i2c | ISA | ++----------+---------+--------+-------+-------+---------+--------+------+-----+ +| as99127f | 7 | 3 | 0 | 3 | 0x31 | 0x12c3 | yes | no | ++----------+---------+--------+-------+-------+---------+--------+------+-----+ +| as99127f rev.2 (type_name = as99127f) | 0x31 | 0x5ca3 | yes | no | ++----------+---------+--------+-------+-------+---------+--------+------+-----+ +| w83781d | 7 | 3 | 0 | 3 | 0x10-1 | 0x5ca3 | yes | yes | ++----------+---------+--------+-------+-------+---------+--------+------+-----+ +| w83782d | 9 | 3 | 2-4 | 3 | 0x30 | 0x5ca3 | yes | yes | ++----------+---------+--------+-------+-------+---------+--------+------+-----+ +| w83783s | 5-6 | 3 | 2 | 1-2 | 0x40 | 0x5ca3 | yes | no | ++----------+---------+--------+-------+-------+---------+--------+------+-----+ Detection of these chips can sometimes be foiled because they can be in an internal state that allows no clean access. If you know the address @@ -124,22 +151,24 @@ or only the beeping for some alarms. Individual alarm and beep bits: -0x000001: in0 -0x000002: in1 -0x000004: in2 -0x000008: in3 -0x000010: temp1 -0x000020: temp2 (+temp3 on W83781D) -0x000040: fan1 -0x000080: fan2 -0x000100: in4 -0x000200: in5 -0x000400: in6 -0x000800: fan3 -0x001000: chassis -0x002000: temp3 (W83782D only) -0x010000: in7 (W83782D only) -0x020000: in8 (W83782D only) +======== ========================== +0x000001 in0 +0x000002 in1 +0x000004 in2 +0x000008 in3 +0x000010 temp1 +0x000020 temp2 (+temp3 on W83781D) +0x000040 fan1 +0x000080 fan2 +0x000100 in4 +0x000200 in5 +0x000400 in6 +0x000800 fan3 +0x001000 chassis +0x002000 temp3 (W83782D only) +0x010000 in7 (W83782D only) +0x020000 in8 (W83782D only) +======== ========================== If an alarm triggers, it will remain triggered until the hardware register is read at least once. This means that the cause for the alarm may @@ -179,68 +208,74 @@ Please do not send mail to the author or the sensors group asking for a datasheet or ideas on how to convince Asus. We can't help. -NOTES: +NOTES ----- 783s has no in1 so that in[2-6] are compatible with the 781d/782d. 783s pin is programmable for -5V or temp1; defaults to -5V, - no control in driver so temp1 doesn't work. + no control in driver so temp1 doesn't work. 782d and 783s datasheets differ on which is pwm1 and which is pwm2. - We chose to follow 782d. + We chose to follow 782d. 782d and 783s pin is programmable for fan3 input or pwm2 output; - defaults to fan3 input. - If pwm2 is enabled (with echo 255 1 > pwm2), then - fan3 will report 0. + defaults to fan3 input. + If pwm2 is enabled (with echo 255 1 > pwm2), then + fan3 will report 0. 782d has pwm1-2 for ISA, pwm1-4 for i2c. (pwm3-4 share pins with - the ISA pins) + the ISA pins) -Data sheet updates: +Data sheet updates ------------------ - PWM clock registers: - - 000: master / 512 - 001: master / 1024 - 010: master / 2048 - 011: master / 4096 - 100: master / 8192 + * 000: master / 512 + * 001: master / 1024 + * 010: master / 2048 + * 011: master / 4096 + * 100: master / 8192 Answers from Winbond tech support --------------------------------- -> -> 1) In the W83781D data sheet section 7.2 last paragraph, it talks about -> reprogramming the R-T table if the Beta of the thermistor is not -> 3435K. The R-T table is described briefly in section 8.20. -> What formulas do I use to program a new R-T table for a given Beta? -> - We are sorry that the calculation for R-T table value is -confidential. If you have another Beta value of thermistor, we can help -to calculate the R-T table for you. But you should give us real R-T -Table which can be gotten by thermistor vendor. Therefore we will calculate -them and obtain 32-byte data, and you can fill the 32-byte data to the -register in Bank0.CR51 of W83781D. +:: + + > + > 1) In the W83781D data sheet section 7.2 last paragraph, it talks about + > reprogramming the R-T table if the Beta of the thermistor is not + > 3435K. The R-T table is described briefly in section 8.20. + > What formulas do I use to program a new R-T table for a given Beta? + > + + We are sorry that the calculation for R-T table value is + confidential. If you have another Beta value of thermistor, we can help + to calculate the R-T table for you. But you should give us real R-T + Table which can be gotten by thermistor vendor. Therefore we will calculate + them and obtain 32-byte data, and you can fill the 32-byte data to the + register in Bank0.CR51 of W83781D. -> 2) In the W83782D data sheet, it mentions that pins 38, 39, and 40 are -> programmable to be either thermistor or Pentium II diode inputs. -> How do I program them for diode inputs? I can't find any register -> to program these to be diode inputs. - --> You may program Bank0 CR[5Dh] and CR[59h] registers. - CR[5Dh] bit 1(VTIN1) bit 2(VTIN2) bit 3(VTIN3) + > 2) In the W83782D data sheet, it mentions that pins 38, 39, and 40 are + > programmable to be either thermistor or Pentium II diode inputs. + > How do I program them for diode inputs? I can't find any register + > to program these to be diode inputs. - thermistor 0 0 0 - diode 1 1 1 + You may program Bank0 CR[5Dh] and CR[59h] registers. + =============================== =============== ============== ============ + CR[5Dh] bit 1(VTIN1) bit 2(VTIN2) bit 3(VTIN3) -(error) CR[59h] bit 4(VTIN1) bit 2(VTIN2) bit 3(VTIN3) -(right) CR[59h] bit 4(VTIN1) bit 5(VTIN2) bit 6(VTIN3) + thermistor 0 0 0 + diode 1 1 1 - PII thermal diode 1 1 1 - 2N3904 diode 0 0 0 + + (error) CR[59h] bit 4(VTIN1) bit 2(VTIN2) bit 3(VTIN3) + (right) CR[59h] bit 4(VTIN1) bit 5(VTIN2) bit 6(VTIN3) + + PII thermal diode 1 1 1 + 2N3904 diode 0 0 0 + =============================== =============== ============== ============ Asus Clones @@ -251,18 +286,21 @@ Here are some very useful information that were given to us by Alex Van Kaam about how to detect these chips, and how to read their values. He also gives advice for another Asus chipset, the Mozart-2 (which we don't support yet). Thanks Alex! + I reworded some parts and added personal comments. -# Detection: +Detection +^^^^^^^^^ AS99127F rev.1, AS99127F rev.2 and ASB100: - I2C address range: 0x29 - 0x2F -- If register 0x58 holds 0x31 then we have an Asus (either ASB100 or - AS99127F) +- If register 0x58 holds 0x31 then we have an Asus (either ASB100 or AS99127F) - Which one depends on register 0x4F (manufacturer ID): - 0x06 or 0x94: ASB100 - 0x12 or 0xC3: AS99127F rev.1 - 0x5C or 0xA3: AS99127F rev.2 + + - 0x06 or 0x94: ASB100 + - 0x12 or 0xC3: AS99127F rev.1 + - 0x5C or 0xA3: AS99127F rev.2 + Note that 0x5CA3 is Winbond's ID (WEC), which let us think Asus get their AS99127F rev.2 direct from Winbond. The other codes mean ATT and DVC, respectively. ATT could stand for Asustek something (although it would be @@ -273,88 +311,103 @@ Mozart-2: - I2C address: 0x77 - If register 0x58 holds 0x56 or 0x10 then we have a Mozart-2 - Of the Mozart there are 3 types: - 0x58=0x56, 0x4E=0x94, 0x4F=0x36: Asus ASM58 Mozart-2 - 0x58=0x56, 0x4E=0x94, 0x4F=0x06: Asus AS2K129R Mozart-2 - 0x58=0x10, 0x4E=0x5C, 0x4F=0xA3: Asus ??? Mozart-2 + + - 0x58=0x56, 0x4E=0x94, 0x4F=0x36: Asus ASM58 Mozart-2 + - 0x58=0x56, 0x4E=0x94, 0x4F=0x06: Asus AS2K129R Mozart-2 + - 0x58=0x10, 0x4E=0x5C, 0x4F=0xA3: Asus ??? Mozart-2 + You can handle all 3 the exact same way :) -# Temperature sensors: +Temperature sensors +^^^^^^^^^^^^^^^^^^^ ASB100: -- sensor 1: register 0x27 -- sensor 2 & 3 are the 2 LM75's on the SMBus -- sensor 4: register 0x17 -Remark: I noticed that on Intel boards sensor 2 is used for the CPU + - sensor 1: register 0x27 + - sensor 2 & 3 are the 2 LM75's on the SMBus + - sensor 4: register 0x17 + +Remark: + + I noticed that on Intel boards sensor 2 is used for the CPU and 4 is ignored/stuck, on AMD boards sensor 4 is the CPU and sensor 2 is either ignored or a socket temperature. AS99127F (rev.1 and 2 alike): -- sensor 1: register 0x27 -- sensor 2 & 3 are the 2 LM75's on the SMBus -Remark: Register 0x5b is suspected to be temperature type selector. Bit 1 + - sensor 1: register 0x27 + - sensor 2 & 3 are the 2 LM75's on the SMBus + +Remark: + + Register 0x5b is suspected to be temperature type selector. Bit 1 would control temp1, bit 3 temp2 and bit 5 temp3. Mozart-2: -- sensor 1: register 0x27 -- sensor 2: register 0x13 + - sensor 1: register 0x27 + - sensor 2: register 0x13 -# Fan sensors: +Fan sensors +^^^^^^^^^^^ ASB100, AS99127F (rev.1 and 2 alike): -- 3 fans, identical to the W83781D + - 3 fans, identical to the W83781D Mozart-2: -- 2 fans only, 1350000/RPM/div -- fan 1: register 0x28, divisor on register 0xA1 (bits 4-5) -- fan 2: register 0x29, divisor on register 0xA1 (bits 6-7) + - 2 fans only, 1350000/RPM/div + - fan 1: register 0x28, divisor on register 0xA1 (bits 4-5) + - fan 2: register 0x29, divisor on register 0xA1 (bits 6-7) -# Voltages: +Voltages +^^^^^^^^ This is where there is a difference between AS99127F rev.1 and 2. -Remark: The difference is similar to the difference between + +Remark: + + The difference is similar to the difference between W83781D and W83782D. ASB100: -in0=r(0x20)*0.016 -in1=r(0x21)*0.016 -in2=r(0x22)*0.016 -in3=r(0x23)*0.016*1.68 -in4=r(0x24)*0.016*3.8 -in5=r(0x25)*(-0.016)*3.97 -in6=r(0x26)*(-0.016)*1.666 + - in0=r(0x20)*0.016 + - in1=r(0x21)*0.016 + - in2=r(0x22)*0.016 + - in3=r(0x23)*0.016*1.68 + - in4=r(0x24)*0.016*3.8 + - in5=r(0x25)*(-0.016)*3.97 + - in6=r(0x26)*(-0.016)*1.666 AS99127F rev.1: -in0=r(0x20)*0.016 -in1=r(0x21)*0.016 -in2=r(0x22)*0.016 -in3=r(0x23)*0.016*1.68 -in4=r(0x24)*0.016*3.8 -in5=r(0x25)*(-0.016)*3.97 -in6=r(0x26)*(-0.016)*1.503 + - in0=r(0x20)*0.016 + - in1=r(0x21)*0.016 + - in2=r(0x22)*0.016 + - in3=r(0x23)*0.016*1.68 + - in4=r(0x24)*0.016*3.8 + - in5=r(0x25)*(-0.016)*3.97 + - in6=r(0x26)*(-0.016)*1.503 AS99127F rev.2: -in0=r(0x20)*0.016 -in1=r(0x21)*0.016 -in2=r(0x22)*0.016 -in3=r(0x23)*0.016*1.68 -in4=r(0x24)*0.016*3.8 -in5=(r(0x25)*0.016-3.6)*5.14+3.6 -in6=(r(0x26)*0.016-3.6)*3.14+3.6 + - in0=r(0x20)*0.016 + - in1=r(0x21)*0.016 + - in2=r(0x22)*0.016 + - in3=r(0x23)*0.016*1.68 + - in4=r(0x24)*0.016*3.8 + - in5=(r(0x25)*0.016-3.6)*5.14+3.6 + - in6=(r(0x26)*0.016-3.6)*3.14+3.6 Mozart-2: -in0=r(0x20)*0.016 -in1=255 -in2=r(0x22)*0.016 -in3=r(0x23)*0.016*1.68 -in4=r(0x24)*0.016*4 -in5=255 -in6=255 + - in0=r(0x20)*0.016 + - in1=255 + - in2=r(0x22)*0.016 + - in3=r(0x23)*0.016*1.68 + - in4=r(0x24)*0.016*4 + - in5=255 + - in6=255 -# PWM +PWM +^^^ * Additional info about PWM on the AS99127F (may apply to other Asus -chips as well) by Jean Delvare as of 2004-04-09: + chips as well) by Jean Delvare as of 2004-04-09: AS99127F revision 2 seems to have two PWM registers at 0x59 and 0x5A, and a temperature sensor type selector at 0x5B (which basically means @@ -401,15 +454,20 @@ AS99127F chips at all. I've been fiddling around with the (in)famous 0x59 register and found out the following values do work as a form of coarse pwm: -0x80 - seems to turn fans off after some time(1-2 minutes)... might be -some form of auto-fan-control based on temp? hmm (Qfan? this mobo is an -old ASUS, it isn't marketed as Qfan. Maybe some beta pre-attempt at Qfan -that was dropped at the BIOS) -0x81 - off -0x82 - slightly "on-ner" than off, but my fans do not get to move. I can -hear the high-pitched PWM sound that motors give off at too-low-pwm. -0x83 - now they do move. Estimate about 70% speed or so. -0x84-0x8f - full on +0x80 + - seems to turn fans off after some time(1-2 minutes)... might be + some form of auto-fan-control based on temp? hmm (Qfan? this mobo is an + old ASUS, it isn't marketed as Qfan. Maybe some beta pre-attempt at Qfan + that was dropped at the BIOS) +0x81 + - off +0x82 + - slightly "on-ner" than off, but my fans do not get to move. I can + hear the high-pitched PWM sound that motors give off at too-low-pwm. +0x83 + - now they do move. Estimate about 70% speed or so. +0x84-0x8f + - full on Changing the high nibble doesn't seem to do much except the high bit (0x80) must be set for PWM to work, else the current pwm doesn't seem to @@ -435,6 +493,7 @@ looks like PWM is filtered on this motherboard. Here are some of measurements: +==== ========= 0x80 20 mV 0x81 20 mV 0x82 232 mV @@ -451,3 +510,4 @@ Here are some of measurements: 0x8d 12.4 V 0x8e 12.4 V 0x8f 12.4 V +==== ========= diff --git a/Documentation/hwmon/w83792d b/Documentation/hwmon/w83792d index f2ffc402ea45..92c4bfe4968c 100644 --- a/Documentation/hwmon/w83792d +++ b/Documentation/hwmon/w83792d @@ -2,9 +2,13 @@ Kernel driver w83792d ===================== Supported chips: + * Winbond W83792D + Prefix: 'w83792d' + Addresses scanned: I2C 0x2c - 0x2f + Datasheet: http://www.winbond.com.tw Author: Shane Huang (Winbond) @@ -15,15 +19,16 @@ Module Parameters ----------------- * init int - (default 1) - Use 'init=0' to bypass initializing the chip. - Try this if your computer crashes when you load the module. + (default 1) + + Use 'init=0' to bypass initializing the chip. + Try this if your computer crashes when you load the module. * force_subclients=bus,caddr,saddr,saddr - This is used to force the i2c addresses for subclients of - a certain chip. Example usage is `force_subclients=0,0x2f,0x4a,0x4b' - to force the subclients of chip 0x2f on bus 0 to i2c addresses - 0x4a and 0x4b. + This is used to force the i2c addresses for subclients of + a certain chip. Example usage is `force_subclients=0,0x2f,0x4a,0x4b` + to force the subclients of chip 0x2f on bus 0 to i2c addresses + 0x4a and 0x4b. Description @@ -67,31 +72,34 @@ or maximum limit. Alarms are provided as output from "realtime status register". Following bits are defined: -bit - alarm on: -0 - in0 -1 - in1 -2 - temp1 -3 - temp2 -4 - temp3 -5 - fan1 -6 - fan2 -7 - fan3 -8 - in2 -9 - in3 -10 - in4 -11 - in5 -12 - in6 -13 - VID change -14 - chassis -15 - fan7 -16 - tart1 -17 - tart2 -18 - tart3 -19 - in7 -20 - in8 -21 - fan4 -22 - fan5 -23 - fan6 +==== ========== +bit alarm on +==== ========== +0 in0 +1 in1 +2 temp1 +3 temp2 +4 temp3 +5 fan1 +6 fan2 +7 fan3 +8 in2 +9 in3 +10 in4 +11 in5 +12 in6 +13 VID change +14 chassis +15 fan7 +16 tart1 +17 tart2 +18 tart3 +19 in7 +20 in8 +21 fan4 +22 fan5 +23 fan6 +==== ========== Tart will be asserted while target temperature cannot be achieved after 3 minutes of full speed rotation of corresponding fan. @@ -114,7 +122,7 @@ Known problems: by CR[0x49h]. - The function of vid and vrm has not been finished, because I'm NOT very familiar with them. Adding support is welcome. -  - The function of chassis open detection needs more tests. + - The function of chassis open detection needs more tests. - If you have ASUS server board and chip was not found: Then you will need to upgrade to latest (or beta) BIOS. If it does not help please contact us. @@ -165,17 +173,27 @@ for each fan. /sys files ---------- -pwm[1-7] - this file stores PWM duty cycle or DC value (fan speed) in range: - 0 (stop) to 255 (full) -pwm[1-3]_enable - this file controls mode of fan/temperature control: - * 0 Disabled - * 1 Manual mode - * 2 Smart Fan II - * 3 Thermal Cruise -pwm[1-7]_mode - Select PWM or DC mode - * 0 DC - * 1 PWM -thermal_cruise[1-3] - Selects the desired temperature for cruise (degC) -tolerance[1-3] - Value in degrees of Celsius (degC) for +- T -sf2_point[1-4]_fan[1-3] - four temperature points for each fan for Smart Fan II -sf2_level[1-3]_fan[1-3] - three PWM/DC levels for each fan for Smart Fan II +pwm[1-7] + - this file stores PWM duty cycle or DC value (fan speed) in range: + + 0 (stop) to 255 (full) +pwm[1-3]_enable + - this file controls mode of fan/temperature control: + + * 0 Disabled + * 1 Manual mode + * 2 Smart Fan II + * 3 Thermal Cruise +pwm[1-7]_mode + - Select PWM or DC mode + + * 0 DC + * 1 PWM +thermal_cruise[1-3] + - Selects the desired temperature for cruise (degC) +tolerance[1-3] + - Value in degrees of Celsius (degC) for +- T +sf2_point[1-4]_fan[1-3] + - four temperature points for each fan for Smart Fan II +sf2_level[1-3]_fan[1-3] + - three PWM/DC levels for each fan for Smart Fan II diff --git a/Documentation/hwmon/w83795 b/Documentation/hwmon/w83795 index d3e678216b9a..d0615e2fabb9 100644 --- a/Documentation/hwmon/w83795 +++ b/Documentation/hwmon/w83795 @@ -2,18 +2,26 @@ Kernel driver w83795 ==================== Supported chips: + * Winbond/Nuvoton W83795G + Prefix: 'w83795g' + Addresses scanned: I2C 0x2c - 0x2f + Datasheet: Available for download on nuvoton.com + * Winbond/Nuvoton W83795ADG + Prefix: 'w83795adg' + Addresses scanned: I2C 0x2c - 0x2f + Datasheet: Available for download on nuvoton.com Authors: - Wei Song (Nuvoton) - Jean Delvare + - Wei Song (Nuvoton) + - Jean Delvare Pin mapping @@ -23,105 +31,112 @@ Here is a summary of the pin mapping for the W83795G and W83795ADG. This can be useful to convert data provided by board manufacturers into working libsensors configuration statements. - W83795G | - Pin | Name | Register | Sysfs attribute ------------------------------------------------------------------- - 13 | VSEN1 (VCORE1) | 10h | in0 - 14 | VSEN2 (VCORE2) | 11h | in1 - 15 | VSEN3 (VCORE3) | 12h | in2 - 16 | VSEN4 | 13h | in3 - 17 | VSEN5 | 14h | in4 - 18 | VSEN6 | 15h | in5 - 19 | VSEN7 | 16h | in6 - 20 | VSEN8 | 17h | in7 - 21 | VSEN9 | 18h | in8 - 22 | VSEN10 | 19h | in9 - 23 | VSEN11 | 1Ah | in10 - 28 | VTT | 1Bh | in11 - 24 | 3VDD | 1Ch | in12 - 25 | 3VSB | 1Dh | in13 - 26 | VBAT | 1Eh | in14 - 3 | VSEN12/TR5 | 1Fh | in15/temp5 - 4 | VSEN13/TR5 | 20h | in16/temp6 - 5/ 6 | VDSEN14/TR1/TD1 | 21h | in17/temp1 - 7/ 8 | VDSEN15/TR2/TD2 | 22h | in18/temp2 - 9/ 10 | VDSEN16/TR3/TD3 | 23h | in19/temp3 - 11/ 12 | VDSEN17/TR4/TD4 | 24h | in20/temp4 - 40 | FANIN1 | 2Eh | fan1 - 42 | FANIN2 | 2Fh | fan2 - 44 | FANIN3 | 30h | fan3 - 46 | FANIN4 | 31h | fan4 - 48 | FANIN5 | 32h | fan5 - 50 | FANIN6 | 33h | fan6 - 52 | FANIN7 | 34h | fan7 - 54 | FANIN8 | 35h | fan8 - 57 | FANIN9 | 36h | fan9 - 58 | FANIN10 | 37h | fan10 - 59 | FANIN11 | 38h | fan11 - 60 | FANIN12 | 39h | fan12 - 31 | FANIN13 | 3Ah | fan13 - 35 | FANIN14 | 3Bh | fan14 - 41 | FANCTL1 | 10h (bank 2) | pwm1 - 43 | FANCTL2 | 11h (bank 2) | pwm2 - 45 | FANCTL3 | 12h (bank 2) | pwm3 - 47 | FANCTL4 | 13h (bank 2) | pwm4 - 49 | FANCTL5 | 14h (bank 2) | pwm5 - 51 | FANCTL6 | 15h (bank 2) | pwm6 - 53 | FANCTL7 | 16h (bank 2) | pwm7 - 55 | FANCTL8 | 17h (bank 2) | pwm8 - 29/ 30 | PECI/TSI (DTS1) | 26h | temp7 - 29/ 30 | PECI/TSI (DTS2) | 27h | temp8 - 29/ 30 | PECI/TSI (DTS3) | 28h | temp9 - 29/ 30 | PECI/TSI (DTS4) | 29h | temp10 - 29/ 30 | PECI/TSI (DTS5) | 2Ah | temp11 - 29/ 30 | PECI/TSI (DTS6) | 2Bh | temp12 - 29/ 30 | PECI/TSI (DTS7) | 2Ch | temp13 - 29/ 30 | PECI/TSI (DTS8) | 2Dh | temp14 - 27 | CASEOPEN# | 46h | intrusion0 - - W83795ADG | - Pin | Name | Register | Sysfs attribute ------------------------------------------------------------------- - 10 | VSEN1 (VCORE1) | 10h | in0 - 11 | VSEN2 (VCORE2) | 11h | in1 - 12 | VSEN3 (VCORE3) | 12h | in2 - 13 | VSEN4 | 13h | in3 - 14 | VSEN5 | 14h | in4 - 15 | VSEN6 | 15h | in5 - 16 | VSEN7 | 16h | in6 - 17 | VSEN8 | 17h | in7 - 22 | VTT | 1Bh | in11 - 18 | 3VDD | 1Ch | in12 - 19 | 3VSB | 1Dh | in13 - 20 | VBAT | 1Eh | in14 - 48 | VSEN12/TR5 | 1Fh | in15/temp5 - 1 | VSEN13/TR5 | 20h | in16/temp6 - 2/ 3 | VDSEN14/TR1/TD1 | 21h | in17/temp1 - 4/ 5 | VDSEN15/TR2/TD2 | 22h | in18/temp2 - 6/ 7 | VDSEN16/TR3/TD3 | 23h | in19/temp3 - 8/ 9 | VDSEN17/TR4/TD4 | 24h | in20/temp4 - 32 | FANIN1 | 2Eh | fan1 - 34 | FANIN2 | 2Fh | fan2 - 36 | FANIN3 | 30h | fan3 - 37 | FANIN4 | 31h | fan4 - 38 | FANIN5 | 32h | fan5 - 39 | FANIN6 | 33h | fan6 - 40 | FANIN7 | 34h | fan7 - 41 | FANIN8 | 35h | fan8 - 43 | FANIN9 | 36h | fan9 - 44 | FANIN10 | 37h | fan10 - 45 | FANIN11 | 38h | fan11 - 46 | FANIN12 | 39h | fan12 - 24 | FANIN13 | 3Ah | fan13 - 28 | FANIN14 | 3Bh | fan14 - 33 | FANCTL1 | 10h (bank 2) | pwm1 - 35 | FANCTL2 | 11h (bank 2) | pwm2 - 23 | PECI (DTS1) | 26h | temp7 - 23 | PECI (DTS2) | 27h | temp8 - 23 | PECI (DTS3) | 28h | temp9 - 23 | PECI (DTS4) | 29h | temp10 - 23 | PECI (DTS5) | 2Ah | temp11 - 23 | PECI (DTS6) | 2Bh | temp12 - 23 | PECI (DTS7) | 2Ch | temp13 - 23 | PECI (DTS8) | 2Dh | temp14 - 21 | CASEOPEN# | 46h | intrusion0 + +- W83795G + +========= ======================= =============== ================ +Pin Name Register Sysfs attribute +========= ======================= =============== ================ + 13 VSEN1 (VCORE1) 10h in0 + 14 VSEN2 (VCORE2) 11h in1 + 15 VSEN3 (VCORE3) 12h in2 + 16 VSEN4 13h in3 + 17 VSEN5 14h in4 + 18 VSEN6 15h in5 + 19 VSEN7 16h in6 + 20 VSEN8 17h in7 + 21 VSEN9 18h in8 + 22 VSEN10 19h in9 + 23 VSEN11 1Ah in10 + 28 VTT 1Bh in11 + 24 3VDD 1Ch in12 + 25 3VSB 1Dh in13 + 26 VBAT 1Eh in14 + 3 VSEN12/TR5 1Fh in15/temp5 + 4 VSEN13/TR5 20h in16/temp6 + 5/ 6 VDSEN14/TR1/TD1 21h in17/temp1 + 7/ 8 VDSEN15/TR2/TD2 22h in18/temp2 + 9/ 10 VDSEN16/TR3/TD3 23h in19/temp3 + 11/ 12 VDSEN17/TR4/TD4 24h in20/temp4 + 40 FANIN1 2Eh fan1 + 42 FANIN2 2Fh fan2 + 44 FANIN3 30h fan3 + 46 FANIN4 31h fan4 + 48 FANIN5 32h fan5 + 50 FANIN6 33h fan6 + 52 FANIN7 34h fan7 + 54 FANIN8 35h fan8 + 57 FANIN9 36h fan9 + 58 FANIN10 37h fan10 + 59 FANIN11 38h fan11 + 60 FANIN12 39h fan12 + 31 FANIN13 3Ah fan13 + 35 FANIN14 3Bh fan14 + 41 FANCTL1 10h (bank 2) pwm1 + 43 FANCTL2 11h (bank 2) pwm2 + 45 FANCTL3 12h (bank 2) pwm3 + 47 FANCTL4 13h (bank 2) pwm4 + 49 FANCTL5 14h (bank 2) pwm5 + 51 FANCTL6 15h (bank 2) pwm6 + 53 FANCTL7 16h (bank 2) pwm7 + 55 FANCTL8 17h (bank 2) pwm8 + 29/ 30 PECI/TSI (DTS1) 26h temp7 + 29/ 30 PECI/TSI (DTS2) 27h temp8 + 29/ 30 PECI/TSI (DTS3) 28h temp9 + 29/ 30 PECI/TSI (DTS4) 29h temp10 + 29/ 30 PECI/TSI (DTS5) 2Ah temp11 + 29/ 30 PECI/TSI (DTS6) 2Bh temp12 + 29/ 30 PECI/TSI (DTS7) 2Ch temp13 + 29/ 30 PECI/TSI (DTS8) 2Dh temp14 + 27 CASEOPEN# 46h intrusion0 +========= ======================= =============== ================ + +- W83795ADG + +========= ======================= =============== ================ +Pin Name Register Sysfs attribute +========= ======================= =============== ================ + 10 VSEN1 (VCORE1) 10h in0 + 11 VSEN2 (VCORE2) 11h in1 + 12 VSEN3 (VCORE3) 12h in2 + 13 VSEN4 13h in3 + 14 VSEN5 14h in4 + 15 VSEN6 15h in5 + 16 VSEN7 16h in6 + 17 VSEN8 17h in7 + 22 VTT 1Bh in11 + 18 3VDD 1Ch in12 + 19 3VSB 1Dh in13 + 20 VBAT 1Eh in14 + 48 VSEN12/TR5 1Fh in15/temp5 + 1 VSEN13/TR5 20h in16/temp6 + 2/ 3 VDSEN14/TR1/TD1 21h in17/temp1 + 4/ 5 VDSEN15/TR2/TD2 22h in18/temp2 + 6/ 7 VDSEN16/TR3/TD3 23h in19/temp3 + 8/ 9 VDSEN17/TR4/TD4 24h in20/temp4 + 32 FANIN1 2Eh fan1 + 34 FANIN2 2Fh fan2 + 36 FANIN3 30h fan3 + 37 FANIN4 31h fan4 + 38 FANIN5 32h fan5 + 39 FANIN6 33h fan6 + 40 FANIN7 34h fan7 + 41 FANIN8 35h fan8 + 43 FANIN9 36h fan9 + 44 FANIN10 37h fan10 + 45 FANIN11 38h fan11 + 46 FANIN12 39h fan12 + 24 FANIN13 3Ah fan13 + 28 FANIN14 3Bh fan14 + 33 FANCTL1 10h (bank 2) pwm1 + 35 FANCTL2 11h (bank 2) pwm2 + 23 PECI (DTS1) 26h temp7 + 23 PECI (DTS2) 27h temp8 + 23 PECI (DTS3) 28h temp9 + 23 PECI (DTS4) 29h temp10 + 23 PECI (DTS5) 2Ah temp11 + 23 PECI (DTS6) 2Bh temp12 + 23 PECI (DTS7) 2Ch temp13 + 23 PECI (DTS8) 2Dh temp14 + 21 CASEOPEN# 46h intrusion0 +========= ======================= =============== ================ diff --git a/Documentation/hwmon/w83l785ts b/Documentation/hwmon/w83l785ts index c8978478871f..7fa5418fed11 100644 --- a/Documentation/hwmon/w83l785ts +++ b/Documentation/hwmon/w83l785ts @@ -2,14 +2,19 @@ Kernel driver w83l785ts ======================= Supported chips: + * Winbond W83L785TS-S + Prefix: 'w83l785ts' + Addresses scanned: I2C 0x2e + Datasheet: Publicly available at the Winbond USA website - http://www.winbond-usa.com/products/winbond_products/pdfs/PCIC/W83L785TS-S.pdf + + http://www.winbond-usa.com/products/winbond_products/pdfs/PCIC/W83L785TS-S.pdf Authors: - Jean Delvare + Jean Delvare Description ----------- diff --git a/Documentation/hwmon/w83l786ng b/Documentation/hwmon/w83l786ng index d8f55d7fff10..2b7776190de3 100644 --- a/Documentation/hwmon/w83l786ng +++ b/Documentation/hwmon/w83l786ng @@ -1,10 +1,14 @@ Kernel driver w83l786ng -===================== +======================= Supported chips: + * Winbond W83L786NG/W83L786NR + Prefix: 'w83l786ng' + Addresses scanned: I2C 0x2e - 0x2f + Datasheet: http://www.winbond-usa.com/products/winbond_products/pdfs/PCIC/W83L786NRNG09.pdf Author: Kevin Lo @@ -14,9 +18,10 @@ Module Parameters ----------------- * reset boolean - (default 0) - Use 'reset=1' to reset the chip (via index 0x40, bit 7). The default - behavior is no chip reset to preserve BIOS settings + (default 0) + + Use 'reset=1' to reset the chip (via index 0x40, bit 7). The default + behavior is no chip reset to preserve BIOS settings Description @@ -41,14 +46,21 @@ or maximum limit. /sys files ---------- -pwm[1-2] - this file stores PWM duty cycle or DC value (fan speed) in range: - 0 (stop) to 255 (full) -pwm[1-2]_enable - this file controls mode of fan/temperature control: - * 0 Manual Mode - * 1 Thermal Cruise - * 2 Smart Fan II - * 4 FAN_SET -pwm[1-2]_mode - Select PWM of DC mode - * 0 DC - * 1 PWM -tolerance[1-2] - Value in degrees of Celsius (degC) for +- T +pwm[1-2] + - this file stores PWM duty cycle or DC value (fan speed) in range: + + 0 (stop) to 255 (full) +pwm[1-2]_enable + - this file controls mode of fan/temperature control: + + * 0 Manual Mode + * 1 Thermal Cruise + * 2 Smart Fan II + * 4 FAN_SET +pwm[1-2]_mode + - Select PWM of DC mode + + * 0 DC + * 1 PWM +tolerance[1-2] + - Value in degrees of Celsius (degC) for +- T diff --git a/Documentation/hwmon/xgene-hwmon b/Documentation/hwmon/xgene-hwmon index 6ec50ed7cc8f..439b30b881b6 100644 --- a/Documentation/hwmon/xgene-hwmon +++ b/Documentation/hwmon/xgene-hwmon @@ -1,7 +1,8 @@ Kernel driver xgene-hwmon -======================== +========================= Supported chips: + * APM X-Gene SoC Description @@ -15,16 +16,21 @@ For ACPI, it is the PCC mailbox. The following sensors are supported * Temperature - - SoC on-die temperature in milli-degree C - - Alarm when high/over temperature occurs + - SoC on-die temperature in milli-degree C + - Alarm when high/over temperature occurs + * Power - - CPU power in uW - - IO power in uW + - CPU power in uW + - IO power in uW sysfs-Interface --------------- -temp0_input - SoC on-die temperature (milli-degree C) -temp0_critical_alarm - An 1 would indicates on-die temperature exceeded threshold -power0_input - CPU power in (uW) -power1_input - IO power in (uW) +temp0_input + - SoC on-die temperature (milli-degree C) +temp0_critical_alarm + - An 1 would indicates on-die temperature exceeded threshold +power0_input + - CPU power in (uW) +power1_input + - IO power in (uW) -- cgit v1.2.3 From 7ebd8b66dd9e5a0b65e5ee5e2b8e7ca382ec97b7 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 17 Apr 2019 06:46:29 -0300 Subject: docs: hwmon: Add an index file and rename docs to *.rst Now that all files were converted to ReST format, rename them and add an index. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Guenter Roeck --- Documentation/devicetree/bindings/hwmon/g762.txt | 2 +- Documentation/hwmon/ab8500 | 26 - Documentation/hwmon/ab8500.rst | 26 + Documentation/hwmon/abituguru | 113 --- Documentation/hwmon/abituguru-datasheet | 336 ------- Documentation/hwmon/abituguru-datasheet.rst | 336 +++++++ Documentation/hwmon/abituguru.rst | 113 +++ Documentation/hwmon/abituguru3 | 75 -- Documentation/hwmon/abituguru3.rst | 75 ++ Documentation/hwmon/abx500 | 32 - Documentation/hwmon/abx500.rst | 32 + Documentation/hwmon/acpi_power_meter | 54 -- Documentation/hwmon/acpi_power_meter.rst | 54 ++ Documentation/hwmon/ad7314 | 34 - Documentation/hwmon/ad7314.rst | 34 + Documentation/hwmon/adc128d818 | 50 - Documentation/hwmon/adc128d818.rst | 50 + Documentation/hwmon/adm1021 | 153 --- Documentation/hwmon/adm1021.rst | 153 +++ Documentation/hwmon/adm1025 | 60 -- Documentation/hwmon/adm1025.rst | 60 ++ Documentation/hwmon/adm1026 | 101 -- Documentation/hwmon/adm1026.rst | 101 ++ Documentation/hwmon/adm1031 | 43 - Documentation/hwmon/adm1031.rst | 43 + Documentation/hwmon/adm1275 | 148 --- Documentation/hwmon/adm1275.rst | 148 +++ Documentation/hwmon/adm9240 | 201 ---- Documentation/hwmon/adm9240.rst | 201 ++++ Documentation/hwmon/ads1015 | 90 -- Documentation/hwmon/ads1015.rst | 90 ++ Documentation/hwmon/ads7828 | 65 -- Documentation/hwmon/ads7828.rst | 65 ++ Documentation/hwmon/adt7410 | 94 -- Documentation/hwmon/adt7410.rst | 94 ++ Documentation/hwmon/adt7411 | 50 - Documentation/hwmon/adt7411.rst | 50 + Documentation/hwmon/adt7462 | 71 -- Documentation/hwmon/adt7462.rst | 70 ++ Documentation/hwmon/adt7470 | 94 -- Documentation/hwmon/adt7470.rst | 94 ++ Documentation/hwmon/adt7475 | 156 ---- Documentation/hwmon/adt7475.rst | 156 ++++ Documentation/hwmon/amc6821 | 109 --- Documentation/hwmon/amc6821.rst | 108 +++ Documentation/hwmon/asb100 | 74 -- Documentation/hwmon/asb100.rst | 73 ++ Documentation/hwmon/asc7621 | 326 ------- Documentation/hwmon/asc7621.rst | 326 +++++++ Documentation/hwmon/aspeed-pwm-tacho | 24 - Documentation/hwmon/aspeed-pwm-tacho.rst | 24 + Documentation/hwmon/coretemp | 195 ---- Documentation/hwmon/coretemp.rst | 195 ++++ Documentation/hwmon/da9052 | 78 -- Documentation/hwmon/da9052.rst | 78 ++ Documentation/hwmon/da9055 | 57 -- Documentation/hwmon/da9055.rst | 57 ++ Documentation/hwmon/dme1737 | 364 -------- Documentation/hwmon/dme1737.rst | 364 ++++++++ Documentation/hwmon/ds1621 | 217 ----- Documentation/hwmon/ds1621.rst | 217 +++++ Documentation/hwmon/ds620 | 38 - Documentation/hwmon/ds620.rst | 38 + Documentation/hwmon/emc1403 | 80 -- Documentation/hwmon/emc1403.rst | 80 ++ Documentation/hwmon/emc2103 | 37 - Documentation/hwmon/emc2103.rst | 37 + Documentation/hwmon/emc6w201 | 47 - Documentation/hwmon/emc6w201.rst | 47 + Documentation/hwmon/f71805f | 181 ---- Documentation/hwmon/f71805f.rst | 181 ++++ Documentation/hwmon/f71882fg | 192 ---- Documentation/hwmon/f71882fg.rst | 192 ++++ Documentation/hwmon/fam15h_power | 131 --- Documentation/hwmon/fam15h_power.rst | 131 +++ Documentation/hwmon/ftsteutates | 33 - Documentation/hwmon/ftsteutates.rst | 33 + Documentation/hwmon/g760a | 40 - Documentation/hwmon/g760a.rst | 40 + Documentation/hwmon/g762 | 74 -- Documentation/hwmon/g762.rst | 74 ++ Documentation/hwmon/gl518sm | 80 -- Documentation/hwmon/gl518sm.rst | 80 ++ Documentation/hwmon/hih6130 | 45 - Documentation/hwmon/hih6130.rst | 45 + Documentation/hwmon/hwmon-kernel-api.rst | 386 ++++++++ Documentation/hwmon/hwmon-kernel-api.txt | 386 -------- Documentation/hwmon/ibm-cffps | 57 -- Documentation/hwmon/ibm-cffps.rst | 57 ++ Documentation/hwmon/ibmaem | 44 - Documentation/hwmon/ibmaem.rst | 44 + Documentation/hwmon/ibmpowernv | 87 -- Documentation/hwmon/ibmpowernv.rst | 87 ++ Documentation/hwmon/ina209 | 99 -- Documentation/hwmon/ina209.rst | 99 ++ Documentation/hwmon/ina2xx | 104 --- Documentation/hwmon/ina2xx.rst | 104 +++ Documentation/hwmon/ina3221 | 49 - Documentation/hwmon/ina3221.rst | 49 + Documentation/hwmon/index.rst | 179 ++++ Documentation/hwmon/ir35221 | 92 -- Documentation/hwmon/ir35221.rst | 92 ++ Documentation/hwmon/it87 | 348 ------- Documentation/hwmon/it87.rst | 348 +++++++ Documentation/hwmon/jc42 | 152 --- Documentation/hwmon/jc42.rst | 152 +++ Documentation/hwmon/k10temp | 112 --- Documentation/hwmon/k10temp.rst | 112 +++ Documentation/hwmon/k8temp | 62 -- Documentation/hwmon/k8temp.rst | 62 ++ Documentation/hwmon/lineage-pem | 85 -- Documentation/hwmon/lineage-pem.rst | 85 ++ Documentation/hwmon/lm25066 | 137 --- Documentation/hwmon/lm25066.rst | 137 +++ Documentation/hwmon/lm63 | 95 -- Documentation/hwmon/lm63.rst | 95 ++ Documentation/hwmon/lm70 | 62 -- Documentation/hwmon/lm70.rst | 62 ++ Documentation/hwmon/lm73 | 98 -- Documentation/hwmon/lm73.rst | 98 ++ Documentation/hwmon/lm75 | 160 ---- Documentation/hwmon/lm75.rst | 160 ++++ Documentation/hwmon/lm77 | 45 - Documentation/hwmon/lm77.rst | 45 + Documentation/hwmon/lm78 | 80 -- Documentation/hwmon/lm78.rst | 80 ++ Documentation/hwmon/lm80 | 74 -- Documentation/hwmon/lm80.rst | 74 ++ Documentation/hwmon/lm83 | 97 -- Documentation/hwmon/lm83.rst | 97 ++ Documentation/hwmon/lm85 | 286 ------ Documentation/hwmon/lm85.rst | 286 ++++++ Documentation/hwmon/lm87 | 86 -- Documentation/hwmon/lm87.rst | 86 ++ Documentation/hwmon/lm90 | 399 -------- Documentation/hwmon/lm90.rst | 399 ++++++++ Documentation/hwmon/lm92 | 48 - Documentation/hwmon/lm92.rst | 48 + Documentation/hwmon/lm93 | 312 ------- Documentation/hwmon/lm93.rst | 312 +++++++ Documentation/hwmon/lm95234 | 48 - Documentation/hwmon/lm95234.rst | 48 + Documentation/hwmon/lm95245 | 48 - Documentation/hwmon/lm95245.rst | 48 + Documentation/hwmon/ltc2945 | 92 -- Documentation/hwmon/ltc2945.rst | 92 ++ Documentation/hwmon/ltc2978 | 355 ------- Documentation/hwmon/ltc2978.rst | 355 +++++++ Documentation/hwmon/ltc2990 | 62 -- Documentation/hwmon/ltc2990.rst | 62 ++ Documentation/hwmon/ltc3815 | 67 -- Documentation/hwmon/ltc3815.rst | 67 ++ Documentation/hwmon/ltc4151 | 55 -- Documentation/hwmon/ltc4151.rst | 55 ++ Documentation/hwmon/ltc4215 | 59 -- Documentation/hwmon/ltc4215.rst | 59 ++ Documentation/hwmon/ltc4245 | 111 --- Documentation/hwmon/ltc4245.rst | 111 +++ Documentation/hwmon/ltc4260 | 64 -- Documentation/hwmon/ltc4260.rst | 64 ++ Documentation/hwmon/ltc4261 | 71 -- Documentation/hwmon/ltc4261.rst | 71 ++ Documentation/hwmon/max16064 | 75 -- Documentation/hwmon/max16064.rst | 75 ++ Documentation/hwmon/max16065 | 127 --- Documentation/hwmon/max16065.rst | 127 +++ Documentation/hwmon/max1619 | 34 - Documentation/hwmon/max1619.rst | 33 + Documentation/hwmon/max1668 | 70 -- Documentation/hwmon/max1668.rst | 70 ++ Documentation/hwmon/max197 | 70 -- Documentation/hwmon/max197.rst | 70 ++ Documentation/hwmon/max20751 | 84 -- Documentation/hwmon/max20751.rst | 84 ++ Documentation/hwmon/max31722 | 46 - Documentation/hwmon/max31722.rst | 46 + Documentation/hwmon/max31785 | 66 -- Documentation/hwmon/max31785.rst | 66 ++ Documentation/hwmon/max31790 | 43 - Documentation/hwmon/max31790.rst | 43 + Documentation/hwmon/max34440 | 195 ---- Documentation/hwmon/max34440.rst | 195 ++++ Documentation/hwmon/max6639 | 55 -- Documentation/hwmon/max6639.rst | 55 ++ Documentation/hwmon/max6642 | 27 - Documentation/hwmon/max6642.rst | 27 + Documentation/hwmon/max6650 | 75 -- Documentation/hwmon/max6650.rst | 74 ++ Documentation/hwmon/max6697 | 91 -- Documentation/hwmon/max6697.rst | 91 ++ Documentation/hwmon/max8688 | 85 -- Documentation/hwmon/max8688.rst | 85 ++ Documentation/hwmon/mc13783-adc | 89 -- Documentation/hwmon/mc13783-adc.rst | 89 ++ Documentation/hwmon/mcp3021 | 38 - Documentation/hwmon/mcp3021.rst | 38 + Documentation/hwmon/menf21bmc | 55 -- Documentation/hwmon/menf21bmc.rst | 55 ++ Documentation/hwmon/mlxreg-fan | 70 -- Documentation/hwmon/mlxreg-fan.rst | 70 ++ Documentation/hwmon/nct6683 | 64 -- Documentation/hwmon/nct6683.rst | 64 ++ Documentation/hwmon/nct6775 | 280 ------ Documentation/hwmon/nct6775.rst | 280 ++++++ Documentation/hwmon/nct7802 | 38 - Documentation/hwmon/nct7802.rst | 38 + Documentation/hwmon/nct7904 | 67 -- Documentation/hwmon/nct7904.rst | 67 ++ Documentation/hwmon/npcm750-pwm-fan | 26 - Documentation/hwmon/npcm750-pwm-fan.rst | 26 + Documentation/hwmon/nsa320 | 64 -- Documentation/hwmon/nsa320.rst | 64 ++ Documentation/hwmon/ntc_thermistor | 111 --- Documentation/hwmon/ntc_thermistor.rst | 111 +++ Documentation/hwmon/occ | 153 --- Documentation/hwmon/occ.rst | 153 +++ Documentation/hwmon/pc87360 | 198 ---- Documentation/hwmon/pc87360.rst | 198 ++++ Documentation/hwmon/pc87427 | 63 -- Documentation/hwmon/pc87427.rst | 63 ++ Documentation/hwmon/pcf8591 | 98 -- Documentation/hwmon/pcf8591.rst | 98 ++ Documentation/hwmon/pmbus | 254 ----- Documentation/hwmon/pmbus-core | 316 ------- Documentation/hwmon/pmbus-core.rst | 316 +++++++ Documentation/hwmon/pmbus.rst | 254 +++++ Documentation/hwmon/powr1220 | 53 -- Documentation/hwmon/powr1220.rst | 53 ++ Documentation/hwmon/pwm-fan | 20 - Documentation/hwmon/pwm-fan.rst | 20 + Documentation/hwmon/raspberrypi-hwmon | 25 - Documentation/hwmon/raspberrypi-hwmon.rst | 25 + Documentation/hwmon/sch5627 | 31 - Documentation/hwmon/sch5627.rst | 31 + Documentation/hwmon/sch5636 | 37 - Documentation/hwmon/sch5636.rst | 37 + Documentation/hwmon/scpi-hwmon | 36 - Documentation/hwmon/scpi-hwmon.rst | 36 + Documentation/hwmon/sht15 | 83 -- Documentation/hwmon/sht15.rst | 83 ++ Documentation/hwmon/sht21 | 68 -- Documentation/hwmon/sht21.rst | 68 ++ Documentation/hwmon/sht3x | 88 -- Documentation/hwmon/sht3x.rst | 88 ++ Documentation/hwmon/shtc1 | 58 -- Documentation/hwmon/shtc1.rst | 58 ++ Documentation/hwmon/sis5595 | 124 --- Documentation/hwmon/sis5595.rst | 123 +++ Documentation/hwmon/smm665 | 187 ---- Documentation/hwmon/smm665.rst | 187 ++++ Documentation/hwmon/smsc47b397 | 197 ---- Documentation/hwmon/smsc47b397.rst | 197 ++++ Documentation/hwmon/smsc47m1 | 86 -- Documentation/hwmon/smsc47m1.rst | 86 ++ Documentation/hwmon/smsc47m192 | 116 --- Documentation/hwmon/smsc47m192.rst | 116 +++ Documentation/hwmon/submitting-patches | 146 --- Documentation/hwmon/submitting-patches.rst | 146 +++ Documentation/hwmon/sysfs-interface | 1086 ---------------------- Documentation/hwmon/sysfs-interface.rst | 1086 ++++++++++++++++++++++ Documentation/hwmon/tc654 | 34 - Documentation/hwmon/tc654.rst | 34 + Documentation/hwmon/tc74 | 23 - Documentation/hwmon/tc74.rst | 23 + Documentation/hwmon/thmc50 | 90 -- Documentation/hwmon/thmc50.rst | 89 ++ Documentation/hwmon/tmp102 | 31 - Documentation/hwmon/tmp102.rst | 31 + Documentation/hwmon/tmp103 | 33 - Documentation/hwmon/tmp103.rst | 33 + Documentation/hwmon/tmp108 | 41 - Documentation/hwmon/tmp108.rst | 41 + Documentation/hwmon/tmp401 | 93 -- Documentation/hwmon/tmp401.rst | 93 ++ Documentation/hwmon/tmp421 | 66 -- Documentation/hwmon/tmp421.rst | 66 ++ Documentation/hwmon/tps40422 | 73 -- Documentation/hwmon/tps40422.rst | 73 ++ Documentation/hwmon/twl4030-madc-hwmon | 49 - Documentation/hwmon/twl4030-madc-hwmon.rst | 49 + Documentation/hwmon/ucd9000 | 129 --- Documentation/hwmon/ucd9000.rst | 129 +++ Documentation/hwmon/ucd9200 | 124 --- Documentation/hwmon/ucd9200.rst | 124 +++ Documentation/hwmon/userspace-tools | 43 - Documentation/hwmon/userspace-tools.rst | 43 + Documentation/hwmon/vexpress | 41 - Documentation/hwmon/vexpress.rst | 41 + Documentation/hwmon/via686a | 84 -- Documentation/hwmon/via686a.rst | 84 ++ Documentation/hwmon/vt1211 | 226 ----- Documentation/hwmon/vt1211.rst | 226 +++++ Documentation/hwmon/w83627ehf | 248 ----- Documentation/hwmon/w83627ehf.rst | 248 +++++ Documentation/hwmon/w83627hf | 124 --- Documentation/hwmon/w83627hf.rst | 124 +++ Documentation/hwmon/w83773g | 35 - Documentation/hwmon/w83773g.rst | 35 + Documentation/hwmon/w83781d | 513 ---------- Documentation/hwmon/w83781d.rst | 513 ++++++++++ Documentation/hwmon/w83791d | 180 ---- Documentation/hwmon/w83791d.rst | 180 ++++ Documentation/hwmon/w83792d | 199 ---- Documentation/hwmon/w83792d.rst | 199 ++++ Documentation/hwmon/w83793 | 113 --- Documentation/hwmon/w83793.rst | 113 +++ Documentation/hwmon/w83795 | 142 --- Documentation/hwmon/w83795.rst | 142 +++ Documentation/hwmon/w83l785ts | 45 - Documentation/hwmon/w83l785ts.rst | 45 + Documentation/hwmon/w83l786ng | 66 -- Documentation/hwmon/w83l786ng.rst | 66 ++ Documentation/hwmon/wm831x | 40 - Documentation/hwmon/wm831x.rst | 40 + Documentation/hwmon/wm8350 | 30 - Documentation/hwmon/wm8350.rst | 30 + Documentation/hwmon/xgene-hwmon | 36 - Documentation/hwmon/xgene-hwmon.rst | 36 + Documentation/hwmon/zl6100 | 213 ----- Documentation/hwmon/zl6100.rst | 213 +++++ Documentation/index.rst | 1 + Documentation/thermal/sysfs-api.txt | 2 +- MAINTAINERS | 108 +-- drivers/hwmon/Kconfig | 8 +- drivers/hwmon/ads7828.c | 2 +- drivers/hwmon/max197.c | 2 +- drivers/hwmon/sht15.c | 2 +- include/linux/platform_data/ads7828.h | 2 +- include/linux/platform_data/ds620.h | 2 +- include/linux/platform_data/ina2xx.h | 2 +- include/linux/platform_data/max197.h | 2 +- include/linux/platform_data/ntc_thermistor.h | 2 +- 332 files changed, 18129 insertions(+), 17956 deletions(-) delete mode 100644 Documentation/hwmon/ab8500 create mode 100644 Documentation/hwmon/ab8500.rst delete mode 100644 Documentation/hwmon/abituguru delete mode 100644 Documentation/hwmon/abituguru-datasheet create mode 100644 Documentation/hwmon/abituguru-datasheet.rst create mode 100644 Documentation/hwmon/abituguru.rst delete mode 100644 Documentation/hwmon/abituguru3 create mode 100644 Documentation/hwmon/abituguru3.rst delete mode 100644 Documentation/hwmon/abx500 create mode 100644 Documentation/hwmon/abx500.rst delete mode 100644 Documentation/hwmon/acpi_power_meter create mode 100644 Documentation/hwmon/acpi_power_meter.rst delete mode 100644 Documentation/hwmon/ad7314 create mode 100644 Documentation/hwmon/ad7314.rst delete mode 100644 Documentation/hwmon/adc128d818 create mode 100644 Documentation/hwmon/adc128d818.rst delete mode 100644 Documentation/hwmon/adm1021 create mode 100644 Documentation/hwmon/adm1021.rst delete mode 100644 Documentation/hwmon/adm1025 create mode 100644 Documentation/hwmon/adm1025.rst delete mode 100644 Documentation/hwmon/adm1026 create mode 100644 Documentation/hwmon/adm1026.rst delete mode 100644 Documentation/hwmon/adm1031 create mode 100644 Documentation/hwmon/adm1031.rst delete mode 100644 Documentation/hwmon/adm1275 create mode 100644 Documentation/hwmon/adm1275.rst delete mode 100644 Documentation/hwmon/adm9240 create mode 100644 Documentation/hwmon/adm9240.rst delete mode 100644 Documentation/hwmon/ads1015 create mode 100644 Documentation/hwmon/ads1015.rst delete mode 100644 Documentation/hwmon/ads7828 create mode 100644 Documentation/hwmon/ads7828.rst delete mode 100644 Documentation/hwmon/adt7410 create mode 100644 Documentation/hwmon/adt7410.rst delete mode 100644 Documentation/hwmon/adt7411 create mode 100644 Documentation/hwmon/adt7411.rst delete mode 100644 Documentation/hwmon/adt7462 create mode 100644 Documentation/hwmon/adt7462.rst delete mode 100644 Documentation/hwmon/adt7470 create mode 100644 Documentation/hwmon/adt7470.rst delete mode 100644 Documentation/hwmon/adt7475 create mode 100644 Documentation/hwmon/adt7475.rst delete mode 100644 Documentation/hwmon/amc6821 create mode 100644 Documentation/hwmon/amc6821.rst delete mode 100644 Documentation/hwmon/asb100 create mode 100644 Documentation/hwmon/asb100.rst delete mode 100644 Documentation/hwmon/asc7621 create mode 100644 Documentation/hwmon/asc7621.rst delete mode 100644 Documentation/hwmon/aspeed-pwm-tacho create mode 100644 Documentation/hwmon/aspeed-pwm-tacho.rst delete mode 100644 Documentation/hwmon/coretemp create mode 100644 Documentation/hwmon/coretemp.rst delete mode 100644 Documentation/hwmon/da9052 create mode 100644 Documentation/hwmon/da9052.rst delete mode 100644 Documentation/hwmon/da9055 create mode 100644 Documentation/hwmon/da9055.rst delete mode 100644 Documentation/hwmon/dme1737 create mode 100644 Documentation/hwmon/dme1737.rst delete mode 100644 Documentation/hwmon/ds1621 create mode 100644 Documentation/hwmon/ds1621.rst delete mode 100644 Documentation/hwmon/ds620 create mode 100644 Documentation/hwmon/ds620.rst delete mode 100644 Documentation/hwmon/emc1403 create mode 100644 Documentation/hwmon/emc1403.rst delete mode 100644 Documentation/hwmon/emc2103 create mode 100644 Documentation/hwmon/emc2103.rst delete mode 100644 Documentation/hwmon/emc6w201 create mode 100644 Documentation/hwmon/emc6w201.rst delete mode 100644 Documentation/hwmon/f71805f create mode 100644 Documentation/hwmon/f71805f.rst delete mode 100644 Documentation/hwmon/f71882fg create mode 100644 Documentation/hwmon/f71882fg.rst delete mode 100644 Documentation/hwmon/fam15h_power create mode 100644 Documentation/hwmon/fam15h_power.rst delete mode 100644 Documentation/hwmon/ftsteutates create mode 100644 Documentation/hwmon/ftsteutates.rst delete mode 100644 Documentation/hwmon/g760a create mode 100644 Documentation/hwmon/g760a.rst delete mode 100644 Documentation/hwmon/g762 create mode 100644 Documentation/hwmon/g762.rst delete mode 100644 Documentation/hwmon/gl518sm create mode 100644 Documentation/hwmon/gl518sm.rst delete mode 100644 Documentation/hwmon/hih6130 create mode 100644 Documentation/hwmon/hih6130.rst create mode 100644 Documentation/hwmon/hwmon-kernel-api.rst delete mode 100644 Documentation/hwmon/hwmon-kernel-api.txt delete mode 100644 Documentation/hwmon/ibm-cffps create mode 100644 Documentation/hwmon/ibm-cffps.rst delete mode 100644 Documentation/hwmon/ibmaem create mode 100644 Documentation/hwmon/ibmaem.rst delete mode 100644 Documentation/hwmon/ibmpowernv create mode 100644 Documentation/hwmon/ibmpowernv.rst delete mode 100644 Documentation/hwmon/ina209 create mode 100644 Documentation/hwmon/ina209.rst delete mode 100644 Documentation/hwmon/ina2xx create mode 100644 Documentation/hwmon/ina2xx.rst delete mode 100644 Documentation/hwmon/ina3221 create mode 100644 Documentation/hwmon/ina3221.rst create mode 100644 Documentation/hwmon/index.rst delete mode 100644 Documentation/hwmon/ir35221 create mode 100644 Documentation/hwmon/ir35221.rst delete mode 100644 Documentation/hwmon/it87 create mode 100644 Documentation/hwmon/it87.rst delete mode 100644 Documentation/hwmon/jc42 create mode 100644 Documentation/hwmon/jc42.rst delete mode 100644 Documentation/hwmon/k10temp create mode 100644 Documentation/hwmon/k10temp.rst delete mode 100644 Documentation/hwmon/k8temp create mode 100644 Documentation/hwmon/k8temp.rst delete mode 100644 Documentation/hwmon/lineage-pem create mode 100644 Documentation/hwmon/lineage-pem.rst delete mode 100644 Documentation/hwmon/lm25066 create mode 100644 Documentation/hwmon/lm25066.rst delete mode 100644 Documentation/hwmon/lm63 create mode 100644 Documentation/hwmon/lm63.rst delete mode 100644 Documentation/hwmon/lm70 create mode 100644 Documentation/hwmon/lm70.rst delete mode 100644 Documentation/hwmon/lm73 create mode 100644 Documentation/hwmon/lm73.rst delete mode 100644 Documentation/hwmon/lm75 create mode 100644 Documentation/hwmon/lm75.rst delete mode 100644 Documentation/hwmon/lm77 create mode 100644 Documentation/hwmon/lm77.rst delete mode 100644 Documentation/hwmon/lm78 create mode 100644 Documentation/hwmon/lm78.rst delete mode 100644 Documentation/hwmon/lm80 create mode 100644 Documentation/hwmon/lm80.rst delete mode 100644 Documentation/hwmon/lm83 create mode 100644 Documentation/hwmon/lm83.rst delete mode 100644 Documentation/hwmon/lm85 create mode 100644 Documentation/hwmon/lm85.rst delete mode 100644 Documentation/hwmon/lm87 create mode 100644 Documentation/hwmon/lm87.rst delete mode 100644 Documentation/hwmon/lm90 create mode 100644 Documentation/hwmon/lm90.rst delete mode 100644 Documentation/hwmon/lm92 create mode 100644 Documentation/hwmon/lm92.rst delete mode 100644 Documentation/hwmon/lm93 create mode 100644 Documentation/hwmon/lm93.rst delete mode 100644 Documentation/hwmon/lm95234 create mode 100644 Documentation/hwmon/lm95234.rst delete mode 100644 Documentation/hwmon/lm95245 create mode 100644 Documentation/hwmon/lm95245.rst delete mode 100644 Documentation/hwmon/ltc2945 create mode 100644 Documentation/hwmon/ltc2945.rst delete mode 100644 Documentation/hwmon/ltc2978 create mode 100644 Documentation/hwmon/ltc2978.rst delete mode 100644 Documentation/hwmon/ltc2990 create mode 100644 Documentation/hwmon/ltc2990.rst delete mode 100644 Documentation/hwmon/ltc3815 create mode 100644 Documentation/hwmon/ltc3815.rst delete mode 100644 Documentation/hwmon/ltc4151 create mode 100644 Documentation/hwmon/ltc4151.rst delete mode 100644 Documentation/hwmon/ltc4215 create mode 100644 Documentation/hwmon/ltc4215.rst delete mode 100644 Documentation/hwmon/ltc4245 create mode 100644 Documentation/hwmon/ltc4245.rst delete mode 100644 Documentation/hwmon/ltc4260 create mode 100644 Documentation/hwmon/ltc4260.rst delete mode 100644 Documentation/hwmon/ltc4261 create mode 100644 Documentation/hwmon/ltc4261.rst delete mode 100644 Documentation/hwmon/max16064 create mode 100644 Documentation/hwmon/max16064.rst delete mode 100644 Documentation/hwmon/max16065 create mode 100644 Documentation/hwmon/max16065.rst delete mode 100644 Documentation/hwmon/max1619 create mode 100644 Documentation/hwmon/max1619.rst delete mode 100644 Documentation/hwmon/max1668 create mode 100644 Documentation/hwmon/max1668.rst delete mode 100644 Documentation/hwmon/max197 create mode 100644 Documentation/hwmon/max197.rst delete mode 100644 Documentation/hwmon/max20751 create mode 100644 Documentation/hwmon/max20751.rst delete mode 100644 Documentation/hwmon/max31722 create mode 100644 Documentation/hwmon/max31722.rst delete mode 100644 Documentation/hwmon/max31785 create mode 100644 Documentation/hwmon/max31785.rst delete mode 100644 Documentation/hwmon/max31790 create mode 100644 Documentation/hwmon/max31790.rst delete mode 100644 Documentation/hwmon/max34440 create mode 100644 Documentation/hwmon/max34440.rst delete mode 100644 Documentation/hwmon/max6639 create mode 100644 Documentation/hwmon/max6639.rst delete mode 100644 Documentation/hwmon/max6642 create mode 100644 Documentation/hwmon/max6642.rst delete mode 100644 Documentation/hwmon/max6650 create mode 100644 Documentation/hwmon/max6650.rst delete mode 100644 Documentation/hwmon/max6697 create mode 100644 Documentation/hwmon/max6697.rst delete mode 100644 Documentation/hwmon/max8688 create mode 100644 Documentation/hwmon/max8688.rst delete mode 100644 Documentation/hwmon/mc13783-adc create mode 100644 Documentation/hwmon/mc13783-adc.rst delete mode 100644 Documentation/hwmon/mcp3021 create mode 100644 Documentation/hwmon/mcp3021.rst delete mode 100644 Documentation/hwmon/menf21bmc create mode 100644 Documentation/hwmon/menf21bmc.rst delete mode 100644 Documentation/hwmon/mlxreg-fan create mode 100644 Documentation/hwmon/mlxreg-fan.rst delete mode 100644 Documentation/hwmon/nct6683 create mode 100644 Documentation/hwmon/nct6683.rst delete mode 100644 Documentation/hwmon/nct6775 create mode 100644 Documentation/hwmon/nct6775.rst delete mode 100644 Documentation/hwmon/nct7802 create mode 100644 Documentation/hwmon/nct7802.rst delete mode 100644 Documentation/hwmon/nct7904 create mode 100644 Documentation/hwmon/nct7904.rst delete mode 100644 Documentation/hwmon/npcm750-pwm-fan create mode 100644 Documentation/hwmon/npcm750-pwm-fan.rst delete mode 100644 Documentation/hwmon/nsa320 create mode 100644 Documentation/hwmon/nsa320.rst delete mode 100644 Documentation/hwmon/ntc_thermistor create mode 100644 Documentation/hwmon/ntc_thermistor.rst delete mode 100644 Documentation/hwmon/occ create mode 100644 Documentation/hwmon/occ.rst delete mode 100644 Documentation/hwmon/pc87360 create mode 100644 Documentation/hwmon/pc87360.rst delete mode 100644 Documentation/hwmon/pc87427 create mode 100644 Documentation/hwmon/pc87427.rst delete mode 100644 Documentation/hwmon/pcf8591 create mode 100644 Documentation/hwmon/pcf8591.rst delete mode 100644 Documentation/hwmon/pmbus delete mode 100644 Documentation/hwmon/pmbus-core create mode 100644 Documentation/hwmon/pmbus-core.rst create mode 100644 Documentation/hwmon/pmbus.rst delete mode 100644 Documentation/hwmon/powr1220 create mode 100644 Documentation/hwmon/powr1220.rst delete mode 100644 Documentation/hwmon/pwm-fan create mode 100644 Documentation/hwmon/pwm-fan.rst delete mode 100644 Documentation/hwmon/raspberrypi-hwmon create mode 100644 Documentation/hwmon/raspberrypi-hwmon.rst delete mode 100644 Documentation/hwmon/sch5627 create mode 100644 Documentation/hwmon/sch5627.rst delete mode 100644 Documentation/hwmon/sch5636 create mode 100644 Documentation/hwmon/sch5636.rst delete mode 100644 Documentation/hwmon/scpi-hwmon create mode 100644 Documentation/hwmon/scpi-hwmon.rst delete mode 100644 Documentation/hwmon/sht15 create mode 100644 Documentation/hwmon/sht15.rst delete mode 100644 Documentation/hwmon/sht21 create mode 100644 Documentation/hwmon/sht21.rst delete mode 100644 Documentation/hwmon/sht3x create mode 100644 Documentation/hwmon/sht3x.rst delete mode 100644 Documentation/hwmon/shtc1 create mode 100644 Documentation/hwmon/shtc1.rst delete mode 100644 Documentation/hwmon/sis5595 create mode 100644 Documentation/hwmon/sis5595.rst delete mode 100644 Documentation/hwmon/smm665 create mode 100644 Documentation/hwmon/smm665.rst delete mode 100644 Documentation/hwmon/smsc47b397 create mode 100644 Documentation/hwmon/smsc47b397.rst delete mode 100644 Documentation/hwmon/smsc47m1 create mode 100644 Documentation/hwmon/smsc47m1.rst delete mode 100644 Documentation/hwmon/smsc47m192 create mode 100644 Documentation/hwmon/smsc47m192.rst delete mode 100644 Documentation/hwmon/submitting-patches create mode 100644 Documentation/hwmon/submitting-patches.rst delete mode 100644 Documentation/hwmon/sysfs-interface create mode 100644 Documentation/hwmon/sysfs-interface.rst delete mode 100644 Documentation/hwmon/tc654 create mode 100644 Documentation/hwmon/tc654.rst delete mode 100644 Documentation/hwmon/tc74 create mode 100644 Documentation/hwmon/tc74.rst delete mode 100644 Documentation/hwmon/thmc50 create mode 100644 Documentation/hwmon/thmc50.rst delete mode 100644 Documentation/hwmon/tmp102 create mode 100644 Documentation/hwmon/tmp102.rst delete mode 100644 Documentation/hwmon/tmp103 create mode 100644 Documentation/hwmon/tmp103.rst delete mode 100644 Documentation/hwmon/tmp108 create mode 100644 Documentation/hwmon/tmp108.rst delete mode 100644 Documentation/hwmon/tmp401 create mode 100644 Documentation/hwmon/tmp401.rst delete mode 100644 Documentation/hwmon/tmp421 create mode 100644 Documentation/hwmon/tmp421.rst delete mode 100644 Documentation/hwmon/tps40422 create mode 100644 Documentation/hwmon/tps40422.rst delete mode 100644 Documentation/hwmon/twl4030-madc-hwmon create mode 100644 Documentation/hwmon/twl4030-madc-hwmon.rst delete mode 100644 Documentation/hwmon/ucd9000 create mode 100644 Documentation/hwmon/ucd9000.rst delete mode 100644 Documentation/hwmon/ucd9200 create mode 100644 Documentation/hwmon/ucd9200.rst delete mode 100644 Documentation/hwmon/userspace-tools create mode 100644 Documentation/hwmon/userspace-tools.rst delete mode 100644 Documentation/hwmon/vexpress create mode 100644 Documentation/hwmon/vexpress.rst delete mode 100644 Documentation/hwmon/via686a create mode 100644 Documentation/hwmon/via686a.rst delete mode 100644 Documentation/hwmon/vt1211 create mode 100644 Documentation/hwmon/vt1211.rst delete mode 100644 Documentation/hwmon/w83627ehf create mode 100644 Documentation/hwmon/w83627ehf.rst delete mode 100644 Documentation/hwmon/w83627hf create mode 100644 Documentation/hwmon/w83627hf.rst delete mode 100644 Documentation/hwmon/w83773g create mode 100644 Documentation/hwmon/w83773g.rst delete mode 100644 Documentation/hwmon/w83781d create mode 100644 Documentation/hwmon/w83781d.rst delete mode 100644 Documentation/hwmon/w83791d create mode 100644 Documentation/hwmon/w83791d.rst delete mode 100644 Documentation/hwmon/w83792d create mode 100644 Documentation/hwmon/w83792d.rst delete mode 100644 Documentation/hwmon/w83793 create mode 100644 Documentation/hwmon/w83793.rst delete mode 100644 Documentation/hwmon/w83795 create mode 100644 Documentation/hwmon/w83795.rst delete mode 100644 Documentation/hwmon/w83l785ts create mode 100644 Documentation/hwmon/w83l785ts.rst delete mode 100644 Documentation/hwmon/w83l786ng create mode 100644 Documentation/hwmon/w83l786ng.rst delete mode 100644 Documentation/hwmon/wm831x create mode 100644 Documentation/hwmon/wm831x.rst delete mode 100644 Documentation/hwmon/wm8350 create mode 100644 Documentation/hwmon/wm8350.rst delete mode 100644 Documentation/hwmon/xgene-hwmon create mode 100644 Documentation/hwmon/xgene-hwmon.rst delete mode 100644 Documentation/hwmon/zl6100 create mode 100644 Documentation/hwmon/zl6100.rst (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/hwmon/g762.txt b/Documentation/devicetree/bindings/hwmon/g762.txt index 25cc6d8ee575..6d154c4923de 100644 --- a/Documentation/devicetree/bindings/hwmon/g762.txt +++ b/Documentation/devicetree/bindings/hwmon/g762.txt @@ -21,7 +21,7 @@ If an optional property is not set in .dts file, then current value is kept unmodified (e.g. u-boot installed value). Additional information on operational parameters for the device is available -in Documentation/hwmon/g762. A detailed datasheet for the device is available +in Documentation/hwmon/g762.rst. A detailed datasheet for the device is available at http://natisbad.org/NAS/refs/GMT_EDS-762_763-080710-0.2.pdf. Example g762 node: diff --git a/Documentation/hwmon/ab8500 b/Documentation/hwmon/ab8500 deleted file mode 100644 index d87c61151239..000000000000 --- a/Documentation/hwmon/ab8500 +++ /dev/null @@ -1,26 +0,0 @@ -Kernel driver ab8500 -==================== - -Supported chips: - - * ST-Ericsson AB8500 - - Prefix: 'ab8500' - - Addresses scanned: - - - Datasheet: http://www.stericsson.com/developers/documentation.jsp - -Authors: - - Martin Persson - - Hongbo Zhang - -Description ------------ - -See also Documentation/hwmon/abx500. This is the ST-Ericsson AB8500 specific -driver. - -Currently only the AB8500 internal sensor and one external sensor for battery -temperature are monitored. Other GPADC channels can also be monitored if needed -in future. diff --git a/Documentation/hwmon/ab8500.rst b/Documentation/hwmon/ab8500.rst new file mode 100644 index 000000000000..33f93a9cec04 --- /dev/null +++ b/Documentation/hwmon/ab8500.rst @@ -0,0 +1,26 @@ +Kernel driver ab8500 +==================== + +Supported chips: + + * ST-Ericsson AB8500 + + Prefix: 'ab8500' + + Addresses scanned: - + + Datasheet: http://www.stericsson.com/developers/documentation.jsp + +Authors: + - Martin Persson + - Hongbo Zhang + +Description +----------- + +See also Documentation/hwmon/abx500.rst. This is the ST-Ericsson AB8500 specific +driver. + +Currently only the AB8500 internal sensor and one external sensor for battery +temperature are monitored. Other GPADC channels can also be monitored if needed +in future. diff --git a/Documentation/hwmon/abituguru b/Documentation/hwmon/abituguru deleted file mode 100644 index d8243c827de9..000000000000 --- a/Documentation/hwmon/abituguru +++ /dev/null @@ -1,113 +0,0 @@ -Kernel driver abituguru -======================= - -Supported chips: - - * Abit uGuru revision 1 & 2 (Hardware Monitor part only) - - Prefix: 'abituguru' - - Addresses scanned: ISA 0x0E0 - - Datasheet: Not available, this driver is based on reverse engineering. - A "Datasheet" has been written based on the reverse engineering it - should be available in the same dir as this file under the name - abituguru-datasheet. - - Note: - The uGuru is a microcontroller with onboard firmware which programs - it to behave as a hwmon IC. There are many different revisions of the - firmware and thus effectivly many different revisions of the uGuru. - Below is an incomplete list with which revisions are used for which - Motherboards: - - - uGuru 1.00 ~ 1.24 (AI7, KV8-MAX3, AN7) [1]_ - - uGuru 2.0.0.0 ~ 2.0.4.2 (KV8-PRO) - - uGuru 2.1.0.0 ~ 2.1.2.8 (AS8, AV8, AA8, AG8, AA8XE, AX8) - - uGuru 2.2.0.0 ~ 2.2.0.6 (AA8 Fatal1ty) - - uGuru 2.3.0.0 ~ 2.3.0.9 (AN8) - - uGuru 3.0.0.0 ~ 3.0.x.x (AW8, AL8, AT8, NI8 SLI, AT8 32X, AN8 32X, - AW9D-MAX) [2]_ - -.. [1] For revisions 2 and 3 uGuru's the driver can autodetect the - sensortype (Volt or Temp) for bank1 sensors, for revision 1 uGuru's - this does not always work. For these uGuru's the autodetection can - be overridden with the bank1_types module param. For all 3 known - revison 1 motherboards the correct use of this param is: - bank1_types=1,1,0,0,0,0,0,2,0,0,0,0,2,0,0,1 - You may also need to specify the fan_sensors option for these boards - fan_sensors=5 - -.. [2] There is a separate abituguru3 driver for these motherboards, - the abituguru (without the 3 !) driver will not work on these - motherboards (and visa versa)! - -Authors: - - Hans de Goede , - - (Initial reverse engineering done by Olle Sandberg - ) - - -Module Parameters ------------------ - -* force: bool - Force detection. Note this parameter only causes the - detection to be skipped, and thus the insmod to - succeed. If the uGuru can't be read the actual hwmon - driver will not load and thus no hwmon device will get - registered. -* bank1_types: int[] - Bank1 sensortype autodetection override: - - * -1 autodetect (default) - * 0 volt sensor - * 1 temp sensor - * 2 not connected -* fan_sensors: int - Tell the driver how many fan speed sensors there are - on your motherboard. Default: 0 (autodetect). -* pwms: int - Tell the driver how many fan speed controls (fan - pwms) your motherboard has. Default: 0 (autodetect). -* verbose: int - How verbose should the driver be? (0-3): - - * 0 normal output - * 1 + verbose error reporting - * 2 + sensors type probing info (default) - * 3 + retryable error reporting - - Default: 2 (the driver is still in the testing phase) - -Notice: if you need any of the first three options above please insmod the -driver with verbose set to 3 and mail me the output of: -dmesg | grep abituguru - - -Description ------------ - -This driver supports the hardware monitoring features of the first and -second revision of the Abit uGuru chip found on Abit uGuru featuring -motherboards (most modern Abit motherboards). - -The first and second revision of the uGuru chip in reality is a Winbond -W83L950D in disguise (despite Abit claiming it is "a new microprocessor -designed by the ABIT Engineers"). Unfortunately this doesn't help since the -W83L950D is a generic microcontroller with a custom Abit application running -on it. - -Despite Abit not releasing any information regarding the uGuru, Olle -Sandberg has managed to reverse engineer the sensor part -of the uGuru. Without his work this driver would not have been possible. - -Known Issues ------------- - -The voltage and frequency control parts of the Abit uGuru are not supported. - -.. toctree:: - :maxdepth: 1 - - abituguru-datasheet.rst diff --git a/Documentation/hwmon/abituguru-datasheet b/Documentation/hwmon/abituguru-datasheet deleted file mode 100644 index 6d5253e2223b..000000000000 --- a/Documentation/hwmon/abituguru-datasheet +++ /dev/null @@ -1,336 +0,0 @@ -=============== -uGuru datasheet -=============== - -First of all, what I know about uGuru is no fact based on any help, hints or -datasheet from Abit. The data I have got on uGuru have I assembled through -my weak knowledge in "backwards engineering". -And just for the record, you may have noticed uGuru isn't a chip developed by -Abit, as they claim it to be. It's really just an microprocessor (uC) created by -Winbond (W83L950D). And no, reading the manual for this specific uC or -mailing Windbond for help won't give any useful data about uGuru, as it is -the program inside the uC that is responding to calls. - -Olle Sandberg , 2005-05-25 - - -Original version by Olle Sandberg who did the heavy lifting of the initial -reverse engineering. This version has been almost fully rewritten for clarity -and extended with write support and info on more databanks, the write support -is once again reverse engineered by Olle the additional databanks have been -reverse engineered by me. I would like to express my thanks to Olle, this -document and the Linux driver could not have been written without his efforts. - -Note: because of the lack of specs only the sensors part of the uGuru is -described here and not the CPU / RAM / etc voltage & frequency control. - -Hans de Goede , 28-01-2006 - - -Detection -========= - -As far as known the uGuru is always placed at and using the (ISA) I/O-ports -0xE0 and 0xE4, so we don't have to scan any port-range, just check what the two -ports are holding for detection. We will refer to 0xE0 as CMD (command-port) -and 0xE4 as DATA because Abit refers to them with these names. - -If DATA holds 0x00 or 0x08 and CMD holds 0x00 or 0xAC an uGuru could be -present. We have to check for two different values at data-port, because -after a reboot uGuru will hold 0x00 here, but if the driver is removed and -later on attached again data-port will hold 0x08, more about this later. - -After wider testing of the Linux kernel driver some variants of the uGuru have -turned up which will hold 0x00 instead of 0xAC at the CMD port, thus we also -have to test CMD for two different values. On these uGuru's DATA will initially -hold 0x09 and will only hold 0x08 after reading CMD first, so CMD must be read -first! - -To be really sure an uGuru is present a test read of one or more register -sets should be done. - - -Reading / Writing -================= - -Addressing ----------- - -The uGuru has a number of different addressing levels. The first addressing -level we will call banks. A bank holds data for one or more sensors. The data -in a bank for a sensor is one or more bytes large. - -The number of bytes is fixed for a given bank, you should always read or write -that many bytes, reading / writing more will fail, the results when writing -less then the number of bytes for a given bank are undetermined. - -See below for all known bank addresses, numbers of sensors in that bank, -number of bytes data per sensor and contents/meaning of those bytes. - -Although both this document and the kernel driver have kept the sensor -terminoligy for the addressing within a bank this is not 100% correct, in -bank 0x24 for example the addressing within the bank selects a PWM output not -a sensor. - -Notice that some banks have both a read and a write address this is how the -uGuru determines if a read from or a write to the bank is taking place, thus -when reading you should always use the read address and when writing the -write address. The write address is always one (1) more than the read address. - - -uGuru ready ------------ - -Before you can read from or write to the uGuru you must first put the uGuru -in "ready" mode. - -To put the uGuru in ready mode first write 0x00 to DATA and then wait for DATA -to hold 0x09, DATA should read 0x09 within 250 read cycles. - -Next CMD _must_ be read and should hold 0xAC, usually CMD will hold 0xAC the -first read but sometimes it takes a while before CMD holds 0xAC and thus it -has to be read a number of times (max 50). - -After reading CMD, DATA should hold 0x08 which means that the uGuru is ready -for input. As above DATA will usually hold 0x08 the first read but not always. -This step can be skipped, but it is undetermined what happens if the uGuru has -not yet reported 0x08 at DATA and you proceed with writing a bank address. - - -Sending bank and sensor addresses to the uGuru ----------------------------------------------- - -First the uGuru must be in "ready" mode as described above, DATA should hold -0x08 indicating that the uGuru wants input, in this case the bank address. - -Next write the bank address to DATA. After the bank address has been written -wait for to DATA to hold 0x08 again indicating that it wants / is ready for -more input (max 250 reads). - -Once DATA holds 0x08 again write the sensor address to CMD. - - -Reading -------- - -First send the bank and sensor addresses as described above. -Then for each byte of data you want to read wait for DATA to hold 0x01 -which indicates that the uGuru is ready to be read (max 250 reads) and once -DATA holds 0x01 read the byte from CMD. - -Once all bytes have been read data will hold 0x09, but there is no reason to -test for this. Notice that the number of bytes is bank address dependent see -above and below. - -After completing a successful read it is advised to put the uGuru back in -ready mode, so that it is ready for the next read / write cycle. This way -if your program / driver is unloaded and later loaded again the detection -algorithm described above will still work. - - - -Writing -------- - -First send the bank and sensor addresses as described above. -Then for each byte of data you want to write wait for DATA to hold 0x00 -which indicates that the uGuru is ready to be written (max 250 reads) and -once DATA holds 0x00 write the byte to CMD. - -Once all bytes have been written wait for DATA to hold 0x01 (max 250 reads) -don't ask why this is the way it is. - -Once DATA holds 0x01 read CMD it should hold 0xAC now. - -After completing a successful write it is advised to put the uGuru back in -ready mode, so that it is ready for the next read / write cycle. This way -if your program / driver is unloaded and later loaded again the detection -algorithm described above will still work. - - -Gotchas -------- - -After wider testing of the Linux kernel driver some variants of the uGuru have -turned up which do not hold 0x08 at DATA within 250 reads after writing the -bank address. With these versions this happens quite frequent, using larger -timeouts doesn't help, they just go offline for a second or 2, doing some -internal callibration or whatever. Your code should be prepared to handle -this and in case of no response in this specific case just goto sleep for a -while and then retry. - - -Address Map -=========== - -Bank 0x20 Alarms (R) --------------------- -This bank contains 0 sensors, iow the sensor address is ignored (but must be -written) just use 0. Bank 0x20 contains 3 bytes: - -Byte 0: - This byte holds the alarm flags for sensor 0-7 of Sensor Bank1, with bit 0 - corresponding to sensor 0, 1 to 1, etc. - -Byte 1: - This byte holds the alarm flags for sensor 8-15 of Sensor Bank1, with bit 0 - corresponding to sensor 8, 1 to 9, etc. - -Byte 2: - This byte holds the alarm flags for sensor 0-5 of Sensor Bank2, with bit 0 - corresponding to sensor 0, 1 to 1, etc. - - -Bank 0x21 Sensor Bank1 Values / Readings (R) --------------------------------------------- -This bank contains 16 sensors, for each sensor it contains 1 byte. -So far the following sensors are known to be available on all motherboards: - -- Sensor 0 CPU temp -- Sensor 1 SYS temp -- Sensor 3 CPU core volt -- Sensor 4 DDR volt -- Sensor 10 DDR Vtt volt -- Sensor 15 PWM temp - -Byte 0: - This byte holds the reading from the sensor. Sensors in Bank1 can be both - volt and temp sensors, this is motherboard specific. The uGuru however does - seem to know (be programmed with) what kindoff sensor is attached see Sensor - Bank1 Settings description. - -Volt sensors use a linear scale, a reading 0 corresponds with 0 volt and a -reading of 255 with 3494 mV. The sensors for higher voltages however are -connected through a division circuit. The currently known division circuits -in use result in ranges of: 0-4361mV, 0-6248mV or 0-14510mV. 3.3 volt sources -use the 0-4361mV range, 5 volt the 0-6248mV and 12 volt the 0-14510mV . - -Temp sensors also use a linear scale, a reading of 0 corresponds with 0 degree -Celsius and a reading of 255 with a reading of 255 degrees Celsius. - - -Bank 0x22 Sensor Bank1 Settings (R) and Bank 0x23 Sensor Bank1 Settings (W) ---------------------------------------------------------------------------- - -Those banks contain 16 sensors, for each sensor it contains 3 bytes. Each -set of 3 bytes contains the settings for the sensor with the same sensor -address in Bank 0x21 . - -Byte 0: - Alarm behaviour for the selected sensor. A 1 enables the described - behaviour. - -Bit 0: - Give an alarm if measured temp is over the warning threshold (RW) [1]_ - -Bit 1: - Give an alarm if measured volt is over the max threshold (RW) [2]_ - -Bit 2: - Give an alarm if measured volt is under the min threshold (RW) [2]_ - -Bit 3: - Beep if alarm (RW) - -Bit 4: - 1 if alarm cause measured temp is over the warning threshold (R) - -Bit 5: - 1 if alarm cause measured volt is over the max threshold (R) - -Bit 6: - 1 if alarm cause measured volt is under the min threshold (R) - -Bit 7: - - Volt sensor: Shutdown if alarm persist for more than 4 seconds (RW) - - Temp sensor: Shutdown if temp is over the shutdown threshold (RW) - -.. [1] This bit is only honored/used by the uGuru if a temp sensor is connected - -.. [2] This bit is only honored/used by the uGuru if a volt sensor is connected - Note with some trickery this can be used to find out what kinda sensor - is detected see the Linux kernel driver for an example with many - comments on how todo this. - -Byte 1: - - Temp sensor: warning threshold (scale as bank 0x21) - - Volt sensor: min threshold (scale as bank 0x21) - -Byte 2: - - Temp sensor: shutdown threshold (scale as bank 0x21) - - Volt sensor: max threshold (scale as bank 0x21) - - -Bank 0x24 PWM outputs for FAN's (R) and Bank 0x25 PWM outputs for FAN's (W) ---------------------------------------------------------------------------- - -Those banks contain 3 "sensors", for each sensor it contains 5 bytes. - - Sensor 0 usually controls the CPU fan - - Sensor 1 usually controls the NB (or chipset for single chip) fan - - Sensor 2 usually controls the System fan - -Byte 0: - Flag 0x80 to enable control, Fan runs at 100% when disabled. - low nibble (temp)sensor address at bank 0x21 used for control. - -Byte 1: - 0-255 = 0-12v (linear), specify voltage at which fan will rotate when under - low threshold temp (specified in byte 3) - -Byte 2: - 0-255 = 0-12v (linear), specify voltage at which fan will rotate when above - high threshold temp (specified in byte 4) - -Byte 3: - Low threshold temp (scale as bank 0x21) - -byte 4: - High threshold temp (scale as bank 0x21) - - -Bank 0x26 Sensors Bank2 Values / Readings (R) ---------------------------------------------- - -This bank contains 6 sensors (AFAIK), for each sensor it contains 1 byte. - -So far the following sensors are known to be available on all motherboards: - - Sensor 0: CPU fan speed - - Sensor 1: NB (or chipset for single chip) fan speed - - Sensor 2: SYS fan speed - -Byte 0: - This byte holds the reading from the sensor. 0-255 = 0-15300 (linear) - - -Bank 0x27 Sensors Bank2 Settings (R) and Bank 0x28 Sensors Bank2 Settings (W) ------------------------------------------------------------------------------ - -Those banks contain 6 sensors (AFAIK), for each sensor it contains 2 bytes. - -Byte 0: - Alarm behaviour for the selected sensor. A 1 enables the described behaviour. - -Bit 0: - Give an alarm if measured rpm is under the min threshold (RW) - -Bit 3: - Beep if alarm (RW) - -Bit 7: - Shutdown if alarm persist for more than 4 seconds (RW) - -Byte 1: - min threshold (scale as bank 0x26) - - -Warning for the adventurous -=========================== - -A word of caution to those who want to experiment and see if they can figure -the voltage / clock programming out, I tried reading and only reading banks -0-0x30 with the reading code used for the sensor banks (0x20-0x28) and this -resulted in a _permanent_ reprogramming of the voltages, luckily I had the -sensors part configured so that it would shutdown my system on any out of spec -voltages which proprably safed my computer (after a reboot I managed to -immediately enter the bios and reload the defaults). This probably means that -the read/write cycle for the non sensor part is different from the sensor part. diff --git a/Documentation/hwmon/abituguru-datasheet.rst b/Documentation/hwmon/abituguru-datasheet.rst new file mode 100644 index 000000000000..6d5253e2223b --- /dev/null +++ b/Documentation/hwmon/abituguru-datasheet.rst @@ -0,0 +1,336 @@ +=============== +uGuru datasheet +=============== + +First of all, what I know about uGuru is no fact based on any help, hints or +datasheet from Abit. The data I have got on uGuru have I assembled through +my weak knowledge in "backwards engineering". +And just for the record, you may have noticed uGuru isn't a chip developed by +Abit, as they claim it to be. It's really just an microprocessor (uC) created by +Winbond (W83L950D). And no, reading the manual for this specific uC or +mailing Windbond for help won't give any useful data about uGuru, as it is +the program inside the uC that is responding to calls. + +Olle Sandberg , 2005-05-25 + + +Original version by Olle Sandberg who did the heavy lifting of the initial +reverse engineering. This version has been almost fully rewritten for clarity +and extended with write support and info on more databanks, the write support +is once again reverse engineered by Olle the additional databanks have been +reverse engineered by me. I would like to express my thanks to Olle, this +document and the Linux driver could not have been written without his efforts. + +Note: because of the lack of specs only the sensors part of the uGuru is +described here and not the CPU / RAM / etc voltage & frequency control. + +Hans de Goede , 28-01-2006 + + +Detection +========= + +As far as known the uGuru is always placed at and using the (ISA) I/O-ports +0xE0 and 0xE4, so we don't have to scan any port-range, just check what the two +ports are holding for detection. We will refer to 0xE0 as CMD (command-port) +and 0xE4 as DATA because Abit refers to them with these names. + +If DATA holds 0x00 or 0x08 and CMD holds 0x00 or 0xAC an uGuru could be +present. We have to check for two different values at data-port, because +after a reboot uGuru will hold 0x00 here, but if the driver is removed and +later on attached again data-port will hold 0x08, more about this later. + +After wider testing of the Linux kernel driver some variants of the uGuru have +turned up which will hold 0x00 instead of 0xAC at the CMD port, thus we also +have to test CMD for two different values. On these uGuru's DATA will initially +hold 0x09 and will only hold 0x08 after reading CMD first, so CMD must be read +first! + +To be really sure an uGuru is present a test read of one or more register +sets should be done. + + +Reading / Writing +================= + +Addressing +---------- + +The uGuru has a number of different addressing levels. The first addressing +level we will call banks. A bank holds data for one or more sensors. The data +in a bank for a sensor is one or more bytes large. + +The number of bytes is fixed for a given bank, you should always read or write +that many bytes, reading / writing more will fail, the results when writing +less then the number of bytes for a given bank are undetermined. + +See below for all known bank addresses, numbers of sensors in that bank, +number of bytes data per sensor and contents/meaning of those bytes. + +Although both this document and the kernel driver have kept the sensor +terminoligy for the addressing within a bank this is not 100% correct, in +bank 0x24 for example the addressing within the bank selects a PWM output not +a sensor. + +Notice that some banks have both a read and a write address this is how the +uGuru determines if a read from or a write to the bank is taking place, thus +when reading you should always use the read address and when writing the +write address. The write address is always one (1) more than the read address. + + +uGuru ready +----------- + +Before you can read from or write to the uGuru you must first put the uGuru +in "ready" mode. + +To put the uGuru in ready mode first write 0x00 to DATA and then wait for DATA +to hold 0x09, DATA should read 0x09 within 250 read cycles. + +Next CMD _must_ be read and should hold 0xAC, usually CMD will hold 0xAC the +first read but sometimes it takes a while before CMD holds 0xAC and thus it +has to be read a number of times (max 50). + +After reading CMD, DATA should hold 0x08 which means that the uGuru is ready +for input. As above DATA will usually hold 0x08 the first read but not always. +This step can be skipped, but it is undetermined what happens if the uGuru has +not yet reported 0x08 at DATA and you proceed with writing a bank address. + + +Sending bank and sensor addresses to the uGuru +---------------------------------------------- + +First the uGuru must be in "ready" mode as described above, DATA should hold +0x08 indicating that the uGuru wants input, in this case the bank address. + +Next write the bank address to DATA. After the bank address has been written +wait for to DATA to hold 0x08 again indicating that it wants / is ready for +more input (max 250 reads). + +Once DATA holds 0x08 again write the sensor address to CMD. + + +Reading +------- + +First send the bank and sensor addresses as described above. +Then for each byte of data you want to read wait for DATA to hold 0x01 +which indicates that the uGuru is ready to be read (max 250 reads) and once +DATA holds 0x01 read the byte from CMD. + +Once all bytes have been read data will hold 0x09, but there is no reason to +test for this. Notice that the number of bytes is bank address dependent see +above and below. + +After completing a successful read it is advised to put the uGuru back in +ready mode, so that it is ready for the next read / write cycle. This way +if your program / driver is unloaded and later loaded again the detection +algorithm described above will still work. + + + +Writing +------- + +First send the bank and sensor addresses as described above. +Then for each byte of data you want to write wait for DATA to hold 0x00 +which indicates that the uGuru is ready to be written (max 250 reads) and +once DATA holds 0x00 write the byte to CMD. + +Once all bytes have been written wait for DATA to hold 0x01 (max 250 reads) +don't ask why this is the way it is. + +Once DATA holds 0x01 read CMD it should hold 0xAC now. + +After completing a successful write it is advised to put the uGuru back in +ready mode, so that it is ready for the next read / write cycle. This way +if your program / driver is unloaded and later loaded again the detection +algorithm described above will still work. + + +Gotchas +------- + +After wider testing of the Linux kernel driver some variants of the uGuru have +turned up which do not hold 0x08 at DATA within 250 reads after writing the +bank address. With these versions this happens quite frequent, using larger +timeouts doesn't help, they just go offline for a second or 2, doing some +internal callibration or whatever. Your code should be prepared to handle +this and in case of no response in this specific case just goto sleep for a +while and then retry. + + +Address Map +=========== + +Bank 0x20 Alarms (R) +-------------------- +This bank contains 0 sensors, iow the sensor address is ignored (but must be +written) just use 0. Bank 0x20 contains 3 bytes: + +Byte 0: + This byte holds the alarm flags for sensor 0-7 of Sensor Bank1, with bit 0 + corresponding to sensor 0, 1 to 1, etc. + +Byte 1: + This byte holds the alarm flags for sensor 8-15 of Sensor Bank1, with bit 0 + corresponding to sensor 8, 1 to 9, etc. + +Byte 2: + This byte holds the alarm flags for sensor 0-5 of Sensor Bank2, with bit 0 + corresponding to sensor 0, 1 to 1, etc. + + +Bank 0x21 Sensor Bank1 Values / Readings (R) +-------------------------------------------- +This bank contains 16 sensors, for each sensor it contains 1 byte. +So far the following sensors are known to be available on all motherboards: + +- Sensor 0 CPU temp +- Sensor 1 SYS temp +- Sensor 3 CPU core volt +- Sensor 4 DDR volt +- Sensor 10 DDR Vtt volt +- Sensor 15 PWM temp + +Byte 0: + This byte holds the reading from the sensor. Sensors in Bank1 can be both + volt and temp sensors, this is motherboard specific. The uGuru however does + seem to know (be programmed with) what kindoff sensor is attached see Sensor + Bank1 Settings description. + +Volt sensors use a linear scale, a reading 0 corresponds with 0 volt and a +reading of 255 with 3494 mV. The sensors for higher voltages however are +connected through a division circuit. The currently known division circuits +in use result in ranges of: 0-4361mV, 0-6248mV or 0-14510mV. 3.3 volt sources +use the 0-4361mV range, 5 volt the 0-6248mV and 12 volt the 0-14510mV . + +Temp sensors also use a linear scale, a reading of 0 corresponds with 0 degree +Celsius and a reading of 255 with a reading of 255 degrees Celsius. + + +Bank 0x22 Sensor Bank1 Settings (R) and Bank 0x23 Sensor Bank1 Settings (W) +--------------------------------------------------------------------------- + +Those banks contain 16 sensors, for each sensor it contains 3 bytes. Each +set of 3 bytes contains the settings for the sensor with the same sensor +address in Bank 0x21 . + +Byte 0: + Alarm behaviour for the selected sensor. A 1 enables the described + behaviour. + +Bit 0: + Give an alarm if measured temp is over the warning threshold (RW) [1]_ + +Bit 1: + Give an alarm if measured volt is over the max threshold (RW) [2]_ + +Bit 2: + Give an alarm if measured volt is under the min threshold (RW) [2]_ + +Bit 3: + Beep if alarm (RW) + +Bit 4: + 1 if alarm cause measured temp is over the warning threshold (R) + +Bit 5: + 1 if alarm cause measured volt is over the max threshold (R) + +Bit 6: + 1 if alarm cause measured volt is under the min threshold (R) + +Bit 7: + - Volt sensor: Shutdown if alarm persist for more than 4 seconds (RW) + - Temp sensor: Shutdown if temp is over the shutdown threshold (RW) + +.. [1] This bit is only honored/used by the uGuru if a temp sensor is connected + +.. [2] This bit is only honored/used by the uGuru if a volt sensor is connected + Note with some trickery this can be used to find out what kinda sensor + is detected see the Linux kernel driver for an example with many + comments on how todo this. + +Byte 1: + - Temp sensor: warning threshold (scale as bank 0x21) + - Volt sensor: min threshold (scale as bank 0x21) + +Byte 2: + - Temp sensor: shutdown threshold (scale as bank 0x21) + - Volt sensor: max threshold (scale as bank 0x21) + + +Bank 0x24 PWM outputs for FAN's (R) and Bank 0x25 PWM outputs for FAN's (W) +--------------------------------------------------------------------------- + +Those banks contain 3 "sensors", for each sensor it contains 5 bytes. + - Sensor 0 usually controls the CPU fan + - Sensor 1 usually controls the NB (or chipset for single chip) fan + - Sensor 2 usually controls the System fan + +Byte 0: + Flag 0x80 to enable control, Fan runs at 100% when disabled. + low nibble (temp)sensor address at bank 0x21 used for control. + +Byte 1: + 0-255 = 0-12v (linear), specify voltage at which fan will rotate when under + low threshold temp (specified in byte 3) + +Byte 2: + 0-255 = 0-12v (linear), specify voltage at which fan will rotate when above + high threshold temp (specified in byte 4) + +Byte 3: + Low threshold temp (scale as bank 0x21) + +byte 4: + High threshold temp (scale as bank 0x21) + + +Bank 0x26 Sensors Bank2 Values / Readings (R) +--------------------------------------------- + +This bank contains 6 sensors (AFAIK), for each sensor it contains 1 byte. + +So far the following sensors are known to be available on all motherboards: + - Sensor 0: CPU fan speed + - Sensor 1: NB (or chipset for single chip) fan speed + - Sensor 2: SYS fan speed + +Byte 0: + This byte holds the reading from the sensor. 0-255 = 0-15300 (linear) + + +Bank 0x27 Sensors Bank2 Settings (R) and Bank 0x28 Sensors Bank2 Settings (W) +----------------------------------------------------------------------------- + +Those banks contain 6 sensors (AFAIK), for each sensor it contains 2 bytes. + +Byte 0: + Alarm behaviour for the selected sensor. A 1 enables the described behaviour. + +Bit 0: + Give an alarm if measured rpm is under the min threshold (RW) + +Bit 3: + Beep if alarm (RW) + +Bit 7: + Shutdown if alarm persist for more than 4 seconds (RW) + +Byte 1: + min threshold (scale as bank 0x26) + + +Warning for the adventurous +=========================== + +A word of caution to those who want to experiment and see if they can figure +the voltage / clock programming out, I tried reading and only reading banks +0-0x30 with the reading code used for the sensor banks (0x20-0x28) and this +resulted in a _permanent_ reprogramming of the voltages, luckily I had the +sensors part configured so that it would shutdown my system on any out of spec +voltages which proprably safed my computer (after a reboot I managed to +immediately enter the bios and reload the defaults). This probably means that +the read/write cycle for the non sensor part is different from the sensor part. diff --git a/Documentation/hwmon/abituguru.rst b/Documentation/hwmon/abituguru.rst new file mode 100644 index 000000000000..d8243c827de9 --- /dev/null +++ b/Documentation/hwmon/abituguru.rst @@ -0,0 +1,113 @@ +Kernel driver abituguru +======================= + +Supported chips: + + * Abit uGuru revision 1 & 2 (Hardware Monitor part only) + + Prefix: 'abituguru' + + Addresses scanned: ISA 0x0E0 + + Datasheet: Not available, this driver is based on reverse engineering. + A "Datasheet" has been written based on the reverse engineering it + should be available in the same dir as this file under the name + abituguru-datasheet. + + Note: + The uGuru is a microcontroller with onboard firmware which programs + it to behave as a hwmon IC. There are many different revisions of the + firmware and thus effectivly many different revisions of the uGuru. + Below is an incomplete list with which revisions are used for which + Motherboards: + + - uGuru 1.00 ~ 1.24 (AI7, KV8-MAX3, AN7) [1]_ + - uGuru 2.0.0.0 ~ 2.0.4.2 (KV8-PRO) + - uGuru 2.1.0.0 ~ 2.1.2.8 (AS8, AV8, AA8, AG8, AA8XE, AX8) + - uGuru 2.2.0.0 ~ 2.2.0.6 (AA8 Fatal1ty) + - uGuru 2.3.0.0 ~ 2.3.0.9 (AN8) + - uGuru 3.0.0.0 ~ 3.0.x.x (AW8, AL8, AT8, NI8 SLI, AT8 32X, AN8 32X, + AW9D-MAX) [2]_ + +.. [1] For revisions 2 and 3 uGuru's the driver can autodetect the + sensortype (Volt or Temp) for bank1 sensors, for revision 1 uGuru's + this does not always work. For these uGuru's the autodetection can + be overridden with the bank1_types module param. For all 3 known + revison 1 motherboards the correct use of this param is: + bank1_types=1,1,0,0,0,0,0,2,0,0,0,0,2,0,0,1 + You may also need to specify the fan_sensors option for these boards + fan_sensors=5 + +.. [2] There is a separate abituguru3 driver for these motherboards, + the abituguru (without the 3 !) driver will not work on these + motherboards (and visa versa)! + +Authors: + - Hans de Goede , + - (Initial reverse engineering done by Olle Sandberg + ) + + +Module Parameters +----------------- + +* force: bool + Force detection. Note this parameter only causes the + detection to be skipped, and thus the insmod to + succeed. If the uGuru can't be read the actual hwmon + driver will not load and thus no hwmon device will get + registered. +* bank1_types: int[] + Bank1 sensortype autodetection override: + + * -1 autodetect (default) + * 0 volt sensor + * 1 temp sensor + * 2 not connected +* fan_sensors: int + Tell the driver how many fan speed sensors there are + on your motherboard. Default: 0 (autodetect). +* pwms: int + Tell the driver how many fan speed controls (fan + pwms) your motherboard has. Default: 0 (autodetect). +* verbose: int + How verbose should the driver be? (0-3): + + * 0 normal output + * 1 + verbose error reporting + * 2 + sensors type probing info (default) + * 3 + retryable error reporting + + Default: 2 (the driver is still in the testing phase) + +Notice: if you need any of the first three options above please insmod the +driver with verbose set to 3 and mail me the output of: +dmesg | grep abituguru + + +Description +----------- + +This driver supports the hardware monitoring features of the first and +second revision of the Abit uGuru chip found on Abit uGuru featuring +motherboards (most modern Abit motherboards). + +The first and second revision of the uGuru chip in reality is a Winbond +W83L950D in disguise (despite Abit claiming it is "a new microprocessor +designed by the ABIT Engineers"). Unfortunately this doesn't help since the +W83L950D is a generic microcontroller with a custom Abit application running +on it. + +Despite Abit not releasing any information regarding the uGuru, Olle +Sandberg has managed to reverse engineer the sensor part +of the uGuru. Without his work this driver would not have been possible. + +Known Issues +------------ + +The voltage and frequency control parts of the Abit uGuru are not supported. + +.. toctree:: + :maxdepth: 1 + + abituguru-datasheet.rst diff --git a/Documentation/hwmon/abituguru3 b/Documentation/hwmon/abituguru3 deleted file mode 100644 index 514f11f41e8b..000000000000 --- a/Documentation/hwmon/abituguru3 +++ /dev/null @@ -1,75 +0,0 @@ -Kernel driver abituguru3 -======================== - -Supported chips: - * Abit uGuru revision 3 (Hardware Monitor part, reading only) - - Prefix: 'abituguru3' - - Addresses scanned: ISA 0x0E0 - - Datasheet: Not available, this driver is based on reverse engineering. - - Note: - The uGuru is a microcontroller with onboard firmware which programs - it to behave as a hwmon IC. There are many different revisions of the - firmware and thus effectivly many different revisions of the uGuru. - Below is an incomplete list with which revisions are used for which - Motherboards: - - - uGuru 1.00 ~ 1.24 (AI7, KV8-MAX3, AN7) - - uGuru 2.0.0.0 ~ 2.0.4.2 (KV8-PRO) - - uGuru 2.1.0.0 ~ 2.1.2.8 (AS8, AV8, AA8, AG8, AA8XE, AX8) - - uGuru 2.3.0.0 ~ 2.3.0.9 (AN8) - - uGuru 3.0.0.0 ~ 3.0.x.x (AW8, AL8, AT8, NI8 SLI, AT8 32X, AN8 32X, - AW9D-MAX) - - The abituguru3 driver is only for revison 3.0.x.x motherboards, - this driver will not work on older motherboards. For older - motherboards use the abituguru (without the 3 !) driver. - -Authors: - - Hans de Goede , - - (Initial reverse engineering done by Louis Kruger) - - -Module Parameters ------------------ - -* force: bool - Force detection. Note this parameter only causes the - detection to be skipped, and thus the insmod to - succeed. If the uGuru can't be read the actual hwmon - driver will not load and thus no hwmon device will get - registered. -* verbose: bool - Should the driver be verbose? - - * 0/off/false normal output - * 1/on/true + verbose error reporting (default) - - Default: 1 (the driver is still in the testing phase) - -Description ------------ - -This driver supports the hardware monitoring features of the third revision of -the Abit uGuru chip, found on recent Abit uGuru featuring motherboards. - -The 3rd revision of the uGuru chip in reality is a Winbond W83L951G. -Unfortunately this doesn't help since the W83L951G is a generic microcontroller -with a custom Abit application running on it. - -Despite Abit not releasing any information regarding the uGuru revision 3, -Louis Kruger has managed to reverse engineer the sensor part of the uGuru. -Without his work this driver would not have been possible. - -Known Issues ------------- - -The voltage and frequency control parts of the Abit uGuru are not supported, -neither is writing any of the sensor settings and writing / reading the -fanspeed control registers (FanEQ) - -If you encounter any problems please mail me and -include the output of: `dmesg | grep abituguru` diff --git a/Documentation/hwmon/abituguru3.rst b/Documentation/hwmon/abituguru3.rst new file mode 100644 index 000000000000..514f11f41e8b --- /dev/null +++ b/Documentation/hwmon/abituguru3.rst @@ -0,0 +1,75 @@ +Kernel driver abituguru3 +======================== + +Supported chips: + * Abit uGuru revision 3 (Hardware Monitor part, reading only) + + Prefix: 'abituguru3' + + Addresses scanned: ISA 0x0E0 + + Datasheet: Not available, this driver is based on reverse engineering. + + Note: + The uGuru is a microcontroller with onboard firmware which programs + it to behave as a hwmon IC. There are many different revisions of the + firmware and thus effectivly many different revisions of the uGuru. + Below is an incomplete list with which revisions are used for which + Motherboards: + + - uGuru 1.00 ~ 1.24 (AI7, KV8-MAX3, AN7) + - uGuru 2.0.0.0 ~ 2.0.4.2 (KV8-PRO) + - uGuru 2.1.0.0 ~ 2.1.2.8 (AS8, AV8, AA8, AG8, AA8XE, AX8) + - uGuru 2.3.0.0 ~ 2.3.0.9 (AN8) + - uGuru 3.0.0.0 ~ 3.0.x.x (AW8, AL8, AT8, NI8 SLI, AT8 32X, AN8 32X, + AW9D-MAX) + + The abituguru3 driver is only for revison 3.0.x.x motherboards, + this driver will not work on older motherboards. For older + motherboards use the abituguru (without the 3 !) driver. + +Authors: + - Hans de Goede , + - (Initial reverse engineering done by Louis Kruger) + + +Module Parameters +----------------- + +* force: bool + Force detection. Note this parameter only causes the + detection to be skipped, and thus the insmod to + succeed. If the uGuru can't be read the actual hwmon + driver will not load and thus no hwmon device will get + registered. +* verbose: bool + Should the driver be verbose? + + * 0/off/false normal output + * 1/on/true + verbose error reporting (default) + + Default: 1 (the driver is still in the testing phase) + +Description +----------- + +This driver supports the hardware monitoring features of the third revision of +the Abit uGuru chip, found on recent Abit uGuru featuring motherboards. + +The 3rd revision of the uGuru chip in reality is a Winbond W83L951G. +Unfortunately this doesn't help since the W83L951G is a generic microcontroller +with a custom Abit application running on it. + +Despite Abit not releasing any information regarding the uGuru revision 3, +Louis Kruger has managed to reverse engineer the sensor part of the uGuru. +Without his work this driver would not have been possible. + +Known Issues +------------ + +The voltage and frequency control parts of the Abit uGuru are not supported, +neither is writing any of the sensor settings and writing / reading the +fanspeed control registers (FanEQ) + +If you encounter any problems please mail me and +include the output of: `dmesg | grep abituguru` diff --git a/Documentation/hwmon/abx500 b/Documentation/hwmon/abx500 deleted file mode 100644 index 3d88b2ce0f00..000000000000 --- a/Documentation/hwmon/abx500 +++ /dev/null @@ -1,32 +0,0 @@ -Kernel driver abx500 -==================== - -Supported chips: - - * ST-Ericsson ABx500 series - - Prefix: 'abx500' - - Addresses scanned: - - - Datasheet: http://www.stericsson.com/developers/documentation.jsp - -Authors: - Martin Persson - Hongbo Zhang - -Description ------------ - -Every ST-Ericsson Ux500 SOC consists of both ABx500 and DBx500 physically, -this is kernel hwmon driver for ABx500. - -There are some GPADCs inside ABx500 which are designed for connecting to -thermal sensors, and there is also a thermal sensor inside ABx500 too, which -raises interrupt when critical temperature reached. - -This abx500 is a common layer which can monitor all of the sensors, every -specific abx500 chip has its special configurations in its own file, e.g. some -sensors can be configured invisible if they are not available on that chip, and -the corresponding gpadc_addr should be set to 0, thus this sensor won't be -polled. diff --git a/Documentation/hwmon/abx500.rst b/Documentation/hwmon/abx500.rst new file mode 100644 index 000000000000..3d88b2ce0f00 --- /dev/null +++ b/Documentation/hwmon/abx500.rst @@ -0,0 +1,32 @@ +Kernel driver abx500 +==================== + +Supported chips: + + * ST-Ericsson ABx500 series + + Prefix: 'abx500' + + Addresses scanned: - + + Datasheet: http://www.stericsson.com/developers/documentation.jsp + +Authors: + Martin Persson + Hongbo Zhang + +Description +----------- + +Every ST-Ericsson Ux500 SOC consists of both ABx500 and DBx500 physically, +this is kernel hwmon driver for ABx500. + +There are some GPADCs inside ABx500 which are designed for connecting to +thermal sensors, and there is also a thermal sensor inside ABx500 too, which +raises interrupt when critical temperature reached. + +This abx500 is a common layer which can monitor all of the sensors, every +specific abx500 chip has its special configurations in its own file, e.g. some +sensors can be configured invisible if they are not available on that chip, and +the corresponding gpadc_addr should be set to 0, thus this sensor won't be +polled. diff --git a/Documentation/hwmon/acpi_power_meter b/Documentation/hwmon/acpi_power_meter deleted file mode 100644 index 7665ca6ba957..000000000000 --- a/Documentation/hwmon/acpi_power_meter +++ /dev/null @@ -1,54 +0,0 @@ -Kernel driver power_meter -========================= - -This driver talks to ACPI 4.0 power meters. - -Supported systems: - - * Any recent system with ACPI 4.0. - - Prefix: 'power_meter' - - Datasheet: http://acpi.info/, section 10.4. - -Author: Darrick J. Wong - -Description ------------ - -This driver implements sensor reading support for the power meters exposed in -the ACPI 4.0 spec (Chapter 10.4). These devices have a simple set of -features--a power meter that returns average power use over a configurable -interval, an optional capping mechanism, and a couple of trip points. The -sysfs interface conforms with the specification outlined in the "Power" section -of Documentation/hwmon/sysfs-interface. - -Special Features ----------------- - -The `power[1-*]_is_battery` knob indicates if the power supply is a battery. -Both `power[1-*]_average_{min,max}` must be set before the trip points will work. -When both of them are set, an ACPI event will be broadcast on the ACPI netlink -socket and a poll notification will be sent to the appropriate -`power[1-*]_average` sysfs file. - -The `power[1-*]_{model_number, serial_number, oem_info}` fields display -arbitrary strings that ACPI provides with the meter. The measures/ directory -contains symlinks to the devices that this meter measures. - -Some computers have the ability to enforce a power cap in hardware. If this is -the case, the `power[1-*]_cap` and related sysfs files will appear. When the -average power consumption exceeds the cap, an ACPI event will be broadcast on -the netlink event socket and a poll notification will be sent to the -appropriate `power[1-*]_alarm` file to indicate that capping has begun, and the -hardware has taken action to reduce power consumption. Most likely this will -result in reduced performance. - -There are a few other ACPI notifications that can be sent by the firmware. In -all cases the ACPI event will be broadcast on the ACPI netlink event socket as -well as sent as a poll notification to a sysfs file. The events are as -follows: - -`power[1-*]_cap` will be notified if the firmware changes the power cap. -`power[1-*]_interval` will be notified if the firmware changes the averaging -interval. diff --git a/Documentation/hwmon/acpi_power_meter.rst b/Documentation/hwmon/acpi_power_meter.rst new file mode 100644 index 000000000000..4a0941ade0ca --- /dev/null +++ b/Documentation/hwmon/acpi_power_meter.rst @@ -0,0 +1,54 @@ +Kernel driver power_meter +========================= + +This driver talks to ACPI 4.0 power meters. + +Supported systems: + + * Any recent system with ACPI 4.0. + + Prefix: 'power_meter' + + Datasheet: http://acpi.info/, section 10.4. + +Author: Darrick J. Wong + +Description +----------- + +This driver implements sensor reading support for the power meters exposed in +the ACPI 4.0 spec (Chapter 10.4). These devices have a simple set of +features--a power meter that returns average power use over a configurable +interval, an optional capping mechanism, and a couple of trip points. The +sysfs interface conforms with the specification outlined in the "Power" section +of Documentation/hwmon/sysfs-interface.rst. + +Special Features +---------------- + +The `power[1-*]_is_battery` knob indicates if the power supply is a battery. +Both `power[1-*]_average_{min,max}` must be set before the trip points will work. +When both of them are set, an ACPI event will be broadcast on the ACPI netlink +socket and a poll notification will be sent to the appropriate +`power[1-*]_average` sysfs file. + +The `power[1-*]_{model_number, serial_number, oem_info}` fields display +arbitrary strings that ACPI provides with the meter. The measures/ directory +contains symlinks to the devices that this meter measures. + +Some computers have the ability to enforce a power cap in hardware. If this is +the case, the `power[1-*]_cap` and related sysfs files will appear. When the +average power consumption exceeds the cap, an ACPI event will be broadcast on +the netlink event socket and a poll notification will be sent to the +appropriate `power[1-*]_alarm` file to indicate that capping has begun, and the +hardware has taken action to reduce power consumption. Most likely this will +result in reduced performance. + +There are a few other ACPI notifications that can be sent by the firmware. In +all cases the ACPI event will be broadcast on the ACPI netlink event socket as +well as sent as a poll notification to a sysfs file. The events are as +follows: + +`power[1-*]_cap` will be notified if the firmware changes the power cap. +`power[1-*]_interval` will be notified if the firmware changes the averaging +interval. diff --git a/Documentation/hwmon/ad7314 b/Documentation/hwmon/ad7314 deleted file mode 100644 index bf389736bcd1..000000000000 --- a/Documentation/hwmon/ad7314 +++ /dev/null @@ -1,34 +0,0 @@ -Kernel driver ad7314 -==================== - -Supported chips: - - * Analog Devices AD7314 - - Prefix: 'ad7314' - - Datasheet: Publicly available at Analog Devices website. - - * Analog Devices ADT7301 - - Prefix: 'adt7301' - - Datasheet: Publicly available at Analog Devices website. - - * Analog Devices ADT7302 - - Prefix: 'adt7302' - - Datasheet: Publicly available at Analog Devices website. - -Description ------------ - -Driver supports the above parts. The ad7314 has a 10 bit -sensor with 1lsb = 0.25 degrees centigrade. The adt7301 and -adt7302 have 14 bit sensors with 1lsb = 0.03125 degrees centigrade. - -Notes ------ - -Currently power down mode is not supported. diff --git a/Documentation/hwmon/ad7314.rst b/Documentation/hwmon/ad7314.rst new file mode 100644 index 000000000000..bf389736bcd1 --- /dev/null +++ b/Documentation/hwmon/ad7314.rst @@ -0,0 +1,34 @@ +Kernel driver ad7314 +==================== + +Supported chips: + + * Analog Devices AD7314 + + Prefix: 'ad7314' + + Datasheet: Publicly available at Analog Devices website. + + * Analog Devices ADT7301 + + Prefix: 'adt7301' + + Datasheet: Publicly available at Analog Devices website. + + * Analog Devices ADT7302 + + Prefix: 'adt7302' + + Datasheet: Publicly available at Analog Devices website. + +Description +----------- + +Driver supports the above parts. The ad7314 has a 10 bit +sensor with 1lsb = 0.25 degrees centigrade. The adt7301 and +adt7302 have 14 bit sensors with 1lsb = 0.03125 degrees centigrade. + +Notes +----- + +Currently power down mode is not supported. diff --git a/Documentation/hwmon/adc128d818 b/Documentation/hwmon/adc128d818 deleted file mode 100644 index 6753468932ab..000000000000 --- a/Documentation/hwmon/adc128d818 +++ /dev/null @@ -1,50 +0,0 @@ -Kernel driver adc128d818 -======================== - -Supported chips: - - * Texas Instruments ADC818D818 - - Prefix: 'adc818d818' - - Addresses scanned: I2C 0x1d, 0x1e, 0x1f, 0x2d, 0x2e, 0x2f - - Datasheet: Publicly available at the TI website http://www.ti.com/ - -Author: Guenter Roeck - -Description ------------ - -This driver implements support for the Texas Instruments ADC128D818. -It is described as 'ADC System Monitor with Temperature Sensor'. - -The ADC128D818 implements one temperature sensor and seven voltage sensors. - -Temperatures are measured in degrees Celsius. There is one set of limits. -When the HOT Temperature Limit is crossed, this will cause an alarm that will -be reasserted until the temperature drops below the HOT Hysteresis. -Measurements are guaranteed between -55 and +125 degrees. The temperature -measurement has a resolution of 0.5 degrees; the limits have a resolution -of 1 degree. - -Voltage sensors (also known as IN sensors) report their values in volts. -An alarm is triggered if the voltage has crossed a programmable minimum -or maximum limit. Note that minimum in this case always means 'closest to -zero'; this is important for negative voltage measurements. All voltage -inputs can measure voltages between 0 and 2.55 volts, with a resolution -of 0.625 mV. - -If an alarm triggers, it will remain triggered until the hardware register -is read at least once. This means that the cause for the alarm may -already have disappeared by the time the alarm is read. The driver -caches the alarm status for each sensor until it is at least reported -once, to ensure that alarms are reported to user space. - -The ADC128D818 only updates its values approximately once per second; -reading it more often will do no harm, but will return 'old' values. - -In addition to the scanned address list, the chip can also be configured for -addresses 0x35 to 0x37. Those addresses are not scanned. You have to instantiate -the driver explicitly if the chip is configured for any of those addresses in -your system. diff --git a/Documentation/hwmon/adc128d818.rst b/Documentation/hwmon/adc128d818.rst new file mode 100644 index 000000000000..6753468932ab --- /dev/null +++ b/Documentation/hwmon/adc128d818.rst @@ -0,0 +1,50 @@ +Kernel driver adc128d818 +======================== + +Supported chips: + + * Texas Instruments ADC818D818 + + Prefix: 'adc818d818' + + Addresses scanned: I2C 0x1d, 0x1e, 0x1f, 0x2d, 0x2e, 0x2f + + Datasheet: Publicly available at the TI website http://www.ti.com/ + +Author: Guenter Roeck + +Description +----------- + +This driver implements support for the Texas Instruments ADC128D818. +It is described as 'ADC System Monitor with Temperature Sensor'. + +The ADC128D818 implements one temperature sensor and seven voltage sensors. + +Temperatures are measured in degrees Celsius. There is one set of limits. +When the HOT Temperature Limit is crossed, this will cause an alarm that will +be reasserted until the temperature drops below the HOT Hysteresis. +Measurements are guaranteed between -55 and +125 degrees. The temperature +measurement has a resolution of 0.5 degrees; the limits have a resolution +of 1 degree. + +Voltage sensors (also known as IN sensors) report their values in volts. +An alarm is triggered if the voltage has crossed a programmable minimum +or maximum limit. Note that minimum in this case always means 'closest to +zero'; this is important for negative voltage measurements. All voltage +inputs can measure voltages between 0 and 2.55 volts, with a resolution +of 0.625 mV. + +If an alarm triggers, it will remain triggered until the hardware register +is read at least once. This means that the cause for the alarm may +already have disappeared by the time the alarm is read. The driver +caches the alarm status for each sensor until it is at least reported +once, to ensure that alarms are reported to user space. + +The ADC128D818 only updates its values approximately once per second; +reading it more often will do no harm, but will return 'old' values. + +In addition to the scanned address list, the chip can also be configured for +addresses 0x35 to 0x37. Those addresses are not scanned. You have to instantiate +the driver explicitly if the chip is configured for any of those addresses in +your system. diff --git a/Documentation/hwmon/adm1021 b/Documentation/hwmon/adm1021 deleted file mode 100644 index 6cbb0f75fe00..000000000000 --- a/Documentation/hwmon/adm1021 +++ /dev/null @@ -1,153 +0,0 @@ -Kernel driver adm1021 -===================== - -Supported chips: - - * Analog Devices ADM1021 - - Prefix: 'adm1021' - - Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e - - Datasheet: Publicly available at the Analog Devices website - - * Analog Devices ADM1021A/ADM1023 - - Prefix: 'adm1023' - - Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e - - Datasheet: Publicly available at the Analog Devices website - - * Genesys Logic GL523SM - - Prefix: 'gl523sm' - - Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e - - Datasheet: - - * Maxim MAX1617 - - Prefix: 'max1617' - - Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e - - Datasheet: Publicly available at the Maxim website - - * Maxim MAX1617A - - Prefix: 'max1617a' - - Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e - - Datasheet: Publicly available at the Maxim website - - * National Semiconductor LM84 - - Prefix: 'lm84' - - Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e - - Datasheet: Publicly available at the National Semiconductor website - - * Philips NE1617 - - Prefix: 'max1617' (probably detected as a max1617) - - Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e - - Datasheet: Publicly available at the Philips website - - * Philips NE1617A - - Prefix: 'max1617' (probably detected as a max1617) - - Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e - - Datasheet: Publicly available at the Philips website - - * TI THMC10 - - Prefix: 'thmc10' - - Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e - - Datasheet: Publicly available at the TI website - - * Onsemi MC1066 - - Prefix: 'mc1066' - - Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e - - Datasheet: Publicly available at the Onsemi website - - -Authors: - - Frodo Looijaard , - - Philip Edelbrock - -Module Parameters ------------------ - -* read_only: int - Don't set any values, read only mode - - -Description ------------ - -The chips supported by this driver are very similar. The Maxim MAX1617 is -the oldest; it has the problem that it is not very well detectable. The -MAX1617A solves that. The ADM1021 is a straight clone of the MAX1617A. -Ditto for the THMC10. From here on, we will refer to all these chips as -ADM1021-clones. - -The ADM1021 and MAX1617A reports a die code, which is a sort of revision -code. This can help us pinpoint problems; it is not very useful -otherwise. - -ADM1021-clones implement two temperature sensors. One of them is internal, -and measures the temperature of the chip itself; the other is external and -is realised in the form of a transistor-like device. A special alarm -indicates whether the remote sensor is connected. - -Each sensor has its own low and high limits. When they are crossed, the -corresponding alarm is set and remains on as long as the temperature stays -out of range. Temperatures are measured in degrees Celsius. Measurements -are possible between -65 and +127 degrees, with a resolution of one degree. - -If an alarm triggers, it will remain triggered until the hardware register -is read at least once. This means that the cause for the alarm may already -have disappeared! - -This driver only updates its values each 1.5 seconds; reading it more often -will do no harm, but will return 'old' values. It is possible to make -ADM1021-clones do faster measurements, but there is really no good reason -for that. - - -Netburst-based Xeon support ---------------------------- - -Some Xeon processors based on the Netburst (early Pentium 4, from 2001 to -2003) microarchitecture had real MAX1617, ADM1021, or compatible chips -within them, with two temperature sensors. Other Xeon processors of this -era (with 400 MHz FSB) had chips with only one temperature sensor. - -If you have such an old Xeon, and you get two valid temperatures when -loading the adm1021 module, then things are good. - -If nothing happens when loading the adm1021 module, and you are certain -that your specific Xeon processor model includes compatible sensors, you -will have to explicitly instantiate the sensor chips from user-space. See -method 4 in Documentation/i2c/instantiating-devices. Possible slave -addresses are 0x18, 0x1a, 0x29, 0x2b, 0x4c, or 0x4e. It is likely that -only temp2 will be correct and temp1 will have to be ignored. - -Previous generations of the Xeon processor (based on Pentium II/III) -didn't have these sensors. Next generations of Xeon processors (533 MHz -FSB and faster) lost them, until the Core-based generation which -introduced integrated digital thermal sensors. These are supported by -the coretemp driver. diff --git a/Documentation/hwmon/adm1021.rst b/Documentation/hwmon/adm1021.rst new file mode 100644 index 000000000000..6cbb0f75fe00 --- /dev/null +++ b/Documentation/hwmon/adm1021.rst @@ -0,0 +1,153 @@ +Kernel driver adm1021 +===================== + +Supported chips: + + * Analog Devices ADM1021 + + Prefix: 'adm1021' + + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + + Datasheet: Publicly available at the Analog Devices website + + * Analog Devices ADM1021A/ADM1023 + + Prefix: 'adm1023' + + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + + Datasheet: Publicly available at the Analog Devices website + + * Genesys Logic GL523SM + + Prefix: 'gl523sm' + + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + + Datasheet: + + * Maxim MAX1617 + + Prefix: 'max1617' + + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + + Datasheet: Publicly available at the Maxim website + + * Maxim MAX1617A + + Prefix: 'max1617a' + + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + + Datasheet: Publicly available at the Maxim website + + * National Semiconductor LM84 + + Prefix: 'lm84' + + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + + Datasheet: Publicly available at the National Semiconductor website + + * Philips NE1617 + + Prefix: 'max1617' (probably detected as a max1617) + + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + + Datasheet: Publicly available at the Philips website + + * Philips NE1617A + + Prefix: 'max1617' (probably detected as a max1617) + + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + + Datasheet: Publicly available at the Philips website + + * TI THMC10 + + Prefix: 'thmc10' + + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + + Datasheet: Publicly available at the TI website + + * Onsemi MC1066 + + Prefix: 'mc1066' + + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + + Datasheet: Publicly available at the Onsemi website + + +Authors: + - Frodo Looijaard , + - Philip Edelbrock + +Module Parameters +----------------- + +* read_only: int + Don't set any values, read only mode + + +Description +----------- + +The chips supported by this driver are very similar. The Maxim MAX1617 is +the oldest; it has the problem that it is not very well detectable. The +MAX1617A solves that. The ADM1021 is a straight clone of the MAX1617A. +Ditto for the THMC10. From here on, we will refer to all these chips as +ADM1021-clones. + +The ADM1021 and MAX1617A reports a die code, which is a sort of revision +code. This can help us pinpoint problems; it is not very useful +otherwise. + +ADM1021-clones implement two temperature sensors. One of them is internal, +and measures the temperature of the chip itself; the other is external and +is realised in the form of a transistor-like device. A special alarm +indicates whether the remote sensor is connected. + +Each sensor has its own low and high limits. When they are crossed, the +corresponding alarm is set and remains on as long as the temperature stays +out of range. Temperatures are measured in degrees Celsius. Measurements +are possible between -65 and +127 degrees, with a resolution of one degree. + +If an alarm triggers, it will remain triggered until the hardware register +is read at least once. This means that the cause for the alarm may already +have disappeared! + +This driver only updates its values each 1.5 seconds; reading it more often +will do no harm, but will return 'old' values. It is possible to make +ADM1021-clones do faster measurements, but there is really no good reason +for that. + + +Netburst-based Xeon support +--------------------------- + +Some Xeon processors based on the Netburst (early Pentium 4, from 2001 to +2003) microarchitecture had real MAX1617, ADM1021, or compatible chips +within them, with two temperature sensors. Other Xeon processors of this +era (with 400 MHz FSB) had chips with only one temperature sensor. + +If you have such an old Xeon, and you get two valid temperatures when +loading the adm1021 module, then things are good. + +If nothing happens when loading the adm1021 module, and you are certain +that your specific Xeon processor model includes compatible sensors, you +will have to explicitly instantiate the sensor chips from user-space. See +method 4 in Documentation/i2c/instantiating-devices. Possible slave +addresses are 0x18, 0x1a, 0x29, 0x2b, 0x4c, or 0x4e. It is likely that +only temp2 will be correct and temp1 will have to be ignored. + +Previous generations of the Xeon processor (based on Pentium II/III) +didn't have these sensors. Next generations of Xeon processors (533 MHz +FSB and faster) lost them, until the Core-based generation which +introduced integrated digital thermal sensors. These are supported by +the coretemp driver. diff --git a/Documentation/hwmon/adm1025 b/Documentation/hwmon/adm1025 deleted file mode 100644 index 283e65e348a5..000000000000 --- a/Documentation/hwmon/adm1025 +++ /dev/null @@ -1,60 +0,0 @@ -Kernel driver adm1025 -===================== - -Supported chips: - - * Analog Devices ADM1025, ADM1025A - - Prefix: 'adm1025' - - Addresses scanned: I2C 0x2c - 0x2e - - Datasheet: Publicly available at the Analog Devices website - - * Philips NE1619 - - Prefix: 'ne1619' - - Addresses scanned: I2C 0x2c - 0x2d - - Datasheet: Publicly available at the Philips website - -The NE1619 presents some differences with the original ADM1025: - - * Only two possible addresses (0x2c - 0x2d). - * No temperature offset register, but we don't use it anyway. - * No INT mode for pin 16. We don't play with it anyway. - -Authors: - - Chen-Yuan Wu , - - Jean Delvare - -Description ------------ - -(This is from Analog Devices.) The ADM1025 is a complete system hardware -monitor for microprocessor-based systems, providing measurement and limit -comparison of various system parameters. Five voltage measurement inputs -are provided, for monitoring +2.5V, +3.3V, +5V and +12V power supplies and -the processor core voltage. The ADM1025 can monitor a sixth power-supply -voltage by measuring its own VCC. One input (two pins) is dedicated to a -remote temperature-sensing diode and an on-chip temperature sensor allows -ambient temperature to be monitored. - -One specificity of this chip is that the pin 11 can be hardwired in two -different manners. It can act as the +12V power-supply voltage analog -input, or as the a fifth digital entry for the VID reading (bit 4). It's -kind of strange since both are useful, and the reason for designing the -chip that way is obscure at least to me. The bit 5 of the configuration -register can be used to define how the chip is hardwired. Please note that -it is not a choice you have to make as the user. The choice was already -made by your motherboard's maker. If the configuration bit isn't set -properly, you'll have a wrong +12V reading or a wrong VID reading. The way -the driver handles that is to preserve this bit through the initialization -process, assuming that the BIOS set it up properly beforehand. If it turns -out not to be true in some cases, we'll provide a module parameter to force -modes. - -This driver also supports the ADM1025A, which differs from the ADM1025 -only in that it has "open-drain VID inputs while the ADM1025 has on-chip -100k pull-ups on the VID inputs". It doesn't make any difference for us. diff --git a/Documentation/hwmon/adm1025.rst b/Documentation/hwmon/adm1025.rst new file mode 100644 index 000000000000..283e65e348a5 --- /dev/null +++ b/Documentation/hwmon/adm1025.rst @@ -0,0 +1,60 @@ +Kernel driver adm1025 +===================== + +Supported chips: + + * Analog Devices ADM1025, ADM1025A + + Prefix: 'adm1025' + + Addresses scanned: I2C 0x2c - 0x2e + + Datasheet: Publicly available at the Analog Devices website + + * Philips NE1619 + + Prefix: 'ne1619' + + Addresses scanned: I2C 0x2c - 0x2d + + Datasheet: Publicly available at the Philips website + +The NE1619 presents some differences with the original ADM1025: + + * Only two possible addresses (0x2c - 0x2d). + * No temperature offset register, but we don't use it anyway. + * No INT mode for pin 16. We don't play with it anyway. + +Authors: + - Chen-Yuan Wu , + - Jean Delvare + +Description +----------- + +(This is from Analog Devices.) The ADM1025 is a complete system hardware +monitor for microprocessor-based systems, providing measurement and limit +comparison of various system parameters. Five voltage measurement inputs +are provided, for monitoring +2.5V, +3.3V, +5V and +12V power supplies and +the processor core voltage. The ADM1025 can monitor a sixth power-supply +voltage by measuring its own VCC. One input (two pins) is dedicated to a +remote temperature-sensing diode and an on-chip temperature sensor allows +ambient temperature to be monitored. + +One specificity of this chip is that the pin 11 can be hardwired in two +different manners. It can act as the +12V power-supply voltage analog +input, or as the a fifth digital entry for the VID reading (bit 4). It's +kind of strange since both are useful, and the reason for designing the +chip that way is obscure at least to me. The bit 5 of the configuration +register can be used to define how the chip is hardwired. Please note that +it is not a choice you have to make as the user. The choice was already +made by your motherboard's maker. If the configuration bit isn't set +properly, you'll have a wrong +12V reading or a wrong VID reading. The way +the driver handles that is to preserve this bit through the initialization +process, assuming that the BIOS set it up properly beforehand. If it turns +out not to be true in some cases, we'll provide a module parameter to force +modes. + +This driver also supports the ADM1025A, which differs from the ADM1025 +only in that it has "open-drain VID inputs while the ADM1025 has on-chip +100k pull-ups on the VID inputs". It doesn't make any difference for us. diff --git a/Documentation/hwmon/adm1026 b/Documentation/hwmon/adm1026 deleted file mode 100644 index 35d63e6498a3..000000000000 --- a/Documentation/hwmon/adm1026 +++ /dev/null @@ -1,101 +0,0 @@ -Kernel driver adm1026 -===================== - -Supported chips: - * Analog Devices ADM1026 - - Prefix: 'adm1026' - - Addresses scanned: I2C 0x2c, 0x2d, 0x2e - - Datasheet: Publicly available at the Analog Devices website - - http://www.onsemi.com/PowerSolutions/product.do?id=ADM1026 - -Authors: - - Philip Pokorny for Penguin Computing - - Justin Thiessen - -Module Parameters ------------------ - -* gpio_input: int array (min = 1, max = 17) - List of GPIO pins (0-16) to program as inputs - -* gpio_output: int array (min = 1, max = 17) - List of GPIO pins (0-16) to program as outputs - -* gpio_inverted: int array (min = 1, max = 17) - List of GPIO pins (0-16) to program as inverted - -* gpio_normal: int array (min = 1, max = 17) - List of GPIO pins (0-16) to program as normal/non-inverted - -* gpio_fan: int array (min = 1, max = 8) - List of GPIO pins (0-7) to program as fan tachs - - -Description ------------ - -This driver implements support for the Analog Devices ADM1026. Analog -Devices calls it a "complete thermal system management controller." - -The ADM1026 implements three (3) temperature sensors, 17 voltage sensors, -16 general purpose digital I/O lines, eight (8) fan speed sensors (8-bit), -an analog output and a PWM output along with limit, alarm and mask bits for -all of the above. There is even 8k bytes of EEPROM memory on chip. - -Temperatures are measured in degrees Celsius. There are two external -sensor inputs and one internal sensor. Each sensor has a high and low -limit. If the limit is exceeded, an interrupt (#SMBALERT) can be -generated. The interrupts can be masked. In addition, there are over-temp -limits for each sensor. If this limit is exceeded, the #THERM output will -be asserted. The current temperature and limits have a resolution of 1 -degree. - -Fan rotation speeds are reported in RPM (rotations per minute) but measured -in counts of a 22.5kHz internal clock. Each fan has a high limit which -corresponds to a minimum fan speed. If the limit is exceeded, an interrupt -can be generated. Each fan can be programmed to divide the reference clock -by 1, 2, 4 or 8. Not all RPM values can accurately be represented, so some -rounding is done. With a divider of 8, the slowest measurable speed of a -two pulse per revolution fan is 661 RPM. - -There are 17 voltage sensors. An alarm is triggered if the voltage has -crossed a programmable minimum or maximum limit. Note that minimum in this -case always means 'closest to zero'; this is important for negative voltage -measurements. Several inputs have integrated attenuators so they can measure -higher voltages directly. 3.3V, 5V, 12V, -12V and battery voltage all have -dedicated inputs. There are several inputs scaled to 0-3V full-scale range -for SCSI terminator power. The remaining inputs are not scaled and have -a 0-2.5V full-scale range. A 2.5V or 1.82V reference voltage is provided -for negative voltage measurements. - -If an alarm triggers, it will remain triggered until the hardware register -is read at least once. This means that the cause for the alarm may already -have disappeared! Note that in the current implementation, all hardware -registers are read whenever any data is read (unless it is less than 2.0 -seconds since the last update). This means that you can easily miss -once-only alarms. - -The ADM1026 measures continuously. Analog inputs are measured about 4 -times a second. Fan speed measurement time depends on fan speed and -divisor. It can take as long as 1.5 seconds to measure all fan speeds. - -The ADM1026 has the ability to automatically control fan speed based on the -temperature sensor inputs. Both the PWM output and the DAC output can be -used to control fan speed. Usually only one of these two outputs will be -used. Write the minimum PWM or DAC value to the appropriate control -register. Then set the low temperature limit in the tmin values for each -temperature sensor. The range of control is fixed at 20 °C, and the -largest difference between current and tmin of the temperature sensors sets -the control output. See the datasheet for several example circuits for -controlling fan speed with the PWM and DAC outputs. The fan speed sensors -do not have PWM compensation, so it is probably best to control the fan -voltage from the power lead rather than on the ground lead. - -The datasheet shows an example application with VID signals attached to -GPIO lines. Unfortunately, the chip may not be connected to the VID lines -in this way. The driver assumes that the chips *is* connected this way to -get a VID voltage. diff --git a/Documentation/hwmon/adm1026.rst b/Documentation/hwmon/adm1026.rst new file mode 100644 index 000000000000..35d63e6498a3 --- /dev/null +++ b/Documentation/hwmon/adm1026.rst @@ -0,0 +1,101 @@ +Kernel driver adm1026 +===================== + +Supported chips: + * Analog Devices ADM1026 + + Prefix: 'adm1026' + + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + + Datasheet: Publicly available at the Analog Devices website + + http://www.onsemi.com/PowerSolutions/product.do?id=ADM1026 + +Authors: + - Philip Pokorny for Penguin Computing + - Justin Thiessen + +Module Parameters +----------------- + +* gpio_input: int array (min = 1, max = 17) + List of GPIO pins (0-16) to program as inputs + +* gpio_output: int array (min = 1, max = 17) + List of GPIO pins (0-16) to program as outputs + +* gpio_inverted: int array (min = 1, max = 17) + List of GPIO pins (0-16) to program as inverted + +* gpio_normal: int array (min = 1, max = 17) + List of GPIO pins (0-16) to program as normal/non-inverted + +* gpio_fan: int array (min = 1, max = 8) + List of GPIO pins (0-7) to program as fan tachs + + +Description +----------- + +This driver implements support for the Analog Devices ADM1026. Analog +Devices calls it a "complete thermal system management controller." + +The ADM1026 implements three (3) temperature sensors, 17 voltage sensors, +16 general purpose digital I/O lines, eight (8) fan speed sensors (8-bit), +an analog output and a PWM output along with limit, alarm and mask bits for +all of the above. There is even 8k bytes of EEPROM memory on chip. + +Temperatures are measured in degrees Celsius. There are two external +sensor inputs and one internal sensor. Each sensor has a high and low +limit. If the limit is exceeded, an interrupt (#SMBALERT) can be +generated. The interrupts can be masked. In addition, there are over-temp +limits for each sensor. If this limit is exceeded, the #THERM output will +be asserted. The current temperature and limits have a resolution of 1 +degree. + +Fan rotation speeds are reported in RPM (rotations per minute) but measured +in counts of a 22.5kHz internal clock. Each fan has a high limit which +corresponds to a minimum fan speed. If the limit is exceeded, an interrupt +can be generated. Each fan can be programmed to divide the reference clock +by 1, 2, 4 or 8. Not all RPM values can accurately be represented, so some +rounding is done. With a divider of 8, the slowest measurable speed of a +two pulse per revolution fan is 661 RPM. + +There are 17 voltage sensors. An alarm is triggered if the voltage has +crossed a programmable minimum or maximum limit. Note that minimum in this +case always means 'closest to zero'; this is important for negative voltage +measurements. Several inputs have integrated attenuators so they can measure +higher voltages directly. 3.3V, 5V, 12V, -12V and battery voltage all have +dedicated inputs. There are several inputs scaled to 0-3V full-scale range +for SCSI terminator power. The remaining inputs are not scaled and have +a 0-2.5V full-scale range. A 2.5V or 1.82V reference voltage is provided +for negative voltage measurements. + +If an alarm triggers, it will remain triggered until the hardware register +is read at least once. This means that the cause for the alarm may already +have disappeared! Note that in the current implementation, all hardware +registers are read whenever any data is read (unless it is less than 2.0 +seconds since the last update). This means that you can easily miss +once-only alarms. + +The ADM1026 measures continuously. Analog inputs are measured about 4 +times a second. Fan speed measurement time depends on fan speed and +divisor. It can take as long as 1.5 seconds to measure all fan speeds. + +The ADM1026 has the ability to automatically control fan speed based on the +temperature sensor inputs. Both the PWM output and the DAC output can be +used to control fan speed. Usually only one of these two outputs will be +used. Write the minimum PWM or DAC value to the appropriate control +register. Then set the low temperature limit in the tmin values for each +temperature sensor. The range of control is fixed at 20 °C, and the +largest difference between current and tmin of the temperature sensors sets +the control output. See the datasheet for several example circuits for +controlling fan speed with the PWM and DAC outputs. The fan speed sensors +do not have PWM compensation, so it is probably best to control the fan +voltage from the power lead rather than on the ground lead. + +The datasheet shows an example application with VID signals attached to +GPIO lines. Unfortunately, the chip may not be connected to the VID lines +in this way. The driver assumes that the chips *is* connected this way to +get a VID voltage. diff --git a/Documentation/hwmon/adm1031 b/Documentation/hwmon/adm1031 deleted file mode 100644 index a677c3ab5574..000000000000 --- a/Documentation/hwmon/adm1031 +++ /dev/null @@ -1,43 +0,0 @@ -Kernel driver adm1031 -===================== - -Supported chips: - * Analog Devices ADM1030 - - Prefix: 'adm1030' - - Addresses scanned: I2C 0x2c to 0x2e - - Datasheet: Publicly available at the Analog Devices website - - http://www.analog.com/en/prod/0%2C2877%2CADM1030%2C00.html - - * Analog Devices ADM1031 - - Prefix: 'adm1031' - - Addresses scanned: I2C 0x2c to 0x2e - - Datasheet: Publicly available at the Analog Devices website - - http://www.analog.com/en/prod/0%2C2877%2CADM1031%2C00.html - -Authors: - - Alexandre d'Alton - - Jean Delvare - -Description ------------ - -The ADM1030 and ADM1031 are digital temperature sensors and fan controllers. -They sense their own temperature as well as the temperature of up to one -(ADM1030) or two (ADM1031) external diodes. - -All temperature values are given in degrees Celsius. Resolution is 0.5 -degree for the local temperature, 0.125 degree for the remote temperatures. - -Each temperature channel has its own high and low limits, plus a critical -limit. - -The ADM1030 monitors a single fan speed, while the ADM1031 monitors up to -two. Each fan channel has its own low speed limit. diff --git a/Documentation/hwmon/adm1031.rst b/Documentation/hwmon/adm1031.rst new file mode 100644 index 000000000000..a677c3ab5574 --- /dev/null +++ b/Documentation/hwmon/adm1031.rst @@ -0,0 +1,43 @@ +Kernel driver adm1031 +===================== + +Supported chips: + * Analog Devices ADM1030 + + Prefix: 'adm1030' + + Addresses scanned: I2C 0x2c to 0x2e + + Datasheet: Publicly available at the Analog Devices website + + http://www.analog.com/en/prod/0%2C2877%2CADM1030%2C00.html + + * Analog Devices ADM1031 + + Prefix: 'adm1031' + + Addresses scanned: I2C 0x2c to 0x2e + + Datasheet: Publicly available at the Analog Devices website + + http://www.analog.com/en/prod/0%2C2877%2CADM1031%2C00.html + +Authors: + - Alexandre d'Alton + - Jean Delvare + +Description +----------- + +The ADM1030 and ADM1031 are digital temperature sensors and fan controllers. +They sense their own temperature as well as the temperature of up to one +(ADM1030) or two (ADM1031) external diodes. + +All temperature values are given in degrees Celsius. Resolution is 0.5 +degree for the local temperature, 0.125 degree for the remote temperatures. + +Each temperature channel has its own high and low limits, plus a critical +limit. + +The ADM1030 monitors a single fan speed, while the ADM1031 monitors up to +two. Each fan channel has its own low speed limit. diff --git a/Documentation/hwmon/adm1275 b/Documentation/hwmon/adm1275 deleted file mode 100644 index 5c5860011d6e..000000000000 --- a/Documentation/hwmon/adm1275 +++ /dev/null @@ -1,148 +0,0 @@ -Kernel driver adm1275 -===================== - -Supported chips: - - * Analog Devices ADM1075 - - Prefix: 'adm1075' - - Addresses scanned: - - - Datasheet: www.analog.com/static/imported-files/data_sheets/ADM1075.pdf - - * Analog Devices ADM1272 - - Prefix: 'adm1272' - - Addresses scanned: - - - Datasheet: www.analog.com/static/imported-files/data_sheets/ADM1272.pdf - - * Analog Devices ADM1275 - - Prefix: 'adm1275' - - Addresses scanned: - - - Datasheet: www.analog.com/static/imported-files/data_sheets/ADM1275.pdf - - * Analog Devices ADM1276 - - Prefix: 'adm1276' - - Addresses scanned: - - - Datasheet: www.analog.com/static/imported-files/data_sheets/ADM1276.pdf - - * Analog Devices ADM1278 - - Prefix: 'adm1278' - - Addresses scanned: - - - Datasheet: www.analog.com/static/imported-files/data_sheets/ADM1278.pdf - - * Analog Devices ADM1293/ADM1294 - - Prefix: 'adm1293', 'adm1294' - - Addresses scanned: - - - Datasheet: http://www.analog.com/media/en/technical-documentation/data-sheets/ADM1293_1294.pdf - -Author: Guenter Roeck - - -Description ------------ - -This driver supports hardware monitoring for Analog Devices ADM1075, ADM1272, -ADM1275, ADM1276, ADM1278, ADM1293, and ADM1294 Hot-Swap Controller and -Digital Power Monitors. - -ADM1075, ADM1272, ADM1275, ADM1276, ADM1278, ADM1293, and ADM1294 are hot-swap -controllers that allow a circuit board to be removed from or inserted into -a live backplane. They also feature current and voltage readback via an -integrated 12 bit analog-to-digital converter (ADC), accessed using a -PMBus interface. - -The driver is a client driver to the core PMBus driver. Please see -Documentation/hwmon/pmbus for details on PMBus client drivers. - - -Usage Notes ------------ - -This driver does not auto-detect devices. You will have to instantiate the -devices explicitly. Please see Documentation/i2c/instantiating-devices for -details. - -The ADM1075, unlike many other PMBus devices, does not support internal voltage -or current scaling. Reported voltages, currents, and power are raw measurements, -and will typically have to be scaled. - -The shunt value in micro-ohms can be set via device tree at compile-time. Please -refer to the Documentation/devicetree/bindings/hwmon/adm1275.txt for bindings -if the device tree is used. - -Platform data support ---------------------- - -The driver supports standard PMBus driver platform data. Please see -Documentation/hwmon/pmbus for details. - - -Sysfs entries -------------- - -The following attributes are supported. Limits are read-write, history reset -attributes are write-only, all other attributes are read-only. - -======================= ======================================================= -inX_label "vin1" or "vout1" depending on chip variant and - configuration. On ADM1075, ADM1293, and ADM1294, - vout1 reports the voltage on the VAUX pin. -inX_input Measured voltage. -inX_min Minimum Voltage. -inX_max Maximum voltage. -inX_min_alarm Voltage low alarm. -inX_max_alarm Voltage high alarm. -inX_highest Historical maximum voltage. -inX_reset_history Write any value to reset history. - -curr1_label "iout1" -curr1_input Measured current. -curr1_max Maximum current. -curr1_max_alarm Current high alarm. -curr1_lcrit Critical minimum current. Depending on the chip - configuration, either curr1_lcrit or curr1_crit is - supported, but not both. -curr1_lcrit_alarm Critical current low alarm. -curr1_crit Critical maximum current. Depending on the chip - configuration, either curr1_lcrit or curr1_crit is - supported, but not both. -curr1_crit_alarm Critical current high alarm. -curr1_highest Historical maximum current. -curr1_reset_history Write any value to reset history. - -power1_label "pin1" -power1_input Input power. -power1_input_lowest Lowest observed input power. ADM1293 and ADM1294 only. -power1_input_highest Highest observed input power. -power1_reset_history Write any value to reset history. - - Power attributes are supported on ADM1075, ADM1272, - ADM1276, ADM1293, and ADM1294. - -temp1_input Chip temperature. -temp1_max Maximum chip temperature. -temp1_max_alarm Temperature alarm. -temp1_crit Critical chip temperature. -temp1_crit_alarm Critical temperature high alarm. -temp1_highest Highest observed temperature. -temp1_reset_history Write any value to reset history. - - Temperature attributes are supported on ADM1272 and - ADM1278. -======================= ======================================================= diff --git a/Documentation/hwmon/adm1275.rst b/Documentation/hwmon/adm1275.rst new file mode 100644 index 000000000000..9a1913e5b4d9 --- /dev/null +++ b/Documentation/hwmon/adm1275.rst @@ -0,0 +1,148 @@ +Kernel driver adm1275 +===================== + +Supported chips: + + * Analog Devices ADM1075 + + Prefix: 'adm1075' + + Addresses scanned: - + + Datasheet: www.analog.com/static/imported-files/data_sheets/ADM1075.pdf + + * Analog Devices ADM1272 + + Prefix: 'adm1272' + + Addresses scanned: - + + Datasheet: www.analog.com/static/imported-files/data_sheets/ADM1272.pdf + + * Analog Devices ADM1275 + + Prefix: 'adm1275' + + Addresses scanned: - + + Datasheet: www.analog.com/static/imported-files/data_sheets/ADM1275.pdf + + * Analog Devices ADM1276 + + Prefix: 'adm1276' + + Addresses scanned: - + + Datasheet: www.analog.com/static/imported-files/data_sheets/ADM1276.pdf + + * Analog Devices ADM1278 + + Prefix: 'adm1278' + + Addresses scanned: - + + Datasheet: www.analog.com/static/imported-files/data_sheets/ADM1278.pdf + + * Analog Devices ADM1293/ADM1294 + + Prefix: 'adm1293', 'adm1294' + + Addresses scanned: - + + Datasheet: http://www.analog.com/media/en/technical-documentation/data-sheets/ADM1293_1294.pdf + +Author: Guenter Roeck + + +Description +----------- + +This driver supports hardware monitoring for Analog Devices ADM1075, ADM1272, +ADM1275, ADM1276, ADM1278, ADM1293, and ADM1294 Hot-Swap Controller and +Digital Power Monitors. + +ADM1075, ADM1272, ADM1275, ADM1276, ADM1278, ADM1293, and ADM1294 are hot-swap +controllers that allow a circuit board to be removed from or inserted into +a live backplane. They also feature current and voltage readback via an +integrated 12 bit analog-to-digital converter (ADC), accessed using a +PMBus interface. + +The driver is a client driver to the core PMBus driver. Please see +Documentation/hwmon/pmbus.rst for details on PMBus client drivers. + + +Usage Notes +----------- + +This driver does not auto-detect devices. You will have to instantiate the +devices explicitly. Please see Documentation/i2c/instantiating-devices for +details. + +The ADM1075, unlike many other PMBus devices, does not support internal voltage +or current scaling. Reported voltages, currents, and power are raw measurements, +and will typically have to be scaled. + +The shunt value in micro-ohms can be set via device tree at compile-time. Please +refer to the Documentation/devicetree/bindings/hwmon/adm1275.txt for bindings +if the device tree is used. + +Platform data support +--------------------- + +The driver supports standard PMBus driver platform data. Please see +Documentation/hwmon/pmbus.rst for details. + + +Sysfs entries +------------- + +The following attributes are supported. Limits are read-write, history reset +attributes are write-only, all other attributes are read-only. + +======================= ======================================================= +inX_label "vin1" or "vout1" depending on chip variant and + configuration. On ADM1075, ADM1293, and ADM1294, + vout1 reports the voltage on the VAUX pin. +inX_input Measured voltage. +inX_min Minimum Voltage. +inX_max Maximum voltage. +inX_min_alarm Voltage low alarm. +inX_max_alarm Voltage high alarm. +inX_highest Historical maximum voltage. +inX_reset_history Write any value to reset history. + +curr1_label "iout1" +curr1_input Measured current. +curr1_max Maximum current. +curr1_max_alarm Current high alarm. +curr1_lcrit Critical minimum current. Depending on the chip + configuration, either curr1_lcrit or curr1_crit is + supported, but not both. +curr1_lcrit_alarm Critical current low alarm. +curr1_crit Critical maximum current. Depending on the chip + configuration, either curr1_lcrit or curr1_crit is + supported, but not both. +curr1_crit_alarm Critical current high alarm. +curr1_highest Historical maximum current. +curr1_reset_history Write any value to reset history. + +power1_label "pin1" +power1_input Input power. +power1_input_lowest Lowest observed input power. ADM1293 and ADM1294 only. +power1_input_highest Highest observed input power. +power1_reset_history Write any value to reset history. + + Power attributes are supported on ADM1075, ADM1272, + ADM1276, ADM1293, and ADM1294. + +temp1_input Chip temperature. +temp1_max Maximum chip temperature. +temp1_max_alarm Temperature alarm. +temp1_crit Critical chip temperature. +temp1_crit_alarm Critical temperature high alarm. +temp1_highest Highest observed temperature. +temp1_reset_history Write any value to reset history. + + Temperature attributes are supported on ADM1272 and + ADM1278. +======================= ======================================================= diff --git a/Documentation/hwmon/adm9240 b/Documentation/hwmon/adm9240 deleted file mode 100644 index 91063b0f4c6f..000000000000 --- a/Documentation/hwmon/adm9240 +++ /dev/null @@ -1,201 +0,0 @@ -Kernel driver adm9240 -===================== - -Supported chips: - - * Analog Devices ADM9240 - - Prefix: 'adm9240' - - Addresses scanned: I2C 0x2c - 0x2f - - Datasheet: Publicly available at the Analog Devices website - - http://www.analog.com/UploadedFiles/Data_Sheets/79857778ADM9240_0.pdf - - * Dallas Semiconductor DS1780 - - Prefix: 'ds1780' - - Addresses scanned: I2C 0x2c - 0x2f - - Datasheet: Publicly available at the Dallas Semiconductor (Maxim) website - - http://pdfserv.maxim-ic.com/en/ds/DS1780.pdf - - * National Semiconductor LM81 - - Prefix: 'lm81' - - Addresses scanned: I2C 0x2c - 0x2f - - Datasheet: Publicly available at the National Semiconductor website - - http://www.national.com/ds.cgi/LM/LM81.pdf - -Authors: - - Frodo Looijaard , - - Philip Edelbrock , - - Michiel Rook , - - Grant Coady with guidance - from Jean Delvare - -Interface ---------- -The I2C addresses listed above assume BIOS has not changed the -chip MSB 5-bit address. Each chip reports a unique manufacturer -identification code as well as the chip revision/stepping level. - -Description ------------ -[From ADM9240] The ADM9240 is a complete system hardware monitor for -microprocessor-based systems, providing measurement and limit comparison -of up to four power supplies and two processor core voltages, plus -temperature, two fan speeds and chassis intrusion. Measured values can -be read out via an I2C-compatible serial System Management Bus, and values -for limit comparisons can be programmed in over the same serial bus. The -high speed successive approximation ADC allows frequent sampling of all -analog channels to ensure a fast interrupt response to any out-of-limit -measurement. - -The ADM9240, DS1780 and LM81 are register compatible, the following -details are common to the three chips. Chip differences are described -after this section. - - -Measurements ------------- -The measurement cycle - -The adm9240 driver will take a measurement reading no faster than once -each two seconds. User-space may read sysfs interface faster than the -measurement update rate and will receive cached data from the most -recent measurement. - -ADM9240 has a very fast 320us temperature and voltage measurement cycle -with independent fan speed measurement cycles counting alternating rising -edges of the fan tacho inputs. - -DS1780 measurement cycle is about once per second including fan speed. - -LM81 measurement cycle is about once per 400ms including fan speed. -The LM81 12-bit extended temperature measurement mode is not supported. - -Temperature ------------ -On chip temperature is reported as degrees Celsius as 9-bit signed data -with resolution of 0.5 degrees Celsius. High and low temperature limits -are 8-bit signed data with resolution of one degree Celsius. - -Temperature alarm is asserted once the temperature exceeds the high limit, -and is cleared when the temperature falls below the temp1_max_hyst value. - -Fan Speed ---------- -Two fan tacho inputs are provided, the ADM9240 gates an internal 22.5kHz -clock via a divider to an 8-bit counter. Fan speed (rpm) is calculated by: - -rpm = (22500 * 60) / (count * divider) - -Automatic fan clock divider - - * User sets 0 to fan_min limit - - - low speed alarm is disabled - - fan clock divider not changed - - auto fan clock adjuster enabled for valid fan speed reading - - * User sets fan_min limit too low - - - low speed alarm is enabled - - fan clock divider set to max - - fan_min set to register value 254 which corresponds - to 664 rpm on adm9240 - - low speed alarm will be asserted if fan speed is - less than minimum measurable speed - - auto fan clock adjuster disabled - - * User sets reasonable fan speed - - - low speed alarm is enabled - - fan clock divider set to suit fan_min - - auto fan clock adjuster enabled: adjusts fan_min - - * User sets unreasonably high low fan speed limit - - - resolution of the low speed limit may be reduced - - alarm will be asserted - - auto fan clock adjuster enabled: adjusts fan_min - - * fan speed may be displayed as zero until the auto fan clock divider - adjuster brings fan speed clock divider back into chip measurement - range, this will occur within a few measurement cycles. - -Analog Output -------------- -An analog output provides a 0 to 1.25 volt signal intended for an external -fan speed amplifier circuit. The analog output is set to maximum value on -power up or reset. This doesn't do much on the test Intel SE440BX-2. - -Voltage Monitor - -^^^^^^^^^^^^^^^ - -Voltage (IN) measurement is internally scaled: - - === =========== =========== ========= ========== - nr label nominal maximum resolution - mV mV mV - === =========== =========== ========= ========== - 0 +2.5V 2500 3320 13.0 - 1 Vccp1 2700 3600 14.1 - 2 +3.3V 3300 4380 17.2 - 3 +5V 5000 6640 26.0 - 4 +12V 12000 15940 62.5 - 5 Vccp2 2700 3600 14.1 - === =========== =========== ========= ========== - -The reading is an unsigned 8-bit value, nominal voltage measurement is -represented by a reading of 192, being 3/4 of the measurement range. - -An alarm is asserted for any voltage going below or above the set limits. - -The driver reports and accepts voltage limits scaled to the above table. - -VID Monitor ------------ -The chip has five inputs to read the 5-bit VID and reports the mV value -based on detected CPU type. - -Chassis Intrusion ------------------ -An alarm is asserted when the CI pin goes active high. The ADM9240 -Datasheet has an example of an external temperature sensor driving -this pin. On an Intel SE440BX-2 the Chassis Intrusion header is -connected to a normally open switch. - -The ADM9240 provides an internal open drain on this line, and may output -a 20 ms active low pulse to reset an external Chassis Intrusion latch. - -Clear the CI latch by writing value 0 to the sysfs intrusion0_alarm file. - -Alarm flags reported as 16-bit word - - === ============= ========================== - bit label comment - === ============= ========================== - 0 +2.5 V_Error high or low limit exceeded - 1 VCCP_Error high or low limit exceeded - 2 +3.3 V_Error high or low limit exceeded - 3 +5 V_Error high or low limit exceeded - 4 Temp_Error temperature error - 6 FAN1_Error fan low limit exceeded - 7 FAN2_Error fan low limit exceeded - 8 +12 V_Error high or low limit exceeded - 9 VCCP2_Error high or low limit exceeded - 12 Chassis_Error CI pin went high - === ============= ========================== - -Remaining bits are reserved and thus undefined. It is important to note -that alarm bits may be cleared on read, user-space may latch alarms and -provide the end-user with a method to clear alarm memory. diff --git a/Documentation/hwmon/adm9240.rst b/Documentation/hwmon/adm9240.rst new file mode 100644 index 000000000000..91063b0f4c6f --- /dev/null +++ b/Documentation/hwmon/adm9240.rst @@ -0,0 +1,201 @@ +Kernel driver adm9240 +===================== + +Supported chips: + + * Analog Devices ADM9240 + + Prefix: 'adm9240' + + Addresses scanned: I2C 0x2c - 0x2f + + Datasheet: Publicly available at the Analog Devices website + + http://www.analog.com/UploadedFiles/Data_Sheets/79857778ADM9240_0.pdf + + * Dallas Semiconductor DS1780 + + Prefix: 'ds1780' + + Addresses scanned: I2C 0x2c - 0x2f + + Datasheet: Publicly available at the Dallas Semiconductor (Maxim) website + + http://pdfserv.maxim-ic.com/en/ds/DS1780.pdf + + * National Semiconductor LM81 + + Prefix: 'lm81' + + Addresses scanned: I2C 0x2c - 0x2f + + Datasheet: Publicly available at the National Semiconductor website + + http://www.national.com/ds.cgi/LM/LM81.pdf + +Authors: + - Frodo Looijaard , + - Philip Edelbrock , + - Michiel Rook , + - Grant Coady with guidance + from Jean Delvare + +Interface +--------- +The I2C addresses listed above assume BIOS has not changed the +chip MSB 5-bit address. Each chip reports a unique manufacturer +identification code as well as the chip revision/stepping level. + +Description +----------- +[From ADM9240] The ADM9240 is a complete system hardware monitor for +microprocessor-based systems, providing measurement and limit comparison +of up to four power supplies and two processor core voltages, plus +temperature, two fan speeds and chassis intrusion. Measured values can +be read out via an I2C-compatible serial System Management Bus, and values +for limit comparisons can be programmed in over the same serial bus. The +high speed successive approximation ADC allows frequent sampling of all +analog channels to ensure a fast interrupt response to any out-of-limit +measurement. + +The ADM9240, DS1780 and LM81 are register compatible, the following +details are common to the three chips. Chip differences are described +after this section. + + +Measurements +------------ +The measurement cycle + +The adm9240 driver will take a measurement reading no faster than once +each two seconds. User-space may read sysfs interface faster than the +measurement update rate and will receive cached data from the most +recent measurement. + +ADM9240 has a very fast 320us temperature and voltage measurement cycle +with independent fan speed measurement cycles counting alternating rising +edges of the fan tacho inputs. + +DS1780 measurement cycle is about once per second including fan speed. + +LM81 measurement cycle is about once per 400ms including fan speed. +The LM81 12-bit extended temperature measurement mode is not supported. + +Temperature +----------- +On chip temperature is reported as degrees Celsius as 9-bit signed data +with resolution of 0.5 degrees Celsius. High and low temperature limits +are 8-bit signed data with resolution of one degree Celsius. + +Temperature alarm is asserted once the temperature exceeds the high limit, +and is cleared when the temperature falls below the temp1_max_hyst value. + +Fan Speed +--------- +Two fan tacho inputs are provided, the ADM9240 gates an internal 22.5kHz +clock via a divider to an 8-bit counter. Fan speed (rpm) is calculated by: + +rpm = (22500 * 60) / (count * divider) + +Automatic fan clock divider + + * User sets 0 to fan_min limit + + - low speed alarm is disabled + - fan clock divider not changed + - auto fan clock adjuster enabled for valid fan speed reading + + * User sets fan_min limit too low + + - low speed alarm is enabled + - fan clock divider set to max + - fan_min set to register value 254 which corresponds + to 664 rpm on adm9240 + - low speed alarm will be asserted if fan speed is + less than minimum measurable speed + - auto fan clock adjuster disabled + + * User sets reasonable fan speed + + - low speed alarm is enabled + - fan clock divider set to suit fan_min + - auto fan clock adjuster enabled: adjusts fan_min + + * User sets unreasonably high low fan speed limit + + - resolution of the low speed limit may be reduced + - alarm will be asserted + - auto fan clock adjuster enabled: adjusts fan_min + + * fan speed may be displayed as zero until the auto fan clock divider + adjuster brings fan speed clock divider back into chip measurement + range, this will occur within a few measurement cycles. + +Analog Output +------------- +An analog output provides a 0 to 1.25 volt signal intended for an external +fan speed amplifier circuit. The analog output is set to maximum value on +power up or reset. This doesn't do much on the test Intel SE440BX-2. + +Voltage Monitor + +^^^^^^^^^^^^^^^ + +Voltage (IN) measurement is internally scaled: + + === =========== =========== ========= ========== + nr label nominal maximum resolution + mV mV mV + === =========== =========== ========= ========== + 0 +2.5V 2500 3320 13.0 + 1 Vccp1 2700 3600 14.1 + 2 +3.3V 3300 4380 17.2 + 3 +5V 5000 6640 26.0 + 4 +12V 12000 15940 62.5 + 5 Vccp2 2700 3600 14.1 + === =========== =========== ========= ========== + +The reading is an unsigned 8-bit value, nominal voltage measurement is +represented by a reading of 192, being 3/4 of the measurement range. + +An alarm is asserted for any voltage going below or above the set limits. + +The driver reports and accepts voltage limits scaled to the above table. + +VID Monitor +----------- +The chip has five inputs to read the 5-bit VID and reports the mV value +based on detected CPU type. + +Chassis Intrusion +----------------- +An alarm is asserted when the CI pin goes active high. The ADM9240 +Datasheet has an example of an external temperature sensor driving +this pin. On an Intel SE440BX-2 the Chassis Intrusion header is +connected to a normally open switch. + +The ADM9240 provides an internal open drain on this line, and may output +a 20 ms active low pulse to reset an external Chassis Intrusion latch. + +Clear the CI latch by writing value 0 to the sysfs intrusion0_alarm file. + +Alarm flags reported as 16-bit word + + === ============= ========================== + bit label comment + === ============= ========================== + 0 +2.5 V_Error high or low limit exceeded + 1 VCCP_Error high or low limit exceeded + 2 +3.3 V_Error high or low limit exceeded + 3 +5 V_Error high or low limit exceeded + 4 Temp_Error temperature error + 6 FAN1_Error fan low limit exceeded + 7 FAN2_Error fan low limit exceeded + 8 +12 V_Error high or low limit exceeded + 9 VCCP2_Error high or low limit exceeded + 12 Chassis_Error CI pin went high + === ============= ========================== + +Remaining bits are reserved and thus undefined. It is important to note +that alarm bits may be cleared on read, user-space may latch alarms and +provide the end-user with a method to clear alarm memory. diff --git a/Documentation/hwmon/ads1015 b/Documentation/hwmon/ads1015 deleted file mode 100644 index e0951c4e57bb..000000000000 --- a/Documentation/hwmon/ads1015 +++ /dev/null @@ -1,90 +0,0 @@ -Kernel driver ads1015 -===================== - -Supported chips: - - * Texas Instruments ADS1015 - - Prefix: 'ads1015' - - Datasheet: Publicly available at the Texas Instruments website: - - http://focus.ti.com/lit/ds/symlink/ads1015.pdf - - * Texas Instruments ADS1115 - - Prefix: 'ads1115' - - Datasheet: Publicly available at the Texas Instruments website: - - http://focus.ti.com/lit/ds/symlink/ads1115.pdf - -Authors: - Dirk Eibach, Guntermann & Drunck GmbH - -Description ------------ - -This driver implements support for the Texas Instruments ADS1015/ADS1115. - -This device is a 12/16-bit A-D converter with 4 inputs. - -The inputs can be used single ended or in certain differential combinations. - -The inputs can be made available by 8 sysfs input files in0_input - in7_input: - - - in0: Voltage over AIN0 and AIN1. - - in1: Voltage over AIN0 and AIN3. - - in2: Voltage over AIN1 and AIN3. - - in3: Voltage over AIN2 and AIN3. - - in4: Voltage over AIN0 and GND. - - in5: Voltage over AIN1 and GND. - - in6: Voltage over AIN2 and GND. - - in7: Voltage over AIN3 and GND. - -Which inputs are available can be configured using platform data or devicetree. - -By default all inputs are exported. - -Platform Data -------------- - -In linux/platform_data/ads1015.h platform data is defined, channel_data contains -configuration data for the used input combinations: - -- pga is the programmable gain amplifier (values are full scale) - - - 0: +/- 6.144 V - - 1: +/- 4.096 V - - 2: +/- 2.048 V - - 3: +/- 1.024 V - - 4: +/- 0.512 V - - 5: +/- 0.256 V - -- data_rate in samples per second - - - 0: 128 - - 1: 250 - - 2: 490 - - 3: 920 - - 4: 1600 - - 5: 2400 - - 6: 3300 - -Example:: - - struct ads1015_platform_data data = { - .channel_data = { - [2] = { .enabled = true, .pga = 1, .data_rate = 0 }, - [4] = { .enabled = true, .pga = 4, .data_rate = 5 }, - } - }; - -In this case only in2_input (FS +/- 4.096 V, 128 SPS) and in4_input -(FS +/- 0.512 V, 2400 SPS) would be created. - -Devicetree ----------- - -Configuration is also possible via devicetree: -Documentation/devicetree/bindings/hwmon/ads1015.txt diff --git a/Documentation/hwmon/ads1015.rst b/Documentation/hwmon/ads1015.rst new file mode 100644 index 000000000000..e0951c4e57bb --- /dev/null +++ b/Documentation/hwmon/ads1015.rst @@ -0,0 +1,90 @@ +Kernel driver ads1015 +===================== + +Supported chips: + + * Texas Instruments ADS1015 + + Prefix: 'ads1015' + + Datasheet: Publicly available at the Texas Instruments website: + + http://focus.ti.com/lit/ds/symlink/ads1015.pdf + + * Texas Instruments ADS1115 + + Prefix: 'ads1115' + + Datasheet: Publicly available at the Texas Instruments website: + + http://focus.ti.com/lit/ds/symlink/ads1115.pdf + +Authors: + Dirk Eibach, Guntermann & Drunck GmbH + +Description +----------- + +This driver implements support for the Texas Instruments ADS1015/ADS1115. + +This device is a 12/16-bit A-D converter with 4 inputs. + +The inputs can be used single ended or in certain differential combinations. + +The inputs can be made available by 8 sysfs input files in0_input - in7_input: + + - in0: Voltage over AIN0 and AIN1. + - in1: Voltage over AIN0 and AIN3. + - in2: Voltage over AIN1 and AIN3. + - in3: Voltage over AIN2 and AIN3. + - in4: Voltage over AIN0 and GND. + - in5: Voltage over AIN1 and GND. + - in6: Voltage over AIN2 and GND. + - in7: Voltage over AIN3 and GND. + +Which inputs are available can be configured using platform data or devicetree. + +By default all inputs are exported. + +Platform Data +------------- + +In linux/platform_data/ads1015.h platform data is defined, channel_data contains +configuration data for the used input combinations: + +- pga is the programmable gain amplifier (values are full scale) + + - 0: +/- 6.144 V + - 1: +/- 4.096 V + - 2: +/- 2.048 V + - 3: +/- 1.024 V + - 4: +/- 0.512 V + - 5: +/- 0.256 V + +- data_rate in samples per second + + - 0: 128 + - 1: 250 + - 2: 490 + - 3: 920 + - 4: 1600 + - 5: 2400 + - 6: 3300 + +Example:: + + struct ads1015_platform_data data = { + .channel_data = { + [2] = { .enabled = true, .pga = 1, .data_rate = 0 }, + [4] = { .enabled = true, .pga = 4, .data_rate = 5 }, + } + }; + +In this case only in2_input (FS +/- 4.096 V, 128 SPS) and in4_input +(FS +/- 0.512 V, 2400 SPS) would be created. + +Devicetree +---------- + +Configuration is also possible via devicetree: +Documentation/devicetree/bindings/hwmon/ads1015.txt diff --git a/Documentation/hwmon/ads7828 b/Documentation/hwmon/ads7828 deleted file mode 100644 index b830b490cfe4..000000000000 --- a/Documentation/hwmon/ads7828 +++ /dev/null @@ -1,65 +0,0 @@ -Kernel driver ads7828 -===================== - -Supported chips: - - * Texas Instruments/Burr-Brown ADS7828 - - Prefix: 'ads7828' - - Datasheet: Publicly available at the Texas Instruments website: - - http://focus.ti.com/lit/ds/symlink/ads7828.pdf - - * Texas Instruments ADS7830 - - Prefix: 'ads7830' - - Datasheet: Publicly available at the Texas Instruments website: - - http://focus.ti.com/lit/ds/symlink/ads7830.pdf - -Authors: - - Steve Hardy - - Vivien Didelot - - Guillaume Roguez - -Platform data -------------- - -The ads7828 driver accepts an optional ads7828_platform_data structure (defined -in include/linux/platform_data/ads7828.h). The structure fields are: - -* diff_input: (bool) Differential operation - set to true for differential mode, false for default single ended mode. - -* ext_vref: (bool) External reference - set to true if it operates with an external reference, false for default - internal reference. - -* vref_mv: (unsigned int) Voltage reference - if using an external reference, set this to the reference voltage in mV, - otherwise it will default to the internal value (2500mV). This value will be - bounded with limits accepted by the chip, described in the datasheet. - - If no structure is provided, the configuration defaults to single ended - operation and internal voltage reference (2.5V). - -Description ------------ - -This driver implements support for the Texas Instruments ADS7828 and ADS7830. - -The ADS7828 device is a 12-bit 8-channel A/D converter, while the ADS7830 does -8-bit sampling. - -It can operate in single ended mode (8 +ve inputs) or in differential mode, -where 4 differential pairs can be measured. - -The chip also has the facility to use an external voltage reference. This -may be required if your hardware supplies the ADS7828 from a 5V supply, see -the datasheet for more details. - -There is no reliable way to identify this chip, so the driver will not scan -some addresses to try to auto-detect it. That means that you will have to -statically declare the device in the platform support code. diff --git a/Documentation/hwmon/ads7828.rst b/Documentation/hwmon/ads7828.rst new file mode 100644 index 000000000000..b830b490cfe4 --- /dev/null +++ b/Documentation/hwmon/ads7828.rst @@ -0,0 +1,65 @@ +Kernel driver ads7828 +===================== + +Supported chips: + + * Texas Instruments/Burr-Brown ADS7828 + + Prefix: 'ads7828' + + Datasheet: Publicly available at the Texas Instruments website: + + http://focus.ti.com/lit/ds/symlink/ads7828.pdf + + * Texas Instruments ADS7830 + + Prefix: 'ads7830' + + Datasheet: Publicly available at the Texas Instruments website: + + http://focus.ti.com/lit/ds/symlink/ads7830.pdf + +Authors: + - Steve Hardy + - Vivien Didelot + - Guillaume Roguez + +Platform data +------------- + +The ads7828 driver accepts an optional ads7828_platform_data structure (defined +in include/linux/platform_data/ads7828.h). The structure fields are: + +* diff_input: (bool) Differential operation + set to true for differential mode, false for default single ended mode. + +* ext_vref: (bool) External reference + set to true if it operates with an external reference, false for default + internal reference. + +* vref_mv: (unsigned int) Voltage reference + if using an external reference, set this to the reference voltage in mV, + otherwise it will default to the internal value (2500mV). This value will be + bounded with limits accepted by the chip, described in the datasheet. + + If no structure is provided, the configuration defaults to single ended + operation and internal voltage reference (2.5V). + +Description +----------- + +This driver implements support for the Texas Instruments ADS7828 and ADS7830. + +The ADS7828 device is a 12-bit 8-channel A/D converter, while the ADS7830 does +8-bit sampling. + +It can operate in single ended mode (8 +ve inputs) or in differential mode, +where 4 differential pairs can be measured. + +The chip also has the facility to use an external voltage reference. This +may be required if your hardware supplies the ADS7828 from a 5V supply, see +the datasheet for more details. + +There is no reliable way to identify this chip, so the driver will not scan +some addresses to try to auto-detect it. That means that you will have to +statically declare the device in the platform support code. diff --git a/Documentation/hwmon/adt7410 b/Documentation/hwmon/adt7410 deleted file mode 100644 index 24caaa83c8ec..000000000000 --- a/Documentation/hwmon/adt7410 +++ /dev/null @@ -1,94 +0,0 @@ -Kernel driver adt7410 -===================== - -Supported chips: - - * Analog Devices ADT7410 - - Prefix: 'adt7410' - - Addresses scanned: None - - Datasheet: Publicly available at the Analog Devices website - - http://www.analog.com/static/imported-files/data_sheets/ADT7410.pdf - * Analog Devices ADT7420 - - Prefix: 'adt7420' - - Addresses scanned: None - - Datasheet: Publicly available at the Analog Devices website - - http://www.analog.com/static/imported-files/data_sheets/ADT7420.pdf - - * Analog Devices ADT7310 - - Prefix: 'adt7310' - - Addresses scanned: None - - Datasheet: Publicly available at the Analog Devices website - - http://www.analog.com/static/imported-files/data_sheets/ADT7310.pdf - - * Analog Devices ADT7320 - - Prefix: 'adt7320' - - Addresses scanned: None - - Datasheet: Publicly available at the Analog Devices website - - http://www.analog.com/static/imported-files/data_sheets/ADT7320.pdf - -Author: Hartmut Knaack - -Description ------------ - -The ADT7310/ADT7410 is a temperature sensor with rated temperature range of --55°C to +150°C. It has a high accuracy of +/-0.5°C and can be operated at a -resolution of 13 bits (0.0625°C) or 16 bits (0.0078°C). The sensor provides an -INT pin to indicate that a minimum or maximum temperature set point has been -exceeded, as well as a critical temperature (CT) pin to indicate that the -critical temperature set point has been exceeded. Both pins can be set up with a -common hysteresis of 0°C - 15°C and a fault queue, ranging from 1 to 4 events. -Both pins can individually set to be active-low or active-high, while the whole -device can either run in comparator mode or interrupt mode. The ADT7410 supports -continuous temperature sampling, as well as sampling one temperature value per -second or even just get one sample on demand for power saving. Besides, it can -completely power down its ADC, if power management is required. - -The ADT7320/ADT7420 is register compatible, the only differences being the -package, a slightly narrower operating temperature range (-40°C to +150°C), and -a better accuracy (0.25°C instead of 0.50°C.) - -The difference between the ADT7310/ADT7320 and ADT7410/ADT7420 is the control -interface, the ADT7310 and ADT7320 use SPI while the ADT7410 and ADT7420 use -I2C. - -Configuration Notes -------------------- - -Since the device uses one hysteresis value, which is an offset to minimum, -maximum and critical temperature, it can only be set for temp#_max_hyst. -However, temp#_min_hyst and temp#_crit_hyst show their corresponding -hysteresis. -The device is set to 16 bit resolution and comparator mode. - -sysfs-Interface ---------------- - -======================== ==================================================== -temp#_input temperature input -temp#_min temperature minimum setpoint -temp#_max temperature maximum setpoint -temp#_crit critical temperature setpoint -temp#_min_hyst hysteresis for temperature minimum (read-only) -temp#_max_hyst hysteresis for temperature maximum (read/write) -temp#_crit_hyst hysteresis for critical temperature (read-only) -temp#_min_alarm temperature minimum alarm flag -temp#_max_alarm temperature maximum alarm flag -temp#_crit_alarm critical temperature alarm flag -======================== ==================================================== diff --git a/Documentation/hwmon/adt7410.rst b/Documentation/hwmon/adt7410.rst new file mode 100644 index 000000000000..24caaa83c8ec --- /dev/null +++ b/Documentation/hwmon/adt7410.rst @@ -0,0 +1,94 @@ +Kernel driver adt7410 +===================== + +Supported chips: + + * Analog Devices ADT7410 + + Prefix: 'adt7410' + + Addresses scanned: None + + Datasheet: Publicly available at the Analog Devices website + + http://www.analog.com/static/imported-files/data_sheets/ADT7410.pdf + * Analog Devices ADT7420 + + Prefix: 'adt7420' + + Addresses scanned: None + + Datasheet: Publicly available at the Analog Devices website + + http://www.analog.com/static/imported-files/data_sheets/ADT7420.pdf + + * Analog Devices ADT7310 + + Prefix: 'adt7310' + + Addresses scanned: None + + Datasheet: Publicly available at the Analog Devices website + + http://www.analog.com/static/imported-files/data_sheets/ADT7310.pdf + + * Analog Devices ADT7320 + + Prefix: 'adt7320' + + Addresses scanned: None + + Datasheet: Publicly available at the Analog Devices website + + http://www.analog.com/static/imported-files/data_sheets/ADT7320.pdf + +Author: Hartmut Knaack + +Description +----------- + +The ADT7310/ADT7410 is a temperature sensor with rated temperature range of +-55°C to +150°C. It has a high accuracy of +/-0.5°C and can be operated at a +resolution of 13 bits (0.0625°C) or 16 bits (0.0078°C). The sensor provides an +INT pin to indicate that a minimum or maximum temperature set point has been +exceeded, as well as a critical temperature (CT) pin to indicate that the +critical temperature set point has been exceeded. Both pins can be set up with a +common hysteresis of 0°C - 15°C and a fault queue, ranging from 1 to 4 events. +Both pins can individually set to be active-low or active-high, while the whole +device can either run in comparator mode or interrupt mode. The ADT7410 supports +continuous temperature sampling, as well as sampling one temperature value per +second or even just get one sample on demand for power saving. Besides, it can +completely power down its ADC, if power management is required. + +The ADT7320/ADT7420 is register compatible, the only differences being the +package, a slightly narrower operating temperature range (-40°C to +150°C), and +a better accuracy (0.25°C instead of 0.50°C.) + +The difference between the ADT7310/ADT7320 and ADT7410/ADT7420 is the control +interface, the ADT7310 and ADT7320 use SPI while the ADT7410 and ADT7420 use +I2C. + +Configuration Notes +------------------- + +Since the device uses one hysteresis value, which is an offset to minimum, +maximum and critical temperature, it can only be set for temp#_max_hyst. +However, temp#_min_hyst and temp#_crit_hyst show their corresponding +hysteresis. +The device is set to 16 bit resolution and comparator mode. + +sysfs-Interface +--------------- + +======================== ==================================================== +temp#_input temperature input +temp#_min temperature minimum setpoint +temp#_max temperature maximum setpoint +temp#_crit critical temperature setpoint +temp#_min_hyst hysteresis for temperature minimum (read-only) +temp#_max_hyst hysteresis for temperature maximum (read/write) +temp#_crit_hyst hysteresis for critical temperature (read-only) +temp#_min_alarm temperature minimum alarm flag +temp#_max_alarm temperature maximum alarm flag +temp#_crit_alarm critical temperature alarm flag +======================== ==================================================== diff --git a/Documentation/hwmon/adt7411 b/Documentation/hwmon/adt7411 deleted file mode 100644 index 57ad16fb216a..000000000000 --- a/Documentation/hwmon/adt7411 +++ /dev/null @@ -1,50 +0,0 @@ -Kernel driver adt7411 -===================== - -Supported chips: - - * Analog Devices ADT7411 - - Prefix: 'adt7411' - - Addresses scanned: 0x48, 0x4a, 0x4b - - Datasheet: Publicly available at the Analog Devices website - -Author: Wolfram Sang (based on adt7470 by Darrick J. Wong) - -Description ------------ - -This driver implements support for the Analog Devices ADT7411 chip. There may -be other chips that implement this interface. - -The ADT7411 can use an I2C/SMBus compatible 2-wire interface or an -SPI-compatible 4-wire interface. It provides a 10-bit analog to digital -converter which measures 1 temperature, vdd and 8 input voltages. It has an -internal temperature sensor, but an external one can also be connected (one -loses 2 inputs then). There are high- and low-limit registers for all inputs. - -Check the datasheet for details. - -sysfs-Interface ---------------- - -================ ================= -in0_input vdd voltage input -in[1-8]_input analog 1-8 input -temp1_input temperature input -================ ================= - -Besides standard interfaces, this driver adds (0 = off, 1 = on): - - ============== ======================================================= - adc_ref_vdd Use vdd as reference instead of 2.25 V - fast_sampling Sample at 22.5 kHz instead of 1.4 kHz, but drop filters - no_average Turn off averaging over 16 samples - ============== ======================================================= - -Notes ------ - -SPI, external temperature sensor and limit registers are not supported yet. diff --git a/Documentation/hwmon/adt7411.rst b/Documentation/hwmon/adt7411.rst new file mode 100644 index 000000000000..57ad16fb216a --- /dev/null +++ b/Documentation/hwmon/adt7411.rst @@ -0,0 +1,50 @@ +Kernel driver adt7411 +===================== + +Supported chips: + + * Analog Devices ADT7411 + + Prefix: 'adt7411' + + Addresses scanned: 0x48, 0x4a, 0x4b + + Datasheet: Publicly available at the Analog Devices website + +Author: Wolfram Sang (based on adt7470 by Darrick J. Wong) + +Description +----------- + +This driver implements support for the Analog Devices ADT7411 chip. There may +be other chips that implement this interface. + +The ADT7411 can use an I2C/SMBus compatible 2-wire interface or an +SPI-compatible 4-wire interface. It provides a 10-bit analog to digital +converter which measures 1 temperature, vdd and 8 input voltages. It has an +internal temperature sensor, but an external one can also be connected (one +loses 2 inputs then). There are high- and low-limit registers for all inputs. + +Check the datasheet for details. + +sysfs-Interface +--------------- + +================ ================= +in0_input vdd voltage input +in[1-8]_input analog 1-8 input +temp1_input temperature input +================ ================= + +Besides standard interfaces, this driver adds (0 = off, 1 = on): + + ============== ======================================================= + adc_ref_vdd Use vdd as reference instead of 2.25 V + fast_sampling Sample at 22.5 kHz instead of 1.4 kHz, but drop filters + no_average Turn off averaging over 16 samples + ============== ======================================================= + +Notes +----- + +SPI, external temperature sensor and limit registers are not supported yet. diff --git a/Documentation/hwmon/adt7462 b/Documentation/hwmon/adt7462 deleted file mode 100644 index a7a831118d32..000000000000 --- a/Documentation/hwmon/adt7462 +++ /dev/null @@ -1,71 +0,0 @@ -Kernel driver adt7462 -===================== - -Supported chips: - - * Analog Devices ADT7462 - - Prefix: 'adt7462' - - Addresses scanned: I2C 0x58, 0x5C - - Datasheet: Publicly available at the Analog Devices website - -Author: Darrick J. Wong - -Description ------------ - -This driver implements support for the Analog Devices ADT7462 chip family. - -This chip is a bit of a beast. It has 8 counters for measuring fan speed. It -can also measure 13 voltages or 4 temperatures, or various combinations of the -two. See the chip documentation for more details about the exact set of -configurations. This driver does not allow one to configure the chip; that is -left to the system designer. - -A sophisticated control system for the PWM outputs is designed into the ADT7462 -that allows fan speed to be adjusted automatically based on any of the three -temperature sensors. Each PWM output is individually adjustable and -programmable. Once configured, the ADT7462 will adjust the PWM outputs in -response to the measured temperatures without further host intervention. This -feature can also be disabled for manual control of the PWM's. - -Each of the measured inputs (voltage, temperature, fan speed) has -corresponding high/low limit values. The ADT7462 will signal an ALARM if -any measured value exceeds either limit. - -The ADT7462 samples all inputs continuously. The driver will not read -the registers more often than once every other second. Further, -configuration data is only read once per minute. - -Special Features ----------------- - -The ADT7462 have a 10-bit ADC and can therefore measure temperatures -with 0.25 degC resolution. - -The Analog Devices datasheet is very detailed and describes a procedure for -determining an optimal configuration for the automatic PWM control. - -The driver will report sensor labels when it is able to determine that -information from the configuration registers. - -Configuration Notes -------------------- - -Besides standard interfaces driver adds the following: - -* PWM Control - -* pwm#_auto_point1_pwm and temp#_auto_point1_temp and -* pwm#_auto_point2_pwm and temp#_auto_point2_temp - - - - point1: Set the pwm speed at a lower temperature bound. - - point2: Set the pwm speed at a higher temperature bound. - -The ADT7462 will scale the pwm between the lower and higher pwm speed when -the temperature is between the two temperature boundaries. PWM values range -from 0 (off) to 255 (full speed). Fan speed will be set to maximum when the -temperature sensor associated with the PWM control exceeds temp#_max. - diff --git a/Documentation/hwmon/adt7462.rst b/Documentation/hwmon/adt7462.rst new file mode 100644 index 000000000000..139e19696188 --- /dev/null +++ b/Documentation/hwmon/adt7462.rst @@ -0,0 +1,70 @@ +Kernel driver adt7462 +===================== + +Supported chips: + + * Analog Devices ADT7462 + + Prefix: 'adt7462' + + Addresses scanned: I2C 0x58, 0x5C + + Datasheet: Publicly available at the Analog Devices website + +Author: Darrick J. Wong + +Description +----------- + +This driver implements support for the Analog Devices ADT7462 chip family. + +This chip is a bit of a beast. It has 8 counters for measuring fan speed. It +can also measure 13 voltages or 4 temperatures, or various combinations of the +two. See the chip documentation for more details about the exact set of +configurations. This driver does not allow one to configure the chip; that is +left to the system designer. + +A sophisticated control system for the PWM outputs is designed into the ADT7462 +that allows fan speed to be adjusted automatically based on any of the three +temperature sensors. Each PWM output is individually adjustable and +programmable. Once configured, the ADT7462 will adjust the PWM outputs in +response to the measured temperatures without further host intervention. This +feature can also be disabled for manual control of the PWM's. + +Each of the measured inputs (voltage, temperature, fan speed) has +corresponding high/low limit values. The ADT7462 will signal an ALARM if +any measured value exceeds either limit. + +The ADT7462 samples all inputs continuously. The driver will not read +the registers more often than once every other second. Further, +configuration data is only read once per minute. + +Special Features +---------------- + +The ADT7462 have a 10-bit ADC and can therefore measure temperatures +with 0.25 degC resolution. + +The Analog Devices datasheet is very detailed and describes a procedure for +determining an optimal configuration for the automatic PWM control. + +The driver will report sensor labels when it is able to determine that +information from the configuration registers. + +Configuration Notes +------------------- + +Besides standard interfaces driver adds the following: + +* PWM Control + +* pwm#_auto_point1_pwm and temp#_auto_point1_temp and +* pwm#_auto_point2_pwm and temp#_auto_point2_temp - + + - point1: Set the pwm speed at a lower temperature bound. + - point2: Set the pwm speed at a higher temperature bound. + +The ADT7462 will scale the pwm between the lower and higher pwm speed when +the temperature is between the two temperature boundaries. PWM values range +from 0 (off) to 255 (full speed). Fan speed will be set to maximum when the +temperature sensor associated with the PWM control exceeds temp#_max. diff --git a/Documentation/hwmon/adt7470 b/Documentation/hwmon/adt7470 deleted file mode 100644 index d225f816e992..000000000000 --- a/Documentation/hwmon/adt7470 +++ /dev/null @@ -1,94 +0,0 @@ -Kernel driver adt7470 -===================== - -Supported chips: - - * Analog Devices ADT7470 - - Prefix: 'adt7470' - - Addresses scanned: I2C 0x2C, 0x2E, 0x2F - - Datasheet: Publicly available at the Analog Devices website - -Author: Darrick J. Wong - -Description ------------ - -This driver implements support for the Analog Devices ADT7470 chip. There may -be other chips that implement this interface. - -The ADT7470 uses the 2-wire interface compatible with the SMBus 2.0 -specification. Using an analog to digital converter it measures up to ten (10) -external temperatures. It has four (4) 16-bit counters for measuring fan speed. -There are four (4) PWM outputs that can be used to control fan speed. - -A sophisticated control system for the PWM outputs is designed into the ADT7470 -that allows fan speed to be adjusted automatically based on any of the ten -temperature sensors. Each PWM output is individually adjustable and -programmable. Once configured, the ADT7470 will adjust the PWM outputs in -response to the measured temperatures with further host intervention. This -feature can also be disabled for manual control of the PWM's. - -Each of the measured inputs (temperature, fan speed) has corresponding high/low -limit values. The ADT7470 will signal an ALARM if any measured value exceeds -either limit. - -The ADT7470 samples all inputs continuously. A kernel thread is started up for -the purpose of periodically querying the temperature sensors, thus allowing the -automatic fan pwm control to set the fan speed. The driver will not read the -registers more often than once every 5 seconds. Further, configuration data is -only read once per minute. - -Special Features ----------------- - -The ADT7470 has a 8-bit ADC and is capable of measuring temperatures with 1 -degC resolution. - -The Analog Devices datasheet is very detailed and describes a procedure for -determining an optimal configuration for the automatic PWM control. - -Configuration Notes -------------------- - -Besides standard interfaces driver adds the following: - -* PWM Control - -* pwm#_auto_point1_pwm and pwm#_auto_point1_temp and -* pwm#_auto_point2_pwm and pwm#_auto_point2_temp - - - - point1: Set the pwm speed at a lower temperature bound. - - point2: Set the pwm speed at a higher temperature bound. - -The ADT7470 will scale the pwm between the lower and higher pwm speed when -the temperature is between the two temperature boundaries. PWM values range -from 0 (off) to 255 (full speed). Fan speed will be set to maximum when the -temperature sensor associated with the PWM control exceeds -pwm#_auto_point2_temp. - -The driver also allows control of the PWM frequency: - -* pwm1_freq - -The PWM frequency is rounded to the nearest one of: - -* 11.0 Hz -* 14.7 Hz -* 22.1 Hz -* 29.4 Hz -* 35.3 Hz -* 44.1 Hz -* 58.8 Hz -* 88.2 Hz -* 1.4 kHz -* 22.5 kHz - -Notes ------ - -The temperature inputs no longer need to be read periodically from userspace in -order for the automatic pwm algorithm to run. This was the case for earlier -versions of the driver. diff --git a/Documentation/hwmon/adt7470.rst b/Documentation/hwmon/adt7470.rst new file mode 100644 index 000000000000..d225f816e992 --- /dev/null +++ b/Documentation/hwmon/adt7470.rst @@ -0,0 +1,94 @@ +Kernel driver adt7470 +===================== + +Supported chips: + + * Analog Devices ADT7470 + + Prefix: 'adt7470' + + Addresses scanned: I2C 0x2C, 0x2E, 0x2F + + Datasheet: Publicly available at the Analog Devices website + +Author: Darrick J. Wong + +Description +----------- + +This driver implements support for the Analog Devices ADT7470 chip. There may +be other chips that implement this interface. + +The ADT7470 uses the 2-wire interface compatible with the SMBus 2.0 +specification. Using an analog to digital converter it measures up to ten (10) +external temperatures. It has four (4) 16-bit counters for measuring fan speed. +There are four (4) PWM outputs that can be used to control fan speed. + +A sophisticated control system for the PWM outputs is designed into the ADT7470 +that allows fan speed to be adjusted automatically based on any of the ten +temperature sensors. Each PWM output is individually adjustable and +programmable. Once configured, the ADT7470 will adjust the PWM outputs in +response to the measured temperatures with further host intervention. This +feature can also be disabled for manual control of the PWM's. + +Each of the measured inputs (temperature, fan speed) has corresponding high/low +limit values. The ADT7470 will signal an ALARM if any measured value exceeds +either limit. + +The ADT7470 samples all inputs continuously. A kernel thread is started up for +the purpose of periodically querying the temperature sensors, thus allowing the +automatic fan pwm control to set the fan speed. The driver will not read the +registers more often than once every 5 seconds. Further, configuration data is +only read once per minute. + +Special Features +---------------- + +The ADT7470 has a 8-bit ADC and is capable of measuring temperatures with 1 +degC resolution. + +The Analog Devices datasheet is very detailed and describes a procedure for +determining an optimal configuration for the automatic PWM control. + +Configuration Notes +------------------- + +Besides standard interfaces driver adds the following: + +* PWM Control + +* pwm#_auto_point1_pwm and pwm#_auto_point1_temp and +* pwm#_auto_point2_pwm and pwm#_auto_point2_temp - + + - point1: Set the pwm speed at a lower temperature bound. + - point2: Set the pwm speed at a higher temperature bound. + +The ADT7470 will scale the pwm between the lower and higher pwm speed when +the temperature is between the two temperature boundaries. PWM values range +from 0 (off) to 255 (full speed). Fan speed will be set to maximum when the +temperature sensor associated with the PWM control exceeds +pwm#_auto_point2_temp. + +The driver also allows control of the PWM frequency: + +* pwm1_freq + +The PWM frequency is rounded to the nearest one of: + +* 11.0 Hz +* 14.7 Hz +* 22.1 Hz +* 29.4 Hz +* 35.3 Hz +* 44.1 Hz +* 58.8 Hz +* 88.2 Hz +* 1.4 kHz +* 22.5 kHz + +Notes +----- + +The temperature inputs no longer need to be read periodically from userspace in +order for the automatic pwm algorithm to run. This was the case for earlier +versions of the driver. diff --git a/Documentation/hwmon/adt7475 b/Documentation/hwmon/adt7475 deleted file mode 100644 index ef3ea1ea9bc1..000000000000 --- a/Documentation/hwmon/adt7475 +++ /dev/null @@ -1,156 +0,0 @@ -Kernel driver adt7475 -===================== - -Supported chips: - - * Analog Devices ADT7473 - - Prefix: 'adt7473' - - Addresses scanned: I2C 0x2C, 0x2D, 0x2E - - Datasheet: Publicly available at the On Semiconductors website - - * Analog Devices ADT7475 - - Prefix: 'adt7475' - - Addresses scanned: I2C 0x2E - - Datasheet: Publicly available at the On Semiconductors website - - * Analog Devices ADT7476 - - Prefix: 'adt7476' - - Addresses scanned: I2C 0x2C, 0x2D, 0x2E - - Datasheet: Publicly available at the On Semiconductors website - - * Analog Devices ADT7490 - - Prefix: 'adt7490' - - Addresses scanned: I2C 0x2C, 0x2D, 0x2E - - Datasheet: Publicly available at the On Semiconductors website - -Authors: - - Jordan Crouse - - Hans de Goede - - Darrick J. Wong (documentation) - - Jean Delvare - - -Description ------------ - -This driver implements support for the Analog Devices ADT7473, ADT7475, -ADT7476 and ADT7490 chip family. The ADT7473 and ADT7475 differ only in -minor details. The ADT7476 has additional features, including extra voltage -measurement inputs and VID support. The ADT7490 also has additional -features, including extra voltage measurement inputs and PECI support. All -the supported chips will be collectively designed by the name "ADT747x" in -the rest of this document. - -The ADT747x uses the 2-wire interface compatible with the SMBus 2.0 -specification. Using an analog to digital converter it measures three (3) -temperatures and two (2) or more voltages. It has four (4) 16-bit counters -for measuring fan speed. There are three (3) PWM outputs that can be used -to control fan speed. - -A sophisticated control system for the PWM outputs is designed into the -ADT747x that allows fan speed to be adjusted automatically based on any of the -three temperature sensors. Each PWM output is individually adjustable and -programmable. Once configured, the ADT747x will adjust the PWM outputs in -response to the measured temperatures without further host intervention. -This feature can also be disabled for manual control of the PWM's. - -Each of the measured inputs (voltage, temperature, fan speed) has -corresponding high/low limit values. The ADT747x will signal an ALARM if -any measured value exceeds either limit. - -The ADT747x samples all inputs continuously. The driver will not read -the registers more often than once every other second. Further, -configuration data is only read once per minute. - -Chip Differences Summary ------------------------- - -ADT7473: - * 2 voltage inputs - * system acoustics optimizations (not implemented) - -ADT7475: - * 2 voltage inputs - -ADT7476: - * 5 voltage inputs - * VID support - -ADT7490: - * 6 voltage inputs - * 1 Imon input (not implemented) - * PECI support (not implemented) - * 2 GPIO pins (not implemented) - * system acoustics optimizations (not implemented) - -Sysfs Mapping -------------- - -==== =========== =========== ========= ========== -in ADT7490 ADT7476 ADT7475 ADT7473 -==== =========== =========== ========= ========== -in0 2.5VIN (22) 2.5VIN (22) - - -in1 VCCP (23) VCCP (23) VCCP (14) VCCP (14) -in2 VCC (4) VCC (4) VCC (4) VCC (3) -in3 5VIN (20) 5VIN (20) -in4 12VIN (21) 12VIN (21) -in5 VTT (8) -==== =========== =========== ========= ========== - -Special Features ----------------- - -The ADT747x has a 10-bit ADC and can therefore measure temperatures -with a resolution of 0.25 degree Celsius. Temperature readings can be -configured either for two's complement format or "Offset 64" format, -wherein 64 is subtracted from the raw value to get the temperature value. - -The datasheet is very detailed and describes a procedure for determining -an optimal configuration for the automatic PWM control. - -Fan Speed Control ------------------ - -The driver exposes two trip points per PWM channel. - -- point1: Set the PWM speed at the lower temperature bound -- point2: Set the PWM speed at the higher temperature bound - -The ADT747x will scale the PWM linearly between the lower and higher PWM -speed when the temperature is between the two temperature boundaries. -Temperature boundaries are associated to temperature channels rather than -PWM outputs, and a given PWM output can be controlled by several temperature -channels. As a result, the ADT747x may compute more than one PWM value -for a channel at a given time, in which case the maximum value (fastest -fan speed) is applied. PWM values range from 0 (off) to 255 (full speed). - -Fan speed may be set to maximum when the temperature sensor associated with -the PWM control exceeds temp#_max. - -At Tmin - hysteresis the PWM output can either be off (0% duty cycle) or at the -minimum (i.e. auto_point1_pwm). This behaviour can be configured using the -`pwm[1-*]_stall_disable sysfs attribute`. A value of 0 means the fans will shut -off. A value of 1 means the fans will run at auto_point1_pwm. - -The responsiveness of the ADT747x to temperature changes can be configured. -This allows smoothing of the fan speed transition. To set the transition time -set the value in ms in the `temp[1-*]_smoothing` sysfs attribute. - -Notes ------ - -The nVidia binary driver presents an ADT7473 chip via an on-card i2c bus. -Unfortunately, they fail to set the i2c adapter class, so this driver may -fail to find the chip until the nvidia driver is patched. diff --git a/Documentation/hwmon/adt7475.rst b/Documentation/hwmon/adt7475.rst new file mode 100644 index 000000000000..ef3ea1ea9bc1 --- /dev/null +++ b/Documentation/hwmon/adt7475.rst @@ -0,0 +1,156 @@ +Kernel driver adt7475 +===================== + +Supported chips: + + * Analog Devices ADT7473 + + Prefix: 'adt7473' + + Addresses scanned: I2C 0x2C, 0x2D, 0x2E + + Datasheet: Publicly available at the On Semiconductors website + + * Analog Devices ADT7475 + + Prefix: 'adt7475' + + Addresses scanned: I2C 0x2E + + Datasheet: Publicly available at the On Semiconductors website + + * Analog Devices ADT7476 + + Prefix: 'adt7476' + + Addresses scanned: I2C 0x2C, 0x2D, 0x2E + + Datasheet: Publicly available at the On Semiconductors website + + * Analog Devices ADT7490 + + Prefix: 'adt7490' + + Addresses scanned: I2C 0x2C, 0x2D, 0x2E + + Datasheet: Publicly available at the On Semiconductors website + +Authors: + - Jordan Crouse + - Hans de Goede + - Darrick J. Wong (documentation) + - Jean Delvare + + +Description +----------- + +This driver implements support for the Analog Devices ADT7473, ADT7475, +ADT7476 and ADT7490 chip family. The ADT7473 and ADT7475 differ only in +minor details. The ADT7476 has additional features, including extra voltage +measurement inputs and VID support. The ADT7490 also has additional +features, including extra voltage measurement inputs and PECI support. All +the supported chips will be collectively designed by the name "ADT747x" in +the rest of this document. + +The ADT747x uses the 2-wire interface compatible with the SMBus 2.0 +specification. Using an analog to digital converter it measures three (3) +temperatures and two (2) or more voltages. It has four (4) 16-bit counters +for measuring fan speed. There are three (3) PWM outputs that can be used +to control fan speed. + +A sophisticated control system for the PWM outputs is designed into the +ADT747x that allows fan speed to be adjusted automatically based on any of the +three temperature sensors. Each PWM output is individually adjustable and +programmable. Once configured, the ADT747x will adjust the PWM outputs in +response to the measured temperatures without further host intervention. +This feature can also be disabled for manual control of the PWM's. + +Each of the measured inputs (voltage, temperature, fan speed) has +corresponding high/low limit values. The ADT747x will signal an ALARM if +any measured value exceeds either limit. + +The ADT747x samples all inputs continuously. The driver will not read +the registers more often than once every other second. Further, +configuration data is only read once per minute. + +Chip Differences Summary +------------------------ + +ADT7473: + * 2 voltage inputs + * system acoustics optimizations (not implemented) + +ADT7475: + * 2 voltage inputs + +ADT7476: + * 5 voltage inputs + * VID support + +ADT7490: + * 6 voltage inputs + * 1 Imon input (not implemented) + * PECI support (not implemented) + * 2 GPIO pins (not implemented) + * system acoustics optimizations (not implemented) + +Sysfs Mapping +------------- + +==== =========== =========== ========= ========== +in ADT7490 ADT7476 ADT7475 ADT7473 +==== =========== =========== ========= ========== +in0 2.5VIN (22) 2.5VIN (22) - - +in1 VCCP (23) VCCP (23) VCCP (14) VCCP (14) +in2 VCC (4) VCC (4) VCC (4) VCC (3) +in3 5VIN (20) 5VIN (20) +in4 12VIN (21) 12VIN (21) +in5 VTT (8) +==== =========== =========== ========= ========== + +Special Features +---------------- + +The ADT747x has a 10-bit ADC and can therefore measure temperatures +with a resolution of 0.25 degree Celsius. Temperature readings can be +configured either for two's complement format or "Offset 64" format, +wherein 64 is subtracted from the raw value to get the temperature value. + +The datasheet is very detailed and describes a procedure for determining +an optimal configuration for the automatic PWM control. + +Fan Speed Control +----------------- + +The driver exposes two trip points per PWM channel. + +- point1: Set the PWM speed at the lower temperature bound +- point2: Set the PWM speed at the higher temperature bound + +The ADT747x will scale the PWM linearly between the lower and higher PWM +speed when the temperature is between the two temperature boundaries. +Temperature boundaries are associated to temperature channels rather than +PWM outputs, and a given PWM output can be controlled by several temperature +channels. As a result, the ADT747x may compute more than one PWM value +for a channel at a given time, in which case the maximum value (fastest +fan speed) is applied. PWM values range from 0 (off) to 255 (full speed). + +Fan speed may be set to maximum when the temperature sensor associated with +the PWM control exceeds temp#_max. + +At Tmin - hysteresis the PWM output can either be off (0% duty cycle) or at the +minimum (i.e. auto_point1_pwm). This behaviour can be configured using the +`pwm[1-*]_stall_disable sysfs attribute`. A value of 0 means the fans will shut +off. A value of 1 means the fans will run at auto_point1_pwm. + +The responsiveness of the ADT747x to temperature changes can be configured. +This allows smoothing of the fan speed transition. To set the transition time +set the value in ms in the `temp[1-*]_smoothing` sysfs attribute. + +Notes +----- + +The nVidia binary driver presents an ADT7473 chip via an on-card i2c bus. +Unfortunately, they fail to set the i2c adapter class, so this driver may +fail to find the chip until the nvidia driver is patched. diff --git a/Documentation/hwmon/amc6821 b/Documentation/hwmon/amc6821 deleted file mode 100644 index d10eabcbc0f3..000000000000 --- a/Documentation/hwmon/amc6821 +++ /dev/null @@ -1,109 +0,0 @@ -Kernel driver amc6821 -===================== - -Supported chips: - - Texas Instruments AMC6821 - - Prefix: 'amc6821' - - Addresses scanned: 0x18, 0x19, 0x1a, 0x2c, 0x2d, 0x2e, 0x4c, 0x4d, 0x4e - - Datasheet: http://focus.ti.com/docs/prod/folders/print/amc6821.html - -Authors: - Tomaz Mertelj - - -Description ------------ - -This driver implements support for the Texas Instruments amc6821 chip. -The chip has one on-chip and one remote temperature sensor and one pwm fan -regulator. -The pwm can be controlled either from software or automatically. - -The driver provides the following sensor accesses in sysfs: - -======================= == =============================================== -temp1_input ro on-chip temperature -temp1_min rw " -temp1_max rw " -temp1_crit rw " -temp1_min_alarm ro " -temp1_max_alarm ro " -temp1_crit_alarm ro " - -temp2_input ro remote temperature -temp2_min rw " -temp2_max rw " -temp2_crit rw " -temp2_min_alarm ro " -temp2_max_alarm ro " -temp2_crit_alarm ro " -temp2_fault ro " - -fan1_input ro tachometer speed -fan1_min rw " -fan1_max rw " -fan1_fault ro " -fan1_div rw Fan divisor can be either 2 or 4. - -pwm1 rw pwm1 -pwm1_enable rw regulator mode, 1=open loop, 2=fan controlled - by remote temperature, 3=fan controlled by - combination of the on-chip temperature and - remote-sensor temperature, -pwm1_auto_channels_temp ro 1 if pwm_enable==2, 3 if pwm_enable==3 -pwm1_auto_point1_pwm ro Hardwired to 0, shared for both - temperature channels. -pwm1_auto_point2_pwm rw This value is shared for both temperature - channels. -pwm1_auto_point3_pwm rw Hardwired to 255, shared for both - temperature channels. - -temp1_auto_point1_temp ro Hardwired to temp2_auto_point1_temp - which is rw. Below this temperature fan stops. -temp1_auto_point2_temp rw The low-temperature limit of the proportional - range. Below this temperature - pwm1 = pwm1_auto_point2_pwm. It can go from - 0 degree C to 124 degree C in steps of - 4 degree C. Read it out after writing to get - the actual value. -temp1_auto_point3_temp rw Above this temperature fan runs at maximum - speed. It can go from temp1_auto_point2_temp. - It can only have certain discrete values - which depend on temp1_auto_point2_temp and - pwm1_auto_point2_pwm. Read it out after - writing to get the actual value. - -temp2_auto_point1_temp rw Must be between 0 degree C and 63 degree C and - it defines the passive cooling temperature. - Below this temperature the fan stops in - the closed loop mode. -temp2_auto_point2_temp rw The low-temperature limit of the proportional - range. Below this temperature - pwm1 = pwm1_auto_point2_pwm. It can go from - 0 degree C to 124 degree C in steps - of 4 degree C. - -temp2_auto_point3_temp rw Above this temperature fan runs at maximum - speed. It can only have certain discrete - values which depend on temp2_auto_point2_temp - and pwm1_auto_point2_pwm. Read it out after - writing to get actual value. -======================= == =============================================== - - -Module parameters ------------------ - -If your board has a BIOS that initializes the amc6821 correctly, you should -load the module with: init=0. - -If your board BIOS doesn't initialize the chip, or you want -different settings, you can set the following parameters: - -- init=1, -- pwminv: 0 default pwm output, 1 inverts pwm output. - diff --git a/Documentation/hwmon/amc6821.rst b/Documentation/hwmon/amc6821.rst new file mode 100644 index 000000000000..5ddb2849da90 --- /dev/null +++ b/Documentation/hwmon/amc6821.rst @@ -0,0 +1,108 @@ +Kernel driver amc6821 +===================== + +Supported chips: + + Texas Instruments AMC6821 + + Prefix: 'amc6821' + + Addresses scanned: 0x18, 0x19, 0x1a, 0x2c, 0x2d, 0x2e, 0x4c, 0x4d, 0x4e + + Datasheet: http://focus.ti.com/docs/prod/folders/print/amc6821.html + +Authors: + Tomaz Mertelj + + +Description +----------- + +This driver implements support for the Texas Instruments amc6821 chip. +The chip has one on-chip and one remote temperature sensor and one pwm fan +regulator. +The pwm can be controlled either from software or automatically. + +The driver provides the following sensor accesses in sysfs: + +======================= == =============================================== +temp1_input ro on-chip temperature +temp1_min rw " +temp1_max rw " +temp1_crit rw " +temp1_min_alarm ro " +temp1_max_alarm ro " +temp1_crit_alarm ro " + +temp2_input ro remote temperature +temp2_min rw " +temp2_max rw " +temp2_crit rw " +temp2_min_alarm ro " +temp2_max_alarm ro " +temp2_crit_alarm ro " +temp2_fault ro " + +fan1_input ro tachometer speed +fan1_min rw " +fan1_max rw " +fan1_fault ro " +fan1_div rw Fan divisor can be either 2 or 4. + +pwm1 rw pwm1 +pwm1_enable rw regulator mode, 1=open loop, 2=fan controlled + by remote temperature, 3=fan controlled by + combination of the on-chip temperature and + remote-sensor temperature, +pwm1_auto_channels_temp ro 1 if pwm_enable==2, 3 if pwm_enable==3 +pwm1_auto_point1_pwm ro Hardwired to 0, shared for both + temperature channels. +pwm1_auto_point2_pwm rw This value is shared for both temperature + channels. +pwm1_auto_point3_pwm rw Hardwired to 255, shared for both + temperature channels. + +temp1_auto_point1_temp ro Hardwired to temp2_auto_point1_temp + which is rw. Below this temperature fan stops. +temp1_auto_point2_temp rw The low-temperature limit of the proportional + range. Below this temperature + pwm1 = pwm1_auto_point2_pwm. It can go from + 0 degree C to 124 degree C in steps of + 4 degree C. Read it out after writing to get + the actual value. +temp1_auto_point3_temp rw Above this temperature fan runs at maximum + speed. It can go from temp1_auto_point2_temp. + It can only have certain discrete values + which depend on temp1_auto_point2_temp and + pwm1_auto_point2_pwm. Read it out after + writing to get the actual value. + +temp2_auto_point1_temp rw Must be between 0 degree C and 63 degree C and + it defines the passive cooling temperature. + Below this temperature the fan stops in + the closed loop mode. +temp2_auto_point2_temp rw The low-temperature limit of the proportional + range. Below this temperature + pwm1 = pwm1_auto_point2_pwm. It can go from + 0 degree C to 124 degree C in steps + of 4 degree C. + +temp2_auto_point3_temp rw Above this temperature fan runs at maximum + speed. It can only have certain discrete + values which depend on temp2_auto_point2_temp + and pwm1_auto_point2_pwm. Read it out after + writing to get actual value. +======================= == =============================================== + + +Module parameters +----------------- + +If your board has a BIOS that initializes the amc6821 correctly, you should +load the module with: init=0. + +If your board BIOS doesn't initialize the chip, or you want +different settings, you can set the following parameters: + +- init=1, +- pwminv: 0 default pwm output, 1 inverts pwm output. diff --git a/Documentation/hwmon/asb100 b/Documentation/hwmon/asb100 deleted file mode 100644 index 311d9f7b6926..000000000000 --- a/Documentation/hwmon/asb100 +++ /dev/null @@ -1,74 +0,0 @@ -Kernel driver asb100 -==================== - -Supported Chips: - - * Asus ASB100 and ASB100-A "Bach" - - Prefix: 'asb100' - - Addresses scanned: I2C 0x2d - - Datasheet: none released - -Author: Mark M. Hoffman - -Description ------------ - -This driver implements support for the Asus ASB100 and ASB100-A "Bach". -These are custom ASICs available only on Asus mainboards. Asus refuses to -supply a datasheet for these chips. Thanks go to many people who helped -investigate their hardware, including: - -Vitaly V. Bursov -Alexander van Kaam (author of MBM for Windows) -Bertrik Sikken - -The ASB100 implements seven voltage sensors, three fan rotation speed -sensors, four temperature sensors, VID lines and alarms. In addition to -these, the ASB100-A also implements a single PWM controller for fans 2 and -3 (i.e. one setting controls both.) If you have a plain ASB100, the PWM -controller will simply not work (or maybe it will for you... it doesn't for -me). - -Temperatures are measured and reported in degrees Celsius. - -Fan speeds are reported in RPM (rotations per minute). An alarm is -triggered if the rotation speed has dropped below a programmable limit. - -Voltage sensors (also known as IN sensors) report values in volts. - -The VID lines encode the core voltage value: the voltage level your -processor should work with. This is hardcoded by the mainboard and/or -processor itself. It is a value in volts. - -Alarms: (TODO question marks indicate may or may not work) - -- 0x0001 => in0 (?) -- 0x0002 => in1 (?) -- 0x0004 => in2 -- 0x0008 => in3 -- 0x0010 => temp1 [1]_ -- 0x0020 => temp2 -- 0x0040 => fan1 -- 0x0080 => fan2 -- 0x0100 => in4 -- 0x0200 => in5 (?) [2]_ -- 0x0400 => in6 (?) [2]_ -- 0x0800 => fan3 -- 0x1000 => chassis switch -- 0x2000 => temp3 - -.. [1] This alarm will only trigger if the hysteresis value is 127C. - I.e. it behaves the same as w83781d. - -.. [2] The min and max registers for these values appear to - be read-only or otherwise stuck at 0x00. - -TODO: - * Experiment with fan divisors > 8. - * Experiment with temp. sensor types. - * Are there really 13 voltage inputs? Probably not... - * Cleanups, no doubt... - diff --git a/Documentation/hwmon/asb100.rst b/Documentation/hwmon/asb100.rst new file mode 100644 index 000000000000..c2d5f97085fe --- /dev/null +++ b/Documentation/hwmon/asb100.rst @@ -0,0 +1,73 @@ +Kernel driver asb100 +==================== + +Supported Chips: + + * Asus ASB100 and ASB100-A "Bach" + + Prefix: 'asb100' + + Addresses scanned: I2C 0x2d + + Datasheet: none released + +Author: Mark M. Hoffman + +Description +----------- + +This driver implements support for the Asus ASB100 and ASB100-A "Bach". +These are custom ASICs available only on Asus mainboards. Asus refuses to +supply a datasheet for these chips. Thanks go to many people who helped +investigate their hardware, including: + +Vitaly V. Bursov +Alexander van Kaam (author of MBM for Windows) +Bertrik Sikken + +The ASB100 implements seven voltage sensors, three fan rotation speed +sensors, four temperature sensors, VID lines and alarms. In addition to +these, the ASB100-A also implements a single PWM controller for fans 2 and +3 (i.e. one setting controls both.) If you have a plain ASB100, the PWM +controller will simply not work (or maybe it will for you... it doesn't for +me). + +Temperatures are measured and reported in degrees Celsius. + +Fan speeds are reported in RPM (rotations per minute). An alarm is +triggered if the rotation speed has dropped below a programmable limit. + +Voltage sensors (also known as IN sensors) report values in volts. + +The VID lines encode the core voltage value: the voltage level your +processor should work with. This is hardcoded by the mainboard and/or +processor itself. It is a value in volts. + +Alarms: (TODO question marks indicate may or may not work) + +- 0x0001 => in0 (?) +- 0x0002 => in1 (?) +- 0x0004 => in2 +- 0x0008 => in3 +- 0x0010 => temp1 [1]_ +- 0x0020 => temp2 +- 0x0040 => fan1 +- 0x0080 => fan2 +- 0x0100 => in4 +- 0x0200 => in5 (?) [2]_ +- 0x0400 => in6 (?) [2]_ +- 0x0800 => fan3 +- 0x1000 => chassis switch +- 0x2000 => temp3 + +.. [1] This alarm will only trigger if the hysteresis value is 127C. + I.e. it behaves the same as w83781d. + +.. [2] The min and max registers for these values appear to + be read-only or otherwise stuck at 0x00. + +TODO: + * Experiment with fan divisors > 8. + * Experiment with temp. sensor types. + * Are there really 13 voltage inputs? Probably not... + * Cleanups, no doubt... diff --git a/Documentation/hwmon/asc7621 b/Documentation/hwmon/asc7621 deleted file mode 100644 index b5a9fad0f172..000000000000 --- a/Documentation/hwmon/asc7621 +++ /dev/null @@ -1,326 +0,0 @@ -===================== -Kernel driver asc7621 -===================== - -Supported chips: - - Andigilog aSC7621 and aSC7621a - - Prefix: 'asc7621' - - Addresses scanned: I2C 0x2c, 0x2d, 0x2e - - Datasheet: http://www.fairview5.com/linux/asc7621/asc7621.pdf - -Author: - George Joseph - -Description provided by Dave Pivin @ Andigilog: - -Andigilog has both the PECI and pre-PECI versions of the Heceta-6, as -Intel calls them. Heceta-6e has high frequency PWM and Heceta-6p has -added PECI and a 4th thermal zone. The Andigilog aSC7611 is the -Heceta-6e part and aSC7621 is the Heceta-6p part. They are both in -volume production, shipping to Intel and their subs. - -We have enhanced both parts relative to the governing Intel -specification. First enhancement is temperature reading resolution. We -have used registers below 20h for vendor-specific functions in addition -to those in the Intel-specified vendor range. - -Our conversion process produces a result that is reported as two bytes. -The fan speed control uses this finer value to produce a "step-less" fan -PWM output. These two bytes are "read-locked" to guarantee that once a -high or low byte is read, the other byte is locked-in until after the -next read of any register. So to get an atomic reading, read high or low -byte, then the very next read should be the opposite byte. Our data -sheet says 10-bits of resolution, although you may find the lower bits -are active, they are not necessarily reliable or useful externally. We -chose not to mask them. - -We employ significant filtering that is user tunable as described in the -data sheet. Our temperature reports and fan PWM outputs are very smooth -when compared to the competition, in addition to the higher resolution -temperature reports. The smoother PWM output does not require user -intervention. - -We offer GPIO features on the former VID pins. These are open-drain -outputs or inputs and may be used as general purpose I/O or as alarm -outputs that are based on temperature limits. These are in 19h and 1Ah. - -We offer flexible mapping of temperature readings to thermal zones. Any -temperature may be mapped to any zone, which has a default assignment -that follows Intel's specs. - -Since there is a fan to zone assignment that allows for the "hotter" of -a set of zones to control the PWM of an individual fan, but there is no -indication to the user, we have added an indicator that shows which zone -is currently controlling the PWM for a given fan. This is in register -00h. - -Both remote diode temperature readings may be given an offset value such -that the reported reading as well as the temperature used to determine -PWM may be offset for system calibration purposes. - -PECI Extended configuration allows for having more than two domains per -PECI address and also provides an enabling function for each PECI -address. One could use our flexible zone assignment to have a zone -assigned to up to 4 PECI addresses. This is not possible in the default -Intel configuration. This would be useful in multi-CPU systems with -individual fans on each that would benefit from individual fan control. -This is in register 0Eh. - -The tachometer measurement system is flexible and able to adapt to many -fan types. We can also support pulse-stretched PWM so that 3-wire fans -may be used. These characteristics are in registers 04h to 07h. - -Finally, we have added a tach disable function that turns off the tach -measurement system for individual tachs in order to save power. That is -in register 75h. - --------------------------------------------------------------------------- - -aSC7621 Product Description -=========================== - -The aSC7621 has a two wire digital interface compatible with SMBus 2.0. -Using a 10-bit ADC, the aSC7621 measures the temperature of two remote diode -connected transistors as well as its own die. Support for Platform -Environmental Control Interface (PECI) is included. - -Using temperature information from these four zones, an automatic fan speed -control algorithm is employed to minimize acoustic impact while achieving -recommended CPU temperature under varying operational loads. - -To set fan speed, the aSC7621 has three independent pulse width modulation -(PWM) outputs that are controlled by one, or a combination of three, -temperature zones. Both high- and low-frequency PWM ranges are supported. - -The aSC7621 also includes a digital filter that can be invoked to smooth -temperature readings for better control of fan speed and minimum acoustic -impact. - -The aSC7621 has tachometer inputs to measure fan speed on up to four fans. -Limit and status registers for all measured values are included to alert -the system host that any measurements are outside of programmed limits -via status registers. - -System voltages of VCCP, 2.5V, 3.3V, 5.0V, and 12V motherboard power are -monitored efficiently with internal scaling resistors. - -Features --------- - -- Supports PECI interface and monitors internal and remote thermal diodes -- 2-wire, SMBus 2.0 compliant, serial interface -- 10-bit ADC -- Monitors VCCP, 2.5V, 3.3V, 5.0V, and 12V motherboard/processor supplies -- Programmable autonomous fan control based on temperature readings -- Noise filtering of temperature reading for fan speed control -- 0.25C digital temperature sensor resolution -- 3 PWM fan speed control outputs for 2-, 3- or 4-wire fans and up to 4 fan - tachometer inputs -- Enhanced measured temperature to Temperature Zone assignment. -- Provides high and low PWM frequency ranges -- 3 GPIO pins for custom use -- 24-Lead QSOP package - -Configuration Notes -=================== - -Except where noted below, the sysfs entries created by this driver follow -the standards defined in "sysfs-interface". - -temp1_source - = =============================================== - 0 (default) peci_legacy = 0, Remote 1 Temperature - peci_legacy = 1, PECI Processor Temperature 0 - 1 Remote 1 Temperature - 2 Remote 2 Temperature - 3 Internal Temperature - 4 PECI Processor Temperature 0 - 5 PECI Processor Temperature 1 - 6 PECI Processor Temperature 2 - 7 PECI Processor Temperature 3 - = =============================================== - -temp2_source - = =============================================== - 0 (default) Internal Temperature - 1 Remote 1 Temperature - 2 Remote 2 Temperature - 3 Internal Temperature - 4 PECI Processor Temperature 0 - 5 PECI Processor Temperature 1 - 6 PECI Processor Temperature 2 - 7 PECI Processor Temperature 3 - = =============================================== - -temp3_source - = =============================================== - 0 (default) Remote 2 Temperature - 1 Remote 1 Temperature - 2 Remote 2 Temperature - 3 Internal Temperature - 4 PECI Processor Temperature 0 - 5 PECI Processor Temperature 1 - 6 PECI Processor Temperature 2 - 7 PECI Processor Temperature 3 - = =============================================== - -temp4_source - = =============================================== - 0 (default) peci_legacy = 0, PECI Processor Temperature 0 - peci_legacy = 1, Remote 1 Temperature - 1 Remote 1 Temperature - 2 Remote 2 Temperature - 3 Internal Temperature - 4 PECI Processor Temperature 0 - 5 PECI Processor Temperature 1 - 6 PECI Processor Temperature 2 - 7 PECI Processor Temperature 3 - = =============================================== - -temp[1-4]_smoothing_enable / temp[1-4]_smoothing_time - Smooths spikes in temp readings caused by noise. - Valid values in milliseconds are: - - * 35000 - * 17600 - * 11800 - * 7000 - * 4400 - * 3000 - * 1600 - * 800 - -temp[1-4]_crit - When the corresponding zone temperature reaches this value, - ALL pwm outputs will got to 100%. - -temp[5-8]_input / temp[5-8]_enable - The aSC7621 can also read temperatures provided by the processor - via the PECI bus. Usually these are "core" temps and are relative - to the point where the automatic thermal control circuit starts - throttling. This means that these are usually negative numbers. - -pwm[1-3]_enable - =============== ======================================================== - 0 Fan off. - 1 Fan on manual control. - 2 Fan on automatic control and will run at the minimum pwm - if the temperature for the zone is below the minimum. - 3 Fan on automatic control but will be off if the - temperature for the zone is below the minimum. - 4-254 Ignored. - 255 Fan on full. - =============== ======================================================== - -pwm[1-3]_auto_channels - Bitmap as described in sysctl-interface with the following - exceptions... - - Only the following combination of zones (and their corresponding masks) - are valid: - - * 1 - * 2 - * 3 - * 2,3 - * 1,2,3 - * 4 - * 1,2,3,4 - - * Special values: - - == ====================== - 0 Disabled. - 16 Fan on manual control. - 31 Fan on full. - == ====================== - - -pwm[1-3]_invert - When set, inverts the meaning of pwm[1-3]. - i.e. when pwm = 0, the fan will be on full and - when pwm = 255 the fan will be off. - -pwm[1-3]_freq - PWM frequency in Hz - Valid values in Hz are: - - * 10 - * 15 - * 23 - * 30 (default) - * 38 - * 47 - * 62 - * 94 - * 23000 - * 24000 - * 25000 - * 26000 - * 27000 - * 28000 - * 29000 - * 30000 - - Setting any other value will be ignored. - -peci_enable - Enables or disables PECI - -peci_avg - Input filter average time. - - * 0 0 Sec. (no Smoothing) (default) - * 1 0.25 Sec. - * 2 0.5 Sec. - * 3 1.0 Sec. - * 4 2.0 Sec. - * 5 4.0 Sec. - * 6 8.0 Sec. - * 7 0.0 Sec. - -peci_legacy - = ============================================ - 0 Standard Mode (default) - Remote Diode 1 reading is associated with - Temperature Zone 1, PECI is associated with - Zone 4 - - 1 Legacy Mode - PECI is associated with Temperature Zone 1, - Remote Diode 1 is associated with Zone 4 - = ============================================ - -peci_diode - Diode filter - - = ==================== - 0 0.25 Sec. - 1 1.1 Sec. - 2 2.4 Sec. (default) - 3 3.4 Sec. - 4 5.0 Sec. - 5 6.8 Sec. - 6 10.2 Sec. - 7 16.4 Sec. - = ==================== - -peci_4domain - Four domain enable - - = =============================================== - 0 1 or 2 Domains for enabled processors (default) - 1 3 or 4 Domains for enabled processors - = =============================================== - -peci_domain - Domain - - = ================================================== - 0 Processor contains a single domain (0) (default) - 1 Processor contains two domains (0,1) - = ================================================== diff --git a/Documentation/hwmon/asc7621.rst b/Documentation/hwmon/asc7621.rst new file mode 100644 index 000000000000..b5a9fad0f172 --- /dev/null +++ b/Documentation/hwmon/asc7621.rst @@ -0,0 +1,326 @@ +===================== +Kernel driver asc7621 +===================== + +Supported chips: + + Andigilog aSC7621 and aSC7621a + + Prefix: 'asc7621' + + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + + Datasheet: http://www.fairview5.com/linux/asc7621/asc7621.pdf + +Author: + George Joseph + +Description provided by Dave Pivin @ Andigilog: + +Andigilog has both the PECI and pre-PECI versions of the Heceta-6, as +Intel calls them. Heceta-6e has high frequency PWM and Heceta-6p has +added PECI and a 4th thermal zone. The Andigilog aSC7611 is the +Heceta-6e part and aSC7621 is the Heceta-6p part. They are both in +volume production, shipping to Intel and their subs. + +We have enhanced both parts relative to the governing Intel +specification. First enhancement is temperature reading resolution. We +have used registers below 20h for vendor-specific functions in addition +to those in the Intel-specified vendor range. + +Our conversion process produces a result that is reported as two bytes. +The fan speed control uses this finer value to produce a "step-less" fan +PWM output. These two bytes are "read-locked" to guarantee that once a +high or low byte is read, the other byte is locked-in until after the +next read of any register. So to get an atomic reading, read high or low +byte, then the very next read should be the opposite byte. Our data +sheet says 10-bits of resolution, although you may find the lower bits +are active, they are not necessarily reliable or useful externally. We +chose not to mask them. + +We employ significant filtering that is user tunable as described in the +data sheet. Our temperature reports and fan PWM outputs are very smooth +when compared to the competition, in addition to the higher resolution +temperature reports. The smoother PWM output does not require user +intervention. + +We offer GPIO features on the former VID pins. These are open-drain +outputs or inputs and may be used as general purpose I/O or as alarm +outputs that are based on temperature limits. These are in 19h and 1Ah. + +We offer flexible mapping of temperature readings to thermal zones. Any +temperature may be mapped to any zone, which has a default assignment +that follows Intel's specs. + +Since there is a fan to zone assignment that allows for the "hotter" of +a set of zones to control the PWM of an individual fan, but there is no +indication to the user, we have added an indicator that shows which zone +is currently controlling the PWM for a given fan. This is in register +00h. + +Both remote diode temperature readings may be given an offset value such +that the reported reading as well as the temperature used to determine +PWM may be offset for system calibration purposes. + +PECI Extended configuration allows for having more than two domains per +PECI address and also provides an enabling function for each PECI +address. One could use our flexible zone assignment to have a zone +assigned to up to 4 PECI addresses. This is not possible in the default +Intel configuration. This would be useful in multi-CPU systems with +individual fans on each that would benefit from individual fan control. +This is in register 0Eh. + +The tachometer measurement system is flexible and able to adapt to many +fan types. We can also support pulse-stretched PWM so that 3-wire fans +may be used. These characteristics are in registers 04h to 07h. + +Finally, we have added a tach disable function that turns off the tach +measurement system for individual tachs in order to save power. That is +in register 75h. + +-------------------------------------------------------------------------- + +aSC7621 Product Description +=========================== + +The aSC7621 has a two wire digital interface compatible with SMBus 2.0. +Using a 10-bit ADC, the aSC7621 measures the temperature of two remote diode +connected transistors as well as its own die. Support for Platform +Environmental Control Interface (PECI) is included. + +Using temperature information from these four zones, an automatic fan speed +control algorithm is employed to minimize acoustic impact while achieving +recommended CPU temperature under varying operational loads. + +To set fan speed, the aSC7621 has three independent pulse width modulation +(PWM) outputs that are controlled by one, or a combination of three, +temperature zones. Both high- and low-frequency PWM ranges are supported. + +The aSC7621 also includes a digital filter that can be invoked to smooth +temperature readings for better control of fan speed and minimum acoustic +impact. + +The aSC7621 has tachometer inputs to measure fan speed on up to four fans. +Limit and status registers for all measured values are included to alert +the system host that any measurements are outside of programmed limits +via status registers. + +System voltages of VCCP, 2.5V, 3.3V, 5.0V, and 12V motherboard power are +monitored efficiently with internal scaling resistors. + +Features +-------- + +- Supports PECI interface and monitors internal and remote thermal diodes +- 2-wire, SMBus 2.0 compliant, serial interface +- 10-bit ADC +- Monitors VCCP, 2.5V, 3.3V, 5.0V, and 12V motherboard/processor supplies +- Programmable autonomous fan control based on temperature readings +- Noise filtering of temperature reading for fan speed control +- 0.25C digital temperature sensor resolution +- 3 PWM fan speed control outputs for 2-, 3- or 4-wire fans and up to 4 fan + tachometer inputs +- Enhanced measured temperature to Temperature Zone assignment. +- Provides high and low PWM frequency ranges +- 3 GPIO pins for custom use +- 24-Lead QSOP package + +Configuration Notes +=================== + +Except where noted below, the sysfs entries created by this driver follow +the standards defined in "sysfs-interface". + +temp1_source + = =============================================== + 0 (default) peci_legacy = 0, Remote 1 Temperature + peci_legacy = 1, PECI Processor Temperature 0 + 1 Remote 1 Temperature + 2 Remote 2 Temperature + 3 Internal Temperature + 4 PECI Processor Temperature 0 + 5 PECI Processor Temperature 1 + 6 PECI Processor Temperature 2 + 7 PECI Processor Temperature 3 + = =============================================== + +temp2_source + = =============================================== + 0 (default) Internal Temperature + 1 Remote 1 Temperature + 2 Remote 2 Temperature + 3 Internal Temperature + 4 PECI Processor Temperature 0 + 5 PECI Processor Temperature 1 + 6 PECI Processor Temperature 2 + 7 PECI Processor Temperature 3 + = =============================================== + +temp3_source + = =============================================== + 0 (default) Remote 2 Temperature + 1 Remote 1 Temperature + 2 Remote 2 Temperature + 3 Internal Temperature + 4 PECI Processor Temperature 0 + 5 PECI Processor Temperature 1 + 6 PECI Processor Temperature 2 + 7 PECI Processor Temperature 3 + = =============================================== + +temp4_source + = =============================================== + 0 (default) peci_legacy = 0, PECI Processor Temperature 0 + peci_legacy = 1, Remote 1 Temperature + 1 Remote 1 Temperature + 2 Remote 2 Temperature + 3 Internal Temperature + 4 PECI Processor Temperature 0 + 5 PECI Processor Temperature 1 + 6 PECI Processor Temperature 2 + 7 PECI Processor Temperature 3 + = =============================================== + +temp[1-4]_smoothing_enable / temp[1-4]_smoothing_time + Smooths spikes in temp readings caused by noise. + Valid values in milliseconds are: + + * 35000 + * 17600 + * 11800 + * 7000 + * 4400 + * 3000 + * 1600 + * 800 + +temp[1-4]_crit + When the corresponding zone temperature reaches this value, + ALL pwm outputs will got to 100%. + +temp[5-8]_input / temp[5-8]_enable + The aSC7621 can also read temperatures provided by the processor + via the PECI bus. Usually these are "core" temps and are relative + to the point where the automatic thermal control circuit starts + throttling. This means that these are usually negative numbers. + +pwm[1-3]_enable + =============== ======================================================== + 0 Fan off. + 1 Fan on manual control. + 2 Fan on automatic control and will run at the minimum pwm + if the temperature for the zone is below the minimum. + 3 Fan on automatic control but will be off if the + temperature for the zone is below the minimum. + 4-254 Ignored. + 255 Fan on full. + =============== ======================================================== + +pwm[1-3]_auto_channels + Bitmap as described in sysctl-interface with the following + exceptions... + + Only the following combination of zones (and their corresponding masks) + are valid: + + * 1 + * 2 + * 3 + * 2,3 + * 1,2,3 + * 4 + * 1,2,3,4 + + * Special values: + + == ====================== + 0 Disabled. + 16 Fan on manual control. + 31 Fan on full. + == ====================== + + +pwm[1-3]_invert + When set, inverts the meaning of pwm[1-3]. + i.e. when pwm = 0, the fan will be on full and + when pwm = 255 the fan will be off. + +pwm[1-3]_freq + PWM frequency in Hz + Valid values in Hz are: + + * 10 + * 15 + * 23 + * 30 (default) + * 38 + * 47 + * 62 + * 94 + * 23000 + * 24000 + * 25000 + * 26000 + * 27000 + * 28000 + * 29000 + * 30000 + + Setting any other value will be ignored. + +peci_enable + Enables or disables PECI + +peci_avg + Input filter average time. + + * 0 0 Sec. (no Smoothing) (default) + * 1 0.25 Sec. + * 2 0.5 Sec. + * 3 1.0 Sec. + * 4 2.0 Sec. + * 5 4.0 Sec. + * 6 8.0 Sec. + * 7 0.0 Sec. + +peci_legacy + = ============================================ + 0 Standard Mode (default) + Remote Diode 1 reading is associated with + Temperature Zone 1, PECI is associated with + Zone 4 + + 1 Legacy Mode + PECI is associated with Temperature Zone 1, + Remote Diode 1 is associated with Zone 4 + = ============================================ + +peci_diode + Diode filter + + = ==================== + 0 0.25 Sec. + 1 1.1 Sec. + 2 2.4 Sec. (default) + 3 3.4 Sec. + 4 5.0 Sec. + 5 6.8 Sec. + 6 10.2 Sec. + 7 16.4 Sec. + = ==================== + +peci_4domain + Four domain enable + + = =============================================== + 0 1 or 2 Domains for enabled processors (default) + 1 3 or 4 Domains for enabled processors + = =============================================== + +peci_domain + Domain + + = ================================================== + 0 Processor contains a single domain (0) (default) + 1 Processor contains two domains (0,1) + = ================================================== diff --git a/Documentation/hwmon/aspeed-pwm-tacho b/Documentation/hwmon/aspeed-pwm-tacho deleted file mode 100644 index 6dcec845fbc7..000000000000 --- a/Documentation/hwmon/aspeed-pwm-tacho +++ /dev/null @@ -1,24 +0,0 @@ -Kernel driver aspeed-pwm-tacho -============================== - -Supported chips: - ASPEED AST2400/2500 - -Authors: - - -Description: ------------- -This driver implements support for ASPEED AST2400/2500 PWM and Fan Tacho -controller. The PWM controller supports upto 8 PWM outputs. The Fan tacho -controller supports up to 16 tachometer inputs. - -The driver provides the following sensor accesses in sysfs: - -=============== ======= ===================================================== -fanX_input ro provide current fan rotation value in RPM as reported - by the fan to the device. - -pwmX rw get or set PWM fan control value. This is an integer - value between 0(off) and 255(full speed). -=============== ======= ===================================================== diff --git a/Documentation/hwmon/aspeed-pwm-tacho.rst b/Documentation/hwmon/aspeed-pwm-tacho.rst new file mode 100644 index 000000000000..6dcec845fbc7 --- /dev/null +++ b/Documentation/hwmon/aspeed-pwm-tacho.rst @@ -0,0 +1,24 @@ +Kernel driver aspeed-pwm-tacho +============================== + +Supported chips: + ASPEED AST2400/2500 + +Authors: + + +Description: +------------ +This driver implements support for ASPEED AST2400/2500 PWM and Fan Tacho +controller. The PWM controller supports upto 8 PWM outputs. The Fan tacho +controller supports up to 16 tachometer inputs. + +The driver provides the following sensor accesses in sysfs: + +=============== ======= ===================================================== +fanX_input ro provide current fan rotation value in RPM as reported + by the fan to the device. + +pwmX rw get or set PWM fan control value. This is an integer + value between 0(off) and 255(full speed). +=============== ======= ===================================================== diff --git a/Documentation/hwmon/coretemp b/Documentation/hwmon/coretemp deleted file mode 100644 index c609329e3bc4..000000000000 --- a/Documentation/hwmon/coretemp +++ /dev/null @@ -1,195 +0,0 @@ -Kernel driver coretemp -====================== - -Supported chips: - * All Intel Core family - - Prefix: 'coretemp' - - CPUID: family 0x6, models - - - 0xe (Pentium M DC), 0xf (Core 2 DC 65nm), - - 0x16 (Core 2 SC 65nm), 0x17 (Penryn 45nm), - - 0x1a (Nehalem), 0x1c (Atom), 0x1e (Lynnfield), - - 0x26 (Tunnel Creek Atom), 0x27 (Medfield Atom), - - 0x36 (Cedar Trail Atom) - - Datasheet: - - Intel 64 and IA-32 Architectures Software Developer's Manual - Volume 3A: System Programming Guide - - http://softwarecommunity.intel.com/Wiki/Mobility/720.htm - -Author: Rudolf Marek - -Description ------------ - -This driver permits reading the DTS (Digital Temperature Sensor) embedded -inside Intel CPUs. This driver can read both the per-core and per-package -temperature using the appropriate sensors. The per-package sensor is new; -as of now, it is present only in the SandyBridge platform. The driver will -show the temperature of all cores inside a package under a single device -directory inside hwmon. - -Temperature is measured in degrees Celsius and measurement resolution is -1 degree C. Valid temperatures are from 0 to TjMax degrees C, because -the actual value of temperature register is in fact a delta from TjMax. - -Temperature known as TjMax is the maximum junction temperature of processor, -which depends on the CPU model. See table below. At this temperature, protection -mechanism will perform actions to forcibly cool down the processor. Alarm -may be raised, if the temperature grows enough (more than TjMax) to trigger -the Out-Of-Spec bit. Following table summarizes the exported sysfs files: - -All Sysfs entries are named with their core_id (represented here by 'X'). - -================= ======================================================== -tempX_input Core temperature (in millidegrees Celsius). -tempX_max All cooling devices should be turned on (on Core2). -tempX_crit Maximum junction temperature (in millidegrees Celsius). -tempX_crit_alarm Set when Out-of-spec bit is set, never clears. - Correct CPU operation is no longer guaranteed. -tempX_label Contains string "Core X", where X is processor - number. For Package temp, this will be "Physical id Y", - where Y is the package number. -================= ======================================================== - -On CPU models which support it, TjMax is read from a model-specific register. -On other models, it is set to an arbitrary value based on weak heuristics. -If these heuristics don't work for you, you can pass the correct TjMax value -as a module parameter (tjmax). - -Appendix A. Known TjMax lists (TBD): -Some information comes from ark.intel.com - -=============== =============================================== ================ -Process Processor TjMax(C) - -22nm Core i5/i7 Processors - i7 3920XM, 3820QM, 3720QM, 3667U, 3520M 105 - i5 3427U, 3360M/3320M 105 - i7 3770/3770K 105 - i5 3570/3570K, 3550, 3470/3450 105 - i7 3770S 103 - i5 3570S/3550S, 3475S/3470S/3450S 103 - i7 3770T 94 - i5 3570T 94 - i5 3470T 91 - -32nm Core i3/i5/i7 Processors - i7 2600 98 - i7 660UM/640/620, 640LM/620, 620M, 610E 105 - i5 540UM/520/430, 540M/520/450/430 105 - i3 330E, 370M/350/330 90 rPGA, 105 BGA - i3 330UM 105 - -32nm Core i7 Extreme Processors - 980X 100 - -32nm Celeron Processors - U3400 105 - P4505/P4500 90 - -32nm Atom Processors - S1260/1220 95 - S1240 102 - Z2460 90 - Z2760 90 - D2700/2550/2500 100 - N2850/2800/2650/2600 100 - -45nm Xeon Processors 5400 Quad-Core - X5492, X5482, X5472, X5470, X5460, X5450 85 - E5472, E5462, E5450/40/30/20/10/05 85 - L5408 95 - L5430, L5420, L5410 70 - -45nm Xeon Processors 5200 Dual-Core - X5282, X5272, X5270, X5260 90 - E5240 90 - E5205, E5220 70, 90 - L5240 70 - L5238, L5215 95 - -45nm Atom Processors - D525/510/425/410 100 - K525/510/425/410 100 - Z670/650 90 - Z560/550/540/530P/530/520PT/520/515/510PT/510P 90 - Z510/500 90 - N570/550 100 - N475/470/455/450 100 - N280/270 90 - 330/230 125 - E680/660/640/620 90 - E680T/660T/640T/620T 110 - E665C/645C 90 - E665CT/645CT 110 - CE4170/4150/4110 110 - CE4200 series unknown - CE5300 series unknown - -45nm Core2 Processors - Solo ULV SU3500/3300 100 - T9900/9800/9600/9550/9500/9400/9300/8300/8100 105 - T6670/6500/6400 105 - T6600 90 - SU9600/9400/9300 105 - SP9600/9400 105 - SL9600/9400/9380/9300 105 - P9700/9600/9500/8800/8700/8600/8400/7570 105 - P7550/7450 90 - -45nm Core2 Quad Processors - Q9100/9000 100 - -45nm Core2 Extreme Processors - X9100/9000 105 - QX9300 100 - -45nm Core i3/i5/i7 Processors - i7 940XM/920 100 - i7 840QM/820/740/720 100 - -45nm Celeron Processors - SU2300 100 - 900 105 - -65nm Core2 Duo Processors - Solo U2200, U2100 100 - U7700/7600/7500 100 - T7800/7700/7600/7500/7400/7300/7250/7200/7100 100 - T5870/5670/5600/5550/5500/5470/5450/5300/5270 100 - T5250 100 - T5800/5750/5200 85 - L7700/7500/7400/7300/7200 100 - -65nm Core2 Extreme Processors - X7900/7800 100 - -65nm Core Duo Processors - U2500/2400 100 - T2700/2600/2450/2400/2350/2300E/2300/2250/2050 100 - L2500/2400/2300 100 - -65nm Core Solo Processors - U1500/1400/1300 100 - T1400/1350/1300/1250 100 - -65nm Xeon Processors 5000 Quad-Core - X5000 90-95 - E5000 80 - L5000 70 - L5318 95 - -65nm Xeon Processors 5000 Dual-Core - 5080, 5063, 5060, 5050, 5030 80-90 - 5160, 5150, 5148, 5140, 5130, 5120, 5110 80 - L5138 100 - -65nm Celeron Processors - T1700/1600 100 - 560/550/540/530 100 -=============== =============================================== ================ diff --git a/Documentation/hwmon/coretemp.rst b/Documentation/hwmon/coretemp.rst new file mode 100644 index 000000000000..c609329e3bc4 --- /dev/null +++ b/Documentation/hwmon/coretemp.rst @@ -0,0 +1,195 @@ +Kernel driver coretemp +====================== + +Supported chips: + * All Intel Core family + + Prefix: 'coretemp' + + CPUID: family 0x6, models + + - 0xe (Pentium M DC), 0xf (Core 2 DC 65nm), + - 0x16 (Core 2 SC 65nm), 0x17 (Penryn 45nm), + - 0x1a (Nehalem), 0x1c (Atom), 0x1e (Lynnfield), + - 0x26 (Tunnel Creek Atom), 0x27 (Medfield Atom), + - 0x36 (Cedar Trail Atom) + + Datasheet: + + Intel 64 and IA-32 Architectures Software Developer's Manual + Volume 3A: System Programming Guide + + http://softwarecommunity.intel.com/Wiki/Mobility/720.htm + +Author: Rudolf Marek + +Description +----------- + +This driver permits reading the DTS (Digital Temperature Sensor) embedded +inside Intel CPUs. This driver can read both the per-core and per-package +temperature using the appropriate sensors. The per-package sensor is new; +as of now, it is present only in the SandyBridge platform. The driver will +show the temperature of all cores inside a package under a single device +directory inside hwmon. + +Temperature is measured in degrees Celsius and measurement resolution is +1 degree C. Valid temperatures are from 0 to TjMax degrees C, because +the actual value of temperature register is in fact a delta from TjMax. + +Temperature known as TjMax is the maximum junction temperature of processor, +which depends on the CPU model. See table below. At this temperature, protection +mechanism will perform actions to forcibly cool down the processor. Alarm +may be raised, if the temperature grows enough (more than TjMax) to trigger +the Out-Of-Spec bit. Following table summarizes the exported sysfs files: + +All Sysfs entries are named with their core_id (represented here by 'X'). + +================= ======================================================== +tempX_input Core temperature (in millidegrees Celsius). +tempX_max All cooling devices should be turned on (on Core2). +tempX_crit Maximum junction temperature (in millidegrees Celsius). +tempX_crit_alarm Set when Out-of-spec bit is set, never clears. + Correct CPU operation is no longer guaranteed. +tempX_label Contains string "Core X", where X is processor + number. For Package temp, this will be "Physical id Y", + where Y is the package number. +================= ======================================================== + +On CPU models which support it, TjMax is read from a model-specific register. +On other models, it is set to an arbitrary value based on weak heuristics. +If these heuristics don't work for you, you can pass the correct TjMax value +as a module parameter (tjmax). + +Appendix A. Known TjMax lists (TBD): +Some information comes from ark.intel.com + +=============== =============================================== ================ +Process Processor TjMax(C) + +22nm Core i5/i7 Processors + i7 3920XM, 3820QM, 3720QM, 3667U, 3520M 105 + i5 3427U, 3360M/3320M 105 + i7 3770/3770K 105 + i5 3570/3570K, 3550, 3470/3450 105 + i7 3770S 103 + i5 3570S/3550S, 3475S/3470S/3450S 103 + i7 3770T 94 + i5 3570T 94 + i5 3470T 91 + +32nm Core i3/i5/i7 Processors + i7 2600 98 + i7 660UM/640/620, 640LM/620, 620M, 610E 105 + i5 540UM/520/430, 540M/520/450/430 105 + i3 330E, 370M/350/330 90 rPGA, 105 BGA + i3 330UM 105 + +32nm Core i7 Extreme Processors + 980X 100 + +32nm Celeron Processors + U3400 105 + P4505/P4500 90 + +32nm Atom Processors + S1260/1220 95 + S1240 102 + Z2460 90 + Z2760 90 + D2700/2550/2500 100 + N2850/2800/2650/2600 100 + +45nm Xeon Processors 5400 Quad-Core + X5492, X5482, X5472, X5470, X5460, X5450 85 + E5472, E5462, E5450/40/30/20/10/05 85 + L5408 95 + L5430, L5420, L5410 70 + +45nm Xeon Processors 5200 Dual-Core + X5282, X5272, X5270, X5260 90 + E5240 90 + E5205, E5220 70, 90 + L5240 70 + L5238, L5215 95 + +45nm Atom Processors + D525/510/425/410 100 + K525/510/425/410 100 + Z670/650 90 + Z560/550/540/530P/530/520PT/520/515/510PT/510P 90 + Z510/500 90 + N570/550 100 + N475/470/455/450 100 + N280/270 90 + 330/230 125 + E680/660/640/620 90 + E680T/660T/640T/620T 110 + E665C/645C 90 + E665CT/645CT 110 + CE4170/4150/4110 110 + CE4200 series unknown + CE5300 series unknown + +45nm Core2 Processors + Solo ULV SU3500/3300 100 + T9900/9800/9600/9550/9500/9400/9300/8300/8100 105 + T6670/6500/6400 105 + T6600 90 + SU9600/9400/9300 105 + SP9600/9400 105 + SL9600/9400/9380/9300 105 + P9700/9600/9500/8800/8700/8600/8400/7570 105 + P7550/7450 90 + +45nm Core2 Quad Processors + Q9100/9000 100 + +45nm Core2 Extreme Processors + X9100/9000 105 + QX9300 100 + +45nm Core i3/i5/i7 Processors + i7 940XM/920 100 + i7 840QM/820/740/720 100 + +45nm Celeron Processors + SU2300 100 + 900 105 + +65nm Core2 Duo Processors + Solo U2200, U2100 100 + U7700/7600/7500 100 + T7800/7700/7600/7500/7400/7300/7250/7200/7100 100 + T5870/5670/5600/5550/5500/5470/5450/5300/5270 100 + T5250 100 + T5800/5750/5200 85 + L7700/7500/7400/7300/7200 100 + +65nm Core2 Extreme Processors + X7900/7800 100 + +65nm Core Duo Processors + U2500/2400 100 + T2700/2600/2450/2400/2350/2300E/2300/2250/2050 100 + L2500/2400/2300 100 + +65nm Core Solo Processors + U1500/1400/1300 100 + T1400/1350/1300/1250 100 + +65nm Xeon Processors 5000 Quad-Core + X5000 90-95 + E5000 80 + L5000 70 + L5318 95 + +65nm Xeon Processors 5000 Dual-Core + 5080, 5063, 5060, 5050, 5030 80-90 + 5160, 5150, 5148, 5140, 5130, 5120, 5110 80 + L5138 100 + +65nm Celeron Processors + T1700/1600 100 + 560/550/540/530 100 +=============== =============================================== ================ diff --git a/Documentation/hwmon/da9052 b/Documentation/hwmon/da9052 deleted file mode 100644 index c1c0f1f08904..000000000000 --- a/Documentation/hwmon/da9052 +++ /dev/null @@ -1,78 +0,0 @@ -Kernel driver da9052 -==================== - -Supported chips: - - * Dialog Semiconductors DA9052-BC and DA9053-AA/Bx PMICs - - Prefix: 'da9052' - - Datasheet: Datasheet is not publicly available. - -Authors: David Dajun Chen - -Description ------------ - -The DA9052/53 provides an Analogue to Digital Converter (ADC) with 10 bits -resolution and track and hold circuitry combined with an analogue input -multiplexer. The analogue input multiplexer will allow conversion of up to 10 -different inputs. The track and hold circuit ensures stable input voltages at -the input of the ADC during the conversion. - -The ADC is used to measure the following inputs: - -========= =================================================================== -Channel 0 VDDOUT - measurement of the system voltage -Channel 1 ICH - internal battery charger current measurement -Channel 2 TBAT - output from the battery NTC -Channel 3 VBAT - measurement of the battery voltage -Channel 4 ADC_IN4 - high impedance input (0 - 2.5V) -Channel 5 ADC_IN5 - high impedance input (0 - 2.5V) -Channel 6 ADC_IN6 - high impedance input (0 - 2.5V) -Channel 7 XY - TSI interface to measure the X and Y voltage of the touch - screen resistive potentiometers -Channel 8 Internal Tjunc. - sense (internal temp. sensor) -Channel 9 VBBAT - measurement of the backup battery voltage -========= =================================================================== - -By using sysfs attributes we can measure the system voltage VDDOUT, the battery -charging current ICH, battery temperature TBAT, battery junction temperature -TJUNC, battery voltage VBAT and the back up battery voltage VBBAT. - -Voltage Monitoring ------------------- - -Voltages are sampled by a 10 bit ADC. - -The battery voltage is calculated as: - - Milli volt = ((ADC value * 1000) / 512) + 2500 - -The backup battery voltage is calculated as: - - Milli volt = (ADC value * 2500) / 512; - -The voltages on ADC channels 4, 5 and 6 are calculated as: - - Milli volt = (ADC value * 2500) / 1023 - -Temperature Monitoring ----------------------- - -Temperatures are sampled by a 10 bit ADC. Junction and battery temperatures -are monitored by the ADC channels. - -The junction temperature is calculated: - - Degrees celsius = 1.708 * (TJUNC_RES - T_OFFSET) - 108.8 - -The junction temperature attribute is supported by the driver. - -The battery temperature is calculated: - - Degree Celsius = 1 / (t1 + 1/298) - 273 - -where t1 = (1/B)* ln(( ADCval * 2.5)/(R25*ITBAT*255)) - -Default values of R25, B, ITBAT are 10e3, 3380 and 50e-6 respectively. diff --git a/Documentation/hwmon/da9052.rst b/Documentation/hwmon/da9052.rst new file mode 100644 index 000000000000..c1c0f1f08904 --- /dev/null +++ b/Documentation/hwmon/da9052.rst @@ -0,0 +1,78 @@ +Kernel driver da9052 +==================== + +Supported chips: + + * Dialog Semiconductors DA9052-BC and DA9053-AA/Bx PMICs + + Prefix: 'da9052' + + Datasheet: Datasheet is not publicly available. + +Authors: David Dajun Chen + +Description +----------- + +The DA9052/53 provides an Analogue to Digital Converter (ADC) with 10 bits +resolution and track and hold circuitry combined with an analogue input +multiplexer. The analogue input multiplexer will allow conversion of up to 10 +different inputs. The track and hold circuit ensures stable input voltages at +the input of the ADC during the conversion. + +The ADC is used to measure the following inputs: + +========= =================================================================== +Channel 0 VDDOUT - measurement of the system voltage +Channel 1 ICH - internal battery charger current measurement +Channel 2 TBAT - output from the battery NTC +Channel 3 VBAT - measurement of the battery voltage +Channel 4 ADC_IN4 - high impedance input (0 - 2.5V) +Channel 5 ADC_IN5 - high impedance input (0 - 2.5V) +Channel 6 ADC_IN6 - high impedance input (0 - 2.5V) +Channel 7 XY - TSI interface to measure the X and Y voltage of the touch + screen resistive potentiometers +Channel 8 Internal Tjunc. - sense (internal temp. sensor) +Channel 9 VBBAT - measurement of the backup battery voltage +========= =================================================================== + +By using sysfs attributes we can measure the system voltage VDDOUT, the battery +charging current ICH, battery temperature TBAT, battery junction temperature +TJUNC, battery voltage VBAT and the back up battery voltage VBBAT. + +Voltage Monitoring +------------------ + +Voltages are sampled by a 10 bit ADC. + +The battery voltage is calculated as: + + Milli volt = ((ADC value * 1000) / 512) + 2500 + +The backup battery voltage is calculated as: + + Milli volt = (ADC value * 2500) / 512; + +The voltages on ADC channels 4, 5 and 6 are calculated as: + + Milli volt = (ADC value * 2500) / 1023 + +Temperature Monitoring +---------------------- + +Temperatures are sampled by a 10 bit ADC. Junction and battery temperatures +are monitored by the ADC channels. + +The junction temperature is calculated: + + Degrees celsius = 1.708 * (TJUNC_RES - T_OFFSET) - 108.8 + +The junction temperature attribute is supported by the driver. + +The battery temperature is calculated: + + Degree Celsius = 1 / (t1 + 1/298) - 273 + +where t1 = (1/B)* ln(( ADCval * 2.5)/(R25*ITBAT*255)) + +Default values of R25, B, ITBAT are 10e3, 3380 and 50e-6 respectively. diff --git a/Documentation/hwmon/da9055 b/Documentation/hwmon/da9055 deleted file mode 100644 index beae271a3312..000000000000 --- a/Documentation/hwmon/da9055 +++ /dev/null @@ -1,57 +0,0 @@ -Kernel driver da9055 -==================== - -Supported chips: - * Dialog Semiconductors DA9055 PMIC - - Prefix: 'da9055' - - Datasheet: Datasheet is not publicly available. - -Authors: David Dajun Chen - -Description ------------ - -The DA9055 provides an Analogue to Digital Converter (ADC) with 10 bits -resolution and track and hold circuitry combined with an analogue input -multiplexer. The analogue input multiplexer will allow conversion of up to 5 -different inputs. The track and hold circuit ensures stable input voltages at -the input of the ADC during the conversion. - -The ADC is used to measure the following inputs: - -- Channel 0: VDDOUT - measurement of the system voltage -- Channel 1: ADC_IN1 - high impedance input (0 - 2.5V) -- Channel 2: ADC_IN2 - high impedance input (0 - 2.5V) -- Channel 3: ADC_IN3 - high impedance input (0 - 2.5V) -- Channel 4: Internal Tjunc. - sense (internal temp. sensor) - -By using sysfs attributes we can measure the system voltage VDDOUT, -chip junction temperature and auxiliary channels voltages. - -Voltage Monitoring ------------------- - -Voltages are sampled in a AUTO mode it can be manually sampled too and results -are stored in a 10 bit ADC. - -The system voltage is calculated as: - - Milli volt = ((ADC value * 1000) / 85) + 2500 - -The voltages on ADC channels 1, 2 and 3 are calculated as: - - Milli volt = (ADC value * 1000) / 102 - -Temperature Monitoring ----------------------- - -Temperatures are sampled by a 10 bit ADC. Junction temperatures -are monitored by the ADC channels. - -The junction temperature is calculated: - - Degrees celsius = -0.4084 * (ADC_RES - T_OFFSET) + 307.6332 - -The junction temperature attribute is supported by the driver. diff --git a/Documentation/hwmon/da9055.rst b/Documentation/hwmon/da9055.rst new file mode 100644 index 000000000000..beae271a3312 --- /dev/null +++ b/Documentation/hwmon/da9055.rst @@ -0,0 +1,57 @@ +Kernel driver da9055 +==================== + +Supported chips: + * Dialog Semiconductors DA9055 PMIC + + Prefix: 'da9055' + + Datasheet: Datasheet is not publicly available. + +Authors: David Dajun Chen + +Description +----------- + +The DA9055 provides an Analogue to Digital Converter (ADC) with 10 bits +resolution and track and hold circuitry combined with an analogue input +multiplexer. The analogue input multiplexer will allow conversion of up to 5 +different inputs. The track and hold circuit ensures stable input voltages at +the input of the ADC during the conversion. + +The ADC is used to measure the following inputs: + +- Channel 0: VDDOUT - measurement of the system voltage +- Channel 1: ADC_IN1 - high impedance input (0 - 2.5V) +- Channel 2: ADC_IN2 - high impedance input (0 - 2.5V) +- Channel 3: ADC_IN3 - high impedance input (0 - 2.5V) +- Channel 4: Internal Tjunc. - sense (internal temp. sensor) + +By using sysfs attributes we can measure the system voltage VDDOUT, +chip junction temperature and auxiliary channels voltages. + +Voltage Monitoring +------------------ + +Voltages are sampled in a AUTO mode it can be manually sampled too and results +are stored in a 10 bit ADC. + +The system voltage is calculated as: + + Milli volt = ((ADC value * 1000) / 85) + 2500 + +The voltages on ADC channels 1, 2 and 3 are calculated as: + + Milli volt = (ADC value * 1000) / 102 + +Temperature Monitoring +---------------------- + +Temperatures are sampled by a 10 bit ADC. Junction temperatures +are monitored by the ADC channels. + +The junction temperature is calculated: + + Degrees celsius = -0.4084 * (ADC_RES - T_OFFSET) + 307.6332 + +The junction temperature attribute is supported by the driver. diff --git a/Documentation/hwmon/dme1737 b/Documentation/hwmon/dme1737 deleted file mode 100644 index 82fcbc6b2b43..000000000000 --- a/Documentation/hwmon/dme1737 +++ /dev/null @@ -1,364 +0,0 @@ -Kernel driver dme1737 -===================== - -Supported chips: - - * SMSC DME1737 and compatibles (like Asus A8000) - - Prefix: 'dme1737' - - Addresses scanned: I2C 0x2c, 0x2d, 0x2e - - Datasheet: Provided by SMSC upon request and under NDA - - * SMSC SCH3112, SCH3114, SCH3116 - - Prefix: 'sch311x' - - Addresses scanned: none, address read from Super-I/O config space - - Datasheet: Available on the Internet - - * SMSC SCH5027 - - Prefix: 'sch5027' - - Addresses scanned: I2C 0x2c, 0x2d, 0x2e - - Datasheet: Provided by SMSC upon request and under NDA - - * SMSC SCH5127 - - Prefix: 'sch5127' - - Addresses scanned: none, address read from Super-I/O config space - - Datasheet: Provided by SMSC upon request and under NDA - -Authors: - Juerg Haefliger - - -Module Parameters ------------------ - -* force_start: bool - Enables the monitoring of voltage, fan and temp inputs - and PWM output control functions. Using this parameter - shouldn't be required since the BIOS usually takes care - of this. - -* probe_all_addr: bool - Include non-standard LPC addresses 0x162e and 0x164e - when probing for ISA devices. This is required for the - following boards: - - VIA EPIA SN18000 - - -Description ------------ - -This driver implements support for the hardware monitoring capabilities of the -SMSC DME1737 and Asus A8000 (which are the same), SMSC SCH5027, SCH311x, -and SCH5127 Super-I/O chips. These chips feature monitoring of 3 temp sensors -temp[1-3] (2 remote diodes and 1 internal), 8 voltages in[0-7] (7 external and -1 internal) and up to 6 fan speeds fan[1-6]. Additionally, the chips implement -up to 5 PWM outputs pwm[1-3,5-6] for controlling fan speeds both manually and -automatically. - -For the DME1737, A8000 and SCH5027, fan[1-2] and pwm[1-2] are always present. -Fan[3-6] and pwm[3,5-6] are optional features and their availability depends on -the configuration of the chip. The driver will detect which features are -present during initialization and create the sysfs attributes accordingly. - -For the SCH311x and SCH5127, fan[1-3] and pwm[1-3] are always present and -fan[4-6] and pwm[5-6] don't exist. - -The hardware monitoring features of the DME1737, A8000, and SCH5027 are only -accessible via SMBus, while the SCH311x and SCH5127 only provide access via -the ISA bus. The driver will therefore register itself as an I2C client driver -if it detects a DME1737, A8000, or SCH5027 and as a platform driver if it -detects a SCH311x or SCH5127 chip. - - -Voltage Monitoring ------------------- - -The voltage inputs are sampled with 12-bit resolution and have internal -scaling resistors. The values returned by the driver therefore reflect true -millivolts and don't need scaling. The voltage inputs are mapped as follows -(the last column indicates the input ranges): - -DME1737, A8000:: - - in0: +5VTR (+5V standby) 0V - 6.64V - in1: Vccp (processor core) 0V - 3V - in2: VCC (internal +3.3V) 0V - 4.38V - in3: +5V 0V - 6.64V - in4: +12V 0V - 16V - in5: VTR (+3.3V standby) 0V - 4.38V - in6: Vbat (+3.0V) 0V - 4.38V - -SCH311x:: - - in0: +2.5V 0V - 3.32V - in1: Vccp (processor core) 0V - 2V - in2: VCC (internal +3.3V) 0V - 4.38V - in3: +5V 0V - 6.64V - in4: +12V 0V - 16V - in5: VTR (+3.3V standby) 0V - 4.38V - in6: Vbat (+3.0V) 0V - 4.38V - -SCH5027:: - - in0: +5VTR (+5V standby) 0V - 6.64V - in1: Vccp (processor core) 0V - 3V - in2: VCC (internal +3.3V) 0V - 4.38V - in3: V2_IN 0V - 1.5V - in4: V1_IN 0V - 1.5V - in5: VTR (+3.3V standby) 0V - 4.38V - in6: Vbat (+3.0V) 0V - 4.38V - -SCH5127:: - - in0: +2.5 0V - 3.32V - in1: Vccp (processor core) 0V - 3V - in2: VCC (internal +3.3V) 0V - 4.38V - in3: V2_IN 0V - 1.5V - in4: V1_IN 0V - 1.5V - in5: VTR (+3.3V standby) 0V - 4.38V - in6: Vbat (+3.0V) 0V - 4.38V - in7: Vtrip (+1.5V) 0V - 1.99V - -Each voltage input has associated min and max limits which trigger an alarm -when crossed. - - -Temperature Monitoring ----------------------- - -Temperatures are measured with 12-bit resolution and reported in millidegree -Celsius. The chip also features offsets for all 3 temperature inputs which - -when programmed - get added to the input readings. The chip does all the -scaling by itself and the driver therefore reports true temperatures that don't -need any user-space adjustments. The temperature inputs are mapped as follows -(the last column indicates the input ranges):: - - temp1: Remote diode 1 (3904 type) temperature -127C - +127C - temp2: DME1737 internal temperature -127C - +127C - temp3: Remote diode 2 (3904 type) temperature -127C - +127C - -Each temperature input has associated min and max limits which trigger an alarm -when crossed. Additionally, each temperature input has a fault attribute that -returns 1 when a faulty diode or an unconnected input is detected and 0 -otherwise. - - -Fan Monitoring --------------- - -Fan RPMs are measured with 16-bit resolution. The chip provides inputs for 6 -fan tachometers. All 6 inputs have an associated min limit which triggers an -alarm when crossed. Fan inputs 1-4 provide type attributes that need to be set -to the number of pulses per fan revolution that the connected tachometer -generates. Supported values are 1, 2, and 4. Fan inputs 5-6 only support fans -that generate 2 pulses per revolution. Fan inputs 5-6 also provide a max -attribute that needs to be set to the maximum attainable RPM (fan at 100% duty- -cycle) of the input. The chip adjusts the sampling rate based on this value. - - -PWM Output Control ------------------- - -This chip features 5 PWM outputs. PWM outputs 1-3 are associated with fan -inputs 1-3 and PWM outputs 5-6 are associated with fan inputs 5-6. PWM outputs -1-3 can be configured to operate either in manual or automatic mode by setting -the appropriate enable attribute accordingly. PWM outputs 5-6 can only operate -in manual mode, their enable attributes are therefore read-only. When set to -manual mode, the fan speed is set by writing the duty-cycle value to the -appropriate PWM attribute. In automatic mode, the PWM attribute returns the -current duty-cycle as set by the fan controller in the chip. All PWM outputs -support the setting of the output frequency via the freq attribute. - -In automatic mode, the chip supports the setting of the PWM ramp rate which -defines how fast the PWM output is adjusting to changes of the associated -temperature input. Associating PWM outputs to temperature inputs is done via -temperature zones. The chip features 3 zones whose assignments to temperature -inputs is static and determined during initialization. These assignments can -be retrieved via the zone[1-3]_auto_channels_temp attributes. Each PWM output -is assigned to one (or hottest of multiple) temperature zone(s) through the -pwm[1-3]_auto_channels_zone attributes. Each PWM output has 3 distinct output -duty-cycles: full, low, and min. Full is internally hard-wired to 255 (100%) -and low and min can be programmed via pwm[1-3]_auto_point1_pwm and -pwm[1-3]_auto_pwm_min, respectively. The thermal thresholds of the zones are -programmed via zone[1-3]_auto_point[1-3]_temp and -zone[1-3]_auto_point1_temp_hyst: - - =============================== ======================================= - pwm[1-3]_auto_point2_pwm full-speed duty-cycle (255, i.e., 100%) - pwm[1-3]_auto_point1_pwm low-speed duty-cycle - pwm[1-3]_auto_pwm_min min-speed duty-cycle - - zone[1-3]_auto_point3_temp full-speed temp (all outputs) - zone[1-3]_auto_point2_temp full-speed temp - zone[1-3]_auto_point1_temp low-speed temp - zone[1-3]_auto_point1_temp_hyst min-speed temp - =============================== ======================================= - -The chip adjusts the output duty-cycle linearly in the range of auto_point1_pwm -to auto_point2_pwm if the temperature of the associated zone is between -auto_point1_temp and auto_point2_temp. If the temperature drops below the -auto_point1_temp_hyst value, the output duty-cycle is set to the auto_pwm_min -value which only supports two values: 0 or auto_point1_pwm. That means that the -fan either turns completely off or keeps spinning with the low-speed -duty-cycle. If any of the temperatures rise above the auto_point3_temp value, -all PWM outputs are set to 100% duty-cycle. - -Following is another representation of how the chip sets the output duty-cycle -based on the temperature of the associated thermal zone: - - =============== =============== ================= - Temperature Duty-Cycle Duty-Cycle - Rising Temp Falling Temp - =============== =============== ================= - full-speed full-speed full-speed - - - < linearly - - adjusted - duty-cycle > - - low-speed low-speed low-speed - - min-speed low-speed - min-speed min-speed min-speed - - min-speed min-speed - =============== =============== ================= - - -Sysfs Attributes ----------------- - -Following is a list of all sysfs attributes that the driver provides, their -permissions and a short description: - -=============================== ======= ======================================= -Name Perm Description -=============================== ======= ======================================= -cpu0_vid RO CPU core reference voltage in - millivolts. -vrm RW Voltage regulator module version - number. - -in[0-7]_input RO Measured voltage in millivolts. -in[0-7]_min RW Low limit for voltage input. -in[0-7]_max RW High limit for voltage input. -in[0-7]_alarm RO Voltage input alarm. Returns 1 if - voltage input is or went outside the - associated min-max range, 0 otherwise. - -temp[1-3]_input RO Measured temperature in millidegree - Celsius. -temp[1-3]_min RW Low limit for temp input. -temp[1-3]_max RW High limit for temp input. -temp[1-3]_offset RW Offset for temp input. This value will - be added by the chip to the measured - temperature. -temp[1-3]_alarm RO Alarm for temp input. Returns 1 if temp - input is or went outside the associated - min-max range, 0 otherwise. -temp[1-3]_fault RO Temp input fault. Returns 1 if the chip - detects a faulty thermal diode or an - unconnected temp input, 0 otherwise. - -zone[1-3]_auto_channels_temp RO Temperature zone to temperature input - mapping. This attribute is a bitfield - and supports the following values: - - - 1: temp1 - - 2: temp2 - - 4: temp3 -zone[1-3]_auto_point1_temp_hyst RW Auto PWM temp point1 hysteresis. The - output of the corresponding PWM is set - to the pwm_auto_min value if the temp - falls below the auto_point1_temp_hyst - value. -zone[1-3]_auto_point[1-3]_temp RW Auto PWM temp points. Auto_point1 is - the low-speed temp, auto_point2 is the - full-speed temp, and auto_point3 is the - temp at which all PWM outputs are set - to full-speed (100% duty-cycle). - -fan[1-6]_input RO Measured fan speed in RPM. -fan[1-6]_min RW Low limit for fan input. -fan[1-6]_alarm RO Alarm for fan input. Returns 1 if fan - input is or went below the associated - min value, 0 otherwise. -fan[1-4]_type RW Type of attached fan. Expressed in - number of pulses per revolution that - the fan generates. Supported values are - 1, 2, and 4. -fan[5-6]_max RW Max attainable RPM at 100% duty-cycle. - Required for chip to adjust the - sampling rate accordingly. - -pmw[1-3,5-6] RO/RW Duty-cycle of PWM output. Supported - values are 0-255 (0%-100%). Only - writeable if the associated PWM is in - manual mode. -pwm[1-3]_enable RW Enable of PWM outputs 1-3. Supported - values are: - - - 0: turned off (output @ 100%) - - 1: manual mode - - 2: automatic mode -pwm[5-6]_enable RO Enable of PWM outputs 5-6. Always - returns 1 since these 2 outputs are - hard-wired to manual mode. -pmw[1-3,5-6]_freq RW Frequency of PWM output. Supported - values are in the range 11Hz-30000Hz - (default is 25000Hz). -pmw[1-3]_ramp_rate RW Ramp rate of PWM output. Determines how - fast the PWM duty-cycle will change - when the PWM is in automatic mode. - Expressed in ms per PWM step. Supported - values are in the range 0ms-206ms - (default is 0, which means the duty- - cycle changes instantly). -pwm[1-3]_auto_channels_zone RW PWM output to temperature zone mapping. - This attribute is a bitfield and - supports the following values: - - - 1: zone1 - - 2: zone2 - - 4: zone3 - - 6: highest of zone[2-3] - - 7: highest of zone[1-3] -pwm[1-3]_auto_pwm_min RW Auto PWM min pwm. Minimum PWM duty- - cycle. Supported values are 0 or - auto_point1_pwm. -pwm[1-3]_auto_point1_pwm RW Auto PWM pwm point. Auto_point1 is the - low-speed duty-cycle. -pwm[1-3]_auto_point2_pwm RO Auto PWM pwm point. Auto_point2 is the - full-speed duty-cycle which is hard- - wired to 255 (100% duty-cycle). -=============================== ======= ======================================= - -Chip Differences ----------------- - -======================= ======= ======= ======= ======= -Feature dme1737 sch311x sch5027 sch5127 -======================= ======= ======= ======= ======= -temp[1-3]_offset yes yes -vid yes -zone3 yes yes yes -zone[1-3]_hyst yes yes -pwm min/off yes yes -fan3 opt yes opt yes -pwm3 opt yes opt yes -fan4 opt opt -fan5 opt opt -pwm5 opt opt -fan6 opt opt -pwm6 opt opt -in7 yes -======================= ======= ======= ======= ======= diff --git a/Documentation/hwmon/dme1737.rst b/Documentation/hwmon/dme1737.rst new file mode 100644 index 000000000000..82fcbc6b2b43 --- /dev/null +++ b/Documentation/hwmon/dme1737.rst @@ -0,0 +1,364 @@ +Kernel driver dme1737 +===================== + +Supported chips: + + * SMSC DME1737 and compatibles (like Asus A8000) + + Prefix: 'dme1737' + + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + + Datasheet: Provided by SMSC upon request and under NDA + + * SMSC SCH3112, SCH3114, SCH3116 + + Prefix: 'sch311x' + + Addresses scanned: none, address read from Super-I/O config space + + Datasheet: Available on the Internet + + * SMSC SCH5027 + + Prefix: 'sch5027' + + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + + Datasheet: Provided by SMSC upon request and under NDA + + * SMSC SCH5127 + + Prefix: 'sch5127' + + Addresses scanned: none, address read from Super-I/O config space + + Datasheet: Provided by SMSC upon request and under NDA + +Authors: + Juerg Haefliger + + +Module Parameters +----------------- + +* force_start: bool + Enables the monitoring of voltage, fan and temp inputs + and PWM output control functions. Using this parameter + shouldn't be required since the BIOS usually takes care + of this. + +* probe_all_addr: bool + Include non-standard LPC addresses 0x162e and 0x164e + when probing for ISA devices. This is required for the + following boards: + - VIA EPIA SN18000 + + +Description +----------- + +This driver implements support for the hardware monitoring capabilities of the +SMSC DME1737 and Asus A8000 (which are the same), SMSC SCH5027, SCH311x, +and SCH5127 Super-I/O chips. These chips feature monitoring of 3 temp sensors +temp[1-3] (2 remote diodes and 1 internal), 8 voltages in[0-7] (7 external and +1 internal) and up to 6 fan speeds fan[1-6]. Additionally, the chips implement +up to 5 PWM outputs pwm[1-3,5-6] for controlling fan speeds both manually and +automatically. + +For the DME1737, A8000 and SCH5027, fan[1-2] and pwm[1-2] are always present. +Fan[3-6] and pwm[3,5-6] are optional features and their availability depends on +the configuration of the chip. The driver will detect which features are +present during initialization and create the sysfs attributes accordingly. + +For the SCH311x and SCH5127, fan[1-3] and pwm[1-3] are always present and +fan[4-6] and pwm[5-6] don't exist. + +The hardware monitoring features of the DME1737, A8000, and SCH5027 are only +accessible via SMBus, while the SCH311x and SCH5127 only provide access via +the ISA bus. The driver will therefore register itself as an I2C client driver +if it detects a DME1737, A8000, or SCH5027 and as a platform driver if it +detects a SCH311x or SCH5127 chip. + + +Voltage Monitoring +------------------ + +The voltage inputs are sampled with 12-bit resolution and have internal +scaling resistors. The values returned by the driver therefore reflect true +millivolts and don't need scaling. The voltage inputs are mapped as follows +(the last column indicates the input ranges): + +DME1737, A8000:: + + in0: +5VTR (+5V standby) 0V - 6.64V + in1: Vccp (processor core) 0V - 3V + in2: VCC (internal +3.3V) 0V - 4.38V + in3: +5V 0V - 6.64V + in4: +12V 0V - 16V + in5: VTR (+3.3V standby) 0V - 4.38V + in6: Vbat (+3.0V) 0V - 4.38V + +SCH311x:: + + in0: +2.5V 0V - 3.32V + in1: Vccp (processor core) 0V - 2V + in2: VCC (internal +3.3V) 0V - 4.38V + in3: +5V 0V - 6.64V + in4: +12V 0V - 16V + in5: VTR (+3.3V standby) 0V - 4.38V + in6: Vbat (+3.0V) 0V - 4.38V + +SCH5027:: + + in0: +5VTR (+5V standby) 0V - 6.64V + in1: Vccp (processor core) 0V - 3V + in2: VCC (internal +3.3V) 0V - 4.38V + in3: V2_IN 0V - 1.5V + in4: V1_IN 0V - 1.5V + in5: VTR (+3.3V standby) 0V - 4.38V + in6: Vbat (+3.0V) 0V - 4.38V + +SCH5127:: + + in0: +2.5 0V - 3.32V + in1: Vccp (processor core) 0V - 3V + in2: VCC (internal +3.3V) 0V - 4.38V + in3: V2_IN 0V - 1.5V + in4: V1_IN 0V - 1.5V + in5: VTR (+3.3V standby) 0V - 4.38V + in6: Vbat (+3.0V) 0V - 4.38V + in7: Vtrip (+1.5V) 0V - 1.99V + +Each voltage input has associated min and max limits which trigger an alarm +when crossed. + + +Temperature Monitoring +---------------------- + +Temperatures are measured with 12-bit resolution and reported in millidegree +Celsius. The chip also features offsets for all 3 temperature inputs which - +when programmed - get added to the input readings. The chip does all the +scaling by itself and the driver therefore reports true temperatures that don't +need any user-space adjustments. The temperature inputs are mapped as follows +(the last column indicates the input ranges):: + + temp1: Remote diode 1 (3904 type) temperature -127C - +127C + temp2: DME1737 internal temperature -127C - +127C + temp3: Remote diode 2 (3904 type) temperature -127C - +127C + +Each temperature input has associated min and max limits which trigger an alarm +when crossed. Additionally, each temperature input has a fault attribute that +returns 1 when a faulty diode or an unconnected input is detected and 0 +otherwise. + + +Fan Monitoring +-------------- + +Fan RPMs are measured with 16-bit resolution. The chip provides inputs for 6 +fan tachometers. All 6 inputs have an associated min limit which triggers an +alarm when crossed. Fan inputs 1-4 provide type attributes that need to be set +to the number of pulses per fan revolution that the connected tachometer +generates. Supported values are 1, 2, and 4. Fan inputs 5-6 only support fans +that generate 2 pulses per revolution. Fan inputs 5-6 also provide a max +attribute that needs to be set to the maximum attainable RPM (fan at 100% duty- +cycle) of the input. The chip adjusts the sampling rate based on this value. + + +PWM Output Control +------------------ + +This chip features 5 PWM outputs. PWM outputs 1-3 are associated with fan +inputs 1-3 and PWM outputs 5-6 are associated with fan inputs 5-6. PWM outputs +1-3 can be configured to operate either in manual or automatic mode by setting +the appropriate enable attribute accordingly. PWM outputs 5-6 can only operate +in manual mode, their enable attributes are therefore read-only. When set to +manual mode, the fan speed is set by writing the duty-cycle value to the +appropriate PWM attribute. In automatic mode, the PWM attribute returns the +current duty-cycle as set by the fan controller in the chip. All PWM outputs +support the setting of the output frequency via the freq attribute. + +In automatic mode, the chip supports the setting of the PWM ramp rate which +defines how fast the PWM output is adjusting to changes of the associated +temperature input. Associating PWM outputs to temperature inputs is done via +temperature zones. The chip features 3 zones whose assignments to temperature +inputs is static and determined during initialization. These assignments can +be retrieved via the zone[1-3]_auto_channels_temp attributes. Each PWM output +is assigned to one (or hottest of multiple) temperature zone(s) through the +pwm[1-3]_auto_channels_zone attributes. Each PWM output has 3 distinct output +duty-cycles: full, low, and min. Full is internally hard-wired to 255 (100%) +and low and min can be programmed via pwm[1-3]_auto_point1_pwm and +pwm[1-3]_auto_pwm_min, respectively. The thermal thresholds of the zones are +programmed via zone[1-3]_auto_point[1-3]_temp and +zone[1-3]_auto_point1_temp_hyst: + + =============================== ======================================= + pwm[1-3]_auto_point2_pwm full-speed duty-cycle (255, i.e., 100%) + pwm[1-3]_auto_point1_pwm low-speed duty-cycle + pwm[1-3]_auto_pwm_min min-speed duty-cycle + + zone[1-3]_auto_point3_temp full-speed temp (all outputs) + zone[1-3]_auto_point2_temp full-speed temp + zone[1-3]_auto_point1_temp low-speed temp + zone[1-3]_auto_point1_temp_hyst min-speed temp + =============================== ======================================= + +The chip adjusts the output duty-cycle linearly in the range of auto_point1_pwm +to auto_point2_pwm if the temperature of the associated zone is between +auto_point1_temp and auto_point2_temp. If the temperature drops below the +auto_point1_temp_hyst value, the output duty-cycle is set to the auto_pwm_min +value which only supports two values: 0 or auto_point1_pwm. That means that the +fan either turns completely off or keeps spinning with the low-speed +duty-cycle. If any of the temperatures rise above the auto_point3_temp value, +all PWM outputs are set to 100% duty-cycle. + +Following is another representation of how the chip sets the output duty-cycle +based on the temperature of the associated thermal zone: + + =============== =============== ================= + Temperature Duty-Cycle Duty-Cycle + Rising Temp Falling Temp + =============== =============== ================= + full-speed full-speed full-speed + + - < linearly - + adjusted + duty-cycle > + + low-speed low-speed low-speed + - min-speed low-speed + min-speed min-speed min-speed + - min-speed min-speed + =============== =============== ================= + + +Sysfs Attributes +---------------- + +Following is a list of all sysfs attributes that the driver provides, their +permissions and a short description: + +=============================== ======= ======================================= +Name Perm Description +=============================== ======= ======================================= +cpu0_vid RO CPU core reference voltage in + millivolts. +vrm RW Voltage regulator module version + number. + +in[0-7]_input RO Measured voltage in millivolts. +in[0-7]_min RW Low limit for voltage input. +in[0-7]_max RW High limit for voltage input. +in[0-7]_alarm RO Voltage input alarm. Returns 1 if + voltage input is or went outside the + associated min-max range, 0 otherwise. + +temp[1-3]_input RO Measured temperature in millidegree + Celsius. +temp[1-3]_min RW Low limit for temp input. +temp[1-3]_max RW High limit for temp input. +temp[1-3]_offset RW Offset for temp input. This value will + be added by the chip to the measured + temperature. +temp[1-3]_alarm RO Alarm for temp input. Returns 1 if temp + input is or went outside the associated + min-max range, 0 otherwise. +temp[1-3]_fault RO Temp input fault. Returns 1 if the chip + detects a faulty thermal diode or an + unconnected temp input, 0 otherwise. + +zone[1-3]_auto_channels_temp RO Temperature zone to temperature input + mapping. This attribute is a bitfield + and supports the following values: + + - 1: temp1 + - 2: temp2 + - 4: temp3 +zone[1-3]_auto_point1_temp_hyst RW Auto PWM temp point1 hysteresis. The + output of the corresponding PWM is set + to the pwm_auto_min value if the temp + falls below the auto_point1_temp_hyst + value. +zone[1-3]_auto_point[1-3]_temp RW Auto PWM temp points. Auto_point1 is + the low-speed temp, auto_point2 is the + full-speed temp, and auto_point3 is the + temp at which all PWM outputs are set + to full-speed (100% duty-cycle). + +fan[1-6]_input RO Measured fan speed in RPM. +fan[1-6]_min RW Low limit for fan input. +fan[1-6]_alarm RO Alarm for fan input. Returns 1 if fan + input is or went below the associated + min value, 0 otherwise. +fan[1-4]_type RW Type of attached fan. Expressed in + number of pulses per revolution that + the fan generates. Supported values are + 1, 2, and 4. +fan[5-6]_max RW Max attainable RPM at 100% duty-cycle. + Required for chip to adjust the + sampling rate accordingly. + +pmw[1-3,5-6] RO/RW Duty-cycle of PWM output. Supported + values are 0-255 (0%-100%). Only + writeable if the associated PWM is in + manual mode. +pwm[1-3]_enable RW Enable of PWM outputs 1-3. Supported + values are: + + - 0: turned off (output @ 100%) + - 1: manual mode + - 2: automatic mode +pwm[5-6]_enable RO Enable of PWM outputs 5-6. Always + returns 1 since these 2 outputs are + hard-wired to manual mode. +pmw[1-3,5-6]_freq RW Frequency of PWM output. Supported + values are in the range 11Hz-30000Hz + (default is 25000Hz). +pmw[1-3]_ramp_rate RW Ramp rate of PWM output. Determines how + fast the PWM duty-cycle will change + when the PWM is in automatic mode. + Expressed in ms per PWM step. Supported + values are in the range 0ms-206ms + (default is 0, which means the duty- + cycle changes instantly). +pwm[1-3]_auto_channels_zone RW PWM output to temperature zone mapping. + This attribute is a bitfield and + supports the following values: + + - 1: zone1 + - 2: zone2 + - 4: zone3 + - 6: highest of zone[2-3] + - 7: highest of zone[1-3] +pwm[1-3]_auto_pwm_min RW Auto PWM min pwm. Minimum PWM duty- + cycle. Supported values are 0 or + auto_point1_pwm. +pwm[1-3]_auto_point1_pwm RW Auto PWM pwm point. Auto_point1 is the + low-speed duty-cycle. +pwm[1-3]_auto_point2_pwm RO Auto PWM pwm point. Auto_point2 is the + full-speed duty-cycle which is hard- + wired to 255 (100% duty-cycle). +=============================== ======= ======================================= + +Chip Differences +---------------- + +======================= ======= ======= ======= ======= +Feature dme1737 sch311x sch5027 sch5127 +======================= ======= ======= ======= ======= +temp[1-3]_offset yes yes +vid yes +zone3 yes yes yes +zone[1-3]_hyst yes yes +pwm min/off yes yes +fan3 opt yes opt yes +pwm3 opt yes opt yes +fan4 opt opt +fan5 opt opt +pwm5 opt opt +fan6 opt opt +pwm6 opt opt +in7 yes +======================= ======= ======= ======= ======= diff --git a/Documentation/hwmon/ds1621 b/Documentation/hwmon/ds1621 deleted file mode 100644 index 552b37e9dd34..000000000000 --- a/Documentation/hwmon/ds1621 +++ /dev/null @@ -1,217 +0,0 @@ -Kernel driver ds1621 -==================== - -Supported chips: - - * Dallas Semiconductor / Maxim Integrated DS1621 - - Prefix: 'ds1621' - - Addresses scanned: none - - Datasheet: Publicly available from www.maximintegrated.com - - * Dallas Semiconductor DS1625 - - Prefix: 'ds1625' - - Addresses scanned: none - - Datasheet: Publicly available from www.datasheetarchive.com - - * Maxim Integrated DS1631 - - Prefix: 'ds1631' - - Addresses scanned: none - - Datasheet: Publicly available from www.maximintegrated.com - - * Maxim Integrated DS1721 - - Prefix: 'ds1721' - - Addresses scanned: none - - Datasheet: Publicly available from www.maximintegrated.com - - * Maxim Integrated DS1731 - - Prefix: 'ds1731' - - Addresses scanned: none - - Datasheet: Publicly available from www.maximintegrated.com - -Authors: - - Christian W. Zuckschwerdt - - valuable contributions by Jan M. Sendler - - ported to 2.6 by Aurelien Jarno - with the help of Jean Delvare - -Module Parameters ------------------- - -* polarity int - Output's polarity: - - * 0 = active high, - * 1 = active low - -Description ------------ - -The DS1621 is a (one instance) digital thermometer and thermostat. It has -both high and low temperature limits which can be user defined (i.e. -programmed into non-volatile on-chip registers). Temperature range is -55 -degree Celsius to +125 in 0.5 increments. You may convert this into a -Fahrenheit range of -67 to +257 degrees with 0.9 steps. If polarity -parameter is not provided, original value is used. - -As for the thermostat, behavior can also be programmed using the polarity -toggle. On the one hand ("heater"), the thermostat output of the chip, -Tout, will trigger when the low limit temperature is met or underrun and -stays high until the high limit is met or exceeded. On the other hand -("cooler"), vice versa. That way "heater" equals "active low", whereas -"conditioner" equals "active high". Please note that the DS1621 data sheet -is somewhat misleading in this point since setting the polarity bit does -not simply invert Tout. - -A second thing is that, during extensive testing, Tout showed a tolerance -of up to +/- 0.5 degrees even when compared against precise temperature -readings. Be sure to have a high vs. low temperature limit gap of al least -1.0 degree Celsius to avoid Tout "bouncing", though! - -The alarm bits are set when the high or low limits are met or exceeded and -are reset by the module as soon as the respective temperature ranges are -left. - -The alarm registers are in no way suitable to find out about the actual -status of Tout. They will only tell you about its history, whether or not -any of the limits have ever been met or exceeded since last power-up or -reset. Be aware: When testing, it showed that the status of Tout can change -with neither of the alarms set. - -Since there is no version or vendor identification register, there is -no unique identification for these devices. Therefore, explicit device -instantiation is required for correct device identification and functionality -(one device per address in this address range: 0x48..0x4f). - -The DS1625 is pin compatible and functionally equivalent with the DS1621, -but the DS1621 is meant to replace it. The DS1631, DS1721, and DS1731 are -also pin compatible with the DS1621 and provide multi-resolution support. - -Additionally, the DS1721 data sheet says the temperature flags (THF and TLF) -are used internally, however, these flags do get set and cleared as the actual -temperature crosses the min or max settings (which by default are set to 75 -and 80 degrees respectively). - -Temperature Conversion ----------------------- - -- DS1621 - 750ms (older devices may take up to 1000ms) -- DS1625 - 500ms -- DS1631 - 93ms..750ms for 9..12 bits resolution, respectively. -- DS1721 - 93ms..750ms for 9..12 bits resolution, respectively. -- DS1731 - 93ms..750ms for 9..12 bits resolution, respectively. - -Note: -On the DS1621, internal access to non-volatile registers may last for 10ms -or less (unverified on the other devices). - -Temperature Accuracy --------------------- - -- DS1621: +/- 0.5 degree Celsius (from 0 to +70 degrees) -- DS1625: +/- 0.5 degree Celsius (from 0 to +70 degrees) -- DS1631: +/- 0.5 degree Celsius (from 0 to +70 degrees) -- DS1721: +/- 1.0 degree Celsius (from -10 to +85 degrees) -- DS1731: +/- 1.0 degree Celsius (from -10 to +85 degrees) - -.. Note:: - - Please refer to the device datasheets for accuracy at other temperatures. - -Temperature Resolution: ------------------------ -As mentioned above, the DS1631, DS1721, and DS1731 provide multi-resolution -support, which is achieved via the R0 and R1 config register bits, where: - -R0..R1 ------- - -== == =============================== -R0 R1 -== == =============================== - 0 0 9 bits, 0.5 degrees Celsius - 1 0 10 bits, 0.25 degrees Celsius - 0 1 11 bits, 0.125 degrees Celsius - 1 1 12 bits, 0.0625 degrees Celsius -== == =============================== - -.. Note:: - - At initial device power-on, the default resolution is set to 12-bits. - -The resolution mode for the DS1631, DS1721, or DS1731 can be changed from -userspace, via the device 'update_interval' sysfs attribute. This attribute -will normalize the range of input values to the device maximum resolution -values defined in the datasheet as follows: - -============= ================== =============== -Resolution Conversion Time Input Range - (C/LSB) (msec) (msec) -============= ================== =============== -0.5 93.75 0....94 -0.25 187.5 95...187 -0.125 375 188..375 -0.0625 750 376..infinity -============= ================== =============== - -The following examples show how the 'update_interval' attribute can be -used to change the conversion time:: - - $ cat update_interval - 750 - $ cat temp1_input - 22062 - $ - $ echo 300 > update_interval - $ cat update_interval - 375 - $ cat temp1_input - 22125 - $ - $ echo 150 > update_interval - $ cat update_interval - 188 - $ cat temp1_input - 22250 - $ - $ echo 1 > update_interval - $ cat update_interval - 94 - $ cat temp1_input - 22000 - $ - $ echo 1000 > update_interval - $ cat update_interval - 750 - $ cat temp1_input - 22062 - $ - -As shown, the ds1621 driver automatically adjusts the 'update_interval' -user input, via a step function. Reading back the 'update_interval' value -after a write operation provides the conversion time used by the device. - -Mathematically, the resolution can be derived from the conversion time -via the following function: - - g(x) = 0.5 * [minimum_conversion_time/x] - -where: - - - 'x' = the output from 'update_interval' - - 'g(x)' = the resolution in degrees C per LSB. - - 93.75ms = minimum conversion time diff --git a/Documentation/hwmon/ds1621.rst b/Documentation/hwmon/ds1621.rst new file mode 100644 index 000000000000..552b37e9dd34 --- /dev/null +++ b/Documentation/hwmon/ds1621.rst @@ -0,0 +1,217 @@ +Kernel driver ds1621 +==================== + +Supported chips: + + * Dallas Semiconductor / Maxim Integrated DS1621 + + Prefix: 'ds1621' + + Addresses scanned: none + + Datasheet: Publicly available from www.maximintegrated.com + + * Dallas Semiconductor DS1625 + + Prefix: 'ds1625' + + Addresses scanned: none + + Datasheet: Publicly available from www.datasheetarchive.com + + * Maxim Integrated DS1631 + + Prefix: 'ds1631' + + Addresses scanned: none + + Datasheet: Publicly available from www.maximintegrated.com + + * Maxim Integrated DS1721 + + Prefix: 'ds1721' + + Addresses scanned: none + + Datasheet: Publicly available from www.maximintegrated.com + + * Maxim Integrated DS1731 + + Prefix: 'ds1731' + + Addresses scanned: none + + Datasheet: Publicly available from www.maximintegrated.com + +Authors: + - Christian W. Zuckschwerdt + - valuable contributions by Jan M. Sendler + - ported to 2.6 by Aurelien Jarno + with the help of Jean Delvare + +Module Parameters +------------------ + +* polarity int + Output's polarity: + + * 0 = active high, + * 1 = active low + +Description +----------- + +The DS1621 is a (one instance) digital thermometer and thermostat. It has +both high and low temperature limits which can be user defined (i.e. +programmed into non-volatile on-chip registers). Temperature range is -55 +degree Celsius to +125 in 0.5 increments. You may convert this into a +Fahrenheit range of -67 to +257 degrees with 0.9 steps. If polarity +parameter is not provided, original value is used. + +As for the thermostat, behavior can also be programmed using the polarity +toggle. On the one hand ("heater"), the thermostat output of the chip, +Tout, will trigger when the low limit temperature is met or underrun and +stays high until the high limit is met or exceeded. On the other hand +("cooler"), vice versa. That way "heater" equals "active low", whereas +"conditioner" equals "active high". Please note that the DS1621 data sheet +is somewhat misleading in this point since setting the polarity bit does +not simply invert Tout. + +A second thing is that, during extensive testing, Tout showed a tolerance +of up to +/- 0.5 degrees even when compared against precise temperature +readings. Be sure to have a high vs. low temperature limit gap of al least +1.0 degree Celsius to avoid Tout "bouncing", though! + +The alarm bits are set when the high or low limits are met or exceeded and +are reset by the module as soon as the respective temperature ranges are +left. + +The alarm registers are in no way suitable to find out about the actual +status of Tout. They will only tell you about its history, whether or not +any of the limits have ever been met or exceeded since last power-up or +reset. Be aware: When testing, it showed that the status of Tout can change +with neither of the alarms set. + +Since there is no version or vendor identification register, there is +no unique identification for these devices. Therefore, explicit device +instantiation is required for correct device identification and functionality +(one device per address in this address range: 0x48..0x4f). + +The DS1625 is pin compatible and functionally equivalent with the DS1621, +but the DS1621 is meant to replace it. The DS1631, DS1721, and DS1731 are +also pin compatible with the DS1621 and provide multi-resolution support. + +Additionally, the DS1721 data sheet says the temperature flags (THF and TLF) +are used internally, however, these flags do get set and cleared as the actual +temperature crosses the min or max settings (which by default are set to 75 +and 80 degrees respectively). + +Temperature Conversion +---------------------- + +- DS1621 - 750ms (older devices may take up to 1000ms) +- DS1625 - 500ms +- DS1631 - 93ms..750ms for 9..12 bits resolution, respectively. +- DS1721 - 93ms..750ms for 9..12 bits resolution, respectively. +- DS1731 - 93ms..750ms for 9..12 bits resolution, respectively. + +Note: +On the DS1621, internal access to non-volatile registers may last for 10ms +or less (unverified on the other devices). + +Temperature Accuracy +-------------------- + +- DS1621: +/- 0.5 degree Celsius (from 0 to +70 degrees) +- DS1625: +/- 0.5 degree Celsius (from 0 to +70 degrees) +- DS1631: +/- 0.5 degree Celsius (from 0 to +70 degrees) +- DS1721: +/- 1.0 degree Celsius (from -10 to +85 degrees) +- DS1731: +/- 1.0 degree Celsius (from -10 to +85 degrees) + +.. Note:: + + Please refer to the device datasheets for accuracy at other temperatures. + +Temperature Resolution: +----------------------- +As mentioned above, the DS1631, DS1721, and DS1731 provide multi-resolution +support, which is achieved via the R0 and R1 config register bits, where: + +R0..R1 +------ + +== == =============================== +R0 R1 +== == =============================== + 0 0 9 bits, 0.5 degrees Celsius + 1 0 10 bits, 0.25 degrees Celsius + 0 1 11 bits, 0.125 degrees Celsius + 1 1 12 bits, 0.0625 degrees Celsius +== == =============================== + +.. Note:: + + At initial device power-on, the default resolution is set to 12-bits. + +The resolution mode for the DS1631, DS1721, or DS1731 can be changed from +userspace, via the device 'update_interval' sysfs attribute. This attribute +will normalize the range of input values to the device maximum resolution +values defined in the datasheet as follows: + +============= ================== =============== +Resolution Conversion Time Input Range + (C/LSB) (msec) (msec) +============= ================== =============== +0.5 93.75 0....94 +0.25 187.5 95...187 +0.125 375 188..375 +0.0625 750 376..infinity +============= ================== =============== + +The following examples show how the 'update_interval' attribute can be +used to change the conversion time:: + + $ cat update_interval + 750 + $ cat temp1_input + 22062 + $ + $ echo 300 > update_interval + $ cat update_interval + 375 + $ cat temp1_input + 22125 + $ + $ echo 150 > update_interval + $ cat update_interval + 188 + $ cat temp1_input + 22250 + $ + $ echo 1 > update_interval + $ cat update_interval + 94 + $ cat temp1_input + 22000 + $ + $ echo 1000 > update_interval + $ cat update_interval + 750 + $ cat temp1_input + 22062 + $ + +As shown, the ds1621 driver automatically adjusts the 'update_interval' +user input, via a step function. Reading back the 'update_interval' value +after a write operation provides the conversion time used by the device. + +Mathematically, the resolution can be derived from the conversion time +via the following function: + + g(x) = 0.5 * [minimum_conversion_time/x] + +where: + + - 'x' = the output from 'update_interval' + - 'g(x)' = the resolution in degrees C per LSB. + - 93.75ms = minimum conversion time diff --git a/Documentation/hwmon/ds620 b/Documentation/hwmon/ds620 deleted file mode 100644 index 2d686b17b547..000000000000 --- a/Documentation/hwmon/ds620 +++ /dev/null @@ -1,38 +0,0 @@ -Kernel driver ds620 -=================== - -Supported chips: - - * Dallas Semiconductor DS620 - - Prefix: 'ds620' - - Datasheet: Publicly available at the Dallas Semiconductor website - - http://www.dalsemi.com/ - -Authors: - Roland Stigge - based on ds1621.c by - Christian W. Zuckschwerdt - -Description ------------ - -The DS620 is a (one instance) digital thermometer and thermostat. It has both -high and low temperature limits which can be user defined (i.e. programmed -into non-volatile on-chip registers). Temperature range is -55 degree Celsius -to +125. Between 0 and 70 degree Celsius, accuracy is 0.5 Kelvin. The value -returned via sysfs displays post decimal positions. - -The thermostat function works as follows: When configured via platform_data -(struct ds620_platform_data) .pomode == 0 (default), the thermostat output pin -PO is always low. If .pomode == 1, the thermostat is in PO_LOW mode. I.e., the -output pin PO becomes active when the temperature falls below temp1_min and -stays active until the temperature goes above temp1_max. - -Likewise, with .pomode == 2, the thermostat is in PO_HIGH mode. I.e., the PO -output pin becomes active when the temperature goes above temp1_max and stays -active until the temperature falls below temp1_min. - -The PO output pin of the DS620 operates active-low. diff --git a/Documentation/hwmon/ds620.rst b/Documentation/hwmon/ds620.rst new file mode 100644 index 000000000000..2d686b17b547 --- /dev/null +++ b/Documentation/hwmon/ds620.rst @@ -0,0 +1,38 @@ +Kernel driver ds620 +=================== + +Supported chips: + + * Dallas Semiconductor DS620 + + Prefix: 'ds620' + + Datasheet: Publicly available at the Dallas Semiconductor website + + http://www.dalsemi.com/ + +Authors: + Roland Stigge + based on ds1621.c by + Christian W. Zuckschwerdt + +Description +----------- + +The DS620 is a (one instance) digital thermometer and thermostat. It has both +high and low temperature limits which can be user defined (i.e. programmed +into non-volatile on-chip registers). Temperature range is -55 degree Celsius +to +125. Between 0 and 70 degree Celsius, accuracy is 0.5 Kelvin. The value +returned via sysfs displays post decimal positions. + +The thermostat function works as follows: When configured via platform_data +(struct ds620_platform_data) .pomode == 0 (default), the thermostat output pin +PO is always low. If .pomode == 1, the thermostat is in PO_LOW mode. I.e., the +output pin PO becomes active when the temperature falls below temp1_min and +stays active until the temperature goes above temp1_max. + +Likewise, with .pomode == 2, the thermostat is in PO_HIGH mode. I.e., the PO +output pin becomes active when the temperature goes above temp1_max and stays +active until the temperature falls below temp1_min. + +The PO output pin of the DS620 operates active-low. diff --git a/Documentation/hwmon/emc1403 b/Documentation/hwmon/emc1403 deleted file mode 100644 index 3a4913b63ef3..000000000000 --- a/Documentation/hwmon/emc1403 +++ /dev/null @@ -1,80 +0,0 @@ -Kernel driver emc1403 -===================== - -Supported chips: - - * SMSC / Microchip EMC1402, EMC1412 - - Addresses scanned: I2C 0x18, 0x1c, 0x29, 0x4c, 0x4d, 0x5c - - Prefix: 'emc1402' - - Datasheets: - - - http://ww1.microchip.com/downloads/en/DeviceDoc/1412.pdf - - http://ww1.microchip.com/downloads/en/DeviceDoc/1402.pdf - - * SMSC / Microchip EMC1403, EMC1404, EMC1413, EMC1414 - - Addresses scanned: I2C 0x18, 0x29, 0x4c, 0x4d - - Prefix: 'emc1403', 'emc1404' - - Datasheets: - - - http://ww1.microchip.com/downloads/en/DeviceDoc/1403_1404.pdf - - http://ww1.microchip.com/downloads/en/DeviceDoc/1413_1414.pdf - - * SMSC / Microchip EMC1422 - - Addresses scanned: I2C 0x4c - - Prefix: 'emc1422' - - Datasheet: - - - http://ww1.microchip.com/downloads/en/DeviceDoc/1422.pdf - - * SMSC / Microchip EMC1423, EMC1424 - - Addresses scanned: I2C 0x4c - - Prefix: 'emc1423', 'emc1424' - - Datasheet: - - - http://ww1.microchip.com/downloads/en/DeviceDoc/1423_1424.pdf - -Author: - Kalhan Trisal - -Description ------------ - -The Standard Microsystems Corporation (SMSC) EMC2103 chips -contain up to 4 temperature sensors and a single fan controller. - -Fan rotation speeds are reported in RPM (rotations per minute). An alarm is -triggered if the rotation speed has dropped below a programmable limit. Fan -readings can be divided by a programmable divider (1, 2, 4 or 8) to give -the readings more range or accuracy. Not all RPM values can accurately be -represented, so some rounding is done. With a divider of 1, the lowest -representable value is 480 RPM. - -This driver supports RPM based control, to use this a fan target -should be written to fan1_target and pwm1_enable should be set to 3. - -The 2103-2 and 2103-4 variants have a third temperature sensor, which can -be connected to two anti-parallel diodes. These values can be read -as temp3 and temp4. If only one diode is attached to this channel, temp4 -will show as "fault". The module parameter "apd=0" can be used to suppress -this 4th channel when anti-parallel diodes are not fitted. diff --git a/Documentation/hwmon/emc2103.rst b/Documentation/hwmon/emc2103.rst new file mode 100644 index 000000000000..6a6ca6d1b34e --- /dev/null +++ b/Documentation/hwmon/emc2103.rst @@ -0,0 +1,37 @@ +Kernel driver emc2103 +====================== + +Supported chips: + + * SMSC EMC2103 + + Addresses scanned: I2C 0x2e + + Prefix: 'emc2103' + + Datasheet: Not public + +Authors: + Steve Glendinning + +Description +----------- + +The Standard Microsystems Corporation (SMSC) EMC2103 chips +contain up to 4 temperature sensors and a single fan controller. + +Fan rotation speeds are reported in RPM (rotations per minute). An alarm is +triggered if the rotation speed has dropped below a programmable limit. Fan +readings can be divided by a programmable divider (1, 2, 4 or 8) to give +the readings more range or accuracy. Not all RPM values can accurately be +represented, so some rounding is done. With a divider of 1, the lowest +representable value is 480 RPM. + +This driver supports RPM based control, to use this a fan target +should be written to fan1_target and pwm1_enable should be set to 3. + +The 2103-2 and 2103-4 variants have a third temperature sensor, which can +be connected to two anti-parallel diodes. These values can be read +as temp3 and temp4. If only one diode is attached to this channel, temp4 +will show as "fault". The module parameter "apd=0" can be used to suppress +this 4th channel when anti-parallel diodes are not fitted. diff --git a/Documentation/hwmon/emc6w201 b/Documentation/hwmon/emc6w201 deleted file mode 100644 index a8e1185b9bb6..000000000000 --- a/Documentation/hwmon/emc6w201 +++ /dev/null @@ -1,47 +0,0 @@ -Kernel driver emc6w201 -====================== - -Supported chips: - - * SMSC EMC6W201 - - Prefix: 'emc6w201' - - Addresses scanned: I2C 0x2c, 0x2d, 0x2e - - Datasheet: Not public - -Author: Jean Delvare - - -Description ------------ - -From the datasheet: - -"The EMC6W201 is an environmental monitoring device with automatic fan -control capability and enhanced system acoustics for noise suppression. -This ACPI compliant device provides hardware monitoring for up to six -voltages (including its own VCC) and five external thermal sensors, -measures the speed of up to five fans, and controls the speed of -multiple DC fans using three Pulse Width Modulator (PWM) outputs. Note -that it is possible to control more than three fans by connecting two -fans to one PWM output. The EMC6W201 will be available in a 36-pin -QFN package." - -The device is functionally close to the EMC6D100 series, but is -register-incompatible. - -The driver currently only supports the monitoring of the voltages, -temperatures and fan speeds. Limits can be changed. Alarms are not -supported, and neither is fan speed control. - - -Known Systems With EMC6W201 ---------------------------- - -The EMC6W201 is a rare device, only found on a few systems, made in -2005 and 2006. Known systems with this device: - -* Dell Precision 670 workstation -* Gigabyte 2CEWH mainboard diff --git a/Documentation/hwmon/emc6w201.rst b/Documentation/hwmon/emc6w201.rst new file mode 100644 index 000000000000..a8e1185b9bb6 --- /dev/null +++ b/Documentation/hwmon/emc6w201.rst @@ -0,0 +1,47 @@ +Kernel driver emc6w201 +====================== + +Supported chips: + + * SMSC EMC6W201 + + Prefix: 'emc6w201' + + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + + Datasheet: Not public + +Author: Jean Delvare + + +Description +----------- + +From the datasheet: + +"The EMC6W201 is an environmental monitoring device with automatic fan +control capability and enhanced system acoustics for noise suppression. +This ACPI compliant device provides hardware monitoring for up to six +voltages (including its own VCC) and five external thermal sensors, +measures the speed of up to five fans, and controls the speed of +multiple DC fans using three Pulse Width Modulator (PWM) outputs. Note +that it is possible to control more than three fans by connecting two +fans to one PWM output. The EMC6W201 will be available in a 36-pin +QFN package." + +The device is functionally close to the EMC6D100 series, but is +register-incompatible. + +The driver currently only supports the monitoring of the voltages, +temperatures and fan speeds. Limits can be changed. Alarms are not +supported, and neither is fan speed control. + + +Known Systems With EMC6W201 +--------------------------- + +The EMC6W201 is a rare device, only found on a few systems, made in +2005 and 2006. Known systems with this device: + +* Dell Precision 670 workstation +* Gigabyte 2CEWH mainboard diff --git a/Documentation/hwmon/f71805f b/Documentation/hwmon/f71805f deleted file mode 100644 index 1efe5e5d337c..000000000000 --- a/Documentation/hwmon/f71805f +++ /dev/null @@ -1,181 +0,0 @@ -Kernel driver f71805f -===================== - -Supported chips: - - * Fintek F71805F/FG - - Prefix: 'f71805f' - - Addresses scanned: none, address read from Super I/O config space - - Datasheet: Available from the Fintek website - - * Fintek F71806F/FG - - Prefix: 'f71872f' - - Addresses scanned: none, address read from Super I/O config space - - Datasheet: Available from the Fintek website - - * Fintek F71872F/FG - - Prefix: 'f71872f' - - Addresses scanned: none, address read from Super I/O config space - - Datasheet: Available from the Fintek website - -Author: Jean Delvare - -Thanks to Denis Kieft from Barracuda Networks for the donation of a -test system (custom Jetway K8M8MS motherboard, with CPU and RAM) and -for providing initial documentation. - -Thanks to Kris Chen and Aaron Huang from Fintek for answering technical -questions and providing additional documentation. - -Thanks to Chris Lin from Jetway for providing wiring schematics and -answering technical questions. - - -Description ------------ - -The Fintek F71805F/FG Super I/O chip includes complete hardware monitoring -capabilities. It can monitor up to 9 voltages (counting its own power -source), 3 fans and 3 temperature sensors. - -This chip also has fan controlling features, using either DC or PWM, in -three different modes (one manual, two automatic). - -The Fintek F71872F/FG Super I/O chip is almost the same, with two -additional internal voltages monitored (VSB and battery). It also features -6 VID inputs. The VID inputs are not yet supported by this driver. - -The Fintek F71806F/FG Super-I/O chip is essentially the same as the -F71872F/FG, and is undistinguishable therefrom. - -The driver assumes that no more than one chip is present, which seems -reasonable. - - -Voltage Monitoring ------------------- - -Voltages are sampled by an 8-bit ADC with a LSB of 8 mV. The supported -range is thus from 0 to 2.040 V. Voltage values outside of this range -need external resistors. An exception is in0, which is used to monitor -the chip's own power source (+3.3V), and is divided internally by a -factor 2. For the F71872F/FG, in9 (VSB) and in10 (battery) are also -divided internally by a factor 2. - -The two LSB of the voltage limit registers are not used (always 0), so -you can only set the limits in steps of 32 mV (before scaling). - -The wirings and resistor values suggested by Fintek are as follow: - -======= ======= =========== ==== ======= ============ ============== -in pin expected - name use R1 R2 divider raw val. -======= ======= =========== ==== ======= ============ ============== -in0 VCC VCC3.3V int. int. 2.00 1.65 V -in1 VIN1 VTT1.2V 10K - 1.00 1.20 V -in2 VIN2 VRAM 100K 100K 2.00 ~1.25 V [1]_ -in3 VIN3 VCHIPSET 47K 100K 1.47 2.24 V [2]_ -in4 VIN4 VCC5V 200K 47K 5.25 0.95 V -in5 VIN5 +12V 200K 20K 11.00 1.05 V -in6 VIN6 VCC1.5V 10K - 1.00 1.50 V -in7 VIN7 VCORE 10K - 1.00 ~1.40 V [1]_ -in8 VIN8 VSB5V 200K 47K 1.00 0.95 V -in10 VSB VSB3.3V int. int. 2.00 1.65 V [3]_ -in9 VBAT VBATTERY int. int. 2.00 1.50 V [3]_ -======= ======= =========== ==== ======= ============ ============== - -.. [1] Depends on your hardware setup. -.. [2] Obviously not correct, swapping R1 and R2 would make more sense. -.. [3] F71872F/FG only. - -These values can be used as hints at best, as motherboard manufacturers -are free to use a completely different setup. As a matter of fact, the -Jetway K8M8MS uses a significantly different setup. You will have to -find out documentation about your own motherboard, and edit sensors.conf -accordingly. - -Each voltage measured has associated low and high limits, each of which -triggers an alarm when crossed. - - -Fan Monitoring --------------- - -Fan rotation speeds are reported as 12-bit values from a gated clock -signal. Speeds down to 366 RPM can be measured. There is no theoretical -high limit, but values over 6000 RPM seem to cause problem. The effective -resolution is much lower than you would expect, the step between different -register values being 10 rather than 1. - -The chip assumes 2 pulse-per-revolution fans. - -An alarm is triggered if the rotation speed drops below a programmable -limit or is too low to be measured. - - -Temperature Monitoring ----------------------- - -Temperatures are reported in degrees Celsius. Each temperature measured -has a high limit, those crossing triggers an alarm. There is an associated -hysteresis value, below which the temperature has to drop before the -alarm is cleared. - -All temperature channels are external, there is no embedded temperature -sensor. Each channel can be used for connecting either a thermal diode -or a thermistor. The driver reports the currently selected mode, but -doesn't allow changing it. In theory, the BIOS should have configured -everything properly. - - -Fan Control ------------ - -Both PWM (pulse-width modulation) and DC fan speed control methods are -supported. The right one to use depends on external circuitry on the -motherboard, so the driver assumes that the BIOS set the method -properly. The driver will report the method, but won't let you change -it. - -When the PWM method is used, you can select the operating frequency, -from 187.5 kHz (default) to 31 Hz. The best frequency depends on the -fan model. As a rule of thumb, lower frequencies seem to give better -control, but may generate annoying high-pitch noise. So a frequency just -above the audible range, such as 25 kHz, may be a good choice; if this -doesn't give you good linear control, try reducing it. Fintek recommends -not going below 1 kHz, as the fan tachometers get confused by lower -frequencies as well. - -When the DC method is used, Fintek recommends not going below 5 V, which -corresponds to a pwm value of 106 for the driver. The driver doesn't -enforce this limit though. - -Three different fan control modes are supported; the mode number is written -to the pwm_enable file. - -* 1: Manual mode - You ask for a specific PWM duty cycle or DC voltage by writing to the - pwm file. - -* 2: Temperature mode - You define 3 temperature/fan speed trip points using the - pwm_auto_point_temp and _fan files. These define a staircase - relationship between temperature and fan speed with two additional points - interpolated between the values that you define. When the temperature - is below auto_point1_temp the fan is switched off. - -* 3: Fan speed mode - You ask for a specific fan speed by writing to the fan_target file. - -Both of the automatic modes require that pwm1 corresponds to fan1, pwm2 to -fan2 and pwm3 to fan3. Temperature mode also requires that temp1 corresponds -to pwm1 and fan1, etc. diff --git a/Documentation/hwmon/f71805f.rst b/Documentation/hwmon/f71805f.rst new file mode 100644 index 000000000000..1efe5e5d337c --- /dev/null +++ b/Documentation/hwmon/f71805f.rst @@ -0,0 +1,181 @@ +Kernel driver f71805f +===================== + +Supported chips: + + * Fintek F71805F/FG + + Prefix: 'f71805f' + + Addresses scanned: none, address read from Super I/O config space + + Datasheet: Available from the Fintek website + + * Fintek F71806F/FG + + Prefix: 'f71872f' + + Addresses scanned: none, address read from Super I/O config space + + Datasheet: Available from the Fintek website + + * Fintek F71872F/FG + + Prefix: 'f71872f' + + Addresses scanned: none, address read from Super I/O config space + + Datasheet: Available from the Fintek website + +Author: Jean Delvare + +Thanks to Denis Kieft from Barracuda Networks for the donation of a +test system (custom Jetway K8M8MS motherboard, with CPU and RAM) and +for providing initial documentation. + +Thanks to Kris Chen and Aaron Huang from Fintek for answering technical +questions and providing additional documentation. + +Thanks to Chris Lin from Jetway for providing wiring schematics and +answering technical questions. + + +Description +----------- + +The Fintek F71805F/FG Super I/O chip includes complete hardware monitoring +capabilities. It can monitor up to 9 voltages (counting its own power +source), 3 fans and 3 temperature sensors. + +This chip also has fan controlling features, using either DC or PWM, in +three different modes (one manual, two automatic). + +The Fintek F71872F/FG Super I/O chip is almost the same, with two +additional internal voltages monitored (VSB and battery). It also features +6 VID inputs. The VID inputs are not yet supported by this driver. + +The Fintek F71806F/FG Super-I/O chip is essentially the same as the +F71872F/FG, and is undistinguishable therefrom. + +The driver assumes that no more than one chip is present, which seems +reasonable. + + +Voltage Monitoring +------------------ + +Voltages are sampled by an 8-bit ADC with a LSB of 8 mV. The supported +range is thus from 0 to 2.040 V. Voltage values outside of this range +need external resistors. An exception is in0, which is used to monitor +the chip's own power source (+3.3V), and is divided internally by a +factor 2. For the F71872F/FG, in9 (VSB) and in10 (battery) are also +divided internally by a factor 2. + +The two LSB of the voltage limit registers are not used (always 0), so +you can only set the limits in steps of 32 mV (before scaling). + +The wirings and resistor values suggested by Fintek are as follow: + +======= ======= =========== ==== ======= ============ ============== +in pin expected + name use R1 R2 divider raw val. +======= ======= =========== ==== ======= ============ ============== +in0 VCC VCC3.3V int. int. 2.00 1.65 V +in1 VIN1 VTT1.2V 10K - 1.00 1.20 V +in2 VIN2 VRAM 100K 100K 2.00 ~1.25 V [1]_ +in3 VIN3 VCHIPSET 47K 100K 1.47 2.24 V [2]_ +in4 VIN4 VCC5V 200K 47K 5.25 0.95 V +in5 VIN5 +12V 200K 20K 11.00 1.05 V +in6 VIN6 VCC1.5V 10K - 1.00 1.50 V +in7 VIN7 VCORE 10K - 1.00 ~1.40 V [1]_ +in8 VIN8 VSB5V 200K 47K 1.00 0.95 V +in10 VSB VSB3.3V int. int. 2.00 1.65 V [3]_ +in9 VBAT VBATTERY int. int. 2.00 1.50 V [3]_ +======= ======= =========== ==== ======= ============ ============== + +.. [1] Depends on your hardware setup. +.. [2] Obviously not correct, swapping R1 and R2 would make more sense. +.. [3] F71872F/FG only. + +These values can be used as hints at best, as motherboard manufacturers +are free to use a completely different setup. As a matter of fact, the +Jetway K8M8MS uses a significantly different setup. You will have to +find out documentation about your own motherboard, and edit sensors.conf +accordingly. + +Each voltage measured has associated low and high limits, each of which +triggers an alarm when crossed. + + +Fan Monitoring +-------------- + +Fan rotation speeds are reported as 12-bit values from a gated clock +signal. Speeds down to 366 RPM can be measured. There is no theoretical +high limit, but values over 6000 RPM seem to cause problem. The effective +resolution is much lower than you would expect, the step between different +register values being 10 rather than 1. + +The chip assumes 2 pulse-per-revolution fans. + +An alarm is triggered if the rotation speed drops below a programmable +limit or is too low to be measured. + + +Temperature Monitoring +---------------------- + +Temperatures are reported in degrees Celsius. Each temperature measured +has a high limit, those crossing triggers an alarm. There is an associated +hysteresis value, below which the temperature has to drop before the +alarm is cleared. + +All temperature channels are external, there is no embedded temperature +sensor. Each channel can be used for connecting either a thermal diode +or a thermistor. The driver reports the currently selected mode, but +doesn't allow changing it. In theory, the BIOS should have configured +everything properly. + + +Fan Control +----------- + +Both PWM (pulse-width modulation) and DC fan speed control methods are +supported. The right one to use depends on external circuitry on the +motherboard, so the driver assumes that the BIOS set the method +properly. The driver will report the method, but won't let you change +it. + +When the PWM method is used, you can select the operating frequency, +from 187.5 kHz (default) to 31 Hz. The best frequency depends on the +fan model. As a rule of thumb, lower frequencies seem to give better +control, but may generate annoying high-pitch noise. So a frequency just +above the audible range, such as 25 kHz, may be a good choice; if this +doesn't give you good linear control, try reducing it. Fintek recommends +not going below 1 kHz, as the fan tachometers get confused by lower +frequencies as well. + +When the DC method is used, Fintek recommends not going below 5 V, which +corresponds to a pwm value of 106 for the driver. The driver doesn't +enforce this limit though. + +Three different fan control modes are supported; the mode number is written +to the pwm_enable file. + +* 1: Manual mode + You ask for a specific PWM duty cycle or DC voltage by writing to the + pwm file. + +* 2: Temperature mode + You define 3 temperature/fan speed trip points using the + pwm_auto_point_temp and _fan files. These define a staircase + relationship between temperature and fan speed with two additional points + interpolated between the values that you define. When the temperature + is below auto_point1_temp the fan is switched off. + +* 3: Fan speed mode + You ask for a specific fan speed by writing to the fan_target file. + +Both of the automatic modes require that pwm1 corresponds to fan1, pwm2 to +fan2 and pwm3 to fan3. Temperature mode also requires that temp1 corresponds +to pwm1 and fan1, etc. diff --git a/Documentation/hwmon/f71882fg b/Documentation/hwmon/f71882fg deleted file mode 100644 index 5c0b7b0db150..000000000000 --- a/Documentation/hwmon/f71882fg +++ /dev/null @@ -1,192 +0,0 @@ -Kernel driver f71882fg -====================== - -Supported chips: - - * Fintek F71808E - - Prefix: 'f71808e' - - Addresses scanned: none, address read from Super I/O config space - - Datasheet: Not public - - * Fintek F71808A - - Prefix: 'f71808a' - - Addresses scanned: none, address read from Super I/O config space - - Datasheet: Not public - - * Fintek F71858FG - - Prefix: 'f71858fg' - - Addresses scanned: none, address read from Super I/O config space - - Datasheet: Available from the Fintek website - - * Fintek F71862FG and F71863FG - - Prefix: 'f71862fg' - - Addresses scanned: none, address read from Super I/O config space - - Datasheet: Available from the Fintek website - - * Fintek F71869F and F71869E - - Prefix: 'f71869' - - Addresses scanned: none, address read from Super I/O config space - - Datasheet: Available from the Fintek website - - * Fintek F71869A - - Prefix: 'f71869a' - - Addresses scanned: none, address read from Super I/O config space - - Datasheet: Not public - - * Fintek F71882FG and F71883FG - - Prefix: 'f71882fg' - - Addresses scanned: none, address read from Super I/O config space - - Datasheet: Available from the Fintek website - - * Fintek F71889FG - - Prefix: 'f71889fg' - - Addresses scanned: none, address read from Super I/O config space - - Datasheet: Available from the Fintek website - - * Fintek F71889ED - - Prefix: 'f71889ed' - - Addresses scanned: none, address read from Super I/O config space - - Datasheet: Should become available on the Fintek website soon - - * Fintek F71889A - - Prefix: 'f71889a' - - Addresses scanned: none, address read from Super I/O config space - - Datasheet: Should become available on the Fintek website soon - - * Fintek F8000 - - Prefix: 'f8000' - - Addresses scanned: none, address read from Super I/O config space - - Datasheet: Not public - - * Fintek F81801U - - Prefix: 'f71889fg' - - Addresses scanned: none, address read from Super I/O config space - - Datasheet: Not public - - Note: - This is the 64-pin variant of the F71889FG, they have the - same device ID and are fully compatible as far as hardware - monitoring is concerned. - - * Fintek F81865F - - Prefix: 'f81865f' - - Addresses scanned: none, address read from Super I/O config space - - Datasheet: Available from the Fintek website - -Author: Hans de Goede - - -Description ------------ - -Fintek F718xx/F8000 Super I/O chips include complete hardware monitoring -capabilities. They can monitor up to 9 voltages, 4 fans and 3 temperature -sensors. - -These chips also have fan controlling features, using either DC or PWM, in -three different modes (one manual, two automatic). - -The driver assumes that no more than one chip is present, which seems -reasonable. - - -Monitoring ----------- - -The Voltage, Fan and Temperature Monitoring uses the standard sysfs -interface as documented in sysfs-interface, without any exceptions. - - -Fan Control ------------ - -Both PWM (pulse-width modulation) and DC fan speed control methods are -supported. The right one to use depends on external circuitry on the -motherboard, so the driver assumes that the BIOS set the method -properly. - -Note that the lowest numbered temperature zone trip point corresponds to -to the border between the highest and one but highest temperature zones, and -vica versa. So the temperature zone trip points 1-4 (or 1-2) go from high temp -to low temp! This is how things are implemented in the IC, and the driver -mimics this. - -There are 2 modes to specify the speed of the fan, PWM duty cycle (or DC -voltage) mode, where 0-100% duty cycle (0-100% of 12V) is specified. And RPM -mode where the actual RPM of the fan (as measured) is controlled and the speed -gets specified as 0-100% of the fan#_full_speed file. - -Since both modes work in a 0-100% (mapped to 0-255) scale, there isn't a -whole lot of a difference when modifying fan control settings. The only -important difference is that in RPM mode the 0-100% controls the fan speed -between 0-100% of fan#_full_speed. It is assumed that if the BIOS programs -RPM mode, it will also set fan#_full_speed properly, if it does not then -fan control will not work properly, unless you set a sane fan#_full_speed -value yourself. - -Switching between these modes requires re-initializing a whole bunch of -registers, so the mode which the BIOS has set is kept. The mode is -printed when loading the driver. - -Three different fan control modes are supported; the mode number is written -to the pwm#_enable file. Note that not all modes are supported on all -chips, and some modes may only be available in RPM / PWM mode. -Writing an unsupported mode will result in an invalid parameter error. - -* 1: Manual mode - You ask for a specific PWM duty cycle / DC voltage or a specific % of - fan#_full_speed by writing to the pwm# file. This mode is only - available on the F71858FG / F8000 if the fan channel is in RPM mode. - -* 2: Normal auto mode - You can define a number of temperature/fan speed trip points, which % the - fan should run at at this temp and which temp a fan should follow using the - standard sysfs interface. The number and type of trip points is chip - depended, see which files are available in sysfs. - Fan/PWM channel 3 of the F8000 is always in this mode! - -* 3: Thermostat mode (Only available on the F8000 when in duty cycle mode) - The fan speed is regulated to keep the temp the fan is mapped to between - temp#_auto_point2_temp and temp#_auto_point3_temp. - -All of the automatic modes require that pwm1 corresponds to fan1, pwm2 to -fan2 and pwm3 to fan3. diff --git a/Documentation/hwmon/f71882fg.rst b/Documentation/hwmon/f71882fg.rst new file mode 100644 index 000000000000..5c0b7b0db150 --- /dev/null +++ b/Documentation/hwmon/f71882fg.rst @@ -0,0 +1,192 @@ +Kernel driver f71882fg +====================== + +Supported chips: + + * Fintek F71808E + + Prefix: 'f71808e' + + Addresses scanned: none, address read from Super I/O config space + + Datasheet: Not public + + * Fintek F71808A + + Prefix: 'f71808a' + + Addresses scanned: none, address read from Super I/O config space + + Datasheet: Not public + + * Fintek F71858FG + + Prefix: 'f71858fg' + + Addresses scanned: none, address read from Super I/O config space + + Datasheet: Available from the Fintek website + + * Fintek F71862FG and F71863FG + + Prefix: 'f71862fg' + + Addresses scanned: none, address read from Super I/O config space + + Datasheet: Available from the Fintek website + + * Fintek F71869F and F71869E + + Prefix: 'f71869' + + Addresses scanned: none, address read from Super I/O config space + + Datasheet: Available from the Fintek website + + * Fintek F71869A + + Prefix: 'f71869a' + + Addresses scanned: none, address read from Super I/O config space + + Datasheet: Not public + + * Fintek F71882FG and F71883FG + + Prefix: 'f71882fg' + + Addresses scanned: none, address read from Super I/O config space + + Datasheet: Available from the Fintek website + + * Fintek F71889FG + + Prefix: 'f71889fg' + + Addresses scanned: none, address read from Super I/O config space + + Datasheet: Available from the Fintek website + + * Fintek F71889ED + + Prefix: 'f71889ed' + + Addresses scanned: none, address read from Super I/O config space + + Datasheet: Should become available on the Fintek website soon + + * Fintek F71889A + + Prefix: 'f71889a' + + Addresses scanned: none, address read from Super I/O config space + + Datasheet: Should become available on the Fintek website soon + + * Fintek F8000 + + Prefix: 'f8000' + + Addresses scanned: none, address read from Super I/O config space + + Datasheet: Not public + + * Fintek F81801U + + Prefix: 'f71889fg' + + Addresses scanned: none, address read from Super I/O config space + + Datasheet: Not public + + Note: + This is the 64-pin variant of the F71889FG, they have the + same device ID and are fully compatible as far as hardware + monitoring is concerned. + + * Fintek F81865F + + Prefix: 'f81865f' + + Addresses scanned: none, address read from Super I/O config space + + Datasheet: Available from the Fintek website + +Author: Hans de Goede + + +Description +----------- + +Fintek F718xx/F8000 Super I/O chips include complete hardware monitoring +capabilities. They can monitor up to 9 voltages, 4 fans and 3 temperature +sensors. + +These chips also have fan controlling features, using either DC or PWM, in +three different modes (one manual, two automatic). + +The driver assumes that no more than one chip is present, which seems +reasonable. + + +Monitoring +---------- + +The Voltage, Fan and Temperature Monitoring uses the standard sysfs +interface as documented in sysfs-interface, without any exceptions. + + +Fan Control +----------- + +Both PWM (pulse-width modulation) and DC fan speed control methods are +supported. The right one to use depends on external circuitry on the +motherboard, so the driver assumes that the BIOS set the method +properly. + +Note that the lowest numbered temperature zone trip point corresponds to +to the border between the highest and one but highest temperature zones, and +vica versa. So the temperature zone trip points 1-4 (or 1-2) go from high temp +to low temp! This is how things are implemented in the IC, and the driver +mimics this. + +There are 2 modes to specify the speed of the fan, PWM duty cycle (or DC +voltage) mode, where 0-100% duty cycle (0-100% of 12V) is specified. And RPM +mode where the actual RPM of the fan (as measured) is controlled and the speed +gets specified as 0-100% of the fan#_full_speed file. + +Since both modes work in a 0-100% (mapped to 0-255) scale, there isn't a +whole lot of a difference when modifying fan control settings. The only +important difference is that in RPM mode the 0-100% controls the fan speed +between 0-100% of fan#_full_speed. It is assumed that if the BIOS programs +RPM mode, it will also set fan#_full_speed properly, if it does not then +fan control will not work properly, unless you set a sane fan#_full_speed +value yourself. + +Switching between these modes requires re-initializing a whole bunch of +registers, so the mode which the BIOS has set is kept. The mode is +printed when loading the driver. + +Three different fan control modes are supported; the mode number is written +to the pwm#_enable file. Note that not all modes are supported on all +chips, and some modes may only be available in RPM / PWM mode. +Writing an unsupported mode will result in an invalid parameter error. + +* 1: Manual mode + You ask for a specific PWM duty cycle / DC voltage or a specific % of + fan#_full_speed by writing to the pwm# file. This mode is only + available on the F71858FG / F8000 if the fan channel is in RPM mode. + +* 2: Normal auto mode + You can define a number of temperature/fan speed trip points, which % the + fan should run at at this temp and which temp a fan should follow using the + standard sysfs interface. The number and type of trip points is chip + depended, see which files are available in sysfs. + Fan/PWM channel 3 of the F8000 is always in this mode! + +* 3: Thermostat mode (Only available on the F8000 when in duty cycle mode) + The fan speed is regulated to keep the temp the fan is mapped to between + temp#_auto_point2_temp and temp#_auto_point3_temp. + +All of the automatic modes require that pwm1 corresponds to fan1, pwm2 to +fan2 and pwm3 to fan3. diff --git a/Documentation/hwmon/fam15h_power b/Documentation/hwmon/fam15h_power deleted file mode 100644 index fdde632c93a3..000000000000 --- a/Documentation/hwmon/fam15h_power +++ /dev/null @@ -1,131 +0,0 @@ -Kernel driver fam15h_power -========================== - -Supported chips: - -* AMD Family 15h Processors - -* AMD Family 16h Processors - - Prefix: 'fam15h_power' - - Addresses scanned: PCI space - - Datasheets: - - - BIOS and Kernel Developer's Guide (BKDG) For AMD Family 15h Processors - - BIOS and Kernel Developer's Guide (BKDG) For AMD Family 16h Processors - - AMD64 Architecture Programmer's Manual Volume 2: System Programming - -Author: Andreas Herrmann - -Description ------------ - -1) Processor TDP (Thermal design power) - -Given a fixed frequency and voltage, the power consumption of a -processor varies based on the workload being executed. Derated power -is the power consumed when running a specific application. Thermal -design power (TDP) is an example of derated power. - -This driver permits reading of registers providing power information -of AMD Family 15h and 16h processors via TDP algorithm. - -For AMD Family 15h and 16h processors the following power values can -be calculated using different processor northbridge function -registers: - -* BasePwrWatts: - Specifies in watts the maximum amount of power - consumed by the processor for NB and logic external to the core. - -* ProcessorPwrWatts: - Specifies in watts the maximum amount of power - the processor can support. -* CurrPwrWatts: - Specifies in watts the current amount of power being - consumed by the processor. - -This driver provides ProcessorPwrWatts and CurrPwrWatts: - -* power1_crit (ProcessorPwrWatts) -* power1_input (CurrPwrWatts) - -On multi-node processors the calculated value is for the entire -package and not for a single node. Thus the driver creates sysfs -attributes only for internal node0 of a multi-node processor. - -2) Accumulated Power Mechanism - -This driver also introduces an algorithm that should be used to -calculate the average power consumed by a processor during a -measurement interval Tm. The feature of accumulated power mechanism is -indicated by CPUID Fn8000_0007_EDX[12]. - -* Tsample: - compute unit power accumulator sample period - -* Tref: - the PTSC counter period - -* PTSC: - performance timestamp counter - -* N: - the ratio of compute unit power accumulator sample period to the - PTSC period - -* Jmax: - max compute unit accumulated power which is indicated by - MaxCpuSwPwrAcc MSR C001007b - -* Jx/Jy: - compute unit accumulated power which is indicated by - CpuSwPwrAcc MSR C001007a -* Tx/Ty: - the value of performance timestamp counter which is indicated - by CU_PTSC MSR C0010280 - -* PwrCPUave: - CPU average power - -i. Determine the ratio of Tsample to Tref by executing CPUID Fn8000_0007. - - N = value of CPUID Fn8000_0007_ECX[CpuPwrSampleTimeRatio[15:0]]. - -ii. Read the full range of the cumulative energy value from the new - MSR MaxCpuSwPwrAcc. - - Jmax = value returned. - -iii. At time x, SW reads CpuSwPwrAcc MSR and samples the PTSC. - - Jx = value read from CpuSwPwrAcc and Tx = value read from PTSC. - -iv. At time y, SW reads CpuSwPwrAcc MSR and samples the PTSC. - - Jy = value read from CpuSwPwrAcc and Ty = value read from PTSC. - -v. Calculate the average power consumption for a compute unit over - time period (y-x). Unit of result is uWatt:: - - if (Jy < Jx) // Rollover has occurred - Jdelta = (Jy + Jmax) - Jx - else - Jdelta = Jy - Jx - PwrCPUave = N * Jdelta * 1000 / (Ty - Tx) - -This driver provides PwrCPUave and interval(default is 10 millisecond -and maximum is 1 second): - -* power1_average (PwrCPUave) -* power1_average_interval (Interval) - -The power1_average_interval can be updated at /etc/sensors3.conf file -as below: - -chip `fam15h_power-*` - set power1_average_interval 0.01 - -Then save it with "sensors -s". diff --git a/Documentation/hwmon/fam15h_power.rst b/Documentation/hwmon/fam15h_power.rst new file mode 100644 index 000000000000..fdde632c93a3 --- /dev/null +++ b/Documentation/hwmon/fam15h_power.rst @@ -0,0 +1,131 @@ +Kernel driver fam15h_power +========================== + +Supported chips: + +* AMD Family 15h Processors + +* AMD Family 16h Processors + + Prefix: 'fam15h_power' + + Addresses scanned: PCI space + + Datasheets: + + - BIOS and Kernel Developer's Guide (BKDG) For AMD Family 15h Processors + - BIOS and Kernel Developer's Guide (BKDG) For AMD Family 16h Processors + - AMD64 Architecture Programmer's Manual Volume 2: System Programming + +Author: Andreas Herrmann + +Description +----------- + +1) Processor TDP (Thermal design power) + +Given a fixed frequency and voltage, the power consumption of a +processor varies based on the workload being executed. Derated power +is the power consumed when running a specific application. Thermal +design power (TDP) is an example of derated power. + +This driver permits reading of registers providing power information +of AMD Family 15h and 16h processors via TDP algorithm. + +For AMD Family 15h and 16h processors the following power values can +be calculated using different processor northbridge function +registers: + +* BasePwrWatts: + Specifies in watts the maximum amount of power + consumed by the processor for NB and logic external to the core. + +* ProcessorPwrWatts: + Specifies in watts the maximum amount of power + the processor can support. +* CurrPwrWatts: + Specifies in watts the current amount of power being + consumed by the processor. + +This driver provides ProcessorPwrWatts and CurrPwrWatts: + +* power1_crit (ProcessorPwrWatts) +* power1_input (CurrPwrWatts) + +On multi-node processors the calculated value is for the entire +package and not for a single node. Thus the driver creates sysfs +attributes only for internal node0 of a multi-node processor. + +2) Accumulated Power Mechanism + +This driver also introduces an algorithm that should be used to +calculate the average power consumed by a processor during a +measurement interval Tm. The feature of accumulated power mechanism is +indicated by CPUID Fn8000_0007_EDX[12]. + +* Tsample: + compute unit power accumulator sample period + +* Tref: + the PTSC counter period + +* PTSC: + performance timestamp counter + +* N: + the ratio of compute unit power accumulator sample period to the + PTSC period + +* Jmax: + max compute unit accumulated power which is indicated by + MaxCpuSwPwrAcc MSR C001007b + +* Jx/Jy: + compute unit accumulated power which is indicated by + CpuSwPwrAcc MSR C001007a +* Tx/Ty: + the value of performance timestamp counter which is indicated + by CU_PTSC MSR C0010280 + +* PwrCPUave: + CPU average power + +i. Determine the ratio of Tsample to Tref by executing CPUID Fn8000_0007. + + N = value of CPUID Fn8000_0007_ECX[CpuPwrSampleTimeRatio[15:0]]. + +ii. Read the full range of the cumulative energy value from the new + MSR MaxCpuSwPwrAcc. + + Jmax = value returned. + +iii. At time x, SW reads CpuSwPwrAcc MSR and samples the PTSC. + + Jx = value read from CpuSwPwrAcc and Tx = value read from PTSC. + +iv. At time y, SW reads CpuSwPwrAcc MSR and samples the PTSC. + + Jy = value read from CpuSwPwrAcc and Ty = value read from PTSC. + +v. Calculate the average power consumption for a compute unit over + time period (y-x). Unit of result is uWatt:: + + if (Jy < Jx) // Rollover has occurred + Jdelta = (Jy + Jmax) - Jx + else + Jdelta = Jy - Jx + PwrCPUave = N * Jdelta * 1000 / (Ty - Tx) + +This driver provides PwrCPUave and interval(default is 10 millisecond +and maximum is 1 second): + +* power1_average (PwrCPUave) +* power1_average_interval (Interval) + +The power1_average_interval can be updated at /etc/sensors3.conf file +as below: + +chip `fam15h_power-*` + set power1_average_interval 0.01 + +Then save it with "sensors -s". diff --git a/Documentation/hwmon/ftsteutates b/Documentation/hwmon/ftsteutates deleted file mode 100644 index 58a2483d8d0d..000000000000 --- a/Documentation/hwmon/ftsteutates +++ /dev/null @@ -1,33 +0,0 @@ -Kernel driver ftsteutates -========================= - -Supported chips: - - * FTS Teutates - - Prefix: 'ftsteutates' - - Addresses scanned: I2C 0x73 (7-Bit) - -Author: Thilo Cestonaro - - -Description ------------ - -The BMC Teutates is the Eleventh generation of Superior System -monitoring and thermal management solution. It is builds on the basic -functionality of the BMC Theseus and contains several new features and -enhancements. It can monitor up to 4 voltages, 16 temperatures and -8 fans. It also contains an integrated watchdog which is currently -implemented in this driver. - -To clear a temperature or fan alarm, execute the following command with the -correct path to the alarm file:: - - echo 0 >XXXX_alarm - -Specification of the chip can be found here: - -- ftp://ftp.ts.fujitsu.com/pub/Mainboard-OEM-Sales/Services/Software&Tools/Linux_SystemMonitoring&Watchdog&GPIO/BMC-Teutates_Specification_V1.21.pdf -- ftp://ftp.ts.fujitsu.com/pub/Mainboard-OEM-Sales/Services/Software&Tools/Linux_SystemMonitoring&Watchdog&GPIO/Fujitsu_mainboards-1-Sensors_HowTo-en-US.pdf diff --git a/Documentation/hwmon/ftsteutates.rst b/Documentation/hwmon/ftsteutates.rst new file mode 100644 index 000000000000..58a2483d8d0d --- /dev/null +++ b/Documentation/hwmon/ftsteutates.rst @@ -0,0 +1,33 @@ +Kernel driver ftsteutates +========================= + +Supported chips: + + * FTS Teutates + + Prefix: 'ftsteutates' + + Addresses scanned: I2C 0x73 (7-Bit) + +Author: Thilo Cestonaro + + +Description +----------- + +The BMC Teutates is the Eleventh generation of Superior System +monitoring and thermal management solution. It is builds on the basic +functionality of the BMC Theseus and contains several new features and +enhancements. It can monitor up to 4 voltages, 16 temperatures and +8 fans. It also contains an integrated watchdog which is currently +implemented in this driver. + +To clear a temperature or fan alarm, execute the following command with the +correct path to the alarm file:: + + echo 0 >XXXX_alarm + +Specification of the chip can be found here: + +- ftp://ftp.ts.fujitsu.com/pub/Mainboard-OEM-Sales/Services/Software&Tools/Linux_SystemMonitoring&Watchdog&GPIO/BMC-Teutates_Specification_V1.21.pdf +- ftp://ftp.ts.fujitsu.com/pub/Mainboard-OEM-Sales/Services/Software&Tools/Linux_SystemMonitoring&Watchdog&GPIO/Fujitsu_mainboards-1-Sensors_HowTo-en-US.pdf diff --git a/Documentation/hwmon/g760a b/Documentation/hwmon/g760a deleted file mode 100644 index d82952cc8319..000000000000 --- a/Documentation/hwmon/g760a +++ /dev/null @@ -1,40 +0,0 @@ -Kernel driver g760a -=================== - -Supported chips: - - * Global Mixed-mode Technology Inc. G760A - - Prefix: 'g760a' - - Datasheet: Publicly available at the GMT website - - http://www.gmt.com.tw/product/datasheet/EDS-760A.pdf - -Author: Herbert Valerio Riedel - -Description ------------ - -The GMT G760A Fan Speed PWM Controller is connected directly to a fan -and performs closed-loop control of the fan speed. - -The fan speed is programmed by setting the period via 'pwm1' of two -consecutive speed pulses. The period is defined in terms of clock -cycle counts of an assumed 32kHz clock source. - -Setting a period of 0 stops the fan; setting the period to 255 sets -fan to maximum speed. - -The measured fan rotation speed returned via 'fan1_input' is derived -from the measured speed pulse period by assuming again a 32kHz clock -source and a 2 pulse-per-revolution fan. - -The 'alarms' file provides access to the two alarm bits provided by -the G760A chip's status register: Bit 0 is set when the actual fan -speed differs more than 20% with respect to the programmed fan speed; -bit 1 is set when fan speed is below 1920 RPM. - -The g760a driver will not update its values more frequently than every -other second; reading them more often will do no harm, but will return -'old' values. diff --git a/Documentation/hwmon/g760a.rst b/Documentation/hwmon/g760a.rst new file mode 100644 index 000000000000..d82952cc8319 --- /dev/null +++ b/Documentation/hwmon/g760a.rst @@ -0,0 +1,40 @@ +Kernel driver g760a +=================== + +Supported chips: + + * Global Mixed-mode Technology Inc. G760A + + Prefix: 'g760a' + + Datasheet: Publicly available at the GMT website + + http://www.gmt.com.tw/product/datasheet/EDS-760A.pdf + +Author: Herbert Valerio Riedel + +Description +----------- + +The GMT G760A Fan Speed PWM Controller is connected directly to a fan +and performs closed-loop control of the fan speed. + +The fan speed is programmed by setting the period via 'pwm1' of two +consecutive speed pulses. The period is defined in terms of clock +cycle counts of an assumed 32kHz clock source. + +Setting a period of 0 stops the fan; setting the period to 255 sets +fan to maximum speed. + +The measured fan rotation speed returned via 'fan1_input' is derived +from the measured speed pulse period by assuming again a 32kHz clock +source and a 2 pulse-per-revolution fan. + +The 'alarms' file provides access to the two alarm bits provided by +the G760A chip's status register: Bit 0 is set when the actual fan +speed differs more than 20% with respect to the programmed fan speed; +bit 1 is set when fan speed is below 1920 RPM. + +The g760a driver will not update its values more frequently than every +other second; reading them more often will do no harm, but will return +'old' values. diff --git a/Documentation/hwmon/g762 b/Documentation/hwmon/g762 deleted file mode 100644 index 54574e26df21..000000000000 --- a/Documentation/hwmon/g762 +++ /dev/null @@ -1,74 +0,0 @@ -Kernel driver g762 -================== - -The GMT G762 Fan Speed PWM Controller is connected directly to a fan -and performs closed-loop or open-loop control of the fan speed. Two -modes - PWM or DC - are supported by the device. - -For additional information, a detailed datasheet is available at -http://natisbad.org/NAS/ref/GMT_EDS-762_763-080710-0.2.pdf. sysfs -bindings are described in Documentation/hwmon/sysfs-interface. - -The following entries are available to the user in a subdirectory of -/sys/bus/i2c/drivers/g762/ to control the operation of the device. -This can be done manually using the following entries but is usually -done via a userland daemon like fancontrol. - -Note that those entries do not provide ways to setup the specific -hardware characteristics of the system (reference clock, pulses per -fan revolution, ...); Those can be modified via devicetree bindings -documented in Documentation/devicetree/bindings/hwmon/g762.txt or -using a specific platform_data structure in board initialization -file (see include/linux/platform_data/g762.h). - - fan1_target: - set desired fan speed. This only makes sense in closed-loop - fan speed control (i.e. when pwm1_enable is set to 2). - - fan1_input: - provide current fan rotation value in RPM as reported by - the fan to the device. - - fan1_div: - fan clock divisor. Supported value are 1, 2, 4 and 8. - - fan1_pulses: - number of pulses per fan revolution. Supported values - are 2 and 4. - - fan1_fault: - reports fan failure, i.e. no transition on fan gear pin for - about 0.7s (if the fan is not voluntarily set off). - - fan1_alarm: - in closed-loop control mode, if fan RPM value is 25% out - of the programmed value for over 6 seconds 'fan1_alarm' is - set to 1. - - pwm1_enable: - set current fan speed control mode i.e. 1 for manual fan - speed control (open-loop) via pwm1 described below, 2 for - automatic fan speed control (closed-loop) via fan1_target - above. - - pwm1_mode: - set or get fan driving mode: 1 for PWM mode, 0 for DC mode. - - pwm1: - get or set PWM fan control value in open-loop mode. This is an - integer value between 0 and 255. 0 stops the fan, 255 makes - it run at full speed. - -Both in PWM mode ('pwm1_mode' set to 1) and DC mode ('pwm1_mode' set to 0), -when current fan speed control mode is open-loop ('pwm1_enable' set to 1), -the fan speed is programmed by setting a value between 0 and 255 via 'pwm1' -entry (0 stops the fan, 255 makes it run at full speed). In closed-loop mode -('pwm1_enable' set to 2), the expected rotation speed in RPM can be passed to -the chip via 'fan1_target'. In closed-loop mode, the target speed is compared -with current speed (available via 'fan1_input') by the device and a feedback -is performed to match that target value. The fan speed value is computed -based on the parameters associated with the physical characteristics of the -system: a reference clock source frequency, a number of pulses per fan -revolution, etc. - -Note that the driver will update its values at most once per second. diff --git a/Documentation/hwmon/g762.rst b/Documentation/hwmon/g762.rst new file mode 100644 index 000000000000..0371b3365c48 --- /dev/null +++ b/Documentation/hwmon/g762.rst @@ -0,0 +1,74 @@ +Kernel driver g762 +================== + +The GMT G762 Fan Speed PWM Controller is connected directly to a fan +and performs closed-loop or open-loop control of the fan speed. Two +modes - PWM or DC - are supported by the device. + +For additional information, a detailed datasheet is available at +http://natisbad.org/NAS/ref/GMT_EDS-762_763-080710-0.2.pdf. sysfs +bindings are described in Documentation/hwmon/sysfs-interface.rst. + +The following entries are available to the user in a subdirectory of +/sys/bus/i2c/drivers/g762/ to control the operation of the device. +This can be done manually using the following entries but is usually +done via a userland daemon like fancontrol. + +Note that those entries do not provide ways to setup the specific +hardware characteristics of the system (reference clock, pulses per +fan revolution, ...); Those can be modified via devicetree bindings +documented in Documentation/devicetree/bindings/hwmon/g762.txt or +using a specific platform_data structure in board initialization +file (see include/linux/platform_data/g762.h). + + fan1_target: + set desired fan speed. This only makes sense in closed-loop + fan speed control (i.e. when pwm1_enable is set to 2). + + fan1_input: + provide current fan rotation value in RPM as reported by + the fan to the device. + + fan1_div: + fan clock divisor. Supported value are 1, 2, 4 and 8. + + fan1_pulses: + number of pulses per fan revolution. Supported values + are 2 and 4. + + fan1_fault: + reports fan failure, i.e. no transition on fan gear pin for + about 0.7s (if the fan is not voluntarily set off). + + fan1_alarm: + in closed-loop control mode, if fan RPM value is 25% out + of the programmed value for over 6 seconds 'fan1_alarm' is + set to 1. + + pwm1_enable: + set current fan speed control mode i.e. 1 for manual fan + speed control (open-loop) via pwm1 described below, 2 for + automatic fan speed control (closed-loop) via fan1_target + above. + + pwm1_mode: + set or get fan driving mode: 1 for PWM mode, 0 for DC mode. + + pwm1: + get or set PWM fan control value in open-loop mode. This is an + integer value between 0 and 255. 0 stops the fan, 255 makes + it run at full speed. + +Both in PWM mode ('pwm1_mode' set to 1) and DC mode ('pwm1_mode' set to 0), +when current fan speed control mode is open-loop ('pwm1_enable' set to 1), +the fan speed is programmed by setting a value between 0 and 255 via 'pwm1' +entry (0 stops the fan, 255 makes it run at full speed). In closed-loop mode +('pwm1_enable' set to 2), the expected rotation speed in RPM can be passed to +the chip via 'fan1_target'. In closed-loop mode, the target speed is compared +with current speed (available via 'fan1_input') by the device and a feedback +is performed to match that target value. The fan speed value is computed +based on the parameters associated with the physical characteristics of the +system: a reference clock source frequency, a number of pulses per fan +revolution, etc. + +Note that the driver will update its values at most once per second. diff --git a/Documentation/hwmon/gl518sm b/Documentation/hwmon/gl518sm deleted file mode 100644 index bf1e0b5e824b..000000000000 --- a/Documentation/hwmon/gl518sm +++ /dev/null @@ -1,80 +0,0 @@ -Kernel driver gl518sm -===================== - -Supported chips: - - * Genesys Logic GL518SM release 0x00 - - Prefix: 'gl518sm' - - Addresses scanned: I2C 0x2c and 0x2d - - * Genesys Logic GL518SM release 0x80 - - Prefix: 'gl518sm' - - Addresses scanned: I2C 0x2c and 0x2d - - Datasheet: http://www.genesyslogic.com/ - -Authors: - - Frodo Looijaard , - - Kyösti Mälkki - - Hong-Gunn Chew - - Jean Delvare - -Description ------------ - -.. important:: - - For the revision 0x00 chip, the in0, in1, and in2 values (+5V, +3V, - and +12V) CANNOT be read. This is a limitation of the chip, not the driver. - -This driver supports the Genesys Logic GL518SM chip. There are at least -two revision of this chip, which we call revision 0x00 and 0x80. Revision -0x80 chips support the reading of all voltages and revision 0x00 only -for VIN3. - -The GL518SM implements one temperature sensor, two fan rotation speed -sensors, and four voltage sensors. It can report alarms through the -computer speakers. - -Temperatures are measured in degrees Celsius. An alarm goes off while the -temperature is above the over temperature limit, and has not yet dropped -below the hysteresis limit. The alarm always reflects the current -situation. Measurements are guaranteed between -10 degrees and +110 -degrees, with a accuracy of +/-3 degrees. - -Rotation speeds are reported in RPM (rotations per minute). An alarm is -triggered if the rotation speed has dropped below a programmable limit. In -case when you have selected to turn fan1 off, no fan1 alarm is triggered. - -Fan readings can be divided by a programmable divider (1, 2, 4 or 8) to -give the readings more range or accuracy. Not all RPM values can -accurately be represented, so some rounding is done. With a divider -of 2, the lowest representable value is around 1900 RPM. - -Voltage sensors (also known as VIN sensors) report their values in volts. -An alarm is triggered if the voltage has crossed a programmable minimum or -maximum limit. Note that minimum in this case always means 'closest to -zero'; this is important for negative voltage measurements. The VDD input -measures voltages between 0.000 and 5.865 volt, with a resolution of 0.023 -volt. The other inputs measure voltages between 0.000 and 4.845 volt, with -a resolution of 0.019 volt. Note that revision 0x00 chips do not support -reading the current voltage of any input except for VIN3; limit setting and -alarms work fine, though. - -When an alarm is triggered, you can be warned by a beeping signal through your -computer speaker. It is possible to enable all beeping globally, or only the -beeping for some alarms. - -If an alarm triggers, it will remain triggered until the hardware register -is read at least once (except for temperature alarms). This means that the -cause for the alarm may already have disappeared! Note that in the current -implementation, all hardware registers are read whenever any data is read -(unless it is less than 1.5 seconds since the last update). This means that -you can easily miss once-only alarms. - -The GL518SM only updates its values each 1.5 seconds; reading it more often -will do no harm, but will return 'old' values. diff --git a/Documentation/hwmon/gl518sm.rst b/Documentation/hwmon/gl518sm.rst new file mode 100644 index 000000000000..bf1e0b5e824b --- /dev/null +++ b/Documentation/hwmon/gl518sm.rst @@ -0,0 +1,80 @@ +Kernel driver gl518sm +===================== + +Supported chips: + + * Genesys Logic GL518SM release 0x00 + + Prefix: 'gl518sm' + + Addresses scanned: I2C 0x2c and 0x2d + + * Genesys Logic GL518SM release 0x80 + + Prefix: 'gl518sm' + + Addresses scanned: I2C 0x2c and 0x2d + + Datasheet: http://www.genesyslogic.com/ + +Authors: + - Frodo Looijaard , + - Kyösti Mälkki + - Hong-Gunn Chew + - Jean Delvare + +Description +----------- + +.. important:: + + For the revision 0x00 chip, the in0, in1, and in2 values (+5V, +3V, + and +12V) CANNOT be read. This is a limitation of the chip, not the driver. + +This driver supports the Genesys Logic GL518SM chip. There are at least +two revision of this chip, which we call revision 0x00 and 0x80. Revision +0x80 chips support the reading of all voltages and revision 0x00 only +for VIN3. + +The GL518SM implements one temperature sensor, two fan rotation speed +sensors, and four voltage sensors. It can report alarms through the +computer speakers. + +Temperatures are measured in degrees Celsius. An alarm goes off while the +temperature is above the over temperature limit, and has not yet dropped +below the hysteresis limit. The alarm always reflects the current +situation. Measurements are guaranteed between -10 degrees and +110 +degrees, with a accuracy of +/-3 degrees. + +Rotation speeds are reported in RPM (rotations per minute). An alarm is +triggered if the rotation speed has dropped below a programmable limit. In +case when you have selected to turn fan1 off, no fan1 alarm is triggered. + +Fan readings can be divided by a programmable divider (1, 2, 4 or 8) to +give the readings more range or accuracy. Not all RPM values can +accurately be represented, so some rounding is done. With a divider +of 2, the lowest representable value is around 1900 RPM. + +Voltage sensors (also known as VIN sensors) report their values in volts. +An alarm is triggered if the voltage has crossed a programmable minimum or +maximum limit. Note that minimum in this case always means 'closest to +zero'; this is important for negative voltage measurements. The VDD input +measures voltages between 0.000 and 5.865 volt, with a resolution of 0.023 +volt. The other inputs measure voltages between 0.000 and 4.845 volt, with +a resolution of 0.019 volt. Note that revision 0x00 chips do not support +reading the current voltage of any input except for VIN3; limit setting and +alarms work fine, though. + +When an alarm is triggered, you can be warned by a beeping signal through your +computer speaker. It is possible to enable all beeping globally, or only the +beeping for some alarms. + +If an alarm triggers, it will remain triggered until the hardware register +is read at least once (except for temperature alarms). This means that the +cause for the alarm may already have disappeared! Note that in the current +implementation, all hardware registers are read whenever any data is read +(unless it is less than 1.5 seconds since the last update). This means that +you can easily miss once-only alarms. + +The GL518SM only updates its values each 1.5 seconds; reading it more often +will do no harm, but will return 'old' values. diff --git a/Documentation/hwmon/hih6130 b/Documentation/hwmon/hih6130 deleted file mode 100644 index 649bd4be4fc2..000000000000 --- a/Documentation/hwmon/hih6130 +++ /dev/null @@ -1,45 +0,0 @@ -Kernel driver hih6130 -===================== - -Supported chips: - - * Honeywell HIH-6130 / HIH-6131 - - Prefix: 'hih6130' - - Addresses scanned: none - - Datasheet: Publicly available at the Honeywell website - - http://sensing.honeywell.com/index.php?ci_id=3106&la_id=1&defId=44872 - -Author: - Iain Paton - -Description ------------ - -The HIH-6130 & HIH-6131 are humidity and temperature sensors in a SO8 package. -The difference between the two devices is that the HIH-6131 has a condensation -filter. - -The devices communicate with the I2C protocol. All sensors are set to the same -I2C address 0x27 by default, so an entry with I2C_BOARD_INFO("hih6130", 0x27) -can be used in the board setup code. - -Please see Documentation/i2c/instantiating-devices for details on how to -instantiate I2C devices. - -sysfs-Interface ---------------- - -temp1_input - temperature input - -humidity1_input - humidity input - -Notes ------ - -Command mode and alarms are not currently supported. diff --git a/Documentation/hwmon/hih6130.rst b/Documentation/hwmon/hih6130.rst new file mode 100644 index 000000000000..649bd4be4fc2 --- /dev/null +++ b/Documentation/hwmon/hih6130.rst @@ -0,0 +1,45 @@ +Kernel driver hih6130 +===================== + +Supported chips: + + * Honeywell HIH-6130 / HIH-6131 + + Prefix: 'hih6130' + + Addresses scanned: none + + Datasheet: Publicly available at the Honeywell website + + http://sensing.honeywell.com/index.php?ci_id=3106&la_id=1&defId=44872 + +Author: + Iain Paton + +Description +----------- + +The HIH-6130 & HIH-6131 are humidity and temperature sensors in a SO8 package. +The difference between the two devices is that the HIH-6131 has a condensation +filter. + +The devices communicate with the I2C protocol. All sensors are set to the same +I2C address 0x27 by default, so an entry with I2C_BOARD_INFO("hih6130", 0x27) +can be used in the board setup code. + +Please see Documentation/i2c/instantiating-devices for details on how to +instantiate I2C devices. + +sysfs-Interface +--------------- + +temp1_input + temperature input + +humidity1_input + humidity input + +Notes +----- + +Command mode and alarms are not currently supported. diff --git a/Documentation/hwmon/hwmon-kernel-api.rst b/Documentation/hwmon/hwmon-kernel-api.rst new file mode 100644 index 000000000000..c41eb6108103 --- /dev/null +++ b/Documentation/hwmon/hwmon-kernel-api.rst @@ -0,0 +1,386 @@ +The Linux Hardware Monitoring kernel API +======================================== + +Guenter Roeck + +Introduction +------------ + +This document describes the API that can be used by hardware monitoring +drivers that want to use the hardware monitoring framework. + +This document does not describe what a hardware monitoring (hwmon) Driver or +Device is. It also does not describe the API which can be used by user space +to communicate with a hardware monitoring device. If you want to know this +then please read the following file: Documentation/hwmon/sysfs-interface.rst. + +For additional guidelines on how to write and improve hwmon drivers, please +also read Documentation/hwmon/submitting-patches.rst. + +The API +------- +Each hardware monitoring driver must #include and, in most +cases, . linux/hwmon.h declares the following +register/unregister functions:: + + struct device * + hwmon_device_register_with_groups(struct device *dev, const char *name, + void *drvdata, + const struct attribute_group **groups); + + struct device * + devm_hwmon_device_register_with_groups(struct device *dev, + const char *name, void *drvdata, + const struct attribute_group **groups); + + struct device * + hwmon_device_register_with_info(struct device *dev, + const char *name, void *drvdata, + const struct hwmon_chip_info *info, + const struct attribute_group **extra_groups); + + struct device * + devm_hwmon_device_register_with_info(struct device *dev, + const char *name, + void *drvdata, + const struct hwmon_chip_info *info, + const struct attribute_group **extra_groups); + + void hwmon_device_unregister(struct device *dev); + + void devm_hwmon_device_unregister(struct device *dev); + +hwmon_device_register_with_groups registers a hardware monitoring device. +The first parameter of this function is a pointer to the parent device. +The name parameter is a pointer to the hwmon device name. The registration +function wil create a name sysfs attribute pointing to this name. +The drvdata parameter is the pointer to the local driver data. +hwmon_device_register_with_groups will attach this pointer to the newly +allocated hwmon device. The pointer can be retrieved by the driver using +dev_get_drvdata() on the hwmon device pointer. The groups parameter is +a pointer to a list of sysfs attribute groups. The list must be NULL terminated. +hwmon_device_register_with_groups creates the hwmon device with name attribute +as well as all sysfs attributes attached to the hwmon device. +This function returns a pointer to the newly created hardware monitoring device +or PTR_ERR for failure. + +devm_hwmon_device_register_with_groups is similar to +hwmon_device_register_with_groups. However, it is device managed, meaning the +hwmon device does not have to be removed explicitly by the removal function. + +hwmon_device_register_with_info is the most comprehensive and preferred means +to register a hardware monitoring device. It creates the standard sysfs +attributes in the hardware monitoring core, letting the driver focus on reading +from and writing to the chip instead of having to bother with sysfs attributes. +The parent device parameter cannot be NULL with non-NULL chip info. Its +parameters are described in more detail below. + +devm_hwmon_device_register_with_info is similar to +hwmon_device_register_with_info. However, it is device managed, meaning the +hwmon device does not have to be removed explicitly by the removal function. + +hwmon_device_unregister deregisters a registered hardware monitoring device. +The parameter of this function is the pointer to the registered hardware +monitoring device structure. This function must be called from the driver +remove function if the hardware monitoring device was registered with +hwmon_device_register_with_groups or hwmon_device_register_with_info. + +devm_hwmon_device_unregister does not normally have to be called. It is only +needed for error handling, and only needed if the driver probe fails after +the call to devm_hwmon_device_register_with_groups or +hwmon_device_register_with_info and if the automatic (device managed) +removal would be too late. + +All supported hwmon device registration functions only accept valid device +names. Device names including invalid characters (whitespace, '*', or '-') +will be rejected. The 'name' parameter is mandatory. + +Using devm_hwmon_device_register_with_info() +-------------------------------------------- + +hwmon_device_register_with_info() registers a hardware monitoring device. +The parameters to this function are + +=============================================== =============================================== +`struct device *dev` Pointer to parent device +`const char *name` Device name +`void *drvdata` Driver private data +`const struct hwmon_chip_info *info` Pointer to chip description. +`const struct attribute_group **extra_groups` Null-terminated list of additional non-standard + sysfs attribute groups. +=============================================== =============================================== + +This function returns a pointer to the created hardware monitoring device +on success and a negative error code for failure. + +The hwmon_chip_info structure looks as follows:: + + struct hwmon_chip_info { + const struct hwmon_ops *ops; + const struct hwmon_channel_info **info; + }; + +It contains the following fields: + +* ops: + Pointer to device operations. +* info: + NULL-terminated list of device channel descriptors. + +The list of hwmon operations is defined as:: + + struct hwmon_ops { + umode_t (*is_visible)(const void *, enum hwmon_sensor_types type, + u32 attr, int); + int (*read)(struct device *, enum hwmon_sensor_types type, + u32 attr, int, long *); + int (*write)(struct device *, enum hwmon_sensor_types type, + u32 attr, int, long); + }; + +It defines the following operations. + +* is_visible: + Pointer to a function to return the file mode for each supported + attribute. This function is mandatory. + +* read: + Pointer to a function for reading a value from the chip. This function + is optional, but must be provided if any readable attributes exist. + +* write: + Pointer to a function for writing a value to the chip. This function is + optional, but must be provided if any writeable attributes exist. + +Each sensor channel is described with struct hwmon_channel_info, which is +defined as follows:: + + struct hwmon_channel_info { + enum hwmon_sensor_types type; + u32 *config; + }; + +It contains following fields: + +* type: + The hardware monitoring sensor type. + + Supported sensor types are + + ================== ================================================== + hwmon_chip A virtual sensor type, used to describe attributes + which are not bound to a specific input or output + hwmon_temp Temperature sensor + hwmon_in Voltage sensor + hwmon_curr Current sensor + hwmon_power Power sensor + hwmon_energy Energy sensor + hwmon_humidity Humidity sensor + hwmon_fan Fan speed sensor + hwmon_pwm PWM control + ================== ================================================== + +* config: + Pointer to a 0-terminated list of configuration values for each + sensor of the given type. Each value is a combination of bit values + describing the attributes supposed by a single sensor. + +As an example, here is the complete description file for a LM75 compatible +sensor chip. The chip has a single temperature sensor. The driver wants to +register with the thermal subsystem (HWMON_C_REGISTER_TZ), and it supports +the update_interval attribute (HWMON_C_UPDATE_INTERVAL). The chip supports +reading the temperature (HWMON_T_INPUT), it has a maximum temperature +register (HWMON_T_MAX) as well as a maximum temperature hysteresis register +(HWMON_T_MAX_HYST):: + + static const u32 lm75_chip_config[] = { + HWMON_C_REGISTER_TZ | HWMON_C_UPDATE_INTERVAL, + 0 + }; + + static const struct hwmon_channel_info lm75_chip = { + .type = hwmon_chip, + .config = lm75_chip_config, + }; + + static const u32 lm75_temp_config[] = { + HWMON_T_INPUT | HWMON_T_MAX | HWMON_T_MAX_HYST, + 0 + }; + + static const struct hwmon_channel_info lm75_temp = { + .type = hwmon_temp, + .config = lm75_temp_config, + }; + + static const struct hwmon_channel_info *lm75_info[] = { + &lm75_chip, + &lm75_temp, + NULL + }; + + The HWMON_CHANNEL_INFO() macro can and should be used when possible. + With this macro, the above example can be simplified to + + static const struct hwmon_channel_info *lm75_info[] = { + HWMON_CHANNEL_INFO(chip, + HWMON_C_REGISTER_TZ | HWMON_C_UPDATE_INTERVAL), + HWMON_CHANNEL_INFO(temp, + HWMON_T_INPUT | HWMON_T_MAX | HWMON_T_MAX_HYST), + NULL + }; + + The remaining declarations are as follows. + + static const struct hwmon_ops lm75_hwmon_ops = { + .is_visible = lm75_is_visible, + .read = lm75_read, + .write = lm75_write, + }; + + static const struct hwmon_chip_info lm75_chip_info = { + .ops = &lm75_hwmon_ops, + .info = lm75_info, + }; + +A complete list of bit values indicating individual attribute support +is defined in include/linux/hwmon.h. Definition prefixes are as follows. + +=============== ================================================= +HWMON_C_xxxx Chip attributes, for use with hwmon_chip. +HWMON_T_xxxx Temperature attributes, for use with hwmon_temp. +HWMON_I_xxxx Voltage attributes, for use with hwmon_in. +HWMON_C_xxxx Current attributes, for use with hwmon_curr. + Notice the prefix overlap with chip attributes. +HWMON_P_xxxx Power attributes, for use with hwmon_power. +HWMON_E_xxxx Energy attributes, for use with hwmon_energy. +HWMON_H_xxxx Humidity attributes, for use with hwmon_humidity. +HWMON_F_xxxx Fan speed attributes, for use with hwmon_fan. +HWMON_PWM_xxxx PWM control attributes, for use with hwmon_pwm. +=============== ================================================= + +Driver callback functions +------------------------- + +Each driver provides is_visible, read, and write functions. Parameters +and return values for those functions are as follows:: + + umode_t is_visible_func(const void *data, enum hwmon_sensor_types type, + u32 attr, int channel) + +Parameters: + data: + Pointer to device private data structure. + type: + The sensor type. + attr: + Attribute identifier associated with a specific attribute. + For example, the attribute value for HWMON_T_INPUT would be + hwmon_temp_input. For complete mappings of bit fields to + attribute values please see include/linux/hwmon.h. + channel: + The sensor channel number. + +Return value: + The file mode for this attribute. Typically, this will be 0 (the + attribute will not be created), S_IRUGO, or 'S_IRUGO | S_IWUSR'. + +:: + + int read_func(struct device *dev, enum hwmon_sensor_types type, + u32 attr, int channel, long *val) + +Parameters: + dev: + Pointer to the hardware monitoring device. + type: + The sensor type. + attr: + Attribute identifier associated with a specific attribute. + For example, the attribute value for HWMON_T_INPUT would be + hwmon_temp_input. For complete mappings please see + include/linux/hwmon.h. + channel: + The sensor channel number. + val: + Pointer to attribute value. + +Return value: + 0 on success, a negative error number otherwise. + +:: + + int write_func(struct device *dev, enum hwmon_sensor_types type, + u32 attr, int channel, long val) + +Parameters: + dev: + Pointer to the hardware monitoring device. + type: + The sensor type. + attr: + Attribute identifier associated with a specific attribute. + For example, the attribute value for HWMON_T_INPUT would be + hwmon_temp_input. For complete mappings please see + include/linux/hwmon.h. + channel: + The sensor channel number. + val: + The value to write to the chip. + +Return value: + 0 on success, a negative error number otherwise. + + +Driver-provided sysfs attributes +-------------------------------- + +If the hardware monitoring device is registered with +hwmon_device_register_with_info or devm_hwmon_device_register_with_info, +it is most likely not necessary to provide sysfs attributes. Only additional +non-standard sysfs attributes need to be provided when one of those registration +functions is used. + +The header file linux/hwmon-sysfs.h provides a number of useful macros to +declare and use hardware monitoring sysfs attributes. + +In many cases, you can use the exsting define DEVICE_ATTR or its variants +DEVICE_ATTR_{RW,RO,WO} to declare such attributes. This is feasible if an +attribute has no additional context. However, in many cases there will be +additional information such as a sensor index which will need to be passed +to the sysfs attribute handling function. + +SENSOR_DEVICE_ATTR and SENSOR_DEVICE_ATTR_2 can be used to define attributes +which need such additional context information. SENSOR_DEVICE_ATTR requires +one additional argument, SENSOR_DEVICE_ATTR_2 requires two. + +Simplified variants of SENSOR_DEVICE_ATTR and SENSOR_DEVICE_ATTR_2 are available +and should be used if standard attribute permissions and function names are +feasible. Standard permissions are 0644 for SENSOR_DEVICE_ATTR[_2]_RW, +0444 for SENSOR_DEVICE_ATTR[_2]_RO, and 0200 for SENSOR_DEVICE_ATTR[_2]_WO. +Standard functions, similar to DEVICE_ATTR_{RW,RO,WO}, have _show and _store +appended to the provided function name. + +SENSOR_DEVICE_ATTR and its variants define a struct sensor_device_attribute +variable. This structure has the following fields:: + + struct sensor_device_attribute { + struct device_attribute dev_attr; + int index; + }; + +You can use to_sensor_dev_attr to get the pointer to this structure from the +attribute read or write function. Its parameter is the device to which the +attribute is attached. + +SENSOR_DEVICE_ATTR_2 and its variants define a struct sensor_device_attribute_2 +variable, which is defined as follows:: + + struct sensor_device_attribute_2 { + struct device_attribute dev_attr; + u8 index; + u8 nr; + }; + +Use to_sensor_dev_attr_2 to get the pointer to this structure. Its parameter +is the device to which the attribute is attached. diff --git a/Documentation/hwmon/hwmon-kernel-api.txt b/Documentation/hwmon/hwmon-kernel-api.txt deleted file mode 100644 index b347b959fcda..000000000000 --- a/Documentation/hwmon/hwmon-kernel-api.txt +++ /dev/null @@ -1,386 +0,0 @@ -The Linux Hardware Monitoring kernel API -======================================== - -Guenter Roeck - -Introduction ------------- - -This document describes the API that can be used by hardware monitoring -drivers that want to use the hardware monitoring framework. - -This document does not describe what a hardware monitoring (hwmon) Driver or -Device is. It also does not describe the API which can be used by user space -to communicate with a hardware monitoring device. If you want to know this -then please read the following file: Documentation/hwmon/sysfs-interface. - -For additional guidelines on how to write and improve hwmon drivers, please -also read Documentation/hwmon/submitting-patches. - -The API -------- -Each hardware monitoring driver must #include and, in most -cases, . linux/hwmon.h declares the following -register/unregister functions:: - - struct device * - hwmon_device_register_with_groups(struct device *dev, const char *name, - void *drvdata, - const struct attribute_group **groups); - - struct device * - devm_hwmon_device_register_with_groups(struct device *dev, - const char *name, void *drvdata, - const struct attribute_group **groups); - - struct device * - hwmon_device_register_with_info(struct device *dev, - const char *name, void *drvdata, - const struct hwmon_chip_info *info, - const struct attribute_group **extra_groups); - - struct device * - devm_hwmon_device_register_with_info(struct device *dev, - const char *name, - void *drvdata, - const struct hwmon_chip_info *info, - const struct attribute_group **extra_groups); - - void hwmon_device_unregister(struct device *dev); - - void devm_hwmon_device_unregister(struct device *dev); - -hwmon_device_register_with_groups registers a hardware monitoring device. -The first parameter of this function is a pointer to the parent device. -The name parameter is a pointer to the hwmon device name. The registration -function wil create a name sysfs attribute pointing to this name. -The drvdata parameter is the pointer to the local driver data. -hwmon_device_register_with_groups will attach this pointer to the newly -allocated hwmon device. The pointer can be retrieved by the driver using -dev_get_drvdata() on the hwmon device pointer. The groups parameter is -a pointer to a list of sysfs attribute groups. The list must be NULL terminated. -hwmon_device_register_with_groups creates the hwmon device with name attribute -as well as all sysfs attributes attached to the hwmon device. -This function returns a pointer to the newly created hardware monitoring device -or PTR_ERR for failure. - -devm_hwmon_device_register_with_groups is similar to -hwmon_device_register_with_groups. However, it is device managed, meaning the -hwmon device does not have to be removed explicitly by the removal function. - -hwmon_device_register_with_info is the most comprehensive and preferred means -to register a hardware monitoring device. It creates the standard sysfs -attributes in the hardware monitoring core, letting the driver focus on reading -from and writing to the chip instead of having to bother with sysfs attributes. -The parent device parameter cannot be NULL with non-NULL chip info. Its -parameters are described in more detail below. - -devm_hwmon_device_register_with_info is similar to -hwmon_device_register_with_info. However, it is device managed, meaning the -hwmon device does not have to be removed explicitly by the removal function. - -hwmon_device_unregister deregisters a registered hardware monitoring device. -The parameter of this function is the pointer to the registered hardware -monitoring device structure. This function must be called from the driver -remove function if the hardware monitoring device was registered with -hwmon_device_register_with_groups or hwmon_device_register_with_info. - -devm_hwmon_device_unregister does not normally have to be called. It is only -needed for error handling, and only needed if the driver probe fails after -the call to devm_hwmon_device_register_with_groups or -hwmon_device_register_with_info and if the automatic (device managed) -removal would be too late. - -All supported hwmon device registration functions only accept valid device -names. Device names including invalid characters (whitespace, '*', or '-') -will be rejected. The 'name' parameter is mandatory. - -Using devm_hwmon_device_register_with_info() --------------------------------------------- - -hwmon_device_register_with_info() registers a hardware monitoring device. -The parameters to this function are - -=============================================== =============================================== -`struct device *dev` Pointer to parent device -`const char *name` Device name -`void *drvdata` Driver private data -`const struct hwmon_chip_info *info` Pointer to chip description. -`const struct attribute_group **extra_groups` Null-terminated list of additional non-standard - sysfs attribute groups. -=============================================== =============================================== - -This function returns a pointer to the created hardware monitoring device -on success and a negative error code for failure. - -The hwmon_chip_info structure looks as follows:: - - struct hwmon_chip_info { - const struct hwmon_ops *ops; - const struct hwmon_channel_info **info; - }; - -It contains the following fields: - -* ops: - Pointer to device operations. -* info: - NULL-terminated list of device channel descriptors. - -The list of hwmon operations is defined as:: - - struct hwmon_ops { - umode_t (*is_visible)(const void *, enum hwmon_sensor_types type, - u32 attr, int); - int (*read)(struct device *, enum hwmon_sensor_types type, - u32 attr, int, long *); - int (*write)(struct device *, enum hwmon_sensor_types type, - u32 attr, int, long); - }; - -It defines the following operations. - -* is_visible: - Pointer to a function to return the file mode for each supported - attribute. This function is mandatory. - -* read: - Pointer to a function for reading a value from the chip. This function - is optional, but must be provided if any readable attributes exist. - -* write: - Pointer to a function for writing a value to the chip. This function is - optional, but must be provided if any writeable attributes exist. - -Each sensor channel is described with struct hwmon_channel_info, which is -defined as follows:: - - struct hwmon_channel_info { - enum hwmon_sensor_types type; - u32 *config; - }; - -It contains following fields: - -* type: - The hardware monitoring sensor type. - - Supported sensor types are - - ================== ================================================== - hwmon_chip A virtual sensor type, used to describe attributes - which are not bound to a specific input or output - hwmon_temp Temperature sensor - hwmon_in Voltage sensor - hwmon_curr Current sensor - hwmon_power Power sensor - hwmon_energy Energy sensor - hwmon_humidity Humidity sensor - hwmon_fan Fan speed sensor - hwmon_pwm PWM control - ================== ================================================== - -* config: - Pointer to a 0-terminated list of configuration values for each - sensor of the given type. Each value is a combination of bit values - describing the attributes supposed by a single sensor. - -As an example, here is the complete description file for a LM75 compatible -sensor chip. The chip has a single temperature sensor. The driver wants to -register with the thermal subsystem (HWMON_C_REGISTER_TZ), and it supports -the update_interval attribute (HWMON_C_UPDATE_INTERVAL). The chip supports -reading the temperature (HWMON_T_INPUT), it has a maximum temperature -register (HWMON_T_MAX) as well as a maximum temperature hysteresis register -(HWMON_T_MAX_HYST):: - - static const u32 lm75_chip_config[] = { - HWMON_C_REGISTER_TZ | HWMON_C_UPDATE_INTERVAL, - 0 - }; - - static const struct hwmon_channel_info lm75_chip = { - .type = hwmon_chip, - .config = lm75_chip_config, - }; - - static const u32 lm75_temp_config[] = { - HWMON_T_INPUT | HWMON_T_MAX | HWMON_T_MAX_HYST, - 0 - }; - - static const struct hwmon_channel_info lm75_temp = { - .type = hwmon_temp, - .config = lm75_temp_config, - }; - - static const struct hwmon_channel_info *lm75_info[] = { - &lm75_chip, - &lm75_temp, - NULL - }; - - The HWMON_CHANNEL_INFO() macro can and should be used when possible. - With this macro, the above example can be simplified to - - static const struct hwmon_channel_info *lm75_info[] = { - HWMON_CHANNEL_INFO(chip, - HWMON_C_REGISTER_TZ | HWMON_C_UPDATE_INTERVAL), - HWMON_CHANNEL_INFO(temp, - HWMON_T_INPUT | HWMON_T_MAX | HWMON_T_MAX_HYST), - NULL - }; - - The remaining declarations are as follows. - - static const struct hwmon_ops lm75_hwmon_ops = { - .is_visible = lm75_is_visible, - .read = lm75_read, - .write = lm75_write, - }; - - static const struct hwmon_chip_info lm75_chip_info = { - .ops = &lm75_hwmon_ops, - .info = lm75_info, - }; - -A complete list of bit values indicating individual attribute support -is defined in include/linux/hwmon.h. Definition prefixes are as follows. - -=============== ================================================= -HWMON_C_xxxx Chip attributes, for use with hwmon_chip. -HWMON_T_xxxx Temperature attributes, for use with hwmon_temp. -HWMON_I_xxxx Voltage attributes, for use with hwmon_in. -HWMON_C_xxxx Current attributes, for use with hwmon_curr. - Notice the prefix overlap with chip attributes. -HWMON_P_xxxx Power attributes, for use with hwmon_power. -HWMON_E_xxxx Energy attributes, for use with hwmon_energy. -HWMON_H_xxxx Humidity attributes, for use with hwmon_humidity. -HWMON_F_xxxx Fan speed attributes, for use with hwmon_fan. -HWMON_PWM_xxxx PWM control attributes, for use with hwmon_pwm. -=============== ================================================= - -Driver callback functions -------------------------- - -Each driver provides is_visible, read, and write functions. Parameters -and return values for those functions are as follows:: - - umode_t is_visible_func(const void *data, enum hwmon_sensor_types type, - u32 attr, int channel) - -Parameters: - data: - Pointer to device private data structure. - type: - The sensor type. - attr: - Attribute identifier associated with a specific attribute. - For example, the attribute value for HWMON_T_INPUT would be - hwmon_temp_input. For complete mappings of bit fields to - attribute values please see include/linux/hwmon.h. - channel: - The sensor channel number. - -Return value: - The file mode for this attribute. Typically, this will be 0 (the - attribute will not be created), S_IRUGO, or 'S_IRUGO | S_IWUSR'. - -:: - - int read_func(struct device *dev, enum hwmon_sensor_types type, - u32 attr, int channel, long *val) - -Parameters: - dev: - Pointer to the hardware monitoring device. - type: - The sensor type. - attr: - Attribute identifier associated with a specific attribute. - For example, the attribute value for HWMON_T_INPUT would be - hwmon_temp_input. For complete mappings please see - include/linux/hwmon.h. - channel: - The sensor channel number. - val: - Pointer to attribute value. - -Return value: - 0 on success, a negative error number otherwise. - -:: - - int write_func(struct device *dev, enum hwmon_sensor_types type, - u32 attr, int channel, long val) - -Parameters: - dev: - Pointer to the hardware monitoring device. - type: - The sensor type. - attr: - Attribute identifier associated with a specific attribute. - For example, the attribute value for HWMON_T_INPUT would be - hwmon_temp_input. For complete mappings please see - include/linux/hwmon.h. - channel: - The sensor channel number. - val: - The value to write to the chip. - -Return value: - 0 on success, a negative error number otherwise. - - -Driver-provided sysfs attributes --------------------------------- - -If the hardware monitoring device is registered with -hwmon_device_register_with_info or devm_hwmon_device_register_with_info, -it is most likely not necessary to provide sysfs attributes. Only additional -non-standard sysfs attributes need to be provided when one of those registration -functions is used. - -The header file linux/hwmon-sysfs.h provides a number of useful macros to -declare and use hardware monitoring sysfs attributes. - -In many cases, you can use the exsting define DEVICE_ATTR or its variants -DEVICE_ATTR_{RW,RO,WO} to declare such attributes. This is feasible if an -attribute has no additional context. However, in many cases there will be -additional information such as a sensor index which will need to be passed -to the sysfs attribute handling function. - -SENSOR_DEVICE_ATTR and SENSOR_DEVICE_ATTR_2 can be used to define attributes -which need such additional context information. SENSOR_DEVICE_ATTR requires -one additional argument, SENSOR_DEVICE_ATTR_2 requires two. - -Simplified variants of SENSOR_DEVICE_ATTR and SENSOR_DEVICE_ATTR_2 are available -and should be used if standard attribute permissions and function names are -feasible. Standard permissions are 0644 for SENSOR_DEVICE_ATTR[_2]_RW, -0444 for SENSOR_DEVICE_ATTR[_2]_RO, and 0200 for SENSOR_DEVICE_ATTR[_2]_WO. -Standard functions, similar to DEVICE_ATTR_{RW,RO,WO}, have _show and _store -appended to the provided function name. - -SENSOR_DEVICE_ATTR and its variants define a struct sensor_device_attribute -variable. This structure has the following fields:: - - struct sensor_device_attribute { - struct device_attribute dev_attr; - int index; - }; - -You can use to_sensor_dev_attr to get the pointer to this structure from the -attribute read or write function. Its parameter is the device to which the -attribute is attached. - -SENSOR_DEVICE_ATTR_2 and its variants define a struct sensor_device_attribute_2 -variable, which is defined as follows:: - - struct sensor_device_attribute_2 { - struct device_attribute dev_attr; - u8 index; - u8 nr; - }; - -Use to_sensor_dev_attr_2 to get the pointer to this structure. Its parameter -is the device to which the attribute is attached. diff --git a/Documentation/hwmon/ibm-cffps b/Documentation/hwmon/ibm-cffps deleted file mode 100644 index 52e74e39463a..000000000000 --- a/Documentation/hwmon/ibm-cffps +++ /dev/null @@ -1,57 +0,0 @@ -Kernel driver ibm-cffps -======================= - -Supported chips: - - * IBM Common Form Factor power supply - -Author: Eddie James - -Description ------------ - -This driver supports IBM Common Form Factor (CFF) power supplies. This driver -is a client to the core PMBus driver. - -Usage Notes ------------ - -This driver does not auto-detect devices. You will have to instantiate the -devices explicitly. Please see Documentation/i2c/instantiating-devices for -details. - -Sysfs entries -------------- - -The following attributes are supported: - -======================= ====================================================== -curr1_alarm Output current over-current alarm. -curr1_input Measured output current in mA. -curr1_label "iout1" - -fan1_alarm Fan 1 warning. -fan1_fault Fan 1 fault. -fan1_input Fan 1 speed in RPM. -fan2_alarm Fan 2 warning. -fan2_fault Fan 2 fault. -fan2_input Fan 2 speed in RPM. - -in1_alarm Input voltage under-voltage alarm. -in1_input Measured input voltage in mV. -in1_label "vin" -in2_alarm Output voltage over-voltage alarm. -in2_input Measured output voltage in mV. -in2_label "vout1" - -power1_alarm Input fault or alarm. -power1_input Measured input power in uW. -power1_label "pin" - -temp1_alarm PSU inlet ambient temperature over-temperature alarm. -temp1_input Measured PSU inlet ambient temp in millidegrees C. -temp2_alarm Secondary rectifier temp over-temperature alarm. -temp2_input Measured secondary rectifier temp in millidegrees C. -temp3_alarm ORing FET temperature over-temperature alarm. -temp3_input Measured ORing FET temperature in millidegrees C. -======================= ====================================================== diff --git a/Documentation/hwmon/ibm-cffps.rst b/Documentation/hwmon/ibm-cffps.rst new file mode 100644 index 000000000000..52e74e39463a --- /dev/null +++ b/Documentation/hwmon/ibm-cffps.rst @@ -0,0 +1,57 @@ +Kernel driver ibm-cffps +======================= + +Supported chips: + + * IBM Common Form Factor power supply + +Author: Eddie James + +Description +----------- + +This driver supports IBM Common Form Factor (CFF) power supplies. This driver +is a client to the core PMBus driver. + +Usage Notes +----------- + +This driver does not auto-detect devices. You will have to instantiate the +devices explicitly. Please see Documentation/i2c/instantiating-devices for +details. + +Sysfs entries +------------- + +The following attributes are supported: + +======================= ====================================================== +curr1_alarm Output current over-current alarm. +curr1_input Measured output current in mA. +curr1_label "iout1" + +fan1_alarm Fan 1 warning. +fan1_fault Fan 1 fault. +fan1_input Fan 1 speed in RPM. +fan2_alarm Fan 2 warning. +fan2_fault Fan 2 fault. +fan2_input Fan 2 speed in RPM. + +in1_alarm Input voltage under-voltage alarm. +in1_input Measured input voltage in mV. +in1_label "vin" +in2_alarm Output voltage over-voltage alarm. +in2_input Measured output voltage in mV. +in2_label "vout1" + +power1_alarm Input fault or alarm. +power1_input Measured input power in uW. +power1_label "pin" + +temp1_alarm PSU inlet ambient temperature over-temperature alarm. +temp1_input Measured PSU inlet ambient temp in millidegrees C. +temp2_alarm Secondary rectifier temp over-temperature alarm. +temp2_input Measured secondary rectifier temp in millidegrees C. +temp3_alarm ORing FET temperature over-temperature alarm. +temp3_input Measured ORing FET temperature in millidegrees C. +======================= ====================================================== diff --git a/Documentation/hwmon/ibmaem b/Documentation/hwmon/ibmaem deleted file mode 100644 index f07a14a1c2f5..000000000000 --- a/Documentation/hwmon/ibmaem +++ /dev/null @@ -1,44 +0,0 @@ -Kernel driver ibmaem -==================== - -This driver talks to the IBM Systems Director Active Energy Manager, known -henceforth as AEM. - -Supported systems: - - * Any recent IBM System X server with AEM support. - - This includes the x3350, x3550, x3650, x3655, x3755, x3850 M2, - x3950 M2, and certain HC10/HS2x/LS2x/QS2x blades. - - The IPMI host interface - driver ("ipmi-si") needs to be loaded for this driver to do anything. - - Prefix: 'ibmaem' - - Datasheet: Not available - -Author: Darrick J. Wong - -Description ------------ - -This driver implements sensor reading support for the energy and power meters -available on various IBM System X hardware through the BMC. All sensor banks -will be exported as platform devices; this driver can talk to both v1 and v2 -interfaces. This driver is completely separate from the older ibmpex driver. - -The v1 AEM interface has a simple set of features to monitor energy use. There -is a register that displays an estimate of raw energy consumption since the -last BMC reset, and a power sensor that returns average power use over a -configurable interval. - -The v2 AEM interface is a bit more sophisticated, being able to present a wider -range of energy and power use registers, the power cap as set by the AEM -software, and temperature sensors. - -Special Features ----------------- - -The "power_cap" value displays the current system power cap, as set by the AEM -software. Setting the power cap from the host is not currently supported. diff --git a/Documentation/hwmon/ibmaem.rst b/Documentation/hwmon/ibmaem.rst new file mode 100644 index 000000000000..f07a14a1c2f5 --- /dev/null +++ b/Documentation/hwmon/ibmaem.rst @@ -0,0 +1,44 @@ +Kernel driver ibmaem +==================== + +This driver talks to the IBM Systems Director Active Energy Manager, known +henceforth as AEM. + +Supported systems: + + * Any recent IBM System X server with AEM support. + + This includes the x3350, x3550, x3650, x3655, x3755, x3850 M2, + x3950 M2, and certain HC10/HS2x/LS2x/QS2x blades. + + The IPMI host interface + driver ("ipmi-si") needs to be loaded for this driver to do anything. + + Prefix: 'ibmaem' + + Datasheet: Not available + +Author: Darrick J. Wong + +Description +----------- + +This driver implements sensor reading support for the energy and power meters +available on various IBM System X hardware through the BMC. All sensor banks +will be exported as platform devices; this driver can talk to both v1 and v2 +interfaces. This driver is completely separate from the older ibmpex driver. + +The v1 AEM interface has a simple set of features to monitor energy use. There +is a register that displays an estimate of raw energy consumption since the +last BMC reset, and a power sensor that returns average power use over a +configurable interval. + +The v2 AEM interface is a bit more sophisticated, being able to present a wider +range of energy and power use registers, the power cap as set by the AEM +software, and temperature sensors. + +Special Features +---------------- + +The "power_cap" value displays the current system power cap, as set by the AEM +software. Setting the power cap from the host is not currently supported. diff --git a/Documentation/hwmon/ibmpowernv b/Documentation/hwmon/ibmpowernv deleted file mode 100644 index 5d642bc3dec0..000000000000 --- a/Documentation/hwmon/ibmpowernv +++ /dev/null @@ -1,87 +0,0 @@ -Kernel Driver IBMPOWERNV -======================== - -Supported systems: - - * Any recent IBM P servers based on POWERNV platform - -Author: Neelesh Gupta - -Description ------------ - -This driver implements reading the platform sensors data like temperature/fan/ -voltage/power for 'POWERNV' platform. - -The driver uses the platform device infrastructure. It probes the device tree -for sensor devices during the __init phase and registers them with the 'hwmon'. -'hwmon' populates the 'sysfs' tree having attribute files, each for a given -sensor type and its attribute data. - -All the nodes in the DT appear under "/ibm,opal/sensors" and each valid node in -the DT maps to an attribute file in 'sysfs'. The node exports unique 'sensor-id' -which the driver uses to make an OPAL call to the firmware. - -Usage notes ------------ -The driver is built statically with the kernel by enabling the config -CONFIG_SENSORS_IBMPOWERNV. It can also be built as module 'ibmpowernv'. - -Sysfs attributes ----------------- - -======================= ======================================================= -fanX_input Measured RPM value. -fanX_min Threshold RPM for alert generation. -fanX_fault - 0: No fail condition - - 1: Failing fan - -tempX_input Measured ambient temperature. -tempX_max Threshold ambient temperature for alert generation. -tempX_highest Historical maximum temperature -tempX_lowest Historical minimum temperature -tempX_enable Enable/disable all temperature sensors belonging to the - sub-group. In POWER9, this attribute corresponds to - each OCC. Using this attribute each OCC can be asked to - disable/enable all of its temperature sensors. - - - 1: Enable - - 0: Disable - -inX_input Measured power supply voltage (millivolt) -inX_fault - 0: No fail condition. - - 1: Failing power supply. -inX_highest Historical maximum voltage -inX_lowest Historical minimum voltage -inX_enable Enable/disable all voltage sensors belonging to the - sub-group. In POWER9, this attribute corresponds to - each OCC. Using this attribute each OCC can be asked to - disable/enable all of its voltage sensors. - - - 1: Enable - - 0: Disable - -powerX_input Power consumption (microWatt) -powerX_input_highest Historical maximum power -powerX_input_lowest Historical minimum power -powerX_enable Enable/disable all power sensors belonging to the - sub-group. In POWER9, this attribute corresponds to - each OCC. Using this attribute each OCC can be asked to - disable/enable all of its power sensors. - - - 1: Enable - - 0: Disable - -currX_input Measured current (milliampere) -currX_highest Historical maximum current -currX_lowest Historical minimum current -currX_enable Enable/disable all current sensors belonging to the - sub-group. In POWER9, this attribute corresponds to - each OCC. Using this attribute each OCC can be asked to - disable/enable all of its current sensors. - - - 1: Enable - - 0: Disable - -energyX_input Cumulative energy (microJoule) -======================= ======================================================= diff --git a/Documentation/hwmon/ibmpowernv.rst b/Documentation/hwmon/ibmpowernv.rst new file mode 100644 index 000000000000..5d642bc3dec0 --- /dev/null +++ b/Documentation/hwmon/ibmpowernv.rst @@ -0,0 +1,87 @@ +Kernel Driver IBMPOWERNV +======================== + +Supported systems: + + * Any recent IBM P servers based on POWERNV platform + +Author: Neelesh Gupta + +Description +----------- + +This driver implements reading the platform sensors data like temperature/fan/ +voltage/power for 'POWERNV' platform. + +The driver uses the platform device infrastructure. It probes the device tree +for sensor devices during the __init phase and registers them with the 'hwmon'. +'hwmon' populates the 'sysfs' tree having attribute files, each for a given +sensor type and its attribute data. + +All the nodes in the DT appear under "/ibm,opal/sensors" and each valid node in +the DT maps to an attribute file in 'sysfs'. The node exports unique 'sensor-id' +which the driver uses to make an OPAL call to the firmware. + +Usage notes +----------- +The driver is built statically with the kernel by enabling the config +CONFIG_SENSORS_IBMPOWERNV. It can also be built as module 'ibmpowernv'. + +Sysfs attributes +---------------- + +======================= ======================================================= +fanX_input Measured RPM value. +fanX_min Threshold RPM for alert generation. +fanX_fault - 0: No fail condition + - 1: Failing fan + +tempX_input Measured ambient temperature. +tempX_max Threshold ambient temperature for alert generation. +tempX_highest Historical maximum temperature +tempX_lowest Historical minimum temperature +tempX_enable Enable/disable all temperature sensors belonging to the + sub-group. In POWER9, this attribute corresponds to + each OCC. Using this attribute each OCC can be asked to + disable/enable all of its temperature sensors. + + - 1: Enable + - 0: Disable + +inX_input Measured power supply voltage (millivolt) +inX_fault - 0: No fail condition. + - 1: Failing power supply. +inX_highest Historical maximum voltage +inX_lowest Historical minimum voltage +inX_enable Enable/disable all voltage sensors belonging to the + sub-group. In POWER9, this attribute corresponds to + each OCC. Using this attribute each OCC can be asked to + disable/enable all of its voltage sensors. + + - 1: Enable + - 0: Disable + +powerX_input Power consumption (microWatt) +powerX_input_highest Historical maximum power +powerX_input_lowest Historical minimum power +powerX_enable Enable/disable all power sensors belonging to the + sub-group. In POWER9, this attribute corresponds to + each OCC. Using this attribute each OCC can be asked to + disable/enable all of its power sensors. + + - 1: Enable + - 0: Disable + +currX_input Measured current (milliampere) +currX_highest Historical maximum current +currX_lowest Historical minimum current +currX_enable Enable/disable all current sensors belonging to the + sub-group. In POWER9, this attribute corresponds to + each OCC. Using this attribute each OCC can be asked to + disable/enable all of its current sensors. + + - 1: Enable + - 0: Disable + +energyX_input Cumulative energy (microJoule) +======================= ======================================================= diff --git a/Documentation/hwmon/ina209 b/Documentation/hwmon/ina209 deleted file mode 100644 index 64322075a145..000000000000 --- a/Documentation/hwmon/ina209 +++ /dev/null @@ -1,99 +0,0 @@ -Kernel driver ina209 -==================== - -Supported chips: - - * Burr-Brown / Texas Instruments INA209 - - Prefix: 'ina209' - - Addresses scanned: - - - Datasheet: - http://www.ti.com/lit/gpn/ina209 - -Author: - - Paul Hays - - Ira W. Snyder - - Guenter Roeck - - -Description ------------ - -The TI / Burr-Brown INA209 monitors voltage, current, and power on the high side -of a D.C. power supply. It can perform measurements and calculations in the -background to supply readings at any time. It includes a programmable -calibration multiplier to scale the displayed current and power values. - - -Sysfs entries -------------- - -The INA209 chip is highly configurable both via hardwiring and via -the I2C bus. See the datasheet for details. - -This tries to expose most monitoring features of the hardware via -sysfs. It does not support every feature of this chip. - -======================= ======================================================= -in0_input shunt voltage (mV) -in0_input_highest shunt voltage historical maximum reading (mV) -in0_input_lowest shunt voltage historical minimum reading (mV) -in0_reset_history reset shunt voltage history -in0_max shunt voltage max alarm limit (mV) -in0_min shunt voltage min alarm limit (mV) -in0_crit_max shunt voltage crit max alarm limit (mV) -in0_crit_min shunt voltage crit min alarm limit (mV) -in0_max_alarm shunt voltage max alarm limit exceeded -in0_min_alarm shunt voltage min alarm limit exceeded -in0_crit_max_alarm shunt voltage crit max alarm limit exceeded -in0_crit_min_alarm shunt voltage crit min alarm limit exceeded - -in1_input bus voltage (mV) -in1_input_highest bus voltage historical maximum reading (mV) -in1_input_lowest bus voltage historical minimum reading (mV) -in1_reset_history reset bus voltage history -in1_max bus voltage max alarm limit (mV) -in1_min bus voltage min alarm limit (mV) -in1_crit_max bus voltage crit max alarm limit (mV) -in1_crit_min bus voltage crit min alarm limit (mV) -in1_max_alarm bus voltage max alarm limit exceeded -in1_min_alarm bus voltage min alarm limit exceeded -in1_crit_max_alarm bus voltage crit max alarm limit exceeded -in1_crit_min_alarm bus voltage crit min alarm limit exceeded - -power1_input power measurement (uW) -power1_input_highest power historical maximum reading (uW) -power1_reset_history reset power history -power1_max power max alarm limit (uW) -power1_crit power crit alarm limit (uW) -power1_max_alarm power max alarm limit exceeded -power1_crit_alarm power crit alarm limit exceeded - -curr1_input current measurement (mA) - -update_interval data conversion time; affects number of samples used - to average results for shunt and bus voltages. -======================= ======================================================= - -General Remarks ---------------- - -The power and current registers in this chip require that the calibration -register is programmed correctly before they are used. Normally this is expected -to be done in the BIOS. In the absence of BIOS programming, the shunt resistor -voltage can be provided using platform data. The driver uses platform data from -the ina2xx driver for this purpose. If calibration register data is not provided -via platform data, the driver checks if the calibration register has been -programmed (ie has a value not equal to zero). If so, this value is retained. -Otherwise, a default value reflecting a shunt resistor value of 10 mOhm is -programmed into the calibration register. - - -Output Pins ------------ - -Output pin programming is a board feature which depends on the BIOS. It is -outside the scope of a hardware monitoring driver to enable or disable output -pins. diff --git a/Documentation/hwmon/ina209.rst b/Documentation/hwmon/ina209.rst new file mode 100644 index 000000000000..64322075a145 --- /dev/null +++ b/Documentation/hwmon/ina209.rst @@ -0,0 +1,99 @@ +Kernel driver ina209 +==================== + +Supported chips: + + * Burr-Brown / Texas Instruments INA209 + + Prefix: 'ina209' + + Addresses scanned: - + + Datasheet: + http://www.ti.com/lit/gpn/ina209 + +Author: + - Paul Hays + - Ira W. Snyder + - Guenter Roeck + + +Description +----------- + +The TI / Burr-Brown INA209 monitors voltage, current, and power on the high side +of a D.C. power supply. It can perform measurements and calculations in the +background to supply readings at any time. It includes a programmable +calibration multiplier to scale the displayed current and power values. + + +Sysfs entries +------------- + +The INA209 chip is highly configurable both via hardwiring and via +the I2C bus. See the datasheet for details. + +This tries to expose most monitoring features of the hardware via +sysfs. It does not support every feature of this chip. + +======================= ======================================================= +in0_input shunt voltage (mV) +in0_input_highest shunt voltage historical maximum reading (mV) +in0_input_lowest shunt voltage historical minimum reading (mV) +in0_reset_history reset shunt voltage history +in0_max shunt voltage max alarm limit (mV) +in0_min shunt voltage min alarm limit (mV) +in0_crit_max shunt voltage crit max alarm limit (mV) +in0_crit_min shunt voltage crit min alarm limit (mV) +in0_max_alarm shunt voltage max alarm limit exceeded +in0_min_alarm shunt voltage min alarm limit exceeded +in0_crit_max_alarm shunt voltage crit max alarm limit exceeded +in0_crit_min_alarm shunt voltage crit min alarm limit exceeded + +in1_input bus voltage (mV) +in1_input_highest bus voltage historical maximum reading (mV) +in1_input_lowest bus voltage historical minimum reading (mV) +in1_reset_history reset bus voltage history +in1_max bus voltage max alarm limit (mV) +in1_min bus voltage min alarm limit (mV) +in1_crit_max bus voltage crit max alarm limit (mV) +in1_crit_min bus voltage crit min alarm limit (mV) +in1_max_alarm bus voltage max alarm limit exceeded +in1_min_alarm bus voltage min alarm limit exceeded +in1_crit_max_alarm bus voltage crit max alarm limit exceeded +in1_crit_min_alarm bus voltage crit min alarm limit exceeded + +power1_input power measurement (uW) +power1_input_highest power historical maximum reading (uW) +power1_reset_history reset power history +power1_max power max alarm limit (uW) +power1_crit power crit alarm limit (uW) +power1_max_alarm power max alarm limit exceeded +power1_crit_alarm power crit alarm limit exceeded + +curr1_input current measurement (mA) + +update_interval data conversion time; affects number of samples used + to average results for shunt and bus voltages. +======================= ======================================================= + +General Remarks +--------------- + +The power and current registers in this chip require that the calibration +register is programmed correctly before they are used. Normally this is expected +to be done in the BIOS. In the absence of BIOS programming, the shunt resistor +voltage can be provided using platform data. The driver uses platform data from +the ina2xx driver for this purpose. If calibration register data is not provided +via platform data, the driver checks if the calibration register has been +programmed (ie has a value not equal to zero). If so, this value is retained. +Otherwise, a default value reflecting a shunt resistor value of 10 mOhm is +programmed into the calibration register. + + +Output Pins +----------- + +Output pin programming is a board feature which depends on the BIOS. It is +outside the scope of a hardware monitoring driver to enable or disable output +pins. diff --git a/Documentation/hwmon/ina2xx b/Documentation/hwmon/ina2xx deleted file mode 100644 index 95badf9c396f..000000000000 --- a/Documentation/hwmon/ina2xx +++ /dev/null @@ -1,104 +0,0 @@ -Kernel driver ina2xx -==================== - -Supported chips: - - * Texas Instruments INA219 - - - Prefix: 'ina219' - Addresses: I2C 0x40 - 0x4f - - Datasheet: Publicly available at the Texas Instruments website - - http://www.ti.com/ - - * Texas Instruments INA220 - - Prefix: 'ina220' - - Addresses: I2C 0x40 - 0x4f - - Datasheet: Publicly available at the Texas Instruments website - - http://www.ti.com/ - - * Texas Instruments INA226 - - Prefix: 'ina226' - - Addresses: I2C 0x40 - 0x4f - - Datasheet: Publicly available at the Texas Instruments website - - http://www.ti.com/ - - * Texas Instruments INA230 - - Prefix: 'ina230' - - Addresses: I2C 0x40 - 0x4f - - Datasheet: Publicly available at the Texas Instruments website - - http://www.ti.com/ - - * Texas Instruments INA231 - - Prefix: 'ina231' - - Addresses: I2C 0x40 - 0x4f - - Datasheet: Publicly available at the Texas Instruments website - - http://www.ti.com/ - -Author: Lothar Felten - -Description ------------ - -The INA219 is a high-side current shunt and power monitor with an I2C -interface. The INA219 monitors both shunt drop and supply voltage, with -programmable conversion times and filtering. - -The INA220 is a high or low side current shunt and power monitor with an I2C -interface. The INA220 monitors both shunt drop and supply voltage. - -The INA226 is a current shunt and power monitor with an I2C interface. -The INA226 monitors both a shunt voltage drop and bus supply voltage. - -INA230 and INA231 are high or low side current shunt and power monitors -with an I2C interface. The chips monitor both a shunt voltage drop and -bus supply voltage. - -The shunt value in micro-ohms can be set via platform data or device tree at -compile-time or via the shunt_resistor attribute in sysfs at run-time. Please -refer to the Documentation/devicetree/bindings/hwmon/ina2xx.txt for bindings -if the device tree is used. - -Additionally ina226 supports update_interval attribute as described in -Documentation/hwmon/sysfs-interface. Internally the interval is the sum of -bus and shunt voltage conversion times multiplied by the averaging rate. We -don't touch the conversion times and only modify the number of averages. The -lower limit of the update_interval is 2 ms, the upper limit is 2253 ms. -The actual programmed interval may vary from the desired value. - -General sysfs entries ---------------------- - -======================= =============================== -in0_input Shunt voltage(mV) channel -in1_input Bus voltage(mV) channel -curr1_input Current(mA) measurement channel -power1_input Power(uW) measurement channel -shunt_resistor Shunt resistance(uOhm) channel -======================= =============================== - -Sysfs entries for ina226, ina230 and ina231 only ------------------------------------------------- - -======================= ==================================================== -update_interval data conversion time; affects number of samples used - to average results for shunt and bus voltages. -======================= ==================================================== diff --git a/Documentation/hwmon/ina2xx.rst b/Documentation/hwmon/ina2xx.rst new file mode 100644 index 000000000000..94b9a260c518 --- /dev/null +++ b/Documentation/hwmon/ina2xx.rst @@ -0,0 +1,104 @@ +Kernel driver ina2xx +==================== + +Supported chips: + + * Texas Instruments INA219 + + + Prefix: 'ina219' + Addresses: I2C 0x40 - 0x4f + + Datasheet: Publicly available at the Texas Instruments website + + http://www.ti.com/ + + * Texas Instruments INA220 + + Prefix: 'ina220' + + Addresses: I2C 0x40 - 0x4f + + Datasheet: Publicly available at the Texas Instruments website + + http://www.ti.com/ + + * Texas Instruments INA226 + + Prefix: 'ina226' + + Addresses: I2C 0x40 - 0x4f + + Datasheet: Publicly available at the Texas Instruments website + + http://www.ti.com/ + + * Texas Instruments INA230 + + Prefix: 'ina230' + + Addresses: I2C 0x40 - 0x4f + + Datasheet: Publicly available at the Texas Instruments website + + http://www.ti.com/ + + * Texas Instruments INA231 + + Prefix: 'ina231' + + Addresses: I2C 0x40 - 0x4f + + Datasheet: Publicly available at the Texas Instruments website + + http://www.ti.com/ + +Author: Lothar Felten + +Description +----------- + +The INA219 is a high-side current shunt and power monitor with an I2C +interface. The INA219 monitors both shunt drop and supply voltage, with +programmable conversion times and filtering. + +The INA220 is a high or low side current shunt and power monitor with an I2C +interface. The INA220 monitors both shunt drop and supply voltage. + +The INA226 is a current shunt and power monitor with an I2C interface. +The INA226 monitors both a shunt voltage drop and bus supply voltage. + +INA230 and INA231 are high or low side current shunt and power monitors +with an I2C interface. The chips monitor both a shunt voltage drop and +bus supply voltage. + +The shunt value in micro-ohms can be set via platform data or device tree at +compile-time or via the shunt_resistor attribute in sysfs at run-time. Please +refer to the Documentation/devicetree/bindings/hwmon/ina2xx.txt for bindings +if the device tree is used. + +Additionally ina226 supports update_interval attribute as described in +Documentation/hwmon/sysfs-interface.rst. Internally the interval is the sum of +bus and shunt voltage conversion times multiplied by the averaging rate. We +don't touch the conversion times and only modify the number of averages. The +lower limit of the update_interval is 2 ms, the upper limit is 2253 ms. +The actual programmed interval may vary from the desired value. + +General sysfs entries +--------------------- + +======================= =============================== +in0_input Shunt voltage(mV) channel +in1_input Bus voltage(mV) channel +curr1_input Current(mA) measurement channel +power1_input Power(uW) measurement channel +shunt_resistor Shunt resistance(uOhm) channel +======================= =============================== + +Sysfs entries for ina226, ina230 and ina231 only +------------------------------------------------ + +======================= ==================================================== +update_interval data conversion time; affects number of samples used + to average results for shunt and bus voltages. +======================= ==================================================== diff --git a/Documentation/hwmon/ina3221 b/Documentation/hwmon/ina3221 deleted file mode 100644 index 1e34abb38b59..000000000000 --- a/Documentation/hwmon/ina3221 +++ /dev/null @@ -1,49 +0,0 @@ -Kernel driver ina3221 -===================== - -Supported chips: - - * Texas Instruments INA3221 - - Prefix: 'ina3221' - - Addresses: I2C 0x40 - 0x43 - - Datasheet: Publicly available at the Texas Instruments website - - http://www.ti.com/ - -Author: Andrew F. Davis - -Description ------------ - -The Texas Instruments INA3221 monitors voltage, current, and power on the high -side of up to three D.C. power supplies. The INA3221 monitors both shunt drop -and supply voltage, with programmable conversion times and averaging, current -and power are calculated host-side from these. - -Sysfs entries -------------- - -======================= ======================================================= -in[123]_label Voltage channel labels -in[123]_enable Voltage channel enable controls -in[123]_input Bus voltage(mV) channels -curr[123]_input Current(mA) measurement channels -shunt[123]_resistor Shunt resistance(uOhm) channels -curr[123]_crit Critical alert current(mA) setting, activates the - corresponding alarm when the respective current - is above this value -curr[123]_crit_alarm Critical alert current limit exceeded -curr[123]_max Warning alert current(mA) setting, activates the - corresponding alarm when the respective current - average is above this value. -curr[123]_max_alarm Warning alert current limit exceeded -in[456]_input Shunt voltage(uV) for channels 1, 2, and 3 respectively -samples Number of samples using in the averaging mode. - - Supports the list of number of samples: - - 1, 4, 16, 64, 128, 256, 512, 1024 -======================= ======================================================= diff --git a/Documentation/hwmon/ina3221.rst b/Documentation/hwmon/ina3221.rst new file mode 100644 index 000000000000..1e34abb38b59 --- /dev/null +++ b/Documentation/hwmon/ina3221.rst @@ -0,0 +1,49 @@ +Kernel driver ina3221 +===================== + +Supported chips: + + * Texas Instruments INA3221 + + Prefix: 'ina3221' + + Addresses: I2C 0x40 - 0x43 + + Datasheet: Publicly available at the Texas Instruments website + + http://www.ti.com/ + +Author: Andrew F. Davis + +Description +----------- + +The Texas Instruments INA3221 monitors voltage, current, and power on the high +side of up to three D.C. power supplies. The INA3221 monitors both shunt drop +and supply voltage, with programmable conversion times and averaging, current +and power are calculated host-side from these. + +Sysfs entries +------------- + +======================= ======================================================= +in[123]_label Voltage channel labels +in[123]_enable Voltage channel enable controls +in[123]_input Bus voltage(mV) channels +curr[123]_input Current(mA) measurement channels +shunt[123]_resistor Shunt resistance(uOhm) channels +curr[123]_crit Critical alert current(mA) setting, activates the + corresponding alarm when the respective current + is above this value +curr[123]_crit_alarm Critical alert current limit exceeded +curr[123]_max Warning alert current(mA) setting, activates the + corresponding alarm when the respective current + average is above this value. +curr[123]_max_alarm Warning alert current limit exceeded +in[456]_input Shunt voltage(uV) for channels 1, 2, and 3 respectively +samples Number of samples using in the averaging mode. + + Supports the list of number of samples: + + 1, 4, 16, 64, 128, 256, 512, 1024 +======================= ======================================================= diff --git a/Documentation/hwmon/index.rst b/Documentation/hwmon/index.rst new file mode 100644 index 000000000000..893804414510 --- /dev/null +++ b/Documentation/hwmon/index.rst @@ -0,0 +1,179 @@ +========================= +Linux Hardware Monitoring +========================= + +.. toctree:: + :maxdepth: 1 + + hwmon-kernel-api.rst + pmbus-core.rst + submitting-patches.rst + sysfs-interface.rst + userspace-tools.rst + +Hardware Monitoring Kernel Drivers +================================== + +.. toctree:: + :maxdepth: 1 + + ab8500.rst + abituguru.rst + abituguru3.rst + abx500.rst + acpi_power_meter.rst + ad7314.rst + adc128d818.rst + adm1021.rst + adm1025.rst + adm1026.rst + adm1031.rst + adm1275.rst + adm9240.rst + ads1015.rst + ads7828.rst + adt7410.rst + adt7411.rst + adt7462.rst + adt7470.rst + adt7475.rst + amc6821.rst + asb100.rst + asc7621.rst + aspeed-pwm-tacho.rst + coretemp.rst + da9052.rst + da9055.rst + dme1737.rst + ds1621.rst + ds620.rst + emc1403.rst + emc2103.rst + emc6w201.rst + f71805f.rst + f71882fg.rst + fam15h_power.rst + ftsteutates.rst + g760a.rst + g762.rst + gl518sm.rst + hih6130.rst + ibmaem.rst + ibm-cffps.rst + ibmpowernv.rst + ina209.rst + ina2xx.rst + ina3221.rst + ir35221.rst + it87.rst + jc42.rst + k10temp.rst + k8temp.rst + lineage-pem.rst + lm25066.rst + lm63.rst + lm70.rst + lm73.rst + lm75.rst + lm77.rst + lm78.rst + lm80.rst + lm83.rst + lm85.rst + lm87.rst + lm90.rst + lm92.rst + lm93.rst + lm95234.rst + lm95245.rst + ltc2945.rst + ltc2978.rst + ltc2990.rst + ltc3815.rst + ltc4151.rst + ltc4215.rst + ltc4245.rst + ltc4260.rst + ltc4261.rst + max16064.rst + max16065.rst + max1619.rst + max1668.rst + max197.rst + max20751.rst + max31722.rst + max31785.rst + max31790.rst + max34440.rst + max6639.rst + max6642.rst + max6650.rst + max6697.rst + max8688.rst + mc13783-adc.rst + mcp3021.rst + menf21bmc.rst + mlxreg-fan.rst + nct6683.rst + nct6775.rst + nct7802.rst + nct7904.rst + npcm750-pwm-fan.rst + nsa320.rst + ntc_thermistor.rst + occ.rst + pc87360.rst + pc87427.rst + pcf8591.rst + pmbus.rst + powr1220.rst + pwm-fan.rst + raspberrypi-hwmon.rst + sch5627.rst + sch5636.rst + scpi-hwmon.rst + sht15.rst + sht21.rst + sht3x.rst + shtc1.rst + sis5595.rst + smm665.rst + smsc47b397.rst + smsc47m192.rst + smsc47m1.rst + tc654.rst + tc74.rst + thmc50.rst + tmp102.rst + tmp103.rst + tmp108.rst + tmp401.rst + tmp421.rst + tps40422.rst + twl4030-madc-hwmon.rst + ucd9000.rst + ucd9200.rst + vexpress.rst + via686a.rst + vt1211.rst + w83627ehf.rst + w83627hf.rst + w83773g.rst + w83781d.rst + w83791d.rst + w83792d.rst + w83793.rst + w83795.rst + w83l785ts.rst + w83l786ng.rst + wm831x.rst + wm8350.rst + xgene-hwmon.rst + zl6100.rst + +.. only:: subproject and html + + Indices + ======= + + * :ref:`genindex` diff --git a/Documentation/hwmon/ir35221 b/Documentation/hwmon/ir35221 deleted file mode 100644 index a83922e5ccb5..000000000000 --- a/Documentation/hwmon/ir35221 +++ /dev/null @@ -1,92 +0,0 @@ -Kernel driver ir35221 -===================== - -Supported chips: - * Infineon IR35221 - - Prefix: 'ir35221' - - Addresses scanned: - - - Datasheet: Datasheet is not publicly available. - -Author: Samuel Mendoza-Jonas - - -Description ------------ - -IR35221 is a Digital DC-DC Multiphase Converter - - -Usage Notes ------------ - -This driver does not probe for PMBus devices. You will have to instantiate -devices explicitly. - -Example: the following commands will load the driver for an IR35221 -at address 0x70 on I2C bus #4:: - - # modprobe ir35221 - # echo ir35221 0x70 > /sys/bus/i2c/devices/i2c-4/new_device - - -Sysfs attributes ----------------- - -======================= ======================================================= -curr1_label "iin" -curr1_input Measured input current -curr1_max Maximum current -curr1_max_alarm Current high alarm - -curr[2-3]_label "iout[1-2]" -curr[2-3]_input Measured output current -curr[2-3]_crit Critical maximum current -curr[2-3]_crit_alarm Current critical high alarm -curr[2-3]_highest Highest output current -curr[2-3]_lowest Lowest output current -curr[2-3]_max Maximum current -curr[2-3]_max_alarm Current high alarm - -in1_label "vin" -in1_input Measured input voltage -in1_crit Critical maximum input voltage -in1_crit_alarm Input voltage critical high alarm -in1_highest Highest input voltage -in1_lowest Lowest input voltage -in1_min Minimum input voltage -in1_min_alarm Input voltage low alarm - -in[2-3]_label "vout[1-2]" -in[2-3]_input Measured output voltage -in[2-3]_lcrit Critical minimum output voltage -in[2-3]_lcrit_alarm Output voltage critical low alarm -in[2-3]_crit Critical maximum output voltage -in[2-3]_crit_alarm Output voltage critical high alarm -in[2-3]_highest Highest output voltage -in[2-3]_lowest Lowest output voltage -in[2-3]_max Maximum output voltage -in[2-3]_max_alarm Output voltage high alarm -in[2-3]_min Minimum output voltage -in[2-3]_min_alarm Output voltage low alarm - -power1_label "pin" -power1_input Measured input power -power1_alarm Input power high alarm -power1_max Input power limit - -power[2-3]_label "pout[1-2]" -power[2-3]_input Measured output power -power[2-3]_max Output power limit -power[2-3]_max_alarm Output power high alarm - -temp[1-2]_input Measured temperature -temp[1-2]_crit Critical high temperature -temp[1-2]_crit_alarm Chip temperature critical high alarm -temp[1-2]_highest Highest temperature -temp[1-2]_lowest Lowest temperature -temp[1-2]_max Maximum temperature -temp[1-2]_max_alarm Chip temperature high alarm -======================= ======================================================= diff --git a/Documentation/hwmon/ir35221.rst b/Documentation/hwmon/ir35221.rst new file mode 100644 index 000000000000..a83922e5ccb5 --- /dev/null +++ b/Documentation/hwmon/ir35221.rst @@ -0,0 +1,92 @@ +Kernel driver ir35221 +===================== + +Supported chips: + * Infineon IR35221 + + Prefix: 'ir35221' + + Addresses scanned: - + + Datasheet: Datasheet is not publicly available. + +Author: Samuel Mendoza-Jonas + + +Description +----------- + +IR35221 is a Digital DC-DC Multiphase Converter + + +Usage Notes +----------- + +This driver does not probe for PMBus devices. You will have to instantiate +devices explicitly. + +Example: the following commands will load the driver for an IR35221 +at address 0x70 on I2C bus #4:: + + # modprobe ir35221 + # echo ir35221 0x70 > /sys/bus/i2c/devices/i2c-4/new_device + + +Sysfs attributes +---------------- + +======================= ======================================================= +curr1_label "iin" +curr1_input Measured input current +curr1_max Maximum current +curr1_max_alarm Current high alarm + +curr[2-3]_label "iout[1-2]" +curr[2-3]_input Measured output current +curr[2-3]_crit Critical maximum current +curr[2-3]_crit_alarm Current critical high alarm +curr[2-3]_highest Highest output current +curr[2-3]_lowest Lowest output current +curr[2-3]_max Maximum current +curr[2-3]_max_alarm Current high alarm + +in1_label "vin" +in1_input Measured input voltage +in1_crit Critical maximum input voltage +in1_crit_alarm Input voltage critical high alarm +in1_highest Highest input voltage +in1_lowest Lowest input voltage +in1_min Minimum input voltage +in1_min_alarm Input voltage low alarm + +in[2-3]_label "vout[1-2]" +in[2-3]_input Measured output voltage +in[2-3]_lcrit Critical minimum output voltage +in[2-3]_lcrit_alarm Output voltage critical low alarm +in[2-3]_crit Critical maximum output voltage +in[2-3]_crit_alarm Output voltage critical high alarm +in[2-3]_highest Highest output voltage +in[2-3]_lowest Lowest output voltage +in[2-3]_max Maximum output voltage +in[2-3]_max_alarm Output voltage high alarm +in[2-3]_min Minimum output voltage +in[2-3]_min_alarm Output voltage low alarm + +power1_label "pin" +power1_input Measured input power +power1_alarm Input power high alarm +power1_max Input power limit + +power[2-3]_label "pout[1-2]" +power[2-3]_input Measured output power +power[2-3]_max Output power limit +power[2-3]_max_alarm Output power high alarm + +temp[1-2]_input Measured temperature +temp[1-2]_crit Critical high temperature +temp[1-2]_crit_alarm Chip temperature critical high alarm +temp[1-2]_highest Highest temperature +temp[1-2]_lowest Lowest temperature +temp[1-2]_max Maximum temperature +temp[1-2]_max_alarm Chip temperature high alarm +======================= ======================================================= diff --git a/Documentation/hwmon/it87 b/Documentation/hwmon/it87 deleted file mode 100644 index 2d83f23bee93..000000000000 --- a/Documentation/hwmon/it87 +++ /dev/null @@ -1,348 +0,0 @@ -Kernel driver it87 -================== - -Supported chips: - - * IT8603E/IT8623E - - Prefix: 'it8603' - - Addresses scanned: from Super I/O config space (8 I/O ports) - - Datasheet: Not publicly available - - * IT8620E - - Prefix: 'it8620' - - Addresses scanned: from Super I/O config space (8 I/O ports) - - * IT8628E - - Prefix: 'it8628' - - Addresses scanned: from Super I/O config space (8 I/O ports) - - Datasheet: Not publicly available - - * IT8705F - - Prefix: 'it87' - - Addresses scanned: from Super I/O config space (8 I/O ports) - - Datasheet: Once publicly available at the ITE website, but no longer - - * IT8712F - - Prefix: 'it8712' - - Addresses scanned: from Super I/O config space (8 I/O ports) - - Datasheet: Once publicly available at the ITE website, but no longer - - * IT8716F/IT8726F - - Prefix: 'it8716' - - Addresses scanned: from Super I/O config space (8 I/O ports) - - Datasheet: Once publicly available at the ITE website, but no longer - - * IT8718F - - Prefix: 'it8718' - - Addresses scanned: from Super I/O config space (8 I/O ports) - - Datasheet: Once publicly available at the ITE website, but no longer - - * IT8720F - - Prefix: 'it8720' - - Addresses scanned: from Super I/O config space (8 I/O ports) - - Datasheet: Not publicly available - - * IT8721F/IT8758E - - Prefix: 'it8721' - - Addresses scanned: from Super I/O config space (8 I/O ports) - - Datasheet: Not publicly available - - * IT8728F - - Prefix: 'it8728' - - Addresses scanned: from Super I/O config space (8 I/O ports) - - Datasheet: Not publicly available - - * IT8732F - - Prefix: 'it8732' - - Addresses scanned: from Super I/O config space (8 I/O ports) - - Datasheet: Not publicly available - - * IT8771E - - Prefix: 'it8771' - - Addresses scanned: from Super I/O config space (8 I/O ports) - - Datasheet: Not publicly available - - * IT8772E - - Prefix: 'it8772' - - Addresses scanned: from Super I/O config space (8 I/O ports) - - Datasheet: Not publicly available - - * IT8781F - - Prefix: 'it8781' - - Addresses scanned: from Super I/O config space (8 I/O ports) - - Datasheet: Not publicly available - - * IT8782F - - Prefix: 'it8782' - - Addresses scanned: from Super I/O config space (8 I/O ports) - - Datasheet: Not publicly available - - * IT8783E/F - - Prefix: 'it8783' - - Addresses scanned: from Super I/O config space (8 I/O ports) - - Datasheet: Not publicly available - - * IT8786E - - Prefix: 'it8786' - - Addresses scanned: from Super I/O config space (8 I/O ports) - - Datasheet: Not publicly available - - * IT8790E - - Prefix: 'it8790' - - Addresses scanned: from Super I/O config space (8 I/O ports) - - Datasheet: Not publicly available - - * SiS950 [clone of IT8705F] - - Prefix: 'it87' - - Addresses scanned: from Super I/O config space (8 I/O ports) - - Datasheet: No longer be available - - -Authors: - - Christophe Gauthron - - Jean Delvare - - -Module Parameters ------------------ - -* update_vbat: int - 0 if vbat should report power on value, 1 if vbat should be updated after - each read. Default is 0. On some boards the battery voltage is provided - by either the battery or the onboard power supply. Only the first reading - at power on will be the actual battery voltage (which the chip does - automatically). On other boards the battery voltage is always fed to - the chip so can be read at any time. Excessive reading may decrease - battery life but no information is given in the datasheet. - -* fix_pwm_polarity int - Force PWM polarity to active high (DANGEROUS). Some chips are - misconfigured by BIOS - PWM values would be inverted. This option tries - to fix this. Please contact your BIOS manufacturer and ask him for fix. - - -Hardware Interfaces -------------------- - -All the chips supported by this driver are LPC Super-I/O chips, accessed -through the LPC bus (ISA-like I/O ports). The IT8712F additionally has an -SMBus interface to the hardware monitoring functions. This driver no -longer supports this interface though, as it is slower and less reliable -than the ISA access, and was only available on a small number of -motherboard models. - - -Description ------------ - -This driver implements support for the IT8603E, IT8620E, IT8623E, IT8628E, -IT8705F, IT8712F, IT8716F, IT8718F, IT8720F, IT8721F, IT8726F, IT8728F, IT8732F, -IT8758E, IT8771E, IT8772E, IT8781F, IT8782F, IT8783E/F, IT8786E, IT8790E, and -SiS950 chips. - -These chips are 'Super I/O chips', supporting floppy disks, infrared ports, -joysticks and other miscellaneous stuff. For hardware monitoring, they -include an 'environment controller' with 3 temperature sensors, 3 fan -rotation speed sensors, 8 voltage sensors, associated alarms, and chassis -intrusion detection. - -The IT8712F and IT8716F additionally feature VID inputs, used to report -the Vcore voltage of the processor. The early IT8712F have 5 VID pins, -the IT8716F and late IT8712F have 6. They are shared with other functions -though, so the functionality may not be available on a given system. - -The IT8718F and IT8720F also features VID inputs (up to 8 pins) but the value -is stored in the Super-I/O configuration space. Due to technical limitations, -this value can currently only be read once at initialization time, so -the driver won't notice and report changes in the VID value. The two -upper VID bits share their pins with voltage inputs (in5 and in6) so you -can't have both on a given board. - -The IT8716F, IT8718F, IT8720F, IT8721F/IT8758E and later IT8712F revisions -have support for 2 additional fans. The additional fans are supported by the -driver. - -The IT8716F, IT8718F, IT8720F, IT8721F/IT8758E, IT8732F, IT8781F, IT8782F, -IT8783E/F, and late IT8712F and IT8705F also have optional 16-bit tachometer -counters for fans 1 to 3. This is better (no more fan clock divider mess) but -not compatible with the older chips and revisions. The 16-bit tachometer mode -is enabled by the driver when one of the above chips is detected. - -The IT8726F is just bit enhanced IT8716F with additional hardware -for AMD power sequencing. Therefore the chip will appear as IT8716F -to userspace applications. - -The IT8728F, IT8771E, and IT8772E are considered compatible with the IT8721F, -until a datasheet becomes available (hopefully.) - -The IT8603E/IT8623E is a custom design, hardware monitoring part is similar to -IT8728F. It only supports 3 fans, 16-bit fan mode, and the full speed mode -of the fan is not supported (value 0 of pwmX_enable). - -The IT8620E and IT8628E are custom designs, hardware monitoring part is similar -to IT8728F. It only supports 16-bit fan mode. Both chips support up to 6 fans. - -The IT8790E supports up to 3 fans. 16-bit fan mode is always enabled. - -The IT8732F supports a closed-loop mode for fan control, but this is not -currently implemented by the driver. - -Temperatures are measured in degrees Celsius. An alarm is triggered once -when the Overtemperature Shutdown limit is crossed. - -Fan rotation speeds are reported in RPM (rotations per minute). An alarm is -triggered if the rotation speed has dropped below a programmable limit. When -16-bit tachometer counters aren't used, fan readings can be divided by -a programmable divider (1, 2, 4 or 8) to give the readings more range or -accuracy. With a divider of 2, the lowest representable value is around -2600 RPM. Not all RPM values can accurately be represented, so some rounding -is done. - -Voltage sensors (also known as IN sensors) report their values in volts. An -alarm is triggered if the voltage has crossed a programmable minimum or -maximum limit. Note that minimum in this case always means 'closest to -zero'; this is important for negative voltage measurements. On most chips, all -voltage inputs can measure voltages between 0 and 4.08 volts, with a resolution -of 0.016 volt. IT8603E, IT8721F/IT8758E and IT8728F can measure between 0 and -3.06 volts, with a resolution of 0.012 volt. IT8732F can measure between 0 and -2.8 volts with a resolution of 0.0109 volt. The battery voltage in8 does not -have limit registers. - -On the IT8603E, IT8620E, IT8628E, IT8721F/IT8758E, IT8732F, IT8781F, IT8782F, -and IT8783E/F, some voltage inputs are internal and scaled inside the chip: -* in3 (optional) -* in7 (optional for IT8781F, IT8782F, and IT8783E/F) -* in8 (always) -* in9 (relevant for IT8603E only) -The driver handles this transparently so user-space doesn't have to care. - -The VID lines (IT8712F/IT8716F/IT8718F/IT8720F) encode the core voltage value: -the voltage level your processor should work with. This is hardcoded by -the mainboard and/or processor itself. It is a value in volts. - -If an alarm triggers, it will remain triggered until the hardware register -is read at least once. This means that the cause for the alarm may already -have disappeared! Note that in the current implementation, all hardware -registers are read whenever any data is read (unless it is less than 1.5 -seconds since the last update). This means that you can easily miss -once-only alarms. - -Out-of-limit readings can also result in beeping, if the chip is properly -wired and configured. Beeping can be enabled or disabled per sensor type -(temperatures, voltages and fans.) - -The IT87xx only updates its values each 1.5 seconds; reading it more often -will do no harm, but will return 'old' values. - -To change sensor N to a thermistor, 'echo 4 > tempN_type' where N is 1, 2, -or 3. To change sensor N to a thermal diode, 'echo 3 > tempN_type'. -Give 0 for unused sensor. Any other value is invalid. To configure this at -startup, consult lm_sensors's /etc/sensors.conf. (4 = thermistor; -3 = thermal diode) - - -Fan speed control ------------------ - -The fan speed control features are limited to manual PWM mode. Automatic -"Smart Guardian" mode control handling is only implemented for older chips -(see below.) However if you want to go for "manual mode" just write 1 to -pwmN_enable. - -If you are only able to control the fan speed with very small PWM values, -try lowering the PWM base frequency (pwm1_freq). Depending on the fan, -it may give you a somewhat greater control range. The same frequency is -used to drive all fan outputs, which is why pwm2_freq and pwm3_freq are -read-only. - - -Automatic fan speed control (old interface) -------------------------------------------- - -The driver supports the old interface to automatic fan speed control -which is implemented by IT8705F chips up to revision F and IT8712F -chips up to revision G. - -This interface implements 4 temperature vs. PWM output trip points. -The PWM output of trip point 4 is always the maximum value (fan running -at full speed) while the PWM output of the other 3 trip points can be -freely chosen. The temperature of all 4 trip points can be freely chosen. -Additionally, trip point 1 has an hysteresis temperature attached, to -prevent fast switching between fan on and off. - -The chip automatically computes the PWM output value based on the input -temperature, based on this simple rule: if the temperature value is -between trip point N and trip point N+1 then the PWM output value is -the one of trip point N. The automatic control mode is less flexible -than the manual control mode, but it reacts faster, is more robust and -doesn't use CPU cycles. - -Trip points must be set properly before switching to automatic fan speed -control mode. The driver will perform basic integrity checks before -actually switching to automatic control mode. - - -Temperature offset attributes ------------------------------ - -The driver supports temp[1-3]_offset sysfs attributes to adjust the reported -temperature for thermal diodes or diode-connected thermal transistors. -If a temperature sensor is configured for thermistors, the attribute values -are ignored. If the thermal sensor type is Intel PECI, the temperature offset -must be programmed to the critical CPU temperature. diff --git a/Documentation/hwmon/it87.rst b/Documentation/hwmon/it87.rst new file mode 100644 index 000000000000..2d83f23bee93 --- /dev/null +++ b/Documentation/hwmon/it87.rst @@ -0,0 +1,348 @@ +Kernel driver it87 +================== + +Supported chips: + + * IT8603E/IT8623E + + Prefix: 'it8603' + + Addresses scanned: from Super I/O config space (8 I/O ports) + + Datasheet: Not publicly available + + * IT8620E + + Prefix: 'it8620' + + Addresses scanned: from Super I/O config space (8 I/O ports) + + * IT8628E + + Prefix: 'it8628' + + Addresses scanned: from Super I/O config space (8 I/O ports) + + Datasheet: Not publicly available + + * IT8705F + + Prefix: 'it87' + + Addresses scanned: from Super I/O config space (8 I/O ports) + + Datasheet: Once publicly available at the ITE website, but no longer + + * IT8712F + + Prefix: 'it8712' + + Addresses scanned: from Super I/O config space (8 I/O ports) + + Datasheet: Once publicly available at the ITE website, but no longer + + * IT8716F/IT8726F + + Prefix: 'it8716' + + Addresses scanned: from Super I/O config space (8 I/O ports) + + Datasheet: Once publicly available at the ITE website, but no longer + + * IT8718F + + Prefix: 'it8718' + + Addresses scanned: from Super I/O config space (8 I/O ports) + + Datasheet: Once publicly available at the ITE website, but no longer + + * IT8720F + + Prefix: 'it8720' + + Addresses scanned: from Super I/O config space (8 I/O ports) + + Datasheet: Not publicly available + + * IT8721F/IT8758E + + Prefix: 'it8721' + + Addresses scanned: from Super I/O config space (8 I/O ports) + + Datasheet: Not publicly available + + * IT8728F + + Prefix: 'it8728' + + Addresses scanned: from Super I/O config space (8 I/O ports) + + Datasheet: Not publicly available + + * IT8732F + + Prefix: 'it8732' + + Addresses scanned: from Super I/O config space (8 I/O ports) + + Datasheet: Not publicly available + + * IT8771E + + Prefix: 'it8771' + + Addresses scanned: from Super I/O config space (8 I/O ports) + + Datasheet: Not publicly available + + * IT8772E + + Prefix: 'it8772' + + Addresses scanned: from Super I/O config space (8 I/O ports) + + Datasheet: Not publicly available + + * IT8781F + + Prefix: 'it8781' + + Addresses scanned: from Super I/O config space (8 I/O ports) + + Datasheet: Not publicly available + + * IT8782F + + Prefix: 'it8782' + + Addresses scanned: from Super I/O config space (8 I/O ports) + + Datasheet: Not publicly available + + * IT8783E/F + + Prefix: 'it8783' + + Addresses scanned: from Super I/O config space (8 I/O ports) + + Datasheet: Not publicly available + + * IT8786E + + Prefix: 'it8786' + + Addresses scanned: from Super I/O config space (8 I/O ports) + + Datasheet: Not publicly available + + * IT8790E + + Prefix: 'it8790' + + Addresses scanned: from Super I/O config space (8 I/O ports) + + Datasheet: Not publicly available + + * SiS950 [clone of IT8705F] + + Prefix: 'it87' + + Addresses scanned: from Super I/O config space (8 I/O ports) + + Datasheet: No longer be available + + +Authors: + - Christophe Gauthron + - Jean Delvare + + +Module Parameters +----------------- + +* update_vbat: int + 0 if vbat should report power on value, 1 if vbat should be updated after + each read. Default is 0. On some boards the battery voltage is provided + by either the battery or the onboard power supply. Only the first reading + at power on will be the actual battery voltage (which the chip does + automatically). On other boards the battery voltage is always fed to + the chip so can be read at any time. Excessive reading may decrease + battery life but no information is given in the datasheet. + +* fix_pwm_polarity int + Force PWM polarity to active high (DANGEROUS). Some chips are + misconfigured by BIOS - PWM values would be inverted. This option tries + to fix this. Please contact your BIOS manufacturer and ask him for fix. + + +Hardware Interfaces +------------------- + +All the chips supported by this driver are LPC Super-I/O chips, accessed +through the LPC bus (ISA-like I/O ports). The IT8712F additionally has an +SMBus interface to the hardware monitoring functions. This driver no +longer supports this interface though, as it is slower and less reliable +than the ISA access, and was only available on a small number of +motherboard models. + + +Description +----------- + +This driver implements support for the IT8603E, IT8620E, IT8623E, IT8628E, +IT8705F, IT8712F, IT8716F, IT8718F, IT8720F, IT8721F, IT8726F, IT8728F, IT8732F, +IT8758E, IT8771E, IT8772E, IT8781F, IT8782F, IT8783E/F, IT8786E, IT8790E, and +SiS950 chips. + +These chips are 'Super I/O chips', supporting floppy disks, infrared ports, +joysticks and other miscellaneous stuff. For hardware monitoring, they +include an 'environment controller' with 3 temperature sensors, 3 fan +rotation speed sensors, 8 voltage sensors, associated alarms, and chassis +intrusion detection. + +The IT8712F and IT8716F additionally feature VID inputs, used to report +the Vcore voltage of the processor. The early IT8712F have 5 VID pins, +the IT8716F and late IT8712F have 6. They are shared with other functions +though, so the functionality may not be available on a given system. + +The IT8718F and IT8720F also features VID inputs (up to 8 pins) but the value +is stored in the Super-I/O configuration space. Due to technical limitations, +this value can currently only be read once at initialization time, so +the driver won't notice and report changes in the VID value. The two +upper VID bits share their pins with voltage inputs (in5 and in6) so you +can't have both on a given board. + +The IT8716F, IT8718F, IT8720F, IT8721F/IT8758E and later IT8712F revisions +have support for 2 additional fans. The additional fans are supported by the +driver. + +The IT8716F, IT8718F, IT8720F, IT8721F/IT8758E, IT8732F, IT8781F, IT8782F, +IT8783E/F, and late IT8712F and IT8705F also have optional 16-bit tachometer +counters for fans 1 to 3. This is better (no more fan clock divider mess) but +not compatible with the older chips and revisions. The 16-bit tachometer mode +is enabled by the driver when one of the above chips is detected. + +The IT8726F is just bit enhanced IT8716F with additional hardware +for AMD power sequencing. Therefore the chip will appear as IT8716F +to userspace applications. + +The IT8728F, IT8771E, and IT8772E are considered compatible with the IT8721F, +until a datasheet becomes available (hopefully.) + +The IT8603E/IT8623E is a custom design, hardware monitoring part is similar to +IT8728F. It only supports 3 fans, 16-bit fan mode, and the full speed mode +of the fan is not supported (value 0 of pwmX_enable). + +The IT8620E and IT8628E are custom designs, hardware monitoring part is similar +to IT8728F. It only supports 16-bit fan mode. Both chips support up to 6 fans. + +The IT8790E supports up to 3 fans. 16-bit fan mode is always enabled. + +The IT8732F supports a closed-loop mode for fan control, but this is not +currently implemented by the driver. + +Temperatures are measured in degrees Celsius. An alarm is triggered once +when the Overtemperature Shutdown limit is crossed. + +Fan rotation speeds are reported in RPM (rotations per minute). An alarm is +triggered if the rotation speed has dropped below a programmable limit. When +16-bit tachometer counters aren't used, fan readings can be divided by +a programmable divider (1, 2, 4 or 8) to give the readings more range or +accuracy. With a divider of 2, the lowest representable value is around +2600 RPM. Not all RPM values can accurately be represented, so some rounding +is done. + +Voltage sensors (also known as IN sensors) report their values in volts. An +alarm is triggered if the voltage has crossed a programmable minimum or +maximum limit. Note that minimum in this case always means 'closest to +zero'; this is important for negative voltage measurements. On most chips, all +voltage inputs can measure voltages between 0 and 4.08 volts, with a resolution +of 0.016 volt. IT8603E, IT8721F/IT8758E and IT8728F can measure between 0 and +3.06 volts, with a resolution of 0.012 volt. IT8732F can measure between 0 and +2.8 volts with a resolution of 0.0109 volt. The battery voltage in8 does not +have limit registers. + +On the IT8603E, IT8620E, IT8628E, IT8721F/IT8758E, IT8732F, IT8781F, IT8782F, +and IT8783E/F, some voltage inputs are internal and scaled inside the chip: +* in3 (optional) +* in7 (optional for IT8781F, IT8782F, and IT8783E/F) +* in8 (always) +* in9 (relevant for IT8603E only) +The driver handles this transparently so user-space doesn't have to care. + +The VID lines (IT8712F/IT8716F/IT8718F/IT8720F) encode the core voltage value: +the voltage level your processor should work with. This is hardcoded by +the mainboard and/or processor itself. It is a value in volts. + +If an alarm triggers, it will remain triggered until the hardware register +is read at least once. This means that the cause for the alarm may already +have disappeared! Note that in the current implementation, all hardware +registers are read whenever any data is read (unless it is less than 1.5 +seconds since the last update). This means that you can easily miss +once-only alarms. + +Out-of-limit readings can also result in beeping, if the chip is properly +wired and configured. Beeping can be enabled or disabled per sensor type +(temperatures, voltages and fans.) + +The IT87xx only updates its values each 1.5 seconds; reading it more often +will do no harm, but will return 'old' values. + +To change sensor N to a thermistor, 'echo 4 > tempN_type' where N is 1, 2, +or 3. To change sensor N to a thermal diode, 'echo 3 > tempN_type'. +Give 0 for unused sensor. Any other value is invalid. To configure this at +startup, consult lm_sensors's /etc/sensors.conf. (4 = thermistor; +3 = thermal diode) + + +Fan speed control +----------------- + +The fan speed control features are limited to manual PWM mode. Automatic +"Smart Guardian" mode control handling is only implemented for older chips +(see below.) However if you want to go for "manual mode" just write 1 to +pwmN_enable. + +If you are only able to control the fan speed with very small PWM values, +try lowering the PWM base frequency (pwm1_freq). Depending on the fan, +it may give you a somewhat greater control range. The same frequency is +used to drive all fan outputs, which is why pwm2_freq and pwm3_freq are +read-only. + + +Automatic fan speed control (old interface) +------------------------------------------- + +The driver supports the old interface to automatic fan speed control +which is implemented by IT8705F chips up to revision F and IT8712F +chips up to revision G. + +This interface implements 4 temperature vs. PWM output trip points. +The PWM output of trip point 4 is always the maximum value (fan running +at full speed) while the PWM output of the other 3 trip points can be +freely chosen. The temperature of all 4 trip points can be freely chosen. +Additionally, trip point 1 has an hysteresis temperature attached, to +prevent fast switching between fan on and off. + +The chip automatically computes the PWM output value based on the input +temperature, based on this simple rule: if the temperature value is +between trip point N and trip point N+1 then the PWM output value is +the one of trip point N. The automatic control mode is less flexible +than the manual control mode, but it reacts faster, is more robust and +doesn't use CPU cycles. + +Trip points must be set properly before switching to automatic fan speed +control mode. The driver will perform basic integrity checks before +actually switching to automatic control mode. + + +Temperature offset attributes +----------------------------- + +The driver supports temp[1-3]_offset sysfs attributes to adjust the reported +temperature for thermal diodes or diode-connected thermal transistors. +If a temperature sensor is configured for thermistors, the attribute values +are ignored. If the thermal sensor type is Intel PECI, the temperature offset +must be programmed to the critical CPU temperature. diff --git a/Documentation/hwmon/jc42 b/Documentation/hwmon/jc42 deleted file mode 100644 index 5b14b49bb6f7..000000000000 --- a/Documentation/hwmon/jc42 +++ /dev/null @@ -1,152 +0,0 @@ -Kernel driver jc42 -================== - -Supported chips: - - * Analog Devices ADT7408 - - Datasheets: - - http://www.analog.com/static/imported-files/data_sheets/ADT7408.pdf - - * Atmel AT30TS00, AT30TS002A/B, AT30TSE004A - - Datasheets: - - http://www.atmel.com/Images/doc8585.pdf - - http://www.atmel.com/Images/doc8711.pdf - - http://www.atmel.com/Images/Atmel-8852-SEEPROM-AT30TSE002A-Datasheet.pdf - - http://www.atmel.com/Images/Atmel-8868-DTS-AT30TSE004A-Datasheet.pdf - - * IDT TSE2002B3, TSE2002GB2, TSE2004GB2, TS3000B3, TS3000GB0, TS3000GB2, - - TS3001GB2 - - Datasheets: - - Available from IDT web site - - * Maxim MAX6604 - - Datasheets: - - http://datasheets.maxim-ic.com/en/ds/MAX6604.pdf - - * Microchip MCP9804, MCP9805, MCP9808, MCP98242, MCP98243, MCP98244, MCP9843 - - Datasheets: - - http://ww1.microchip.com/downloads/en/DeviceDoc/22203C.pdf - - http://ww1.microchip.com/downloads/en/DeviceDoc/21977b.pdf - - http://ww1.microchip.com/downloads/en/DeviceDoc/25095A.pdf - - http://ww1.microchip.com/downloads/en/DeviceDoc/21996a.pdf - - http://ww1.microchip.com/downloads/en/DeviceDoc/22153c.pdf - - http://ww1.microchip.com/downloads/en/DeviceDoc/22327A.pdf - - * NXP Semiconductors SE97, SE97B, SE98, SE98A - - Datasheets: - - http://www.nxp.com/documents/data_sheet/SE97.pdf - - http://www.nxp.com/documents/data_sheet/SE97B.pdf - - http://www.nxp.com/documents/data_sheet/SE98.pdf - - http://www.nxp.com/documents/data_sheet/SE98A.pdf - - * ON Semiconductor CAT34TS02, CAT6095 - - Datasheet: - - http://www.onsemi.com/pub_link/Collateral/CAT34TS02-D.PDF - - http://www.onsemi.com/pub/Collateral/CAT6095-D.PDF - - * ST Microelectronics STTS424, STTS424E02, STTS2002, STTS2004, STTS3000 - - Datasheets: - - http://www.st.com/web/en/resource/technical/document/datasheet/CD00157556.pdf - - http://www.st.com/web/en/resource/technical/document/datasheet/CD00157558.pdf - - http://www.st.com/web/en/resource/technical/document/datasheet/CD00266638.pdf - - http://www.st.com/web/en/resource/technical/document/datasheet/CD00225278.pdf - - http://www.st.com/web/en/resource/technical/document/datasheet/DM00076709.pdf - - * JEDEC JC 42.4 compliant temperature sensor chips - - Datasheet: - - http://www.jedec.org/sites/default/files/docs/4_01_04R19.pdf - - - Common for all chips: - - Prefix: 'jc42' - - Addresses scanned: I2C 0x18 - 0x1f - -Author: - Guenter Roeck - - -Description ------------ - -This driver implements support for JEDEC JC 42.4 compliant temperature sensors, -which are used on many DDR3 memory modules for mobile devices and servers. Some -systems use the sensor to prevent memory overheating by automatically throttling -the memory controller. - -The driver auto-detects the chips listed above, but can be manually instantiated -to support other JC 42.4 compliant chips. - -Example: the following will load the driver for a generic JC 42.4 compliant -temperature sensor at address 0x18 on I2C bus #1:: - - # modprobe jc42 - # echo jc42 0x18 > /sys/bus/i2c/devices/i2c-1/new_device - -A JC 42.4 compliant chip supports a single temperature sensor. Minimum, maximum, -and critical temperature can be configured. There are alarms for high, low, -and critical thresholds. - -There is also an hysteresis to control the thresholds for resetting alarms. -Per JC 42.4 specification, the hysteresis threshold can be configured to 0, 1.5, -3.0, and 6.0 degrees C. Configured hysteresis values will be rounded to those -limits. The chip supports only a single register to configure the hysteresis, -which applies to all limits. This register can be written by writing into -temp1_crit_hyst. Other hysteresis attributes are read-only. - -If the BIOS has configured the sensor for automatic temperature management, it -is likely that it has locked the registers, i.e., that the temperature limits -cannot be changed. - -Sysfs entries -------------- - -======================= =========================================== -temp1_input Temperature (RO) -temp1_min Minimum temperature (RO or RW) -temp1_max Maximum temperature (RO or RW) -temp1_crit Critical high temperature (RO or RW) - -temp1_crit_hyst Critical hysteresis temperature (RO or RW) -temp1_max_hyst Maximum hysteresis temperature (RO) - -temp1_min_alarm Temperature low alarm -temp1_max_alarm Temperature high alarm -temp1_crit_alarm Temperature critical alarm -======================= =========================================== diff --git a/Documentation/hwmon/jc42.rst b/Documentation/hwmon/jc42.rst new file mode 100644 index 000000000000..5b14b49bb6f7 --- /dev/null +++ b/Documentation/hwmon/jc42.rst @@ -0,0 +1,152 @@ +Kernel driver jc42 +================== + +Supported chips: + + * Analog Devices ADT7408 + + Datasheets: + + http://www.analog.com/static/imported-files/data_sheets/ADT7408.pdf + + * Atmel AT30TS00, AT30TS002A/B, AT30TSE004A + + Datasheets: + + http://www.atmel.com/Images/doc8585.pdf + + http://www.atmel.com/Images/doc8711.pdf + + http://www.atmel.com/Images/Atmel-8852-SEEPROM-AT30TSE002A-Datasheet.pdf + + http://www.atmel.com/Images/Atmel-8868-DTS-AT30TSE004A-Datasheet.pdf + + * IDT TSE2002B3, TSE2002GB2, TSE2004GB2, TS3000B3, TS3000GB0, TS3000GB2, + + TS3001GB2 + + Datasheets: + + Available from IDT web site + + * Maxim MAX6604 + + Datasheets: + + http://datasheets.maxim-ic.com/en/ds/MAX6604.pdf + + * Microchip MCP9804, MCP9805, MCP9808, MCP98242, MCP98243, MCP98244, MCP9843 + + Datasheets: + + http://ww1.microchip.com/downloads/en/DeviceDoc/22203C.pdf + + http://ww1.microchip.com/downloads/en/DeviceDoc/21977b.pdf + + http://ww1.microchip.com/downloads/en/DeviceDoc/25095A.pdf + + http://ww1.microchip.com/downloads/en/DeviceDoc/21996a.pdf + + http://ww1.microchip.com/downloads/en/DeviceDoc/22153c.pdf + + http://ww1.microchip.com/downloads/en/DeviceDoc/22327A.pdf + + * NXP Semiconductors SE97, SE97B, SE98, SE98A + + Datasheets: + + http://www.nxp.com/documents/data_sheet/SE97.pdf + + http://www.nxp.com/documents/data_sheet/SE97B.pdf + + http://www.nxp.com/documents/data_sheet/SE98.pdf + + http://www.nxp.com/documents/data_sheet/SE98A.pdf + + * ON Semiconductor CAT34TS02, CAT6095 + + Datasheet: + + http://www.onsemi.com/pub_link/Collateral/CAT34TS02-D.PDF + + http://www.onsemi.com/pub/Collateral/CAT6095-D.PDF + + * ST Microelectronics STTS424, STTS424E02, STTS2002, STTS2004, STTS3000 + + Datasheets: + + http://www.st.com/web/en/resource/technical/document/datasheet/CD00157556.pdf + + http://www.st.com/web/en/resource/technical/document/datasheet/CD00157558.pdf + + http://www.st.com/web/en/resource/technical/document/datasheet/CD00266638.pdf + + http://www.st.com/web/en/resource/technical/document/datasheet/CD00225278.pdf + + http://www.st.com/web/en/resource/technical/document/datasheet/DM00076709.pdf + + * JEDEC JC 42.4 compliant temperature sensor chips + + Datasheet: + + http://www.jedec.org/sites/default/files/docs/4_01_04R19.pdf + + + Common for all chips: + + Prefix: 'jc42' + + Addresses scanned: I2C 0x18 - 0x1f + +Author: + Guenter Roeck + + +Description +----------- + +This driver implements support for JEDEC JC 42.4 compliant temperature sensors, +which are used on many DDR3 memory modules for mobile devices and servers. Some +systems use the sensor to prevent memory overheating by automatically throttling +the memory controller. + +The driver auto-detects the chips listed above, but can be manually instantiated +to support other JC 42.4 compliant chips. + +Example: the following will load the driver for a generic JC 42.4 compliant +temperature sensor at address 0x18 on I2C bus #1:: + + # modprobe jc42 + # echo jc42 0x18 > /sys/bus/i2c/devices/i2c-1/new_device + +A JC 42.4 compliant chip supports a single temperature sensor. Minimum, maximum, +and critical temperature can be configured. There are alarms for high, low, +and critical thresholds. + +There is also an hysteresis to control the thresholds for resetting alarms. +Per JC 42.4 specification, the hysteresis threshold can be configured to 0, 1.5, +3.0, and 6.0 degrees C. Configured hysteresis values will be rounded to those +limits. The chip supports only a single register to configure the hysteresis, +which applies to all limits. This register can be written by writing into +temp1_crit_hyst. Other hysteresis attributes are read-only. + +If the BIOS has configured the sensor for automatic temperature management, it +is likely that it has locked the registers, i.e., that the temperature limits +cannot be changed. + +Sysfs entries +------------- + +======================= =========================================== +temp1_input Temperature (RO) +temp1_min Minimum temperature (RO or RW) +temp1_max Maximum temperature (RO or RW) +temp1_crit Critical high temperature (RO or RW) + +temp1_crit_hyst Critical hysteresis temperature (RO or RW) +temp1_max_hyst Maximum hysteresis temperature (RO) + +temp1_min_alarm Temperature low alarm +temp1_max_alarm Temperature high alarm +temp1_crit_alarm Temperature critical alarm +======================= =========================================== diff --git a/Documentation/hwmon/k10temp b/Documentation/hwmon/k10temp deleted file mode 100644 index 12a86ba17de9..000000000000 --- a/Documentation/hwmon/k10temp +++ /dev/null @@ -1,112 +0,0 @@ -Kernel driver k10temp -===================== - -Supported chips: - -* AMD Family 10h processors: - - Socket F: Quad-Core/Six-Core/Embedded Opteron (but see below) - - Socket AM2+: Quad-Core Opteron, Phenom (II) X3/X4, Athlon X2 (but see below) - - Socket AM3: Quad-Core Opteron, Athlon/Phenom II X2/X3/X4, Sempron II - - Socket S1G3: Athlon II, Sempron, Turion II - -* AMD Family 11h processors: - - Socket S1G2: Athlon (X2), Sempron (X2), Turion X2 (Ultra) - -* AMD Family 12h processors: "Llano" (E2/A4/A6/A8-Series) - -* AMD Family 14h processors: "Brazos" (C/E/G/Z-Series) - -* AMD Family 15h processors: "Bulldozer" (FX-Series), "Trinity", "Kaveri", "Carrizo" - -* AMD Family 16h processors: "Kabini", "Mullins" - - Prefix: 'k10temp' - - Addresses scanned: PCI space - - Datasheets: - - BIOS and Kernel Developer's Guide (BKDG) For AMD Family 10h Processors: - - http://support.amd.com/us/Processor_TechDocs/31116.pdf - - BIOS and Kernel Developer's Guide (BKDG) for AMD Family 11h Processors: - - http://support.amd.com/us/Processor_TechDocs/41256.pdf - - BIOS and Kernel Developer's Guide (BKDG) for AMD Family 12h Processors: - - http://support.amd.com/us/Processor_TechDocs/41131.pdf - - BIOS and Kernel Developer's Guide (BKDG) for AMD Family 14h Models 00h-0Fh Processors: - - http://support.amd.com/us/Processor_TechDocs/43170.pdf - - Revision Guide for AMD Family 10h Processors: - - http://support.amd.com/us/Processor_TechDocs/41322.pdf - - Revision Guide for AMD Family 11h Processors: - - http://support.amd.com/us/Processor_TechDocs/41788.pdf - - Revision Guide for AMD Family 12h Processors: - - http://support.amd.com/us/Processor_TechDocs/44739.pdf - - Revision Guide for AMD Family 14h Models 00h-0Fh Processors: - - http://support.amd.com/us/Processor_TechDocs/47534.pdf - - AMD Family 11h Processor Power and Thermal Data Sheet for Notebooks: - - http://support.amd.com/us/Processor_TechDocs/43373.pdf - - AMD Family 10h Server and Workstation Processor Power and Thermal Data Sheet: - - http://support.amd.com/us/Processor_TechDocs/43374.pdf - - AMD Family 10h Desktop Processor Power and Thermal Data Sheet: - - http://support.amd.com/us/Processor_TechDocs/43375.pdf - -Author: Clemens Ladisch - -Description ------------ - -This driver permits reading of the internal temperature sensor of AMD -Family 10h/11h/12h/14h/15h/16h processors. - -All these processors have a sensor, but on those for Socket F or AM2+, -the sensor may return inconsistent values (erratum 319). The driver -will refuse to load on these revisions unless you specify the "force=1" -module parameter. - -Due to technical reasons, the driver can detect only the mainboard's -socket type, not the processor's actual capabilities. Therefore, if you -are using an AM3 processor on an AM2+ mainboard, you can safely use the -"force=1" parameter. - -There is one temperature measurement value, available as temp1_input in -sysfs. It is measured in degrees Celsius with a resolution of 1/8th degree. -Please note that it is defined as a relative value; to quote the AMD manual:: - - Tctl is the processor temperature control value, used by the platform to - control cooling systems. Tctl is a non-physical temperature on an - arbitrary scale measured in degrees. It does _not_ represent an actual - physical temperature like die or case temperature. Instead, it specifies - the processor temperature relative to the point at which the system must - supply the maximum cooling for the processor's specified maximum case - temperature and maximum thermal power dissipation. - -The maximum value for Tctl is available in the file temp1_max. - -If the BIOS has enabled hardware temperature control, the threshold at -which the processor will throttle itself to avoid damage is available in -temp1_crit and temp1_crit_hyst. diff --git a/Documentation/hwmon/k10temp.rst b/Documentation/hwmon/k10temp.rst new file mode 100644 index 000000000000..12a86ba17de9 --- /dev/null +++ b/Documentation/hwmon/k10temp.rst @@ -0,0 +1,112 @@ +Kernel driver k10temp +===================== + +Supported chips: + +* AMD Family 10h processors: + + Socket F: Quad-Core/Six-Core/Embedded Opteron (but see below) + + Socket AM2+: Quad-Core Opteron, Phenom (II) X3/X4, Athlon X2 (but see below) + + Socket AM3: Quad-Core Opteron, Athlon/Phenom II X2/X3/X4, Sempron II + + Socket S1G3: Athlon II, Sempron, Turion II + +* AMD Family 11h processors: + + Socket S1G2: Athlon (X2), Sempron (X2), Turion X2 (Ultra) + +* AMD Family 12h processors: "Llano" (E2/A4/A6/A8-Series) + +* AMD Family 14h processors: "Brazos" (C/E/G/Z-Series) + +* AMD Family 15h processors: "Bulldozer" (FX-Series), "Trinity", "Kaveri", "Carrizo" + +* AMD Family 16h processors: "Kabini", "Mullins" + + Prefix: 'k10temp' + + Addresses scanned: PCI space + + Datasheets: + + BIOS and Kernel Developer's Guide (BKDG) For AMD Family 10h Processors: + + http://support.amd.com/us/Processor_TechDocs/31116.pdf + + BIOS and Kernel Developer's Guide (BKDG) for AMD Family 11h Processors: + + http://support.amd.com/us/Processor_TechDocs/41256.pdf + + BIOS and Kernel Developer's Guide (BKDG) for AMD Family 12h Processors: + + http://support.amd.com/us/Processor_TechDocs/41131.pdf + + BIOS and Kernel Developer's Guide (BKDG) for AMD Family 14h Models 00h-0Fh Processors: + + http://support.amd.com/us/Processor_TechDocs/43170.pdf + + Revision Guide for AMD Family 10h Processors: + + http://support.amd.com/us/Processor_TechDocs/41322.pdf + + Revision Guide for AMD Family 11h Processors: + + http://support.amd.com/us/Processor_TechDocs/41788.pdf + + Revision Guide for AMD Family 12h Processors: + + http://support.amd.com/us/Processor_TechDocs/44739.pdf + + Revision Guide for AMD Family 14h Models 00h-0Fh Processors: + + http://support.amd.com/us/Processor_TechDocs/47534.pdf + + AMD Family 11h Processor Power and Thermal Data Sheet for Notebooks: + + http://support.amd.com/us/Processor_TechDocs/43373.pdf + + AMD Family 10h Server and Workstation Processor Power and Thermal Data Sheet: + + http://support.amd.com/us/Processor_TechDocs/43374.pdf + + AMD Family 10h Desktop Processor Power and Thermal Data Sheet: + + http://support.amd.com/us/Processor_TechDocs/43375.pdf + +Author: Clemens Ladisch + +Description +----------- + +This driver permits reading of the internal temperature sensor of AMD +Family 10h/11h/12h/14h/15h/16h processors. + +All these processors have a sensor, but on those for Socket F or AM2+, +the sensor may return inconsistent values (erratum 319). The driver +will refuse to load on these revisions unless you specify the "force=1" +module parameter. + +Due to technical reasons, the driver can detect only the mainboard's +socket type, not the processor's actual capabilities. Therefore, if you +are using an AM3 processor on an AM2+ mainboard, you can safely use the +"force=1" parameter. + +There is one temperature measurement value, available as temp1_input in +sysfs. It is measured in degrees Celsius with a resolution of 1/8th degree. +Please note that it is defined as a relative value; to quote the AMD manual:: + + Tctl is the processor temperature control value, used by the platform to + control cooling systems. Tctl is a non-physical temperature on an + arbitrary scale measured in degrees. It does _not_ represent an actual + physical temperature like die or case temperature. Instead, it specifies + the processor temperature relative to the point at which the system must + supply the maximum cooling for the processor's specified maximum case + temperature and maximum thermal power dissipation. + +The maximum value for Tctl is available in the file temp1_max. + +If the BIOS has enabled hardware temperature control, the threshold at +which the processor will throttle itself to avoid damage is available in +temp1_crit and temp1_crit_hyst. diff --git a/Documentation/hwmon/k8temp b/Documentation/hwmon/k8temp deleted file mode 100644 index 72da12aa17e5..000000000000 --- a/Documentation/hwmon/k8temp +++ /dev/null @@ -1,62 +0,0 @@ -Kernel driver k8temp -==================== - -Supported chips: - - * AMD Athlon64/FX or Opteron CPUs - - Prefix: 'k8temp' - - Addresses scanned: PCI space - - Datasheet: http://support.amd.com/us/Processor_TechDocs/32559.pdf - -Author: Rudolf Marek - -Contact: Rudolf Marek - -Description ------------ - -This driver permits reading temperature sensor(s) embedded inside AMD K8 -family CPUs (Athlon64/FX, Opteron). Official documentation says that it works -from revision F of K8 core, but in fact it seems to be implemented for all -revisions of K8 except the first two revisions (SH-B0 and SH-B3). - -Please note that you will need at least lm-sensors 2.10.1 for proper userspace -support. - -There can be up to four temperature sensors inside single CPU. The driver -will auto-detect the sensors and will display only temperatures from -implemented sensors. - -Mapping of /sys files is as follows: - -============= =================================== -temp1_input temperature of Core 0 and "place" 0 -temp2_input temperature of Core 0 and "place" 1 -temp3_input temperature of Core 1 and "place" 0 -temp4_input temperature of Core 1 and "place" 1 -============= =================================== - -Temperatures are measured in degrees Celsius and measurement resolution is -1 degree C. It is expected that future CPU will have better resolution. The -temperature is updated once a second. Valid temperatures are from -49 to -206 degrees C. - -Temperature known as TCaseMax was specified for processors up to revision E. -This temperature is defined as temperature between heat-spreader and CPU -case, so the internal CPU temperature supplied by this driver can be higher. -There is no easy way how to measure the temperature which will correlate -with TCaseMax temperature. - -For newer revisions of CPU (rev F, socket AM2) there is a mathematically -computed temperature called TControl, which must be lower than TControlMax. - -The relationship is following: - - temp1_input - TjOffset*2 < TControlMax, - -TjOffset is not yet exported by the driver, TControlMax is usually -70 degrees C. The rule of the thumb -> CPU temperature should not cross -60 degrees C too much. diff --git a/Documentation/hwmon/k8temp.rst b/Documentation/hwmon/k8temp.rst new file mode 100644 index 000000000000..72da12aa17e5 --- /dev/null +++ b/Documentation/hwmon/k8temp.rst @@ -0,0 +1,62 @@ +Kernel driver k8temp +==================== + +Supported chips: + + * AMD Athlon64/FX or Opteron CPUs + + Prefix: 'k8temp' + + Addresses scanned: PCI space + + Datasheet: http://support.amd.com/us/Processor_TechDocs/32559.pdf + +Author: Rudolf Marek + +Contact: Rudolf Marek + +Description +----------- + +This driver permits reading temperature sensor(s) embedded inside AMD K8 +family CPUs (Athlon64/FX, Opteron). Official documentation says that it works +from revision F of K8 core, but in fact it seems to be implemented for all +revisions of K8 except the first two revisions (SH-B0 and SH-B3). + +Please note that you will need at least lm-sensors 2.10.1 for proper userspace +support. + +There can be up to four temperature sensors inside single CPU. The driver +will auto-detect the sensors and will display only temperatures from +implemented sensors. + +Mapping of /sys files is as follows: + +============= =================================== +temp1_input temperature of Core 0 and "place" 0 +temp2_input temperature of Core 0 and "place" 1 +temp3_input temperature of Core 1 and "place" 0 +temp4_input temperature of Core 1 and "place" 1 +============= =================================== + +Temperatures are measured in degrees Celsius and measurement resolution is +1 degree C. It is expected that future CPU will have better resolution. The +temperature is updated once a second. Valid temperatures are from -49 to +206 degrees C. + +Temperature known as TCaseMax was specified for processors up to revision E. +This temperature is defined as temperature between heat-spreader and CPU +case, so the internal CPU temperature supplied by this driver can be higher. +There is no easy way how to measure the temperature which will correlate +with TCaseMax temperature. + +For newer revisions of CPU (rev F, socket AM2) there is a mathematically +computed temperature called TControl, which must be lower than TControlMax. + +The relationship is following: + + temp1_input - TjOffset*2 < TControlMax, + +TjOffset is not yet exported by the driver, TControlMax is usually +70 degrees C. The rule of the thumb -> CPU temperature should not cross +60 degrees C too much. diff --git a/Documentation/hwmon/lineage-pem b/Documentation/hwmon/lineage-pem deleted file mode 100644 index 10c271dc20e8..000000000000 --- a/Documentation/hwmon/lineage-pem +++ /dev/null @@ -1,85 +0,0 @@ -Kernel driver lineage-pem -========================= - -Supported devices: - - * Lineage Compact Power Line Power Entry Modules - - Prefix: 'lineage-pem' - - Addresses scanned: - - - Documentation: - - http://www.lineagepower.com/oem/pdf/CPLI2C.pdf - -Author: Guenter Roeck - - -Description ------------ - -This driver supports various Lineage Compact Power Line DC/DC and AC/DC -converters such as CP1800, CP2000AC, CP2000DC, CP2100DC, and others. - -Lineage CPL power entry modules are nominally PMBus compliant. However, most -standard PMBus commands are not supported. Specifically, all hardware monitoring -and status reporting commands are non-standard. For this reason, a standard -PMBus driver can not be used. - - -Usage Notes ------------ - -This driver does not probe for Lineage CPL devices, since there is no register -which can be safely used to identify the chip. You will have to instantiate -the devices explicitly. - -Example: the following will load the driver for a Lineage PEM at address 0x40 -on I2C bus #1:: - - $ modprobe lineage-pem - $ echo lineage-pem 0x40 > /sys/bus/i2c/devices/i2c-1/new_device - -All Lineage CPL power entry modules have a built-in I2C bus master selector -(PCA9541). To ensure device access, this driver should only be used as client -driver to the pca9541 I2C master selector driver. - - -Sysfs entries -------------- - -All Lineage CPL devices report output voltage and device temperature as well as -alarms for output voltage, temperature, input voltage, input current, input power, -and fan status. - -Input voltage, input current, input power, and fan speed measurement is only -supported on newer devices. The driver detects if those attributes are supported, -and only creates respective sysfs entries if they are. - -======================= =============================== -in1_input Output voltage (mV) -in1_min_alarm Output undervoltage alarm -in1_max_alarm Output overvoltage alarm -in1_crit Output voltage critical alarm - -in2_input Input voltage (mV, optional) -in2_alarm Input voltage alarm - -curr1_input Input current (mA, optional) -curr1_alarm Input overcurrent alarm - -power1_input Input power (uW, optional) -power1_alarm Input power alarm - -fan1_input Fan 1 speed (rpm, optional) -fan2_input Fan 2 speed (rpm, optional) -fan3_input Fan 3 speed (rpm, optional) - -temp1_input -temp1_max -temp1_crit -temp1_alarm -temp1_crit_alarm -temp1_fault -======================= =============================== diff --git a/Documentation/hwmon/lineage-pem.rst b/Documentation/hwmon/lineage-pem.rst new file mode 100644 index 000000000000..10c271dc20e8 --- /dev/null +++ b/Documentation/hwmon/lineage-pem.rst @@ -0,0 +1,85 @@ +Kernel driver lineage-pem +========================= + +Supported devices: + + * Lineage Compact Power Line Power Entry Modules + + Prefix: 'lineage-pem' + + Addresses scanned: - + + Documentation: + + http://www.lineagepower.com/oem/pdf/CPLI2C.pdf + +Author: Guenter Roeck + + +Description +----------- + +This driver supports various Lineage Compact Power Line DC/DC and AC/DC +converters such as CP1800, CP2000AC, CP2000DC, CP2100DC, and others. + +Lineage CPL power entry modules are nominally PMBus compliant. However, most +standard PMBus commands are not supported. Specifically, all hardware monitoring +and status reporting commands are non-standard. For this reason, a standard +PMBus driver can not be used. + + +Usage Notes +----------- + +This driver does not probe for Lineage CPL devices, since there is no register +which can be safely used to identify the chip. You will have to instantiate +the devices explicitly. + +Example: the following will load the driver for a Lineage PEM at address 0x40 +on I2C bus #1:: + + $ modprobe lineage-pem + $ echo lineage-pem 0x40 > /sys/bus/i2c/devices/i2c-1/new_device + +All Lineage CPL power entry modules have a built-in I2C bus master selector +(PCA9541). To ensure device access, this driver should only be used as client +driver to the pca9541 I2C master selector driver. + + +Sysfs entries +------------- + +All Lineage CPL devices report output voltage and device temperature as well as +alarms for output voltage, temperature, input voltage, input current, input power, +and fan status. + +Input voltage, input current, input power, and fan speed measurement is only +supported on newer devices. The driver detects if those attributes are supported, +and only creates respective sysfs entries if they are. + +======================= =============================== +in1_input Output voltage (mV) +in1_min_alarm Output undervoltage alarm +in1_max_alarm Output overvoltage alarm +in1_crit Output voltage critical alarm + +in2_input Input voltage (mV, optional) +in2_alarm Input voltage alarm + +curr1_input Input current (mA, optional) +curr1_alarm Input overcurrent alarm + +power1_input Input power (uW, optional) +power1_alarm Input power alarm + +fan1_input Fan 1 speed (rpm, optional) +fan2_input Fan 2 speed (rpm, optional) +fan3_input Fan 3 speed (rpm, optional) + +temp1_input +temp1_max +temp1_crit +temp1_alarm +temp1_crit_alarm +temp1_fault +======================= =============================== diff --git a/Documentation/hwmon/lm25066 b/Documentation/hwmon/lm25066 deleted file mode 100644 index 60b7f2722931..000000000000 --- a/Documentation/hwmon/lm25066 +++ /dev/null @@ -1,137 +0,0 @@ -Kernel driver lm25066 -===================== - -Supported chips: - - * TI LM25056 - - Prefix: 'lm25056' - - Addresses scanned: - - - Datasheets: - - http://www.ti.com/lit/gpn/lm25056 - - http://www.ti.com/lit/gpn/lm25056a - - * National Semiconductor LM25066 - - Prefix: 'lm25066' - - Addresses scanned: - - - Datasheets: - - http://www.national.com/pf/LM/LM25066.html - - http://www.national.com/pf/LM/LM25066A.html - - * National Semiconductor LM5064 - - Prefix: 'lm5064' - - Addresses scanned: - - - Datasheet: - - http://www.national.com/pf/LM/LM5064.html - - * National Semiconductor LM5066 - - Prefix: 'lm5066' - - Addresses scanned: - - - Datasheet: - - http://www.national.com/pf/LM/LM5066.html - - * Texas Instruments LM5066I - - Prefix: 'lm5066i' - - Addresses scanned: - - - Datasheet: - - http://www.ti.com/product/LM5066I - - -Author: Guenter Roeck - - -Description ------------ - -This driver supports hardware monitoring for National Semiconductor / TI LM25056, -LM25066, LM5064, and LM5066/LM5066I Power Management, Monitoring, -Control, and Protection ICs. - -The driver is a client driver to the core PMBus driver. Please see -Documentation/hwmon/pmbus for details on PMBus client drivers. - - -Usage Notes ------------ - -This driver does not auto-detect devices. You will have to instantiate the -devices explicitly. Please see Documentation/i2c/instantiating-devices for -details. - - -Platform data support ---------------------- - -The driver supports standard PMBus driver platform data. - - -Sysfs entries -------------- - -The following attributes are supported. Limits are read-write; all other -attributes are read-only. - -======================= ======================================================= -in1_label "vin" -in1_input Measured input voltage. -in1_average Average measured input voltage. -in1_min Minimum input voltage. -in1_max Maximum input voltage. -in1_min_alarm Input voltage low alarm. -in1_max_alarm Input voltage high alarm. - -in2_label "vmon" -in2_input Measured voltage on VAUX pin -in2_min Minimum VAUX voltage (LM25056 only). -in2_max Maximum VAUX voltage (LM25056 only). -in2_min_alarm VAUX voltage low alarm (LM25056 only). -in2_max_alarm VAUX voltage high alarm (LM25056 only). - -in3_label "vout1" - Not supported on LM25056. -in3_input Measured output voltage. -in3_average Average measured output voltage. -in3_min Minimum output voltage. -in3_min_alarm Output voltage low alarm. - -curr1_label "iin" -curr1_input Measured input current. -curr1_average Average measured input current. -curr1_max Maximum input current. -curr1_max_alarm Input current high alarm. - -power1_label "pin" -power1_input Measured input power. -power1_average Average measured input power. -power1_max Maximum input power limit. -power1_alarm Input power alarm -power1_input_highest Historical maximum power. -power1_reset_history Write any value to reset maximum power history. - -temp1_input Measured temperature. -temp1_max Maximum temperature. -temp1_crit Critical high temperature. -temp1_max_alarm Chip temperature high alarm. -temp1_crit_alarm Chip temperature critical high alarm. -======================= ======================================================= diff --git a/Documentation/hwmon/lm25066.rst b/Documentation/hwmon/lm25066.rst new file mode 100644 index 000000000000..da15e3094c8c --- /dev/null +++ b/Documentation/hwmon/lm25066.rst @@ -0,0 +1,137 @@ +Kernel driver lm25066 +===================== + +Supported chips: + + * TI LM25056 + + Prefix: 'lm25056' + + Addresses scanned: - + + Datasheets: + + http://www.ti.com/lit/gpn/lm25056 + + http://www.ti.com/lit/gpn/lm25056a + + * National Semiconductor LM25066 + + Prefix: 'lm25066' + + Addresses scanned: - + + Datasheets: + + http://www.national.com/pf/LM/LM25066.html + + http://www.national.com/pf/LM/LM25066A.html + + * National Semiconductor LM5064 + + Prefix: 'lm5064' + + Addresses scanned: - + + Datasheet: + + http://www.national.com/pf/LM/LM5064.html + + * National Semiconductor LM5066 + + Prefix: 'lm5066' + + Addresses scanned: - + + Datasheet: + + http://www.national.com/pf/LM/LM5066.html + + * Texas Instruments LM5066I + + Prefix: 'lm5066i' + + Addresses scanned: - + + Datasheet: + + http://www.ti.com/product/LM5066I + + +Author: Guenter Roeck + + +Description +----------- + +This driver supports hardware monitoring for National Semiconductor / TI LM25056, +LM25066, LM5064, and LM5066/LM5066I Power Management, Monitoring, +Control, and Protection ICs. + +The driver is a client driver to the core PMBus driver. Please see +Documentation/hwmon/pmbus.rst for details on PMBus client drivers. + + +Usage Notes +----------- + +This driver does not auto-detect devices. You will have to instantiate the +devices explicitly. Please see Documentation/i2c/instantiating-devices for +details. + + +Platform data support +--------------------- + +The driver supports standard PMBus driver platform data. + + +Sysfs entries +------------- + +The following attributes are supported. Limits are read-write; all other +attributes are read-only. + +======================= ======================================================= +in1_label "vin" +in1_input Measured input voltage. +in1_average Average measured input voltage. +in1_min Minimum input voltage. +in1_max Maximum input voltage. +in1_min_alarm Input voltage low alarm. +in1_max_alarm Input voltage high alarm. + +in2_label "vmon" +in2_input Measured voltage on VAUX pin +in2_min Minimum VAUX voltage (LM25056 only). +in2_max Maximum VAUX voltage (LM25056 only). +in2_min_alarm VAUX voltage low alarm (LM25056 only). +in2_max_alarm VAUX voltage high alarm (LM25056 only). + +in3_label "vout1" + Not supported on LM25056. +in3_input Measured output voltage. +in3_average Average measured output voltage. +in3_min Minimum output voltage. +in3_min_alarm Output voltage low alarm. + +curr1_label "iin" +curr1_input Measured input current. +curr1_average Average measured input current. +curr1_max Maximum input current. +curr1_max_alarm Input current high alarm. + +power1_label "pin" +power1_input Measured input power. +power1_average Average measured input power. +power1_max Maximum input power limit. +power1_alarm Input power alarm +power1_input_highest Historical maximum power. +power1_reset_history Write any value to reset maximum power history. + +temp1_input Measured temperature. +temp1_max Maximum temperature. +temp1_crit Critical high temperature. +temp1_max_alarm Chip temperature high alarm. +temp1_crit_alarm Chip temperature critical high alarm. +======================= ======================================================= diff --git a/Documentation/hwmon/lm63 b/Documentation/hwmon/lm63 deleted file mode 100644 index f478132b0408..000000000000 --- a/Documentation/hwmon/lm63 +++ /dev/null @@ -1,95 +0,0 @@ -Kernel driver lm63 -================== - -Supported chips: - - * National Semiconductor LM63 - - Prefix: 'lm63' - - Addresses scanned: I2C 0x4c - - Datasheet: Publicly available at the National Semiconductor website - - http://www.national.com/pf/LM/LM63.html - - * National Semiconductor LM64 - - Prefix: 'lm64' - - Addresses scanned: I2C 0x18 and 0x4e - - Datasheet: Publicly available at the National Semiconductor website - - http://www.national.com/pf/LM/LM64.html - - * National Semiconductor LM96163 - - Prefix: 'lm96163' - - Addresses scanned: I2C 0x4c - - Datasheet: Publicly available at the National Semiconductor website - - http://www.national.com/pf/LM/LM96163.html - - -Author: Jean Delvare - -Thanks go to Tyan and especially Alex Buckingham for setting up a remote -access to their S4882 test platform for this driver. - - http://www.tyan.com/ - -Description ------------ - -The LM63 is a digital temperature sensor with integrated fan monitoring -and control. - -The LM63 is basically an LM86 with fan speed monitoring and control -capabilities added. It misses some of the LM86 features though: - - - No low limit for local temperature. - - No critical limit for local temperature. - - Critical limit for remote temperature can be changed only once. We - will consider that the critical limit is read-only. - -The datasheet isn't very clear about what the tachometer reading is. - -An explanation from National Semiconductor: The two lower bits of the read -value have to be masked out. The value is still 16 bit in width. - -All temperature values are given in degrees Celsius. Resolution is 1.0 -degree for the local temperature, 0.125 degree for the remote temperature. - -The fan speed is measured using a tachometer. Contrary to most chips which -store the value in an 8-bit register and have a selectable clock divider -to make sure that the result will fit in the register, the LM63 uses 16-bit -value for measuring the speed of the fan. It can measure fan speeds down to -83 RPM, at least in theory. - -Note that the pin used for fan monitoring is shared with an alert out -function. Depending on how the board designer wanted to use the chip, fan -speed monitoring will or will not be possible. The proper chip configuration -is left to the BIOS, and the driver will blindly trust it. Only the original -LM63 suffers from this limitation, the LM64 and LM96163 have separate pins -for fan monitoring and alert out. On the LM64, monitoring is always enabled; -on the LM96163 it can be disabled. - -A PWM output can be used to control the speed of the fan. The LM63 has two -PWM modes: manual and automatic. Automatic mode is not fully implemented yet -(you cannot define your custom PWM/temperature curve), and mode change isn't -supported either. - -The lm63 driver will not update its values more frequently than configured with -the update_interval sysfs attribute; reading them more often will do no harm, -but will return 'old' values. Values in the automatic fan control lookup table -(attributes pwm1_auto_*) have their own independent lifetime of 5 seconds. - -The LM64 is effectively an LM63 with GPIO lines. The driver does not -support these GPIO lines at present. - -The LM96163 is an enhanced version of LM63 with improved temperature accuracy -and better PWM resolution. For LM96163, the external temperature sensor type is -configurable as CPU embedded diode(1) or 3904 transistor(2). diff --git a/Documentation/hwmon/lm63.rst b/Documentation/hwmon/lm63.rst new file mode 100644 index 000000000000..f478132b0408 --- /dev/null +++ b/Documentation/hwmon/lm63.rst @@ -0,0 +1,95 @@ +Kernel driver lm63 +================== + +Supported chips: + + * National Semiconductor LM63 + + Prefix: 'lm63' + + Addresses scanned: I2C 0x4c + + Datasheet: Publicly available at the National Semiconductor website + + http://www.national.com/pf/LM/LM63.html + + * National Semiconductor LM64 + + Prefix: 'lm64' + + Addresses scanned: I2C 0x18 and 0x4e + + Datasheet: Publicly available at the National Semiconductor website + + http://www.national.com/pf/LM/LM64.html + + * National Semiconductor LM96163 + + Prefix: 'lm96163' + + Addresses scanned: I2C 0x4c + + Datasheet: Publicly available at the National Semiconductor website + + http://www.national.com/pf/LM/LM96163.html + + +Author: Jean Delvare + +Thanks go to Tyan and especially Alex Buckingham for setting up a remote +access to their S4882 test platform for this driver. + + http://www.tyan.com/ + +Description +----------- + +The LM63 is a digital temperature sensor with integrated fan monitoring +and control. + +The LM63 is basically an LM86 with fan speed monitoring and control +capabilities added. It misses some of the LM86 features though: + + - No low limit for local temperature. + - No critical limit for local temperature. + - Critical limit for remote temperature can be changed only once. We + will consider that the critical limit is read-only. + +The datasheet isn't very clear about what the tachometer reading is. + +An explanation from National Semiconductor: The two lower bits of the read +value have to be masked out. The value is still 16 bit in width. + +All temperature values are given in degrees Celsius. Resolution is 1.0 +degree for the local temperature, 0.125 degree for the remote temperature. + +The fan speed is measured using a tachometer. Contrary to most chips which +store the value in an 8-bit register and have a selectable clock divider +to make sure that the result will fit in the register, the LM63 uses 16-bit +value for measuring the speed of the fan. It can measure fan speeds down to +83 RPM, at least in theory. + +Note that the pin used for fan monitoring is shared with an alert out +function. Depending on how the board designer wanted to use the chip, fan +speed monitoring will or will not be possible. The proper chip configuration +is left to the BIOS, and the driver will blindly trust it. Only the original +LM63 suffers from this limitation, the LM64 and LM96163 have separate pins +for fan monitoring and alert out. On the LM64, monitoring is always enabled; +on the LM96163 it can be disabled. + +A PWM output can be used to control the speed of the fan. The LM63 has two +PWM modes: manual and automatic. Automatic mode is not fully implemented yet +(you cannot define your custom PWM/temperature curve), and mode change isn't +supported either. + +The lm63 driver will not update its values more frequently than configured with +the update_interval sysfs attribute; reading them more often will do no harm, +but will return 'old' values. Values in the automatic fan control lookup table +(attributes pwm1_auto_*) have their own independent lifetime of 5 seconds. + +The LM64 is effectively an LM63 with GPIO lines. The driver does not +support these GPIO lines at present. + +The LM96163 is an enhanced version of LM63 with improved temperature accuracy +and better PWM resolution. For LM96163, the external temperature sensor type is +configurable as CPU embedded diode(1) or 3904 transistor(2). diff --git a/Documentation/hwmon/lm70 b/Documentation/hwmon/lm70 deleted file mode 100644 index f259bc1fcd91..000000000000 --- a/Documentation/hwmon/lm70 +++ /dev/null @@ -1,62 +0,0 @@ -Kernel driver lm70 -================== - -Supported chips: - - * National Semiconductor LM70 - - Datasheet: http://www.national.com/pf/LM/LM70.html - - * Texas Instruments TMP121/TMP123 - - Information: http://focus.ti.com/docs/prod/folders/print/tmp121.html - - * Texas Instruments TMP122/TMP124 - - Information: http://www.ti.com/product/tmp122 - - * National Semiconductor LM71 - - Datasheet: http://www.ti.com/product/LM71 - - * National Semiconductor LM74 - - Datasheet: http://www.ti.com/product/LM74 - - -Author: - Kaiwan N Billimoria - -Description ------------ - -This driver implements support for the National Semiconductor LM70 -temperature sensor. - -The LM70 temperature sensor chip supports a single temperature sensor. -It communicates with a host processor (or microcontroller) via an -SPI/Microwire Bus interface. - -Communication with the LM70 is simple: when the temperature is to be sensed, -the driver accesses the LM70 using SPI communication: 16 SCLK cycles -comprise the MOSI/MISO loop. At the end of the transfer, the 11-bit 2's -complement digital temperature (sent via the SIO line), is available in the -driver for interpretation. This driver makes use of the kernel's in-core -SPI support. - -As a real (in-tree) example of this "SPI protocol driver" interfacing -with a "SPI master controller driver", see drivers/spi/spi_lm70llp.c -and its associated documentation. - -The LM74 and TMP121/TMP122/TMP123/TMP124 are very similar; main difference is -13-bit temperature data (0.0625 degrees celsius resolution). - -The TMP122/TMP124 also feature configurable temperature thresholds. - -The LM71 is also very similar; main difference is 14-bit temperature -data (0.03125 degrees celsius resolution). - -Thanks to ---------- -Jean Delvare for mentoring the hwmon-side driver -development. diff --git a/Documentation/hwmon/lm70.rst b/Documentation/hwmon/lm70.rst new file mode 100644 index 000000000000..f259bc1fcd91 --- /dev/null +++ b/Documentation/hwmon/lm70.rst @@ -0,0 +1,62 @@ +Kernel driver lm70 +================== + +Supported chips: + + * National Semiconductor LM70 + + Datasheet: http://www.national.com/pf/LM/LM70.html + + * Texas Instruments TMP121/TMP123 + + Information: http://focus.ti.com/docs/prod/folders/print/tmp121.html + + * Texas Instruments TMP122/TMP124 + + Information: http://www.ti.com/product/tmp122 + + * National Semiconductor LM71 + + Datasheet: http://www.ti.com/product/LM71 + + * National Semiconductor LM74 + + Datasheet: http://www.ti.com/product/LM74 + + +Author: + Kaiwan N Billimoria + +Description +----------- + +This driver implements support for the National Semiconductor LM70 +temperature sensor. + +The LM70 temperature sensor chip supports a single temperature sensor. +It communicates with a host processor (or microcontroller) via an +SPI/Microwire Bus interface. + +Communication with the LM70 is simple: when the temperature is to be sensed, +the driver accesses the LM70 using SPI communication: 16 SCLK cycles +comprise the MOSI/MISO loop. At the end of the transfer, the 11-bit 2's +complement digital temperature (sent via the SIO line), is available in the +driver for interpretation. This driver makes use of the kernel's in-core +SPI support. + +As a real (in-tree) example of this "SPI protocol driver" interfacing +with a "SPI master controller driver", see drivers/spi/spi_lm70llp.c +and its associated documentation. + +The LM74 and TMP121/TMP122/TMP123/TMP124 are very similar; main difference is +13-bit temperature data (0.0625 degrees celsius resolution). + +The TMP122/TMP124 also feature configurable temperature thresholds. + +The LM71 is also very similar; main difference is 14-bit temperature +data (0.03125 degrees celsius resolution). + +Thanks to +--------- +Jean Delvare for mentoring the hwmon-side driver +development. diff --git a/Documentation/hwmon/lm73 b/Documentation/hwmon/lm73 deleted file mode 100644 index 1d6a46844e85..000000000000 --- a/Documentation/hwmon/lm73 +++ /dev/null @@ -1,98 +0,0 @@ -Kernel driver lm73 -================== - -Supported chips: - - * Texas Instruments LM73 - - Prefix: 'lm73' - - Addresses scanned: I2C 0x48, 0x49, 0x4a, 0x4c, 0x4d, and 0x4e - - Datasheet: Publicly available at the Texas Instruments website - - http://www.ti.com/product/lm73 - - -Author: Guillaume Ligneul - -Documentation: Chris Verges - - -Description ------------ - -The LM73 is a digital temperature sensor. All temperature values are -given in degrees Celsius. - -Measurement Resolution Support ------------------------------- - -The LM73 supports four resolutions, defined in terms of degrees C per -LSB: 0.25, 0.125, 0.0625, and 0.3125. Changing the resolution mode -affects the conversion time of the LM73's analog-to-digital converter. -From userspace, the desired resolution can be specified as a function of -conversion time via the 'update_interval' sysfs attribute for the -device. This attribute will normalize ranges of input values to the -maximum times defined for the resolution in the datasheet. - - ============= ============= ============ - Resolution Conv. Time Input Range - (C/LSB) (msec) (msec) - ============= ============= ============ - 0.25 14 0..14 - 0.125 28 15..28 - 0.0625 56 29..56 - 0.03125 112 57..infinity - ============= ============= ============ - -The following examples show how the 'update_interval' attribute can be -used to change the conversion time:: - - $ echo 0 > update_interval - $ cat update_interval - 14 - $ cat temp1_input - 24250 - - $ echo 22 > update_interval - $ cat update_interval - 28 - $ cat temp1_input - 24125 - - $ echo 56 > update_interval - $ cat update_interval - 56 - $ cat temp1_input - 24062 - - $ echo 85 > update_interval - $ cat update_interval - 112 - $ cat temp1_input - 24031 - -As shown here, the lm73 driver automatically adjusts any user input for -'update_interval' via a step function. Reading back the -'update_interval' value after a write operation will confirm the -conversion time actively in use. - -Mathematically, the resolution can be derived from the conversion time -via the following function: - - g(x) = 0.250 * [log(x/14) / log(2)] - -where 'x' is the output from 'update_interval' and 'g(x)' is the -resolution in degrees C per LSB. - -Alarm Support -------------- - -The LM73 features a simple over-temperature alarm mechanism. This -feature is exposed via the sysfs attributes. - -The attributes 'temp1_max_alarm' and 'temp1_min_alarm' are flags -provided by the LM73 that indicate whether the measured temperature has -passed the 'temp1_max' and 'temp1_min' thresholds, respectively. These -values _must_ be read to clear the registers on the LM73. diff --git a/Documentation/hwmon/lm73.rst b/Documentation/hwmon/lm73.rst new file mode 100644 index 000000000000..1d6a46844e85 --- /dev/null +++ b/Documentation/hwmon/lm73.rst @@ -0,0 +1,98 @@ +Kernel driver lm73 +================== + +Supported chips: + + * Texas Instruments LM73 + + Prefix: 'lm73' + + Addresses scanned: I2C 0x48, 0x49, 0x4a, 0x4c, 0x4d, and 0x4e + + Datasheet: Publicly available at the Texas Instruments website + + http://www.ti.com/product/lm73 + + +Author: Guillaume Ligneul + +Documentation: Chris Verges + + +Description +----------- + +The LM73 is a digital temperature sensor. All temperature values are +given in degrees Celsius. + +Measurement Resolution Support +------------------------------ + +The LM73 supports four resolutions, defined in terms of degrees C per +LSB: 0.25, 0.125, 0.0625, and 0.3125. Changing the resolution mode +affects the conversion time of the LM73's analog-to-digital converter. +From userspace, the desired resolution can be specified as a function of +conversion time via the 'update_interval' sysfs attribute for the +device. This attribute will normalize ranges of input values to the +maximum times defined for the resolution in the datasheet. + + ============= ============= ============ + Resolution Conv. Time Input Range + (C/LSB) (msec) (msec) + ============= ============= ============ + 0.25 14 0..14 + 0.125 28 15..28 + 0.0625 56 29..56 + 0.03125 112 57..infinity + ============= ============= ============ + +The following examples show how the 'update_interval' attribute can be +used to change the conversion time:: + + $ echo 0 > update_interval + $ cat update_interval + 14 + $ cat temp1_input + 24250 + + $ echo 22 > update_interval + $ cat update_interval + 28 + $ cat temp1_input + 24125 + + $ echo 56 > update_interval + $ cat update_interval + 56 + $ cat temp1_input + 24062 + + $ echo 85 > update_interval + $ cat update_interval + 112 + $ cat temp1_input + 24031 + +As shown here, the lm73 driver automatically adjusts any user input for +'update_interval' via a step function. Reading back the +'update_interval' value after a write operation will confirm the +conversion time actively in use. + +Mathematically, the resolution can be derived from the conversion time +via the following function: + + g(x) = 0.250 * [log(x/14) / log(2)] + +where 'x' is the output from 'update_interval' and 'g(x)' is the +resolution in degrees C per LSB. + +Alarm Support +------------- + +The LM73 features a simple over-temperature alarm mechanism. This +feature is exposed via the sysfs attributes. + +The attributes 'temp1_max_alarm' and 'temp1_min_alarm' are flags +provided by the LM73 that indicate whether the measured temperature has +passed the 'temp1_max' and 'temp1_min' thresholds, respectively. These +values _must_ be read to clear the registers on the LM73. diff --git a/Documentation/hwmon/lm75 b/Documentation/hwmon/lm75 deleted file mode 100644 index 6fd4d2df5420..000000000000 --- a/Documentation/hwmon/lm75 +++ /dev/null @@ -1,160 +0,0 @@ -Kernel driver lm75 -================== - -Supported chips: - - * National Semiconductor LM75 - - Prefix: 'lm75' - - Addresses scanned: I2C 0x48 - 0x4f - - Datasheet: Publicly available at the National Semiconductor website - - http://www.national.com/ - - * National Semiconductor LM75A - - Prefix: 'lm75a' - - Addresses scanned: I2C 0x48 - 0x4f - - Datasheet: Publicly available at the National Semiconductor website - - http://www.national.com/ - - * Dallas Semiconductor (now Maxim) DS75, DS1775, DS7505 - - Prefixes: 'ds75', 'ds1775', 'ds7505' - - Addresses scanned: none - - Datasheet: Publicly available at the Maxim website - - http://www.maximintegrated.com/ - - * Maxim MAX6625, MAX6626, MAX31725, MAX31726 - - Prefixes: 'max6625', 'max6626', 'max31725', 'max31726' - - Addresses scanned: none - - Datasheet: Publicly available at the Maxim website - - http://www.maxim-ic.com/ - - * Microchip (TelCom) TCN75 - - Prefix: 'tcn75' - - Addresses scanned: none - - Datasheet: Publicly available at the Microchip website - - http://www.microchip.com/ - - * Microchip MCP9800, MCP9801, MCP9802, MCP9803 - - Prefix: 'mcp980x' - - Addresses scanned: none - - Datasheet: Publicly available at the Microchip website - - http://www.microchip.com/ - - * Analog Devices ADT75 - - Prefix: 'adt75' - - Addresses scanned: none - - Datasheet: Publicly available at the Analog Devices website - - http://www.analog.com/adt75 - - * ST Microelectronics STDS75 - - Prefix: 'stds75' - - Addresses scanned: none - - Datasheet: Publicly available at the ST website - - http://www.st.com/internet/analog/product/121769.jsp - - * ST Microelectronics STLM75 - - Prefix: 'stlm75' - - Addresses scanned: none - - Datasheet: Publicly available at the ST website - - https://www.st.com/resource/en/datasheet/stlm75.pdf - - * Texas Instruments TMP100, TMP101, TMP105, TMP112, TMP75, TMP75C, TMP175, TMP275 - - Prefixes: 'tmp100', 'tmp101', 'tmp105', 'tmp112', 'tmp175', 'tmp75', 'tmp75c', 'tmp275' - - Addresses scanned: none - - Datasheet: Publicly available at the Texas Instruments website - - http://www.ti.com/product/tmp100 - - http://www.ti.com/product/tmp101 - - http://www.ti.com/product/tmp105 - - http://www.ti.com/product/tmp112 - - http://www.ti.com/product/tmp75 - - http://www.ti.com/product/tmp75c - - http://www.ti.com/product/tmp175 - - http://www.ti.com/product/tmp275 - - * NXP LM75B - - Prefix: 'lm75b' - - Addresses scanned: none - - Datasheet: Publicly available at the NXP website - - http://www.nxp.com/documents/data_sheet/LM75B.pdf - -Author: Frodo Looijaard - -Description ------------ - -The LM75 implements one temperature sensor. Limits can be set through the -Overtemperature Shutdown register and Hysteresis register. Each value can be -set and read to half-degree accuracy. -An alarm is issued (usually to a connected LM78) when the temperature -gets higher then the Overtemperature Shutdown value; it stays on until -the temperature falls below the Hysteresis value. -All temperatures are in degrees Celsius, and are guaranteed within a -range of -55 to +125 degrees. - -The driver caches the values for a period varying between 1 second for the -slowest chips and 125 ms for the fastest chips; reading it more often -will do no harm, but will return 'old' values. - -The original LM75 was typically used in combination with LM78-like chips -on PC motherboards, to measure the temperature of the processor(s). Clones -are now used in various embedded designs. - -The LM75 is essentially an industry standard; there may be other -LM75 clones not listed here, with or without various enhancements, -that are supported. The clones are not detected by the driver, unless -they reproduce the exact register tricks of the original LM75, and must -therefore be instantiated explicitly. Higher resolution up to 16-bit -is supported by this driver, other specific enhancements are not. - -The LM77 is not supported, contrary to what we pretended for a long time. -Both chips are simply not compatible, value encoding differs. diff --git a/Documentation/hwmon/lm75.rst b/Documentation/hwmon/lm75.rst new file mode 100644 index 000000000000..6fd4d2df5420 --- /dev/null +++ b/Documentation/hwmon/lm75.rst @@ -0,0 +1,160 @@ +Kernel driver lm75 +================== + +Supported chips: + + * National Semiconductor LM75 + + Prefix: 'lm75' + + Addresses scanned: I2C 0x48 - 0x4f + + Datasheet: Publicly available at the National Semiconductor website + + http://www.national.com/ + + * National Semiconductor LM75A + + Prefix: 'lm75a' + + Addresses scanned: I2C 0x48 - 0x4f + + Datasheet: Publicly available at the National Semiconductor website + + http://www.national.com/ + + * Dallas Semiconductor (now Maxim) DS75, DS1775, DS7505 + + Prefixes: 'ds75', 'ds1775', 'ds7505' + + Addresses scanned: none + + Datasheet: Publicly available at the Maxim website + + http://www.maximintegrated.com/ + + * Maxim MAX6625, MAX6626, MAX31725, MAX31726 + + Prefixes: 'max6625', 'max6626', 'max31725', 'max31726' + + Addresses scanned: none + + Datasheet: Publicly available at the Maxim website + + http://www.maxim-ic.com/ + + * Microchip (TelCom) TCN75 + + Prefix: 'tcn75' + + Addresses scanned: none + + Datasheet: Publicly available at the Microchip website + + http://www.microchip.com/ + + * Microchip MCP9800, MCP9801, MCP9802, MCP9803 + + Prefix: 'mcp980x' + + Addresses scanned: none + + Datasheet: Publicly available at the Microchip website + + http://www.microchip.com/ + + * Analog Devices ADT75 + + Prefix: 'adt75' + + Addresses scanned: none + + Datasheet: Publicly available at the Analog Devices website + + http://www.analog.com/adt75 + + * ST Microelectronics STDS75 + + Prefix: 'stds75' + + Addresses scanned: none + + Datasheet: Publicly available at the ST website + + http://www.st.com/internet/analog/product/121769.jsp + + * ST Microelectronics STLM75 + + Prefix: 'stlm75' + + Addresses scanned: none + + Datasheet: Publicly available at the ST website + + https://www.st.com/resource/en/datasheet/stlm75.pdf + + * Texas Instruments TMP100, TMP101, TMP105, TMP112, TMP75, TMP75C, TMP175, TMP275 + + Prefixes: 'tmp100', 'tmp101', 'tmp105', 'tmp112', 'tmp175', 'tmp75', 'tmp75c', 'tmp275' + + Addresses scanned: none + + Datasheet: Publicly available at the Texas Instruments website + + http://www.ti.com/product/tmp100 + + http://www.ti.com/product/tmp101 + + http://www.ti.com/product/tmp105 + + http://www.ti.com/product/tmp112 + + http://www.ti.com/product/tmp75 + + http://www.ti.com/product/tmp75c + + http://www.ti.com/product/tmp175 + + http://www.ti.com/product/tmp275 + + * NXP LM75B + + Prefix: 'lm75b' + + Addresses scanned: none + + Datasheet: Publicly available at the NXP website + + http://www.nxp.com/documents/data_sheet/LM75B.pdf + +Author: Frodo Looijaard + +Description +----------- + +The LM75 implements one temperature sensor. Limits can be set through the +Overtemperature Shutdown register and Hysteresis register. Each value can be +set and read to half-degree accuracy. +An alarm is issued (usually to a connected LM78) when the temperature +gets higher then the Overtemperature Shutdown value; it stays on until +the temperature falls below the Hysteresis value. +All temperatures are in degrees Celsius, and are guaranteed within a +range of -55 to +125 degrees. + +The driver caches the values for a period varying between 1 second for the +slowest chips and 125 ms for the fastest chips; reading it more often +will do no harm, but will return 'old' values. + +The original LM75 was typically used in combination with LM78-like chips +on PC motherboards, to measure the temperature of the processor(s). Clones +are now used in various embedded designs. + +The LM75 is essentially an industry standard; there may be other +LM75 clones not listed here, with or without various enhancements, +that are supported. The clones are not detected by the driver, unless +they reproduce the exact register tricks of the original LM75, and must +therefore be instantiated explicitly. Higher resolution up to 16-bit +is supported by this driver, other specific enhancements are not. + +The LM77 is not supported, contrary to what we pretended for a long time. +Both chips are simply not compatible, value encoding differs. diff --git a/Documentation/hwmon/lm77 b/Documentation/hwmon/lm77 deleted file mode 100644 index 4ed3fe6b999a..000000000000 --- a/Documentation/hwmon/lm77 +++ /dev/null @@ -1,45 +0,0 @@ -Kernel driver lm77 -================== - -Supported chips: - - * National Semiconductor LM77 - - Prefix: 'lm77' - - Addresses scanned: I2C 0x48 - 0x4b - - Datasheet: Publicly available at the National Semiconductor website - - http://www.national.com/ - - -Author: Andras BALI - -Description ------------ - -The LM77 implements one temperature sensor. The temperature -sensor incorporates a band-gap type temperature sensor, -10-bit ADC, and a digital comparator with user-programmable upper -and lower limit values. - -The LM77 implements 3 limits: low (temp1_min), high (temp1_max) and -critical (temp1_crit.) It also implements an hysteresis mechanism which -applies to all 3 limits. The relative difference is stored in a single -register on the chip, which means that the relative difference between -the limit and its hysteresis is always the same for all 3 limits. - -This implementation detail implies the following: - -* When setting a limit, its hysteresis will automatically follow, the - difference staying unchanged. For example, if the old critical limit - was 80 degrees C, and the hysteresis was 75 degrees C, and you change - the critical limit to 90 degrees C, then the hysteresis will - automatically change to 85 degrees C. -* All 3 hysteresis can't be set independently. We decided to make - temp1_crit_hyst writable, while temp1_min_hyst and temp1_max_hyst are - read-only. Setting temp1_crit_hyst writes the difference between - temp1_crit_hyst and temp1_crit into the chip, and the same relative - hysteresis applies automatically to the low and high limits. -* The limits should be set before the hysteresis. diff --git a/Documentation/hwmon/lm77.rst b/Documentation/hwmon/lm77.rst new file mode 100644 index 000000000000..4ed3fe6b999a --- /dev/null +++ b/Documentation/hwmon/lm77.rst @@ -0,0 +1,45 @@ +Kernel driver lm77 +================== + +Supported chips: + + * National Semiconductor LM77 + + Prefix: 'lm77' + + Addresses scanned: I2C 0x48 - 0x4b + + Datasheet: Publicly available at the National Semiconductor website + + http://www.national.com/ + + +Author: Andras BALI + +Description +----------- + +The LM77 implements one temperature sensor. The temperature +sensor incorporates a band-gap type temperature sensor, +10-bit ADC, and a digital comparator with user-programmable upper +and lower limit values. + +The LM77 implements 3 limits: low (temp1_min), high (temp1_max) and +critical (temp1_crit.) It also implements an hysteresis mechanism which +applies to all 3 limits. The relative difference is stored in a single +register on the chip, which means that the relative difference between +the limit and its hysteresis is always the same for all 3 limits. + +This implementation detail implies the following: + +* When setting a limit, its hysteresis will automatically follow, the + difference staying unchanged. For example, if the old critical limit + was 80 degrees C, and the hysteresis was 75 degrees C, and you change + the critical limit to 90 degrees C, then the hysteresis will + automatically change to 85 degrees C. +* All 3 hysteresis can't be set independently. We decided to make + temp1_crit_hyst writable, while temp1_min_hyst and temp1_max_hyst are + read-only. Setting temp1_crit_hyst writes the difference between + temp1_crit_hyst and temp1_crit into the chip, and the same relative + hysteresis applies automatically to the low and high limits. +* The limits should be set before the hysteresis. diff --git a/Documentation/hwmon/lm78 b/Documentation/hwmon/lm78 deleted file mode 100644 index cb7a4832f35e..000000000000 --- a/Documentation/hwmon/lm78 +++ /dev/null @@ -1,80 +0,0 @@ -Kernel driver lm78 -================== - -Supported chips: - - * National Semiconductor LM78 / LM78-J - - Prefix: 'lm78' - - Addresses scanned: I2C 0x28 - 0x2f, ISA 0x290 (8 I/O ports) - - Datasheet: Publicly available at the National Semiconductor website - - http://www.national.com/ - - * National Semiconductor LM79 - - Prefix: 'lm79' - - Addresses scanned: I2C 0x28 - 0x2f, ISA 0x290 (8 I/O ports) - - Datasheet: Publicly available at the National Semiconductor website - - http://www.national.com/ - - -Authors: - - Frodo Looijaard - - Jean Delvare - -Description ------------ - -This driver implements support for the National Semiconductor LM78, LM78-J -and LM79. They are described as 'Microprocessor System Hardware Monitors'. - -There is almost no difference between the three supported chips. Functionally, -the LM78 and LM78-J are exactly identical. The LM79 has one more VID line, -which is used to report the lower voltages newer Pentium processors use. -From here on, LM7* means either of these three types. - -The LM7* implements one temperature sensor, three fan rotation speed sensors, -seven voltage sensors, VID lines, alarms, and some miscellaneous stuff. - -Temperatures are measured in degrees Celsius. An alarm is triggered once -when the Overtemperature Shutdown limit is crossed; it is triggered again -as soon as it drops below the Hysteresis value. A more useful behavior -can be found by setting the Hysteresis value to +127 degrees Celsius; in -this case, alarms are issued during all the time when the actual temperature -is above the Overtemperature Shutdown value. Measurements are guaranteed -between -55 and +125 degrees, with a resolution of 1 degree. - -Fan rotation speeds are reported in RPM (rotations per minute). An alarm is -triggered if the rotation speed has dropped below a programmable limit. Fan -readings can be divided by a programmable divider (1, 2, 4 or 8) to give -the readings more range or accuracy. Not all RPM values can accurately be -represented, so some rounding is done. With a divider of 2, the lowest -representable value is around 2600 RPM. - -Voltage sensors (also known as IN sensors) report their values in volts. -An alarm is triggered if the voltage has crossed a programmable minimum -or maximum limit. Note that minimum in this case always means 'closest to -zero'; this is important for negative voltage measurements. All voltage -inputs can measure voltages between 0 and 4.08 volts, with a resolution -of 0.016 volt. - -The VID lines encode the core voltage value: the voltage level your processor -should work with. This is hardcoded by the mainboard and/or processor itself. -It is a value in volts. When it is unconnected, you will often find the -value 3.50 V here. - -If an alarm triggers, it will remain triggered until the hardware register -is read at least once. This means that the cause for the alarm may -already have disappeared! Note that in the current implementation, all -hardware registers are read whenever any data is read (unless it is less -than 1.5 seconds since the last update). This means that you can easily -miss once-only alarms. - -The LM7* only updates its values each 1.5 seconds; reading it more often -will do no harm, but will return 'old' values. diff --git a/Documentation/hwmon/lm78.rst b/Documentation/hwmon/lm78.rst new file mode 100644 index 000000000000..cb7a4832f35e --- /dev/null +++ b/Documentation/hwmon/lm78.rst @@ -0,0 +1,80 @@ +Kernel driver lm78 +================== + +Supported chips: + + * National Semiconductor LM78 / LM78-J + + Prefix: 'lm78' + + Addresses scanned: I2C 0x28 - 0x2f, ISA 0x290 (8 I/O ports) + + Datasheet: Publicly available at the National Semiconductor website + + http://www.national.com/ + + * National Semiconductor LM79 + + Prefix: 'lm79' + + Addresses scanned: I2C 0x28 - 0x2f, ISA 0x290 (8 I/O ports) + + Datasheet: Publicly available at the National Semiconductor website + + http://www.national.com/ + + +Authors: + - Frodo Looijaard + - Jean Delvare + +Description +----------- + +This driver implements support for the National Semiconductor LM78, LM78-J +and LM79. They are described as 'Microprocessor System Hardware Monitors'. + +There is almost no difference between the three supported chips. Functionally, +the LM78 and LM78-J are exactly identical. The LM79 has one more VID line, +which is used to report the lower voltages newer Pentium processors use. +From here on, LM7* means either of these three types. + +The LM7* implements one temperature sensor, three fan rotation speed sensors, +seven voltage sensors, VID lines, alarms, and some miscellaneous stuff. + +Temperatures are measured in degrees Celsius. An alarm is triggered once +when the Overtemperature Shutdown limit is crossed; it is triggered again +as soon as it drops below the Hysteresis value. A more useful behavior +can be found by setting the Hysteresis value to +127 degrees Celsius; in +this case, alarms are issued during all the time when the actual temperature +is above the Overtemperature Shutdown value. Measurements are guaranteed +between -55 and +125 degrees, with a resolution of 1 degree. + +Fan rotation speeds are reported in RPM (rotations per minute). An alarm is +triggered if the rotation speed has dropped below a programmable limit. Fan +readings can be divided by a programmable divider (1, 2, 4 or 8) to give +the readings more range or accuracy. Not all RPM values can accurately be +represented, so some rounding is done. With a divider of 2, the lowest +representable value is around 2600 RPM. + +Voltage sensors (also known as IN sensors) report their values in volts. +An alarm is triggered if the voltage has crossed a programmable minimum +or maximum limit. Note that minimum in this case always means 'closest to +zero'; this is important for negative voltage measurements. All voltage +inputs can measure voltages between 0 and 4.08 volts, with a resolution +of 0.016 volt. + +The VID lines encode the core voltage value: the voltage level your processor +should work with. This is hardcoded by the mainboard and/or processor itself. +It is a value in volts. When it is unconnected, you will often find the +value 3.50 V here. + +If an alarm triggers, it will remain triggered until the hardware register +is read at least once. This means that the cause for the alarm may +already have disappeared! Note that in the current implementation, all +hardware registers are read whenever any data is read (unless it is less +than 1.5 seconds since the last update). This means that you can easily +miss once-only alarms. + +The LM7* only updates its values each 1.5 seconds; reading it more often +will do no harm, but will return 'old' values. diff --git a/Documentation/hwmon/lm80 b/Documentation/hwmon/lm80 deleted file mode 100644 index c53186abd82e..000000000000 --- a/Documentation/hwmon/lm80 +++ /dev/null @@ -1,74 +0,0 @@ -Kernel driver lm80 -================== - -Supported chips: - - * National Semiconductor LM80 - - Prefix: 'lm80' - - Addresses scanned: I2C 0x28 - 0x2f - - Datasheet: Publicly available at the National Semiconductor website - - http://www.national.com/ - - * National Semiconductor LM96080 - - Prefix: 'lm96080' - - Addresses scanned: I2C 0x28 - 0x2f - - Datasheet: Publicly available at the National Semiconductor website - - http://www.national.com/ - - -Authors: - - Frodo Looijaard , - - Philip Edelbrock - -Description ------------ - -This driver implements support for the National Semiconductor LM80. -It is described as a 'Serial Interface ACPI-Compatible Microprocessor -System Hardware Monitor'. The LM96080 is a more recent incarnation, -it is pin and register compatible, with a few additional features not -yet supported by the driver. - -The LM80 implements one temperature sensor, two fan rotation speed sensors, -seven voltage sensors, alarms, and some miscellaneous stuff. - -Temperatures are measured in degrees Celsius. There are two sets of limits -which operate independently. When the HOT Temperature Limit is crossed, -this will cause an alarm that will be reasserted until the temperature -drops below the HOT Hysteresis. The Overtemperature Shutdown (OS) limits -should work in the same way (but this must be checked; the datasheet -is unclear about this). Measurements are guaranteed between -55 and -+125 degrees. The current temperature measurement has a resolution of -0.0625 degrees; the limits have a resolution of 1 degree. - -Fan rotation speeds are reported in RPM (rotations per minute). An alarm is -triggered if the rotation speed has dropped below a programmable limit. Fan -readings can be divided by a programmable divider (1, 2, 4 or 8) to give -the readings more range or accuracy. Not all RPM values can accurately be -represented, so some rounding is done. With a divider of 2, the lowest -representable value is around 2600 RPM. - -Voltage sensors (also known as IN sensors) report their values in volts. -An alarm is triggered if the voltage has crossed a programmable minimum -or maximum limit. Note that minimum in this case always means 'closest to -zero'; this is important for negative voltage measurements. All voltage -inputs can measure voltages between 0 and 2.55 volts, with a resolution -of 0.01 volt. - -If an alarm triggers, it will remain triggered until the hardware register -is read at least once. This means that the cause for the alarm may -already have disappeared! Note that in the current implementation, all -hardware registers are read whenever any data is read (unless it is less -than 2.0 seconds since the last update). This means that you can easily -miss once-only alarms. - -The LM80 only updates its values each 1.5 seconds; reading it more often -will do no harm, but will return 'old' values. diff --git a/Documentation/hwmon/lm80.rst b/Documentation/hwmon/lm80.rst new file mode 100644 index 000000000000..c53186abd82e --- /dev/null +++ b/Documentation/hwmon/lm80.rst @@ -0,0 +1,74 @@ +Kernel driver lm80 +================== + +Supported chips: + + * National Semiconductor LM80 + + Prefix: 'lm80' + + Addresses scanned: I2C 0x28 - 0x2f + + Datasheet: Publicly available at the National Semiconductor website + + http://www.national.com/ + + * National Semiconductor LM96080 + + Prefix: 'lm96080' + + Addresses scanned: I2C 0x28 - 0x2f + + Datasheet: Publicly available at the National Semiconductor website + + http://www.national.com/ + + +Authors: + - Frodo Looijaard , + - Philip Edelbrock + +Description +----------- + +This driver implements support for the National Semiconductor LM80. +It is described as a 'Serial Interface ACPI-Compatible Microprocessor +System Hardware Monitor'. The LM96080 is a more recent incarnation, +it is pin and register compatible, with a few additional features not +yet supported by the driver. + +The LM80 implements one temperature sensor, two fan rotation speed sensors, +seven voltage sensors, alarms, and some miscellaneous stuff. + +Temperatures are measured in degrees Celsius. There are two sets of limits +which operate independently. When the HOT Temperature Limit is crossed, +this will cause an alarm that will be reasserted until the temperature +drops below the HOT Hysteresis. The Overtemperature Shutdown (OS) limits +should work in the same way (but this must be checked; the datasheet +is unclear about this). Measurements are guaranteed between -55 and ++125 degrees. The current temperature measurement has a resolution of +0.0625 degrees; the limits have a resolution of 1 degree. + +Fan rotation speeds are reported in RPM (rotations per minute). An alarm is +triggered if the rotation speed has dropped below a programmable limit. Fan +readings can be divided by a programmable divider (1, 2, 4 or 8) to give +the readings more range or accuracy. Not all RPM values can accurately be +represented, so some rounding is done. With a divider of 2, the lowest +representable value is around 2600 RPM. + +Voltage sensors (also known as IN sensors) report their values in volts. +An alarm is triggered if the voltage has crossed a programmable minimum +or maximum limit. Note that minimum in this case always means 'closest to +zero'; this is important for negative voltage measurements. All voltage +inputs can measure voltages between 0 and 2.55 volts, with a resolution +of 0.01 volt. + +If an alarm triggers, it will remain triggered until the hardware register +is read at least once. This means that the cause for the alarm may +already have disappeared! Note that in the current implementation, all +hardware registers are read whenever any data is read (unless it is less +than 2.0 seconds since the last update). This means that you can easily +miss once-only alarms. + +The LM80 only updates its values each 1.5 seconds; reading it more often +will do no harm, but will return 'old' values. diff --git a/Documentation/hwmon/lm83 b/Documentation/hwmon/lm83 deleted file mode 100644 index ecf83819960e..000000000000 --- a/Documentation/hwmon/lm83 +++ /dev/null @@ -1,97 +0,0 @@ -Kernel driver lm83 -================== - -Supported chips: - - * National Semiconductor LM83 - - Prefix: 'lm83' - - Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e - - Datasheet: Publicly available at the National Semiconductor website - - http://www.national.com/pf/LM/LM83.html - - * National Semiconductor LM82 - - Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e - - Datasheet: Publicly available at the National Semiconductor website - - http://www.national.com/pf/LM/LM82.html - -Author: Jean Delvare - -Description ------------ - -The LM83 is a digital temperature sensor. It senses its own temperature as -well as the temperature of up to three external diodes. The LM82 is -a stripped down version of the LM83 that only supports one external diode. -Both are compatible with many other devices such as the LM84 and all -other ADM1021 clones. The main difference between the LM83 and the LM84 -in that the later can only sense the temperature of one external diode. - -Using the adm1021 driver for a LM83 should work, but only two temperatures -will be reported instead of four. - -The LM83 is only found on a handful of motherboards. Both a confirmed -list and an unconfirmed list follow. If you can confirm or infirm the -fact that any of these motherboards do actually have an LM83, please -contact us. Note that the LM90 can easily be misdetected as a LM83. - -Confirmed motherboards: - === ===== - SBS P014 - SBS PSL09 - === ===== - -Unconfirmed motherboards: - =========== ========== - Gigabyte GA-8IK1100 - Iwill MPX2 - Soltek SL-75DRV5 - =========== ========== - -The LM82 is confirmed to have been found on most AMD Geode reference -designs and test platforms. - -The driver has been successfully tested by Magnus Forsström, who I'd -like to thank here. More testers will be of course welcome. - -The fact that the LM83 is only scarcely used can be easily explained. -Most motherboards come with more than just temperature sensors for -health monitoring. They also have voltage and fan rotation speed -sensors. This means that temperature-only chips are usually used as -secondary chips coupled with another chip such as an IT8705F or similar -chip, which provides more features. Since systems usually need three -temperature sensors (motherboard, processor, power supply) and primary -chips provide some temperature sensors, the secondary chip, if needed, -won't have to handle more than two temperatures. Thus, ADM1021 clones -are sufficient, and there is no need for a four temperatures sensor -chip such as the LM83. The only case where using an LM83 would make -sense is on SMP systems, such as the above-mentioned Iwill MPX2, -because you want an additional temperature sensor for each additional -CPU. - -On the SBS P014, this is different, since the LM83 is the only hardware -monitoring chipset. One temperature sensor is used for the motherboard -(actually measuring the LM83's own temperature), one is used for the -CPU. The two other sensors must be used to measure the temperature of -two other points of the motherboard. We suspect these points to be the -north and south bridges, but this couldn't be confirmed. - -All temperature values are given in degrees Celsius. Local temperature -is given within a range of 0 to +85 degrees. Remote temperatures are -given within a range of 0 to +125 degrees. Resolution is 1.0 degree, -accuracy is guaranteed to 3.0 degrees (see the datasheet for more -details). - -Each sensor has its own high limit, but the critical limit is common to -all four sensors. There is no hysteresis mechanism as found on most -recent temperature sensors. - -The lm83 driver will not update its values more frequently than every -other second; reading them more often will do no harm, but will return -'old' values. diff --git a/Documentation/hwmon/lm83.rst b/Documentation/hwmon/lm83.rst new file mode 100644 index 000000000000..ecf83819960e --- /dev/null +++ b/Documentation/hwmon/lm83.rst @@ -0,0 +1,97 @@ +Kernel driver lm83 +================== + +Supported chips: + + * National Semiconductor LM83 + + Prefix: 'lm83' + + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + + Datasheet: Publicly available at the National Semiconductor website + + http://www.national.com/pf/LM/LM83.html + + * National Semiconductor LM82 + + Addresses scanned: I2C 0x18 - 0x1a, 0x29 - 0x2b, 0x4c - 0x4e + + Datasheet: Publicly available at the National Semiconductor website + + http://www.national.com/pf/LM/LM82.html + +Author: Jean Delvare + +Description +----------- + +The LM83 is a digital temperature sensor. It senses its own temperature as +well as the temperature of up to three external diodes. The LM82 is +a stripped down version of the LM83 that only supports one external diode. +Both are compatible with many other devices such as the LM84 and all +other ADM1021 clones. The main difference between the LM83 and the LM84 +in that the later can only sense the temperature of one external diode. + +Using the adm1021 driver for a LM83 should work, but only two temperatures +will be reported instead of four. + +The LM83 is only found on a handful of motherboards. Both a confirmed +list and an unconfirmed list follow. If you can confirm or infirm the +fact that any of these motherboards do actually have an LM83, please +contact us. Note that the LM90 can easily be misdetected as a LM83. + +Confirmed motherboards: + === ===== + SBS P014 + SBS PSL09 + === ===== + +Unconfirmed motherboards: + =========== ========== + Gigabyte GA-8IK1100 + Iwill MPX2 + Soltek SL-75DRV5 + =========== ========== + +The LM82 is confirmed to have been found on most AMD Geode reference +designs and test platforms. + +The driver has been successfully tested by Magnus Forsström, who I'd +like to thank here. More testers will be of course welcome. + +The fact that the LM83 is only scarcely used can be easily explained. +Most motherboards come with more than just temperature sensors for +health monitoring. They also have voltage and fan rotation speed +sensors. This means that temperature-only chips are usually used as +secondary chips coupled with another chip such as an IT8705F or similar +chip, which provides more features. Since systems usually need three +temperature sensors (motherboard, processor, power supply) and primary +chips provide some temperature sensors, the secondary chip, if needed, +won't have to handle more than two temperatures. Thus, ADM1021 clones +are sufficient, and there is no need for a four temperatures sensor +chip such as the LM83. The only case where using an LM83 would make +sense is on SMP systems, such as the above-mentioned Iwill MPX2, +because you want an additional temperature sensor for each additional +CPU. + +On the SBS P014, this is different, since the LM83 is the only hardware +monitoring chipset. One temperature sensor is used for the motherboard +(actually measuring the LM83's own temperature), one is used for the +CPU. The two other sensors must be used to measure the temperature of +two other points of the motherboard. We suspect these points to be the +north and south bridges, but this couldn't be confirmed. + +All temperature values are given in degrees Celsius. Local temperature +is given within a range of 0 to +85 degrees. Remote temperatures are +given within a range of 0 to +125 degrees. Resolution is 1.0 degree, +accuracy is guaranteed to 3.0 degrees (see the datasheet for more +details). + +Each sensor has its own high limit, but the critical limit is common to +all four sensors. There is no hysteresis mechanism as found on most +recent temperature sensors. + +The lm83 driver will not update its values more frequently than every +other second; reading them more often will do no harm, but will return +'old' values. diff --git a/Documentation/hwmon/lm85 b/Documentation/hwmon/lm85 deleted file mode 100644 index faa92f54431c..000000000000 --- a/Documentation/hwmon/lm85 +++ /dev/null @@ -1,286 +0,0 @@ -Kernel driver lm85 -================== - -Supported chips: - - * National Semiconductor LM85 (B and C versions) - - Prefix: 'lm85b' or 'lm85c' - - Addresses scanned: I2C 0x2c, 0x2d, 0x2e - - Datasheet: http://www.national.com/pf/LM/LM85.html - - * Texas Instruments LM96000 - - Prefix: 'lm9600' - - Addresses scanned: I2C 0x2c, 0x2d, 0x2e - - Datasheet: http://www.ti.com/lit/ds/symlink/lm96000.pdf - - * Analog Devices ADM1027 - - Prefix: 'adm1027' - - Addresses scanned: I2C 0x2c, 0x2d, 0x2e - - Datasheet: http://www.onsemi.com/PowerSolutions/product.do?id=ADM1027 - - * Analog Devices ADT7463 - - Prefix: 'adt7463' - - Addresses scanned: I2C 0x2c, 0x2d, 0x2e - - Datasheet: http://www.onsemi.com/PowerSolutions/product.do?id=ADT7463 - - * Analog Devices ADT7468 - - Prefix: 'adt7468' - - Addresses scanned: I2C 0x2c, 0x2d, 0x2e - - Datasheet: http://www.onsemi.com/PowerSolutions/product.do?id=ADT7468 - - * SMSC EMC6D100, SMSC EMC6D101 - - Prefix: 'emc6d100' - - Addresses scanned: I2C 0x2c, 0x2d, 0x2e - - Datasheet: http://www.smsc.com/media/Downloads_Public/discontinued/6d100.pdf - - * SMSC EMC6D102 - - Prefix: 'emc6d102' - - Addresses scanned: I2C 0x2c, 0x2d, 0x2e - - Datasheet: http://www.smsc.com/main/catalog/emc6d102.html - - * SMSC EMC6D103 - - Prefix: 'emc6d103' - - Addresses scanned: I2C 0x2c, 0x2d, 0x2e - - Datasheet: http://www.smsc.com/main/catalog/emc6d103.html - - * SMSC EMC6D103S - - Prefix: 'emc6d103s' - - Addresses scanned: I2C 0x2c, 0x2d, 0x2e - - Datasheet: http://www.smsc.com/main/catalog/emc6d103s.html - -Authors: - - Philip Pokorny , - - Frodo Looijaard , - - Richard Barrington , - - Margit Schubert-While , - - Justin Thiessen - -Description ------------ - -This driver implements support for the National Semiconductor LM85 and -compatible chips including the Analog Devices ADM1027, ADT7463, ADT7468 and -SMSC EMC6D10x chips family. - -The LM85 uses the 2-wire interface compatible with the SMBUS 2.0 -specification. Using an analog to digital converter it measures three (3) -temperatures and five (5) voltages. It has four (4) 16-bit counters for -measuring fan speed. Five (5) digital inputs are provided for sampling the -VID signals from the processor to the VRM. Lastly, there are three (3) PWM -outputs that can be used to control fan speed. - -The voltage inputs have internal scaling resistors so that the following -voltage can be measured without external resistors: - - 2.5V, 3.3V, 5V, 12V, and CPU core voltage (2.25V) - -The temperatures measured are one internal diode, and two remote diodes. -Remote 1 is generally the CPU temperature. These inputs are designed to -measure a thermal diode like the one in a Pentium 4 processor in a socket -423 or socket 478 package. They can also measure temperature using a -transistor like the 2N3904. - -A sophisticated control system for the PWM outputs is designed into the -LM85 that allows fan speed to be adjusted automatically based on any of the -three temperature sensors. Each PWM output is individually adjustable and -programmable. Once configured, the LM85 will adjust the PWM outputs in -response to the measured temperatures without further host intervention. -This feature can also be disabled for manual control of the PWM's. - -Each of the measured inputs (voltage, temperature, fan speed) has -corresponding high/low limit values. The LM85 will signal an ALARM if any -measured value exceeds either limit. - -The LM85 samples all inputs continuously. The lm85 driver will not read -the registers more often than once a second. Further, configuration data is -only read once each 5 minutes. There is twice as much config data as -measurements, so this would seem to be a worthwhile optimization. - -Special Features ----------------- - -The LM85 has four fan speed monitoring modes. The ADM1027 has only two. -Both have special circuitry to compensate for PWM interactions with the -TACH signal from the fans. The ADM1027 can be configured to measure the -speed of a two wire fan, but the input conditioning circuitry is different -for 3-wire and 2-wire mode. For this reason, the 2-wire fan modes are not -exposed to user control. The BIOS should initialize them to the correct -mode. If you've designed your own ADM1027, you'll have to modify the -init_client function and add an insmod parameter to set this up. - -To smooth the response of fans to changes in temperature, the LM85 has an -optional filter for smoothing temperatures. The ADM1027 has the same -config option but uses it to rate limit the changes to fan speed instead. - -The ADM1027, ADT7463 and ADT7468 have a 10-bit ADC and can therefore -measure temperatures with 0.25 degC resolution. They also provide an offset -to the temperature readings that is automatically applied during -measurement. This offset can be used to zero out any errors due to traces -and placement. The documentation says that the offset is in 0.25 degC -steps, but in initial testing of the ADM1027 it was 1.00 degC steps. Analog -Devices has confirmed this "bug". The ADT7463 is reported to work as -described in the documentation. The current lm85 driver does not show the -offset register. - -The ADT7468 has a high-frequency PWM mode, where all PWM outputs are -driven by a 22.5 kHz clock. This is a global mode, not per-PWM output, -which means that setting any PWM frequency above 11.3 kHz will switch -all 3 PWM outputs to a 22.5 kHz frequency. Conversely, setting any PWM -frequency below 11.3 kHz will switch all 3 PWM outputs to a frequency -between 10 and 100 Hz, which can then be tuned separately. - -See the vendor datasheets for more information. There is application note -from National (AN-1260) with some additional information about the LM85. -The Analog Devices datasheet is very detailed and describes a procedure for -determining an optimal configuration for the automatic PWM control. - -The SMSC EMC6D100 & EMC6D101 monitor external voltages, temperatures, and -fan speeds. They use this monitoring capability to alert the system to out -of limit conditions and can automatically control the speeds of multiple -fans in a PC or embedded system. The EMC6D101, available in a 24-pin SSOP -package, and the EMC6D100, available in a 28-pin SSOP package, are designed -to be register compatible. The EMC6D100 offers all the features of the -EMC6D101 plus additional voltage monitoring and system control features. -Unfortunately it is not possible to distinguish between the package -versions on register level so these additional voltage inputs may read -zero. EMC6D102 and EMC6D103 feature additional ADC bits thus extending precision -of voltage and temperature channels. - -SMSC EMC6D103S is similar to EMC6D103, but does not support pwm#_auto_pwm_minctl -and temp#_auto_temp_off. - -The LM96000 supports additional high frequency PWM modes (22.5 kHz, 24 kHz, -25.7 kHz, 27.7 kHz and 30 kHz), which can be configured on a per-PWM basis. - -Hardware Configurations ------------------------ - -The LM85 can be jumpered for 3 different SMBus addresses. There are -no other hardware configuration options for the LM85. - -The lm85 driver detects both LM85B and LM85C revisions of the chip. See the -datasheet for a complete description of the differences. Other than -identifying the chip, the driver behaves no differently with regard to -these two chips. The LM85B is recommended for new designs. - -The ADM1027, ADT7463 and ADT7468 chips have an optional SMBALERT output -that can be used to signal the chipset in case a limit is exceeded or the -temperature sensors fail. Individual sensor interrupts can be masked so -they won't trigger SMBALERT. The SMBALERT output if configured replaces one -of the other functions (PWM2 or IN0). This functionality is not implemented -in current driver. - -The ADT7463 and ADT7468 also have an optional THERM output/input which can -be connected to the processor PROC_HOT output. If available, the autofan -control dynamic Tmin feature can be enabled to keep the system temperature -within spec (just?!) with the least possible fan noise. - -Configuration Notes -------------------- - -Besides standard interfaces driver adds following: - -* Temperatures and Zones - -Each temperature sensor is associated with a Zone. There are three -sensors and therefore three zones (# 1, 2 and 3). Each zone has the following -temperature configuration points: - -* temp#_auto_temp_off - - temperature below which fans should be off or spinning very low. -* temp#_auto_temp_min - - temperature over which fans start to spin. -* temp#_auto_temp_max - - temperature when fans spin at full speed. -* temp#_auto_temp_crit - - temperature when all fans will run full speed. - -PWM Control -^^^^^^^^^^^ - -There are three PWM outputs. The LM85 datasheet suggests that the -pwm3 output control both fan3 and fan4. Each PWM can be individually -configured and assigned to a zone for its control value. Each PWM can be -configured individually according to the following options. - -* pwm#_auto_pwm_min - - this specifies the PWM value for temp#_auto_temp_off - temperature. (PWM value from 0 to 255) - -* pwm#_auto_pwm_minctl - - this flags selects for temp#_auto_temp_off temperature - the behaviour of fans. Write 1 to let fans spinning at - pwm#_auto_pwm_min or write 0 to let them off. - -.. note:: - - It has been reported that there is a bug in the LM85 that causes - the flag to be associated with the zones not the PWMs. This - contradicts all the published documentation. Setting pwm#_min_ctl - in this case actually affects all PWMs controlled by zone '#'. - -PWM Controlling Zone selection -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -* pwm#_auto_channels - - controls zone that is associated with PWM - -Configuration choices: - -========== ============================================= -Value Meaning -========== ============================================= - 1 Controlled by Zone 1 - 2 Controlled by Zone 2 - 3 Controlled by Zone 3 - 23 Controlled by higher temp of Zone 2 or 3 - 123 Controlled by highest temp of Zone 1, 2 or 3 - 0 PWM always 0% (off) - -1 PWM always 100% (full on) - -2 Manual control (write to 'pwm#' to set) -========== ============================================= - -The National LM85's have two vendor specific configuration -features. Tach. mode and Spinup Control. For more details on these, -see the LM85 datasheet or Application Note AN-1260. These features -are not currently supported by the lm85 driver. - -The Analog Devices ADM1027 has several vendor specific enhancements. -The number of pulses-per-rev of the fans can be set, Tach monitoring -can be optimized for PWM operation, and an offset can be applied to -the temperatures to compensate for systemic errors in the -measurements. These features are not currently supported by the lm85 -driver. - -In addition to the ADM1027 features, the ADT7463 and ADT7468 also have -Tmin control and THERM asserted counts. Automatic Tmin control acts to -adjust the Tmin value to maintain the measured temperature sensor at a -specified temperature. There isn't much documentation on this feature in -the ADT7463 data sheet. This is not supported by current driver. diff --git a/Documentation/hwmon/lm85.rst b/Documentation/hwmon/lm85.rst new file mode 100644 index 000000000000..faa92f54431c --- /dev/null +++ b/Documentation/hwmon/lm85.rst @@ -0,0 +1,286 @@ +Kernel driver lm85 +================== + +Supported chips: + + * National Semiconductor LM85 (B and C versions) + + Prefix: 'lm85b' or 'lm85c' + + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + + Datasheet: http://www.national.com/pf/LM/LM85.html + + * Texas Instruments LM96000 + + Prefix: 'lm9600' + + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + + Datasheet: http://www.ti.com/lit/ds/symlink/lm96000.pdf + + * Analog Devices ADM1027 + + Prefix: 'adm1027' + + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + + Datasheet: http://www.onsemi.com/PowerSolutions/product.do?id=ADM1027 + + * Analog Devices ADT7463 + + Prefix: 'adt7463' + + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + + Datasheet: http://www.onsemi.com/PowerSolutions/product.do?id=ADT7463 + + * Analog Devices ADT7468 + + Prefix: 'adt7468' + + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + + Datasheet: http://www.onsemi.com/PowerSolutions/product.do?id=ADT7468 + + * SMSC EMC6D100, SMSC EMC6D101 + + Prefix: 'emc6d100' + + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + + Datasheet: http://www.smsc.com/media/Downloads_Public/discontinued/6d100.pdf + + * SMSC EMC6D102 + + Prefix: 'emc6d102' + + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + + Datasheet: http://www.smsc.com/main/catalog/emc6d102.html + + * SMSC EMC6D103 + + Prefix: 'emc6d103' + + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + + Datasheet: http://www.smsc.com/main/catalog/emc6d103.html + + * SMSC EMC6D103S + + Prefix: 'emc6d103s' + + Addresses scanned: I2C 0x2c, 0x2d, 0x2e + + Datasheet: http://www.smsc.com/main/catalog/emc6d103s.html + +Authors: + - Philip Pokorny , + - Frodo Looijaard , + - Richard Barrington , + - Margit Schubert-While , + - Justin Thiessen + +Description +----------- + +This driver implements support for the National Semiconductor LM85 and +compatible chips including the Analog Devices ADM1027, ADT7463, ADT7468 and +SMSC EMC6D10x chips family. + +The LM85 uses the 2-wire interface compatible with the SMBUS 2.0 +specification. Using an analog to digital converter it measures three (3) +temperatures and five (5) voltages. It has four (4) 16-bit counters for +measuring fan speed. Five (5) digital inputs are provided for sampling the +VID signals from the processor to the VRM. Lastly, there are three (3) PWM +outputs that can be used to control fan speed. + +The voltage inputs have internal scaling resistors so that the following +voltage can be measured without external resistors: + + 2.5V, 3.3V, 5V, 12V, and CPU core voltage (2.25V) + +The temperatures measured are one internal diode, and two remote diodes. +Remote 1 is generally the CPU temperature. These inputs are designed to +measure a thermal diode like the one in a Pentium 4 processor in a socket +423 or socket 478 package. They can also measure temperature using a +transistor like the 2N3904. + +A sophisticated control system for the PWM outputs is designed into the +LM85 that allows fan speed to be adjusted automatically based on any of the +three temperature sensors. Each PWM output is individually adjustable and +programmable. Once configured, the LM85 will adjust the PWM outputs in +response to the measured temperatures without further host intervention. +This feature can also be disabled for manual control of the PWM's. + +Each of the measured inputs (voltage, temperature, fan speed) has +corresponding high/low limit values. The LM85 will signal an ALARM if any +measured value exceeds either limit. + +The LM85 samples all inputs continuously. The lm85 driver will not read +the registers more often than once a second. Further, configuration data is +only read once each 5 minutes. There is twice as much config data as +measurements, so this would seem to be a worthwhile optimization. + +Special Features +---------------- + +The LM85 has four fan speed monitoring modes. The ADM1027 has only two. +Both have special circuitry to compensate for PWM interactions with the +TACH signal from the fans. The ADM1027 can be configured to measure the +speed of a two wire fan, but the input conditioning circuitry is different +for 3-wire and 2-wire mode. For this reason, the 2-wire fan modes are not +exposed to user control. The BIOS should initialize them to the correct +mode. If you've designed your own ADM1027, you'll have to modify the +init_client function and add an insmod parameter to set this up. + +To smooth the response of fans to changes in temperature, the LM85 has an +optional filter for smoothing temperatures. The ADM1027 has the same +config option but uses it to rate limit the changes to fan speed instead. + +The ADM1027, ADT7463 and ADT7468 have a 10-bit ADC and can therefore +measure temperatures with 0.25 degC resolution. They also provide an offset +to the temperature readings that is automatically applied during +measurement. This offset can be used to zero out any errors due to traces +and placement. The documentation says that the offset is in 0.25 degC +steps, but in initial testing of the ADM1027 it was 1.00 degC steps. Analog +Devices has confirmed this "bug". The ADT7463 is reported to work as +described in the documentation. The current lm85 driver does not show the +offset register. + +The ADT7468 has a high-frequency PWM mode, where all PWM outputs are +driven by a 22.5 kHz clock. This is a global mode, not per-PWM output, +which means that setting any PWM frequency above 11.3 kHz will switch +all 3 PWM outputs to a 22.5 kHz frequency. Conversely, setting any PWM +frequency below 11.3 kHz will switch all 3 PWM outputs to a frequency +between 10 and 100 Hz, which can then be tuned separately. + +See the vendor datasheets for more information. There is application note +from National (AN-1260) with some additional information about the LM85. +The Analog Devices datasheet is very detailed and describes a procedure for +determining an optimal configuration for the automatic PWM control. + +The SMSC EMC6D100 & EMC6D101 monitor external voltages, temperatures, and +fan speeds. They use this monitoring capability to alert the system to out +of limit conditions and can automatically control the speeds of multiple +fans in a PC or embedded system. The EMC6D101, available in a 24-pin SSOP +package, and the EMC6D100, available in a 28-pin SSOP package, are designed +to be register compatible. The EMC6D100 offers all the features of the +EMC6D101 plus additional voltage monitoring and system control features. +Unfortunately it is not possible to distinguish between the package +versions on register level so these additional voltage inputs may read +zero. EMC6D102 and EMC6D103 feature additional ADC bits thus extending precision +of voltage and temperature channels. + +SMSC EMC6D103S is similar to EMC6D103, but does not support pwm#_auto_pwm_minctl +and temp#_auto_temp_off. + +The LM96000 supports additional high frequency PWM modes (22.5 kHz, 24 kHz, +25.7 kHz, 27.7 kHz and 30 kHz), which can be configured on a per-PWM basis. + +Hardware Configurations +----------------------- + +The LM85 can be jumpered for 3 different SMBus addresses. There are +no other hardware configuration options for the LM85. + +The lm85 driver detects both LM85B and LM85C revisions of the chip. See the +datasheet for a complete description of the differences. Other than +identifying the chip, the driver behaves no differently with regard to +these two chips. The LM85B is recommended for new designs. + +The ADM1027, ADT7463 and ADT7468 chips have an optional SMBALERT output +that can be used to signal the chipset in case a limit is exceeded or the +temperature sensors fail. Individual sensor interrupts can be masked so +they won't trigger SMBALERT. The SMBALERT output if configured replaces one +of the other functions (PWM2 or IN0). This functionality is not implemented +in current driver. + +The ADT7463 and ADT7468 also have an optional THERM output/input which can +be connected to the processor PROC_HOT output. If available, the autofan +control dynamic Tmin feature can be enabled to keep the system temperature +within spec (just?!) with the least possible fan noise. + +Configuration Notes +------------------- + +Besides standard interfaces driver adds following: + +* Temperatures and Zones + +Each temperature sensor is associated with a Zone. There are three +sensors and therefore three zones (# 1, 2 and 3). Each zone has the following +temperature configuration points: + +* temp#_auto_temp_off + - temperature below which fans should be off or spinning very low. +* temp#_auto_temp_min + - temperature over which fans start to spin. +* temp#_auto_temp_max + - temperature when fans spin at full speed. +* temp#_auto_temp_crit + - temperature when all fans will run full speed. + +PWM Control +^^^^^^^^^^^ + +There are three PWM outputs. The LM85 datasheet suggests that the +pwm3 output control both fan3 and fan4. Each PWM can be individually +configured and assigned to a zone for its control value. Each PWM can be +configured individually according to the following options. + +* pwm#_auto_pwm_min + - this specifies the PWM value for temp#_auto_temp_off + temperature. (PWM value from 0 to 255) + +* pwm#_auto_pwm_minctl + - this flags selects for temp#_auto_temp_off temperature + the behaviour of fans. Write 1 to let fans spinning at + pwm#_auto_pwm_min or write 0 to let them off. + +.. note:: + + It has been reported that there is a bug in the LM85 that causes + the flag to be associated with the zones not the PWMs. This + contradicts all the published documentation. Setting pwm#_min_ctl + in this case actually affects all PWMs controlled by zone '#'. + +PWM Controlling Zone selection +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +* pwm#_auto_channels + - controls zone that is associated with PWM + +Configuration choices: + +========== ============================================= +Value Meaning +========== ============================================= + 1 Controlled by Zone 1 + 2 Controlled by Zone 2 + 3 Controlled by Zone 3 + 23 Controlled by higher temp of Zone 2 or 3 + 123 Controlled by highest temp of Zone 1, 2 or 3 + 0 PWM always 0% (off) + -1 PWM always 100% (full on) + -2 Manual control (write to 'pwm#' to set) +========== ============================================= + +The National LM85's have two vendor specific configuration +features. Tach. mode and Spinup Control. For more details on these, +see the LM85 datasheet or Application Note AN-1260. These features +are not currently supported by the lm85 driver. + +The Analog Devices ADM1027 has several vendor specific enhancements. +The number of pulses-per-rev of the fans can be set, Tach monitoring +can be optimized for PWM operation, and an offset can be applied to +the temperatures to compensate for systemic errors in the +measurements. These features are not currently supported by the lm85 +driver. + +In addition to the ADM1027 features, the ADT7463 and ADT7468 also have +Tmin control and THERM asserted counts. Automatic Tmin control acts to +adjust the Tmin value to maintain the measured temperature sensor at a +specified temperature. There isn't much documentation on this feature in +the ADT7463 data sheet. This is not supported by current driver. diff --git a/Documentation/hwmon/lm87 b/Documentation/hwmon/lm87 deleted file mode 100644 index 72fcb577ef2a..000000000000 --- a/Documentation/hwmon/lm87 +++ /dev/null @@ -1,86 +0,0 @@ -Kernel driver lm87 -================== - -Supported chips: - - * National Semiconductor LM87 - - Prefix: 'lm87' - - Addresses scanned: I2C 0x2c - 0x2e - - Datasheet: http://www.national.com/pf/LM/LM87.html - - * Analog Devices ADM1024 - - Prefix: 'adm1024' - - Addresses scanned: I2C 0x2c - 0x2e - - Datasheet: http://www.analog.com/en/prod/0,2877,ADM1024,00.html - - -Authors: - - Frodo Looijaard , - - Philip Edelbrock , - - Mark Studebaker , - - Stephen Rousset , - - Dan Eaton , - - Jean Delvare , - - Original 2.6 port Jeff Oliver - -Description ------------ - -This driver implements support for the National Semiconductor LM87 -and the Analog Devices ADM1024. - -The LM87 implements up to three temperature sensors, up to two fan -rotation speed sensors, up to seven voltage sensors, alarms, and some -miscellaneous stuff. The ADM1024 is fully compatible. - -Temperatures are measured in degrees Celsius. Each input has a high -and low alarm settings. A high limit produces an alarm when the value -goes above it, and an alarm is also produced when the value goes below -the low limit. - -Fan rotation speeds are reported in RPM (rotations per minute). An alarm is -triggered if the rotation speed has dropped below a programmable limit. Fan -readings can be divided by a programmable divider (1, 2, 4 or 8) to give -the readings more range or accuracy. Not all RPM values can accurately be -represented, so some rounding is done. With a divider of 2, the lowest -representable value is around 2600 RPM. - -Voltage sensors (also known as IN sensors) report their values in -volts. An alarm is triggered if the voltage has crossed a programmable -minimum or maximum limit. Note that minimum in this case always means -'closest to zero'; this is important for negative voltage measurements. - -If an alarm triggers, it will remain triggered until the hardware register -is read at least once. This means that the cause for the alarm may -already have disappeared! Note that in the current implementation, all -hardware registers are read whenever any data is read (unless it is less -than 1.0 seconds since the last update). This means that you can easily -miss once-only alarms. - -The lm87 driver only updates its values each 1.0 seconds; reading it more -often will do no harm, but will return 'old' values. - - -Hardware Configurations ------------------------ - -The LM87 has four pins which can serve one of two possible functions, -depending on the hardware configuration. - -Some functions share pins, so not all functions are available at the same -time. Which are depends on the hardware setup. This driver normally -assumes that firmware configured the chip correctly. Where this is not -the case, platform code must set the I2C client's platform_data to point -to a u8 value to be written to the channel register. - -For reference, here is the list of exclusive functions: - - in0+in5 (default) or temp3 - - fan1 (default) or in6 - - fan2 (default) or in7 - - VID lines (default) or IRQ lines (not handled by this driver) diff --git a/Documentation/hwmon/lm87.rst b/Documentation/hwmon/lm87.rst new file mode 100644 index 000000000000..72fcb577ef2a --- /dev/null +++ b/Documentation/hwmon/lm87.rst @@ -0,0 +1,86 @@ +Kernel driver lm87 +================== + +Supported chips: + + * National Semiconductor LM87 + + Prefix: 'lm87' + + Addresses scanned: I2C 0x2c - 0x2e + + Datasheet: http://www.national.com/pf/LM/LM87.html + + * Analog Devices ADM1024 + + Prefix: 'adm1024' + + Addresses scanned: I2C 0x2c - 0x2e + + Datasheet: http://www.analog.com/en/prod/0,2877,ADM1024,00.html + + +Authors: + - Frodo Looijaard , + - Philip Edelbrock , + - Mark Studebaker , + - Stephen Rousset , + - Dan Eaton , + - Jean Delvare , + - Original 2.6 port Jeff Oliver + +Description +----------- + +This driver implements support for the National Semiconductor LM87 +and the Analog Devices ADM1024. + +The LM87 implements up to three temperature sensors, up to two fan +rotation speed sensors, up to seven voltage sensors, alarms, and some +miscellaneous stuff. The ADM1024 is fully compatible. + +Temperatures are measured in degrees Celsius. Each input has a high +and low alarm settings. A high limit produces an alarm when the value +goes above it, and an alarm is also produced when the value goes below +the low limit. + +Fan rotation speeds are reported in RPM (rotations per minute). An alarm is +triggered if the rotation speed has dropped below a programmable limit. Fan +readings can be divided by a programmable divider (1, 2, 4 or 8) to give +the readings more range or accuracy. Not all RPM values can accurately be +represented, so some rounding is done. With a divider of 2, the lowest +representable value is around 2600 RPM. + +Voltage sensors (also known as IN sensors) report their values in +volts. An alarm is triggered if the voltage has crossed a programmable +minimum or maximum limit. Note that minimum in this case always means +'closest to zero'; this is important for negative voltage measurements. + +If an alarm triggers, it will remain triggered until the hardware register +is read at least once. This means that the cause for the alarm may +already have disappeared! Note that in the current implementation, all +hardware registers are read whenever any data is read (unless it is less +than 1.0 seconds since the last update). This means that you can easily +miss once-only alarms. + +The lm87 driver only updates its values each 1.0 seconds; reading it more +often will do no harm, but will return 'old' values. + + +Hardware Configurations +----------------------- + +The LM87 has four pins which can serve one of two possible functions, +depending on the hardware configuration. + +Some functions share pins, so not all functions are available at the same +time. Which are depends on the hardware setup. This driver normally +assumes that firmware configured the chip correctly. Where this is not +the case, platform code must set the I2C client's platform_data to point +to a u8 value to be written to the channel register. + +For reference, here is the list of exclusive functions: + - in0+in5 (default) or temp3 + - fan1 (default) or in6 + - fan2 (default) or in7 + - VID lines (default) or IRQ lines (not handled by this driver) diff --git a/Documentation/hwmon/lm90 b/Documentation/hwmon/lm90 deleted file mode 100644 index 953315987c06..000000000000 --- a/Documentation/hwmon/lm90 +++ /dev/null @@ -1,399 +0,0 @@ -Kernel driver lm90 -================== - -Supported chips: - - * National Semiconductor LM90 - - Prefix: 'lm90' - - Addresses scanned: I2C 0x4c - - Datasheet: Publicly available at the National Semiconductor website - - http://www.national.com/pf/LM/LM90.html - - * National Semiconductor LM89 - - Prefix: 'lm89' (no auto-detection) - - Addresses scanned: I2C 0x4c and 0x4d - - Datasheet: Publicly available at the National Semiconductor website - - http://www.national.com/mpf/LM/LM89.html - - * National Semiconductor LM99 - - Prefix: 'lm99' - - Addresses scanned: I2C 0x4c and 0x4d - - Datasheet: Publicly available at the National Semiconductor website - - http://www.national.com/pf/LM/LM99.html - - * National Semiconductor LM86 - - Prefix: 'lm86' - - Addresses scanned: I2C 0x4c - - Datasheet: Publicly available at the National Semiconductor website - - http://www.national.com/mpf/LM/LM86.html - - * Analog Devices ADM1032 - - Prefix: 'adm1032' - - Addresses scanned: I2C 0x4c and 0x4d - - Datasheet: Publicly available at the ON Semiconductor website - - http://www.onsemi.com/PowerSolutions/product.do?id=ADM1032 - - * Analog Devices ADT7461 - - Prefix: 'adt7461' - - Addresses scanned: I2C 0x4c and 0x4d - - Datasheet: Publicly available at the ON Semiconductor website - - http://www.onsemi.com/PowerSolutions/product.do?id=ADT7461 - - * Analog Devices ADT7461A - - Prefix: 'adt7461a' - - Addresses scanned: I2C 0x4c and 0x4d - - Datasheet: Publicly available at the ON Semiconductor website - - http://www.onsemi.com/PowerSolutions/product.do?id=ADT7461A - - * ON Semiconductor NCT1008 - - Prefix: 'nct1008' - - Addresses scanned: I2C 0x4c and 0x4d - - Datasheet: Publicly available at the ON Semiconductor website - - http://www.onsemi.com/PowerSolutions/product.do?id=NCT1008 - - * Maxim MAX6646 - - Prefix: 'max6646' - - Addresses scanned: I2C 0x4d - - Datasheet: Publicly available at the Maxim website - - http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3497 - - * Maxim MAX6647 - - Prefix: 'max6646' - - Addresses scanned: I2C 0x4e - - Datasheet: Publicly available at the Maxim website - - http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3497 - - * Maxim MAX6648 - - Prefix: 'max6646' - - Addresses scanned: I2C 0x4c - - Datasheet: Publicly available at the Maxim website - - http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3500 - - * Maxim MAX6649 - - Prefix: 'max6646' - - Addresses scanned: I2C 0x4c - - Datasheet: Publicly available at the Maxim website - - http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3497 - - * Maxim MAX6657 - - Prefix: 'max6657' - - Addresses scanned: I2C 0x4c - - Datasheet: Publicly available at the Maxim website - - http://www.maxim-ic.com/quick_view2.cfm/qv_pk/2578 - - * Maxim MAX6658 - - Prefix: 'max6657' - - Addresses scanned: I2C 0x4c - - Datasheet: Publicly available at the Maxim website - - http://www.maxim-ic.com/quick_view2.cfm/qv_pk/2578 - - * Maxim MAX6659 - - Prefix: 'max6659' - - Addresses scanned: I2C 0x4c, 0x4d, 0x4e - - Datasheet: Publicly available at the Maxim website - - http://www.maxim-ic.com/quick_view2.cfm/qv_pk/2578 - - * Maxim MAX6680 - - Prefix: 'max6680' - - Addresses scanned: I2C 0x18, 0x19, 0x1a, 0x29, 0x2a, 0x2b, - - 0x4c, 0x4d and 0x4e - - Datasheet: Publicly available at the Maxim website - - http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3370 - - * Maxim MAX6681 - - Prefix: 'max6680' - - Addresses scanned: I2C 0x18, 0x19, 0x1a, 0x29, 0x2a, 0x2b, - - 0x4c, 0x4d and 0x4e - - Datasheet: Publicly available at the Maxim website - - http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3370 - - * Maxim MAX6692 - - Prefix: 'max6646' - - Addresses scanned: I2C 0x4c - - Datasheet: Publicly available at the Maxim website - - http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3500 - - * Maxim MAX6695 - - Prefix: 'max6695' - - Addresses scanned: I2C 0x18 - - Datasheet: Publicly available at the Maxim website - - http://www.maxim-ic.com/datasheet/index.mvp/id/4199 - - * Maxim MAX6696 - - Prefix: 'max6695' - - Addresses scanned: I2C 0x18, 0x19, 0x1a, 0x29, 0x2a, 0x2b, - - 0x4c, 0x4d and 0x4e - - Datasheet: Publicly available at the Maxim website - - http://www.maxim-ic.com/datasheet/index.mvp/id/4199 - - * Winbond/Nuvoton W83L771W/G - - Prefix: 'w83l771' - - Addresses scanned: I2C 0x4c - - Datasheet: No longer available - - * Winbond/Nuvoton W83L771AWG/ASG - - Prefix: 'w83l771' - - Addresses scanned: I2C 0x4c - - Datasheet: Not publicly available, can be requested from Nuvoton - - * Philips/NXP SA56004X - - Prefix: 'sa56004' - - Addresses scanned: I2C 0x48 through 0x4F - - Datasheet: Publicly available at NXP website - - http://ics.nxp.com/products/interface/datasheet/sa56004x.pdf - - * GMT G781 - - Prefix: 'g781' - - Addresses scanned: I2C 0x4c, 0x4d - - Datasheet: Not publicly available from GMT - - * Texas Instruments TMP451 - - Prefix: 'tmp451' - - Addresses scanned: I2C 0x4c - - Datasheet: Publicly available at TI website - - http://www.ti.com/litv/pdf/sbos686 - -Author: Jean Delvare - - -Description ------------ - -The LM90 is a digital temperature sensor. It senses its own temperature as -well as the temperature of up to one external diode. It is compatible -with many other devices, many of which are supported by this driver. - -Note that there is no easy way to differentiate between the MAX6657, -MAX6658 and MAX6659 variants. The extra features of the MAX6659 are only -supported by this driver if the chip is located at address 0x4d or 0x4e, -or if the chip type is explicitly selected as max6659. -The MAX6680 and MAX6681 only differ in their pinout, therefore they obviously -can't (and don't need to) be distinguished. - -The specificity of this family of chipsets over the ADM1021/LM84 -family is that it features critical limits with hysteresis, and an -increased resolution of the remote temperature measurement. - -The different chipsets of the family are not strictly identical, although -very similar. For reference, here comes a non-exhaustive list of specific -features: - -LM90: - * Filter and alert configuration register at 0xBF. - * ALERT is triggered by temperatures over critical limits. - -LM86 and LM89: - * Same as LM90 - * Better external channel accuracy - -LM99: - * Same as LM89 - * External temperature shifted by 16 degrees down - -ADM1032: - * Consecutive alert register at 0x22. - * Conversion averaging. - * Up to 64 conversions/s. - * ALERT is triggered by open remote sensor. - * SMBus PEC support for Write Byte and Receive Byte transactions. - -ADT7461, ADT7461A, NCT1008: - * Extended temperature range (breaks compatibility) - * Lower resolution for remote temperature - -MAX6657 and MAX6658: - * Better local resolution - * Remote sensor type selection - -MAX6659: - * Better local resolution - * Selectable address - * Second critical temperature limit - * Remote sensor type selection - -MAX6680 and MAX6681: - * Selectable address - * Remote sensor type selection - -MAX6695 and MAX6696: - * Better local resolution - * Selectable address (max6696) - * Second critical temperature limit - * Two remote sensors - -W83L771W/G - * The G variant is lead-free, otherwise similar to the W. - * Filter and alert configuration register at 0xBF - * Moving average (depending on conversion rate) - -W83L771AWG/ASG - * Successor of the W83L771W/G, same features. - * The AWG and ASG variants only differ in package format. - * Diode ideality factor configuration (remote sensor) at 0xE3 - -SA56004X: - * Better local resolution - -All temperature values are given in degrees Celsius. Resolution -is 1.0 degree for the local temperature, 0.125 degree for the remote -temperature, except for the MAX6657, MAX6658 and MAX6659 which have a -resolution of 0.125 degree for both temperatures. - -Each sensor has its own high and low limits, plus a critical limit. -Additionally, there is a relative hysteresis value common to both critical -values. To make life easier to user-space applications, two absolute values -are exported, one for each channel, but these values are of course linked. -Only the local hysteresis can be set from user-space, and the same delta -applies to the remote hysteresis. - -The lm90 driver will not update its values more frequently than configured with -the update_interval attribute; reading them more often will do no harm, but will -return 'old' values. - -SMBus Alert Support -------------------- - -This driver has basic support for SMBus alert. When an alert is received, -the status register is read and the faulty temperature channel is logged. - -The Analog Devices chips (ADM1032, ADT7461 and ADT7461A) and ON -Semiconductor chips (NCT1008) do not implement the SMBus alert protocol -properly so additional care is needed: the ALERT output is disabled when -an alert is received, and is re-enabled only when the alarm is gone. -Otherwise the chip would block alerts from other chips in the bus as long -as the alarm is active. - -PEC Support ------------ - -The ADM1032 is the only chip of the family which supports PEC. It does -not support PEC on all transactions though, so some care must be taken. - -When reading a register value, the PEC byte is computed and sent by the -ADM1032 chip. However, in the case of a combined transaction (SMBus Read -Byte), the ADM1032 computes the CRC value over only the second half of -the message rather than its entirety, because it thinks the first half -of the message belongs to a different transaction. As a result, the CRC -value differs from what the SMBus master expects, and all reads fail. - -For this reason, the lm90 driver will enable PEC for the ADM1032 only if -the bus supports the SMBus Send Byte and Receive Byte transaction types. -These transactions will be used to read register values, instead of -SMBus Read Byte, and PEC will work properly. - -Additionally, the ADM1032 doesn't support SMBus Send Byte with PEC. -Instead, it will try to write the PEC value to the register (because the -SMBus Send Byte transaction with PEC is similar to a Write Byte transaction -without PEC), which is not what we want. Thus, PEC is explicitly disabled -on SMBus Send Byte transactions in the lm90 driver. - -PEC on byte data transactions represents a significant increase in bandwidth -usage (+33% for writes, +25% for reads) in normal conditions. With the need -to use two SMBus transaction for reads, this overhead jumps to +50%. Worse, -two transactions will typically mean twice as much delay waiting for -transaction completion, effectively doubling the register cache refresh time. -I guess reliability comes at a price, but it's quite expensive this time. - -So, as not everyone might enjoy the slowdown, PEC can be disabled through -sysfs. Just write 0 to the "pec" file and PEC will be disabled. Write 1 -to that file to enable PEC again. diff --git a/Documentation/hwmon/lm90.rst b/Documentation/hwmon/lm90.rst new file mode 100644 index 000000000000..953315987c06 --- /dev/null +++ b/Documentation/hwmon/lm90.rst @@ -0,0 +1,399 @@ +Kernel driver lm90 +================== + +Supported chips: + + * National Semiconductor LM90 + + Prefix: 'lm90' + + Addresses scanned: I2C 0x4c + + Datasheet: Publicly available at the National Semiconductor website + + http://www.national.com/pf/LM/LM90.html + + * National Semiconductor LM89 + + Prefix: 'lm89' (no auto-detection) + + Addresses scanned: I2C 0x4c and 0x4d + + Datasheet: Publicly available at the National Semiconductor website + + http://www.national.com/mpf/LM/LM89.html + + * National Semiconductor LM99 + + Prefix: 'lm99' + + Addresses scanned: I2C 0x4c and 0x4d + + Datasheet: Publicly available at the National Semiconductor website + + http://www.national.com/pf/LM/LM99.html + + * National Semiconductor LM86 + + Prefix: 'lm86' + + Addresses scanned: I2C 0x4c + + Datasheet: Publicly available at the National Semiconductor website + + http://www.national.com/mpf/LM/LM86.html + + * Analog Devices ADM1032 + + Prefix: 'adm1032' + + Addresses scanned: I2C 0x4c and 0x4d + + Datasheet: Publicly available at the ON Semiconductor website + + http://www.onsemi.com/PowerSolutions/product.do?id=ADM1032 + + * Analog Devices ADT7461 + + Prefix: 'adt7461' + + Addresses scanned: I2C 0x4c and 0x4d + + Datasheet: Publicly available at the ON Semiconductor website + + http://www.onsemi.com/PowerSolutions/product.do?id=ADT7461 + + * Analog Devices ADT7461A + + Prefix: 'adt7461a' + + Addresses scanned: I2C 0x4c and 0x4d + + Datasheet: Publicly available at the ON Semiconductor website + + http://www.onsemi.com/PowerSolutions/product.do?id=ADT7461A + + * ON Semiconductor NCT1008 + + Prefix: 'nct1008' + + Addresses scanned: I2C 0x4c and 0x4d + + Datasheet: Publicly available at the ON Semiconductor website + + http://www.onsemi.com/PowerSolutions/product.do?id=NCT1008 + + * Maxim MAX6646 + + Prefix: 'max6646' + + Addresses scanned: I2C 0x4d + + Datasheet: Publicly available at the Maxim website + + http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3497 + + * Maxim MAX6647 + + Prefix: 'max6646' + + Addresses scanned: I2C 0x4e + + Datasheet: Publicly available at the Maxim website + + http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3497 + + * Maxim MAX6648 + + Prefix: 'max6646' + + Addresses scanned: I2C 0x4c + + Datasheet: Publicly available at the Maxim website + + http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3500 + + * Maxim MAX6649 + + Prefix: 'max6646' + + Addresses scanned: I2C 0x4c + + Datasheet: Publicly available at the Maxim website + + http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3497 + + * Maxim MAX6657 + + Prefix: 'max6657' + + Addresses scanned: I2C 0x4c + + Datasheet: Publicly available at the Maxim website + + http://www.maxim-ic.com/quick_view2.cfm/qv_pk/2578 + + * Maxim MAX6658 + + Prefix: 'max6657' + + Addresses scanned: I2C 0x4c + + Datasheet: Publicly available at the Maxim website + + http://www.maxim-ic.com/quick_view2.cfm/qv_pk/2578 + + * Maxim MAX6659 + + Prefix: 'max6659' + + Addresses scanned: I2C 0x4c, 0x4d, 0x4e + + Datasheet: Publicly available at the Maxim website + + http://www.maxim-ic.com/quick_view2.cfm/qv_pk/2578 + + * Maxim MAX6680 + + Prefix: 'max6680' + + Addresses scanned: I2C 0x18, 0x19, 0x1a, 0x29, 0x2a, 0x2b, + + 0x4c, 0x4d and 0x4e + + Datasheet: Publicly available at the Maxim website + + http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3370 + + * Maxim MAX6681 + + Prefix: 'max6680' + + Addresses scanned: I2C 0x18, 0x19, 0x1a, 0x29, 0x2a, 0x2b, + + 0x4c, 0x4d and 0x4e + + Datasheet: Publicly available at the Maxim website + + http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3370 + + * Maxim MAX6692 + + Prefix: 'max6646' + + Addresses scanned: I2C 0x4c + + Datasheet: Publicly available at the Maxim website + + http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3500 + + * Maxim MAX6695 + + Prefix: 'max6695' + + Addresses scanned: I2C 0x18 + + Datasheet: Publicly available at the Maxim website + + http://www.maxim-ic.com/datasheet/index.mvp/id/4199 + + * Maxim MAX6696 + + Prefix: 'max6695' + + Addresses scanned: I2C 0x18, 0x19, 0x1a, 0x29, 0x2a, 0x2b, + + 0x4c, 0x4d and 0x4e + + Datasheet: Publicly available at the Maxim website + + http://www.maxim-ic.com/datasheet/index.mvp/id/4199 + + * Winbond/Nuvoton W83L771W/G + + Prefix: 'w83l771' + + Addresses scanned: I2C 0x4c + + Datasheet: No longer available + + * Winbond/Nuvoton W83L771AWG/ASG + + Prefix: 'w83l771' + + Addresses scanned: I2C 0x4c + + Datasheet: Not publicly available, can be requested from Nuvoton + + * Philips/NXP SA56004X + + Prefix: 'sa56004' + + Addresses scanned: I2C 0x48 through 0x4F + + Datasheet: Publicly available at NXP website + + http://ics.nxp.com/products/interface/datasheet/sa56004x.pdf + + * GMT G781 + + Prefix: 'g781' + + Addresses scanned: I2C 0x4c, 0x4d + + Datasheet: Not publicly available from GMT + + * Texas Instruments TMP451 + + Prefix: 'tmp451' + + Addresses scanned: I2C 0x4c + + Datasheet: Publicly available at TI website + + http://www.ti.com/litv/pdf/sbos686 + +Author: Jean Delvare + + +Description +----------- + +The LM90 is a digital temperature sensor. It senses its own temperature as +well as the temperature of up to one external diode. It is compatible +with many other devices, many of which are supported by this driver. + +Note that there is no easy way to differentiate between the MAX6657, +MAX6658 and MAX6659 variants. The extra features of the MAX6659 are only +supported by this driver if the chip is located at address 0x4d or 0x4e, +or if the chip type is explicitly selected as max6659. +The MAX6680 and MAX6681 only differ in their pinout, therefore they obviously +can't (and don't need to) be distinguished. + +The specificity of this family of chipsets over the ADM1021/LM84 +family is that it features critical limits with hysteresis, and an +increased resolution of the remote temperature measurement. + +The different chipsets of the family are not strictly identical, although +very similar. For reference, here comes a non-exhaustive list of specific +features: + +LM90: + * Filter and alert configuration register at 0xBF. + * ALERT is triggered by temperatures over critical limits. + +LM86 and LM89: + * Same as LM90 + * Better external channel accuracy + +LM99: + * Same as LM89 + * External temperature shifted by 16 degrees down + +ADM1032: + * Consecutive alert register at 0x22. + * Conversion averaging. + * Up to 64 conversions/s. + * ALERT is triggered by open remote sensor. + * SMBus PEC support for Write Byte and Receive Byte transactions. + +ADT7461, ADT7461A, NCT1008: + * Extended temperature range (breaks compatibility) + * Lower resolution for remote temperature + +MAX6657 and MAX6658: + * Better local resolution + * Remote sensor type selection + +MAX6659: + * Better local resolution + * Selectable address + * Second critical temperature limit + * Remote sensor type selection + +MAX6680 and MAX6681: + * Selectable address + * Remote sensor type selection + +MAX6695 and MAX6696: + * Better local resolution + * Selectable address (max6696) + * Second critical temperature limit + * Two remote sensors + +W83L771W/G + * The G variant is lead-free, otherwise similar to the W. + * Filter and alert configuration register at 0xBF + * Moving average (depending on conversion rate) + +W83L771AWG/ASG + * Successor of the W83L771W/G, same features. + * The AWG and ASG variants only differ in package format. + * Diode ideality factor configuration (remote sensor) at 0xE3 + +SA56004X: + * Better local resolution + +All temperature values are given in degrees Celsius. Resolution +is 1.0 degree for the local temperature, 0.125 degree for the remote +temperature, except for the MAX6657, MAX6658 and MAX6659 which have a +resolution of 0.125 degree for both temperatures. + +Each sensor has its own high and low limits, plus a critical limit. +Additionally, there is a relative hysteresis value common to both critical +values. To make life easier to user-space applications, two absolute values +are exported, one for each channel, but these values are of course linked. +Only the local hysteresis can be set from user-space, and the same delta +applies to the remote hysteresis. + +The lm90 driver will not update its values more frequently than configured with +the update_interval attribute; reading them more often will do no harm, but will +return 'old' values. + +SMBus Alert Support +------------------- + +This driver has basic support for SMBus alert. When an alert is received, +the status register is read and the faulty temperature channel is logged. + +The Analog Devices chips (ADM1032, ADT7461 and ADT7461A) and ON +Semiconductor chips (NCT1008) do not implement the SMBus alert protocol +properly so additional care is needed: the ALERT output is disabled when +an alert is received, and is re-enabled only when the alarm is gone. +Otherwise the chip would block alerts from other chips in the bus as long +as the alarm is active. + +PEC Support +----------- + +The ADM1032 is the only chip of the family which supports PEC. It does +not support PEC on all transactions though, so some care must be taken. + +When reading a register value, the PEC byte is computed and sent by the +ADM1032 chip. However, in the case of a combined transaction (SMBus Read +Byte), the ADM1032 computes the CRC value over only the second half of +the message rather than its entirety, because it thinks the first half +of the message belongs to a different transaction. As a result, the CRC +value differs from what the SMBus master expects, and all reads fail. + +For this reason, the lm90 driver will enable PEC for the ADM1032 only if +the bus supports the SMBus Send Byte and Receive Byte transaction types. +These transactions will be used to read register values, instead of +SMBus Read Byte, and PEC will work properly. + +Additionally, the ADM1032 doesn't support SMBus Send Byte with PEC. +Instead, it will try to write the PEC value to the register (because the +SMBus Send Byte transaction with PEC is similar to a Write Byte transaction +without PEC), which is not what we want. Thus, PEC is explicitly disabled +on SMBus Send Byte transactions in the lm90 driver. + +PEC on byte data transactions represents a significant increase in bandwidth +usage (+33% for writes, +25% for reads) in normal conditions. With the need +to use two SMBus transaction for reads, this overhead jumps to +50%. Worse, +two transactions will typically mean twice as much delay waiting for +transaction completion, effectively doubling the register cache refresh time. +I guess reliability comes at a price, but it's quite expensive this time. + +So, as not everyone might enjoy the slowdown, PEC can be disabled through +sysfs. Just write 0 to the "pec" file and PEC will be disabled. Write 1 +to that file to enable PEC again. diff --git a/Documentation/hwmon/lm92 b/Documentation/hwmon/lm92 deleted file mode 100644 index c131b923ed36..000000000000 --- a/Documentation/hwmon/lm92 +++ /dev/null @@ -1,48 +0,0 @@ -Kernel driver lm92 -================== - -Supported chips: - - * National Semiconductor LM92 - - Prefix: 'lm92' - - Addresses scanned: I2C 0x48 - 0x4b - - Datasheet: http://www.national.com/pf/LM/LM92.html - - * National Semiconductor LM76 - - Prefix: 'lm92' - - Addresses scanned: none, force parameter needed - - Datasheet: http://www.national.com/pf/LM/LM76.html - - * Maxim MAX6633/MAX6634/MAX6635 - - Prefix: 'max6635' - - Addresses scanned: none, force parameter needed - - Datasheet: http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3074 - - -Authors: - - Abraham van der Merwe - - Jean Delvare - - -Description ------------ - -This driver implements support for the National Semiconductor LM92 -temperature sensor. - -Each LM92 temperature sensor supports a single temperature sensor. There are -alarms for high, low, and critical thresholds. There's also an hysteresis to -control the thresholds for resetting alarms. - -Support was added later for the LM76 and Maxim MAX6633/MAX6634/MAX6635, -which are mostly compatible. They have not all been tested, so you -may need to use the force parameter. diff --git a/Documentation/hwmon/lm92.rst b/Documentation/hwmon/lm92.rst new file mode 100644 index 000000000000..c131b923ed36 --- /dev/null +++ b/Documentation/hwmon/lm92.rst @@ -0,0 +1,48 @@ +Kernel driver lm92 +================== + +Supported chips: + + * National Semiconductor LM92 + + Prefix: 'lm92' + + Addresses scanned: I2C 0x48 - 0x4b + + Datasheet: http://www.national.com/pf/LM/LM92.html + + * National Semiconductor LM76 + + Prefix: 'lm92' + + Addresses scanned: none, force parameter needed + + Datasheet: http://www.national.com/pf/LM/LM76.html + + * Maxim MAX6633/MAX6634/MAX6635 + + Prefix: 'max6635' + + Addresses scanned: none, force parameter needed + + Datasheet: http://www.maxim-ic.com/quick_view2.cfm/qv_pk/3074 + + +Authors: + - Abraham van der Merwe + - Jean Delvare + + +Description +----------- + +This driver implements support for the National Semiconductor LM92 +temperature sensor. + +Each LM92 temperature sensor supports a single temperature sensor. There are +alarms for high, low, and critical thresholds. There's also an hysteresis to +control the thresholds for resetting alarms. + +Support was added later for the LM76 and Maxim MAX6633/MAX6634/MAX6635, +which are mostly compatible. They have not all been tested, so you +may need to use the force parameter. diff --git a/Documentation/hwmon/lm93 b/Documentation/hwmon/lm93 deleted file mode 100644 index 49d199b45b67..000000000000 --- a/Documentation/hwmon/lm93 +++ /dev/null @@ -1,312 +0,0 @@ -Kernel driver lm93 -================== - -Supported chips: - - * National Semiconductor LM93 - - Prefix 'lm93' - - Addresses scanned: I2C 0x2c-0x2e - - Datasheet: http://www.national.com/ds.cgi/LM/LM93.pdf - - * National Semiconductor LM94 - - Prefix 'lm94' - - Addresses scanned: I2C 0x2c-0x2e - - Datasheet: http://www.national.com/ds.cgi/LM/LM94.pdf - - -Authors: - - Mark M. Hoffman - - Ported to 2.6 by Eric J. Bowersox - - Adapted to 2.6.20 by Carsten Emde - - Modified for mainline integration by Hans J. Koch - -Module Parameters ------------------ - -* init: integer - Set to non-zero to force some initializations (default is 0). -* disable_block: integer - A "0" allows SMBus block data transactions if the host supports them. A "1" - disables SMBus block data transactions. The default is 0. -* vccp_limit_type: integer array (2) - Configures in7 and in8 limit type, where 0 means absolute and non-zero - means relative. "Relative" here refers to "Dynamic Vccp Monitoring using - VID" from the datasheet. It greatly simplifies the interface to allow - only one set of limits (absolute or relative) to be in operation at a - time (even though the hardware is capable of enabling both). There's - not a compelling use case for enabling both at once, anyway. The default - is "0,0". -* vid_agtl: integer - A "0" configures the VID pins for V(ih) = 2.1V min, V(il) = 0.8V max. - A "1" configures the VID pins for V(ih) = 0.8V min, V(il) = 0.4V max. - (The latter setting is referred to as AGTL+ Compatible in the datasheet.) - I.e. this parameter controls the VID pin input thresholds; if your VID - inputs are not working, try changing this. The default value is "0". - - -Hardware Description --------------------- - -(from the datasheet) - -The LM93 hardware monitor has a two wire digital interface compatible with -SMBus 2.0. Using an 8-bit ADC, the LM93 measures the temperature of two remote -diode connected transistors as well as its own die and 16 power supply -voltages. To set fan speed, the LM93 has two PWM outputs that are each -controlled by up to four temperature zones. The fancontrol algorithm is lookup -table based. The LM93 includes a digital filter that can be invoked to smooth -temperature readings for better control of fan speed. The LM93 has four -tachometer inputs to measure fan speed. Limit and status registers for all -measured values are included. The LM93 builds upon the functionality of -previous motherboard management ASICs and uses some of the LM85's features -(i.e. smart tachometer mode). It also adds measurement and control support -for dynamic Vccp monitoring and PROCHOT. It is designed to monitor a dual -processor Xeon class motherboard with a minimum of external components. - -LM94 is also supported in LM93 compatible mode. Extra sensors and features of -LM94 are not supported. - - -User Interface --------------- - -#PROCHOT -^^^^^^^^ - -The LM93 can monitor two #PROCHOT signals. The results are found in the -sysfs files prochot1, prochot2, prochot1_avg, prochot2_avg, prochot1_max, -and prochot2_max. prochot1_max and prochot2_max contain the user limits -for #PROCHOT1 and #PROCHOT2, respectively. prochot1 and prochot2 contain -the current readings for the most recent complete time interval. The -value of prochot1_avg and prochot2_avg is something like a 2 period -exponential moving average (but not quite - check the datasheet). Note -that this third value is calculated by the chip itself. All values range -from 0-255 where 0 indicates no throttling, and 255 indicates > 99.6%. - -The monitoring intervals for the two #PROCHOT signals is also configurable. -These intervals can be found in the sysfs files prochot1_interval and -prochot2_interval. The values in these files specify the intervals for -#P1_PROCHOT and #P2_PROCHOT, respectively. Selecting a value not in this -list will cause the driver to use the next largest interval. The available -intervals are (in seconds): - -#PROCHOT intervals: - 0.73, 1.46, 2.9, 5.8, 11.7, 23.3, 46.6, 93.2, 186, 372 - -It is possible to configure the LM93 to logically short the two #PROCHOT -signals. I.e. when #P1_PROCHOT is asserted, the LM93 will automatically -assert #P2_PROCHOT, and vice-versa. This mode is enabled by writing a -non-zero integer to the sysfs file prochot_short. - -The LM93 can also override the #PROCHOT pins by driving a PWM signal onto -one or both of them. When overridden, the signal has a period of 3.56 ms, -a minimum pulse width of 5 clocks (at 22.5kHz => 6.25% duty cycle), and -a maximum pulse width of 80 clocks (at 22.5kHz => 99.88% duty cycle). - -The sysfs files prochot1_override and prochot2_override contain boolean -integers which enable or disable the override function for #P1_PROCHOT and -#P2_PROCHOT, respectively. The sysfs file prochot_override_duty_cycle -contains a value controlling the duty cycle for the PWM signal used when -the override function is enabled. This value ranges from 0 to 15, with 0 -indicating minimum duty cycle and 15 indicating maximum. - -#VRD_HOT -^^^^^^^^ - -The LM93 can monitor two #VRD_HOT signals. The results are found in the -sysfs files vrdhot1 and vrdhot2. There is one value per file: a boolean for -which 1 indicates #VRD_HOT is asserted and 0 indicates it is negated. These -files are read-only. - -Smart Tach Mode (from the datasheet):: - - If a fan is driven using a low-side drive PWM, the tachometer - output of the fan is corrupted. The LM93 includes smart tachometer - circuitry that allows an accurate tachometer reading to be - achieved despite the signal corruption. In smart tach mode all - four signals are measured within 4 seconds. - -Smart tach mode is enabled by the driver by writing 1 or 2 (associating the -the fan tachometer with a pwm) to the sysfs file fan_smart_tach. A zero -will disable the function for that fan. Note that Smart tach mode cannot be -enabled if the PWM output frequency is 22500 Hz (see below). - -Manual PWM -^^^^^^^^^^ - -The LM93 has a fixed or override mode for the two PWM outputs (although, there -are still some conditions that will override even this mode - see section -15.10.6 of the datasheet for details.) The sysfs files pwm1_override -and pwm2_override are used to enable this mode; each is a boolean integer -where 0 disables and 1 enables the manual control mode. The sysfs files pwm1 -and pwm2 are used to set the manual duty cycle; each is an integer (0-255) -where 0 is 0% duty cycle, and 255 is 100%. Note that the duty cycle values -are constrained by the hardware. Selecting a value which is not available -will cause the driver to use the next largest value. Also note: when manual -PWM mode is disabled, the value of pwm1 and pwm2 indicates the current duty -cycle chosen by the h/w. - -PWM Output Frequency -^^^^^^^^^^^^^^^^^^^^ - -The LM93 supports several different frequencies for the PWM output channels. -The sysfs files pwm1_freq and pwm2_freq are used to select the frequency. The -frequency values are constrained by the hardware. Selecting a value which is -not available will cause the driver to use the next largest value. Also note -that this parameter has implications for the Smart Tach Mode (see above). - -PWM Output Frequencies (in Hz): - 12, 36, 48, 60, 72, 84, 96, 22500 (default) - -Automatic PWM -^^^^^^^^^^^^^ - -The LM93 is capable of complex automatic fan control, with many different -points of configuration. To start, each PWM output can be bound to any -combination of eight control sources. The final PWM is the largest of all -individual control sources to which the PWM output is bound. - -The eight control sources are: temp1-temp4 (aka "zones" in the datasheet), -#PROCHOT 1 & 2, and #VRDHOT 1 & 2. The bindings are expressed as a bitmask -in the sysfs files pwm_auto_channels, where a "1" enables the binding, and -a "0" disables it. The h/w default is 0x0f (all temperatures bound). - - ====== =========== - 0x01 Temp 1 - 0x02 Temp 2 - 0x04 Temp 3 - 0x08 Temp 4 - 0x10 #PROCHOT 1 - 0x20 #PROCHOT 2 - 0x40 #VRDHOT 1 - 0x80 #VRDHOT 2 - ====== =========== - -The function y = f(x) takes a source temperature x to a PWM output y. This -function of the LM93 is derived from a base temperature and a table of 12 -temperature offsets. The base temperature is expressed in degrees C in the -sysfs files temp_auto_base. The offsets are expressed in cumulative -degrees C, with the value of offset for temperature value being -contained in the file temp_auto_offset. E.g. if the base temperature -is 40C: - - ========== ======================= =============== ======= - offset # temp_auto_offset range pwm - ========== ======================= =============== ======= - 1 0 - 25.00% - 2 0 - 28.57% - 3 1 40C - 41C 32.14% - 4 1 41C - 42C 35.71% - 5 2 42C - 44C 39.29% - 6 2 44C - 46C 42.86% - 7 2 48C - 50C 46.43% - 8 2 50C - 52C 50.00% - 9 2 52C - 54C 53.57% - 10 2 54C - 56C 57.14% - 11 2 56C - 58C 71.43% - 12 2 58C - 60C 85.71% - - - > 60C 100.00% - ========== ======================= =============== ======= - -Valid offsets are in the range 0C <= x <= 7.5C in 0.5C increments. - -There is an independent base temperature for each temperature channel. Note, -however, there are only two tables of offsets: one each for temp[12] and -temp[34]. Therefore, any change to e.g. temp1_auto_offset will also -affect temp2_auto_offset. - -The LM93 can also apply hysteresis to the offset table, to prevent unwanted -oscillation between two steps in the offsets table. These values are found in -the sysfs files temp_auto_offset_hyst. The value in this file has the -same representation as in temp_auto_offset. - -If a temperature reading falls below the base value for that channel, the LM93 -will use the minimum PWM value. These values are found in the sysfs files -temp_auto_pwm_min. Note, there are only two minimums: one each for temp[12] -and temp[34]. Therefore, any change to e.g. temp1_auto_pwm_min will also -affect temp2_auto_pwm_min. - -PWM Spin-Up Cycle -^^^^^^^^^^^^^^^^^ - -A spin-up cycle occurs when a PWM output is commanded from 0% duty cycle to -some value > 0%. The LM93 supports a minimum duty cycle during spin-up. These -values are found in the sysfs files pwm_auto_spinup_min. The value in this -file has the same representation as other PWM duty cycle values. The -duration of the spin-up cycle is also configurable. These values are found in -the sysfs files pwm_auto_spinup_time. The value in this file is -the spin-up time in seconds. The available spin-up times are constrained by -the hardware. Selecting a value which is not available will cause the driver -to use the next largest value. - -Spin-up Durations: - 0 (disabled, h/w default), 0.1, 0.25, 0.4, 0.7, 1.0, 2.0, 4.0 - -#PROCHOT and #VRDHOT PWM Ramping -^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ - -If the #PROCHOT or #VRDHOT signals are asserted while bound to a PWM output -channel, the LM93 will ramp the PWM output up to 100% duty cycle in discrete -steps. The duration of each step is configurable. There are two files, with -one value each in seconds: pwm_auto_prochot_ramp and pwm_auto_vrdhot_ramp. -The available ramp times are constrained by the hardware. Selecting a value -which is not available will cause the driver to use the next largest value. - -Ramp Times: - 0 (disabled, h/w default) to 0.75 in 0.05 second intervals - -Fan Boost -^^^^^^^^^ - -For each temperature channel, there is a boost temperature: if the channel -exceeds this limit, the LM93 will immediately drive both PWM outputs to 100%. -This limit is expressed in degrees C in the sysfs files temp_auto_boost. -There is also a hysteresis temperature for this function: after the boost -limit is reached, the temperature channel must drop below this value before -the boost function is disabled. This temperature is also expressed in degrees -C in the sysfs files temp_auto_boost_hyst. - -GPIO Pins -^^^^^^^^^ - -The LM93 can monitor the logic level of four dedicated GPIO pins as well as the -four tach input pins. GPIO0-GPIO3 correspond to (fan) tach 1-4, respectively. -All eight GPIOs are read by reading the bitmask in the sysfs file gpio. The -LSB is GPIO0, and the MSB is GPIO7. - - -LM93 Unique sysfs Files ------------------------ - -=========================== =============================================== -file description -=========================== =============================================== -prochot current #PROCHOT % -prochot_avg moving average #PROCHOT % -prochot_max limit #PROCHOT % -prochot_short enable or disable logical #PROCHOT pin short -prochot_override force #PROCHOT assertion as PWM -prochot_override_duty_cycle duty cycle for the PWM signal used when - #PROCHOT is overridden -prochot_interval #PROCHOT PWM sampling interval -vrdhot 0 means negated, 1 means asserted -fan_smart_tach enable or disable smart tach mode -pwm_auto_channels select control sources for PWM outputs -pwm_auto_spinup_min minimum duty cycle during spin-up -pwm_auto_spinup_time duration of spin-up -pwm_auto_prochot_ramp ramp time per step when #PROCHOT asserted -pwm_auto_vrdhot_ramp ramp time per step when #VRDHOT asserted -temp_auto_base temperature channel base -temp_auto_offset[1-12] temperature channel offsets -temp_auto_offset_hyst temperature channel offset hysteresis -temp_auto_boost temperature channel boost (PWMs to 100%) - limit -temp_auto_boost_hyst temperature channel boost hysteresis -gpio input state of 8 GPIO pins; read-only -=========================== =============================================== diff --git a/Documentation/hwmon/lm93.rst b/Documentation/hwmon/lm93.rst new file mode 100644 index 000000000000..49d199b45b67 --- /dev/null +++ b/Documentation/hwmon/lm93.rst @@ -0,0 +1,312 @@ +Kernel driver lm93 +================== + +Supported chips: + + * National Semiconductor LM93 + + Prefix 'lm93' + + Addresses scanned: I2C 0x2c-0x2e + + Datasheet: http://www.national.com/ds.cgi/LM/LM93.pdf + + * National Semiconductor LM94 + + Prefix 'lm94' + + Addresses scanned: I2C 0x2c-0x2e + + Datasheet: http://www.national.com/ds.cgi/LM/LM94.pdf + + +Authors: + - Mark M. Hoffman + - Ported to 2.6 by Eric J. Bowersox + - Adapted to 2.6.20 by Carsten Emde + - Modified for mainline integration by Hans J. Koch + +Module Parameters +----------------- + +* init: integer + Set to non-zero to force some initializations (default is 0). +* disable_block: integer + A "0" allows SMBus block data transactions if the host supports them. A "1" + disables SMBus block data transactions. The default is 0. +* vccp_limit_type: integer array (2) + Configures in7 and in8 limit type, where 0 means absolute and non-zero + means relative. "Relative" here refers to "Dynamic Vccp Monitoring using + VID" from the datasheet. It greatly simplifies the interface to allow + only one set of limits (absolute or relative) to be in operation at a + time (even though the hardware is capable of enabling both). There's + not a compelling use case for enabling both at once, anyway. The default + is "0,0". +* vid_agtl: integer + A "0" configures the VID pins for V(ih) = 2.1V min, V(il) = 0.8V max. + A "1" configures the VID pins for V(ih) = 0.8V min, V(il) = 0.4V max. + (The latter setting is referred to as AGTL+ Compatible in the datasheet.) + I.e. this parameter controls the VID pin input thresholds; if your VID + inputs are not working, try changing this. The default value is "0". + + +Hardware Description +-------------------- + +(from the datasheet) + +The LM93 hardware monitor has a two wire digital interface compatible with +SMBus 2.0. Using an 8-bit ADC, the LM93 measures the temperature of two remote +diode connected transistors as well as its own die and 16 power supply +voltages. To set fan speed, the LM93 has two PWM outputs that are each +controlled by up to four temperature zones. The fancontrol algorithm is lookup +table based. The LM93 includes a digital filter that can be invoked to smooth +temperature readings for better control of fan speed. The LM93 has four +tachometer inputs to measure fan speed. Limit and status registers for all +measured values are included. The LM93 builds upon the functionality of +previous motherboard management ASICs and uses some of the LM85's features +(i.e. smart tachometer mode). It also adds measurement and control support +for dynamic Vccp monitoring and PROCHOT. It is designed to monitor a dual +processor Xeon class motherboard with a minimum of external components. + +LM94 is also supported in LM93 compatible mode. Extra sensors and features of +LM94 are not supported. + + +User Interface +-------------- + +#PROCHOT +^^^^^^^^ + +The LM93 can monitor two #PROCHOT signals. The results are found in the +sysfs files prochot1, prochot2, prochot1_avg, prochot2_avg, prochot1_max, +and prochot2_max. prochot1_max and prochot2_max contain the user limits +for #PROCHOT1 and #PROCHOT2, respectively. prochot1 and prochot2 contain +the current readings for the most recent complete time interval. The +value of prochot1_avg and prochot2_avg is something like a 2 period +exponential moving average (but not quite - check the datasheet). Note +that this third value is calculated by the chip itself. All values range +from 0-255 where 0 indicates no throttling, and 255 indicates > 99.6%. + +The monitoring intervals for the two #PROCHOT signals is also configurable. +These intervals can be found in the sysfs files prochot1_interval and +prochot2_interval. The values in these files specify the intervals for +#P1_PROCHOT and #P2_PROCHOT, respectively. Selecting a value not in this +list will cause the driver to use the next largest interval. The available +intervals are (in seconds): + +#PROCHOT intervals: + 0.73, 1.46, 2.9, 5.8, 11.7, 23.3, 46.6, 93.2, 186, 372 + +It is possible to configure the LM93 to logically short the two #PROCHOT +signals. I.e. when #P1_PROCHOT is asserted, the LM93 will automatically +assert #P2_PROCHOT, and vice-versa. This mode is enabled by writing a +non-zero integer to the sysfs file prochot_short. + +The LM93 can also override the #PROCHOT pins by driving a PWM signal onto +one or both of them. When overridden, the signal has a period of 3.56 ms, +a minimum pulse width of 5 clocks (at 22.5kHz => 6.25% duty cycle), and +a maximum pulse width of 80 clocks (at 22.5kHz => 99.88% duty cycle). + +The sysfs files prochot1_override and prochot2_override contain boolean +integers which enable or disable the override function for #P1_PROCHOT and +#P2_PROCHOT, respectively. The sysfs file prochot_override_duty_cycle +contains a value controlling the duty cycle for the PWM signal used when +the override function is enabled. This value ranges from 0 to 15, with 0 +indicating minimum duty cycle and 15 indicating maximum. + +#VRD_HOT +^^^^^^^^ + +The LM93 can monitor two #VRD_HOT signals. The results are found in the +sysfs files vrdhot1 and vrdhot2. There is one value per file: a boolean for +which 1 indicates #VRD_HOT is asserted and 0 indicates it is negated. These +files are read-only. + +Smart Tach Mode (from the datasheet):: + + If a fan is driven using a low-side drive PWM, the tachometer + output of the fan is corrupted. The LM93 includes smart tachometer + circuitry that allows an accurate tachometer reading to be + achieved despite the signal corruption. In smart tach mode all + four signals are measured within 4 seconds. + +Smart tach mode is enabled by the driver by writing 1 or 2 (associating the +the fan tachometer with a pwm) to the sysfs file fan_smart_tach. A zero +will disable the function for that fan. Note that Smart tach mode cannot be +enabled if the PWM output frequency is 22500 Hz (see below). + +Manual PWM +^^^^^^^^^^ + +The LM93 has a fixed or override mode for the two PWM outputs (although, there +are still some conditions that will override even this mode - see section +15.10.6 of the datasheet for details.) The sysfs files pwm1_override +and pwm2_override are used to enable this mode; each is a boolean integer +where 0 disables and 1 enables the manual control mode. The sysfs files pwm1 +and pwm2 are used to set the manual duty cycle; each is an integer (0-255) +where 0 is 0% duty cycle, and 255 is 100%. Note that the duty cycle values +are constrained by the hardware. Selecting a value which is not available +will cause the driver to use the next largest value. Also note: when manual +PWM mode is disabled, the value of pwm1 and pwm2 indicates the current duty +cycle chosen by the h/w. + +PWM Output Frequency +^^^^^^^^^^^^^^^^^^^^ + +The LM93 supports several different frequencies for the PWM output channels. +The sysfs files pwm1_freq and pwm2_freq are used to select the frequency. The +frequency values are constrained by the hardware. Selecting a value which is +not available will cause the driver to use the next largest value. Also note +that this parameter has implications for the Smart Tach Mode (see above). + +PWM Output Frequencies (in Hz): + 12, 36, 48, 60, 72, 84, 96, 22500 (default) + +Automatic PWM +^^^^^^^^^^^^^ + +The LM93 is capable of complex automatic fan control, with many different +points of configuration. To start, each PWM output can be bound to any +combination of eight control sources. The final PWM is the largest of all +individual control sources to which the PWM output is bound. + +The eight control sources are: temp1-temp4 (aka "zones" in the datasheet), +#PROCHOT 1 & 2, and #VRDHOT 1 & 2. The bindings are expressed as a bitmask +in the sysfs files pwm_auto_channels, where a "1" enables the binding, and +a "0" disables it. The h/w default is 0x0f (all temperatures bound). + + ====== =========== + 0x01 Temp 1 + 0x02 Temp 2 + 0x04 Temp 3 + 0x08 Temp 4 + 0x10 #PROCHOT 1 + 0x20 #PROCHOT 2 + 0x40 #VRDHOT 1 + 0x80 #VRDHOT 2 + ====== =========== + +The function y = f(x) takes a source temperature x to a PWM output y. This +function of the LM93 is derived from a base temperature and a table of 12 +temperature offsets. The base temperature is expressed in degrees C in the +sysfs files temp_auto_base. The offsets are expressed in cumulative +degrees C, with the value of offset for temperature value being +contained in the file temp_auto_offset. E.g. if the base temperature +is 40C: + + ========== ======================= =============== ======= + offset # temp_auto_offset range pwm + ========== ======================= =============== ======= + 1 0 - 25.00% + 2 0 - 28.57% + 3 1 40C - 41C 32.14% + 4 1 41C - 42C 35.71% + 5 2 42C - 44C 39.29% + 6 2 44C - 46C 42.86% + 7 2 48C - 50C 46.43% + 8 2 50C - 52C 50.00% + 9 2 52C - 54C 53.57% + 10 2 54C - 56C 57.14% + 11 2 56C - 58C 71.43% + 12 2 58C - 60C 85.71% + - - > 60C 100.00% + ========== ======================= =============== ======= + +Valid offsets are in the range 0C <= x <= 7.5C in 0.5C increments. + +There is an independent base temperature for each temperature channel. Note, +however, there are only two tables of offsets: one each for temp[12] and +temp[34]. Therefore, any change to e.g. temp1_auto_offset will also +affect temp2_auto_offset. + +The LM93 can also apply hysteresis to the offset table, to prevent unwanted +oscillation between two steps in the offsets table. These values are found in +the sysfs files temp_auto_offset_hyst. The value in this file has the +same representation as in temp_auto_offset. + +If a temperature reading falls below the base value for that channel, the LM93 +will use the minimum PWM value. These values are found in the sysfs files +temp_auto_pwm_min. Note, there are only two minimums: one each for temp[12] +and temp[34]. Therefore, any change to e.g. temp1_auto_pwm_min will also +affect temp2_auto_pwm_min. + +PWM Spin-Up Cycle +^^^^^^^^^^^^^^^^^ + +A spin-up cycle occurs when a PWM output is commanded from 0% duty cycle to +some value > 0%. The LM93 supports a minimum duty cycle during spin-up. These +values are found in the sysfs files pwm_auto_spinup_min. The value in this +file has the same representation as other PWM duty cycle values. The +duration of the spin-up cycle is also configurable. These values are found in +the sysfs files pwm_auto_spinup_time. The value in this file is +the spin-up time in seconds. The available spin-up times are constrained by +the hardware. Selecting a value which is not available will cause the driver +to use the next largest value. + +Spin-up Durations: + 0 (disabled, h/w default), 0.1, 0.25, 0.4, 0.7, 1.0, 2.0, 4.0 + +#PROCHOT and #VRDHOT PWM Ramping +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +If the #PROCHOT or #VRDHOT signals are asserted while bound to a PWM output +channel, the LM93 will ramp the PWM output up to 100% duty cycle in discrete +steps. The duration of each step is configurable. There are two files, with +one value each in seconds: pwm_auto_prochot_ramp and pwm_auto_vrdhot_ramp. +The available ramp times are constrained by the hardware. Selecting a value +which is not available will cause the driver to use the next largest value. + +Ramp Times: + 0 (disabled, h/w default) to 0.75 in 0.05 second intervals + +Fan Boost +^^^^^^^^^ + +For each temperature channel, there is a boost temperature: if the channel +exceeds this limit, the LM93 will immediately drive both PWM outputs to 100%. +This limit is expressed in degrees C in the sysfs files temp_auto_boost. +There is also a hysteresis temperature for this function: after the boost +limit is reached, the temperature channel must drop below this value before +the boost function is disabled. This temperature is also expressed in degrees +C in the sysfs files temp_auto_boost_hyst. + +GPIO Pins +^^^^^^^^^ + +The LM93 can monitor the logic level of four dedicated GPIO pins as well as the +four tach input pins. GPIO0-GPIO3 correspond to (fan) tach 1-4, respectively. +All eight GPIOs are read by reading the bitmask in the sysfs file gpio. The +LSB is GPIO0, and the MSB is GPIO7. + + +LM93 Unique sysfs Files +----------------------- + +=========================== =============================================== +file description +=========================== =============================================== +prochot current #PROCHOT % +prochot_avg moving average #PROCHOT % +prochot_max limit #PROCHOT % +prochot_short enable or disable logical #PROCHOT pin short +prochot_override force #PROCHOT assertion as PWM +prochot_override_duty_cycle duty cycle for the PWM signal used when + #PROCHOT is overridden +prochot_interval #PROCHOT PWM sampling interval +vrdhot 0 means negated, 1 means asserted +fan_smart_tach enable or disable smart tach mode +pwm_auto_channels select control sources for PWM outputs +pwm_auto_spinup_min minimum duty cycle during spin-up +pwm_auto_spinup_time duration of spin-up +pwm_auto_prochot_ramp ramp time per step when #PROCHOT asserted +pwm_auto_vrdhot_ramp ramp time per step when #VRDHOT asserted +temp_auto_base temperature channel base +temp_auto_offset[1-12] temperature channel offsets +temp_auto_offset_hyst temperature channel offset hysteresis +temp_auto_boost temperature channel boost (PWMs to 100%) + limit +temp_auto_boost_hyst temperature channel boost hysteresis +gpio input state of 8 GPIO pins; read-only +=========================== =============================================== diff --git a/Documentation/hwmon/lm95234 b/Documentation/hwmon/lm95234 deleted file mode 100644 index e4c14bea5efd..000000000000 --- a/Documentation/hwmon/lm95234 +++ /dev/null @@ -1,48 +0,0 @@ -Kernel driver lm95234 -===================== - -Supported chips: - - * National Semiconductor / Texas Instruments LM95233 - - Addresses scanned: I2C 0x18, 0x2a, 0x2b - - Datasheet: Publicly available at the Texas Instruments website - - http://www.ti.com/product/lm95233 - - * National Semiconductor / Texas Instruments LM95234 - - Addresses scanned: I2C 0x18, 0x4d, 0x4e - - Datasheet: Publicly available at the Texas Instruments website - - http://www.ti.com/product/lm95234 - -Author: Guenter Roeck - -Description ------------ - -LM95233 and LM95234 are 11-bit digital temperature sensors with a 2-wire -System Management Bus (SMBus) interface and TrueTherm technology -that can very accurately monitor the temperature of two (LM95233) -or four (LM95234) remote diodes as well as its own temperature. -The remote diodes can be external devices such as microprocessors, -graphics processors or diode-connected 2N3904s. The chip's TruTherm -beta compensation technology allows sensing of 90 nm or 65 nm process -thermal diodes accurately. - -All temperature values are given in millidegrees Celsius. Temperature -is provided within a range of -127 to +255 degrees (+127.875 degrees for -the internal sensor). Resolution depends on temperature input and range. - -Each sensor has its own maximum limit, but the hysteresis is common to all -channels. The hysteresis is configurable with the tem1_max_hyst attribute and -affects the hysteresis on all channels. The first two external sensors also -have a critical limit. - -The lm95234 driver can change its update interval to a fixed set of values. -It will round up to the next selectable interval. See the datasheet for exact -values. Reading sensor values more often will do no harm, but will return -'old' values. diff --git a/Documentation/hwmon/lm95234.rst b/Documentation/hwmon/lm95234.rst new file mode 100644 index 000000000000..e4c14bea5efd --- /dev/null +++ b/Documentation/hwmon/lm95234.rst @@ -0,0 +1,48 @@ +Kernel driver lm95234 +===================== + +Supported chips: + + * National Semiconductor / Texas Instruments LM95233 + + Addresses scanned: I2C 0x18, 0x2a, 0x2b + + Datasheet: Publicly available at the Texas Instruments website + + http://www.ti.com/product/lm95233 + + * National Semiconductor / Texas Instruments LM95234 + + Addresses scanned: I2C 0x18, 0x4d, 0x4e + + Datasheet: Publicly available at the Texas Instruments website + + http://www.ti.com/product/lm95234 + +Author: Guenter Roeck + +Description +----------- + +LM95233 and LM95234 are 11-bit digital temperature sensors with a 2-wire +System Management Bus (SMBus) interface and TrueTherm technology +that can very accurately monitor the temperature of two (LM95233) +or four (LM95234) remote diodes as well as its own temperature. +The remote diodes can be external devices such as microprocessors, +graphics processors or diode-connected 2N3904s. The chip's TruTherm +beta compensation technology allows sensing of 90 nm or 65 nm process +thermal diodes accurately. + +All temperature values are given in millidegrees Celsius. Temperature +is provided within a range of -127 to +255 degrees (+127.875 degrees for +the internal sensor). Resolution depends on temperature input and range. + +Each sensor has its own maximum limit, but the hysteresis is common to all +channels. The hysteresis is configurable with the tem1_max_hyst attribute and +affects the hysteresis on all channels. The first two external sensors also +have a critical limit. + +The lm95234 driver can change its update interval to a fixed set of values. +It will round up to the next selectable interval. See the datasheet for exact +values. Reading sensor values more often will do no harm, but will return +'old' values. diff --git a/Documentation/hwmon/lm95245 b/Documentation/hwmon/lm95245 deleted file mode 100644 index 566d1dc8c5a6..000000000000 --- a/Documentation/hwmon/lm95245 +++ /dev/null @@ -1,48 +0,0 @@ -Kernel driver lm95245 -===================== - -Supported chips: - - * TI LM95235 - - Addresses scanned: I2C 0x18, 0x29, 0x4c - - Datasheet: Publicly available at the TI website - - http://www.ti.com/lit/ds/symlink/lm95235.pdf - - * TI / National Semiconductor LM95245 - - Addresses scanned: I2C 0x18, 0x19, 0x29, 0x4c, 0x4d - - Datasheet: Publicly available at the TI website - - http://www.ti.com/lit/ds/symlink/lm95245.pdf - -Author: Alexander Stein - -Description ------------ - -LM95235 and LM95245 are 11-bit digital temperature sensors with a 2-wire System -Management Bus (SMBus) interface and TruTherm technology that can monitor -the temperature of a remote diode as well as its own temperature. -The chips can be used to very accurately monitor the temperature of -external devices such as microprocessors. - -All temperature values are given in millidegrees Celsius. Local temperature -is given within a range of -127 to +127.875 degrees. Remote temperatures are -given within a range of -127 to +255 degrees. Resolution depends on -temperature input and range. - -Each sensor has its own critical limit. Additionally, there is a relative -hysteresis value common to both critical limits. To make life easier to -user-space applications, two absolute values are exported, one for each -channel, but these values are of course linked. Only the local hysteresis -can be set from user-space, and the same delta applies to the remote -hysteresis. - -The lm95245 driver can change its update interval to a fixed set of values. -It will round up to the next selectable interval. See the datasheet for exact -values. Reading sensor values more often will do no harm, but will return -'old' values. diff --git a/Documentation/hwmon/lm95245.rst b/Documentation/hwmon/lm95245.rst new file mode 100644 index 000000000000..566d1dc8c5a6 --- /dev/null +++ b/Documentation/hwmon/lm95245.rst @@ -0,0 +1,48 @@ +Kernel driver lm95245 +===================== + +Supported chips: + + * TI LM95235 + + Addresses scanned: I2C 0x18, 0x29, 0x4c + + Datasheet: Publicly available at the TI website + + http://www.ti.com/lit/ds/symlink/lm95235.pdf + + * TI / National Semiconductor LM95245 + + Addresses scanned: I2C 0x18, 0x19, 0x29, 0x4c, 0x4d + + Datasheet: Publicly available at the TI website + + http://www.ti.com/lit/ds/symlink/lm95245.pdf + +Author: Alexander Stein + +Description +----------- + +LM95235 and LM95245 are 11-bit digital temperature sensors with a 2-wire System +Management Bus (SMBus) interface and TruTherm technology that can monitor +the temperature of a remote diode as well as its own temperature. +The chips can be used to very accurately monitor the temperature of +external devices such as microprocessors. + +All temperature values are given in millidegrees Celsius. Local temperature +is given within a range of -127 to +127.875 degrees. Remote temperatures are +given within a range of -127 to +255 degrees. Resolution depends on +temperature input and range. + +Each sensor has its own critical limit. Additionally, there is a relative +hysteresis value common to both critical limits. To make life easier to +user-space applications, two absolute values are exported, one for each +channel, but these values are of course linked. Only the local hysteresis +can be set from user-space, and the same delta applies to the remote +hysteresis. + +The lm95245 driver can change its update interval to a fixed set of values. +It will round up to the next selectable interval. See the datasheet for exact +values. Reading sensor values more often will do no harm, but will return +'old' values. diff --git a/Documentation/hwmon/ltc2945 b/Documentation/hwmon/ltc2945 deleted file mode 100644 index 20c884985367..000000000000 --- a/Documentation/hwmon/ltc2945 +++ /dev/null @@ -1,92 +0,0 @@ -Kernel driver ltc2945 -===================== - -Supported chips: - - * Linear Technology LTC2945 - - Prefix: 'ltc2945' - - Addresses scanned: - - - Datasheet: - - http://cds.linear.com/docs/en/datasheet/2945fa.pdf - -Author: Guenter Roeck - - -Description ------------ - -The LTC2945 is a rail-to-rail system monitor that measures current, voltage, -and power consumption. - - -Usage Notes ------------ - -This driver does not probe for LTC2945 devices, since there is no register -which can be safely used to identify the chip. You will have to instantiate -the devices explicitly. - -Example: the following will load the driver for an LTC2945 at address 0x10 -on I2C bus #1:: - - $ modprobe ltc2945 - $ echo ltc2945 0x10 > /sys/bus/i2c/devices/i2c-1/new_device - - -Sysfs entries -------------- - -Voltage readings provided by this driver are reported as obtained from the ADC -registers. If a set of voltage divider resistors is installed, calculate the -real voltage by multiplying the reported value with (R1+R2)/R2, where R1 is the -value of the divider resistor against the measured voltage and R2 is the value -of the divider resistor against Ground. - -Current reading provided by this driver is reported as obtained from the ADC -Current Sense register. The reported value assumes that a 1 mOhm sense resistor -is installed. If a different sense resistor is installed, calculate the real -current by dividing the reported value by the sense resistor value in mOhm. - -======================= ======================================================== -in1_input VIN voltage (mV). Voltage is measured either at - SENSE+ or VDD pin depending on chip configuration. -in1_min Undervoltage threshold -in1_max Overvoltage threshold -in1_lowest Lowest measured voltage -in1_highest Highest measured voltage -in1_reset_history Write 1 to reset in1 history -in1_min_alarm Undervoltage alarm -in1_max_alarm Overvoltage alarm - -in2_input ADIN voltage (mV) -in2_min Undervoltage threshold -in2_max Overvoltage threshold -in2_lowest Lowest measured voltage -in2_highest Highest measured voltage -in2_reset_history Write 1 to reset in2 history -in2_min_alarm Undervoltage alarm -in2_max_alarm Overvoltage alarm - -curr1_input SENSE current (mA) -curr1_min Undercurrent threshold -curr1_max Overcurrent threshold -curr1_lowest Lowest measured current -curr1_highest Highest measured current -curr1_reset_history Write 1 to reset curr1 history -curr1_min_alarm Undercurrent alarm -curr1_max_alarm Overcurrent alarm - -power1_input Power (in uW). Power is calculated based on SENSE+/VDD - voltage or ADIN voltage depending on chip configuration. -power1_min Low lower threshold -power1_max High power threshold -power1_input_lowest Historical minimum power use -power1_input_highest Historical maximum power use -power1_reset_history Write 1 to reset power1 history -power1_min_alarm Low power alarm -power1_max_alarm High power alarm -======================= ======================================================== diff --git a/Documentation/hwmon/ltc2945.rst b/Documentation/hwmon/ltc2945.rst new file mode 100644 index 000000000000..20c884985367 --- /dev/null +++ b/Documentation/hwmon/ltc2945.rst @@ -0,0 +1,92 @@ +Kernel driver ltc2945 +===================== + +Supported chips: + + * Linear Technology LTC2945 + + Prefix: 'ltc2945' + + Addresses scanned: - + + Datasheet: + + http://cds.linear.com/docs/en/datasheet/2945fa.pdf + +Author: Guenter Roeck + + +Description +----------- + +The LTC2945 is a rail-to-rail system monitor that measures current, voltage, +and power consumption. + + +Usage Notes +----------- + +This driver does not probe for LTC2945 devices, since there is no register +which can be safely used to identify the chip. You will have to instantiate +the devices explicitly. + +Example: the following will load the driver for an LTC2945 at address 0x10 +on I2C bus #1:: + + $ modprobe ltc2945 + $ echo ltc2945 0x10 > /sys/bus/i2c/devices/i2c-1/new_device + + +Sysfs entries +------------- + +Voltage readings provided by this driver are reported as obtained from the ADC +registers. If a set of voltage divider resistors is installed, calculate the +real voltage by multiplying the reported value with (R1+R2)/R2, where R1 is the +value of the divider resistor against the measured voltage and R2 is the value +of the divider resistor against Ground. + +Current reading provided by this driver is reported as obtained from the ADC +Current Sense register. The reported value assumes that a 1 mOhm sense resistor +is installed. If a different sense resistor is installed, calculate the real +current by dividing the reported value by the sense resistor value in mOhm. + +======================= ======================================================== +in1_input VIN voltage (mV). Voltage is measured either at + SENSE+ or VDD pin depending on chip configuration. +in1_min Undervoltage threshold +in1_max Overvoltage threshold +in1_lowest Lowest measured voltage +in1_highest Highest measured voltage +in1_reset_history Write 1 to reset in1 history +in1_min_alarm Undervoltage alarm +in1_max_alarm Overvoltage alarm + +in2_input ADIN voltage (mV) +in2_min Undervoltage threshold +in2_max Overvoltage threshold +in2_lowest Lowest measured voltage +in2_highest Highest measured voltage +in2_reset_history Write 1 to reset in2 history +in2_min_alarm Undervoltage alarm +in2_max_alarm Overvoltage alarm + +curr1_input SENSE current (mA) +curr1_min Undercurrent threshold +curr1_max Overcurrent threshold +curr1_lowest Lowest measured current +curr1_highest Highest measured current +curr1_reset_history Write 1 to reset curr1 history +curr1_min_alarm Undercurrent alarm +curr1_max_alarm Overcurrent alarm + +power1_input Power (in uW). Power is calculated based on SENSE+/VDD + voltage or ADIN voltage depending on chip configuration. +power1_min Low lower threshold +power1_max High power threshold +power1_input_lowest Historical minimum power use +power1_input_highest Historical maximum power use +power1_reset_history Write 1 to reset power1 history +power1_min_alarm Low power alarm +power1_max_alarm High power alarm +======================= ======================================================== diff --git a/Documentation/hwmon/ltc2978 b/Documentation/hwmon/ltc2978 deleted file mode 100644 index 01a24fd6d5fe..000000000000 --- a/Documentation/hwmon/ltc2978 +++ /dev/null @@ -1,355 +0,0 @@ -Kernel driver ltc2978 -===================== - -Supported chips: - - * Linear Technology LTC2974 - - Prefix: 'ltc2974' - - Addresses scanned: - - - Datasheet: http://www.linear.com/product/ltc2974 - - * Linear Technology LTC2975 - - Prefix: 'ltc2975' - - Addresses scanned: - - - Datasheet: http://www.linear.com/product/ltc2975 - - * Linear Technology LTC2977 - - Prefix: 'ltc2977' - - Addresses scanned: - - - Datasheet: http://www.linear.com/product/ltc2977 - - * Linear Technology LTC2978, LTC2978A - - Prefix: 'ltc2978' - - Addresses scanned: - - - Datasheet: http://www.linear.com/product/ltc2978 - - http://www.linear.com/product/ltc2978a - - * Linear Technology LTC2980 - - Prefix: 'ltc2980' - - Addresses scanned: - - - Datasheet: http://www.linear.com/product/ltc2980 - - * Linear Technology LTC3880 - - Prefix: 'ltc3880' - - Addresses scanned: - - - Datasheet: http://www.linear.com/product/ltc3880 - - * Linear Technology LTC3882 - - Prefix: 'ltc3882' - - Addresses scanned: - - - Datasheet: http://www.linear.com/product/ltc3882 - - * Linear Technology LTC3883 - - Prefix: 'ltc3883' - - Addresses scanned: - - - Datasheet: http://www.linear.com/product/ltc3883 - - * Linear Technology LTC3886 - - Prefix: 'ltc3886' - - Addresses scanned: - - - Datasheet: http://www.linear.com/product/ltc3886 - - * Linear Technology LTC3887 - - Prefix: 'ltc3887' - - Addresses scanned: - - - Datasheet: http://www.linear.com/product/ltc3887 - - * Linear Technology LTM2987 - - Prefix: 'ltm2987' - - Addresses scanned: - - - Datasheet: http://www.linear.com/product/ltm2987 - - * Linear Technology LTM4675 - - Prefix: 'ltm4675' - - Addresses scanned: - - - Datasheet: http://www.linear.com/product/ltm4675 - - * Linear Technology LTM4676 - - Prefix: 'ltm4676' - - Addresses scanned: - - - Datasheet: http://www.linear.com/product/ltm4676 - - * Analog Devices LTM4686 - - Prefix: 'ltm4686' - - Addresses scanned: - - - Datasheet: http://www.analog.com/ltm4686 - - -Author: Guenter Roeck - - -Description ------------ - -- LTC2974 and LTC2975 are quad digital power supply managers. -- LTC2978 is an octal power supply monitor. -- LTC2977 is a pin compatible replacement for LTC2978. -- LTC2980 is a 16-channel Power System Manager, consisting of two LTC2977 -- in a single die. The chip is instantiated and reported as two separate chips -- on two different I2C bus addresses. -- LTC3880, LTC3882, LTC3886, and LTC3887 are dual output poly-phase step-down -- DC/DC controllers. -- LTC3883 is a single phase step-down DC/DC controller. -- LTM2987 is a 16-channel Power System Manager with two LTC2977 plus -- additional components on a single die. The chip is instantiated and reported -- as two separate chips on two different I2C bus addresses. -- LTM4675 is a dual 9A or single 18A μModule regulator -- LTM4676 is a dual 13A or single 26A uModule regulator. -- LTM4686 is a dual 10A or single 20A uModule regulator. - - -Usage Notes ------------ - -This driver does not probe for PMBus devices. You will have to instantiate -devices explicitly. - -Example: the following commands will load the driver for an LTC2978 at address -0x60 on I2C bus #1:: - - # modprobe ltc2978 - # echo ltc2978 0x60 > /sys/bus/i2c/devices/i2c-1/new_device - - -Sysfs attributes ----------------- - -======================= ======================================================== -in1_label "vin" - -in1_input Measured input voltage. - -in1_min Minimum input voltage. - -in1_max Maximum input voltage. - - LTC2974, LTC2975, LTC2977, LTC2980, LTC2978, and - LTM2987 only. - -in1_lcrit Critical minimum input voltage. - - LTC2974, LTC2975, LTC2977, LTC2980, LTC2978, and - LTM2987 only. - -in1_crit Critical maximum input voltage. - -in1_min_alarm Input voltage low alarm. - -in1_max_alarm Input voltage high alarm. - - LTC2974, LTC2975, LTC2977, LTC2980, LTC2978, and - LTM2987 only. -in1_lcrit_alarm Input voltage critical low alarm. - - LTC2974, LTC2975, LTC2977, LTC2980, LTC2978, and - LTM2987 only. -in1_crit_alarm Input voltage critical high alarm. - -in1_lowest Lowest input voltage. - - LTC2974, LTC2975, LTC2977, LTC2980, LTC2978, and - LTM2987 only. -in1_highest Highest input voltage. - -in1_reset_history Reset input voltage history. - -in[N]_label "vout[1-8]". - - - LTC2974, LTC2975: N=2-5 - - LTC2977, LTC2980, LTM2987: N=2-9 - - LTC2978: N=2-9 - - LTC3880, LTC3882, LTC23886 LTC3887, LTM4675, LTM4676: - N=2-3 - - LTC3883: N=2 - -in[N]_input Measured output voltage. - -in[N]_min Minimum output voltage. - -in[N]_max Maximum output voltage. - -in[N]_lcrit Critical minimum output voltage. - -in[N]_crit Critical maximum output voltage. - -in[N]_min_alarm Output voltage low alarm. - -in[N]_max_alarm Output voltage high alarm. - -in[N]_lcrit_alarm Output voltage critical low alarm. - -in[N]_crit_alarm Output voltage critical high alarm. - -in[N]_lowest Lowest output voltage. - - - LTC2974, LTC2975,and LTC2978 only. - -in[N]_highest Highest output voltage. - -in[N]_reset_history Reset output voltage history. - -temp[N]_input Measured temperature. - - - On LTC2974 and LTC2975, temp[1-4] report external - temperatures, and temp5 reports the chip temperature. - - On LTC2977, LTC2980, LTC2978, and LTM2987, only one - temperature measurement is supported and reports - the chip temperature. - - On LTC3880, LTC3882, LTC3887, LTM4675, and LTM4676, - temp1 and temp2 report external temperatures, and - temp3 reports the chip temperature. - - On LTC3883, temp1 reports an external temperature, - and temp2 reports the chip temperature. - -temp[N]_min Mimimum temperature. - - LTC2974, LCT2977, LTM2980, LTC2978, and LTM2987 only. - -temp[N]_max Maximum temperature. - -temp[N]_lcrit Critical low temperature. - -temp[N]_crit Critical high temperature. - -temp[N]_min_alarm Temperature low alarm. - - LTC2974, LTC2975, LTC2977, LTM2980, LTC2978, and - LTM2987 only. - -temp[N]_max_alarm Temperature high alarm. - - -temp[N]_lcrit_alarm Temperature critical low alarm. - -temp[N]_crit_alarm Temperature critical high alarm. - -temp[N]_lowest Lowest measured temperature. - - - LTC2974, LTC2975, LTC2977, LTM2980, LTC2978, and - LTM2987 only. - - Not supported for chip temperature sensor on LTC2974 - and LTC2975. - -temp[N]_highest Highest measured temperature. - - Not supported for chip temperature sensor on - LTC2974 and LTC2975. - -temp[N]_reset_history Reset temperature history. - - Not supported for chip temperature sensor on - LTC2974 and LTC2975. - -power1_label "pin". LTC3883 and LTC3886 only. - -power1_input Measured input power. - -power[N]_label "pout[1-4]". - - - LTC2974, LTC2975: N=1-4 - - LTC2977, LTC2980, LTM2987: Not supported - - LTC2978: Not supported - - LTC3880, LTC3882, LTC3886, LTC3887, LTM4675, LTM4676: - N=1-2 - - LTC3883: N=2 - -power[N]_input Measured output power. - -curr1_label "iin". - - LTC3880, LTC3883, LTC3886, LTC3887, LTM4675, - and LTM4676 only. - -curr1_input Measured input current. - -curr1_max Maximum input current. - -curr1_max_alarm Input current high alarm. - -curr1_highest Highest input current. - - LTC3883 and LTC3886 only. - -curr1_reset_history Reset input current history. - - LTC3883 and LTC3886 only. - -curr[N]_label "iout[1-4]". - - - LTC2974, LTC2975: N=1-4 - - LTC2977, LTC2980, LTM2987: not supported - - LTC2978: not supported - - LTC3880, LTC3882, LTC3886, LTC3887, LTM4675, LTM4676: - N=2-3 - - LTC3883: N=2 - -curr[N]_input Measured output current. - -curr[N]_max Maximum output current. - -curr[N]_crit Critical high output current. - -curr[N]_lcrit Critical low output current. - - LTC2974 and LTC2975 only. - -curr[N]_max_alarm Output current high alarm. - -curr[N]_crit_alarm Output current critical high alarm. - -curr[N]_lcrit_alarm Output current critical low alarm. - - LTC2974 and LTC2975 only. - -curr[N]_lowest Lowest output current. - - LTC2974 and LTC2975 only. - -curr[N]_highest Highest output current. - -curr[N]_reset_history Reset output current history. -======================= ======================================================== diff --git a/Documentation/hwmon/ltc2978.rst b/Documentation/hwmon/ltc2978.rst new file mode 100644 index 000000000000..01a24fd6d5fe --- /dev/null +++ b/Documentation/hwmon/ltc2978.rst @@ -0,0 +1,355 @@ +Kernel driver ltc2978 +===================== + +Supported chips: + + * Linear Technology LTC2974 + + Prefix: 'ltc2974' + + Addresses scanned: - + + Datasheet: http://www.linear.com/product/ltc2974 + + * Linear Technology LTC2975 + + Prefix: 'ltc2975' + + Addresses scanned: - + + Datasheet: http://www.linear.com/product/ltc2975 + + * Linear Technology LTC2977 + + Prefix: 'ltc2977' + + Addresses scanned: - + + Datasheet: http://www.linear.com/product/ltc2977 + + * Linear Technology LTC2978, LTC2978A + + Prefix: 'ltc2978' + + Addresses scanned: - + + Datasheet: http://www.linear.com/product/ltc2978 + + http://www.linear.com/product/ltc2978a + + * Linear Technology LTC2980 + + Prefix: 'ltc2980' + + Addresses scanned: - + + Datasheet: http://www.linear.com/product/ltc2980 + + * Linear Technology LTC3880 + + Prefix: 'ltc3880' + + Addresses scanned: - + + Datasheet: http://www.linear.com/product/ltc3880 + + * Linear Technology LTC3882 + + Prefix: 'ltc3882' + + Addresses scanned: - + + Datasheet: http://www.linear.com/product/ltc3882 + + * Linear Technology LTC3883 + + Prefix: 'ltc3883' + + Addresses scanned: - + + Datasheet: http://www.linear.com/product/ltc3883 + + * Linear Technology LTC3886 + + Prefix: 'ltc3886' + + Addresses scanned: - + + Datasheet: http://www.linear.com/product/ltc3886 + + * Linear Technology LTC3887 + + Prefix: 'ltc3887' + + Addresses scanned: - + + Datasheet: http://www.linear.com/product/ltc3887 + + * Linear Technology LTM2987 + + Prefix: 'ltm2987' + + Addresses scanned: - + + Datasheet: http://www.linear.com/product/ltm2987 + + * Linear Technology LTM4675 + + Prefix: 'ltm4675' + + Addresses scanned: - + + Datasheet: http://www.linear.com/product/ltm4675 + + * Linear Technology LTM4676 + + Prefix: 'ltm4676' + + Addresses scanned: - + + Datasheet: http://www.linear.com/product/ltm4676 + + * Analog Devices LTM4686 + + Prefix: 'ltm4686' + + Addresses scanned: - + + Datasheet: http://www.analog.com/ltm4686 + + +Author: Guenter Roeck + + +Description +----------- + +- LTC2974 and LTC2975 are quad digital power supply managers. +- LTC2978 is an octal power supply monitor. +- LTC2977 is a pin compatible replacement for LTC2978. +- LTC2980 is a 16-channel Power System Manager, consisting of two LTC2977 +- in a single die. The chip is instantiated and reported as two separate chips +- on two different I2C bus addresses. +- LTC3880, LTC3882, LTC3886, and LTC3887 are dual output poly-phase step-down +- DC/DC controllers. +- LTC3883 is a single phase step-down DC/DC controller. +- LTM2987 is a 16-channel Power System Manager with two LTC2977 plus +- additional components on a single die. The chip is instantiated and reported +- as two separate chips on two different I2C bus addresses. +- LTM4675 is a dual 9A or single 18A μModule regulator +- LTM4676 is a dual 13A or single 26A uModule regulator. +- LTM4686 is a dual 10A or single 20A uModule regulator. + + +Usage Notes +----------- + +This driver does not probe for PMBus devices. You will have to instantiate +devices explicitly. + +Example: the following commands will load the driver for an LTC2978 at address +0x60 on I2C bus #1:: + + # modprobe ltc2978 + # echo ltc2978 0x60 > /sys/bus/i2c/devices/i2c-1/new_device + + +Sysfs attributes +---------------- + +======================= ======================================================== +in1_label "vin" + +in1_input Measured input voltage. + +in1_min Minimum input voltage. + +in1_max Maximum input voltage. + + LTC2974, LTC2975, LTC2977, LTC2980, LTC2978, and + LTM2987 only. + +in1_lcrit Critical minimum input voltage. + + LTC2974, LTC2975, LTC2977, LTC2980, LTC2978, and + LTM2987 only. + +in1_crit Critical maximum input voltage. + +in1_min_alarm Input voltage low alarm. + +in1_max_alarm Input voltage high alarm. + + LTC2974, LTC2975, LTC2977, LTC2980, LTC2978, and + LTM2987 only. +in1_lcrit_alarm Input voltage critical low alarm. + + LTC2974, LTC2975, LTC2977, LTC2980, LTC2978, and + LTM2987 only. +in1_crit_alarm Input voltage critical high alarm. + +in1_lowest Lowest input voltage. + + LTC2974, LTC2975, LTC2977, LTC2980, LTC2978, and + LTM2987 only. +in1_highest Highest input voltage. + +in1_reset_history Reset input voltage history. + +in[N]_label "vout[1-8]". + + - LTC2974, LTC2975: N=2-5 + - LTC2977, LTC2980, LTM2987: N=2-9 + - LTC2978: N=2-9 + - LTC3880, LTC3882, LTC23886 LTC3887, LTM4675, LTM4676: + N=2-3 + - LTC3883: N=2 + +in[N]_input Measured output voltage. + +in[N]_min Minimum output voltage. + +in[N]_max Maximum output voltage. + +in[N]_lcrit Critical minimum output voltage. + +in[N]_crit Critical maximum output voltage. + +in[N]_min_alarm Output voltage low alarm. + +in[N]_max_alarm Output voltage high alarm. + +in[N]_lcrit_alarm Output voltage critical low alarm. + +in[N]_crit_alarm Output voltage critical high alarm. + +in[N]_lowest Lowest output voltage. + + + LTC2974, LTC2975,and LTC2978 only. + +in[N]_highest Highest output voltage. + +in[N]_reset_history Reset output voltage history. + +temp[N]_input Measured temperature. + + - On LTC2974 and LTC2975, temp[1-4] report external + temperatures, and temp5 reports the chip temperature. + - On LTC2977, LTC2980, LTC2978, and LTM2987, only one + temperature measurement is supported and reports + the chip temperature. + - On LTC3880, LTC3882, LTC3887, LTM4675, and LTM4676, + temp1 and temp2 report external temperatures, and + temp3 reports the chip temperature. + - On LTC3883, temp1 reports an external temperature, + and temp2 reports the chip temperature. + +temp[N]_min Mimimum temperature. + + LTC2974, LCT2977, LTM2980, LTC2978, and LTM2987 only. + +temp[N]_max Maximum temperature. + +temp[N]_lcrit Critical low temperature. + +temp[N]_crit Critical high temperature. + +temp[N]_min_alarm Temperature low alarm. + + LTC2974, LTC2975, LTC2977, LTM2980, LTC2978, and + LTM2987 only. + +temp[N]_max_alarm Temperature high alarm. + + +temp[N]_lcrit_alarm Temperature critical low alarm. + +temp[N]_crit_alarm Temperature critical high alarm. + +temp[N]_lowest Lowest measured temperature. + + - LTC2974, LTC2975, LTC2977, LTM2980, LTC2978, and + LTM2987 only. + - Not supported for chip temperature sensor on LTC2974 + and LTC2975. + +temp[N]_highest Highest measured temperature. + + Not supported for chip temperature sensor on + LTC2974 and LTC2975. + +temp[N]_reset_history Reset temperature history. + + Not supported for chip temperature sensor on + LTC2974 and LTC2975. + +power1_label "pin". LTC3883 and LTC3886 only. + +power1_input Measured input power. + +power[N]_label "pout[1-4]". + + - LTC2974, LTC2975: N=1-4 + - LTC2977, LTC2980, LTM2987: Not supported + - LTC2978: Not supported + - LTC3880, LTC3882, LTC3886, LTC3887, LTM4675, LTM4676: + N=1-2 + - LTC3883: N=2 + +power[N]_input Measured output power. + +curr1_label "iin". + + LTC3880, LTC3883, LTC3886, LTC3887, LTM4675, + and LTM4676 only. + +curr1_input Measured input current. + +curr1_max Maximum input current. + +curr1_max_alarm Input current high alarm. + +curr1_highest Highest input current. + + LTC3883 and LTC3886 only. + +curr1_reset_history Reset input current history. + + LTC3883 and LTC3886 only. + +curr[N]_label "iout[1-4]". + + - LTC2974, LTC2975: N=1-4 + - LTC2977, LTC2980, LTM2987: not supported + - LTC2978: not supported + - LTC3880, LTC3882, LTC3886, LTC3887, LTM4675, LTM4676: + N=2-3 + - LTC3883: N=2 + +curr[N]_input Measured output current. + +curr[N]_max Maximum output current. + +curr[N]_crit Critical high output current. + +curr[N]_lcrit Critical low output current. + + LTC2974 and LTC2975 only. + +curr[N]_max_alarm Output current high alarm. + +curr[N]_crit_alarm Output current critical high alarm. + +curr[N]_lcrit_alarm Output current critical low alarm. + + LTC2974 and LTC2975 only. + +curr[N]_lowest Lowest output current. + + LTC2974 and LTC2975 only. + +curr[N]_highest Highest output current. + +curr[N]_reset_history Reset output current history. +======================= ======================================================== diff --git a/Documentation/hwmon/ltc2990 b/Documentation/hwmon/ltc2990 deleted file mode 100644 index e0a369e679d3..000000000000 --- a/Documentation/hwmon/ltc2990 +++ /dev/null @@ -1,62 +0,0 @@ -Kernel driver ltc2990 -===================== - - -Supported chips: - - * Linear Technology LTC2990 - - Prefix: 'ltc2990' - - Addresses scanned: - - - Datasheet: http://www.linear.com/product/ltc2990 - - - -Author: - - - Mike Looijmans - - Tom Levens - - -Description ------------ - -LTC2990 is a Quad I2C Voltage, Current and Temperature Monitor. -The chip's inputs can measure 4 voltages, or two inputs together (1+2 and 3+4) -can be combined to measure a differential voltage, which is typically used to -measure current through a series resistor, or a temperature with an external -diode. - - -Usage Notes ------------ - -This driver does not probe for PMBus devices. You will have to instantiate -devices explicitly. - - -Sysfs attributes ----------------- - -============= ================================================== -in0_input Voltage at Vcc pin in millivolt (range 2.5V to 5V) -temp1_input Internal chip temperature in millidegrees Celsius -============= ================================================== - -A subset of the following attributes are visible, depending on the measurement -mode of the chip. - -============= ========================================================== -in[1-4]_input Voltage at V[1-4] pin in millivolt -temp2_input External temperature sensor TR1 in millidegrees Celsius -temp3_input External temperature sensor TR2 in millidegrees Celsius -curr1_input Current in mA across V1-V2 assuming a 1mOhm sense resistor -curr2_input Current in mA across V3-V4 assuming a 1mOhm sense resistor -============= ========================================================== - -The "curr*_input" measurements actually report the voltage drop across the -input pins in microvolts. This is equivalent to the current through a 1mOhm -sense resistor. Divide the reported value by the actual sense resistor value -in mOhm to get the actual value. diff --git a/Documentation/hwmon/ltc2990.rst b/Documentation/hwmon/ltc2990.rst new file mode 100644 index 000000000000..e0a369e679d3 --- /dev/null +++ b/Documentation/hwmon/ltc2990.rst @@ -0,0 +1,62 @@ +Kernel driver ltc2990 +===================== + + +Supported chips: + + * Linear Technology LTC2990 + + Prefix: 'ltc2990' + + Addresses scanned: - + + Datasheet: http://www.linear.com/product/ltc2990 + + + +Author: + + - Mike Looijmans + - Tom Levens + + +Description +----------- + +LTC2990 is a Quad I2C Voltage, Current and Temperature Monitor. +The chip's inputs can measure 4 voltages, or two inputs together (1+2 and 3+4) +can be combined to measure a differential voltage, which is typically used to +measure current through a series resistor, or a temperature with an external +diode. + + +Usage Notes +----------- + +This driver does not probe for PMBus devices. You will have to instantiate +devices explicitly. + + +Sysfs attributes +---------------- + +============= ================================================== +in0_input Voltage at Vcc pin in millivolt (range 2.5V to 5V) +temp1_input Internal chip temperature in millidegrees Celsius +============= ================================================== + +A subset of the following attributes are visible, depending on the measurement +mode of the chip. + +============= ========================================================== +in[1-4]_input Voltage at V[1-4] pin in millivolt +temp2_input External temperature sensor TR1 in millidegrees Celsius +temp3_input External temperature sensor TR2 in millidegrees Celsius +curr1_input Current in mA across V1-V2 assuming a 1mOhm sense resistor +curr2_input Current in mA across V3-V4 assuming a 1mOhm sense resistor +============= ========================================================== + +The "curr*_input" measurements actually report the voltage drop across the +input pins in microvolts. This is equivalent to the current through a 1mOhm +sense resistor. Divide the reported value by the actual sense resistor value +in mOhm to get the actual value. diff --git a/Documentation/hwmon/ltc3815 b/Documentation/hwmon/ltc3815 deleted file mode 100644 index fb0135fc1925..000000000000 --- a/Documentation/hwmon/ltc3815 +++ /dev/null @@ -1,67 +0,0 @@ -Kernel driver ltc3815 -===================== - -Supported chips: - - * Linear Technology LTC3815 - - Prefix: 'ltc3815' - - Addresses scanned: - - - Datasheet: http://www.linear.com/product/ltc3815 - -Author: Guenter Roeck - - -Description ------------ - -LTC3815 is a Monolithic Synchronous DC/DC Step-Down Converter. - - -Usage Notes ------------ - -This driver does not probe for PMBus devices. You will have to instantiate -devices explicitly. - -Example: the following commands will load the driver for an LTC3815 -at address 0x20 on I2C bus #1:: - - # modprobe ltc3815 - # echo ltc3815 0x20 > /sys/bus/i2c/devices/i2c-1/new_device - - -Sysfs attributes ----------------- - -======================= ======================================================= -in1_label "vin" -in1_input Measured input voltage. -in1_alarm Input voltage alarm. -in1_highest Highest input voltage. -in1_reset_history Reset input voltage history. - -in2_label "vout1". -in2_input Measured output voltage. -in2_alarm Output voltage alarm. -in2_highest Highest output voltage. -in2_reset_history Reset output voltage history. - -temp1_input Measured chip temperature. -temp1_alarm Temperature alarm. -temp1_highest Highest measured temperature. -temp1_reset_history Reset temperature history. - -curr1_label "iin". -curr1_input Measured input current. -curr1_highest Highest input current. -curr1_reset_history Reset input current history. - -curr2_label "iout1". -curr2_input Measured output current. -curr2_alarm Output current alarm. -curr2_highest Highest output current. -curr2_reset_history Reset output current history. -======================= ======================================================= diff --git a/Documentation/hwmon/ltc3815.rst b/Documentation/hwmon/ltc3815.rst new file mode 100644 index 000000000000..fb0135fc1925 --- /dev/null +++ b/Documentation/hwmon/ltc3815.rst @@ -0,0 +1,67 @@ +Kernel driver ltc3815 +===================== + +Supported chips: + + * Linear Technology LTC3815 + + Prefix: 'ltc3815' + + Addresses scanned: - + + Datasheet: http://www.linear.com/product/ltc3815 + +Author: Guenter Roeck + + +Description +----------- + +LTC3815 is a Monolithic Synchronous DC/DC Step-Down Converter. + + +Usage Notes +----------- + +This driver does not probe for PMBus devices. You will have to instantiate +devices explicitly. + +Example: the following commands will load the driver for an LTC3815 +at address 0x20 on I2C bus #1:: + + # modprobe ltc3815 + # echo ltc3815 0x20 > /sys/bus/i2c/devices/i2c-1/new_device + + +Sysfs attributes +---------------- + +======================= ======================================================= +in1_label "vin" +in1_input Measured input voltage. +in1_alarm Input voltage alarm. +in1_highest Highest input voltage. +in1_reset_history Reset input voltage history. + +in2_label "vout1". +in2_input Measured output voltage. +in2_alarm Output voltage alarm. +in2_highest Highest output voltage. +in2_reset_history Reset output voltage history. + +temp1_input Measured chip temperature. +temp1_alarm Temperature alarm. +temp1_highest Highest measured temperature. +temp1_reset_history Reset temperature history. + +curr1_label "iin". +curr1_input Measured input current. +curr1_highest Highest input current. +curr1_reset_history Reset input current history. + +curr2_label "iout1". +curr2_input Measured output current. +curr2_alarm Output current alarm. +curr2_highest Highest output current. +curr2_reset_history Reset output current history. +======================= ======================================================= diff --git a/Documentation/hwmon/ltc4151 b/Documentation/hwmon/ltc4151 deleted file mode 100644 index c39229b19624..000000000000 --- a/Documentation/hwmon/ltc4151 +++ /dev/null @@ -1,55 +0,0 @@ -Kernel driver ltc4151 -===================== - -Supported chips: - - * Linear Technology LTC4151 - - Prefix: 'ltc4151' - - Addresses scanned: - - - Datasheet: - - http://www.linear.com/docs/Datasheet/4151fc.pdf - -Author: Per Dalen - - -Description ------------ - -The LTC4151 is a High Voltage I2C Current and Voltage Monitor. - - -Usage Notes ------------ - -This driver does not probe for LTC4151 devices, since there is no register -which can be safely used to identify the chip. You will have to instantiate -the devices explicitly. - -Example: the following will load the driver for an LTC4151 at address 0x6f -on I2C bus #0:: - - # modprobe ltc4151 - # echo ltc4151 0x6f > /sys/bus/i2c/devices/i2c-0/new_device - - -Sysfs entries -------------- - -Voltage readings provided by this driver are reported as obtained from the ADIN -and VIN registers. - -Current reading provided by this driver is reported as obtained from the Current -Sense register. The reported value assumes that a 1 mOhm sense resistor is -installed. - -======================= ================== -in1_input VDIN voltage (mV) - -in2_input ADIN voltage (mV) - -curr1_input SENSE current (mA) -======================= ================== diff --git a/Documentation/hwmon/ltc4151.rst b/Documentation/hwmon/ltc4151.rst new file mode 100644 index 000000000000..c39229b19624 --- /dev/null +++ b/Documentation/hwmon/ltc4151.rst @@ -0,0 +1,55 @@ +Kernel driver ltc4151 +===================== + +Supported chips: + + * Linear Technology LTC4151 + + Prefix: 'ltc4151' + + Addresses scanned: - + + Datasheet: + + http://www.linear.com/docs/Datasheet/4151fc.pdf + +Author: Per Dalen + + +Description +----------- + +The LTC4151 is a High Voltage I2C Current and Voltage Monitor. + + +Usage Notes +----------- + +This driver does not probe for LTC4151 devices, since there is no register +which can be safely used to identify the chip. You will have to instantiate +the devices explicitly. + +Example: the following will load the driver for an LTC4151 at address 0x6f +on I2C bus #0:: + + # modprobe ltc4151 + # echo ltc4151 0x6f > /sys/bus/i2c/devices/i2c-0/new_device + + +Sysfs entries +------------- + +Voltage readings provided by this driver are reported as obtained from the ADIN +and VIN registers. + +Current reading provided by this driver is reported as obtained from the Current +Sense register. The reported value assumes that a 1 mOhm sense resistor is +installed. + +======================= ================== +in1_input VDIN voltage (mV) + +in2_input ADIN voltage (mV) + +curr1_input SENSE current (mA) +======================= ================== diff --git a/Documentation/hwmon/ltc4215 b/Documentation/hwmon/ltc4215 deleted file mode 100644 index 8d5044d99bab..000000000000 --- a/Documentation/hwmon/ltc4215 +++ /dev/null @@ -1,59 +0,0 @@ -Kernel driver ltc4215 -===================== - -Supported chips: - - * Linear Technology LTC4215 - - Prefix: 'ltc4215' - - Addresses scanned: 0x44 - - Datasheet: - - http://www.linear.com/pc/downloadDocument.do?navId=H0,C1,C1003,C1006,C1163,P17572,D12697 - -Author: Ira W. Snyder - - -Description ------------ - -The LTC4215 controller allows a board to be safely inserted and removed -from a live backplane. - - -Usage Notes ------------ - -This driver does not probe for LTC4215 devices, due to the fact that some -of the possible addresses are unfriendly to probing. You will have to -instantiate the devices explicitly. - -Example: the following will load the driver for an LTC4215 at address 0x44 -on I2C bus #0:: - - $ modprobe ltc4215 - $ echo ltc4215 0x44 > /sys/bus/i2c/devices/i2c-0/new_device - - -Sysfs entries -------------- - -The LTC4215 has built-in limits for overvoltage, undervoltage, and -undercurrent warnings. This makes it very likely that the reference -circuit will be used. - -======================= ========================= -in1_input input voltage -in2_input output voltage - -in1_min_alarm input undervoltage alarm -in1_max_alarm input overvoltage alarm - -curr1_input current -curr1_max_alarm overcurrent alarm - -power1_input power usage -power1_alarm power bad alarm -======================= ========================= diff --git a/Documentation/hwmon/ltc4215.rst b/Documentation/hwmon/ltc4215.rst new file mode 100644 index 000000000000..8d5044d99bab --- /dev/null +++ b/Documentation/hwmon/ltc4215.rst @@ -0,0 +1,59 @@ +Kernel driver ltc4215 +===================== + +Supported chips: + + * Linear Technology LTC4215 + + Prefix: 'ltc4215' + + Addresses scanned: 0x44 + + Datasheet: + + http://www.linear.com/pc/downloadDocument.do?navId=H0,C1,C1003,C1006,C1163,P17572,D12697 + +Author: Ira W. Snyder + + +Description +----------- + +The LTC4215 controller allows a board to be safely inserted and removed +from a live backplane. + + +Usage Notes +----------- + +This driver does not probe for LTC4215 devices, due to the fact that some +of the possible addresses are unfriendly to probing. You will have to +instantiate the devices explicitly. + +Example: the following will load the driver for an LTC4215 at address 0x44 +on I2C bus #0:: + + $ modprobe ltc4215 + $ echo ltc4215 0x44 > /sys/bus/i2c/devices/i2c-0/new_device + + +Sysfs entries +------------- + +The LTC4215 has built-in limits for overvoltage, undervoltage, and +undercurrent warnings. This makes it very likely that the reference +circuit will be used. + +======================= ========================= +in1_input input voltage +in2_input output voltage + +in1_min_alarm input undervoltage alarm +in1_max_alarm input overvoltage alarm + +curr1_input current +curr1_max_alarm overcurrent alarm + +power1_input power usage +power1_alarm power bad alarm +======================= ========================= diff --git a/Documentation/hwmon/ltc4245 b/Documentation/hwmon/ltc4245 deleted file mode 100644 index 3dafd08a4e87..000000000000 --- a/Documentation/hwmon/ltc4245 +++ /dev/null @@ -1,111 +0,0 @@ -Kernel driver ltc4245 -===================== - -Supported chips: - - * Linear Technology LTC4245 - - Prefix: 'ltc4245' - - Addresses scanned: 0x20-0x3f - - Datasheet: - - http://www.linear.com/pc/downloadDocument.do?navId=H0,C1,C1003,C1006,C1140,P19392,D13517 - -Author: Ira W. Snyder - - -Description ------------ - -The LTC4245 controller allows a board to be safely inserted and removed -from a live backplane in multiple supply systems such as CompactPCI and -PCI Express. - - -Usage Notes ------------ - -This driver does not probe for LTC4245 devices, due to the fact that some -of the possible addresses are unfriendly to probing. You will have to -instantiate the devices explicitly. - -Example: the following will load the driver for an LTC4245 at address 0x23 -on I2C bus #1:: - - $ modprobe ltc4245 - $ echo ltc4245 0x23 > /sys/bus/i2c/devices/i2c-1/new_device - - -Sysfs entries -------------- - -The LTC4245 has built-in limits for over and under current warnings. This -makes it very likely that the reference circuit will be used. - -This driver uses the values in the datasheet to change the register values -into the values specified in the sysfs-interface document. The current readings -rely on the sense resistors listed in Table 2: "Sense Resistor Values". - -======================= ======================================================= -in1_input 12v input voltage (mV) -in2_input 5v input voltage (mV) -in3_input 3v input voltage (mV) -in4_input Vee (-12v) input voltage (mV) - -in1_min_alarm 12v input undervoltage alarm -in2_min_alarm 5v input undervoltage alarm -in3_min_alarm 3v input undervoltage alarm -in4_min_alarm Vee (-12v) input undervoltage alarm - -curr1_input 12v current (mA) -curr2_input 5v current (mA) -curr3_input 3v current (mA) -curr4_input Vee (-12v) current (mA) - -curr1_max_alarm 12v overcurrent alarm -curr2_max_alarm 5v overcurrent alarm -curr3_max_alarm 3v overcurrent alarm -curr4_max_alarm Vee (-12v) overcurrent alarm - -in5_input 12v output voltage (mV) -in6_input 5v output voltage (mV) -in7_input 3v output voltage (mV) -in8_input Vee (-12v) output voltage (mV) - -in5_min_alarm 12v output undervoltage alarm -in6_min_alarm 5v output undervoltage alarm -in7_min_alarm 3v output undervoltage alarm -in8_min_alarm Vee (-12v) output undervoltage alarm - -in9_input GPIO voltage data (see note 1) -in10_input GPIO voltage data (see note 1) -in11_input GPIO voltage data (see note 1) - -power1_input 12v power usage (mW) -power2_input 5v power usage (mW) -power3_input 3v power usage (mW) -power4_input Vee (-12v) power usage (mW) -======================= ======================================================= - - -Note 1 ------- - -If you have NOT configured the driver to sample all GPIO pins as analog -voltages, then the in10_input and in11_input sysfs attributes will not be -created. The driver will sample the GPIO pin that is currently connected to the -ADC as an analog voltage, and report the value in in9_input. - -If you have configured the driver to sample all GPIO pins as analog voltages, -then they will be sampled in round-robin fashion. If userspace reads too -slowly, -EAGAIN will be returned when you read the sysfs attribute containing -the sensor reading. - -The LTC4245 chip can be configured to sample all GPIO pins with two methods: - -1) platform data -- see include/linux/platform_data/ltc4245.h -2) OF device tree -- add the "ltc4245,use-extra-gpios" property to each chip - -The default mode of operation is to sample a single GPIO pin. diff --git a/Documentation/hwmon/ltc4245.rst b/Documentation/hwmon/ltc4245.rst new file mode 100644 index 000000000000..3dafd08a4e87 --- /dev/null +++ b/Documentation/hwmon/ltc4245.rst @@ -0,0 +1,111 @@ +Kernel driver ltc4245 +===================== + +Supported chips: + + * Linear Technology LTC4245 + + Prefix: 'ltc4245' + + Addresses scanned: 0x20-0x3f + + Datasheet: + + http://www.linear.com/pc/downloadDocument.do?navId=H0,C1,C1003,C1006,C1140,P19392,D13517 + +Author: Ira W. Snyder + + +Description +----------- + +The LTC4245 controller allows a board to be safely inserted and removed +from a live backplane in multiple supply systems such as CompactPCI and +PCI Express. + + +Usage Notes +----------- + +This driver does not probe for LTC4245 devices, due to the fact that some +of the possible addresses are unfriendly to probing. You will have to +instantiate the devices explicitly. + +Example: the following will load the driver for an LTC4245 at address 0x23 +on I2C bus #1:: + + $ modprobe ltc4245 + $ echo ltc4245 0x23 > /sys/bus/i2c/devices/i2c-1/new_device + + +Sysfs entries +------------- + +The LTC4245 has built-in limits for over and under current warnings. This +makes it very likely that the reference circuit will be used. + +This driver uses the values in the datasheet to change the register values +into the values specified in the sysfs-interface document. The current readings +rely on the sense resistors listed in Table 2: "Sense Resistor Values". + +======================= ======================================================= +in1_input 12v input voltage (mV) +in2_input 5v input voltage (mV) +in3_input 3v input voltage (mV) +in4_input Vee (-12v) input voltage (mV) + +in1_min_alarm 12v input undervoltage alarm +in2_min_alarm 5v input undervoltage alarm +in3_min_alarm 3v input undervoltage alarm +in4_min_alarm Vee (-12v) input undervoltage alarm + +curr1_input 12v current (mA) +curr2_input 5v current (mA) +curr3_input 3v current (mA) +curr4_input Vee (-12v) current (mA) + +curr1_max_alarm 12v overcurrent alarm +curr2_max_alarm 5v overcurrent alarm +curr3_max_alarm 3v overcurrent alarm +curr4_max_alarm Vee (-12v) overcurrent alarm + +in5_input 12v output voltage (mV) +in6_input 5v output voltage (mV) +in7_input 3v output voltage (mV) +in8_input Vee (-12v) output voltage (mV) + +in5_min_alarm 12v output undervoltage alarm +in6_min_alarm 5v output undervoltage alarm +in7_min_alarm 3v output undervoltage alarm +in8_min_alarm Vee (-12v) output undervoltage alarm + +in9_input GPIO voltage data (see note 1) +in10_input GPIO voltage data (see note 1) +in11_input GPIO voltage data (see note 1) + +power1_input 12v power usage (mW) +power2_input 5v power usage (mW) +power3_input 3v power usage (mW) +power4_input Vee (-12v) power usage (mW) +======================= ======================================================= + + +Note 1 +------ + +If you have NOT configured the driver to sample all GPIO pins as analog +voltages, then the in10_input and in11_input sysfs attributes will not be +created. The driver will sample the GPIO pin that is currently connected to the +ADC as an analog voltage, and report the value in in9_input. + +If you have configured the driver to sample all GPIO pins as analog voltages, +then they will be sampled in round-robin fashion. If userspace reads too +slowly, -EAGAIN will be returned when you read the sysfs attribute containing +the sensor reading. + +The LTC4245 chip can be configured to sample all GPIO pins with two methods: + +1) platform data -- see include/linux/platform_data/ltc4245.h +2) OF device tree -- add the "ltc4245,use-extra-gpios" property to each chip + +The default mode of operation is to sample a single GPIO pin. diff --git a/Documentation/hwmon/ltc4260 b/Documentation/hwmon/ltc4260 deleted file mode 100644 index 4c335b6a51d1..000000000000 --- a/Documentation/hwmon/ltc4260 +++ /dev/null @@ -1,64 +0,0 @@ -Kernel driver ltc4260 -===================== - -Supported chips: - - * Linear Technology LTC4260 - - Prefix: 'ltc4260' - - Addresses scanned: - - - Datasheet: - - http://cds.linear.com/docs/en/datasheet/4260fc.pdf - -Author: Guenter Roeck - - -Description ------------ - -The LTC4260 Hot Swap controller allows a board to be safely inserted -and removed from a live backplane. - - -Usage Notes ------------ - -This driver does not probe for LTC4260 devices, since there is no register -which can be safely used to identify the chip. You will have to instantiate -the devices explicitly. - -Example: the following will load the driver for an LTC4260 at address 0x10 -on I2C bus #1:: - - $ modprobe ltc4260 - $ echo ltc4260 0x10 > /sys/bus/i2c/devices/i2c-1/new_device - - -Sysfs entries -------------- - -Voltage readings provided by this driver are reported as obtained from the ADC -registers. If a set of voltage divider resistors is installed, calculate the -real voltage by multiplying the reported value with (R1+R2)/R2, where R1 is the -value of the divider resistor against the measured voltage and R2 is the value -of the divider resistor against Ground. - -Current reading provided by this driver is reported as obtained from the ADC -Current Sense register. The reported value assumes that a 1 mOhm sense resistor -is installed. If a different sense resistor is installed, calculate the real -current by dividing the reported value by the sense resistor value in mOhm. - -======================= ======================= -in1_input SOURCE voltage (mV) -in1_min_alarm Undervoltage alarm -in1_max_alarm Overvoltage alarm - -in2_input ADIN voltage (mV) -in2_alarm Power bad alarm - -curr1_input SENSE current (mA) -curr1_alarm SENSE overcurrent alarm -======================= ======================= diff --git a/Documentation/hwmon/ltc4260.rst b/Documentation/hwmon/ltc4260.rst new file mode 100644 index 000000000000..4c335b6a51d1 --- /dev/null +++ b/Documentation/hwmon/ltc4260.rst @@ -0,0 +1,64 @@ +Kernel driver ltc4260 +===================== + +Supported chips: + + * Linear Technology LTC4260 + + Prefix: 'ltc4260' + + Addresses scanned: - + + Datasheet: + + http://cds.linear.com/docs/en/datasheet/4260fc.pdf + +Author: Guenter Roeck + + +Description +----------- + +The LTC4260 Hot Swap controller allows a board to be safely inserted +and removed from a live backplane. + + +Usage Notes +----------- + +This driver does not probe for LTC4260 devices, since there is no register +which can be safely used to identify the chip. You will have to instantiate +the devices explicitly. + +Example: the following will load the driver for an LTC4260 at address 0x10 +on I2C bus #1:: + + $ modprobe ltc4260 + $ echo ltc4260 0x10 > /sys/bus/i2c/devices/i2c-1/new_device + + +Sysfs entries +------------- + +Voltage readings provided by this driver are reported as obtained from the ADC +registers. If a set of voltage divider resistors is installed, calculate the +real voltage by multiplying the reported value with (R1+R2)/R2, where R1 is the +value of the divider resistor against the measured voltage and R2 is the value +of the divider resistor against Ground. + +Current reading provided by this driver is reported as obtained from the ADC +Current Sense register. The reported value assumes that a 1 mOhm sense resistor +is installed. If a different sense resistor is installed, calculate the real +current by dividing the reported value by the sense resistor value in mOhm. + +======================= ======================= +in1_input SOURCE voltage (mV) +in1_min_alarm Undervoltage alarm +in1_max_alarm Overvoltage alarm + +in2_input ADIN voltage (mV) +in2_alarm Power bad alarm + +curr1_input SENSE current (mA) +curr1_alarm SENSE overcurrent alarm +======================= ======================= diff --git a/Documentation/hwmon/ltc4261 b/Documentation/hwmon/ltc4261 deleted file mode 100644 index c80233f8082e..000000000000 --- a/Documentation/hwmon/ltc4261 +++ /dev/null @@ -1,71 +0,0 @@ -Kernel driver ltc4261 -===================== - -Supported chips: - - * Linear Technology LTC4261 - - Prefix: 'ltc4261' - - Addresses scanned: - - - Datasheet: - - http://cds.linear.com/docs/Datasheet/42612fb.pdf - -Author: Guenter Roeck - - -Description ------------ - -The LTC4261/LTC4261-2 negative voltage Hot Swap controllers allow a board -to be safely inserted and removed from a live backplane. - - -Usage Notes ------------ - -This driver does not probe for LTC4261 devices, since there is no register -which can be safely used to identify the chip. You will have to instantiate -the devices explicitly. - -Example: the following will load the driver for an LTC4261 at address 0x10 -on I2C bus #1:: - - $ modprobe ltc4261 - $ echo ltc4261 0x10 > /sys/bus/i2c/devices/i2c-1/new_device - - -Sysfs entries -------------- - -Voltage readings provided by this driver are reported as obtained from the ADC -registers. If a set of voltage divider resistors is installed, calculate the -real voltage by multiplying the reported value with (R1+R2)/R2, where R1 is the -value of the divider resistor against the measured voltage and R2 is the value -of the divider resistor against Ground. - -Current reading provided by this driver is reported as obtained from the ADC -Current Sense register. The reported value assumes that a 1 mOhm sense resistor -is installed. If a different sense resistor is installed, calculate the real -current by dividing the reported value by the sense resistor value in mOhm. - -The chip has two voltage sensors, but only one set of voltage alarm status bits. -In many many designs, those alarms are associated with the ADIN2 sensor, due to -the proximity of the ADIN2 pin to the OV pin. ADIN2 is, however, not available -on all chip variants. To ensure that the alarm condition is reported to the user, -report it with both voltage sensors. - -======================= ============================= -in1_input ADIN2 voltage (mV) -in1_min_alarm ADIN/ADIN2 Undervoltage alarm -in1_max_alarm ADIN/ADIN2 Overvoltage alarm - -in2_input ADIN voltage (mV) -in2_min_alarm ADIN/ADIN2 Undervoltage alarm -in2_max_alarm ADIN/ADIN2 Overvoltage alarm - -curr1_input SENSE current (mA) -curr1_alarm SENSE overcurrent alarm -======================= ============================= diff --git a/Documentation/hwmon/ltc4261.rst b/Documentation/hwmon/ltc4261.rst new file mode 100644 index 000000000000..c80233f8082e --- /dev/null +++ b/Documentation/hwmon/ltc4261.rst @@ -0,0 +1,71 @@ +Kernel driver ltc4261 +===================== + +Supported chips: + + * Linear Technology LTC4261 + + Prefix: 'ltc4261' + + Addresses scanned: - + + Datasheet: + + http://cds.linear.com/docs/Datasheet/42612fb.pdf + +Author: Guenter Roeck + + +Description +----------- + +The LTC4261/LTC4261-2 negative voltage Hot Swap controllers allow a board +to be safely inserted and removed from a live backplane. + + +Usage Notes +----------- + +This driver does not probe for LTC4261 devices, since there is no register +which can be safely used to identify the chip. You will have to instantiate +the devices explicitly. + +Example: the following will load the driver for an LTC4261 at address 0x10 +on I2C bus #1:: + + $ modprobe ltc4261 + $ echo ltc4261 0x10 > /sys/bus/i2c/devices/i2c-1/new_device + + +Sysfs entries +------------- + +Voltage readings provided by this driver are reported as obtained from the ADC +registers. If a set of voltage divider resistors is installed, calculate the +real voltage by multiplying the reported value with (R1+R2)/R2, where R1 is the +value of the divider resistor against the measured voltage and R2 is the value +of the divider resistor against Ground. + +Current reading provided by this driver is reported as obtained from the ADC +Current Sense register. The reported value assumes that a 1 mOhm sense resistor +is installed. If a different sense resistor is installed, calculate the real +current by dividing the reported value by the sense resistor value in mOhm. + +The chip has two voltage sensors, but only one set of voltage alarm status bits. +In many many designs, those alarms are associated with the ADIN2 sensor, due to +the proximity of the ADIN2 pin to the OV pin. ADIN2 is, however, not available +on all chip variants. To ensure that the alarm condition is reported to the user, +report it with both voltage sensors. + +======================= ============================= +in1_input ADIN2 voltage (mV) +in1_min_alarm ADIN/ADIN2 Undervoltage alarm +in1_max_alarm ADIN/ADIN2 Overvoltage alarm + +in2_input ADIN voltage (mV) +in2_min_alarm ADIN/ADIN2 Undervoltage alarm +in2_max_alarm ADIN/ADIN2 Overvoltage alarm + +curr1_input SENSE current (mA) +curr1_alarm SENSE overcurrent alarm +======================= ============================= diff --git a/Documentation/hwmon/max16064 b/Documentation/hwmon/max16064 deleted file mode 100644 index 61ec679dc477..000000000000 --- a/Documentation/hwmon/max16064 +++ /dev/null @@ -1,75 +0,0 @@ -Kernel driver max16064 -====================== - -Supported chips: - - * Maxim MAX16064 - - Prefix: 'max16064' - - Addresses scanned: - - - Datasheet: http://datasheets.maxim-ic.com/en/ds/MAX16064.pdf - -Author: Guenter Roeck - - -Description ------------ - -This driver supports hardware monitoring for Maxim MAX16064 Quad Power-Supply -Controller with Active-Voltage Output Control and PMBus Interface. - -The driver is a client driver to the core PMBus driver. -Please see Documentation/hwmon/pmbus for details on PMBus client drivers. - - -Usage Notes ------------ - -This driver does not auto-detect devices. You will have to instantiate the -devices explicitly. Please see Documentation/i2c/instantiating-devices for -details. - - -Platform data support ---------------------- - -The driver supports standard PMBus driver platform data. - - -Sysfs entries -------------- - -The following attributes are supported. Limits are read-write; all other -attributes are read-only. - -======================= ======================================================== -in[1-4]_label "vout[1-4]" -in[1-4]_input Measured voltage. From READ_VOUT register. -in[1-4]_min Minimum Voltage. From VOUT_UV_WARN_LIMIT register. -in[1-4]_max Maximum voltage. From VOUT_OV_WARN_LIMIT register. -in[1-4]_lcrit Critical minimum Voltage. VOUT_UV_FAULT_LIMIT register. -in[1-4]_crit Critical maximum voltage. From VOUT_OV_FAULT_LIMIT - register. -in[1-4]_min_alarm Voltage low alarm. From VOLTAGE_UV_WARNING status. -in[1-4]_max_alarm Voltage high alarm. From VOLTAGE_OV_WARNING status. -in[1-4]_lcrit_alarm Voltage critical low alarm. From VOLTAGE_UV_FAULT - status. -in[1-4]_crit_alarm Voltage critical high alarm. From VOLTAGE_OV_FAULT - status. -in[1-4]_highest Historical maximum voltage. -in[1-4]_reset_history Write any value to reset history. - -temp1_input Measured temperature. From READ_TEMPERATURE_1 register. -temp1_max Maximum temperature. From OT_WARN_LIMIT register. -temp1_crit Critical high temperature. From OT_FAULT_LIMIT register. -temp1_max_alarm Chip temperature high alarm. Set by comparing - READ_TEMPERATURE_1 with OT_WARN_LIMIT if TEMP_OT_WARNING - status is set. -temp1_crit_alarm Chip temperature critical high alarm. Set by comparing - READ_TEMPERATURE_1 with OT_FAULT_LIMIT if TEMP_OT_FAULT - status is set. -temp1_highest Historical maximum temperature. -temp1_reset_history Write any value to reset history. -======================= ======================================================== diff --git a/Documentation/hwmon/max16064.rst b/Documentation/hwmon/max16064.rst new file mode 100644 index 000000000000..6d5e9538991f --- /dev/null +++ b/Documentation/hwmon/max16064.rst @@ -0,0 +1,75 @@ +Kernel driver max16064 +====================== + +Supported chips: + + * Maxim MAX16064 + + Prefix: 'max16064' + + Addresses scanned: - + + Datasheet: http://datasheets.maxim-ic.com/en/ds/MAX16064.pdf + +Author: Guenter Roeck + + +Description +----------- + +This driver supports hardware monitoring for Maxim MAX16064 Quad Power-Supply +Controller with Active-Voltage Output Control and PMBus Interface. + +The driver is a client driver to the core PMBus driver. +Please see Documentation/hwmon/pmbus.rst for details on PMBus client drivers. + + +Usage Notes +----------- + +This driver does not auto-detect devices. You will have to instantiate the +devices explicitly. Please see Documentation/i2c/instantiating-devices for +details. + + +Platform data support +--------------------- + +The driver supports standard PMBus driver platform data. + + +Sysfs entries +------------- + +The following attributes are supported. Limits are read-write; all other +attributes are read-only. + +======================= ======================================================== +in[1-4]_label "vout[1-4]" +in[1-4]_input Measured voltage. From READ_VOUT register. +in[1-4]_min Minimum Voltage. From VOUT_UV_WARN_LIMIT register. +in[1-4]_max Maximum voltage. From VOUT_OV_WARN_LIMIT register. +in[1-4]_lcrit Critical minimum Voltage. VOUT_UV_FAULT_LIMIT register. +in[1-4]_crit Critical maximum voltage. From VOUT_OV_FAULT_LIMIT + register. +in[1-4]_min_alarm Voltage low alarm. From VOLTAGE_UV_WARNING status. +in[1-4]_max_alarm Voltage high alarm. From VOLTAGE_OV_WARNING status. +in[1-4]_lcrit_alarm Voltage critical low alarm. From VOLTAGE_UV_FAULT + status. +in[1-4]_crit_alarm Voltage critical high alarm. From VOLTAGE_OV_FAULT + status. +in[1-4]_highest Historical maximum voltage. +in[1-4]_reset_history Write any value to reset history. + +temp1_input Measured temperature. From READ_TEMPERATURE_1 register. +temp1_max Maximum temperature. From OT_WARN_LIMIT register. +temp1_crit Critical high temperature. From OT_FAULT_LIMIT register. +temp1_max_alarm Chip temperature high alarm. Set by comparing + READ_TEMPERATURE_1 with OT_WARN_LIMIT if TEMP_OT_WARNING + status is set. +temp1_crit_alarm Chip temperature critical high alarm. Set by comparing + READ_TEMPERATURE_1 with OT_FAULT_LIMIT if TEMP_OT_FAULT + status is set. +temp1_highest Historical maximum temperature. +temp1_reset_history Write any value to reset history. +======================= ======================================================== diff --git a/Documentation/hwmon/max16065 b/Documentation/hwmon/max16065 deleted file mode 100644 index fa5c852a178c..000000000000 --- a/Documentation/hwmon/max16065 +++ /dev/null @@ -1,127 +0,0 @@ -Kernel driver max16065 -====================== - - -Supported chips: - - * Maxim MAX16065, MAX16066 - - Prefixes: 'max16065', 'max16066' - - Addresses scanned: - - - Datasheet: - - http://datasheets.maxim-ic.com/en/ds/MAX16065-MAX16066.pdf - - * Maxim MAX16067 - - Prefix: 'max16067' - - Addresses scanned: - - - Datasheet: - - http://datasheets.maxim-ic.com/en/ds/MAX16067.pdf - - * Maxim MAX16068 - - Prefix: 'max16068' - - Addresses scanned: - - - Datasheet: - - http://datasheets.maxim-ic.com/en/ds/MAX16068.pdf - - * Maxim MAX16070/MAX16071 - - Prefixes: 'max16070', 'max16071' - - Addresses scanned: - - - Datasheet: - - http://datasheets.maxim-ic.com/en/ds/MAX16070-MAX16071.pdf - -Author: Guenter Roeck - - -Description ------------ - -[From datasheets] The MAX16065/MAX16066 flash-configurable system managers -monitor and sequence multiple system voltages. The MAX16065/MAX16066 can also -accurately monitor (+/-2.5%) one current channel using a dedicated high-side -current-sense amplifier. The MAX16065 manages up to twelve system voltages -simultaneously, and the MAX16066 manages up to eight supply voltages. - -The MAX16067 flash-configurable system manager monitors and sequences multiple -system voltages. The MAX16067 manages up to six system voltages simultaneously. - -The MAX16068 flash-configurable system manager monitors and manages up to six -system voltages simultaneously. - -The MAX16070/MAX16071 flash-configurable system monitors supervise multiple -system voltages. The MAX16070/MAX16071 can also accurately monitor (+/-2.5%) -one current channel using a dedicated high-side current-sense amplifier. The -MAX16070 monitors up to twelve system voltages simultaneously, and the MAX16071 -monitors up to eight supply voltages. - -Each monitored channel has its own low and high critical limits. MAX16065, -MAX16066, MAX16070, and MAX16071 support an additional limit which is -configurable as either low or high secondary limit. MAX16065, MAX16066, -MAX16070, and MAX16071 also support supply current monitoring. - - -Usage Notes ------------ - -This driver does not probe for devices, since there is no register which -can be safely used to identify the chip. You will have to instantiate -the devices explicitly. Please see Documentation/i2c/instantiating-devices for -details. - -WARNING: Do not access chip registers using the i2cdump command, and do not use -any of the i2ctools commands on a command register (0xa5 to 0xac). The chips -supported by this driver interpret any access to a command register (including -read commands) as request to execute the command in question. This may result in -power loss, board resets, and/or Flash corruption. Worst case, your board may -turn into a brick. - - -Sysfs entries -------------- - -======================= ======================================================== -in[0-11]_input Input voltage measurements. - -in12_input Voltage on CSP (Current Sense Positive) pin. - Only if the chip supports current sensing and if - current sensing is enabled. - -in[0-11]_min Low warning limit. - Supported on MAX16065, MAX16066, MAX16070, and MAX16071 - only. - -in[0-11]_max High warning limit. - Supported on MAX16065, MAX16066, MAX16070, and MAX16071 - only. - - Either low or high warning limits are supported - (depending on chip configuration), but not both. - -in[0-11]_lcrit Low critical limit. - -in[0-11]_crit High critical limit. - -in[0-11]_alarm Input voltage alarm. - -curr1_input Current sense input; only if the chip supports current - sensing and if current sensing is enabled. - Displayed current assumes 0.001 Ohm current sense - resistor. - -curr1_alarm Overcurrent alarm; only if the chip supports current - sensing and if current sensing is enabled. -======================= ======================================================== diff --git a/Documentation/hwmon/max16065.rst b/Documentation/hwmon/max16065.rst new file mode 100644 index 000000000000..fa5c852a178c --- /dev/null +++ b/Documentation/hwmon/max16065.rst @@ -0,0 +1,127 @@ +Kernel driver max16065 +====================== + + +Supported chips: + + * Maxim MAX16065, MAX16066 + + Prefixes: 'max16065', 'max16066' + + Addresses scanned: - + + Datasheet: + + http://datasheets.maxim-ic.com/en/ds/MAX16065-MAX16066.pdf + + * Maxim MAX16067 + + Prefix: 'max16067' + + Addresses scanned: - + + Datasheet: + + http://datasheets.maxim-ic.com/en/ds/MAX16067.pdf + + * Maxim MAX16068 + + Prefix: 'max16068' + + Addresses scanned: - + + Datasheet: + + http://datasheets.maxim-ic.com/en/ds/MAX16068.pdf + + * Maxim MAX16070/MAX16071 + + Prefixes: 'max16070', 'max16071' + + Addresses scanned: - + + Datasheet: + + http://datasheets.maxim-ic.com/en/ds/MAX16070-MAX16071.pdf + +Author: Guenter Roeck + + +Description +----------- + +[From datasheets] The MAX16065/MAX16066 flash-configurable system managers +monitor and sequence multiple system voltages. The MAX16065/MAX16066 can also +accurately monitor (+/-2.5%) one current channel using a dedicated high-side +current-sense amplifier. The MAX16065 manages up to twelve system voltages +simultaneously, and the MAX16066 manages up to eight supply voltages. + +The MAX16067 flash-configurable system manager monitors and sequences multiple +system voltages. The MAX16067 manages up to six system voltages simultaneously. + +The MAX16068 flash-configurable system manager monitors and manages up to six +system voltages simultaneously. + +The MAX16070/MAX16071 flash-configurable system monitors supervise multiple +system voltages. The MAX16070/MAX16071 can also accurately monitor (+/-2.5%) +one current channel using a dedicated high-side current-sense amplifier. The +MAX16070 monitors up to twelve system voltages simultaneously, and the MAX16071 +monitors up to eight supply voltages. + +Each monitored channel has its own low and high critical limits. MAX16065, +MAX16066, MAX16070, and MAX16071 support an additional limit which is +configurable as either low or high secondary limit. MAX16065, MAX16066, +MAX16070, and MAX16071 also support supply current monitoring. + + +Usage Notes +----------- + +This driver does not probe for devices, since there is no register which +can be safely used to identify the chip. You will have to instantiate +the devices explicitly. Please see Documentation/i2c/instantiating-devices for +details. + +WARNING: Do not access chip registers using the i2cdump command, and do not use +any of the i2ctools commands on a command register (0xa5 to 0xac). The chips +supported by this driver interpret any access to a command register (including +read commands) as request to execute the command in question. This may result in +power loss, board resets, and/or Flash corruption. Worst case, your board may +turn into a brick. + + +Sysfs entries +------------- + +======================= ======================================================== +in[0-11]_input Input voltage measurements. + +in12_input Voltage on CSP (Current Sense Positive) pin. + Only if the chip supports current sensing and if + current sensing is enabled. + +in[0-11]_min Low warning limit. + Supported on MAX16065, MAX16066, MAX16070, and MAX16071 + only. + +in[0-11]_max High warning limit. + Supported on MAX16065, MAX16066, MAX16070, and MAX16071 + only. + + Either low or high warning limits are supported + (depending on chip configuration), but not both. + +in[0-11]_lcrit Low critical limit. + +in[0-11]_crit High critical limit. + +in[0-11]_alarm Input voltage alarm. + +curr1_input Current sense input; only if the chip supports current + sensing and if current sensing is enabled. + Displayed current assumes 0.001 Ohm current sense + resistor. + +curr1_alarm Overcurrent alarm; only if the chip supports current + sensing and if current sensing is enabled. +======================= ======================================================== diff --git a/Documentation/hwmon/max1619 b/Documentation/hwmon/max1619 deleted file mode 100644 index 4b3762c4eceb..000000000000 --- a/Documentation/hwmon/max1619 +++ /dev/null @@ -1,34 +0,0 @@ -Kernel driver max1619 -===================== - -Supported chips: - - * Maxim MAX1619 - - Prefix: 'max1619' - - Addresses scanned: I2C 0x18-0x1a, 0x29-0x2b, 0x4c-0x4e - - Datasheet: Publicly available at the Maxim website - - http://pdfserv.maxim-ic.com/en/ds/MAX1619.pdf - -Authors: - - Oleksij Rempel , - - Jean Delvare - -Description ------------ - -The MAX1619 is a digital temperature sensor. It senses its own temperature as -well as the temperature of up to one external diode. - -All temperature values are given in degrees Celsius. Resolution -is 1.0 degree for the local temperature and for the remote temperature. - -Only the external sensor has high and low limits. - -The max1619 driver will not update its values more frequently than every -other second; reading them more often will do no harm, but will return -'old' values. - diff --git a/Documentation/hwmon/max1619.rst b/Documentation/hwmon/max1619.rst new file mode 100644 index 000000000000..e25956e70f73 --- /dev/null +++ b/Documentation/hwmon/max1619.rst @@ -0,0 +1,33 @@ +Kernel driver max1619 +===================== + +Supported chips: + + * Maxim MAX1619 + + Prefix: 'max1619' + + Addresses scanned: I2C 0x18-0x1a, 0x29-0x2b, 0x4c-0x4e + + Datasheet: Publicly available at the Maxim website + + http://pdfserv.maxim-ic.com/en/ds/MAX1619.pdf + +Authors: + - Oleksij Rempel , + - Jean Delvare + +Description +----------- + +The MAX1619 is a digital temperature sensor. It senses its own temperature as +well as the temperature of up to one external diode. + +All temperature values are given in degrees Celsius. Resolution +is 1.0 degree for the local temperature and for the remote temperature. + +Only the external sensor has high and low limits. + +The max1619 driver will not update its values more frequently than every +other second; reading them more often will do no harm, but will return +'old' values. diff --git a/Documentation/hwmon/max1668 b/Documentation/hwmon/max1668 deleted file mode 100644 index 417f17d750e6..000000000000 --- a/Documentation/hwmon/max1668 +++ /dev/null @@ -1,70 +0,0 @@ -Kernel driver max1668 -===================== - -Supported chips: - - * Maxim MAX1668, MAX1805 and MAX1989 - - Prefix: 'max1668' - - Addresses scanned: I2C 0x18, 0x19, 0x1a, 0x29, 0x2a, 0x2b, 0x4c, 0x4d, 0x4e - - Datasheet: http://datasheets.maxim-ic.com/en/ds/MAX1668-MAX1989.pdf - -Author: - - David George - -Description ------------ - -This driver implements support for the Maxim MAX1668, MAX1805 and MAX1989 -chips. - -The three devices are very similar, but the MAX1805 has a reduced feature -set; only two remote temperature inputs vs the four available on the other -two ICs. - -The driver is able to distinguish between the devices and creates sysfs -entries as follows: - -- MAX1805, MAX1668 and MAX1989: - -=============== == ============================================================ -temp1_input ro local (ambient) temperature -temp1_max rw local temperature maximum threshold for alarm -temp1_max_alarm ro local temperature maximum threshold alarm -temp1_min rw local temperature minimum threshold for alarm -temp1_min_alarm ro local temperature minimum threshold alarm -temp2_input ro remote temperature 1 -temp2_max rw remote temperature 1 maximum threshold for alarm -temp2_max_alarm ro remote temperature 1 maximum threshold alarm -temp2_min rw remote temperature 1 minimum threshold for alarm -temp2_min_alarm ro remote temperature 1 minimum threshold alarm -temp3_input ro remote temperature 2 -temp3_max rw remote temperature 2 maximum threshold for alarm -temp3_max_alarm ro remote temperature 2 maximum threshold alarm -temp3_min rw remote temperature 2 minimum threshold for alarm -temp3_min_alarm ro remote temperature 2 minimum threshold alarm -=============== == ============================================================ - -- MAX1668 and MAX1989 only: - -=============== == ============================================================ -temp4_input ro remote temperature 3 -temp4_max rw remote temperature 3 maximum threshold for alarm -temp4_max_alarm ro remote temperature 3 maximum threshold alarm -temp4_min rw remote temperature 3 minimum threshold for alarm -temp4_min_alarm ro remote temperature 3 minimum threshold alarm -temp5_input ro remote temperature 4 -temp5_max rw remote temperature 4 maximum threshold for alarm -temp5_max_alarm ro remote temperature 4 maximum threshold alarm -temp5_min rw remote temperature 4 minimum threshold for alarm -temp5_min_alarm ro remote temperature 4 minimum threshold alarm -=============== == ============================================================ - -Module Parameters ------------------ - -* read_only: int - Set to non-zero if you wish to prevent write access to alarm thresholds. diff --git a/Documentation/hwmon/max1668.rst b/Documentation/hwmon/max1668.rst new file mode 100644 index 000000000000..417f17d750e6 --- /dev/null +++ b/Documentation/hwmon/max1668.rst @@ -0,0 +1,70 @@ +Kernel driver max1668 +===================== + +Supported chips: + + * Maxim MAX1668, MAX1805 and MAX1989 + + Prefix: 'max1668' + + Addresses scanned: I2C 0x18, 0x19, 0x1a, 0x29, 0x2a, 0x2b, 0x4c, 0x4d, 0x4e + + Datasheet: http://datasheets.maxim-ic.com/en/ds/MAX1668-MAX1989.pdf + +Author: + + David George + +Description +----------- + +This driver implements support for the Maxim MAX1668, MAX1805 and MAX1989 +chips. + +The three devices are very similar, but the MAX1805 has a reduced feature +set; only two remote temperature inputs vs the four available on the other +two ICs. + +The driver is able to distinguish between the devices and creates sysfs +entries as follows: + +- MAX1805, MAX1668 and MAX1989: + +=============== == ============================================================ +temp1_input ro local (ambient) temperature +temp1_max rw local temperature maximum threshold for alarm +temp1_max_alarm ro local temperature maximum threshold alarm +temp1_min rw local temperature minimum threshold for alarm +temp1_min_alarm ro local temperature minimum threshold alarm +temp2_input ro remote temperature 1 +temp2_max rw remote temperature 1 maximum threshold for alarm +temp2_max_alarm ro remote temperature 1 maximum threshold alarm +temp2_min rw remote temperature 1 minimum threshold for alarm +temp2_min_alarm ro remote temperature 1 minimum threshold alarm +temp3_input ro remote temperature 2 +temp3_max rw remote temperature 2 maximum threshold for alarm +temp3_max_alarm ro remote temperature 2 maximum threshold alarm +temp3_min rw remote temperature 2 minimum threshold for alarm +temp3_min_alarm ro remote temperature 2 minimum threshold alarm +=============== == ============================================================ + +- MAX1668 and MAX1989 only: + +=============== == ============================================================ +temp4_input ro remote temperature 3 +temp4_max rw remote temperature 3 maximum threshold for alarm +temp4_max_alarm ro remote temperature 3 maximum threshold alarm +temp4_min rw remote temperature 3 minimum threshold for alarm +temp4_min_alarm ro remote temperature 3 minimum threshold alarm +temp5_input ro remote temperature 4 +temp5_max rw remote temperature 4 maximum threshold for alarm +temp5_max_alarm ro remote temperature 4 maximum threshold alarm +temp5_min rw remote temperature 4 minimum threshold for alarm +temp5_min_alarm ro remote temperature 4 minimum threshold alarm +=============== == ============================================================ + +Module Parameters +----------------- + +* read_only: int + Set to non-zero if you wish to prevent write access to alarm thresholds. diff --git a/Documentation/hwmon/max197 b/Documentation/hwmon/max197 deleted file mode 100644 index 02fe19bc3428..000000000000 --- a/Documentation/hwmon/max197 +++ /dev/null @@ -1,70 +0,0 @@ -Kernel driver max197 -==================== - -Author: - - * Vivien Didelot - -Supported chips: - - * Maxim MAX197 - - Prefix: 'max197' - - Datasheet: http://datasheets.maxim-ic.com/en/ds/MAX197.pdf - - * Maxim MAX199 - - Prefix: 'max199' - - Datasheet: http://datasheets.maxim-ic.com/en/ds/MAX199.pdf - -Description ------------ - -The A/D converters MAX197, and MAX199 are both 8-Channel, Multi-Range, 5V, -12-Bit DAS with 8+4 Bus Interface and Fault Protection. - -The available ranges for the MAX197 are {0,-5V} to 5V, and {0,-10V} to 10V, -while they are {0,-2V} to 2V, and {0,-4V} to 4V on the MAX199. - -Platform data -------------- - -The MAX197 platform data (defined in linux/platform_data/max197.h) should be -filled with a pointer to a conversion function, defined like:: - - int convert(u8 ctrl); - -ctrl is the control byte to write to start a new conversion. -On success, the function must return the 12-bit raw value read from the chip, -or a negative error code otherwise. - -Control byte format: - -======= ========== ============================================ -Bit Name Description -7,6 PD1,PD0 Clock and Power-Down modes -5 ACQMOD Internal or External Controlled Acquisition -4 RNG Full-scale voltage magnitude at the input -3 BIP Unipolar or Bipolar conversion mode -2,1,0 A2,A1,A0 Channel -======= ========== ============================================ - -Sysfs interface ---------------- - - ============== ============================================================== - in[0-7]_input The conversion value for the corresponding channel. - RO - - in[0-7]_min The lower limit (in mV) for the corresponding channel. - For the MAX197, it will be adjusted to -10000, -5000, or 0. - For the MAX199, it will be adjusted to -4000, -2000, or 0. - RW - - in[0-7]_max The higher limit (in mV) for the corresponding channel. - For the MAX197, it will be adjusted to 0, 5000, or 10000. - For the MAX199, it will be adjusted to 0, 2000, or 4000. - RW - ============== ============================================================== diff --git a/Documentation/hwmon/max197.rst b/Documentation/hwmon/max197.rst new file mode 100644 index 000000000000..02fe19bc3428 --- /dev/null +++ b/Documentation/hwmon/max197.rst @@ -0,0 +1,70 @@ +Kernel driver max197 +==================== + +Author: + + * Vivien Didelot + +Supported chips: + + * Maxim MAX197 + + Prefix: 'max197' + + Datasheet: http://datasheets.maxim-ic.com/en/ds/MAX197.pdf + + * Maxim MAX199 + + Prefix: 'max199' + + Datasheet: http://datasheets.maxim-ic.com/en/ds/MAX199.pdf + +Description +----------- + +The A/D converters MAX197, and MAX199 are both 8-Channel, Multi-Range, 5V, +12-Bit DAS with 8+4 Bus Interface and Fault Protection. + +The available ranges for the MAX197 are {0,-5V} to 5V, and {0,-10V} to 10V, +while they are {0,-2V} to 2V, and {0,-4V} to 4V on the MAX199. + +Platform data +------------- + +The MAX197 platform data (defined in linux/platform_data/max197.h) should be +filled with a pointer to a conversion function, defined like:: + + int convert(u8 ctrl); + +ctrl is the control byte to write to start a new conversion. +On success, the function must return the 12-bit raw value read from the chip, +or a negative error code otherwise. + +Control byte format: + +======= ========== ============================================ +Bit Name Description +7,6 PD1,PD0 Clock and Power-Down modes +5 ACQMOD Internal or External Controlled Acquisition +4 RNG Full-scale voltage magnitude at the input +3 BIP Unipolar or Bipolar conversion mode +2,1,0 A2,A1,A0 Channel +======= ========== ============================================ + +Sysfs interface +--------------- + + ============== ============================================================== + in[0-7]_input The conversion value for the corresponding channel. + RO + + in[0-7]_min The lower limit (in mV) for the corresponding channel. + For the MAX197, it will be adjusted to -10000, -5000, or 0. + For the MAX199, it will be adjusted to -4000, -2000, or 0. + RW + + in[0-7]_max The higher limit (in mV) for the corresponding channel. + For the MAX197, it will be adjusted to 0, 5000, or 10000. + For the MAX199, it will be adjusted to 0, 2000, or 4000. + RW + ============== ============================================================== diff --git a/Documentation/hwmon/max20751 b/Documentation/hwmon/max20751 deleted file mode 100644 index d546695900ef..000000000000 --- a/Documentation/hwmon/max20751 +++ /dev/null @@ -1,84 +0,0 @@ -Kernel driver max20751 -====================== - -Supported chips: - - * maxim MAX20751 - - Prefix: 'max20751' - - Addresses scanned: - - - Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX20751.pdf - - Application note: http://pdfserv.maximintegrated.com/en/an/AN5941.pdf - -Author: Guenter Roeck - - -Description ------------ - -This driver supports MAX20751 Multiphase Master with PMBus Interface -and Internal Buck Converter. - -The driver is a client driver to the core PMBus driver. -Please see Documentation/hwmon/pmbus for details on PMBus client drivers. - - -Usage Notes ------------ - -This driver does not auto-detect devices. You will have to instantiate the -devices explicitly. Please see Documentation/i2c/instantiating-devices for -details. - - -Platform data support ---------------------- - -The driver supports standard PMBus driver platform data. - - -Sysfs entries -------------- - -The following attributes are supported. - -======================= ======================================================= -in1_label "vin1" -in1_input Measured voltage. -in1_min Minimum input voltage. -in1_max Maximum input voltage. -in1_lcrit Critical minimum input voltage. -in1_crit Critical maximum input voltage. -in1_min_alarm Input voltage low alarm. -in1_lcrit_alarm Input voltage critical low alarm. -in1_min_alarm Input voltage low alarm. -in1_max_alarm Input voltage high alarm. - -in2_label "vout1" -in2_input Measured voltage. -in2_min Minimum output voltage. -in2_max Maximum output voltage. -in2_lcrit Critical minimum output voltage. -in2_crit Critical maximum output voltage. -in2_min_alarm Output voltage low alarm. -in2_lcrit_alarm Output voltage critical low alarm. -in2_min_alarm Output voltage low alarm. -in2_max_alarm Output voltage high alarm. - -curr1_input Measured output current. -curr1_label "iout1" -curr1_max Maximum output current. -curr1_alarm Current high alarm. - -temp1_input Measured temperature. -temp1_max Maximum temperature. -temp1_crit Critical high temperature. -temp1_max_alarm Chip temperature high alarm. -temp1_crit_alarm Chip temperature critical high alarm. - -power1_input Output power. -power1_label "pout1" -======================= ======================================================= diff --git a/Documentation/hwmon/max20751.rst b/Documentation/hwmon/max20751.rst new file mode 100644 index 000000000000..aa4469be6674 --- /dev/null +++ b/Documentation/hwmon/max20751.rst @@ -0,0 +1,84 @@ +Kernel driver max20751 +====================== + +Supported chips: + + * maxim MAX20751 + + Prefix: 'max20751' + + Addresses scanned: - + + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX20751.pdf + + Application note: http://pdfserv.maximintegrated.com/en/an/AN5941.pdf + +Author: Guenter Roeck + + +Description +----------- + +This driver supports MAX20751 Multiphase Master with PMBus Interface +and Internal Buck Converter. + +The driver is a client driver to the core PMBus driver. +Please see Documentation/hwmon/pmbus.rst for details on PMBus client drivers. + + +Usage Notes +----------- + +This driver does not auto-detect devices. You will have to instantiate the +devices explicitly. Please see Documentation/i2c/instantiating-devices for +details. + + +Platform data support +--------------------- + +The driver supports standard PMBus driver platform data. + + +Sysfs entries +------------- + +The following attributes are supported. + +======================= ======================================================= +in1_label "vin1" +in1_input Measured voltage. +in1_min Minimum input voltage. +in1_max Maximum input voltage. +in1_lcrit Critical minimum input voltage. +in1_crit Critical maximum input voltage. +in1_min_alarm Input voltage low alarm. +in1_lcrit_alarm Input voltage critical low alarm. +in1_min_alarm Input voltage low alarm. +in1_max_alarm Input voltage high alarm. + +in2_label "vout1" +in2_input Measured voltage. +in2_min Minimum output voltage. +in2_max Maximum output voltage. +in2_lcrit Critical minimum output voltage. +in2_crit Critical maximum output voltage. +in2_min_alarm Output voltage low alarm. +in2_lcrit_alarm Output voltage critical low alarm. +in2_min_alarm Output voltage low alarm. +in2_max_alarm Output voltage high alarm. + +curr1_input Measured output current. +curr1_label "iout1" +curr1_max Maximum output current. +curr1_alarm Current high alarm. + +temp1_input Measured temperature. +temp1_max Maximum temperature. +temp1_crit Critical high temperature. +temp1_max_alarm Chip temperature high alarm. +temp1_crit_alarm Chip temperature critical high alarm. + +power1_input Output power. +power1_label "pout1" +======================= ======================================================= diff --git a/Documentation/hwmon/max31722 b/Documentation/hwmon/max31722 deleted file mode 100644 index 0ab15c00b226..000000000000 --- a/Documentation/hwmon/max31722 +++ /dev/null @@ -1,46 +0,0 @@ -Kernel driver max31722 -====================== - -Supported chips: - - * Maxim Integrated MAX31722 - - Prefix: 'max31722' - - ACPI ID: MAX31722 - - Addresses scanned: - - - Datasheet: https://datasheets.maximintegrated.com/en/ds/MAX31722-MAX31723.pdf - - * Maxim Integrated MAX31723 - - Prefix: 'max31723' - - ACPI ID: MAX31723 - - Addresses scanned: - - - Datasheet: https://datasheets.maximintegrated.com/en/ds/MAX31722-MAX31723.pdf - -Author: Tiberiu Breana - -Description ------------ - -This driver adds support for the Maxim Integrated MAX31722/MAX31723 thermometers -and thermostats running over an SPI interface. - -Usage Notes ------------ - -This driver uses ACPI to auto-detect devices. See ACPI IDs in the above section. - -Sysfs entries -------------- - -The following attribute is supported: - -======================= ======================================================= -temp1_input Measured temperature. Read-only. -======================= ======================================================= diff --git a/Documentation/hwmon/max31722.rst b/Documentation/hwmon/max31722.rst new file mode 100644 index 000000000000..0ab15c00b226 --- /dev/null +++ b/Documentation/hwmon/max31722.rst @@ -0,0 +1,46 @@ +Kernel driver max31722 +====================== + +Supported chips: + + * Maxim Integrated MAX31722 + + Prefix: 'max31722' + + ACPI ID: MAX31722 + + Addresses scanned: - + + Datasheet: https://datasheets.maximintegrated.com/en/ds/MAX31722-MAX31723.pdf + + * Maxim Integrated MAX31723 + + Prefix: 'max31723' + + ACPI ID: MAX31723 + + Addresses scanned: - + + Datasheet: https://datasheets.maximintegrated.com/en/ds/MAX31722-MAX31723.pdf + +Author: Tiberiu Breana + +Description +----------- + +This driver adds support for the Maxim Integrated MAX31722/MAX31723 thermometers +and thermostats running over an SPI interface. + +Usage Notes +----------- + +This driver uses ACPI to auto-detect devices. See ACPI IDs in the above section. + +Sysfs entries +------------- + +The following attribute is supported: + +======================= ======================================================= +temp1_input Measured temperature. Read-only. +======================= ======================================================= diff --git a/Documentation/hwmon/max31785 b/Documentation/hwmon/max31785 deleted file mode 100644 index c8c6756d0ee1..000000000000 --- a/Documentation/hwmon/max31785 +++ /dev/null @@ -1,66 +0,0 @@ -Kernel driver max31785 -====================== - -Supported chips: - - * Maxim MAX31785, MAX31785A - - Prefix: 'max31785' or 'max31785a' - - Addresses scanned: - - - Datasheet: https://datasheets.maximintegrated.com/en/ds/MAX31785.pdf - -Author: Andrew Jeffery - -Description ------------ - -The Maxim MAX31785 is a PMBus device providing closed-loop, multi-channel fan -management with temperature and remote voltage sensing. Various fan control -features are provided, including PWM frequency control, temperature hysteresis, -dual tachometer measurements, and fan health monitoring. - -For dual-rotor configurations the MAX31785A exposes the second rotor tachometer -readings in attributes fan[5-8]_input. By contrast the MAX31785 only exposes -the slowest rotor measurement, and does so in the fan[1-4]_input attributes. - -Usage Notes ------------ - -This driver does not probe for PMBus devices. You will have to instantiate -devices explicitly. - -Sysfs attributes ----------------- - -======================= ======================================================= -fan[1-4]_alarm Fan alarm. -fan[1-4]_fault Fan fault. -fan[1-8]_input Fan RPM. On the MAX31785A, inputs 5-8 correspond to the - second rotor of fans 1-4 -fan[1-4]_target Fan input target - -in[1-6]_crit Critical maximum output voltage -in[1-6]_crit_alarm Output voltage critical high alarm -in[1-6]_input Measured output voltage -in[1-6]_label "vout[18-23]" -in[1-6]_lcrit Critical minimum output voltage -in[1-6]_lcrit_alarm Output voltage critical low alarm -in[1-6]_max Maximum output voltage -in[1-6]_max_alarm Output voltage high alarm -in[1-6]_min Minimum output voltage -in[1-6]_min_alarm Output voltage low alarm - -pwm[1-4] Fan target duty cycle (0..255) -pwm[1-4]_enable 0: Full-speed - 1: Manual PWM control - 2: Automatic PWM (tach-feedback RPM fan-control) - 3: Automatic closed-loop (temp-feedback fan-control) - -temp[1-11]_crit Critical high temperature -temp[1-11]_crit_alarm Chip temperature critical high alarm -temp[1-11]_input Measured temperature -temp[1-11]_max Maximum temperature -temp[1-11]_max_alarm Chip temperature high alarm -======================= ======================================================= diff --git a/Documentation/hwmon/max31785.rst b/Documentation/hwmon/max31785.rst new file mode 100644 index 000000000000..c8c6756d0ee1 --- /dev/null +++ b/Documentation/hwmon/max31785.rst @@ -0,0 +1,66 @@ +Kernel driver max31785 +====================== + +Supported chips: + + * Maxim MAX31785, MAX31785A + + Prefix: 'max31785' or 'max31785a' + + Addresses scanned: - + + Datasheet: https://datasheets.maximintegrated.com/en/ds/MAX31785.pdf + +Author: Andrew Jeffery + +Description +----------- + +The Maxim MAX31785 is a PMBus device providing closed-loop, multi-channel fan +management with temperature and remote voltage sensing. Various fan control +features are provided, including PWM frequency control, temperature hysteresis, +dual tachometer measurements, and fan health monitoring. + +For dual-rotor configurations the MAX31785A exposes the second rotor tachometer +readings in attributes fan[5-8]_input. By contrast the MAX31785 only exposes +the slowest rotor measurement, and does so in the fan[1-4]_input attributes. + +Usage Notes +----------- + +This driver does not probe for PMBus devices. You will have to instantiate +devices explicitly. + +Sysfs attributes +---------------- + +======================= ======================================================= +fan[1-4]_alarm Fan alarm. +fan[1-4]_fault Fan fault. +fan[1-8]_input Fan RPM. On the MAX31785A, inputs 5-8 correspond to the + second rotor of fans 1-4 +fan[1-4]_target Fan input target + +in[1-6]_crit Critical maximum output voltage +in[1-6]_crit_alarm Output voltage critical high alarm +in[1-6]_input Measured output voltage +in[1-6]_label "vout[18-23]" +in[1-6]_lcrit Critical minimum output voltage +in[1-6]_lcrit_alarm Output voltage critical low alarm +in[1-6]_max Maximum output voltage +in[1-6]_max_alarm Output voltage high alarm +in[1-6]_min Minimum output voltage +in[1-6]_min_alarm Output voltage low alarm + +pwm[1-4] Fan target duty cycle (0..255) +pwm[1-4]_enable 0: Full-speed + 1: Manual PWM control + 2: Automatic PWM (tach-feedback RPM fan-control) + 3: Automatic closed-loop (temp-feedback fan-control) + +temp[1-11]_crit Critical high temperature +temp[1-11]_crit_alarm Chip temperature critical high alarm +temp[1-11]_input Measured temperature +temp[1-11]_max Maximum temperature +temp[1-11]_max_alarm Chip temperature high alarm +======================= ======================================================= diff --git a/Documentation/hwmon/max31790 b/Documentation/hwmon/max31790 deleted file mode 100644 index 84c62a12ef3a..000000000000 --- a/Documentation/hwmon/max31790 +++ /dev/null @@ -1,43 +0,0 @@ -Kernel driver max31790 -====================== - -Supported chips: - - * Maxim MAX31790 - - Prefix: 'max31790' - - Addresses scanned: - - - Datasheet: http://pdfserv.maximintegrated.com/en/ds/MAX31790.pdf - -Author: Il Han - - -Description ------------ - -This driver implements support for the Maxim MAX31790 chip. - -The MAX31790 controls the speeds of up to six fans using six independent -PWM outputs. The desired fan speeds (or PWM duty cycles) are written -through the I2C interface. The outputs drive "4-wire" fans directly, -or can be used to modulate the fan's power terminals using an external -pass transistor. - -Tachometer inputs monitor fan tachometer logic outputs for precise (+/-1%) -monitoring and control of fan RPM as well as detection of fan failure. -Six pins are dedicated tachometer inputs. Any of the six PWM outputs can -also be configured to serve as tachometer inputs. - - -Sysfs entries -------------- - -================== === ======================================================= -fan[1-12]_input RO fan tachometer speed in RPM -fan[1-12]_fault RO fan experienced fault -fan[1-6]_target RW desired fan speed in RPM -pwm[1-6]_enable RW regulator mode, 0=disabled, 1=manual mode, 2=rpm mode -pwm[1-6] RW fan target duty cycle (0-255) -================== === ======================================================= diff --git a/Documentation/hwmon/max31790.rst b/Documentation/hwmon/max31790.rst new file mode 100644 index 000000000000..84c62a12ef3a --- /dev/null +++ b/Documentation/hwmon/max31790.rst @@ -0,0 +1,43 @@ +Kernel driver max31790 +====================== + +Supported chips: + + * Maxim MAX31790 + + Prefix: 'max31790' + + Addresses scanned: - + + Datasheet: http://pdfserv.maximintegrated.com/en/ds/MAX31790.pdf + +Author: Il Han + + +Description +----------- + +This driver implements support for the Maxim MAX31790 chip. + +The MAX31790 controls the speeds of up to six fans using six independent +PWM outputs. The desired fan speeds (or PWM duty cycles) are written +through the I2C interface. The outputs drive "4-wire" fans directly, +or can be used to modulate the fan's power terminals using an external +pass transistor. + +Tachometer inputs monitor fan tachometer logic outputs for precise (+/-1%) +monitoring and control of fan RPM as well as detection of fan failure. +Six pins are dedicated tachometer inputs. Any of the six PWM outputs can +also be configured to serve as tachometer inputs. + + +Sysfs entries +------------- + +================== === ======================================================= +fan[1-12]_input RO fan tachometer speed in RPM +fan[1-12]_fault RO fan experienced fault +fan[1-6]_target RW desired fan speed in RPM +pwm[1-6]_enable RW regulator mode, 0=disabled, 1=manual mode, 2=rpm mode +pwm[1-6] RW fan target duty cycle (0-255) +================== === ======================================================= diff --git a/Documentation/hwmon/max34440 b/Documentation/hwmon/max34440 deleted file mode 100644 index 639838ef29fd..000000000000 --- a/Documentation/hwmon/max34440 +++ /dev/null @@ -1,195 +0,0 @@ -Kernel driver max34440 -====================== - -Supported chips: - - * Maxim MAX34440 - - Prefixes: 'max34440' - - Addresses scanned: - - - Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX34440.pdf - - * Maxim MAX34441 - - PMBus 5-Channel Power-Supply Manager and Intelligent Fan Controller - - Prefixes: 'max34441' - - Addresses scanned: - - - Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX34441.pdf - - * Maxim MAX34446 - - PMBus Power-Supply Data Logger - - Prefixes: 'max34446' - - Addresses scanned: - - - Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX34446.pdf - - * Maxim MAX34451 - - PMBus 16-Channel V/I Monitor and 12-Channel Sequencer/Marginer - - Prefixes: 'max34451' - - Addresses scanned: - - - Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX34451.pdf - - * Maxim MAX34460 - - PMBus 12-Channel Voltage Monitor & Sequencer - - Prefix: 'max34460' - - Addresses scanned: - - - Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX34460.pdf - - * Maxim MAX34461 - - PMBus 16-Channel Voltage Monitor & Sequencer - - Prefix: 'max34461' - - Addresses scanned: - - - Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX34461.pdf - -Author: Guenter Roeck - - -Description ------------ - -This driver supports hardware monitoring for Maxim MAX34440 PMBus 6-Channel -Power-Supply Manager, MAX34441 PMBus 5-Channel Power-Supply Manager -and Intelligent Fan Controller, and MAX34446 PMBus Power-Supply Data Logger. -It also supports the MAX34451, MAX34460, and MAX34461 PMBus Voltage Monitor & -Sequencers. The MAX34451 supports monitoring voltage or current of 12 channels -based on GIN pins. The MAX34460 supports 12 voltage channels, and the MAX34461 -supports 16 voltage channels. - -The driver is a client driver to the core PMBus driver. Please see -Documentation/hwmon/pmbus for details on PMBus client drivers. - - -Usage Notes ------------ - -This driver does not auto-detect devices. You will have to instantiate the -devices explicitly. Please see Documentation/i2c/instantiating-devices for -details. - -For MAX34446, the value of the currX_crit attribute determines if current or -voltage measurement is enabled for a given channel. Voltage measurement is -enabled if currX_crit is set to 0; current measurement is enabled if the -attribute is set to a positive value. Power measurement is only enabled if -channel 1 (3) is configured for voltage measurement, and channel 2 (4) is -configured for current measurement. - - -Platform data support ---------------------- - -The driver supports standard PMBus driver platform data. - - -Sysfs entries -------------- - -The following attributes are supported. Limits are read-write; all other -attributes are read-only. - -In -~~ - -======================= ======================================================= -in[1-6]_label "vout[1-6]". -in[1-6]_input Measured voltage. From READ_VOUT register. -in[1-6]_min Minimum Voltage. From VOUT_UV_WARN_LIMIT register. -in[1-6]_max Maximum voltage. From VOUT_OV_WARN_LIMIT register. -in[1-6]_lcrit Critical minimum Voltage. VOUT_UV_FAULT_LIMIT register. -in[1-6]_crit Critical maximum voltage. From VOUT_OV_FAULT_LIMIT - register. -in[1-6]_min_alarm Voltage low alarm. From VOLTAGE_UV_WARNING status. -in[1-6]_max_alarm Voltage high alarm. From VOLTAGE_OV_WARNING status. -in[1-6]_lcrit_alarm Voltage critical low alarm. From VOLTAGE_UV_FAULT - status. -in[1-6]_crit_alarm Voltage critical high alarm. From VOLTAGE_OV_FAULT - status. -in[1-6]_lowest Historical minimum voltage. -in[1-6]_highest Historical maximum voltage. -in[1-6]_reset_history Write any value to reset history. -======================= ======================================================= - -.. note:: MAX34446 only supports in[1-4]. - -Curr -~~~~ - -======================= ======================================================== -curr[1-6]_label "iout[1-6]". -curr[1-6]_input Measured current. From READ_IOUT register. -curr[1-6]_max Maximum current. From IOUT_OC_WARN_LIMIT register. -curr[1-6]_crit Critical maximum current. From IOUT_OC_FAULT_LIMIT - register. -curr[1-6]_max_alarm Current high alarm. From IOUT_OC_WARNING status. -curr[1-6]_crit_alarm Current critical high alarm. From IOUT_OC_FAULT status. -curr[1-4]_average Historical average current (MAX34446/34451 only). -curr[1-6]_highest Historical maximum current. -curr[1-6]_reset_history Write any value to reset history. -======================= ======================================================== - -.. note:: - - - in6 and curr6 attributes only exist for MAX34440. - - MAX34446 only supports curr[1-4]. - -Power -~~~~~ - -======================= ======================================================== -power[1,3]_label "pout[1,3]" -power[1,3]_input Measured power. -power[1,3]_average Historical average power. -power[1,3]_highest Historical maximum power. -======================= ======================================================== - -.. note:: Power attributes only exist for MAX34446. - -Temp -~~~~ - -======================= ======================================================== -temp[1-8]_input Measured temperatures. From READ_TEMPERATURE_1 register. - temp1 is the chip's internal temperature. temp2..temp5 - are remote I2C temperature sensors. For MAX34441, temp6 - is a remote thermal-diode sensor. For MAX34440, temp6..8 - are remote I2C temperature sensors. -temp[1-8]_max Maximum temperature. From OT_WARN_LIMIT register. -temp[1-8]_crit Critical high temperature. From OT_FAULT_LIMIT register. -temp[1-8]_max_alarm Temperature high alarm. -temp[1-8]_crit_alarm Temperature critical high alarm. -temp[1-8]_average Historical average temperature (MAX34446 only). -temp[1-8]_highest Historical maximum temperature. -temp[1-8]_reset_history Write any value to reset history. -======================= ======================================================== - - -.. note:: - - temp7 and temp8 attributes only exist for MAX34440. - - MAX34446 only supports temp[1-3]. - - -.. note:: - - - MAX34451 supports attribute groups in[1-16] (or curr[1-16] based on - input pins) and temp[1-5]. - - MAX34460 supports attribute groups in[1-12] and temp[1-5]. - - MAX34461 supports attribute groups in[1-16] and temp[1-5]. diff --git a/Documentation/hwmon/max34440.rst b/Documentation/hwmon/max34440.rst new file mode 100644 index 000000000000..939138e12b02 --- /dev/null +++ b/Documentation/hwmon/max34440.rst @@ -0,0 +1,195 @@ +Kernel driver max34440 +====================== + +Supported chips: + + * Maxim MAX34440 + + Prefixes: 'max34440' + + Addresses scanned: - + + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX34440.pdf + + * Maxim MAX34441 + + PMBus 5-Channel Power-Supply Manager and Intelligent Fan Controller + + Prefixes: 'max34441' + + Addresses scanned: - + + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX34441.pdf + + * Maxim MAX34446 + + PMBus Power-Supply Data Logger + + Prefixes: 'max34446' + + Addresses scanned: - + + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX34446.pdf + + * Maxim MAX34451 + + PMBus 16-Channel V/I Monitor and 12-Channel Sequencer/Marginer + + Prefixes: 'max34451' + + Addresses scanned: - + + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX34451.pdf + + * Maxim MAX34460 + + PMBus 12-Channel Voltage Monitor & Sequencer + + Prefix: 'max34460' + + Addresses scanned: - + + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX34460.pdf + + * Maxim MAX34461 + + PMBus 16-Channel Voltage Monitor & Sequencer + + Prefix: 'max34461' + + Addresses scanned: - + + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX34461.pdf + +Author: Guenter Roeck + + +Description +----------- + +This driver supports hardware monitoring for Maxim MAX34440 PMBus 6-Channel +Power-Supply Manager, MAX34441 PMBus 5-Channel Power-Supply Manager +and Intelligent Fan Controller, and MAX34446 PMBus Power-Supply Data Logger. +It also supports the MAX34451, MAX34460, and MAX34461 PMBus Voltage Monitor & +Sequencers. The MAX34451 supports monitoring voltage or current of 12 channels +based on GIN pins. The MAX34460 supports 12 voltage channels, and the MAX34461 +supports 16 voltage channels. + +The driver is a client driver to the core PMBus driver. Please see +Documentation/hwmon/pmbus.rst for details on PMBus client drivers. + + +Usage Notes +----------- + +This driver does not auto-detect devices. You will have to instantiate the +devices explicitly. Please see Documentation/i2c/instantiating-devices for +details. + +For MAX34446, the value of the currX_crit attribute determines if current or +voltage measurement is enabled for a given channel. Voltage measurement is +enabled if currX_crit is set to 0; current measurement is enabled if the +attribute is set to a positive value. Power measurement is only enabled if +channel 1 (3) is configured for voltage measurement, and channel 2 (4) is +configured for current measurement. + + +Platform data support +--------------------- + +The driver supports standard PMBus driver platform data. + + +Sysfs entries +------------- + +The following attributes are supported. Limits are read-write; all other +attributes are read-only. + +In +~~ + +======================= ======================================================= +in[1-6]_label "vout[1-6]". +in[1-6]_input Measured voltage. From READ_VOUT register. +in[1-6]_min Minimum Voltage. From VOUT_UV_WARN_LIMIT register. +in[1-6]_max Maximum voltage. From VOUT_OV_WARN_LIMIT register. +in[1-6]_lcrit Critical minimum Voltage. VOUT_UV_FAULT_LIMIT register. +in[1-6]_crit Critical maximum voltage. From VOUT_OV_FAULT_LIMIT + register. +in[1-6]_min_alarm Voltage low alarm. From VOLTAGE_UV_WARNING status. +in[1-6]_max_alarm Voltage high alarm. From VOLTAGE_OV_WARNING status. +in[1-6]_lcrit_alarm Voltage critical low alarm. From VOLTAGE_UV_FAULT + status. +in[1-6]_crit_alarm Voltage critical high alarm. From VOLTAGE_OV_FAULT + status. +in[1-6]_lowest Historical minimum voltage. +in[1-6]_highest Historical maximum voltage. +in[1-6]_reset_history Write any value to reset history. +======================= ======================================================= + +.. note:: MAX34446 only supports in[1-4]. + +Curr +~~~~ + +======================= ======================================================== +curr[1-6]_label "iout[1-6]". +curr[1-6]_input Measured current. From READ_IOUT register. +curr[1-6]_max Maximum current. From IOUT_OC_WARN_LIMIT register. +curr[1-6]_crit Critical maximum current. From IOUT_OC_FAULT_LIMIT + register. +curr[1-6]_max_alarm Current high alarm. From IOUT_OC_WARNING status. +curr[1-6]_crit_alarm Current critical high alarm. From IOUT_OC_FAULT status. +curr[1-4]_average Historical average current (MAX34446/34451 only). +curr[1-6]_highest Historical maximum current. +curr[1-6]_reset_history Write any value to reset history. +======================= ======================================================== + +.. note:: + + - in6 and curr6 attributes only exist for MAX34440. + - MAX34446 only supports curr[1-4]. + +Power +~~~~~ + +======================= ======================================================== +power[1,3]_label "pout[1,3]" +power[1,3]_input Measured power. +power[1,3]_average Historical average power. +power[1,3]_highest Historical maximum power. +======================= ======================================================== + +.. note:: Power attributes only exist for MAX34446. + +Temp +~~~~ + +======================= ======================================================== +temp[1-8]_input Measured temperatures. From READ_TEMPERATURE_1 register. + temp1 is the chip's internal temperature. temp2..temp5 + are remote I2C temperature sensors. For MAX34441, temp6 + is a remote thermal-diode sensor. For MAX34440, temp6..8 + are remote I2C temperature sensors. +temp[1-8]_max Maximum temperature. From OT_WARN_LIMIT register. +temp[1-8]_crit Critical high temperature. From OT_FAULT_LIMIT register. +temp[1-8]_max_alarm Temperature high alarm. +temp[1-8]_crit_alarm Temperature critical high alarm. +temp[1-8]_average Historical average temperature (MAX34446 only). +temp[1-8]_highest Historical maximum temperature. +temp[1-8]_reset_history Write any value to reset history. +======================= ======================================================== + + +.. note:: + - temp7 and temp8 attributes only exist for MAX34440. + - MAX34446 only supports temp[1-3]. + + +.. note:: + + - MAX34451 supports attribute groups in[1-16] (or curr[1-16] based on + input pins) and temp[1-5]. + - MAX34460 supports attribute groups in[1-12] and temp[1-5]. + - MAX34461 supports attribute groups in[1-16] and temp[1-5]. diff --git a/Documentation/hwmon/max6639 b/Documentation/hwmon/max6639 deleted file mode 100644 index 3da54225f83c..000000000000 --- a/Documentation/hwmon/max6639 +++ /dev/null @@ -1,55 +0,0 @@ -Kernel driver max6639 -===================== - -Supported chips: - - * Maxim MAX6639 - - Prefix: 'max6639' - - Addresses scanned: I2C 0x2c, 0x2e, 0x2f - - Datasheet: http://pdfserv.maxim-ic.com/en/ds/MAX6639.pdf - -Authors: - - He Changqing - - Roland Stigge - -Description ------------ - -This driver implements support for the Maxim MAX6639. This chip is a 2-channel -temperature monitor with dual PWM fan speed controller. It can monitor its own -temperature and one external diode-connected transistor or two external -diode-connected transistors. - -The following device attributes are implemented via sysfs: - -====================== ==== =================================================== -Attribute R/W Contents -====================== ==== =================================================== -temp1_input R Temperature channel 1 input (0..150 C) -temp2_input R Temperature channel 2 input (0..150 C) -temp1_fault R Temperature channel 1 diode fault -temp2_fault R Temperature channel 2 diode fault -temp1_max RW Set THERM temperature for input 1 - (in C, see datasheet) -temp2_max RW Set THERM temperature for input 2 -temp1_crit RW Set ALERT temperature for input 1 -temp2_crit RW Set ALERT temperature for input 2 -temp1_emergency RW Set OT temperature for input 1 - (in C, see datasheet) -temp2_emergency RW Set OT temperature for input 2 -pwm1 RW Fan 1 target duty cycle (0..255) -pwm2 RW Fan 2 target duty cycle (0..255) -fan1_input R TACH1 fan tachometer input (in RPM) -fan2_input R TACH2 fan tachometer input (in RPM) -fan1_fault R Fan 1 fault -fan2_fault R Fan 2 fault -temp1_max_alarm R Alarm on THERM temperature on channel 1 -temp2_max_alarm R Alarm on THERM temperature on channel 2 -temp1_crit_alarm R Alarm on ALERT temperature on channel 1 -temp2_crit_alarm R Alarm on ALERT temperature on channel 2 -temp1_emergency_alarm R Alarm on OT temperature on channel 1 -temp2_emergency_alarm R Alarm on OT temperature on channel 2 -====================== ==== =================================================== diff --git a/Documentation/hwmon/max6639.rst b/Documentation/hwmon/max6639.rst new file mode 100644 index 000000000000..3da54225f83c --- /dev/null +++ b/Documentation/hwmon/max6639.rst @@ -0,0 +1,55 @@ +Kernel driver max6639 +===================== + +Supported chips: + + * Maxim MAX6639 + + Prefix: 'max6639' + + Addresses scanned: I2C 0x2c, 0x2e, 0x2f + + Datasheet: http://pdfserv.maxim-ic.com/en/ds/MAX6639.pdf + +Authors: + - He Changqing + - Roland Stigge + +Description +----------- + +This driver implements support for the Maxim MAX6639. This chip is a 2-channel +temperature monitor with dual PWM fan speed controller. It can monitor its own +temperature and one external diode-connected transistor or two external +diode-connected transistors. + +The following device attributes are implemented via sysfs: + +====================== ==== =================================================== +Attribute R/W Contents +====================== ==== =================================================== +temp1_input R Temperature channel 1 input (0..150 C) +temp2_input R Temperature channel 2 input (0..150 C) +temp1_fault R Temperature channel 1 diode fault +temp2_fault R Temperature channel 2 diode fault +temp1_max RW Set THERM temperature for input 1 + (in C, see datasheet) +temp2_max RW Set THERM temperature for input 2 +temp1_crit RW Set ALERT temperature for input 1 +temp2_crit RW Set ALERT temperature for input 2 +temp1_emergency RW Set OT temperature for input 1 + (in C, see datasheet) +temp2_emergency RW Set OT temperature for input 2 +pwm1 RW Fan 1 target duty cycle (0..255) +pwm2 RW Fan 2 target duty cycle (0..255) +fan1_input R TACH1 fan tachometer input (in RPM) +fan2_input R TACH2 fan tachometer input (in RPM) +fan1_fault R Fan 1 fault +fan2_fault R Fan 2 fault +temp1_max_alarm R Alarm on THERM temperature on channel 1 +temp2_max_alarm R Alarm on THERM temperature on channel 2 +temp1_crit_alarm R Alarm on ALERT temperature on channel 1 +temp2_crit_alarm R Alarm on ALERT temperature on channel 2 +temp1_emergency_alarm R Alarm on OT temperature on channel 1 +temp2_emergency_alarm R Alarm on OT temperature on channel 2 +====================== ==== =================================================== diff --git a/Documentation/hwmon/max6642 b/Documentation/hwmon/max6642 deleted file mode 100644 index 7e5b7d4f9492..000000000000 --- a/Documentation/hwmon/max6642 +++ /dev/null @@ -1,27 +0,0 @@ -Kernel driver max6642 -===================== - -Supported chips: - - * Maxim MAX6642 - - Prefix: 'max6642' - - Addresses scanned: I2C 0x48-0x4f - - Datasheet: Publicly available at the Maxim website - - http://datasheets.maxim-ic.com/en/ds/MAX6642.pdf - -Authors: - - Per Dalen - -Description ------------ - -The MAX6642 is a digital temperature sensor. It senses its own temperature as -well as the temperature on one external diode. - -All temperature values are given in degrees Celsius. Resolution -is 0.25 degree for the local temperature and for the remote temperature. diff --git a/Documentation/hwmon/max6642.rst b/Documentation/hwmon/max6642.rst new file mode 100644 index 000000000000..7e5b7d4f9492 --- /dev/null +++ b/Documentation/hwmon/max6642.rst @@ -0,0 +1,27 @@ +Kernel driver max6642 +===================== + +Supported chips: + + * Maxim MAX6642 + + Prefix: 'max6642' + + Addresses scanned: I2C 0x48-0x4f + + Datasheet: Publicly available at the Maxim website + + http://datasheets.maxim-ic.com/en/ds/MAX6642.pdf + +Authors: + + Per Dalen + +Description +----------- + +The MAX6642 is a digital temperature sensor. It senses its own temperature as +well as the temperature on one external diode. + +All temperature values are given in degrees Celsius. Resolution +is 0.25 degree for the local temperature and for the remote temperature. diff --git a/Documentation/hwmon/max6650 b/Documentation/hwmon/max6650 deleted file mode 100644 index 74dc3f0caaa2..000000000000 --- a/Documentation/hwmon/max6650 +++ /dev/null @@ -1,75 +0,0 @@ -Kernel driver max6650 -===================== - -Supported chips: - - * Maxim MAX6650 - - Prefix: 'max6650' - - Addresses scanned: none - - Datasheet: http://pdfserv.maxim-ic.com/en/ds/MAX6650-MAX6651.pdf - - * Maxim MAX6651 - - Prefix: 'max6651' - - Addresses scanned: none - - Datasheet: http://pdfserv.maxim-ic.com/en/ds/MAX6650-MAX6651.pdf - -Authors: - - Hans J. Koch - - John Morris - - Claus Gindhart - -Description ------------ - -This driver implements support for the Maxim MAX6650 and MAX6651. - -The 2 devices are very similar, but the MAX6550 has a reduced feature -set, e.g. only one fan-input, instead of 4 for the MAX6651. - -The driver is not able to distinguish between the 2 devices. - -The driver provides the following sensor accesses in sysfs: - -=============== ======= ======================================================= -fan1_input ro fan tachometer speed in RPM -fan2_input ro " -fan3_input ro " -fan4_input ro " -fan1_target rw desired fan speed in RPM (closed loop mode only) -pwm1_enable rw regulator mode, 0=full on, 1=open loop, 2=closed loop - 3=off -pwm1 rw relative speed (0-255), 255=max. speed. - Used in open loop mode only. -fan1_div rw sets the speed range the inputs can handle. Legal - values are 1, 2, 4, and 8. Use lower values for - faster fans. -=============== ======= ======================================================= - -Usage notes ------------ - -This driver does not auto-detect devices. You will have to instantiate the -devices explicitly. Please see Documentation/i2c/instantiating-devices for -details. - -Module parameters ------------------ - -If your board has a BIOS that initializes the MAX6650/6651 correctly, you can -simply load your module without parameters. It won't touch the configuration -registers then. If your board BIOS doesn't initialize the chip, or you want -different settings, you can set the following parameters: - -voltage_12V: 5=5V fan, 12=12V fan, 0=don't change -prescaler: Possible values are 1,2,4,8,16, or 0 for don't change -clock: The clock frequency in Hz of the chip the driver should assume [254000] - -Please have a look at the MAX6650/6651 data sheet and make sure that you fully -understand the meaning of these parameters before you attempt to change them. - diff --git a/Documentation/hwmon/max6650.rst b/Documentation/hwmon/max6650.rst new file mode 100644 index 000000000000..253482add082 --- /dev/null +++ b/Documentation/hwmon/max6650.rst @@ -0,0 +1,74 @@ +Kernel driver max6650 +===================== + +Supported chips: + + * Maxim MAX6650 + + Prefix: 'max6650' + + Addresses scanned: none + + Datasheet: http://pdfserv.maxim-ic.com/en/ds/MAX6650-MAX6651.pdf + + * Maxim MAX6651 + + Prefix: 'max6651' + + Addresses scanned: none + + Datasheet: http://pdfserv.maxim-ic.com/en/ds/MAX6650-MAX6651.pdf + +Authors: + - Hans J. Koch + - John Morris + - Claus Gindhart + +Description +----------- + +This driver implements support for the Maxim MAX6650 and MAX6651. + +The 2 devices are very similar, but the MAX6550 has a reduced feature +set, e.g. only one fan-input, instead of 4 for the MAX6651. + +The driver is not able to distinguish between the 2 devices. + +The driver provides the following sensor accesses in sysfs: + +=============== ======= ======================================================= +fan1_input ro fan tachometer speed in RPM +fan2_input ro " +fan3_input ro " +fan4_input ro " +fan1_target rw desired fan speed in RPM (closed loop mode only) +pwm1_enable rw regulator mode, 0=full on, 1=open loop, 2=closed loop + 3=off +pwm1 rw relative speed (0-255), 255=max. speed. + Used in open loop mode only. +fan1_div rw sets the speed range the inputs can handle. Legal + values are 1, 2, 4, and 8. Use lower values for + faster fans. +=============== ======= ======================================================= + +Usage notes +----------- + +This driver does not auto-detect devices. You will have to instantiate the +devices explicitly. Please see Documentation/i2c/instantiating-devices for +details. + +Module parameters +----------------- + +If your board has a BIOS that initializes the MAX6650/6651 correctly, you can +simply load your module without parameters. It won't touch the configuration +registers then. If your board BIOS doesn't initialize the chip, or you want +different settings, you can set the following parameters: + +voltage_12V: 5=5V fan, 12=12V fan, 0=don't change +prescaler: Possible values are 1,2,4,8,16, or 0 for don't change +clock: The clock frequency in Hz of the chip the driver should assume [254000] + +Please have a look at the MAX6650/6651 data sheet and make sure that you fully +understand the meaning of these parameters before you attempt to change them. diff --git a/Documentation/hwmon/max6697 b/Documentation/hwmon/max6697 deleted file mode 100644 index ffc5a7d8d33b..000000000000 --- a/Documentation/hwmon/max6697 +++ /dev/null @@ -1,91 +0,0 @@ -Kernel driver max6697 -===================== - -Supported chips: - - * Maxim MAX6581 - - Prefix: 'max6581' - - Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6581.pdf - - * Maxim MAX6602 - - Prefix: 'max6602' - - Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6602.pdf - - * Maxim MAX6622 - - Prefix: 'max6622' - - Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6622.pdf - - * Maxim MAX6636 - - Prefix: 'max6636' - - Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6636.pdf - - * Maxim MAX6689 - - Prefix: 'max6689' - - Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6689.pdf - - * Maxim MAX6693 - - Prefix: 'max6693' - - Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6693.pdf - - * Maxim MAX6694 - - Prefix: 'max6694' - - Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6694.pdf - - * Maxim MAX6697 - - Prefix: 'max6697' - - Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6697.pdf - - * Maxim MAX6698 - - Prefix: 'max6698' - - Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6698.pdf - - * Maxim MAX6699 - - Prefix: 'max6699' - - Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6699.pdf - -Author: - - Guenter Roeck - -Description ------------ - -This driver implements support for several MAX6697 compatible temperature sensor -chips. The chips support one local temperature sensor plus four, six, or seven -remote temperature sensors. Remote temperature sensors are diode-connected -thermal transitors, except for MAX6698 which supports three diode-connected -thermal transistors plus three thermistors in addition to the local temperature -sensor. - -The driver provides the following sysfs attributes. temp1 is the local (chip) -temperature, temp[2..n] are remote temperatures. The actually supported -per-channel attributes are chip type and channel dependent. - -================ == ========================================================== -tempX_input RO temperature -tempX_max RW temperature maximum threshold -tempX_max_alarm RO temperature maximum threshold alarm -tempX_crit RW temperature critical threshold -tempX_crit_alarm RO temperature critical threshold alarm -tempX_fault RO temperature diode fault (remote sensors only) -================ == ========================================================== diff --git a/Documentation/hwmon/max6697.rst b/Documentation/hwmon/max6697.rst new file mode 100644 index 000000000000..ffc5a7d8d33b --- /dev/null +++ b/Documentation/hwmon/max6697.rst @@ -0,0 +1,91 @@ +Kernel driver max6697 +===================== + +Supported chips: + + * Maxim MAX6581 + + Prefix: 'max6581' + + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6581.pdf + + * Maxim MAX6602 + + Prefix: 'max6602' + + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6602.pdf + + * Maxim MAX6622 + + Prefix: 'max6622' + + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6622.pdf + + * Maxim MAX6636 + + Prefix: 'max6636' + + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6636.pdf + + * Maxim MAX6689 + + Prefix: 'max6689' + + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6689.pdf + + * Maxim MAX6693 + + Prefix: 'max6693' + + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6693.pdf + + * Maxim MAX6694 + + Prefix: 'max6694' + + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6694.pdf + + * Maxim MAX6697 + + Prefix: 'max6697' + + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6697.pdf + + * Maxim MAX6698 + + Prefix: 'max6698' + + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6698.pdf + + * Maxim MAX6699 + + Prefix: 'max6699' + + Datasheet: http://datasheets.maximintegrated.com/en/ds/MAX6699.pdf + +Author: + + Guenter Roeck + +Description +----------- + +This driver implements support for several MAX6697 compatible temperature sensor +chips. The chips support one local temperature sensor plus four, six, or seven +remote temperature sensors. Remote temperature sensors are diode-connected +thermal transitors, except for MAX6698 which supports three diode-connected +thermal transistors plus three thermistors in addition to the local temperature +sensor. + +The driver provides the following sysfs attributes. temp1 is the local (chip) +temperature, temp[2..n] are remote temperatures. The actually supported +per-channel attributes are chip type and channel dependent. + +================ == ========================================================== +tempX_input RO temperature +tempX_max RW temperature maximum threshold +tempX_max_alarm RO temperature maximum threshold alarm +tempX_crit RW temperature critical threshold +tempX_crit_alarm RO temperature critical threshold alarm +tempX_fault RO temperature diode fault (remote sensors only) +================ == ========================================================== diff --git a/Documentation/hwmon/max8688 b/Documentation/hwmon/max8688 deleted file mode 100644 index 43da139234c1..000000000000 --- a/Documentation/hwmon/max8688 +++ /dev/null @@ -1,85 +0,0 @@ -Kernel driver max8688 -===================== - -Supported chips: - - * Maxim MAX8688 - - Prefix: 'max8688' - - Addresses scanned: - - - Datasheet: http://datasheets.maxim-ic.com/en/ds/MAX8688.pdf - -Author: Guenter Roeck - - -Description ------------ - -This driver supports hardware monitoring for Maxim MAX8688 Digital Power-Supply -Controller/Monitor with PMBus Interface. - -The driver is a client driver to the core PMBus driver. Please see -Documentation/hwmon/pmbus for details on PMBus client drivers. - - -Usage Notes ------------ - -This driver does not auto-detect devices. You will have to instantiate the -devices explicitly. Please see Documentation/i2c/instantiating-devices for -details. - - -Platform data support ---------------------- - -The driver supports standard PMBus driver platform data. - - -Sysfs entries -------------- - -The following attributes are supported. Limits are read-write; all other -attributes are read-only. - -======================= ======================================================== -in1_label "vout1" -in1_input Measured voltage. From READ_VOUT register. -in1_min Minimum Voltage. From VOUT_UV_WARN_LIMIT register. -in1_max Maximum voltage. From VOUT_OV_WARN_LIMIT register. -in1_lcrit Critical minimum Voltage. VOUT_UV_FAULT_LIMIT register. -in1_crit Critical maximum voltage. From VOUT_OV_FAULT_LIMIT - register. -in1_min_alarm Voltage low alarm. From VOLTAGE_UV_WARNING status. -in1_max_alarm Voltage high alarm. From VOLTAGE_OV_WARNING status. -in1_lcrit_alarm Voltage critical low alarm. From VOLTAGE_UV_FAULT - status. -in1_crit_alarm Voltage critical high alarm. From VOLTAGE_OV_FAULT - status. -in1_highest Historical maximum voltage. -in1_reset_history Write any value to reset history. - -curr1_label "iout1" -curr1_input Measured current. From READ_IOUT register. -curr1_max Maximum current. From IOUT_OC_WARN_LIMIT register. -curr1_crit Critical maximum current. From IOUT_OC_FAULT_LIMIT - register. -curr1_max_alarm Current high alarm. From IOUT_OC_WARN_LIMIT register. -curr1_crit_alarm Current critical high alarm. From IOUT_OC_FAULT status. -curr1_highest Historical maximum current. -curr1_reset_history Write any value to reset history. - -temp1_input Measured temperature. From READ_TEMPERATURE_1 register. -temp1_max Maximum temperature. From OT_WARN_LIMIT register. -temp1_crit Critical high temperature. From OT_FAULT_LIMIT register. -temp1_max_alarm Chip temperature high alarm. Set by comparing - READ_TEMPERATURE_1 with OT_WARN_LIMIT if TEMP_OT_WARNING - status is set. -temp1_crit_alarm Chip temperature critical high alarm. Set by comparing - READ_TEMPERATURE_1 with OT_FAULT_LIMIT if TEMP_OT_FAULT - status is set. -temp1_highest Historical maximum temperature. -temp1_reset_history Write any value to reset history. -======================= ======================================================== diff --git a/Documentation/hwmon/max8688.rst b/Documentation/hwmon/max8688.rst new file mode 100644 index 000000000000..009487759c61 --- /dev/null +++ b/Documentation/hwmon/max8688.rst @@ -0,0 +1,85 @@ +Kernel driver max8688 +===================== + +Supported chips: + + * Maxim MAX8688 + + Prefix: 'max8688' + + Addresses scanned: - + + Datasheet: http://datasheets.maxim-ic.com/en/ds/MAX8688.pdf + +Author: Guenter Roeck + + +Description +----------- + +This driver supports hardware monitoring for Maxim MAX8688 Digital Power-Supply +Controller/Monitor with PMBus Interface. + +The driver is a client driver to the core PMBus driver. Please see +Documentation/hwmon/pmbus.rst for details on PMBus client drivers. + + +Usage Notes +----------- + +This driver does not auto-detect devices. You will have to instantiate the +devices explicitly. Please see Documentation/i2c/instantiating-devices for +details. + + +Platform data support +--------------------- + +The driver supports standard PMBus driver platform data. + + +Sysfs entries +------------- + +The following attributes are supported. Limits are read-write; all other +attributes are read-only. + +======================= ======================================================== +in1_label "vout1" +in1_input Measured voltage. From READ_VOUT register. +in1_min Minimum Voltage. From VOUT_UV_WARN_LIMIT register. +in1_max Maximum voltage. From VOUT_OV_WARN_LIMIT register. +in1_lcrit Critical minimum Voltage. VOUT_UV_FAULT_LIMIT register. +in1_crit Critical maximum voltage. From VOUT_OV_FAULT_LIMIT + register. +in1_min_alarm Voltage low alarm. From VOLTAGE_UV_WARNING status. +in1_max_alarm Voltage high alarm. From VOLTAGE_OV_WARNING status. +in1_lcrit_alarm Voltage critical low alarm. From VOLTAGE_UV_FAULT + status. +in1_crit_alarm Voltage critical high alarm. From VOLTAGE_OV_FAULT + status. +in1_highest Historical maximum voltage. +in1_reset_history Write any value to reset history. + +curr1_label "iout1" +curr1_input Measured current. From READ_IOUT register. +curr1_max Maximum current. From IOUT_OC_WARN_LIMIT register. +curr1_crit Critical maximum current. From IOUT_OC_FAULT_LIMIT + register. +curr1_max_alarm Current high alarm. From IOUT_OC_WARN_LIMIT register. +curr1_crit_alarm Current critical high alarm. From IOUT_OC_FAULT status. +curr1_highest Historical maximum current. +curr1_reset_history Write any value to reset history. + +temp1_input Measured temperature. From READ_TEMPERATURE_1 register. +temp1_max Maximum temperature. From OT_WARN_LIMIT register. +temp1_crit Critical high temperature. From OT_FAULT_LIMIT register. +temp1_max_alarm Chip temperature high alarm. Set by comparing + READ_TEMPERATURE_1 with OT_WARN_LIMIT if TEMP_OT_WARNING + status is set. +temp1_crit_alarm Chip temperature critical high alarm. Set by comparing + READ_TEMPERATURE_1 with OT_FAULT_LIMIT if TEMP_OT_FAULT + status is set. +temp1_highest Historical maximum temperature. +temp1_reset_history Write any value to reset history. +======================= ======================================================== diff --git a/Documentation/hwmon/mc13783-adc b/Documentation/hwmon/mc13783-adc deleted file mode 100644 index cae70350ba2f..000000000000 --- a/Documentation/hwmon/mc13783-adc +++ /dev/null @@ -1,89 +0,0 @@ -Kernel driver mc13783-adc -========================= - -Supported chips: - - * Freescale MC13783 - - Prefix: 'mc13783' - - Datasheet: https://www.nxp.com/docs/en/data-sheet/MC13783.pdf - - * Freescale MC13892 - - Prefix: 'mc13892' - - Datasheet: https://www.nxp.com/docs/en/data-sheet/MC13892.pdf - - - -Authors: - - - Sascha Hauer - - Luotao Fu - -Description ------------ - -The Freescale MC13783 and MC13892 are Power Management and Audio Circuits. -Among other things they contain a 10-bit A/D converter. The converter has 16 -(MC13783) resp. 12 (MC13892) channels which can be used in different modes. The -A/D converter has a resolution of 2.25mV. - -Some channels can be used as General Purpose inputs or in a dedicated mode with -a chip internal scaling applied . - -Currently the driver only supports the Application Supply channel (BP / BPSNS), -the General Purpose inputs and touchscreen. - -See the following tables for the meaning of the different channels and their -chip internal scaling: - -- MC13783: - -======= =============================================== =============== ======= -Channel Signal Input Range Scaling -======= =============================================== =============== ======= -0 Battery Voltage (BATT) 2.50 - 4.65V -2.40V -1 Battery Current (BATT - BATTISNS) -50 - 50 mV x20 -2 Application Supply (BP) 2.50 - 4.65V -2.40V -3 Charger Voltage (CHRGRAW) 0 - 10V / /5 - 0 - 20V /10 -4 Charger Current (CHRGISNSP-CHRGISNSN) -0.25 - 0.25V x4 -5 General Purpose ADIN5 / Battery Pack Thermistor 0 - 2.30V No -6 General Purpose ADIN6 / Backup Voltage (LICELL) 0 - 2.30V / No / - 1.50 - 3.50V -1.20V -7 General Purpose ADIN7 / UID / Die Temperature 0 - 2.30V / No / - 0 - 2.55V / x0.9 / No -8 General Purpose ADIN8 0 - 2.30V No -9 General Purpose ADIN9 0 - 2.30V No -10 General Purpose ADIN10 0 - 2.30V No -11 General Purpose ADIN11 0 - 2.30V No -12 General Purpose TSX1 / Touchscreen X-plate 1 0 - 2.30V No -13 General Purpose TSX2 / Touchscreen X-plate 2 0 - 2.30V No -14 General Purpose TSY1 / Touchscreen Y-plate 1 0 - 2.30V No -15 General Purpose TSY2 / Touchscreen Y-plate 2 0 - 2.30V No -======= =============================================== =============== ======= - -- MC13892: - -======= =============================================== =============== ======= -Channel Signal Input Range Scaling -======= =============================================== =============== ======= -0 Battery Voltage (BATT) 0 - 4.8V /2 -1 Battery Current (BATT - BATTISNSCC) -60 - 60 mV x20 -2 Application Supply (BPSNS) 0 - 4.8V /2 -3 Charger Voltage (CHRGRAW) 0 - 12V / /5 - 0 - 20V /10 -4 Charger Current (CHRGISNS-BPSNS) / -0.3 - 0.3V / x4 / - Touchscreen X-plate 1 0 - 2.4V No -5 General Purpose ADIN5 / Battery Pack Thermistor 0 - 2.4V No -6 General Purpose ADIN6 / Backup Voltage (LICELL) 0 - 2.4V / No - Backup Voltage (LICELL) 0 - 3.6V x2/3 -7 General Purpose ADIN7 / UID / Die Temperature 0 - 2.4V / No / - 0 - 4.8V /2 -12 General Purpose TSX1 / Touchscreen X-plate 1 0 - 2.4V No -13 General Purpose TSX2 / Touchscreen X-plate 2 0 - 2.4V No -14 General Purpose TSY1 / Touchscreen Y-plate 1 0 - 2.4V No -15 General Purpose TSY2 / Touchscreen Y-plate 2 0 - 2.4V No -======= =============================================== =============== ======= diff --git a/Documentation/hwmon/mc13783-adc.rst b/Documentation/hwmon/mc13783-adc.rst new file mode 100644 index 000000000000..cae70350ba2f --- /dev/null +++ b/Documentation/hwmon/mc13783-adc.rst @@ -0,0 +1,89 @@ +Kernel driver mc13783-adc +========================= + +Supported chips: + + * Freescale MC13783 + + Prefix: 'mc13783' + + Datasheet: https://www.nxp.com/docs/en/data-sheet/MC13783.pdf + + * Freescale MC13892 + + Prefix: 'mc13892' + + Datasheet: https://www.nxp.com/docs/en/data-sheet/MC13892.pdf + + + +Authors: + + - Sascha Hauer + - Luotao Fu + +Description +----------- + +The Freescale MC13783 and MC13892 are Power Management and Audio Circuits. +Among other things they contain a 10-bit A/D converter. The converter has 16 +(MC13783) resp. 12 (MC13892) channels which can be used in different modes. The +A/D converter has a resolution of 2.25mV. + +Some channels can be used as General Purpose inputs or in a dedicated mode with +a chip internal scaling applied . + +Currently the driver only supports the Application Supply channel (BP / BPSNS), +the General Purpose inputs and touchscreen. + +See the following tables for the meaning of the different channels and their +chip internal scaling: + +- MC13783: + +======= =============================================== =============== ======= +Channel Signal Input Range Scaling +======= =============================================== =============== ======= +0 Battery Voltage (BATT) 2.50 - 4.65V -2.40V +1 Battery Current (BATT - BATTISNS) -50 - 50 mV x20 +2 Application Supply (BP) 2.50 - 4.65V -2.40V +3 Charger Voltage (CHRGRAW) 0 - 10V / /5 + 0 - 20V /10 +4 Charger Current (CHRGISNSP-CHRGISNSN) -0.25 - 0.25V x4 +5 General Purpose ADIN5 / Battery Pack Thermistor 0 - 2.30V No +6 General Purpose ADIN6 / Backup Voltage (LICELL) 0 - 2.30V / No / + 1.50 - 3.50V -1.20V +7 General Purpose ADIN7 / UID / Die Temperature 0 - 2.30V / No / + 0 - 2.55V / x0.9 / No +8 General Purpose ADIN8 0 - 2.30V No +9 General Purpose ADIN9 0 - 2.30V No +10 General Purpose ADIN10 0 - 2.30V No +11 General Purpose ADIN11 0 - 2.30V No +12 General Purpose TSX1 / Touchscreen X-plate 1 0 - 2.30V No +13 General Purpose TSX2 / Touchscreen X-plate 2 0 - 2.30V No +14 General Purpose TSY1 / Touchscreen Y-plate 1 0 - 2.30V No +15 General Purpose TSY2 / Touchscreen Y-plate 2 0 - 2.30V No +======= =============================================== =============== ======= + +- MC13892: + +======= =============================================== =============== ======= +Channel Signal Input Range Scaling +======= =============================================== =============== ======= +0 Battery Voltage (BATT) 0 - 4.8V /2 +1 Battery Current (BATT - BATTISNSCC) -60 - 60 mV x20 +2 Application Supply (BPSNS) 0 - 4.8V /2 +3 Charger Voltage (CHRGRAW) 0 - 12V / /5 + 0 - 20V /10 +4 Charger Current (CHRGISNS-BPSNS) / -0.3 - 0.3V / x4 / + Touchscreen X-plate 1 0 - 2.4V No +5 General Purpose ADIN5 / Battery Pack Thermistor 0 - 2.4V No +6 General Purpose ADIN6 / Backup Voltage (LICELL) 0 - 2.4V / No + Backup Voltage (LICELL) 0 - 3.6V x2/3 +7 General Purpose ADIN7 / UID / Die Temperature 0 - 2.4V / No / + 0 - 4.8V /2 +12 General Purpose TSX1 / Touchscreen X-plate 1 0 - 2.4V No +13 General Purpose TSX2 / Touchscreen X-plate 2 0 - 2.4V No +14 General Purpose TSY1 / Touchscreen Y-plate 1 0 - 2.4V No +15 General Purpose TSY2 / Touchscreen Y-plate 2 0 - 2.4V No +======= =============================================== =============== ======= diff --git a/Documentation/hwmon/mcp3021 b/Documentation/hwmon/mcp3021 deleted file mode 100644 index 83f4bda2f269..000000000000 --- a/Documentation/hwmon/mcp3021 +++ /dev/null @@ -1,38 +0,0 @@ -Kernel driver MCP3021 -===================== - -Supported chips: - - * Microchip Technology MCP3021 - - Prefix: 'mcp3021' - - Datasheet: http://ww1.microchip.com/downloads/en/DeviceDoc/21805a.pdf - - * Microchip Technology MCP3221 - - Prefix: 'mcp3221' - - Datasheet: http://ww1.microchip.com/downloads/en/DeviceDoc/21732c.pdf - - - -Authors: - - - Mingkai Hu - - Sven Schuchmann - -Description ------------ - -This driver implements support for the Microchip Technology MCP3021 and -MCP3221 chip. - -The Microchip Technology Inc. MCP3021 is a successive approximation A/D -converter (ADC) with 10-bit resolution. The MCP3221 has 12-bit resolution. - -These devices provide one single-ended input with very low power consumption. -Communication to the MCP3021/MCP3221 is performed using a 2-wire I2C -compatible interface. Standard (100 kHz) and Fast (400 kHz) I2C modes are -available. The default I2C device address is 0x4d (contact the Microchip -factory for additional address options). diff --git a/Documentation/hwmon/mcp3021.rst b/Documentation/hwmon/mcp3021.rst new file mode 100644 index 000000000000..83f4bda2f269 --- /dev/null +++ b/Documentation/hwmon/mcp3021.rst @@ -0,0 +1,38 @@ +Kernel driver MCP3021 +===================== + +Supported chips: + + * Microchip Technology MCP3021 + + Prefix: 'mcp3021' + + Datasheet: http://ww1.microchip.com/downloads/en/DeviceDoc/21805a.pdf + + * Microchip Technology MCP3221 + + Prefix: 'mcp3221' + + Datasheet: http://ww1.microchip.com/downloads/en/DeviceDoc/21732c.pdf + + + +Authors: + + - Mingkai Hu + - Sven Schuchmann + +Description +----------- + +This driver implements support for the Microchip Technology MCP3021 and +MCP3221 chip. + +The Microchip Technology Inc. MCP3021 is a successive approximation A/D +converter (ADC) with 10-bit resolution. The MCP3221 has 12-bit resolution. + +These devices provide one single-ended input with very low power consumption. +Communication to the MCP3021/MCP3221 is performed using a 2-wire I2C +compatible interface. Standard (100 kHz) and Fast (400 kHz) I2C modes are +available. The default I2C device address is 0x4d (contact the Microchip +factory for additional address options). diff --git a/Documentation/hwmon/menf21bmc b/Documentation/hwmon/menf21bmc deleted file mode 100644 index 1f0c6b2235ab..000000000000 --- a/Documentation/hwmon/menf21bmc +++ /dev/null @@ -1,55 +0,0 @@ -Kernel driver menf21bmc_hwmon -============================= - -Supported chips: - - * MEN 14F021P00 - - Prefix: 'menf21bmc_hwmon' - - Adresses scanned: - - -Author: Andreas Werner - -Description ------------ - -The menf21bmc is a Board Management Controller (BMC) which provides an I2C -interface to the host to access the features implemented in the BMC. - -This driver gives access to the voltage monitoring feature of the main -voltages of the board. -The voltage sensors are connected to the ADC inputs of the BMC which is -a PIC16F917 Mikrocontroller. - -Usage Notes ------------ - -This driver is part of the MFD driver named "menf21bmc" and does -not auto-detect devices. -You will have to instantiate the MFD driver explicitly. -Please see Documentation/i2c/instantiating-devices for -details. - -Sysfs entries -------------- - -The following attributes are supported. All attributes are read only -The Limits are read once by the driver. - -=============== ========================== -in0_input +3.3V input voltage -in1_input +5.0V input voltage -in2_input +12.0V input voltage -in3_input +5V Standby input voltage -in4_input VBAT (on board battery) - -in[0-4]_min Minimum voltage limit -in[0-4]_max Maximum voltage limit - -in0_label "MON_3_3V" -in1_label "MON_5V" -in2_label "MON_12V" -in3_label "5V_STANDBY" -in4_label "VBAT" -=============== ========================== diff --git a/Documentation/hwmon/menf21bmc.rst b/Documentation/hwmon/menf21bmc.rst new file mode 100644 index 000000000000..1f0c6b2235ab --- /dev/null +++ b/Documentation/hwmon/menf21bmc.rst @@ -0,0 +1,55 @@ +Kernel driver menf21bmc_hwmon +============================= + +Supported chips: + + * MEN 14F021P00 + + Prefix: 'menf21bmc_hwmon' + + Adresses scanned: - + +Author: Andreas Werner + +Description +----------- + +The menf21bmc is a Board Management Controller (BMC) which provides an I2C +interface to the host to access the features implemented in the BMC. + +This driver gives access to the voltage monitoring feature of the main +voltages of the board. +The voltage sensors are connected to the ADC inputs of the BMC which is +a PIC16F917 Mikrocontroller. + +Usage Notes +----------- + +This driver is part of the MFD driver named "menf21bmc" and does +not auto-detect devices. +You will have to instantiate the MFD driver explicitly. +Please see Documentation/i2c/instantiating-devices for +details. + +Sysfs entries +------------- + +The following attributes are supported. All attributes are read only +The Limits are read once by the driver. + +=============== ========================== +in0_input +3.3V input voltage +in1_input +5.0V input voltage +in2_input +12.0V input voltage +in3_input +5V Standby input voltage +in4_input VBAT (on board battery) + +in[0-4]_min Minimum voltage limit +in[0-4]_max Maximum voltage limit + +in0_label "MON_3_3V" +in1_label "MON_5V" +in2_label "MON_12V" +in3_label "5V_STANDBY" +in4_label "VBAT" +=============== ========================== diff --git a/Documentation/hwmon/mlxreg-fan b/Documentation/hwmon/mlxreg-fan deleted file mode 100644 index c92b8e885f7e..000000000000 --- a/Documentation/hwmon/mlxreg-fan +++ /dev/null @@ -1,70 +0,0 @@ -Kernel driver mlxreg-fan -======================== - -Provides FAN control for the next Mellanox systems: - -- QMB700, equipped with 40x200GbE InfiniBand ports; -- MSN3700, equipped with 32x200GbE or 16x400GbE Ethernet ports; -- MSN3410, equipped with 6x400GbE plus 48x50GbE Ethernet ports; -- MSN3800, equipped with 64x1000GbE Ethernet ports; - -Author: Vadim Pasternak - -These are the Top of the Rack systems, equipped with Mellanox switch -board with Mellanox Quantum or Spectrume-2 devices. -FAN controller is implemented by the programmable device logic. - -The default registers offsets set within the programmable device is as -following: - -======================= ==== -pwm1 0xe3 -fan1 (tacho1) 0xe4 -fan2 (tacho2) 0xe5 -fan3 (tacho3) 0xe6 -fan4 (tacho4) 0xe7 -fan5 (tacho5) 0xe8 -fan6 (tacho6) 0xe9 -fan7 (tacho7) 0xea -fan8 (tacho8) 0xeb -fan9 (tacho9) 0xec -fan10 (tacho10) 0xed -fan11 (tacho11) 0xee -fan12 (tacho12) 0xef -======================= ==== - -This setup can be re-programmed with other registers. - -Description ------------ - -The driver implements a simple interface for driving a fan connected to -a PWM output and tachometer inputs. -This driver obtains PWM and tachometers registers location according to -the system configuration and creates FAN/PWM hwmon objects and a cooling -device. PWM and tachometers are sensed through the on-board programmable -device, which exports its register map. This device could be attached to -any bus type, for which register mapping is supported. -Single instance is created with one PWM control, up to 12 tachometers and -one cooling device. It could be as many instances as programmable device -supports. -The driver exposes the fan to the user space through the hwmon's and -thermal's sysfs interfaces. - -/sys files in hwmon subsystem ------------------------------ - -================= == =================================================== -fan[1-12]_fault RO files for tachometers TACH1-TACH12 fault indication -fan[1-12]_input RO files for tachometers TACH1-TACH12 input (in RPM) -pwm1 RW file for fan[1-12] target duty cycle (0..255) -================= == =================================================== - -/sys files in thermal subsystem -------------------------------- - -================= == ==================================================== -cur_state RW file for current cooling state of the cooling device - (0..max_state) -max_state RO file for maximum cooling state of the cooling device -================= == ==================================================== diff --git a/Documentation/hwmon/mlxreg-fan.rst b/Documentation/hwmon/mlxreg-fan.rst new file mode 100644 index 000000000000..c92b8e885f7e --- /dev/null +++ b/Documentation/hwmon/mlxreg-fan.rst @@ -0,0 +1,70 @@ +Kernel driver mlxreg-fan +======================== + +Provides FAN control for the next Mellanox systems: + +- QMB700, equipped with 40x200GbE InfiniBand ports; +- MSN3700, equipped with 32x200GbE or 16x400GbE Ethernet ports; +- MSN3410, equipped with 6x400GbE plus 48x50GbE Ethernet ports; +- MSN3800, equipped with 64x1000GbE Ethernet ports; + +Author: Vadim Pasternak + +These are the Top of the Rack systems, equipped with Mellanox switch +board with Mellanox Quantum or Spectrume-2 devices. +FAN controller is implemented by the programmable device logic. + +The default registers offsets set within the programmable device is as +following: + +======================= ==== +pwm1 0xe3 +fan1 (tacho1) 0xe4 +fan2 (tacho2) 0xe5 +fan3 (tacho3) 0xe6 +fan4 (tacho4) 0xe7 +fan5 (tacho5) 0xe8 +fan6 (tacho6) 0xe9 +fan7 (tacho7) 0xea +fan8 (tacho8) 0xeb +fan9 (tacho9) 0xec +fan10 (tacho10) 0xed +fan11 (tacho11) 0xee +fan12 (tacho12) 0xef +======================= ==== + +This setup can be re-programmed with other registers. + +Description +----------- + +The driver implements a simple interface for driving a fan connected to +a PWM output and tachometer inputs. +This driver obtains PWM and tachometers registers location according to +the system configuration and creates FAN/PWM hwmon objects and a cooling +device. PWM and tachometers are sensed through the on-board programmable +device, which exports its register map. This device could be attached to +any bus type, for which register mapping is supported. +Single instance is created with one PWM control, up to 12 tachometers and +one cooling device. It could be as many instances as programmable device +supports. +The driver exposes the fan to the user space through the hwmon's and +thermal's sysfs interfaces. + +/sys files in hwmon subsystem +----------------------------- + +================= == =================================================== +fan[1-12]_fault RO files for tachometers TACH1-TACH12 fault indication +fan[1-12]_input RO files for tachometers TACH1-TACH12 input (in RPM) +pwm1 RW file for fan[1-12] target duty cycle (0..255) +================= == =================================================== + +/sys files in thermal subsystem +------------------------------- + +================= == ==================================================== +cur_state RW file for current cooling state of the cooling device + (0..max_state) +max_state RO file for maximum cooling state of the cooling device +================= == ==================================================== diff --git a/Documentation/hwmon/nct6683 b/Documentation/hwmon/nct6683 deleted file mode 100644 index efbf7e9703ec..000000000000 --- a/Documentation/hwmon/nct6683 +++ /dev/null @@ -1,64 +0,0 @@ -Kernel driver nct6683 -===================== - -Supported chips: - - * Nuvoton NCT6683D - - Prefix: 'nct6683' - - Addresses scanned: ISA address retrieved from Super I/O registers - - Datasheet: Available from Nuvoton upon request - -Authors: - - Guenter Roeck - -Description ------------ - -This driver implements support for the Nuvoton NCT6683D eSIO chip. - -The chips implement up to shared 32 temperature and voltage sensors. -It supports up to 16 fan rotation sensors and up to 8 fan control engines. - -Temperatures are measured in degrees Celsius. Measurement resolution is -0.5 degrees C. - -Voltage sensors (also known as IN sensors) report their values in millivolts. - -Fan rotation speeds are reported in RPM (rotations per minute). - -Usage Note ----------- - -Limit register locations on Intel boards with EC firmware version 1.0 -build date 04/03/13 do not match the register locations in the Nuvoton -datasheet. Nuvoton confirms that Intel uses a special firmware version -with different register addresses. The specification describing the Intel -firmware is held under NDA by Nuvoton and Intel and not available -to the public. - -Some of the register locations can be reverse engineered; others are too -well hidden. Given this, writing any values from the operating system is -considered too risky with this firmware and has been disabled. All limits -must all be written from the BIOS. - -The driver has only been tested with the Intel firmware, and by default -only instantiates on Intel boards. To enable it on non-Intel boards, -set the 'force' module parameter to 1. - -Tested Boards and Firmware Versions ------------------------------------ - -The driver has been reported to work with the following boards and -firmware versions. - -=============== =============================================== -Board Firmware version -=============== =============================================== -Intel DH87RL NCT6683D EC firmware version 1.0 build 04/03/13 -Intel DH87MC NCT6683D EC firmware version 1.0 build 04/03/13 -Intel DB85FL NCT6683D EC firmware version 1.0 build 04/03/13 -=============== =============================================== diff --git a/Documentation/hwmon/nct6683.rst b/Documentation/hwmon/nct6683.rst new file mode 100644 index 000000000000..efbf7e9703ec --- /dev/null +++ b/Documentation/hwmon/nct6683.rst @@ -0,0 +1,64 @@ +Kernel driver nct6683 +===================== + +Supported chips: + + * Nuvoton NCT6683D + + Prefix: 'nct6683' + + Addresses scanned: ISA address retrieved from Super I/O registers + + Datasheet: Available from Nuvoton upon request + +Authors: + + Guenter Roeck + +Description +----------- + +This driver implements support for the Nuvoton NCT6683D eSIO chip. + +The chips implement up to shared 32 temperature and voltage sensors. +It supports up to 16 fan rotation sensors and up to 8 fan control engines. + +Temperatures are measured in degrees Celsius. Measurement resolution is +0.5 degrees C. + +Voltage sensors (also known as IN sensors) report their values in millivolts. + +Fan rotation speeds are reported in RPM (rotations per minute). + +Usage Note +---------- + +Limit register locations on Intel boards with EC firmware version 1.0 +build date 04/03/13 do not match the register locations in the Nuvoton +datasheet. Nuvoton confirms that Intel uses a special firmware version +with different register addresses. The specification describing the Intel +firmware is held under NDA by Nuvoton and Intel and not available +to the public. + +Some of the register locations can be reverse engineered; others are too +well hidden. Given this, writing any values from the operating system is +considered too risky with this firmware and has been disabled. All limits +must all be written from the BIOS. + +The driver has only been tested with the Intel firmware, and by default +only instantiates on Intel boards. To enable it on non-Intel boards, +set the 'force' module parameter to 1. + +Tested Boards and Firmware Versions +----------------------------------- + +The driver has been reported to work with the following boards and +firmware versions. + +=============== =============================================== +Board Firmware version +=============== =============================================== +Intel DH87RL NCT6683D EC firmware version 1.0 build 04/03/13 +Intel DH87MC NCT6683D EC firmware version 1.0 build 04/03/13 +Intel DB85FL NCT6683D EC firmware version 1.0 build 04/03/13 +=============== =============================================== diff --git a/Documentation/hwmon/nct6775 b/Documentation/hwmon/nct6775 deleted file mode 100644 index 1d0315c40952..000000000000 --- a/Documentation/hwmon/nct6775 +++ /dev/null @@ -1,280 +0,0 @@ -Kernel driver NCT6775 -===================== - -.. note:: - - This driver supersedes the NCT6775F and NCT6776F support in the W83627EHF - driver. - -Supported chips: - - * Nuvoton NCT6102D/NCT6104D/NCT6106D - - Prefix: 'nct6106' - - Addresses scanned: ISA address retrieved from Super I/O registers - - Datasheet: Available from the Nuvoton web site - - * Nuvoton NCT5572D/NCT6771F/NCT6772F/NCT6775F/W83677HG-I - - Prefix: 'nct6775' - - Addresses scanned: ISA address retrieved from Super I/O registers - - Datasheet: Available from Nuvoton upon request - - * Nuvoton NCT5573D/NCT5577D/NCT6776D/NCT6776F - - Prefix: 'nct6776' - - Addresses scanned: ISA address retrieved from Super I/O registers - - Datasheet: Available from Nuvoton upon request - - * Nuvoton NCT5532D/NCT6779D - - Prefix: 'nct6779' - - Addresses scanned: ISA address retrieved from Super I/O registers - - Datasheet: Available from Nuvoton upon request - - * Nuvoton NCT6791D - - Prefix: 'nct6791' - - Addresses scanned: ISA address retrieved from Super I/O registers - - Datasheet: Available from Nuvoton upon request - - * Nuvoton NCT6792D - - Prefix: 'nct6792' - - Addresses scanned: ISA address retrieved from Super I/O registers - - Datasheet: Available from Nuvoton upon request - - * Nuvoton NCT6793D - - Prefix: 'nct6793' - - Addresses scanned: ISA address retrieved from Super I/O registers - - Datasheet: Available from Nuvoton upon request - - * Nuvoton NCT6795D - - Prefix: 'nct6795' - - Addresses scanned: ISA address retrieved from Super I/O registers - - Datasheet: Available from Nuvoton upon request - - * Nuvoton NCT6796D - - Prefix: 'nct6796' - - Addresses scanned: ISA address retrieved from Super I/O registers - - Datasheet: Available from Nuvoton upon request - - - -Authors: - - Guenter Roeck - -Description ------------ - -This driver implements support for the Nuvoton NCT6775F, NCT6776F, and NCT6779D -and compatible super I/O chips. - -The chips support up to 25 temperature monitoring sources. Up to 6 of those are -direct temperature sensor inputs, the others are special sources such as PECI, -PCH, and SMBUS. Depending on the chip type, 2 to 6 of the temperature sources -can be monitored and compared against minimum, maximum, and critical -temperatures. The driver reports up to 10 of the temperatures to the user. -There are 4 to 5 fan rotation speed sensors, 8 to 15 analog voltage sensors, -one VID, alarms with beep warnings (control unimplemented), and some automatic -fan regulation strategies (plus manual fan control mode). - -The temperature sensor sources on all chips are configurable. The configured -source for each of the temperature sensors is provided in tempX_label. - -Temperatures are measured in degrees Celsius and measurement resolution is -either 1 degC or 0.5 degC, depending on the temperature source and -configuration. An alarm is triggered when the temperature gets higher than -the high limit; it stays on until the temperature falls below the hysteresis -value. Alarms are only supported for temp1 to temp6, depending on the chip type. - -Fan rotation speeds are reported in RPM (rotations per minute). An alarm is -triggered if the rotation speed has dropped below a programmable limit. On -NCT6775F, fan readings can be divided by a programmable divider (1, 2, 4, 8, -16, 32, 64 or 128) to give the readings more range or accuracy; the other chips -do not have a fan speed divider. The driver sets the most suitable fan divisor -itself; specifically, it increases the divider value each time a fan speed -reading returns an invalid value, and it reduces it if the fan speed reading -is lower than optimal. Some fans might not be present because they share pins -with other functions. - -Voltage sensors (also known as IN sensors) report their values in millivolts. -An alarm is triggered if the voltage has crossed a programmable minimum -or maximum limit. - -The driver supports automatic fan control mode known as Thermal Cruise. -In this mode, the chip attempts to keep the measured temperature in a -predefined temperature range. If the temperature goes out of range, fan -is driven slower/faster to reach the predefined range again. - -The mode works for fan1-fan5. - -sysfs attributes ----------------- - -pwm[1-7] - - this file stores PWM duty cycle or DC value (fan speed) in range: - - 0 (lowest speed) to 255 (full) - -pwm[1-7]_enable - - this file controls mode of fan/temperature control: - - * 0 Fan control disabled (fans set to maximum speed) - * 1 Manual mode, write to pwm[0-5] any value 0-255 - * 2 "Thermal Cruise" mode - * 3 "Fan Speed Cruise" mode - * 4 "Smart Fan III" mode (NCT6775F only) - * 5 "Smart Fan IV" mode - -pwm[1-7]_mode - - controls if output is PWM or DC level - - * 0 DC output - * 1 PWM output - -Common fan control attributes ------------------------------ - -pwm[1-7]_temp_sel - Temperature source. Value is temperature sensor index. - For example, select '1' for temp1_input. - -pwm[1-7]_weight_temp_sel - Secondary temperature source. Value is temperature - sensor index. For example, select '1' for temp1_input. - Set to 0 to disable secondary temperature control. - -If secondary temperature functionality is enabled, it is controlled with the -following attributes. - -pwm[1-7]_weight_duty_step - Duty step size. - -pwm[1-7]_weight_temp_step - Temperature step size. With each step over - temp_step_base, the value of weight_duty_step is added - to the current pwm value. - -pwm[1-7]_weight_temp_step_base - Temperature at which secondary temperature control kicks - in. - -pwm[1-7]_weight_temp_step_tol - Temperature step tolerance. - -Thermal Cruise mode (2) ------------------------ - -If the temperature is in the range defined by: - -pwm[1-7]_target_temp - Target temperature, unit millidegree Celsius - (range 0 - 127000) - -pwm[1-7]_temp_tolerance - Target temperature tolerance, unit millidegree Celsius - -There are no changes to fan speed. Once the temperature leaves the interval, fan -speed increases (if temperature is higher that desired) or decreases (if -temperature is lower than desired), using the following limits and time -intervals. - -pwm[1-7]_start - fan pwm start value (range 1 - 255), to start fan - when the temperature is above defined range. - -pwm[1-7]_floor - lowest fan pwm (range 0 - 255) if temperature is below - the defined range. If set to 0, the fan is expected to - stop if the temperature is below the defined range. - -pwm[1-7]_step_up_time - milliseconds before fan speed is increased - -pwm[1-7]_step_down_time - milliseconds before fan speed is decreased - -pwm[1-7]_stop_time - how many milliseconds must elapse to switch - corresponding fan off (when the temperature was below - defined range). - -Speed Cruise mode (3) ---------------------- - -This modes tries to keep the fan speed constant. - -fan[1-7]_target - Target fan speed - -fan[1-7]_tolerance - Target speed tolerance - - -Untested; use at your own risk. - -Smart Fan IV mode (5) ---------------------- - -This mode offers multiple slopes to control the fan speed. The slopes can be -controlled by setting the pwm and temperature attributes. When the temperature -rises, the chip will calculate the DC/PWM output based on the current slope. -There are up to seven data points depending on the chip type. Subsequent data -points should be set to higher temperatures and higher pwm values to achieve -higher fan speeds with increasing temperature. The last data point reflects -critical temperature mode, in which the fans should run at full speed. - -pwm[1-7]_auto_point[1-7]_pwm - pwm value to be set if temperature reaches matching - temperature range. - -pwm[1-7]_auto_point[1-7]_temp - Temperature over which the matching pwm is enabled. - -pwm[1-7]_temp_tolerance - Temperature tolerance, unit millidegree Celsius - -pwm[1-7]_crit_temp_tolerance - Temperature tolerance for critical temperature, - unit millidegree Celsius - -pwm[1-7]_step_up_time - milliseconds before fan speed is increased - -pwm[1-7]_step_down_time - milliseconds before fan speed is decreased - -Usage Notes ------------ - -On various ASUS boards with NCT6776F, it appears that CPUTIN is not really -connected to anything and floats, or that it is connected to some non-standard -temperature measurement device. As a result, the temperature reported on CPUTIN -will not reflect a usable value. It often reports unreasonably high -temperatures, and in some cases the reported temperature declines if the actual -temperature increases (similar to the raw PECI temperature value - see PECI -specification for details). CPUTIN should therefore be be ignored on ASUS -boards. The CPU temperature on ASUS boards is reported from PECI 0. diff --git a/Documentation/hwmon/nct6775.rst b/Documentation/hwmon/nct6775.rst new file mode 100644 index 000000000000..1d0315c40952 --- /dev/null +++ b/Documentation/hwmon/nct6775.rst @@ -0,0 +1,280 @@ +Kernel driver NCT6775 +===================== + +.. note:: + + This driver supersedes the NCT6775F and NCT6776F support in the W83627EHF + driver. + +Supported chips: + + * Nuvoton NCT6102D/NCT6104D/NCT6106D + + Prefix: 'nct6106' + + Addresses scanned: ISA address retrieved from Super I/O registers + + Datasheet: Available from the Nuvoton web site + + * Nuvoton NCT5572D/NCT6771F/NCT6772F/NCT6775F/W83677HG-I + + Prefix: 'nct6775' + + Addresses scanned: ISA address retrieved from Super I/O registers + + Datasheet: Available from Nuvoton upon request + + * Nuvoton NCT5573D/NCT5577D/NCT6776D/NCT6776F + + Prefix: 'nct6776' + + Addresses scanned: ISA address retrieved from Super I/O registers + + Datasheet: Available from Nuvoton upon request + + * Nuvoton NCT5532D/NCT6779D + + Prefix: 'nct6779' + + Addresses scanned: ISA address retrieved from Super I/O registers + + Datasheet: Available from Nuvoton upon request + + * Nuvoton NCT6791D + + Prefix: 'nct6791' + + Addresses scanned: ISA address retrieved from Super I/O registers + + Datasheet: Available from Nuvoton upon request + + * Nuvoton NCT6792D + + Prefix: 'nct6792' + + Addresses scanned: ISA address retrieved from Super I/O registers + + Datasheet: Available from Nuvoton upon request + + * Nuvoton NCT6793D + + Prefix: 'nct6793' + + Addresses scanned: ISA address retrieved from Super I/O registers + + Datasheet: Available from Nuvoton upon request + + * Nuvoton NCT6795D + + Prefix: 'nct6795' + + Addresses scanned: ISA address retrieved from Super I/O registers + + Datasheet: Available from Nuvoton upon request + + * Nuvoton NCT6796D + + Prefix: 'nct6796' + + Addresses scanned: ISA address retrieved from Super I/O registers + + Datasheet: Available from Nuvoton upon request + + + +Authors: + + Guenter Roeck + +Description +----------- + +This driver implements support for the Nuvoton NCT6775F, NCT6776F, and NCT6779D +and compatible super I/O chips. + +The chips support up to 25 temperature monitoring sources. Up to 6 of those are +direct temperature sensor inputs, the others are special sources such as PECI, +PCH, and SMBUS. Depending on the chip type, 2 to 6 of the temperature sources +can be monitored and compared against minimum, maximum, and critical +temperatures. The driver reports up to 10 of the temperatures to the user. +There are 4 to 5 fan rotation speed sensors, 8 to 15 analog voltage sensors, +one VID, alarms with beep warnings (control unimplemented), and some automatic +fan regulation strategies (plus manual fan control mode). + +The temperature sensor sources on all chips are configurable. The configured +source for each of the temperature sensors is provided in tempX_label. + +Temperatures are measured in degrees Celsius and measurement resolution is +either 1 degC or 0.5 degC, depending on the temperature source and +configuration. An alarm is triggered when the temperature gets higher than +the high limit; it stays on until the temperature falls below the hysteresis +value. Alarms are only supported for temp1 to temp6, depending on the chip type. + +Fan rotation speeds are reported in RPM (rotations per minute). An alarm is +triggered if the rotation speed has dropped below a programmable limit. On +NCT6775F, fan readings can be divided by a programmable divider (1, 2, 4, 8, +16, 32, 64 or 128) to give the readings more range or accuracy; the other chips +do not have a fan speed divider. The driver sets the most suitable fan divisor +itself; specifically, it increases the divider value each time a fan speed +reading returns an invalid value, and it reduces it if the fan speed reading +is lower than optimal. Some fans might not be present because they share pins +with other functions. + +Voltage sensors (also known as IN sensors) report their values in millivolts. +An alarm is triggered if the voltage has crossed a programmable minimum +or maximum limit. + +The driver supports automatic fan control mode known as Thermal Cruise. +In this mode, the chip attempts to keep the measured temperature in a +predefined temperature range. If the temperature goes out of range, fan +is driven slower/faster to reach the predefined range again. + +The mode works for fan1-fan5. + +sysfs attributes +---------------- + +pwm[1-7] + - this file stores PWM duty cycle or DC value (fan speed) in range: + + 0 (lowest speed) to 255 (full) + +pwm[1-7]_enable + - this file controls mode of fan/temperature control: + + * 0 Fan control disabled (fans set to maximum speed) + * 1 Manual mode, write to pwm[0-5] any value 0-255 + * 2 "Thermal Cruise" mode + * 3 "Fan Speed Cruise" mode + * 4 "Smart Fan III" mode (NCT6775F only) + * 5 "Smart Fan IV" mode + +pwm[1-7]_mode + - controls if output is PWM or DC level + + * 0 DC output + * 1 PWM output + +Common fan control attributes +----------------------------- + +pwm[1-7]_temp_sel + Temperature source. Value is temperature sensor index. + For example, select '1' for temp1_input. + +pwm[1-7]_weight_temp_sel + Secondary temperature source. Value is temperature + sensor index. For example, select '1' for temp1_input. + Set to 0 to disable secondary temperature control. + +If secondary temperature functionality is enabled, it is controlled with the +following attributes. + +pwm[1-7]_weight_duty_step + Duty step size. + +pwm[1-7]_weight_temp_step + Temperature step size. With each step over + temp_step_base, the value of weight_duty_step is added + to the current pwm value. + +pwm[1-7]_weight_temp_step_base + Temperature at which secondary temperature control kicks + in. + +pwm[1-7]_weight_temp_step_tol + Temperature step tolerance. + +Thermal Cruise mode (2) +----------------------- + +If the temperature is in the range defined by: + +pwm[1-7]_target_temp + Target temperature, unit millidegree Celsius + (range 0 - 127000) + +pwm[1-7]_temp_tolerance + Target temperature tolerance, unit millidegree Celsius + +There are no changes to fan speed. Once the temperature leaves the interval, fan +speed increases (if temperature is higher that desired) or decreases (if +temperature is lower than desired), using the following limits and time +intervals. + +pwm[1-7]_start + fan pwm start value (range 1 - 255), to start fan + when the temperature is above defined range. + +pwm[1-7]_floor + lowest fan pwm (range 0 - 255) if temperature is below + the defined range. If set to 0, the fan is expected to + stop if the temperature is below the defined range. + +pwm[1-7]_step_up_time + milliseconds before fan speed is increased + +pwm[1-7]_step_down_time + milliseconds before fan speed is decreased + +pwm[1-7]_stop_time + how many milliseconds must elapse to switch + corresponding fan off (when the temperature was below + defined range). + +Speed Cruise mode (3) +--------------------- + +This modes tries to keep the fan speed constant. + +fan[1-7]_target + Target fan speed + +fan[1-7]_tolerance + Target speed tolerance + + +Untested; use at your own risk. + +Smart Fan IV mode (5) +--------------------- + +This mode offers multiple slopes to control the fan speed. The slopes can be +controlled by setting the pwm and temperature attributes. When the temperature +rises, the chip will calculate the DC/PWM output based on the current slope. +There are up to seven data points depending on the chip type. Subsequent data +points should be set to higher temperatures and higher pwm values to achieve +higher fan speeds with increasing temperature. The last data point reflects +critical temperature mode, in which the fans should run at full speed. + +pwm[1-7]_auto_point[1-7]_pwm + pwm value to be set if temperature reaches matching + temperature range. + +pwm[1-7]_auto_point[1-7]_temp + Temperature over which the matching pwm is enabled. + +pwm[1-7]_temp_tolerance + Temperature tolerance, unit millidegree Celsius + +pwm[1-7]_crit_temp_tolerance + Temperature tolerance for critical temperature, + unit millidegree Celsius + +pwm[1-7]_step_up_time + milliseconds before fan speed is increased + +pwm[1-7]_step_down_time + milliseconds before fan speed is decreased + +Usage Notes +----------- + +On various ASUS boards with NCT6776F, it appears that CPUTIN is not really +connected to anything and floats, or that it is connected to some non-standard +temperature measurement device. As a result, the temperature reported on CPUTIN +will not reflect a usable value. It often reports unreasonably high +temperatures, and in some cases the reported temperature declines if the actual +temperature increases (similar to the raw PECI temperature value - see PECI +specification for details). CPUTIN should therefore be be ignored on ASUS +boards. The CPU temperature on ASUS boards is reported from PECI 0. diff --git a/Documentation/hwmon/nct7802 b/Documentation/hwmon/nct7802 deleted file mode 100644 index 8b7365a7cb32..000000000000 --- a/Documentation/hwmon/nct7802 +++ /dev/null @@ -1,38 +0,0 @@ -Kernel driver nct7802 -===================== - -Supported chips: - - * Nuvoton NCT7802Y - - Prefix: 'nct7802' - - Addresses scanned: I2C 0x28..0x2f - - Datasheet: Available from Nuvoton web site - -Authors: - - Guenter Roeck - -Description ------------ - -This driver implements support for the Nuvoton NCT7802Y hardware monitoring -chip. NCT7802Y supports 6 temperature sensors, 5 voltage sensors, and 3 fan -speed sensors. - -Smart Fan™ speed control is available via pwmX_auto_point attributes. - -Tested Boards and BIOS Versions -------------------------------- - -The driver has been reported to work with the following boards and -BIOS versions. - -======================= =============================================== -Board BIOS version -======================= =============================================== -Kontron COMe-bSC2 CHR2E934.001.GGO -Kontron COMe-bIP2 CCR2E212 -======================= =============================================== diff --git a/Documentation/hwmon/nct7802.rst b/Documentation/hwmon/nct7802.rst new file mode 100644 index 000000000000..8b7365a7cb32 --- /dev/null +++ b/Documentation/hwmon/nct7802.rst @@ -0,0 +1,38 @@ +Kernel driver nct7802 +===================== + +Supported chips: + + * Nuvoton NCT7802Y + + Prefix: 'nct7802' + + Addresses scanned: I2C 0x28..0x2f + + Datasheet: Available from Nuvoton web site + +Authors: + + Guenter Roeck + +Description +----------- + +This driver implements support for the Nuvoton NCT7802Y hardware monitoring +chip. NCT7802Y supports 6 temperature sensors, 5 voltage sensors, and 3 fan +speed sensors. + +Smart Fan™ speed control is available via pwmX_auto_point attributes. + +Tested Boards and BIOS Versions +------------------------------- + +The driver has been reported to work with the following boards and +BIOS versions. + +======================= =============================================== +Board BIOS version +======================= =============================================== +Kontron COMe-bSC2 CHR2E934.001.GGO +Kontron COMe-bIP2 CCR2E212 +======================= =============================================== diff --git a/Documentation/hwmon/nct7904 b/Documentation/hwmon/nct7904 deleted file mode 100644 index 5b2f111582ff..000000000000 --- a/Documentation/hwmon/nct7904 +++ /dev/null @@ -1,67 +0,0 @@ -Kernel driver nct7904 -===================== - -Supported chip: - - * Nuvoton NCT7904D - - Prefix: nct7904 - - Addresses: I2C 0x2d, 0x2e - - Datasheet: Publicly available at Nuvoton website - - http://www.nuvoton.com/ - -Author: Vadim V. Vlasov - - -Description ------------ - -The NCT7904D is a hardware monitor supporting up to 20 voltage sensors, -internal temperature sensor, Intel PECI and AMD SB-TSI CPU temperature -interface, up to 12 fan tachometer inputs, up to 4 fan control channels -with SmartFan. - - -Sysfs entries -------------- - -Currently, the driver supports only the following features: - -======================= ======================================================= -in[1-20]_input Input voltage measurements (mV) - -fan[1-12]_input Fan tachometer measurements (rpm) - -temp1_input Local temperature (1/1000 degree, - 0.125 degree resolution) - -temp[2-9]_input CPU temperatures (1/1000 degree, - 0.125 degree resolution) - -pwm[1-4]_enable R/W, 1/2 for manual or SmartFan mode - Setting SmartFan mode is supported only if it has been - previously configured by BIOS (or configuration EEPROM) - -pwm[1-4] R/O in SmartFan mode, R/W in manual control mode -======================= ======================================================= - -The driver checks sensor control registers and does not export the sensors -that are not enabled. Anyway, a sensor that is enabled may actually be not -connected and thus provide zero readings. - - -Limitations ------------ - -The following features are not supported in current version: - - - SmartFan control - - Watchdog - - GPIO - - external temperature sensors - - SMI - - min/max values - - many other... diff --git a/Documentation/hwmon/nct7904.rst b/Documentation/hwmon/nct7904.rst new file mode 100644 index 000000000000..5b2f111582ff --- /dev/null +++ b/Documentation/hwmon/nct7904.rst @@ -0,0 +1,67 @@ +Kernel driver nct7904 +===================== + +Supported chip: + + * Nuvoton NCT7904D + + Prefix: nct7904 + + Addresses: I2C 0x2d, 0x2e + + Datasheet: Publicly available at Nuvoton website + + http://www.nuvoton.com/ + +Author: Vadim V. Vlasov + + +Description +----------- + +The NCT7904D is a hardware monitor supporting up to 20 voltage sensors, +internal temperature sensor, Intel PECI and AMD SB-TSI CPU temperature +interface, up to 12 fan tachometer inputs, up to 4 fan control channels +with SmartFan. + + +Sysfs entries +------------- + +Currently, the driver supports only the following features: + +======================= ======================================================= +in[1-20]_input Input voltage measurements (mV) + +fan[1-12]_input Fan tachometer measurements (rpm) + +temp1_input Local temperature (1/1000 degree, + 0.125 degree resolution) + +temp[2-9]_input CPU temperatures (1/1000 degree, + 0.125 degree resolution) + +pwm[1-4]_enable R/W, 1/2 for manual or SmartFan mode + Setting SmartFan mode is supported only if it has been + previously configured by BIOS (or configuration EEPROM) + +pwm[1-4] R/O in SmartFan mode, R/W in manual control mode +======================= ======================================================= + +The driver checks sensor control registers and does not export the sensors +that are not enabled. Anyway, a sensor that is enabled may actually be not +connected and thus provide zero readings. + + +Limitations +----------- + +The following features are not supported in current version: + + - SmartFan control + - Watchdog + - GPIO + - external temperature sensors + - SMI + - min/max values + - many other... diff --git a/Documentation/hwmon/npcm750-pwm-fan b/Documentation/hwmon/npcm750-pwm-fan deleted file mode 100644 index c67af08b6773..000000000000 --- a/Documentation/hwmon/npcm750-pwm-fan +++ /dev/null @@ -1,26 +0,0 @@ -Kernel driver npcm750-pwm-fan -============================= - -Supported chips: - - NUVOTON NPCM750/730/715/705 - -Authors: - - - -Description: ------------- -This driver implements support for NUVOTON NPCM7XX PWM and Fan Tacho -controller. The PWM controller supports up to 8 PWM outputs. The Fan tacho -controller supports up to 16 tachometer inputs. - -The driver provides the following sensor accesses in sysfs: - -=============== ======= ===================================================== -fanX_input ro provide current fan rotation value in RPM as reported - by the fan to the device. - -pwmX rw get or set PWM fan control value. This is an integer - value between 0(off) and 255(full speed). -=============== ======= ===================================================== diff --git a/Documentation/hwmon/npcm750-pwm-fan.rst b/Documentation/hwmon/npcm750-pwm-fan.rst new file mode 100644 index 000000000000..c67af08b6773 --- /dev/null +++ b/Documentation/hwmon/npcm750-pwm-fan.rst @@ -0,0 +1,26 @@ +Kernel driver npcm750-pwm-fan +============================= + +Supported chips: + + NUVOTON NPCM750/730/715/705 + +Authors: + + + +Description: +------------ +This driver implements support for NUVOTON NPCM7XX PWM and Fan Tacho +controller. The PWM controller supports up to 8 PWM outputs. The Fan tacho +controller supports up to 16 tachometer inputs. + +The driver provides the following sensor accesses in sysfs: + +=============== ======= ===================================================== +fanX_input ro provide current fan rotation value in RPM as reported + by the fan to the device. + +pwmX rw get or set PWM fan control value. This is an integer + value between 0(off) and 255(full speed). +=============== ======= ===================================================== diff --git a/Documentation/hwmon/nsa320 b/Documentation/hwmon/nsa320 deleted file mode 100644 index 4fe75fd2f937..000000000000 --- a/Documentation/hwmon/nsa320 +++ /dev/null @@ -1,64 +0,0 @@ -Kernel driver nsa320_hwmon -========================== - -Supported chips: - - * Holtek HT46R065 microcontroller with onboard firmware that configures - - it to act as a hardware monitor. - - Prefix: 'nsa320' - - Addresses scanned: none - - Datasheet: Not available, driver was reverse engineered based upon the - - Zyxel kernel source - - - -Author: - - Adam Baker - -Description ------------ - -This chip is known to be used in the Zyxel NSA320 and NSA325 NAS Units and -also in some variants of the NSA310 but the driver has only been tested -on the NSA320. In all of these devices it is connected to the same 3 GPIO -lines which are used to provide chip select, clock and data lines. The -interface behaves similarly to SPI but at much lower speeds than are normally -used for SPI. - -Following each chip select pulse the chip will generate a single 32 bit word -that contains 0x55 as a marker to indicate that data is being read correctly, -followed by an 8 bit fan speed in 100s of RPM and a 16 bit temperature in -tenths of a degree. - - -sysfs-Interface ---------------- - -============= ================= -temp1_input temperature input -fan1_input fan speed -============= ================= - -Notes ------ - -The access timings used in the driver are the same as used in the Zyxel -provided kernel. Testing has shown that if the delay between chip select and -the first clock pulse is reduced from 100 ms to just under 10ms then the chip -will not produce any output. If the duration of either phase of the clock -is reduced from 100 us to less than 15 us then data pulses are likely to be -read twice corrupting the output. The above analysis is based upon a sample -of one unit but suggests that the Zyxel provided delay values include a -reasonable tolerance. - -The driver incorporates a limit that it will not check for updated values -faster than once a second. This is because the hardware takes a relatively long -time to read the data from the device and when it does it reads both temp and -fan speed. As the most likely case for two accesses in quick succession is -to read both of these values avoiding a second read delay is desirable. diff --git a/Documentation/hwmon/nsa320.rst b/Documentation/hwmon/nsa320.rst new file mode 100644 index 000000000000..4fe75fd2f937 --- /dev/null +++ b/Documentation/hwmon/nsa320.rst @@ -0,0 +1,64 @@ +Kernel driver nsa320_hwmon +========================== + +Supported chips: + + * Holtek HT46R065 microcontroller with onboard firmware that configures + + it to act as a hardware monitor. + + Prefix: 'nsa320' + + Addresses scanned: none + + Datasheet: Not available, driver was reverse engineered based upon the + + Zyxel kernel source + + + +Author: + + Adam Baker + +Description +----------- + +This chip is known to be used in the Zyxel NSA320 and NSA325 NAS Units and +also in some variants of the NSA310 but the driver has only been tested +on the NSA320. In all of these devices it is connected to the same 3 GPIO +lines which are used to provide chip select, clock and data lines. The +interface behaves similarly to SPI but at much lower speeds than are normally +used for SPI. + +Following each chip select pulse the chip will generate a single 32 bit word +that contains 0x55 as a marker to indicate that data is being read correctly, +followed by an 8 bit fan speed in 100s of RPM and a 16 bit temperature in +tenths of a degree. + + +sysfs-Interface +--------------- + +============= ================= +temp1_input temperature input +fan1_input fan speed +============= ================= + +Notes +----- + +The access timings used in the driver are the same as used in the Zyxel +provided kernel. Testing has shown that if the delay between chip select and +the first clock pulse is reduced from 100 ms to just under 10ms then the chip +will not produce any output. If the duration of either phase of the clock +is reduced from 100 us to less than 15 us then data pulses are likely to be +read twice corrupting the output. The above analysis is based upon a sample +of one unit but suggests that the Zyxel provided delay values include a +reasonable tolerance. + +The driver incorporates a limit that it will not check for updated values +faster than once a second. This is because the hardware takes a relatively long +time to read the data from the device and when it does it reads both temp and +fan speed. As the most likely case for two accesses in quick succession is +to read both of these values avoiding a second read delay is desirable. diff --git a/Documentation/hwmon/ntc_thermistor b/Documentation/hwmon/ntc_thermistor deleted file mode 100644 index d0e7f91726b9..000000000000 --- a/Documentation/hwmon/ntc_thermistor +++ /dev/null @@ -1,111 +0,0 @@ -Kernel driver ntc_thermistor -============================ - -Supported thermistors from Murata: - -* Murata NTC Thermistors NCP15WB473, NCP18WB473, NCP21WB473, NCP03WB473, - NCP15WL333, NCP03WF104, NCP15XH103 - - Prefixes: 'ncp15wb473', 'ncp18wb473', 'ncp21wb473', 'ncp03wb473', - 'ncp15wl333', 'ncp03wf104', 'ncp15xh103' - - Datasheet: Publicly available at Murata - -Supported thermistors from EPCOS: - -* EPCOS NTC Thermistors B57330V2103 - - Prefixes: b57330v2103 - - Datasheet: Publicly available at EPCOS - -Other NTC thermistors can be supported simply by adding compensation -tables; e.g., NCP15WL333 support is added by the table ncpXXwl333. - -Authors: - - MyungJoo Ham - -Description ------------ - -The NTC (Negative Temperature Coefficient) thermistor is a simple thermistor -that requires users to provide the resistance and lookup the corresponding -compensation table to get the temperature input. - -The NTC driver provides lookup tables with a linear approximation function -and four circuit models with an option not to use any of the four models. - -Using the following convention:: - - $ resistor - [TH] the thermistor - -The four circuit models provided are: - -1. connect = NTC_CONNECTED_POSITIVE, pullup_ohm > 0:: - - [pullup_uV] - | | - [TH] $ (pullup_ohm) - | | - +----+-----------------------[read_uV] - | - $ (pulldown_ohm) - | - -+- (ground) - -2. connect = NTC_CONNECTED_POSITIVE, pullup_ohm = 0 (not-connected):: - - [pullup_uV] - | - [TH] - | - +----------------------------[read_uV] - | - $ (pulldown_ohm) - | - -+- (ground) - -3. connect = NTC_CONNECTED_GROUND, pulldown_ohm > 0:: - - [pullup_uV] - | - $ (pullup_ohm) - | - +----+-----------------------[read_uV] - | | - [TH] $ (pulldown_ohm) - | | - -+----+- (ground) - -4. connect = NTC_CONNECTED_GROUND, pulldown_ohm = 0 (not-connected):: - - [pullup_uV] - | - $ (pullup_ohm) - | - +----------------------------[read_uV] - | - [TH] - | - -+- (ground) - -When one of the four circuit models is used, read_uV, pullup_uV, pullup_ohm, -pulldown_ohm, and connect should be provided. When none of the four models -are suitable or the user can get the resistance directly, the user should -provide read_ohm and _not_ provide the others. - -Sysfs Interface ---------------- - -=============== == ============================================================= -name the mandatory global attribute, the thermistor name. -=============== == ============================================================= -temp1_type RO always 4 (thermistor) - -temp1_input RO measure the temperature and provide the measured value. - (reading this file initiates the reading procedure.) -=============== == ============================================================= - -Note that each NTC thermistor has only _one_ thermistor; thus, only temp1 exists. diff --git a/Documentation/hwmon/ntc_thermistor.rst b/Documentation/hwmon/ntc_thermistor.rst new file mode 100644 index 000000000000..d0e7f91726b9 --- /dev/null +++ b/Documentation/hwmon/ntc_thermistor.rst @@ -0,0 +1,111 @@ +Kernel driver ntc_thermistor +============================ + +Supported thermistors from Murata: + +* Murata NTC Thermistors NCP15WB473, NCP18WB473, NCP21WB473, NCP03WB473, + NCP15WL333, NCP03WF104, NCP15XH103 + + Prefixes: 'ncp15wb473', 'ncp18wb473', 'ncp21wb473', 'ncp03wb473', + 'ncp15wl333', 'ncp03wf104', 'ncp15xh103' + + Datasheet: Publicly available at Murata + +Supported thermistors from EPCOS: + +* EPCOS NTC Thermistors B57330V2103 + + Prefixes: b57330v2103 + + Datasheet: Publicly available at EPCOS + +Other NTC thermistors can be supported simply by adding compensation +tables; e.g., NCP15WL333 support is added by the table ncpXXwl333. + +Authors: + + MyungJoo Ham + +Description +----------- + +The NTC (Negative Temperature Coefficient) thermistor is a simple thermistor +that requires users to provide the resistance and lookup the corresponding +compensation table to get the temperature input. + +The NTC driver provides lookup tables with a linear approximation function +and four circuit models with an option not to use any of the four models. + +Using the following convention:: + + $ resistor + [TH] the thermistor + +The four circuit models provided are: + +1. connect = NTC_CONNECTED_POSITIVE, pullup_ohm > 0:: + + [pullup_uV] + | | + [TH] $ (pullup_ohm) + | | + +----+-----------------------[read_uV] + | + $ (pulldown_ohm) + | + -+- (ground) + +2. connect = NTC_CONNECTED_POSITIVE, pullup_ohm = 0 (not-connected):: + + [pullup_uV] + | + [TH] + | + +----------------------------[read_uV] + | + $ (pulldown_ohm) + | + -+- (ground) + +3. connect = NTC_CONNECTED_GROUND, pulldown_ohm > 0:: + + [pullup_uV] + | + $ (pullup_ohm) + | + +----+-----------------------[read_uV] + | | + [TH] $ (pulldown_ohm) + | | + -+----+- (ground) + +4. connect = NTC_CONNECTED_GROUND, pulldown_ohm = 0 (not-connected):: + + [pullup_uV] + | + $ (pullup_ohm) + | + +----------------------------[read_uV] + | + [TH] + | + -+- (ground) + +When one of the four circuit models is used, read_uV, pullup_uV, pullup_ohm, +pulldown_ohm, and connect should be provided. When none of the four models +are suitable or the user can get the resistance directly, the user should +provide read_ohm and _not_ provide the others. + +Sysfs Interface +--------------- + +=============== == ============================================================= +name the mandatory global attribute, the thermistor name. +=============== == ============================================================= +temp1_type RO always 4 (thermistor) + +temp1_input RO measure the temperature and provide the measured value. + (reading this file initiates the reading procedure.) +=============== == ============================================================= + +Note that each NTC thermistor has only _one_ thermistor; thus, only temp1 exists. diff --git a/Documentation/hwmon/occ b/Documentation/hwmon/occ deleted file mode 100644 index bf41c162d70e..000000000000 --- a/Documentation/hwmon/occ +++ /dev/null @@ -1,153 +0,0 @@ -Kernel driver occ-hwmon -======================= - -Supported chips: - - * POWER8 - * POWER9 - -Author: Eddie James - -Description ------------ - -This driver supports hardware monitoring for the On-Chip Controller (OCC) -embedded on POWER processors. The OCC is a device that collects and aggregates -sensor data from the processor and the system. The OCC can provide the raw -sensor data as well as perform thermal and power management on the system. - -The P8 version of this driver is a client driver of I2C. It may be probed -manually if an "ibm,p8-occ-hwmon" compatible device is found under the -appropriate I2C bus node in the device-tree. - -The P9 version of this driver is a client driver of the FSI-based OCC driver. -It will be probed automatically by the FSI-based OCC driver. - -Sysfs entries -------------- - -The following attributes are supported. All attributes are read-only unless -specified. - -The OCC sensor ID is an integer that represents the unique identifier of the -sensor with respect to the OCC. For example, a temperature sensor for the third -DIMM slot in the system may have a sensor ID of 7. This mapping is unavailable -to the device driver, which must therefore export the sensor ID as-is. - -Some entries are only present with certain OCC sensor versions or only on -certain OCCs in the system. The version number is not exported to the user -but can be inferred. - -temp[1-n]_label - OCC sensor ID. - -[with temperature sensor version 1] - - temp[1-n]_input - Measured temperature of the component in millidegrees - Celsius. - -[with temperature sensor version >= 2] - - temp[1-n]_type - The FRU (Field Replaceable Unit) type - (represented by an integer) for the component - that this sensor measures. - temp[1-n]_fault - Temperature sensor fault boolean; 1 to indicate - that a fault is present or 0 to indicate that - no fault is present. - - [with type == 3 (FRU type is VRM)] - - temp[1-n]_alarm - VRM temperature alarm boolean; 1 to indicate - alarm, 0 to indicate no alarm - - [else] - - temp[1-n]_input - Measured temperature of the component in - millidegrees Celsius. - -freq[1-n]_label - OCC sensor ID. -freq[1-n]_input - Measured frequency of the component in MHz. -power[1-n]_input - Latest measured power reading of the component in - microwatts. -power[1-n]_average - Average power of the component in microwatts. -power[1-n]_average_interval - The amount of time over which the power average - was taken in microseconds. - -[with power sensor version < 2] - - power[1-n]_label - OCC sensor ID. - -[with power sensor version >= 2] - - power[1-n]_label - OCC sensor ID + function ID + channel in the form - of a string, delimited by underscores, i.e. "0_15_1". - Both the function ID and channel are integers that - further identify the power sensor. - -[with power sensor version 0xa0] - - power[1-n]_label - OCC sensor ID + sensor type in the form of a string, - delimited by an underscore, i.e. "0_system". Sensor - type will be one of "system", "proc", "vdd" or "vdn". - For this sensor version, OCC sensor ID will be the same - for all power sensors. - -[present only on "master" OCC; represents the whole system power; only one of -this type of power sensor will be present] - - power[1-n]_label - "system" - power[1-n]_input - Latest system output power in microwatts. - power[1-n]_cap - Current system power cap in microwatts. - power[1-n]_cap_not_redundant - System power cap in microwatts when - there is not redundant power. - power[1-n]_cap_max - Maximum power cap that the OCC can enforce in - microwatts. - power[1-n]_cap_min Minimum power cap that the OCC can enforce in - microwatts. - power[1-n]_cap_user The power cap set by the user, in microwatts. - This attribute will return 0 if no user power - cap has been set. This attribute is read-write, - but writing any precision below watts will be - ignored, i.e. requesting a power cap of - 500900000 microwatts will result in a power cap - request of 500 watts. - - [with caps sensor version > 1] - - power[1-n]_cap_user_source - Indicates how the user power cap was - set. This is an integer that maps to - system or firmware components that can - set the user power cap. - -The following "extn" sensors are exported as a way for the OCC to provide data -that doesn't fit anywhere else. The meaning of these sensors is entirely -dependent on their data, and cannot be statically defined. - -extn[1-n]_label - ASCII ID or OCC sensor ID. -extn[1-n]_flags - This is one byte hexadecimal value. Bit 7 indicates the - type of the label attribute; 1 for sensor ID, 0 for - ASCII ID. Other bits are reserved. -extn[1-n]_input - 6 bytes of hexadecimal data, with a meaning defined by - the sensor ID. diff --git a/Documentation/hwmon/occ.rst b/Documentation/hwmon/occ.rst new file mode 100644 index 000000000000..bf41c162d70e --- /dev/null +++ b/Documentation/hwmon/occ.rst @@ -0,0 +1,153 @@ +Kernel driver occ-hwmon +======================= + +Supported chips: + + * POWER8 + * POWER9 + +Author: Eddie James + +Description +----------- + +This driver supports hardware monitoring for the On-Chip Controller (OCC) +embedded on POWER processors. The OCC is a device that collects and aggregates +sensor data from the processor and the system. The OCC can provide the raw +sensor data as well as perform thermal and power management on the system. + +The P8 version of this driver is a client driver of I2C. It may be probed +manually if an "ibm,p8-occ-hwmon" compatible device is found under the +appropriate I2C bus node in the device-tree. + +The P9 version of this driver is a client driver of the FSI-based OCC driver. +It will be probed automatically by the FSI-based OCC driver. + +Sysfs entries +------------- + +The following attributes are supported. All attributes are read-only unless +specified. + +The OCC sensor ID is an integer that represents the unique identifier of the +sensor with respect to the OCC. For example, a temperature sensor for the third +DIMM slot in the system may have a sensor ID of 7. This mapping is unavailable +to the device driver, which must therefore export the sensor ID as-is. + +Some entries are only present with certain OCC sensor versions or only on +certain OCCs in the system. The version number is not exported to the user +but can be inferred. + +temp[1-n]_label + OCC sensor ID. + +[with temperature sensor version 1] + + temp[1-n]_input + Measured temperature of the component in millidegrees + Celsius. + +[with temperature sensor version >= 2] + + temp[1-n]_type + The FRU (Field Replaceable Unit) type + (represented by an integer) for the component + that this sensor measures. + temp[1-n]_fault + Temperature sensor fault boolean; 1 to indicate + that a fault is present or 0 to indicate that + no fault is present. + + [with type == 3 (FRU type is VRM)] + + temp[1-n]_alarm + VRM temperature alarm boolean; 1 to indicate + alarm, 0 to indicate no alarm + + [else] + + temp[1-n]_input + Measured temperature of the component in + millidegrees Celsius. + +freq[1-n]_label + OCC sensor ID. +freq[1-n]_input + Measured frequency of the component in MHz. +power[1-n]_input + Latest measured power reading of the component in + microwatts. +power[1-n]_average + Average power of the component in microwatts. +power[1-n]_average_interval + The amount of time over which the power average + was taken in microseconds. + +[with power sensor version < 2] + + power[1-n]_label + OCC sensor ID. + +[with power sensor version >= 2] + + power[1-n]_label + OCC sensor ID + function ID + channel in the form + of a string, delimited by underscores, i.e. "0_15_1". + Both the function ID and channel are integers that + further identify the power sensor. + +[with power sensor version 0xa0] + + power[1-n]_label + OCC sensor ID + sensor type in the form of a string, + delimited by an underscore, i.e. "0_system". Sensor + type will be one of "system", "proc", "vdd" or "vdn". + For this sensor version, OCC sensor ID will be the same + for all power sensors. + +[present only on "master" OCC; represents the whole system power; only one of +this type of power sensor will be present] + + power[1-n]_label + "system" + power[1-n]_input + Latest system output power in microwatts. + power[1-n]_cap + Current system power cap in microwatts. + power[1-n]_cap_not_redundant + System power cap in microwatts when + there is not redundant power. + power[1-n]_cap_max + Maximum power cap that the OCC can enforce in + microwatts. + power[1-n]_cap_min Minimum power cap that the OCC can enforce in + microwatts. + power[1-n]_cap_user The power cap set by the user, in microwatts. + This attribute will return 0 if no user power + cap has been set. This attribute is read-write, + but writing any precision below watts will be + ignored, i.e. requesting a power cap of + 500900000 microwatts will result in a power cap + request of 500 watts. + + [with caps sensor version > 1] + + power[1-n]_cap_user_source + Indicates how the user power cap was + set. This is an integer that maps to + system or firmware components that can + set the user power cap. + +The following "extn" sensors are exported as a way for the OCC to provide data +that doesn't fit anywhere else. The meaning of these sensors is entirely +dependent on their data, and cannot be statically defined. + +extn[1-n]_label + ASCII ID or OCC sensor ID. +extn[1-n]_flags + This is one byte hexadecimal value. Bit 7 indicates the + type of the label attribute; 1 for sensor ID, 0 for + ASCII ID. Other bits are reserved. +extn[1-n]_input + 6 bytes of hexadecimal data, with a meaning defined by + the sensor ID. diff --git a/Documentation/hwmon/pc87360 b/Documentation/hwmon/pc87360 deleted file mode 100644 index 4bad07bce54b..000000000000 --- a/Documentation/hwmon/pc87360 +++ /dev/null @@ -1,198 +0,0 @@ -Kernel driver pc87360 -===================== - -Supported chips: - - * National Semiconductor PC87360, PC87363, PC87364, PC87365 and PC87366 - - Prefixes: 'pc87360', 'pc87363', 'pc87364', 'pc87365', 'pc87366' - - Addresses scanned: none, address read from Super I/O config space - - Datasheets: No longer available - -Authors: Jean Delvare - -Thanks to Sandeep Mehta, Tonko de Rooy and Daniel Ceregatti for testing. - -Thanks to Rudolf Marek for helping me investigate conversion issues. - - -Module Parameters ------------------ - -* init int - Chip initialization level: - - - 0: None - - **1**: Forcibly enable internal voltage and temperature channels, - except in9 - - 2: Forcibly enable all voltage and temperature channels, except in9 - - 3: Forcibly enable all voltage and temperature channels, including in9 - -Note that this parameter has no effect for the PC87360, PC87363 and PC87364 -chips. - -Also note that for the PC87366, initialization levels 2 and 3 don't enable -all temperature channels, because some of them share pins with each other, -so they can't be used at the same time. - - -Description ------------ - -The National Semiconductor PC87360 Super I/O chip contains monitoring and -PWM control circuitry for two fans. The PC87363 chip is similar, and the -PC87364 chip has monitoring and PWM control for a third fan. - -The National Semiconductor PC87365 and PC87366 Super I/O chips are complete -hardware monitoring chipsets, not only controlling and monitoring three fans, -but also monitoring eleven voltage inputs and two (PC87365) or up to four -(PC87366) temperatures. - - =========== ======= ======= ======= ======= ===== - Chip #vin #fan #pwm #temp devid - =========== ======= ======= ======= ======= ===== - PC87360 - 2 2 - 0xE1 - PC87363 - 2 2 - 0xE8 - PC87364 - 3 3 - 0xE4 - PC87365 11 3 3 2 0xE5 - PC87366 11 3 3 3-4 0xE9 - =========== ======= ======= ======= ======= ===== - -The driver assumes that no more than one chip is present, and one of the -standard Super I/O addresses is used (0x2E/0x2F or 0x4E/0x4F) - -Fan Monitoring --------------- - -Fan rotation speeds are reported in RPM (revolutions per minute). An alarm -is triggered if the rotation speed has dropped below a programmable limit. -A different alarm is triggered if the fan speed is too low to be measured. - -Fan readings are affected by a programmable clock divider, giving the -readings more range or accuracy. Usually, users have to learn how it works, -but this driver implements dynamic clock divider selection, so you don't -have to care no more. - -For reference, here are a few values about clock dividers: - - =========== =============== =============== =========== - slowest accuracy highest - measurable around 3000 accurate - divider speed (RPM) RPM (RPM) speed (RPM) - =========== =============== =============== =========== - 1 1882 18 6928 - 2 941 37 4898 - 4 470 74 3464 - 8 235 150 2449 - =========== =============== =============== =========== - -For the curious, here is how the values above were computed: - - * slowest measurable speed: clock/(255*divider) - * accuracy around 3000 RPM: 3000^2/clock - * highest accurate speed: sqrt(clock*100) - -The clock speed for the PC87360 family is 480 kHz. I arbitrarily chose 100 -RPM as the lowest acceptable accuracy. - -As mentioned above, you don't have to care about this no more. - -Note that not all RPM values can be represented, even when the best clock -divider is selected. This is not only true for the measured speeds, but -also for the programmable low limits, so don't be surprised if you try to -set, say, fan1_min to 2900 and it finally reads 2909. - - -Fan Control ------------ - -PWM (pulse width modulation) values range from 0 to 255, with 0 meaning -that the fan is stopped, and 255 meaning that the fan goes at full speed. - -Be extremely careful when changing PWM values. Low PWM values, even -non-zero, can stop the fan, which may cause irreversible damage to your -hardware if temperature increases too much. When changing PWM values, go -step by step and keep an eye on temperatures. - -One user reported problems with PWM. Changing PWM values would break fan -speed readings. No explanation nor fix could be found. - - -Temperature Monitoring ----------------------- - -Temperatures are reported in degrees Celsius. Each temperature measured has -associated low, high and overtemperature limits, each of which triggers an -alarm when crossed. - -The first two temperature channels are external. The third one (PC87366 -only) is internal. - -The PC87366 has three additional temperature channels, based on -thermistors (as opposed to thermal diodes for the first three temperature -channels). For technical reasons, these channels are held by the VLM -(voltage level monitor) logical device, not the TMS (temperature -measurement) one. As a consequence, these temperatures are exported as -voltages, and converted into temperatures in user-space. - -Note that these three additional channels share their pins with the -external thermal diode channels, so you (physically) can't use them all at -the same time. Although it should be possible to mix the two sensor types, -the documents from National Semiconductor suggest that motherboard -manufacturers should choose one type and stick to it. So you will more -likely have either channels 1 to 3 (thermal diodes) or 3 to 6 (internal -thermal diode, and thermistors). - - -Voltage Monitoring ------------------- - -Voltages are reported relatively to a reference voltage, either internal or -external. Some of them (in7:Vsb, in8:Vdd and in10:AVdd) are divided by two -internally, you will have to compensate in sensors.conf. Others (in0 to in6) -are likely to be divided externally. The meaning of each of these inputs as -well as the values of the resistors used for division is left to the -motherboard manufacturers, so you will have to document yourself and edit -sensors.conf accordingly. National Semiconductor has a document with -recommended resistor values for some voltages, but this still leaves much -room for per motherboard specificities, unfortunately. Even worse, -motherboard manufacturers don't seem to care about National Semiconductor's -recommendations. - -Each voltage measured has associated low and high limits, each of which -triggers an alarm when crossed. - -When available, VID inputs are used to provide the nominal CPU Core voltage. -The driver will default to VRM 9.0, but this can be changed from user-space. -The chipsets can handle two sets of VID inputs (on dual-CPU systems), but -the driver will only export one for now. This may change later if there is -a need. - - -General Remarks ---------------- - -If an alarm triggers, it will remain triggered until the hardware register -is read at least once. This means that the cause for the alarm may already -have disappeared! Note that all hardware registers are read whenever any -data is read (unless it is less than 2 seconds since the last update, in -which case cached values are returned instead). As a consequence, when -a once-only alarm triggers, it may take 2 seconds for it to show, and 2 -more seconds for it to disappear. - -Monitoring of in9 isn't enabled at lower init levels (<3) because that -channel measures the battery voltage (Vbat). It is a known fact that -repeatedly sampling the battery voltage reduces its lifetime. National -Semiconductor smartly designed their chipset so that in9 is sampled only -once every 1024 sampling cycles (that is every 34 minutes at the default -sampling rate), so the effect is attenuated, but still present. - - -Limitations ------------ - -The datasheets suggests that some values (fan mins, fan dividers) -shouldn't be changed once the monitoring has started, but we ignore that -recommendation. We'll reconsider if it actually causes trouble. diff --git a/Documentation/hwmon/pc87360.rst b/Documentation/hwmon/pc87360.rst new file mode 100644 index 000000000000..4bad07bce54b --- /dev/null +++ b/Documentation/hwmon/pc87360.rst @@ -0,0 +1,198 @@ +Kernel driver pc87360 +===================== + +Supported chips: + + * National Semiconductor PC87360, PC87363, PC87364, PC87365 and PC87366 + + Prefixes: 'pc87360', 'pc87363', 'pc87364', 'pc87365', 'pc87366' + + Addresses scanned: none, address read from Super I/O config space + + Datasheets: No longer available + +Authors: Jean Delvare + +Thanks to Sandeep Mehta, Tonko de Rooy and Daniel Ceregatti for testing. + +Thanks to Rudolf Marek for helping me investigate conversion issues. + + +Module Parameters +----------------- + +* init int + Chip initialization level: + + - 0: None + - **1**: Forcibly enable internal voltage and temperature channels, + except in9 + - 2: Forcibly enable all voltage and temperature channels, except in9 + - 3: Forcibly enable all voltage and temperature channels, including in9 + +Note that this parameter has no effect for the PC87360, PC87363 and PC87364 +chips. + +Also note that for the PC87366, initialization levels 2 and 3 don't enable +all temperature channels, because some of them share pins with each other, +so they can't be used at the same time. + + +Description +----------- + +The National Semiconductor PC87360 Super I/O chip contains monitoring and +PWM control circuitry for two fans. The PC87363 chip is similar, and the +PC87364 chip has monitoring and PWM control for a third fan. + +The National Semiconductor PC87365 and PC87366 Super I/O chips are complete +hardware monitoring chipsets, not only controlling and monitoring three fans, +but also monitoring eleven voltage inputs and two (PC87365) or up to four +(PC87366) temperatures. + + =========== ======= ======= ======= ======= ===== + Chip #vin #fan #pwm #temp devid + =========== ======= ======= ======= ======= ===== + PC87360 - 2 2 - 0xE1 + PC87363 - 2 2 - 0xE8 + PC87364 - 3 3 - 0xE4 + PC87365 11 3 3 2 0xE5 + PC87366 11 3 3 3-4 0xE9 + =========== ======= ======= ======= ======= ===== + +The driver assumes that no more than one chip is present, and one of the +standard Super I/O addresses is used (0x2E/0x2F or 0x4E/0x4F) + +Fan Monitoring +-------------- + +Fan rotation speeds are reported in RPM (revolutions per minute). An alarm +is triggered if the rotation speed has dropped below a programmable limit. +A different alarm is triggered if the fan speed is too low to be measured. + +Fan readings are affected by a programmable clock divider, giving the +readings more range or accuracy. Usually, users have to learn how it works, +but this driver implements dynamic clock divider selection, so you don't +have to care no more. + +For reference, here are a few values about clock dividers: + + =========== =============== =============== =========== + slowest accuracy highest + measurable around 3000 accurate + divider speed (RPM) RPM (RPM) speed (RPM) + =========== =============== =============== =========== + 1 1882 18 6928 + 2 941 37 4898 + 4 470 74 3464 + 8 235 150 2449 + =========== =============== =============== =========== + +For the curious, here is how the values above were computed: + + * slowest measurable speed: clock/(255*divider) + * accuracy around 3000 RPM: 3000^2/clock + * highest accurate speed: sqrt(clock*100) + +The clock speed for the PC87360 family is 480 kHz. I arbitrarily chose 100 +RPM as the lowest acceptable accuracy. + +As mentioned above, you don't have to care about this no more. + +Note that not all RPM values can be represented, even when the best clock +divider is selected. This is not only true for the measured speeds, but +also for the programmable low limits, so don't be surprised if you try to +set, say, fan1_min to 2900 and it finally reads 2909. + + +Fan Control +----------- + +PWM (pulse width modulation) values range from 0 to 255, with 0 meaning +that the fan is stopped, and 255 meaning that the fan goes at full speed. + +Be extremely careful when changing PWM values. Low PWM values, even +non-zero, can stop the fan, which may cause irreversible damage to your +hardware if temperature increases too much. When changing PWM values, go +step by step and keep an eye on temperatures. + +One user reported problems with PWM. Changing PWM values would break fan +speed readings. No explanation nor fix could be found. + + +Temperature Monitoring +---------------------- + +Temperatures are reported in degrees Celsius. Each temperature measured has +associated low, high and overtemperature limits, each of which triggers an +alarm when crossed. + +The first two temperature channels are external. The third one (PC87366 +only) is internal. + +The PC87366 has three additional temperature channels, based on +thermistors (as opposed to thermal diodes for the first three temperature +channels). For technical reasons, these channels are held by the VLM +(voltage level monitor) logical device, not the TMS (temperature +measurement) one. As a consequence, these temperatures are exported as +voltages, and converted into temperatures in user-space. + +Note that these three additional channels share their pins with the +external thermal diode channels, so you (physically) can't use them all at +the same time. Although it should be possible to mix the two sensor types, +the documents from National Semiconductor suggest that motherboard +manufacturers should choose one type and stick to it. So you will more +likely have either channels 1 to 3 (thermal diodes) or 3 to 6 (internal +thermal diode, and thermistors). + + +Voltage Monitoring +------------------ + +Voltages are reported relatively to a reference voltage, either internal or +external. Some of them (in7:Vsb, in8:Vdd and in10:AVdd) are divided by two +internally, you will have to compensate in sensors.conf. Others (in0 to in6) +are likely to be divided externally. The meaning of each of these inputs as +well as the values of the resistors used for division is left to the +motherboard manufacturers, so you will have to document yourself and edit +sensors.conf accordingly. National Semiconductor has a document with +recommended resistor values for some voltages, but this still leaves much +room for per motherboard specificities, unfortunately. Even worse, +motherboard manufacturers don't seem to care about National Semiconductor's +recommendations. + +Each voltage measured has associated low and high limits, each of which +triggers an alarm when crossed. + +When available, VID inputs are used to provide the nominal CPU Core voltage. +The driver will default to VRM 9.0, but this can be changed from user-space. +The chipsets can handle two sets of VID inputs (on dual-CPU systems), but +the driver will only export one for now. This may change later if there is +a need. + + +General Remarks +--------------- + +If an alarm triggers, it will remain triggered until the hardware register +is read at least once. This means that the cause for the alarm may already +have disappeared! Note that all hardware registers are read whenever any +data is read (unless it is less than 2 seconds since the last update, in +which case cached values are returned instead). As a consequence, when +a once-only alarm triggers, it may take 2 seconds for it to show, and 2 +more seconds for it to disappear. + +Monitoring of in9 isn't enabled at lower init levels (<3) because that +channel measures the battery voltage (Vbat). It is a known fact that +repeatedly sampling the battery voltage reduces its lifetime. National +Semiconductor smartly designed their chipset so that in9 is sampled only +once every 1024 sampling cycles (that is every 34 minutes at the default +sampling rate), so the effect is attenuated, but still present. + + +Limitations +----------- + +The datasheets suggests that some values (fan mins, fan dividers) +shouldn't be changed once the monitoring has started, but we ignore that +recommendation. We'll reconsider if it actually causes trouble. diff --git a/Documentation/hwmon/pc87427 b/Documentation/hwmon/pc87427 deleted file mode 100644 index 22d8f62d851f..000000000000 --- a/Documentation/hwmon/pc87427 +++ /dev/null @@ -1,63 +0,0 @@ -Kernel driver pc87427 -===================== - -Supported chips: - - * National Semiconductor PC87427 - - Prefix: 'pc87427' - - Addresses scanned: none, address read from Super I/O config space - - Datasheet: No longer available - -Author: Jean Delvare - -Thanks to Amir Habibi at Candelis for setting up a test system, and to -Michael Kress for testing several iterations of this driver. - - -Description ------------ - -The National Semiconductor Super I/O chip includes complete hardware -monitoring capabilities. It can monitor up to 18 voltages, 8 fans and -6 temperature sensors. Only the fans and temperatures are supported at -the moment, voltages aren't. - -This chip also has fan controlling features (up to 4 PWM outputs), -which are partly supported by this driver. - -The driver assumes that no more than one chip is present, which seems -reasonable. - - -Fan Monitoring --------------- - -Fan rotation speeds are reported as 14-bit values from a gated clock -signal. Speeds down to 83 RPM can be measured. - -An alarm is triggered if the rotation speed drops below a programmable -limit. Another alarm is triggered if the speed is too low to be measured -(including stalled or missing fan). - - -Fan Speed Control ------------------ - -Fan speed can be controlled by PWM outputs. There are 4 possible modes: -always off, always on, manual and automatic. The latter isn't supported -by the driver: you can only return to that mode if it was the original -setting, and the configuration interface is missing. - - -Temperature Monitoring ----------------------- - -The PC87427 relies on external sensors (following the SensorPath -standard), so the resolution and range depend on the type of sensor -connected. The integer part can be 8-bit or 9-bit, and can be signed or -not. I couldn't find a way to figure out the external sensor data -temperature format, so user-space adjustment (typically by a factor 2) -may be required. diff --git a/Documentation/hwmon/pc87427.rst b/Documentation/hwmon/pc87427.rst new file mode 100644 index 000000000000..22d8f62d851f --- /dev/null +++ b/Documentation/hwmon/pc87427.rst @@ -0,0 +1,63 @@ +Kernel driver pc87427 +===================== + +Supported chips: + + * National Semiconductor PC87427 + + Prefix: 'pc87427' + + Addresses scanned: none, address read from Super I/O config space + + Datasheet: No longer available + +Author: Jean Delvare + +Thanks to Amir Habibi at Candelis for setting up a test system, and to +Michael Kress for testing several iterations of this driver. + + +Description +----------- + +The National Semiconductor Super I/O chip includes complete hardware +monitoring capabilities. It can monitor up to 18 voltages, 8 fans and +6 temperature sensors. Only the fans and temperatures are supported at +the moment, voltages aren't. + +This chip also has fan controlling features (up to 4 PWM outputs), +which are partly supported by this driver. + +The driver assumes that no more than one chip is present, which seems +reasonable. + + +Fan Monitoring +-------------- + +Fan rotation speeds are reported as 14-bit values from a gated clock +signal. Speeds down to 83 RPM can be measured. + +An alarm is triggered if the rotation speed drops below a programmable +limit. Another alarm is triggered if the speed is too low to be measured +(including stalled or missing fan). + + +Fan Speed Control +----------------- + +Fan speed can be controlled by PWM outputs. There are 4 possible modes: +always off, always on, manual and automatic. The latter isn't supported +by the driver: you can only return to that mode if it was the original +setting, and the configuration interface is missing. + + +Temperature Monitoring +---------------------- + +The PC87427 relies on external sensors (following the SensorPath +standard), so the resolution and range depend on the type of sensor +connected. The integer part can be 8-bit or 9-bit, and can be signed or +not. I couldn't find a way to figure out the external sensor data +temperature format, so user-space adjustment (typically by a factor 2) +may be required. diff --git a/Documentation/hwmon/pcf8591 b/Documentation/hwmon/pcf8591 deleted file mode 100644 index e98bd542a441..000000000000 --- a/Documentation/hwmon/pcf8591 +++ /dev/null @@ -1,98 +0,0 @@ -Kernel driver pcf8591 -===================== - -Supported chips: - - * Philips/NXP PCF8591 - - Prefix: 'pcf8591' - - Addresses scanned: none - - Datasheet: Publicly available at the NXP website - - http://www.nxp.com/pip/PCF8591_6.html - -Authors: - - Aurelien Jarno - - valuable contributions by Jan M. Sendler , - - Jean Delvare - - -Description ------------ - -The PCF8591 is an 8-bit A/D and D/A converter (4 analog inputs and one -analog output) for the I2C bus produced by Philips Semiconductors (now NXP). -It is designed to provide a byte I2C interface to up to 4 separate devices. - -The PCF8591 has 4 analog inputs programmable as single-ended or -differential inputs: - -- mode 0 : four single ended inputs - Pins AIN0 to AIN3 are single ended inputs for channels 0 to 3 - -- mode 1 : three differential inputs - Pins AIN3 is the common negative differential input - Pins AIN0 to AIN2 are positive differential inputs for channels 0 to 2 - -- mode 2 : single ended and differential mixed - Pins AIN0 and AIN1 are single ended inputs for channels 0 and 1 - Pins AIN2 is the positive differential input for channel 3 - Pins AIN3 is the negative differential input for channel 3 - -- mode 3 : two differential inputs - Pins AIN0 is the positive differential input for channel 0 - Pins AIN1 is the negative differential input for channel 0 - Pins AIN2 is the positive differential input for channel 1 - Pins AIN3 is the negative differential input for channel 1 - -See the datasheet for details. - -Module parameters ------------------ - -* input_mode int - - Analog input mode: - - - 0 = four single ended inputs - - 1 = three differential inputs - - 2 = single ended and differential mixed - - 3 = two differential inputs - - -Accessing PCF8591 via /sys interface -------------------------------------- - -The PCF8591 is plainly impossible to detect! Thus the driver won't even -try. You have to explicitly instantiate the device at the relevant -address (in the interval [0x48..0x4f]) either through platform data, or -using the sysfs interface. See Documentation/i2c/instantiating-devices -for details. - -Directories are being created for each instantiated PCF8591: - -/sys/bus/i2c/devices/<0>-<1>/ - where <0> is the bus the chip is connected to (e. g. i2c-0) - and <1> the chip address ([48..4f]) - -Inside these directories, there are such files: - - in0_input, in1_input, in2_input, in3_input, out0_enable, out0_output, name - -Name contains chip name. - -The in0_input, in1_input, in2_input and in3_input files are RO. Reading gives -the value of the corresponding channel. Depending on the current analog inputs -configuration, files in2_input and in3_input may not exist. Values range -from 0 to 255 for single ended inputs and -128 to +127 for differential inputs -(8-bit ADC). - -The out0_enable file is RW. Reading gives "1" for analog output enabled and -"0" for analog output disabled. Writing accepts "0" and "1" accordingly. - -The out0_output file is RW. Writing a number between 0 and 255 (8-bit DAC), send -the value to the digital-to-analog converter. Note that a voltage will -only appears on AOUT pin if aout0_enable equals 1. Reading returns the last -value written. diff --git a/Documentation/hwmon/pcf8591.rst b/Documentation/hwmon/pcf8591.rst new file mode 100644 index 000000000000..e98bd542a441 --- /dev/null +++ b/Documentation/hwmon/pcf8591.rst @@ -0,0 +1,98 @@ +Kernel driver pcf8591 +===================== + +Supported chips: + + * Philips/NXP PCF8591 + + Prefix: 'pcf8591' + + Addresses scanned: none + + Datasheet: Publicly available at the NXP website + + http://www.nxp.com/pip/PCF8591_6.html + +Authors: + - Aurelien Jarno + - valuable contributions by Jan M. Sendler , + - Jean Delvare + + +Description +----------- + +The PCF8591 is an 8-bit A/D and D/A converter (4 analog inputs and one +analog output) for the I2C bus produced by Philips Semiconductors (now NXP). +It is designed to provide a byte I2C interface to up to 4 separate devices. + +The PCF8591 has 4 analog inputs programmable as single-ended or +differential inputs: + +- mode 0 : four single ended inputs + Pins AIN0 to AIN3 are single ended inputs for channels 0 to 3 + +- mode 1 : three differential inputs + Pins AIN3 is the common negative differential input + Pins AIN0 to AIN2 are positive differential inputs for channels 0 to 2 + +- mode 2 : single ended and differential mixed + Pins AIN0 and AIN1 are single ended inputs for channels 0 and 1 + Pins AIN2 is the positive differential input for channel 3 + Pins AIN3 is the negative differential input for channel 3 + +- mode 3 : two differential inputs + Pins AIN0 is the positive differential input for channel 0 + Pins AIN1 is the negative differential input for channel 0 + Pins AIN2 is the positive differential input for channel 1 + Pins AIN3 is the negative differential input for channel 1 + +See the datasheet for details. + +Module parameters +----------------- + +* input_mode int + + Analog input mode: + + - 0 = four single ended inputs + - 1 = three differential inputs + - 2 = single ended and differential mixed + - 3 = two differential inputs + + +Accessing PCF8591 via /sys interface +------------------------------------- + +The PCF8591 is plainly impossible to detect! Thus the driver won't even +try. You have to explicitly instantiate the device at the relevant +address (in the interval [0x48..0x4f]) either through platform data, or +using the sysfs interface. See Documentation/i2c/instantiating-devices +for details. + +Directories are being created for each instantiated PCF8591: + +/sys/bus/i2c/devices/<0>-<1>/ + where <0> is the bus the chip is connected to (e. g. i2c-0) + and <1> the chip address ([48..4f]) + +Inside these directories, there are such files: + + in0_input, in1_input, in2_input, in3_input, out0_enable, out0_output, name + +Name contains chip name. + +The in0_input, in1_input, in2_input and in3_input files are RO. Reading gives +the value of the corresponding channel. Depending on the current analog inputs +configuration, files in2_input and in3_input may not exist. Values range +from 0 to 255 for single ended inputs and -128 to +127 for differential inputs +(8-bit ADC). + +The out0_enable file is RW. Reading gives "1" for analog output enabled and +"0" for analog output disabled. Writing accepts "0" and "1" accordingly. + +The out0_output file is RW. Writing a number between 0 and 255 (8-bit DAC), send +the value to the digital-to-analog converter. Note that a voltage will +only appears on AOUT pin if aout0_enable equals 1. Reading returns the last +value written. diff --git a/Documentation/hwmon/pmbus b/Documentation/hwmon/pmbus deleted file mode 100644 index abfb9dd4857d..000000000000 --- a/Documentation/hwmon/pmbus +++ /dev/null @@ -1,254 +0,0 @@ -Kernel driver pmbus -=================== - -Supported chips: - - * Ericsson BMR453, BMR454 - - Prefixes: 'bmr453', 'bmr454' - - Addresses scanned: - - - Datasheet: - - http://archive.ericsson.net/service/internet/picov/get?DocNo=28701-EN/LZT146395 - - * ON Semiconductor ADP4000, NCP4200, NCP4208 - - Prefixes: 'adp4000', 'ncp4200', 'ncp4208' - - Addresses scanned: - - - Datasheets: - - http://www.onsemi.com/pub_link/Collateral/ADP4000-D.PDF - - http://www.onsemi.com/pub_link/Collateral/NCP4200-D.PDF - - http://www.onsemi.com/pub_link/Collateral/JUNE%202009-%20REV.%200.PDF - - * Lineage Power - - Prefixes: 'mdt040', 'pdt003', 'pdt006', 'pdt012', 'udt020' - - Addresses scanned: - - - Datasheets: - - http://www.lineagepower.com/oem/pdf/PDT003A0X.pdf - - http://www.lineagepower.com/oem/pdf/PDT006A0X.pdf - - http://www.lineagepower.com/oem/pdf/PDT012A0X.pdf - - http://www.lineagepower.com/oem/pdf/UDT020A0X.pdf - - http://www.lineagepower.com/oem/pdf/MDT040A0X.pdf - - * Texas Instruments TPS40400, TPS544B20, TPS544B25, TPS544C20, TPS544C25 - - Prefixes: 'tps40400', 'tps544b20', 'tps544b25', 'tps544c20', 'tps544c25' - - Addresses scanned: - - - Datasheets: - - http://www.ti.com/lit/gpn/tps40400 - - http://www.ti.com/lit/gpn/tps544b20 - - http://www.ti.com/lit/gpn/tps544b25 - - http://www.ti.com/lit/gpn/tps544c20 - - http://www.ti.com/lit/gpn/tps544c25 - - * Generic PMBus devices - - Prefix: 'pmbus' - - Addresses scanned: - - - Datasheet: n.a. - - -Author: Guenter Roeck - - -Description ------------ - -This driver supports hardware monitoring for various PMBus compliant devices. -It supports voltage, current, power, and temperature sensors as supported -by the device. - -Each monitored channel has its own high and low limits, plus a critical -limit. - -Fan support will be added in a later version of this driver. - - -Usage Notes ------------ - -This driver does not probe for PMBus devices, since there is no register -which can be safely used to identify the chip (The MFG_ID register is not -supported by all chips), and since there is no well defined address range for -PMBus devices. You will have to instantiate the devices explicitly. - -Example: the following will load the driver for an LTC2978 at address 0x60 -on I2C bus #1:: - - $ modprobe pmbus - $ echo ltc2978 0x60 > /sys/bus/i2c/devices/i2c-1/new_device - - -Platform data support ---------------------- - -Support for additional PMBus chips can be added by defining chip parameters in -a new chip specific driver file. For example, (untested) code to add support for -Emerson DS1200 power modules might look as follows:: - - static struct pmbus_driver_info ds1200_info = { - .pages = 1, - /* Note: All other sensors are in linear mode */ - .direct[PSC_VOLTAGE_OUT] = true, - .direct[PSC_TEMPERATURE] = true, - .direct[PSC_CURRENT_OUT] = true, - .m[PSC_VOLTAGE_IN] = 1, - .b[PSC_VOLTAGE_IN] = 0, - .R[PSC_VOLTAGE_IN] = 3, - .m[PSC_VOLTAGE_OUT] = 1, - .b[PSC_VOLTAGE_OUT] = 0, - .R[PSC_VOLTAGE_OUT] = 3, - .m[PSC_TEMPERATURE] = 1, - .b[PSC_TEMPERATURE] = 0, - .R[PSC_TEMPERATURE] = 3, - .func[0] = PMBUS_HAVE_VIN | PMBUS_HAVE_IIN | PMBUS_HAVE_STATUS_INPUT - | PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT - | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT - | PMBUS_HAVE_PIN | PMBUS_HAVE_POUT - | PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP - | PMBUS_HAVE_FAN12 | PMBUS_HAVE_STATUS_FAN12, - }; - - static int ds1200_probe(struct i2c_client *client, - const struct i2c_device_id *id) - { - return pmbus_do_probe(client, id, &ds1200_info); - } - - static int ds1200_remove(struct i2c_client *client) - { - return pmbus_do_remove(client); - } - - static const struct i2c_device_id ds1200_id[] = { - {"ds1200", 0}, - {} - }; - - MODULE_DEVICE_TABLE(i2c, ds1200_id); - - /* This is the driver that will be inserted */ - static struct i2c_driver ds1200_driver = { - .driver = { - .name = "ds1200", - }, - .probe = ds1200_probe, - .remove = ds1200_remove, - .id_table = ds1200_id, - }; - - static int __init ds1200_init(void) - { - return i2c_add_driver(&ds1200_driver); - } - - static void __exit ds1200_exit(void) - { - i2c_del_driver(&ds1200_driver); - } - - -Sysfs entries -------------- - -When probing the chip, the driver identifies which PMBus registers are -supported, and determines available sensors from this information. -Attribute files only exist if respective sensors are supported by the chip. -Labels are provided to inform the user about the sensor associated with -a given sysfs entry. - -The following attributes are supported. Limits are read-write; all other -attributes are read-only. - -======================= ======================================================== -inX_input Measured voltage. From READ_VIN or READ_VOUT register. -inX_min Minimum Voltage. - From VIN_UV_WARN_LIMIT or VOUT_UV_WARN_LIMIT register. -inX_max Maximum voltage. - From VIN_OV_WARN_LIMIT or VOUT_OV_WARN_LIMIT register. -inX_lcrit Critical minimum Voltage. - From VIN_UV_FAULT_LIMIT or VOUT_UV_FAULT_LIMIT register. -inX_crit Critical maximum voltage. - From VIN_OV_FAULT_LIMIT or VOUT_OV_FAULT_LIMIT register. -inX_min_alarm Voltage low alarm. From VOLTAGE_UV_WARNING status. -inX_max_alarm Voltage high alarm. From VOLTAGE_OV_WARNING status. -inX_lcrit_alarm Voltage critical low alarm. - From VOLTAGE_UV_FAULT status. -inX_crit_alarm Voltage critical high alarm. - From VOLTAGE_OV_FAULT status. -inX_label "vin", "vcap", or "voutY" - -currX_input Measured current. From READ_IIN or READ_IOUT register. -currX_max Maximum current. - From IIN_OC_WARN_LIMIT or IOUT_OC_WARN_LIMIT register. -currX_lcrit Critical minimum output current. - From IOUT_UC_FAULT_LIMIT register. -currX_crit Critical maximum current. - From IIN_OC_FAULT_LIMIT or IOUT_OC_FAULT_LIMIT register. -currX_alarm Current high alarm. - From IIN_OC_WARNING or IOUT_OC_WARNING status. -currX_max_alarm Current high alarm. - From IIN_OC_WARN_LIMIT or IOUT_OC_WARN_LIMIT status. -currX_lcrit_alarm Output current critical low alarm. - From IOUT_UC_FAULT status. -currX_crit_alarm Current critical high alarm. - From IIN_OC_FAULT or IOUT_OC_FAULT status. -currX_label "iin" or "ioutY" - -powerX_input Measured power. From READ_PIN or READ_POUT register. -powerX_cap Output power cap. From POUT_MAX register. -powerX_max Power limit. From PIN_OP_WARN_LIMIT or - POUT_OP_WARN_LIMIT register. -powerX_crit Critical output power limit. - From POUT_OP_FAULT_LIMIT register. -powerX_alarm Power high alarm. - From PIN_OP_WARNING or POUT_OP_WARNING status. -powerX_crit_alarm Output power critical high alarm. - From POUT_OP_FAULT status. -powerX_label "pin" or "poutY" - -tempX_input Measured temperature. - From READ_TEMPERATURE_X register. -tempX_min Mimimum temperature. From UT_WARN_LIMIT register. -tempX_max Maximum temperature. From OT_WARN_LIMIT register. -tempX_lcrit Critical low temperature. - From UT_FAULT_LIMIT register. -tempX_crit Critical high temperature. - From OT_FAULT_LIMIT register. -tempX_min_alarm Chip temperature low alarm. Set by comparing - READ_TEMPERATURE_X with UT_WARN_LIMIT if - TEMP_UT_WARNING status is set. -tempX_max_alarm Chip temperature high alarm. Set by comparing - READ_TEMPERATURE_X with OT_WARN_LIMIT if - TEMP_OT_WARNING status is set. -tempX_lcrit_alarm Chip temperature critical low alarm. Set by comparing - READ_TEMPERATURE_X with UT_FAULT_LIMIT if - TEMP_UT_FAULT status is set. -tempX_crit_alarm Chip temperature critical high alarm. Set by comparing - READ_TEMPERATURE_X with OT_FAULT_LIMIT if - TEMP_OT_FAULT status is set. -======================= ======================================================== diff --git a/Documentation/hwmon/pmbus-core b/Documentation/hwmon/pmbus-core deleted file mode 100644 index 92515c446fe3..000000000000 --- a/Documentation/hwmon/pmbus-core +++ /dev/null @@ -1,316 +0,0 @@ -================================== -PMBus core driver and internal API -================================== - -Introduction -============ - -[from pmbus.org] The Power Management Bus (PMBus) is an open standard -power-management protocol with a fully defined command language that facilitates -communication with power converters and other devices in a power system. The -protocol is implemented over the industry-standard SMBus serial interface and -enables programming, control, and real-time monitoring of compliant power -conversion products. This flexible and highly versatile standard allows for -communication between devices based on both analog and digital technologies, and -provides true interoperability which will reduce design complexity and shorten -time to market for power system designers. Pioneered by leading power supply and -semiconductor companies, this open power system standard is maintained and -promoted by the PMBus Implementers Forum (PMBus-IF), comprising 30+ adopters -with the objective to provide support to, and facilitate adoption among, users. - -Unfortunately, while PMBus commands are standardized, there are no mandatory -commands, and manufacturers can add as many non-standard commands as they like. -Also, different PMBUs devices act differently if non-supported commands are -executed. Some devices return an error, some devices return 0xff or 0xffff and -set a status error flag, and some devices may simply hang up. - -Despite all those difficulties, a generic PMBus device driver is still useful -and supported since kernel version 2.6.39. However, it was necessary to support -device specific extensions in addition to the core PMBus driver, since it is -simply unknown what new device specific functionality PMBus device developers -come up with next. - -To make device specific extensions as scalable as possible, and to avoid having -to modify the core PMBus driver repeatedly for new devices, the PMBus driver was -split into core, generic, and device specific code. The core code (in -pmbus_core.c) provides generic functionality. The generic code (in pmbus.c) -provides support for generic PMBus devices. Device specific code is responsible -for device specific initialization and, if needed, maps device specific -functionality into generic functionality. This is to some degree comparable -to PCI code, where generic code is augmented as needed with quirks for all kinds -of devices. - -PMBus device capabilities auto-detection -======================================== - -For generic PMBus devices, code in pmbus.c attempts to auto-detect all supported -PMBus commands. Auto-detection is somewhat limited, since there are simply too -many variables to consider. For example, it is almost impossible to autodetect -which PMBus commands are paged and which commands are replicated across all -pages (see the PMBus specification for details on multi-page PMBus devices). - -For this reason, it often makes sense to provide a device specific driver if not -all commands can be auto-detected. The data structures in this driver can be -used to inform the core driver about functionality supported by individual -chips. - -Some commands are always auto-detected. This applies to all limit commands -(lcrit, min, max, and crit attributes) as well as associated alarm attributes. -Limits and alarm attributes are auto-detected because there are simply too many -possible combinations to provide a manual configuration interface. - -PMBus internal API -================== - -The API between core and device specific PMBus code is defined in -drivers/hwmon/pmbus/pmbus.h. In addition to the internal API, pmbus.h defines -standard PMBus commands and virtual PMBus commands. - -Standard PMBus commands ------------------------ - -Standard PMBus commands (commands values 0x00 to 0xff) are defined in the PMBUs -specification. - -Virtual PMBus commands ----------------------- - -Virtual PMBus commands are provided to enable support for non-standard -functionality which has been implemented by several chip vendors and is thus -desirable to support. - -Virtual PMBus commands start with command value 0x100 and can thus easily be -distinguished from standard PMBus commands (which can not have values larger -than 0xff). Support for virtual PMBus commands is device specific and thus has -to be implemented in device specific code. - -Virtual commands are named PMBUS_VIRT_xxx and start with PMBUS_VIRT_BASE. All -virtual commands are word sized. - -There are currently two types of virtual commands. - -- READ commands are read-only; writes are either ignored or return an error. -- RESET commands are read/write. Reading reset registers returns zero - (used for detection), writing any value causes the associated history to be - reset. - -Virtual commands have to be handled in device specific driver code. Chip driver -code returns non-negative values if a virtual command is supported, or a -negative error code if not. The chip driver may return -ENODATA or any other -Linux error code in this case, though an error code other than -ENODATA is -handled more efficiently and thus preferred. Either case, the calling PMBus -core code will abort if the chip driver returns an error code when reading -or writing virtual registers (in other words, the PMBus core code will never -send a virtual command to a chip). - -PMBus driver information ------------------------- - -PMBus driver information, defined in struct pmbus_driver_info, is the main means -for device specific drivers to pass information to the core PMBus driver. -Specifically, it provides the following information. - -- For devices supporting its data in Direct Data Format, it provides coefficients - for converting register values into normalized data. This data is usually - provided by chip manufacturers in device datasheets. -- Supported chip functionality can be provided to the core driver. This may be - necessary for chips which react badly if non-supported commands are executed, - and/or to speed up device detection and initialization. -- Several function entry points are provided to support overriding and/or - augmenting generic command execution. This functionality can be used to map - non-standard PMBus commands to standard commands, or to augment standard - command return values with device specific information. - -API functions -============= - -Functions provided by chip driver ---------------------------------- - -All functions return the command return value (read) or zero (write) if -successful. A return value of -ENODATA indicates that there is no manufacturer -specific command, but that a standard PMBus command may exist. Any other -negative return value indicates that the commands does not exist for this -chip, and that no attempt should be made to read or write the standard -command. - -As mentioned above, an exception to this rule applies to virtual commands, -which *must* be handled in driver specific code. See "Virtual PMBus Commands" -above for more details. - -Command execution in the core PMBus driver code is as follows:: - - if (chip_access_function) { - status = chip_access_function(); - if (status != -ENODATA) - return status; - } - if (command >= PMBUS_VIRT_BASE) /* For word commands/registers only */ - return -EINVAL; - return generic_access(); - -Chip drivers may provide pointers to the following functions in struct -pmbus_driver_info. All functions are optional. - -:: - - int (*read_byte_data)(struct i2c_client *client, int page, int reg); - -Read byte from page , register . - may be -1, which means "current page". - - -:: - - int (*read_word_data)(struct i2c_client *client, int page, int reg); - -Read word from page , register . - -:: - - int (*write_word_data)(struct i2c_client *client, int page, int reg, - u16 word); - -Write word to page , register . - -:: - - int (*write_byte)(struct i2c_client *client, int page, u8 value); - -Write byte to page , register . - may be -1, which means "current page". - -:: - - int (*identify)(struct i2c_client *client, struct pmbus_driver_info *info); - -Determine supported PMBus functionality. This function is only necessary -if a chip driver supports multiple chips, and the chip functionality is not -pre-determined. It is currently only used by the generic pmbus driver -(pmbus.c). - -Functions exported by core driver ---------------------------------- - -Chip drivers are expected to use the following functions to read or write -PMBus registers. Chip drivers may also use direct I2C commands. If direct I2C -commands are used, the chip driver code must not directly modify the current -page, since the selected page is cached in the core driver and the core driver -will assume that it is selected. Using pmbus_set_page() to select a new page -is mandatory. - -:: - - int pmbus_set_page(struct i2c_client *client, u8 page); - -Set PMBus page register to for subsequent commands. - -:: - - int pmbus_read_word_data(struct i2c_client *client, u8 page, u8 reg); - -Read word data from , . Similar to i2c_smbus_read_word_data(), but -selects page first. - -:: - - int pmbus_write_word_data(struct i2c_client *client, u8 page, u8 reg, - u16 word); - -Write word data to , . Similar to i2c_smbus_write_word_data(), but -selects page first. - -:: - - int pmbus_read_byte_data(struct i2c_client *client, int page, u8 reg); - -Read byte data from , . Similar to i2c_smbus_read_byte_data(), but -selects page first. may be -1, which means "current page". - -:: - - int pmbus_write_byte(struct i2c_client *client, int page, u8 value); - -Write byte data to , . Similar to i2c_smbus_write_byte(), but -selects page first. may be -1, which means "current page". - -:: - - void pmbus_clear_faults(struct i2c_client *client); - -Execute PMBus "Clear Fault" command on all chip pages. -This function calls the device specific write_byte function if defined. -Therefore, it must _not_ be called from that function. - -:: - - bool pmbus_check_byte_register(struct i2c_client *client, int page, int reg); - -Check if byte register exists. Return true if the register exists, false -otherwise. -This function calls the device specific write_byte function if defined to -obtain the chip status. Therefore, it must _not_ be called from that function. - -:: - - bool pmbus_check_word_register(struct i2c_client *client, int page, int reg); - -Check if word register exists. Return true if the register exists, false -otherwise. -This function calls the device specific write_byte function if defined to -obtain the chip status. Therefore, it must _not_ be called from that function. - -:: - - int pmbus_do_probe(struct i2c_client *client, const struct i2c_device_id *id, - struct pmbus_driver_info *info); - -Execute probe function. Similar to standard probe function for other drivers, -with the pointer to struct pmbus_driver_info as additional argument. Calls -identify function if supported. Must only be called from device probe -function. - -:: - - void pmbus_do_remove(struct i2c_client *client); - -Execute driver remove function. Similar to standard driver remove function. - -:: - - const struct pmbus_driver_info - *pmbus_get_driver_info(struct i2c_client *client); - -Return pointer to struct pmbus_driver_info as passed to pmbus_do_probe(). - - -PMBus driver platform data -========================== - -PMBus platform data is defined in include/linux/pmbus.h. Platform data -currently only provides a flag field with a single bit used:: - - #define PMBUS_SKIP_STATUS_CHECK (1 << 0) - - struct pmbus_platform_data { - u32 flags; /* Device specific flags */ - }; - - -Flags ------ - -PMBUS_SKIP_STATUS_CHECK - During register detection, skip checking the status register for - communication or command errors. - -Some PMBus chips respond with valid data when trying to read an unsupported -register. For such chips, checking the status register is mandatory when -trying to determine if a chip register exists or not. -Other PMBus chips don't support the STATUS_CML register, or report -communication errors for no explicable reason. For such chips, checking the -status register must be disabled. - -Some i2c controllers do not support single-byte commands (write commands with -no data, i2c_smbus_write_byte()). With such controllers, clearing the status -register is impossible, and the PMBUS_SKIP_STATUS_CHECK flag must be set. diff --git a/Documentation/hwmon/pmbus-core.rst b/Documentation/hwmon/pmbus-core.rst new file mode 100644 index 000000000000..92515c446fe3 --- /dev/null +++ b/Documentation/hwmon/pmbus-core.rst @@ -0,0 +1,316 @@ +================================== +PMBus core driver and internal API +================================== + +Introduction +============ + +[from pmbus.org] The Power Management Bus (PMBus) is an open standard +power-management protocol with a fully defined command language that facilitates +communication with power converters and other devices in a power system. The +protocol is implemented over the industry-standard SMBus serial interface and +enables programming, control, and real-time monitoring of compliant power +conversion products. This flexible and highly versatile standard allows for +communication between devices based on both analog and digital technologies, and +provides true interoperability which will reduce design complexity and shorten +time to market for power system designers. Pioneered by leading power supply and +semiconductor companies, this open power system standard is maintained and +promoted by the PMBus Implementers Forum (PMBus-IF), comprising 30+ adopters +with the objective to provide support to, and facilitate adoption among, users. + +Unfortunately, while PMBus commands are standardized, there are no mandatory +commands, and manufacturers can add as many non-standard commands as they like. +Also, different PMBUs devices act differently if non-supported commands are +executed. Some devices return an error, some devices return 0xff or 0xffff and +set a status error flag, and some devices may simply hang up. + +Despite all those difficulties, a generic PMBus device driver is still useful +and supported since kernel version 2.6.39. However, it was necessary to support +device specific extensions in addition to the core PMBus driver, since it is +simply unknown what new device specific functionality PMBus device developers +come up with next. + +To make device specific extensions as scalable as possible, and to avoid having +to modify the core PMBus driver repeatedly for new devices, the PMBus driver was +split into core, generic, and device specific code. The core code (in +pmbus_core.c) provides generic functionality. The generic code (in pmbus.c) +provides support for generic PMBus devices. Device specific code is responsible +for device specific initialization and, if needed, maps device specific +functionality into generic functionality. This is to some degree comparable +to PCI code, where generic code is augmented as needed with quirks for all kinds +of devices. + +PMBus device capabilities auto-detection +======================================== + +For generic PMBus devices, code in pmbus.c attempts to auto-detect all supported +PMBus commands. Auto-detection is somewhat limited, since there are simply too +many variables to consider. For example, it is almost impossible to autodetect +which PMBus commands are paged and which commands are replicated across all +pages (see the PMBus specification for details on multi-page PMBus devices). + +For this reason, it often makes sense to provide a device specific driver if not +all commands can be auto-detected. The data structures in this driver can be +used to inform the core driver about functionality supported by individual +chips. + +Some commands are always auto-detected. This applies to all limit commands +(lcrit, min, max, and crit attributes) as well as associated alarm attributes. +Limits and alarm attributes are auto-detected because there are simply too many +possible combinations to provide a manual configuration interface. + +PMBus internal API +================== + +The API between core and device specific PMBus code is defined in +drivers/hwmon/pmbus/pmbus.h. In addition to the internal API, pmbus.h defines +standard PMBus commands and virtual PMBus commands. + +Standard PMBus commands +----------------------- + +Standard PMBus commands (commands values 0x00 to 0xff) are defined in the PMBUs +specification. + +Virtual PMBus commands +---------------------- + +Virtual PMBus commands are provided to enable support for non-standard +functionality which has been implemented by several chip vendors and is thus +desirable to support. + +Virtual PMBus commands start with command value 0x100 and can thus easily be +distinguished from standard PMBus commands (which can not have values larger +than 0xff). Support for virtual PMBus commands is device specific and thus has +to be implemented in device specific code. + +Virtual commands are named PMBUS_VIRT_xxx and start with PMBUS_VIRT_BASE. All +virtual commands are word sized. + +There are currently two types of virtual commands. + +- READ commands are read-only; writes are either ignored or return an error. +- RESET commands are read/write. Reading reset registers returns zero + (used for detection), writing any value causes the associated history to be + reset. + +Virtual commands have to be handled in device specific driver code. Chip driver +code returns non-negative values if a virtual command is supported, or a +negative error code if not. The chip driver may return -ENODATA or any other +Linux error code in this case, though an error code other than -ENODATA is +handled more efficiently and thus preferred. Either case, the calling PMBus +core code will abort if the chip driver returns an error code when reading +or writing virtual registers (in other words, the PMBus core code will never +send a virtual command to a chip). + +PMBus driver information +------------------------ + +PMBus driver information, defined in struct pmbus_driver_info, is the main means +for device specific drivers to pass information to the core PMBus driver. +Specifically, it provides the following information. + +- For devices supporting its data in Direct Data Format, it provides coefficients + for converting register values into normalized data. This data is usually + provided by chip manufacturers in device datasheets. +- Supported chip functionality can be provided to the core driver. This may be + necessary for chips which react badly if non-supported commands are executed, + and/or to speed up device detection and initialization. +- Several function entry points are provided to support overriding and/or + augmenting generic command execution. This functionality can be used to map + non-standard PMBus commands to standard commands, or to augment standard + command return values with device specific information. + +API functions +============= + +Functions provided by chip driver +--------------------------------- + +All functions return the command return value (read) or zero (write) if +successful. A return value of -ENODATA indicates that there is no manufacturer +specific command, but that a standard PMBus command may exist. Any other +negative return value indicates that the commands does not exist for this +chip, and that no attempt should be made to read or write the standard +command. + +As mentioned above, an exception to this rule applies to virtual commands, +which *must* be handled in driver specific code. See "Virtual PMBus Commands" +above for more details. + +Command execution in the core PMBus driver code is as follows:: + + if (chip_access_function) { + status = chip_access_function(); + if (status != -ENODATA) + return status; + } + if (command >= PMBUS_VIRT_BASE) /* For word commands/registers only */ + return -EINVAL; + return generic_access(); + +Chip drivers may provide pointers to the following functions in struct +pmbus_driver_info. All functions are optional. + +:: + + int (*read_byte_data)(struct i2c_client *client, int page, int reg); + +Read byte from page , register . + may be -1, which means "current page". + + +:: + + int (*read_word_data)(struct i2c_client *client, int page, int reg); + +Read word from page , register . + +:: + + int (*write_word_data)(struct i2c_client *client, int page, int reg, + u16 word); + +Write word to page , register . + +:: + + int (*write_byte)(struct i2c_client *client, int page, u8 value); + +Write byte to page , register . + may be -1, which means "current page". + +:: + + int (*identify)(struct i2c_client *client, struct pmbus_driver_info *info); + +Determine supported PMBus functionality. This function is only necessary +if a chip driver supports multiple chips, and the chip functionality is not +pre-determined. It is currently only used by the generic pmbus driver +(pmbus.c). + +Functions exported by core driver +--------------------------------- + +Chip drivers are expected to use the following functions to read or write +PMBus registers. Chip drivers may also use direct I2C commands. If direct I2C +commands are used, the chip driver code must not directly modify the current +page, since the selected page is cached in the core driver and the core driver +will assume that it is selected. Using pmbus_set_page() to select a new page +is mandatory. + +:: + + int pmbus_set_page(struct i2c_client *client, u8 page); + +Set PMBus page register to for subsequent commands. + +:: + + int pmbus_read_word_data(struct i2c_client *client, u8 page, u8 reg); + +Read word data from , . Similar to i2c_smbus_read_word_data(), but +selects page first. + +:: + + int pmbus_write_word_data(struct i2c_client *client, u8 page, u8 reg, + u16 word); + +Write word data to , . Similar to i2c_smbus_write_word_data(), but +selects page first. + +:: + + int pmbus_read_byte_data(struct i2c_client *client, int page, u8 reg); + +Read byte data from , . Similar to i2c_smbus_read_byte_data(), but +selects page first. may be -1, which means "current page". + +:: + + int pmbus_write_byte(struct i2c_client *client, int page, u8 value); + +Write byte data to , . Similar to i2c_smbus_write_byte(), but +selects page first. may be -1, which means "current page". + +:: + + void pmbus_clear_faults(struct i2c_client *client); + +Execute PMBus "Clear Fault" command on all chip pages. +This function calls the device specific write_byte function if defined. +Therefore, it must _not_ be called from that function. + +:: + + bool pmbus_check_byte_register(struct i2c_client *client, int page, int reg); + +Check if byte register exists. Return true if the register exists, false +otherwise. +This function calls the device specific write_byte function if defined to +obtain the chip status. Therefore, it must _not_ be called from that function. + +:: + + bool pmbus_check_word_register(struct i2c_client *client, int page, int reg); + +Check if word register exists. Return true if the register exists, false +otherwise. +This function calls the device specific write_byte function if defined to +obtain the chip status. Therefore, it must _not_ be called from that function. + +:: + + int pmbus_do_probe(struct i2c_client *client, const struct i2c_device_id *id, + struct pmbus_driver_info *info); + +Execute probe function. Similar to standard probe function for other drivers, +with the pointer to struct pmbus_driver_info as additional argument. Calls +identify function if supported. Must only be called from device probe +function. + +:: + + void pmbus_do_remove(struct i2c_client *client); + +Execute driver remove function. Similar to standard driver remove function. + +:: + + const struct pmbus_driver_info + *pmbus_get_driver_info(struct i2c_client *client); + +Return pointer to struct pmbus_driver_info as passed to pmbus_do_probe(). + + +PMBus driver platform data +========================== + +PMBus platform data is defined in include/linux/pmbus.h. Platform data +currently only provides a flag field with a single bit used:: + + #define PMBUS_SKIP_STATUS_CHECK (1 << 0) + + struct pmbus_platform_data { + u32 flags; /* Device specific flags */ + }; + + +Flags +----- + +PMBUS_SKIP_STATUS_CHECK + During register detection, skip checking the status register for + communication or command errors. + +Some PMBus chips respond with valid data when trying to read an unsupported +register. For such chips, checking the status register is mandatory when +trying to determine if a chip register exists or not. +Other PMBus chips don't support the STATUS_CML register, or report +communication errors for no explicable reason. For such chips, checking the +status register must be disabled. + +Some i2c controllers do not support single-byte commands (write commands with +no data, i2c_smbus_write_byte()). With such controllers, clearing the status +register is impossible, and the PMBUS_SKIP_STATUS_CHECK flag must be set. diff --git a/Documentation/hwmon/pmbus.rst b/Documentation/hwmon/pmbus.rst new file mode 100644 index 000000000000..abfb9dd4857d --- /dev/null +++ b/Documentation/hwmon/pmbus.rst @@ -0,0 +1,254 @@ +Kernel driver pmbus +=================== + +Supported chips: + + * Ericsson BMR453, BMR454 + + Prefixes: 'bmr453', 'bmr454' + + Addresses scanned: - + + Datasheet: + + http://archive.ericsson.net/service/internet/picov/get?DocNo=28701-EN/LZT146395 + + * ON Semiconductor ADP4000, NCP4200, NCP4208 + + Prefixes: 'adp4000', 'ncp4200', 'ncp4208' + + Addresses scanned: - + + Datasheets: + + http://www.onsemi.com/pub_link/Collateral/ADP4000-D.PDF + + http://www.onsemi.com/pub_link/Collateral/NCP4200-D.PDF + + http://www.onsemi.com/pub_link/Collateral/JUNE%202009-%20REV.%200.PDF + + * Lineage Power + + Prefixes: 'mdt040', 'pdt003', 'pdt006', 'pdt012', 'udt020' + + Addresses scanned: - + + Datasheets: + + http://www.lineagepower.com/oem/pdf/PDT003A0X.pdf + + http://www.lineagepower.com/oem/pdf/PDT006A0X.pdf + + http://www.lineagepower.com/oem/pdf/PDT012A0X.pdf + + http://www.lineagepower.com/oem/pdf/UDT020A0X.pdf + + http://www.lineagepower.com/oem/pdf/MDT040A0X.pdf + + * Texas Instruments TPS40400, TPS544B20, TPS544B25, TPS544C20, TPS544C25 + + Prefixes: 'tps40400', 'tps544b20', 'tps544b25', 'tps544c20', 'tps544c25' + + Addresses scanned: - + + Datasheets: + + http://www.ti.com/lit/gpn/tps40400 + + http://www.ti.com/lit/gpn/tps544b20 + + http://www.ti.com/lit/gpn/tps544b25 + + http://www.ti.com/lit/gpn/tps544c20 + + http://www.ti.com/lit/gpn/tps544c25 + + * Generic PMBus devices + + Prefix: 'pmbus' + + Addresses scanned: - + + Datasheet: n.a. + + +Author: Guenter Roeck + + +Description +----------- + +This driver supports hardware monitoring for various PMBus compliant devices. +It supports voltage, current, power, and temperature sensors as supported +by the device. + +Each monitored channel has its own high and low limits, plus a critical +limit. + +Fan support will be added in a later version of this driver. + + +Usage Notes +----------- + +This driver does not probe for PMBus devices, since there is no register +which can be safely used to identify the chip (The MFG_ID register is not +supported by all chips), and since there is no well defined address range for +PMBus devices. You will have to instantiate the devices explicitly. + +Example: the following will load the driver for an LTC2978 at address 0x60 +on I2C bus #1:: + + $ modprobe pmbus + $ echo ltc2978 0x60 > /sys/bus/i2c/devices/i2c-1/new_device + + +Platform data support +--------------------- + +Support for additional PMBus chips can be added by defining chip parameters in +a new chip specific driver file. For example, (untested) code to add support for +Emerson DS1200 power modules might look as follows:: + + static struct pmbus_driver_info ds1200_info = { + .pages = 1, + /* Note: All other sensors are in linear mode */ + .direct[PSC_VOLTAGE_OUT] = true, + .direct[PSC_TEMPERATURE] = true, + .direct[PSC_CURRENT_OUT] = true, + .m[PSC_VOLTAGE_IN] = 1, + .b[PSC_VOLTAGE_IN] = 0, + .R[PSC_VOLTAGE_IN] = 3, + .m[PSC_VOLTAGE_OUT] = 1, + .b[PSC_VOLTAGE_OUT] = 0, + .R[PSC_VOLTAGE_OUT] = 3, + .m[PSC_TEMPERATURE] = 1, + .b[PSC_TEMPERATURE] = 0, + .R[PSC_TEMPERATURE] = 3, + .func[0] = PMBUS_HAVE_VIN | PMBUS_HAVE_IIN | PMBUS_HAVE_STATUS_INPUT + | PMBUS_HAVE_VOUT | PMBUS_HAVE_STATUS_VOUT + | PMBUS_HAVE_IOUT | PMBUS_HAVE_STATUS_IOUT + | PMBUS_HAVE_PIN | PMBUS_HAVE_POUT + | PMBUS_HAVE_TEMP | PMBUS_HAVE_STATUS_TEMP + | PMBUS_HAVE_FAN12 | PMBUS_HAVE_STATUS_FAN12, + }; + + static int ds1200_probe(struct i2c_client *client, + const struct i2c_device_id *id) + { + return pmbus_do_probe(client, id, &ds1200_info); + } + + static int ds1200_remove(struct i2c_client *client) + { + return pmbus_do_remove(client); + } + + static const struct i2c_device_id ds1200_id[] = { + {"ds1200", 0}, + {} + }; + + MODULE_DEVICE_TABLE(i2c, ds1200_id); + + /* This is the driver that will be inserted */ + static struct i2c_driver ds1200_driver = { + .driver = { + .name = "ds1200", + }, + .probe = ds1200_probe, + .remove = ds1200_remove, + .id_table = ds1200_id, + }; + + static int __init ds1200_init(void) + { + return i2c_add_driver(&ds1200_driver); + } + + static void __exit ds1200_exit(void) + { + i2c_del_driver(&ds1200_driver); + } + + +Sysfs entries +------------- + +When probing the chip, the driver identifies which PMBus registers are +supported, and determines available sensors from this information. +Attribute files only exist if respective sensors are supported by the chip. +Labels are provided to inform the user about the sensor associated with +a given sysfs entry. + +The following attributes are supported. Limits are read-write; all other +attributes are read-only. + +======================= ======================================================== +inX_input Measured voltage. From READ_VIN or READ_VOUT register. +inX_min Minimum Voltage. + From VIN_UV_WARN_LIMIT or VOUT_UV_WARN_LIMIT register. +inX_max Maximum voltage. + From VIN_OV_WARN_LIMIT or VOUT_OV_WARN_LIMIT register. +inX_lcrit Critical minimum Voltage. + From VIN_UV_FAULT_LIMIT or VOUT_UV_FAULT_LIMIT register. +inX_crit Critical maximum voltage. + From VIN_OV_FAULT_LIMIT or VOUT_OV_FAULT_LIMIT register. +inX_min_alarm Voltage low alarm. From VOLTAGE_UV_WARNING status. +inX_max_alarm Voltage high alarm. From VOLTAGE_OV_WARNING status. +inX_lcrit_alarm Voltage critical low alarm. + From VOLTAGE_UV_FAULT status. +inX_crit_alarm Voltage critical high alarm. + From VOLTAGE_OV_FAULT status. +inX_label "vin", "vcap", or "voutY" + +currX_input Measured current. From READ_IIN or READ_IOUT register. +currX_max Maximum current. + From IIN_OC_WARN_LIMIT or IOUT_OC_WARN_LIMIT register. +currX_lcrit Critical minimum output current. + From IOUT_UC_FAULT_LIMIT register. +currX_crit Critical maximum current. + From IIN_OC_FAULT_LIMIT or IOUT_OC_FAULT_LIMIT register. +currX_alarm Current high alarm. + From IIN_OC_WARNING or IOUT_OC_WARNING status. +currX_max_alarm Current high alarm. + From IIN_OC_WARN_LIMIT or IOUT_OC_WARN_LIMIT status. +currX_lcrit_alarm Output current critical low alarm. + From IOUT_UC_FAULT status. +currX_crit_alarm Current critical high alarm. + From IIN_OC_FAULT or IOUT_OC_FAULT status. +currX_label "iin" or "ioutY" + +powerX_input Measured power. From READ_PIN or READ_POUT register. +powerX_cap Output power cap. From POUT_MAX register. +powerX_max Power limit. From PIN_OP_WARN_LIMIT or + POUT_OP_WARN_LIMIT register. +powerX_crit Critical output power limit. + From POUT_OP_FAULT_LIMIT register. +powerX_alarm Power high alarm. + From PIN_OP_WARNING or POUT_OP_WARNING status. +powerX_crit_alarm Output power critical high alarm. + From POUT_OP_FAULT status. +powerX_label "pin" or "poutY" + +tempX_input Measured temperature. + From READ_TEMPERATURE_X register. +tempX_min Mimimum temperature. From UT_WARN_LIMIT register. +tempX_max Maximum temperature. From OT_WARN_LIMIT register. +tempX_lcrit Critical low temperature. + From UT_FAULT_LIMIT register. +tempX_crit Critical high temperature. + From OT_FAULT_LIMIT register. +tempX_min_alarm Chip temperature low alarm. Set by comparing + READ_TEMPERATURE_X with UT_WARN_LIMIT if + TEMP_UT_WARNING status is set. +tempX_max_alarm Chip temperature high alarm. Set by comparing + READ_TEMPERATURE_X with OT_WARN_LIMIT if + TEMP_OT_WARNING status is set. +tempX_lcrit_alarm Chip temperature critical low alarm. Set by comparing + READ_TEMPERATURE_X with UT_FAULT_LIMIT if + TEMP_UT_FAULT status is set. +tempX_crit_alarm Chip temperature critical high alarm. Set by comparing + READ_TEMPERATURE_X with OT_FAULT_LIMIT if + TEMP_OT_FAULT status is set. +======================= ======================================================== diff --git a/Documentation/hwmon/powr1220 b/Documentation/hwmon/powr1220 deleted file mode 100644 index a7fc258da0a8..000000000000 --- a/Documentation/hwmon/powr1220 +++ /dev/null @@ -1,53 +0,0 @@ -Kernel driver powr1220 -====================== - -Supported chips: - - * Lattice POWR1220AT8 - - Prefix: 'powr1220' - - Addresses scanned: none - - Datasheet: Publicly available at the Lattice website - - http://www.latticesemi.com/ - -Author: Scott Kanowitz - -Description ------------ - -This driver supports the Lattice POWR1220AT8 chip. The POWR1220 -includes voltage monitoring for 14 inputs as well as trim settings -for output voltages and GPIOs. This driver implements the voltage -monitoring portion of the chip. - -Voltages are sampled by a 12-bit ADC with a step size of 2 mV. -An in-line attenuator allows measurements from 0 to 6 V. The -attenuator is enabled or disabled depending on the setting of the -input's max value. The driver will enable the attenuator for any -value over the low measurement range maximum of 2 V. - -The input naming convention is as follows: - -============== ======== -driver name pin name -============== ======== -in0 VMON1 -in1 VMON2 -in2 VMON3 -in2 VMON4 -in4 VMON5 -in5 VMON6 -in6 VMON7 -in7 VMON8 -in8 VMON9 -in9 VMON10 -in10 VMON11 -in11 VMON12 -in12 VCCA -in13 VCCINP -============== ======== - -The ADC readings are updated on request with a minimum period of 1s. diff --git a/Documentation/hwmon/powr1220.rst b/Documentation/hwmon/powr1220.rst new file mode 100644 index 000000000000..a7fc258da0a8 --- /dev/null +++ b/Documentation/hwmon/powr1220.rst @@ -0,0 +1,53 @@ +Kernel driver powr1220 +====================== + +Supported chips: + + * Lattice POWR1220AT8 + + Prefix: 'powr1220' + + Addresses scanned: none + + Datasheet: Publicly available at the Lattice website + + http://www.latticesemi.com/ + +Author: Scott Kanowitz + +Description +----------- + +This driver supports the Lattice POWR1220AT8 chip. The POWR1220 +includes voltage monitoring for 14 inputs as well as trim settings +for output voltages and GPIOs. This driver implements the voltage +monitoring portion of the chip. + +Voltages are sampled by a 12-bit ADC with a step size of 2 mV. +An in-line attenuator allows measurements from 0 to 6 V. The +attenuator is enabled or disabled depending on the setting of the +input's max value. The driver will enable the attenuator for any +value over the low measurement range maximum of 2 V. + +The input naming convention is as follows: + +============== ======== +driver name pin name +============== ======== +in0 VMON1 +in1 VMON2 +in2 VMON3 +in2 VMON4 +in4 VMON5 +in5 VMON6 +in6 VMON7 +in7 VMON8 +in8 VMON9 +in9 VMON10 +in10 VMON11 +in11 VMON12 +in12 VCCA +in13 VCCINP +============== ======== + +The ADC readings are updated on request with a minimum period of 1s. diff --git a/Documentation/hwmon/pwm-fan b/Documentation/hwmon/pwm-fan deleted file mode 100644 index 82fe96742fee..000000000000 --- a/Documentation/hwmon/pwm-fan +++ /dev/null @@ -1,20 +0,0 @@ -Kernel driver pwm-fan -===================== - -This driver enables the use of a PWM module to drive a fan. It uses the -generic PWM interface thus it is hardware independent. It can be used on -many SoCs, as long as the SoC supplies a PWM line driver that exposes -the generic PWM API. - -Author: Kamil Debski - -Description ------------ - -The driver implements a simple interface for driving a fan connected to -a PWM output. It uses the generic PWM interface, thus it can be used with -a range of SoCs. The driver exposes the fan to the user space through -the hwmon's sysfs interface. - -The fan rotation speed returned via the optional 'fan1_input' is extrapolated -from the sampled interrupts from the tachometer signal within 1 second. diff --git a/Documentation/hwmon/pwm-fan.rst b/Documentation/hwmon/pwm-fan.rst new file mode 100644 index 000000000000..82fe96742fee --- /dev/null +++ b/Documentation/hwmon/pwm-fan.rst @@ -0,0 +1,20 @@ +Kernel driver pwm-fan +===================== + +This driver enables the use of a PWM module to drive a fan. It uses the +generic PWM interface thus it is hardware independent. It can be used on +many SoCs, as long as the SoC supplies a PWM line driver that exposes +the generic PWM API. + +Author: Kamil Debski + +Description +----------- + +The driver implements a simple interface for driving a fan connected to +a PWM output. It uses the generic PWM interface, thus it can be used with +a range of SoCs. The driver exposes the fan to the user space through +the hwmon's sysfs interface. + +The fan rotation speed returned via the optional 'fan1_input' is extrapolated +from the sampled interrupts from the tachometer signal within 1 second. diff --git a/Documentation/hwmon/raspberrypi-hwmon b/Documentation/hwmon/raspberrypi-hwmon deleted file mode 100644 index 8038ade36490..000000000000 --- a/Documentation/hwmon/raspberrypi-hwmon +++ /dev/null @@ -1,25 +0,0 @@ -Kernel driver raspberrypi-hwmon -=============================== - -Supported boards: - - * Raspberry Pi A+ (via GPIO on SoC) - * Raspberry Pi B+ (via GPIO on SoC) - * Raspberry Pi 2 B (via GPIO on SoC) - * Raspberry Pi 3 B (via GPIO on port expander) - * Raspberry Pi 3 B+ (via PMIC) - -Author: Stefan Wahren - -Description ------------ - -This driver periodically polls a mailbox property of the VC4 firmware to detect -undervoltage conditions. - -Sysfs entries -------------- - -======================= ================== -in0_lcrit_alarm Undervoltage alarm -======================= ================== diff --git a/Documentation/hwmon/raspberrypi-hwmon.rst b/Documentation/hwmon/raspberrypi-hwmon.rst new file mode 100644 index 000000000000..8038ade36490 --- /dev/null +++ b/Documentation/hwmon/raspberrypi-hwmon.rst @@ -0,0 +1,25 @@ +Kernel driver raspberrypi-hwmon +=============================== + +Supported boards: + + * Raspberry Pi A+ (via GPIO on SoC) + * Raspberry Pi B+ (via GPIO on SoC) + * Raspberry Pi 2 B (via GPIO on SoC) + * Raspberry Pi 3 B (via GPIO on port expander) + * Raspberry Pi 3 B+ (via PMIC) + +Author: Stefan Wahren + +Description +----------- + +This driver periodically polls a mailbox property of the VC4 firmware to detect +undervoltage conditions. + +Sysfs entries +------------- + +======================= ================== +in0_lcrit_alarm Undervoltage alarm +======================= ================== diff --git a/Documentation/hwmon/sch5627 b/Documentation/hwmon/sch5627 deleted file mode 100644 index 187682e99114..000000000000 --- a/Documentation/hwmon/sch5627 +++ /dev/null @@ -1,31 +0,0 @@ -Kernel driver sch5627 -===================== - -Supported chips: - - * SMSC SCH5627 - - Prefix: 'sch5627' - - Addresses scanned: none, address read from Super I/O config space - - Datasheet: Application Note available upon request - -Author: Hans de Goede - - -Description ------------ - -SMSC SCH5627 Super I/O chips include complete hardware monitoring -capabilities. They can monitor up to 5 voltages, 4 fans and 8 temperatures. - -The SMSC SCH5627 hardware monitoring part also contains an integrated -watchdog. In order for this watchdog to function some motherboard specific -initialization most be done by the BIOS, so if the watchdog is not enabled -by the BIOS the sch5627 driver will not register a watchdog device. - -The hardware monitoring part of the SMSC SCH5627 is accessed by talking -through an embedded microcontroller. An application note describing the -protocol for communicating with the microcontroller is available upon -request. Please mail me if you want a copy. diff --git a/Documentation/hwmon/sch5627.rst b/Documentation/hwmon/sch5627.rst new file mode 100644 index 000000000000..187682e99114 --- /dev/null +++ b/Documentation/hwmon/sch5627.rst @@ -0,0 +1,31 @@ +Kernel driver sch5627 +===================== + +Supported chips: + + * SMSC SCH5627 + + Prefix: 'sch5627' + + Addresses scanned: none, address read from Super I/O config space + + Datasheet: Application Note available upon request + +Author: Hans de Goede + + +Description +----------- + +SMSC SCH5627 Super I/O chips include complete hardware monitoring +capabilities. They can monitor up to 5 voltages, 4 fans and 8 temperatures. + +The SMSC SCH5627 hardware monitoring part also contains an integrated +watchdog. In order for this watchdog to function some motherboard specific +initialization most be done by the BIOS, so if the watchdog is not enabled +by the BIOS the sch5627 driver will not register a watchdog device. + +The hardware monitoring part of the SMSC SCH5627 is accessed by talking +through an embedded microcontroller. An application note describing the +protocol for communicating with the microcontroller is available upon +request. Please mail me if you want a copy. diff --git a/Documentation/hwmon/sch5636 b/Documentation/hwmon/sch5636 deleted file mode 100644 index 4aaee3672f13..000000000000 --- a/Documentation/hwmon/sch5636 +++ /dev/null @@ -1,37 +0,0 @@ -Kernel driver sch5636 -===================== - -Supported chips: - - * SMSC SCH5636 - - Prefix: 'sch5636' - - Addresses scanned: none, address read from Super I/O config space - -Author: Hans de Goede - - -Description ------------ - -SMSC SCH5636 Super I/O chips include an embedded microcontroller for -hardware monitoring solutions, allowing motherboard manufacturers to create -their own custom hwmon solution based upon the SCH5636. - -Currently the sch5636 driver only supports the Fujitsu Theseus SCH5636 based -hwmon solution. The sch5636 driver runs a sanity check on loading to ensure -it is dealing with a Fujitsu Theseus and not with another custom SCH5636 based -hwmon solution. - -The Fujitsu Theseus can monitor up to 5 voltages, 8 fans and 16 -temperatures. Note that the driver detects how many fan headers / -temperature sensors are actually implemented on the motherboard, so you will -likely see fewer temperature and fan inputs. - -The Fujitsu Theseus hwmon solution also contains an integrated watchdog. -This watchdog is fully supported by the sch5636 driver. - -An application note describing the Theseus' registers, as well as an -application note describing the protocol for communicating with the -microcontroller is available upon request. Please mail me if you want a copy. diff --git a/Documentation/hwmon/sch5636.rst b/Documentation/hwmon/sch5636.rst new file mode 100644 index 000000000000..4aaee3672f13 --- /dev/null +++ b/Documentation/hwmon/sch5636.rst @@ -0,0 +1,37 @@ +Kernel driver sch5636 +===================== + +Supported chips: + + * SMSC SCH5636 + + Prefix: 'sch5636' + + Addresses scanned: none, address read from Super I/O config space + +Author: Hans de Goede + + +Description +----------- + +SMSC SCH5636 Super I/O chips include an embedded microcontroller for +hardware monitoring solutions, allowing motherboard manufacturers to create +their own custom hwmon solution based upon the SCH5636. + +Currently the sch5636 driver only supports the Fujitsu Theseus SCH5636 based +hwmon solution. The sch5636 driver runs a sanity check on loading to ensure +it is dealing with a Fujitsu Theseus and not with another custom SCH5636 based +hwmon solution. + +The Fujitsu Theseus can monitor up to 5 voltages, 8 fans and 16 +temperatures. Note that the driver detects how many fan headers / +temperature sensors are actually implemented on the motherboard, so you will +likely see fewer temperature and fan inputs. + +The Fujitsu Theseus hwmon solution also contains an integrated watchdog. +This watchdog is fully supported by the sch5636 driver. + +An application note describing the Theseus' registers, as well as an +application note describing the protocol for communicating with the +microcontroller is available upon request. Please mail me if you want a copy. diff --git a/Documentation/hwmon/scpi-hwmon b/Documentation/hwmon/scpi-hwmon deleted file mode 100644 index eee7022b44db..000000000000 --- a/Documentation/hwmon/scpi-hwmon +++ /dev/null @@ -1,36 +0,0 @@ -Kernel driver scpi-hwmon -======================== - -Supported chips: - - * Chips based on ARM System Control Processor Interface - - Addresses scanned: - - - Datasheet: http://infocenter.arm.com/help/index.jsp?topic=/com.arm.doc.dui0922b/index.html - -Author: Punit Agrawal - -Description ------------ - -This driver supports hardware monitoring for SoC's based on the ARM -System Control Processor (SCP) implementing the System Control -Processor Interface (SCPI). The following sensor types are supported -by the SCP: - - * temperature - * voltage - * current - * power - -The SCP interface provides an API to query the available sensors and -their values which are then exported to userspace by this driver. - -Usage Notes ------------ - -The driver relies on device tree node to indicate the presence of SCPI -support in the kernel. See -Documentation/devicetree/bindings/arm/arm,scpi.txt for details of the -devicetree node. diff --git a/Documentation/hwmon/scpi-hwmon.rst b/Documentation/hwmon/scpi-hwmon.rst new file mode 100644 index 000000000000..eee7022b44db --- /dev/null +++ b/Documentation/hwmon/scpi-hwmon.rst @@ -0,0 +1,36 @@ +Kernel driver scpi-hwmon +======================== + +Supported chips: + + * Chips based on ARM System Control Processor Interface + + Addresses scanned: - + + Datasheet: http://infocenter.arm.com/help/index.jsp?topic=/com.arm.doc.dui0922b/index.html + +Author: Punit Agrawal + +Description +----------- + +This driver supports hardware monitoring for SoC's based on the ARM +System Control Processor (SCP) implementing the System Control +Processor Interface (SCPI). The following sensor types are supported +by the SCP: + + * temperature + * voltage + * current + * power + +The SCP interface provides an API to query the available sensors and +their values which are then exported to userspace by this driver. + +Usage Notes +----------- + +The driver relies on device tree node to indicate the presence of SCPI +support in the kernel. See +Documentation/devicetree/bindings/arm/arm,scpi.txt for details of the +devicetree node. diff --git a/Documentation/hwmon/sht15 b/Documentation/hwmon/sht15 deleted file mode 100644 index 485abe037f6c..000000000000 --- a/Documentation/hwmon/sht15 +++ /dev/null @@ -1,83 +0,0 @@ -Kernel driver sht15 -=================== - -Authors: - - * Wouter Horre - * Jonathan Cameron - * Vivien Didelot - * Jerome Oufella - -Supported chips: - - * Sensirion SHT10 - - Prefix: 'sht10' - - * Sensirion SHT11 - - Prefix: 'sht11' - - * Sensirion SHT15 - - Prefix: 'sht15' - - * Sensirion SHT71 - - Prefix: 'sht71' - - * Sensirion SHT75 - - Prefix: 'sht75' - -Datasheet: Publicly available at the Sensirion website - - http://www.sensirion.ch/en/pdf/product_information/Datasheet-humidity-sensor-SHT1x.pdf - -Description ------------ - -The SHT10, SHT11, SHT15, SHT71, and SHT75 are humidity and temperature -sensors. - -The devices communicate using two GPIO lines. - -Supported resolutions for the measurements are 14 bits for temperature and 12 -bits for humidity, or 12 bits for temperature and 8 bits for humidity. - -The humidity calibration coefficients are programmed into an OTP memory on the -chip. These coefficients are used to internally calibrate the signals from the -sensors. Disabling the reload of those coefficients allows saving 10ms for each -measurement and decrease power consumption, while losing on precision. - -Some options may be set via sysfs attributes. - -Notes: - * The regulator supply name is set to "vcc". - * If a CRC validation fails, a soft reset command is sent, which resets - status register to its hardware default value, but the driver will try to - restore the previous device configuration. - -Platform data -------------- - -* checksum: - set it to true to enable CRC validation of the readings (default to false). -* no_otp_reload: - flag to indicate not to reload from OTP (default to false). -* low_resolution: - flag to indicate the temp/humidity resolution to use (default to false). - -Sysfs interface ---------------- - -================== ========================================================== -temp1_input temperature input -humidity1_input humidity input -heater_enable write 1 in this attribute to enable the on-chip heater, - 0 to disable it. Be careful not to enable the heater - for too long. -temp1_fault if 1, this means that the voltage is low (below 2.47V) and - measurement may be invalid. -humidity1_fault same as temp1_fault. -================== ========================================================== diff --git a/Documentation/hwmon/sht15.rst b/Documentation/hwmon/sht15.rst new file mode 100644 index 000000000000..485abe037f6c --- /dev/null +++ b/Documentation/hwmon/sht15.rst @@ -0,0 +1,83 @@ +Kernel driver sht15 +=================== + +Authors: + + * Wouter Horre + * Jonathan Cameron + * Vivien Didelot + * Jerome Oufella + +Supported chips: + + * Sensirion SHT10 + + Prefix: 'sht10' + + * Sensirion SHT11 + + Prefix: 'sht11' + + * Sensirion SHT15 + + Prefix: 'sht15' + + * Sensirion SHT71 + + Prefix: 'sht71' + + * Sensirion SHT75 + + Prefix: 'sht75' + +Datasheet: Publicly available at the Sensirion website + + http://www.sensirion.ch/en/pdf/product_information/Datasheet-humidity-sensor-SHT1x.pdf + +Description +----------- + +The SHT10, SHT11, SHT15, SHT71, and SHT75 are humidity and temperature +sensors. + +The devices communicate using two GPIO lines. + +Supported resolutions for the measurements are 14 bits for temperature and 12 +bits for humidity, or 12 bits for temperature and 8 bits for humidity. + +The humidity calibration coefficients are programmed into an OTP memory on the +chip. These coefficients are used to internally calibrate the signals from the +sensors. Disabling the reload of those coefficients allows saving 10ms for each +measurement and decrease power consumption, while losing on precision. + +Some options may be set via sysfs attributes. + +Notes: + * The regulator supply name is set to "vcc". + * If a CRC validation fails, a soft reset command is sent, which resets + status register to its hardware default value, but the driver will try to + restore the previous device configuration. + +Platform data +------------- + +* checksum: + set it to true to enable CRC validation of the readings (default to false). +* no_otp_reload: + flag to indicate not to reload from OTP (default to false). +* low_resolution: + flag to indicate the temp/humidity resolution to use (default to false). + +Sysfs interface +--------------- + +================== ========================================================== +temp1_input temperature input +humidity1_input humidity input +heater_enable write 1 in this attribute to enable the on-chip heater, + 0 to disable it. Be careful not to enable the heater + for too long. +temp1_fault if 1, this means that the voltage is low (below 2.47V) and + measurement may be invalid. +humidity1_fault same as temp1_fault. +================== ========================================================== diff --git a/Documentation/hwmon/sht21 b/Documentation/hwmon/sht21 deleted file mode 100644 index f1f5da030108..000000000000 --- a/Documentation/hwmon/sht21 +++ /dev/null @@ -1,68 +0,0 @@ -Kernel driver sht21 -=================== - -Supported chips: - - * Sensirion SHT21 - - Prefix: 'sht21' - - Addresses scanned: none - - Datasheet: Publicly available at the Sensirion website - - http://www.sensirion.com/file/datasheet_sht21 - - - - * Sensirion SHT25 - - Prefix: 'sht25' - - Addresses scanned: none - - Datasheet: Publicly available at the Sensirion website - - http://www.sensirion.com/file/datasheet_sht25 - - - -Author: - - Urs Fleisch - -Description ------------ - -The SHT21 and SHT25 are humidity and temperature sensors in a DFN package of -only 3 x 3 mm footprint and 1.1 mm height. The difference between the two -devices is the higher level of precision of the SHT25 (1.8% relative humidity, -0.2 degree Celsius) compared with the SHT21 (2.0% relative humidity, -0.3 degree Celsius). - -The devices communicate with the I2C protocol. All sensors are set to the same -I2C address 0x40, so an entry with I2C_BOARD_INFO("sht21", 0x40) can be used -in the board setup code. - -sysfs-Interface ---------------- - -temp1_input - - temperature input - -humidity1_input - - humidity input -eic - - Electronic Identification Code - -Notes ------ - -The driver uses the default resolution settings of 12 bit for humidity and 14 -bit for temperature, which results in typical measurement times of 22 ms for -humidity and 66 ms for temperature. To keep self heating below 0.1 degree -Celsius, the device should not be active for more than 10% of the time, -e.g. maximum two measurements per second at the given resolution. - -Different resolutions, the on-chip heater, and using the CRC checksum -are not supported yet. diff --git a/Documentation/hwmon/sht21.rst b/Documentation/hwmon/sht21.rst new file mode 100644 index 000000000000..f1f5da030108 --- /dev/null +++ b/Documentation/hwmon/sht21.rst @@ -0,0 +1,68 @@ +Kernel driver sht21 +=================== + +Supported chips: + + * Sensirion SHT21 + + Prefix: 'sht21' + + Addresses scanned: none + + Datasheet: Publicly available at the Sensirion website + + http://www.sensirion.com/file/datasheet_sht21 + + + + * Sensirion SHT25 + + Prefix: 'sht25' + + Addresses scanned: none + + Datasheet: Publicly available at the Sensirion website + + http://www.sensirion.com/file/datasheet_sht25 + + + +Author: + + Urs Fleisch + +Description +----------- + +The SHT21 and SHT25 are humidity and temperature sensors in a DFN package of +only 3 x 3 mm footprint and 1.1 mm height. The difference between the two +devices is the higher level of precision of the SHT25 (1.8% relative humidity, +0.2 degree Celsius) compared with the SHT21 (2.0% relative humidity, +0.3 degree Celsius). + +The devices communicate with the I2C protocol. All sensors are set to the same +I2C address 0x40, so an entry with I2C_BOARD_INFO("sht21", 0x40) can be used +in the board setup code. + +sysfs-Interface +--------------- + +temp1_input + - temperature input + +humidity1_input + - humidity input +eic + - Electronic Identification Code + +Notes +----- + +The driver uses the default resolution settings of 12 bit for humidity and 14 +bit for temperature, which results in typical measurement times of 22 ms for +humidity and 66 ms for temperature. To keep self heating below 0.1 degree +Celsius, the device should not be active for more than 10% of the time, +e.g. maximum two measurements per second at the given resolution. + +Different resolutions, the on-chip heater, and using the CRC checksum +are not supported yet. diff --git a/Documentation/hwmon/sht3x b/Documentation/hwmon/sht3x deleted file mode 100644 index 978a7117e4b2..000000000000 --- a/Documentation/hwmon/sht3x +++ /dev/null @@ -1,88 +0,0 @@ -Kernel driver sht3x -=================== - -Supported chips: - - * Sensirion SHT3x-DIS - - Prefix: 'sht3x' - - Addresses scanned: none - - Datasheet: https://www.sensirion.com/file/datasheet_sht3x_digital - -Author: - - - David Frey - - Pascal Sachs - -Description ------------ - -This driver implements support for the Sensirion SHT3x-DIS chip, a humidity -and temperature sensor. Temperature is measured in degrees celsius, relative -humidity is expressed as a percentage. In the sysfs interface, all values are -scaled by 1000, i.e. the value for 31.5 degrees celsius is 31500. - -The device communicates with the I2C protocol. Sensors can have the I2C -addresses 0x44 or 0x45, depending on the wiring. See -Documentation/i2c/instantiating-devices for methods to instantiate the device. - -There are two options configurable by means of sht3x_platform_data: - -1. blocking (pull the I2C clock line down while performing the measurement) or - non-blocking mode. Blocking mode will guarantee the fastest result but - the I2C bus will be busy during that time. By default, non-blocking mode - is used. Make sure clock-stretching works properly on your device if you - want to use blocking mode. -2. high or low accuracy. High accuracy is used by default and using it is - strongly recommended. - -The sht3x sensor supports a single shot mode as well as 5 periodic measure -modes, which can be controlled with the update_interval sysfs interface. -The allowed update_interval in milliseconds are as follows: - - ===== ======= ==================== - 0 single shot mode - 2000 0.5 Hz periodic measurement - 1000 1 Hz periodic measurement - 500 2 Hz periodic measurement - 250 4 Hz periodic measurement - 100 10 Hz periodic measurement - ===== ======= ==================== - -In the periodic measure mode, the sensor automatically triggers a measurement -with the configured update interval on the chip. When a temperature or humidity -reading exceeds the configured limits, the alert attribute is set to 1 and -the alert pin on the sensor is set to high. -When the temperature and humidity readings move back between the hysteresis -values, the alert bit is set to 0 and the alert pin on the sensor is set to -low. - -sysfs-Interface ---------------- - -=================== ============================================================ -temp1_input: temperature input -humidity1_input: humidity input -temp1_max: temperature max value -temp1_max_hyst: temperature hysteresis value for max limit -humidity1_max: humidity max value -humidity1_max_hyst: humidity hysteresis value for max limit -temp1_min: temperature min value -temp1_min_hyst: temperature hysteresis value for min limit -humidity1_min: humidity min value -humidity1_min_hyst: humidity hysteresis value for min limit -temp1_alarm: alarm flag is set to 1 if the temperature is outside the - configured limits. Alarm only works in periodic measure mode -humidity1_alarm: alarm flag is set to 1 if the humidity is outside the - configured limits. Alarm only works in periodic measure mode -heater_enable: heater enable, heating element removes excess humidity from - sensor: - - - 0: turned off - - 1: turned on -update_interval: update interval, 0 for single shot, interval in msec - for periodic measurement. If the interval is not supported - by the sensor, the next faster interval is chosen -=================== ============================================================ diff --git a/Documentation/hwmon/sht3x.rst b/Documentation/hwmon/sht3x.rst new file mode 100644 index 000000000000..978a7117e4b2 --- /dev/null +++ b/Documentation/hwmon/sht3x.rst @@ -0,0 +1,88 @@ +Kernel driver sht3x +=================== + +Supported chips: + + * Sensirion SHT3x-DIS + + Prefix: 'sht3x' + + Addresses scanned: none + + Datasheet: https://www.sensirion.com/file/datasheet_sht3x_digital + +Author: + + - David Frey + - Pascal Sachs + +Description +----------- + +This driver implements support for the Sensirion SHT3x-DIS chip, a humidity +and temperature sensor. Temperature is measured in degrees celsius, relative +humidity is expressed as a percentage. In the sysfs interface, all values are +scaled by 1000, i.e. the value for 31.5 degrees celsius is 31500. + +The device communicates with the I2C protocol. Sensors can have the I2C +addresses 0x44 or 0x45, depending on the wiring. See +Documentation/i2c/instantiating-devices for methods to instantiate the device. + +There are two options configurable by means of sht3x_platform_data: + +1. blocking (pull the I2C clock line down while performing the measurement) or + non-blocking mode. Blocking mode will guarantee the fastest result but + the I2C bus will be busy during that time. By default, non-blocking mode + is used. Make sure clock-stretching works properly on your device if you + want to use blocking mode. +2. high or low accuracy. High accuracy is used by default and using it is + strongly recommended. + +The sht3x sensor supports a single shot mode as well as 5 periodic measure +modes, which can be controlled with the update_interval sysfs interface. +The allowed update_interval in milliseconds are as follows: + + ===== ======= ==================== + 0 single shot mode + 2000 0.5 Hz periodic measurement + 1000 1 Hz periodic measurement + 500 2 Hz periodic measurement + 250 4 Hz periodic measurement + 100 10 Hz periodic measurement + ===== ======= ==================== + +In the periodic measure mode, the sensor automatically triggers a measurement +with the configured update interval on the chip. When a temperature or humidity +reading exceeds the configured limits, the alert attribute is set to 1 and +the alert pin on the sensor is set to high. +When the temperature and humidity readings move back between the hysteresis +values, the alert bit is set to 0 and the alert pin on the sensor is set to +low. + +sysfs-Interface +--------------- + +=================== ============================================================ +temp1_input: temperature input +humidity1_input: humidity input +temp1_max: temperature max value +temp1_max_hyst: temperature hysteresis value for max limit +humidity1_max: humidity max value +humidity1_max_hyst: humidity hysteresis value for max limit +temp1_min: temperature min value +temp1_min_hyst: temperature hysteresis value for min limit +humidity1_min: humidity min value +humidity1_min_hyst: humidity hysteresis value for min limit +temp1_alarm: alarm flag is set to 1 if the temperature is outside the + configured limits. Alarm only works in periodic measure mode +humidity1_alarm: alarm flag is set to 1 if the humidity is outside the + configured limits. Alarm only works in periodic measure mode +heater_enable: heater enable, heating element removes excess humidity from + sensor: + + - 0: turned off + - 1: turned on +update_interval: update interval, 0 for single shot, interval in msec + for periodic measurement. If the interval is not supported + by the sensor, the next faster interval is chosen +=================== ============================================================ diff --git a/Documentation/hwmon/shtc1 b/Documentation/hwmon/shtc1 deleted file mode 100644 index aa116332ba26..000000000000 --- a/Documentation/hwmon/shtc1 +++ /dev/null @@ -1,58 +0,0 @@ -Kernel driver shtc1 -=================== - -Supported chips: - - * Sensirion SHTC1 - - Prefix: 'shtc1' - - Addresses scanned: none - - Datasheet: http://www.sensirion.com/file/datasheet_shtc1 - - - - * Sensirion SHTW1 - - Prefix: 'shtw1' - - Addresses scanned: none - - Datasheet: Not publicly available - - - -Author: - - Johannes Winkelmann - -Description ------------ - -This driver implements support for the Sensirion SHTC1 chip, a humidity and -temperature sensor. Temperature is measured in degrees celsius, relative -humidity is expressed as a percentage. Driver can be used as well for SHTW1 -chip, which has the same electrical interface. - -The device communicates with the I2C protocol. All sensors are set to I2C -address 0x70. See Documentation/i2c/instantiating-devices for methods to -instantiate the device. - -There are two options configurable by means of shtc1_platform_data: - -1. blocking (pull the I2C clock line down while performing the measurement) or - non-blocking mode. Blocking mode will guarantee the fastest result but - the I2C bus will be busy during that time. By default, non-blocking mode - is used. Make sure clock-stretching works properly on your device if you - want to use blocking mode. -2. high or low accuracy. High accuracy is used by default and using it is - strongly recommended. - -sysfs-Interface ---------------- - -temp1_input - - temperature input -humidity1_input - - humidity input diff --git a/Documentation/hwmon/shtc1.rst b/Documentation/hwmon/shtc1.rst new file mode 100644 index 000000000000..aa116332ba26 --- /dev/null +++ b/Documentation/hwmon/shtc1.rst @@ -0,0 +1,58 @@ +Kernel driver shtc1 +=================== + +Supported chips: + + * Sensirion SHTC1 + + Prefix: 'shtc1' + + Addresses scanned: none + + Datasheet: http://www.sensirion.com/file/datasheet_shtc1 + + + + * Sensirion SHTW1 + + Prefix: 'shtw1' + + Addresses scanned: none + + Datasheet: Not publicly available + + + +Author: + + Johannes Winkelmann + +Description +----------- + +This driver implements support for the Sensirion SHTC1 chip, a humidity and +temperature sensor. Temperature is measured in degrees celsius, relative +humidity is expressed as a percentage. Driver can be used as well for SHTW1 +chip, which has the same electrical interface. + +The device communicates with the I2C protocol. All sensors are set to I2C +address 0x70. See Documentation/i2c/instantiating-devices for methods to +instantiate the device. + +There are two options configurable by means of shtc1_platform_data: + +1. blocking (pull the I2C clock line down while performing the measurement) or + non-blocking mode. Blocking mode will guarantee the fastest result but + the I2C bus will be busy during that time. By default, non-blocking mode + is used. Make sure clock-stretching works properly on your device if you + want to use blocking mode. +2. high or low accuracy. High accuracy is used by default and using it is + strongly recommended. + +sysfs-Interface +--------------- + +temp1_input + - temperature input +humidity1_input + - humidity input diff --git a/Documentation/hwmon/sis5595 b/Documentation/hwmon/sis5595 deleted file mode 100644 index 5acba6b0c0db..000000000000 --- a/Documentation/hwmon/sis5595 +++ /dev/null @@ -1,124 +0,0 @@ -Kernel driver sis5595 -===================== - -Supported chips: - - * Silicon Integrated Systems Corp. SiS5595 Southbridge Hardware Monitor - - Prefix: 'sis5595' - - Addresses scanned: ISA in PCI-space encoded address - - Datasheet: Publicly available at the Silicon Integrated Systems Corp. site. - - - -Authors: - - - Kyösti Mälkki , - - Mark D. Studebaker , - - Aurelien Jarno 2.6 port - - SiS southbridge has a LM78-like chip integrated on the same IC. - This driver is a customized copy of lm78.c - - Supports following revisions: - - =============== =============== ============== - Version PCI ID PCI Revision - =============== =============== ============== - 1 1039/0008 AF or less - 2 1039/0008 B0 or greater - =============== =============== ============== - - Note: these chips contain a 0008 device which is incompatible with the - 5595. We recognize these by the presence of the listed - "blacklist" PCI ID and refuse to load. - - =================== =============== ================ - NOT SUPPORTED PCI ID BLACKLIST PCI ID - =================== =============== ================ - 540 0008 0540 - 550 0008 0550 - 5513 0008 5511 - 5581 0008 5597 - 5582 0008 5597 - 5597 0008 5597 - 630 0008 0630 - 645 0008 0645 - 730 0008 0730 - 735 0008 0735 - =================== =============== ================ - - -Module Parameters ------------------ - -======================= ===================================================== -force_addr=0xaddr Set the I/O base address. Useful for boards - that don't set the address in the BIOS. Does not do a - PCI force; the device must still be present in lspci. - Don't use this unless the driver complains that the - base address is not set. - - Example: 'modprobe sis5595 force_addr=0x290' -======================= ===================================================== - - -Description ------------ - -The SiS5595 southbridge has integrated hardware monitor functions. It also -has an I2C bus, but this driver only supports the hardware monitor. For the -I2C bus driver see i2c-sis5595. - -The SiS5595 implements zero or one temperature sensor, two fan speed -sensors, four or five voltage sensors, and alarms. - -On the first version of the chip, there are four voltage sensors and one -temperature sensor. - -On the second version of the chip, the temperature sensor (temp) and the -fifth voltage sensor (in4) share a pin which is configurable, but not -through the driver. Sorry. The driver senses the configuration of the pin, -which was hopefully set by the BIOS. - -Temperatures are measured in degrees Celsius. An alarm is triggered once -when the max is crossed; it is also triggered when it drops below the min -value. Measurements are guaranteed between -55 and +125 degrees, with a -resolution of 1 degree. - -Fan rotation speeds are reported in RPM (rotations per minute). An alarm is -triggered if the rotation speed has dropped below a programmable limit. Fan -readings can be divided by a programmable divider (1, 2, 4 or 8) to give -the readings more range or accuracy. Not all RPM values can accurately be -represented, so some rounding is done. With a divider of 2, the lowest -representable value is around 2600 RPM. - -Voltage sensors (also known as IN sensors) report their values in volts. An -alarm is triggered if the voltage has crossed a programmable minimum or -maximum limit. Note that minimum in this case always means 'closest to -zero'; this is important for negative voltage measurements. All voltage -inputs can measure voltages between 0 and 4.08 volts, with a resolution of -0.016 volt. - -In addition to the alarms described above, there is a BTI alarm, which gets -triggered when an external chip has crossed its limits. Usually, this is -connected to some LM75-like chip; if at least one crosses its limits, this -bit gets set. - -If an alarm triggers, it will remain triggered until the hardware register -is read at least once. This means that the cause for the alarm may already -have disappeared! Note that in the current implementation, all hardware -registers are read whenever any data is read (unless it is less than 1.5 -seconds since the last update). This means that you can easily miss -once-only alarms. - -The SiS5595 only updates its values each 1.5 seconds; reading it more often -will do no harm, but will return 'old' values. - -Problems --------- -Some chips refuse to be enabled. We don't know why. -The driver will recognize this and print a message in dmesg. - diff --git a/Documentation/hwmon/sis5595.rst b/Documentation/hwmon/sis5595.rst new file mode 100644 index 000000000000..16123b3bfff9 --- /dev/null +++ b/Documentation/hwmon/sis5595.rst @@ -0,0 +1,123 @@ +Kernel driver sis5595 +===================== + +Supported chips: + + * Silicon Integrated Systems Corp. SiS5595 Southbridge Hardware Monitor + + Prefix: 'sis5595' + + Addresses scanned: ISA in PCI-space encoded address + + Datasheet: Publicly available at the Silicon Integrated Systems Corp. site. + + + +Authors: + + - Kyösti Mälkki , + - Mark D. Studebaker , + - Aurelien Jarno 2.6 port + + SiS southbridge has a LM78-like chip integrated on the same IC. + This driver is a customized copy of lm78.c + + Supports following revisions: + + =============== =============== ============== + Version PCI ID PCI Revision + =============== =============== ============== + 1 1039/0008 AF or less + 2 1039/0008 B0 or greater + =============== =============== ============== + + Note: these chips contain a 0008 device which is incompatible with the + 5595. We recognize these by the presence of the listed + "blacklist" PCI ID and refuse to load. + + =================== =============== ================ + NOT SUPPORTED PCI ID BLACKLIST PCI ID + =================== =============== ================ + 540 0008 0540 + 550 0008 0550 + 5513 0008 5511 + 5581 0008 5597 + 5582 0008 5597 + 5597 0008 5597 + 630 0008 0630 + 645 0008 0645 + 730 0008 0730 + 735 0008 0735 + =================== =============== ================ + + +Module Parameters +----------------- + +======================= ===================================================== +force_addr=0xaddr Set the I/O base address. Useful for boards + that don't set the address in the BIOS. Does not do a + PCI force; the device must still be present in lspci. + Don't use this unless the driver complains that the + base address is not set. + + Example: 'modprobe sis5595 force_addr=0x290' +======================= ===================================================== + + +Description +----------- + +The SiS5595 southbridge has integrated hardware monitor functions. It also +has an I2C bus, but this driver only supports the hardware monitor. For the +I2C bus driver see i2c-sis5595. + +The SiS5595 implements zero or one temperature sensor, two fan speed +sensors, four or five voltage sensors, and alarms. + +On the first version of the chip, there are four voltage sensors and one +temperature sensor. + +On the second version of the chip, the temperature sensor (temp) and the +fifth voltage sensor (in4) share a pin which is configurable, but not +through the driver. Sorry. The driver senses the configuration of the pin, +which was hopefully set by the BIOS. + +Temperatures are measured in degrees Celsius. An alarm is triggered once +when the max is crossed; it is also triggered when it drops below the min +value. Measurements are guaranteed between -55 and +125 degrees, with a +resolution of 1 degree. + +Fan rotation speeds are reported in RPM (rotations per minute). An alarm is +triggered if the rotation speed has dropped below a programmable limit. Fan +readings can be divided by a programmable divider (1, 2, 4 or 8) to give +the readings more range or accuracy. Not all RPM values can accurately be +represented, so some rounding is done. With a divider of 2, the lowest +representable value is around 2600 RPM. + +Voltage sensors (also known as IN sensors) report their values in volts. An +alarm is triggered if the voltage has crossed a programmable minimum or +maximum limit. Note that minimum in this case always means 'closest to +zero'; this is important for negative voltage measurements. All voltage +inputs can measure voltages between 0 and 4.08 volts, with a resolution of +0.016 volt. + +In addition to the alarms described above, there is a BTI alarm, which gets +triggered when an external chip has crossed its limits. Usually, this is +connected to some LM75-like chip; if at least one crosses its limits, this +bit gets set. + +If an alarm triggers, it will remain triggered until the hardware register +is read at least once. This means that the cause for the alarm may already +have disappeared! Note that in the current implementation, all hardware +registers are read whenever any data is read (unless it is less than 1.5 +seconds since the last update). This means that you can easily miss +once-only alarms. + +The SiS5595 only updates its values each 1.5 seconds; reading it more often +will do no harm, but will return 'old' values. + +Problems +-------- +Some chips refuse to be enabled. We don't know why. +The driver will recognize this and print a message in dmesg. diff --git a/Documentation/hwmon/smm665 b/Documentation/hwmon/smm665 deleted file mode 100644 index a0e27f62b57b..000000000000 --- a/Documentation/hwmon/smm665 +++ /dev/null @@ -1,187 +0,0 @@ -Kernel driver smm665 -==================== - -Supported chips: - - * Summit Microelectronics SMM465 - - Prefix: 'smm465' - - Addresses scanned: - - - Datasheet: - - http://www.summitmicro.com/prod_select/summary/SMM465/SMM465DS.pdf - - * Summit Microelectronics SMM665, SMM665B - - Prefix: 'smm665' - - Addresses scanned: - - - Datasheet: - - http://www.summitmicro.com/prod_select/summary/SMM665/SMM665B_2089_20.pdf - - * Summit Microelectronics SMM665C - - Prefix: 'smm665c' - - Addresses scanned: - - - Datasheet: - - http://www.summitmicro.com/prod_select/summary/SMM665C/SMM665C_2125.pdf - - * Summit Microelectronics SMM764 - - Prefix: 'smm764' - - Addresses scanned: - - - Datasheet: - - http://www.summitmicro.com/prod_select/summary/SMM764/SMM764_2098.pdf - - * Summit Microelectronics SMM766, SMM766B - - Prefix: 'smm766' - - Addresses scanned: - - - Datasheets: - - http://www.summitmicro.com/prod_select/summary/SMM766/SMM766_2086.pdf - - http://www.summitmicro.com/prod_select/summary/SMM766B/SMM766B_2122.pdf - -Author: Guenter Roeck - - -Module Parameters ------------------ - -* vref: int - Default: 1250 (mV) - - Reference voltage on VREF_ADC pin in mV. It should not be necessary to set - this parameter unless a non-default reference voltage is used. - - -Description ------------ - -[From datasheet] The SMM665 is an Active DC Output power supply Controller -that monitors, margins and cascade sequences power. The part monitors six -power supply channels as well as VDD, 12V input, two general-purpose analog -inputs and an internal temperature sensor using a 10-bit ADC. - -Each monitored channel has its own high and low limits, plus a critical -limit. - -Support for SMM465, SMM764, and SMM766 has been implemented but is untested. - - -Usage Notes ------------ - -This driver does not probe for devices, since there is no register which -can be safely used to identify the chip. You will have to instantiate -the devices explicitly. When instantiating the device, you have to specify -its configuration register address. - -Example: the following will load the driver for an SMM665 at address 0x57 -on I2C bus #1:: - - $ modprobe smm665 - $ echo smm665 0x57 > /sys/bus/i2c/devices/i2c-1/new_device - - -Sysfs entries -------------- - -This driver uses the values in the datasheet to convert ADC register values -into the values specified in the sysfs-interface document. All attributes are -read only. - -Min, max, lcrit, and crit values are used by the chip to trigger external signals -and/or other activity. Triggered signals can include HEALTHY, RST, Power Off, -or Fault depending on the chip configuration. The driver reports values as lcrit -or crit if exceeding the limits triggers RST, Power Off, or Fault, and as min or -max otherwise. For details please see the SMM665 datasheet. - -For SMM465 and SMM764, values for Channel E and F are reported but undefined. - -======================= ======================================================= -in1_input 12V input voltage (mV) -in2_input 3.3V (VDD) input voltage (mV) -in3_input Channel A voltage (mV) -in4_input Channel B voltage (mV) -in5_input Channel C voltage (mV) -in6_input Channel D voltage (mV) -in7_input Channel E voltage (mV) -in8_input Channel F voltage (mV) -in9_input AIN1 voltage (mV) -in10_input AIN2 voltage (mV) - -in1_min 12v input minimum voltage (mV) -in2_min 3.3V (VDD) input minimum voltage (mV) -in3_min Channel A minimum voltage (mV) -in4_min Channel B minimum voltage (mV) -in5_min Channel C minimum voltage (mV) -in6_min Channel D minimum voltage (mV) -in7_min Channel E minimum voltage (mV) -in8_min Channel F minimum voltage (mV) -in9_min AIN1 minimum voltage (mV) -in10_min AIN2 minimum voltage (mV) - -in1_max 12v input maximum voltage (mV) -in2_max 3.3V (VDD) input maximum voltage (mV) -in3_max Channel A maximum voltage (mV) -in4_max Channel B maximum voltage (mV) -in5_max Channel C maximum voltage (mV) -in6_max Channel D maximum voltage (mV) -in7_max Channel E maximum voltage (mV) -in8_max Channel F maximum voltage (mV) -in9_max AIN1 maximum voltage (mV) -in10_max AIN2 maximum voltage (mV) - -in1_lcrit 12v input critical minimum voltage (mV) -in2_lcrit 3.3V (VDD) input critical minimum voltage (mV) -in3_lcrit Channel A critical minimum voltage (mV) -in4_lcrit Channel B critical minimum voltage (mV) -in5_lcrit Channel C critical minimum voltage (mV) -in6_lcrit Channel D critical minimum voltage (mV) -in7_lcrit Channel E critical minimum voltage (mV) -in8_lcrit Channel F critical minimum voltage (mV) -in9_lcrit AIN1 critical minimum voltage (mV) -in10_lcrit AIN2 critical minimum voltage (mV) - -in1_crit 12v input critical maximum voltage (mV) -in2_crit 3.3V (VDD) input critical maximum voltage (mV) -in3_crit Channel A critical maximum voltage (mV) -in4_crit Channel B critical maximum voltage (mV) -in5_crit Channel C critical maximum voltage (mV) -in6_crit Channel D critical maximum voltage (mV) -in7_crit Channel E critical maximum voltage (mV) -in8_crit Channel F critical maximum voltage (mV) -in9_crit AIN1 critical maximum voltage (mV) -in10_crit AIN2 critical maximum voltage (mV) - -in1_crit_alarm 12v input critical alarm -in2_crit_alarm 3.3V (VDD) input critical alarm -in3_crit_alarm Channel A critical alarm -in4_crit_alarm Channel B critical alarm -in5_crit_alarm Channel C critical alarm -in6_crit_alarm Channel D critical alarm -in7_crit_alarm Channel E critical alarm -in8_crit_alarm Channel F critical alarm -in9_crit_alarm AIN1 critical alarm -in10_crit_alarm AIN2 critical alarm - -temp1_input Chip temperature -temp1_min Mimimum chip temperature -temp1_max Maximum chip temperature -temp1_crit Critical chip temperature -temp1_crit_alarm Temperature critical alarm -======================= ======================================================= diff --git a/Documentation/hwmon/smm665.rst b/Documentation/hwmon/smm665.rst new file mode 100644 index 000000000000..a0e27f62b57b --- /dev/null +++ b/Documentation/hwmon/smm665.rst @@ -0,0 +1,187 @@ +Kernel driver smm665 +==================== + +Supported chips: + + * Summit Microelectronics SMM465 + + Prefix: 'smm465' + + Addresses scanned: - + + Datasheet: + + http://www.summitmicro.com/prod_select/summary/SMM465/SMM465DS.pdf + + * Summit Microelectronics SMM665, SMM665B + + Prefix: 'smm665' + + Addresses scanned: - + + Datasheet: + + http://www.summitmicro.com/prod_select/summary/SMM665/SMM665B_2089_20.pdf + + * Summit Microelectronics SMM665C + + Prefix: 'smm665c' + + Addresses scanned: - + + Datasheet: + + http://www.summitmicro.com/prod_select/summary/SMM665C/SMM665C_2125.pdf + + * Summit Microelectronics SMM764 + + Prefix: 'smm764' + + Addresses scanned: - + + Datasheet: + + http://www.summitmicro.com/prod_select/summary/SMM764/SMM764_2098.pdf + + * Summit Microelectronics SMM766, SMM766B + + Prefix: 'smm766' + + Addresses scanned: - + + Datasheets: + + http://www.summitmicro.com/prod_select/summary/SMM766/SMM766_2086.pdf + + http://www.summitmicro.com/prod_select/summary/SMM766B/SMM766B_2122.pdf + +Author: Guenter Roeck + + +Module Parameters +----------------- + +* vref: int + Default: 1250 (mV) + + Reference voltage on VREF_ADC pin in mV. It should not be necessary to set + this parameter unless a non-default reference voltage is used. + + +Description +----------- + +[From datasheet] The SMM665 is an Active DC Output power supply Controller +that monitors, margins and cascade sequences power. The part monitors six +power supply channels as well as VDD, 12V input, two general-purpose analog +inputs and an internal temperature sensor using a 10-bit ADC. + +Each monitored channel has its own high and low limits, plus a critical +limit. + +Support for SMM465, SMM764, and SMM766 has been implemented but is untested. + + +Usage Notes +----------- + +This driver does not probe for devices, since there is no register which +can be safely used to identify the chip. You will have to instantiate +the devices explicitly. When instantiating the device, you have to specify +its configuration register address. + +Example: the following will load the driver for an SMM665 at address 0x57 +on I2C bus #1:: + + $ modprobe smm665 + $ echo smm665 0x57 > /sys/bus/i2c/devices/i2c-1/new_device + + +Sysfs entries +------------- + +This driver uses the values in the datasheet to convert ADC register values +into the values specified in the sysfs-interface document. All attributes are +read only. + +Min, max, lcrit, and crit values are used by the chip to trigger external signals +and/or other activity. Triggered signals can include HEALTHY, RST, Power Off, +or Fault depending on the chip configuration. The driver reports values as lcrit +or crit if exceeding the limits triggers RST, Power Off, or Fault, and as min or +max otherwise. For details please see the SMM665 datasheet. + +For SMM465 and SMM764, values for Channel E and F are reported but undefined. + +======================= ======================================================= +in1_input 12V input voltage (mV) +in2_input 3.3V (VDD) input voltage (mV) +in3_input Channel A voltage (mV) +in4_input Channel B voltage (mV) +in5_input Channel C voltage (mV) +in6_input Channel D voltage (mV) +in7_input Channel E voltage (mV) +in8_input Channel F voltage (mV) +in9_input AIN1 voltage (mV) +in10_input AIN2 voltage (mV) + +in1_min 12v input minimum voltage (mV) +in2_min 3.3V (VDD) input minimum voltage (mV) +in3_min Channel A minimum voltage (mV) +in4_min Channel B minimum voltage (mV) +in5_min Channel C minimum voltage (mV) +in6_min Channel D minimum voltage (mV) +in7_min Channel E minimum voltage (mV) +in8_min Channel F minimum voltage (mV) +in9_min AIN1 minimum voltage (mV) +in10_min AIN2 minimum voltage (mV) + +in1_max 12v input maximum voltage (mV) +in2_max 3.3V (VDD) input maximum voltage (mV) +in3_max Channel A maximum voltage (mV) +in4_max Channel B maximum voltage (mV) +in5_max Channel C maximum voltage (mV) +in6_max Channel D maximum voltage (mV) +in7_max Channel E maximum voltage (mV) +in8_max Channel F maximum voltage (mV) +in9_max AIN1 maximum voltage (mV) +in10_max AIN2 maximum voltage (mV) + +in1_lcrit 12v input critical minimum voltage (mV) +in2_lcrit 3.3V (VDD) input critical minimum voltage (mV) +in3_lcrit Channel A critical minimum voltage (mV) +in4_lcrit Channel B critical minimum voltage (mV) +in5_lcrit Channel C critical minimum voltage (mV) +in6_lcrit Channel D critical minimum voltage (mV) +in7_lcrit Channel E critical minimum voltage (mV) +in8_lcrit Channel F critical minimum voltage (mV) +in9_lcrit AIN1 critical minimum voltage (mV) +in10_lcrit AIN2 critical minimum voltage (mV) + +in1_crit 12v input critical maximum voltage (mV) +in2_crit 3.3V (VDD) input critical maximum voltage (mV) +in3_crit Channel A critical maximum voltage (mV) +in4_crit Channel B critical maximum voltage (mV) +in5_crit Channel C critical maximum voltage (mV) +in6_crit Channel D critical maximum voltage (mV) +in7_crit Channel E critical maximum voltage (mV) +in8_crit Channel F critical maximum voltage (mV) +in9_crit AIN1 critical maximum voltage (mV) +in10_crit AIN2 critical maximum voltage (mV) + +in1_crit_alarm 12v input critical alarm +in2_crit_alarm 3.3V (VDD) input critical alarm +in3_crit_alarm Channel A critical alarm +in4_crit_alarm Channel B critical alarm +in5_crit_alarm Channel C critical alarm +in6_crit_alarm Channel D critical alarm +in7_crit_alarm Channel E critical alarm +in8_crit_alarm Channel F critical alarm +in9_crit_alarm AIN1 critical alarm +in10_crit_alarm AIN2 critical alarm + +temp1_input Chip temperature +temp1_min Mimimum chip temperature +temp1_max Maximum chip temperature +temp1_crit Critical chip temperature +temp1_crit_alarm Temperature critical alarm +======================= ======================================================= diff --git a/Documentation/hwmon/smsc47b397 b/Documentation/hwmon/smsc47b397 deleted file mode 100644 index 600194cf1804..000000000000 --- a/Documentation/hwmon/smsc47b397 +++ /dev/null @@ -1,197 +0,0 @@ -Kernel driver smsc47b397 -======================== - -Supported chips: - - * SMSC LPC47B397-NC - - * SMSC SCH5307-NS - - * SMSC SCH5317 - - Prefix: 'smsc47b397' - - Addresses scanned: none, address read from Super I/O config space - - Datasheet: In this file - -Authors: - - - Mark M. Hoffman - - Utilitek Systems, Inc. - -November 23, 2004 - -The following specification describes the SMSC LPC47B397-NC [1]_ sensor chip -(for which there is no public datasheet available). This document was -provided by Craig Kelly (In-Store Broadcast Network) and edited/corrected -by Mark M. Hoffman . - -.. [1] And SMSC SCH5307-NS and SCH5317, which have different device IDs but are - otherwise compatible. - -------------------------------------------------------------------------- - -Methods for detecting the HP SIO and reading the thermal data on a dc7100 -------------------------------------------------------------------------- - -The thermal information on the dc7100 is contained in the SIO Hardware Monitor -(HWM). The information is accessed through an index/data pair. The index/data -pair is located at the HWM Base Address + 0 and the HWM Base Address + 1. The -HWM Base address can be obtained from Logical Device 8, registers 0x60 (MSB) -and 0x61 (LSB). Currently we are using 0x480 for the HWM Base Address and -0x480 and 0x481 for the index/data pair. - -Reading temperature information. -The temperature information is located in the following registers: - -=============== ======= ======================================================= -Temp1 0x25 (Currently, this reflects the CPU temp on all systems). -Temp2 0x26 -Temp3 0x27 -Temp4 0x80 -=============== ======= ======================================================= - -Programming Example -The following is an example of how to read the HWM temperature registers:: - - MOV DX,480H - MOV AX,25H - OUT DX,AL - MOV DX,481H - IN AL,DX - -AL contains the data in hex, the temperature in Celsius is the decimal -equivalent. - -Ex: If AL contains 0x2A, the temperature is 42 degrees C. - -Reading tach information. -The fan speed information is located in the following registers: - -=============== ======= ======= ================================= - LSB MSB -Tach1 0x28 0x29 (Currently, this reflects the CPU - fan speed on all systems). -Tach2 0x2A 0x2B -Tach3 0x2C 0x2D -Tach4 0x2E 0x2F -=============== ======= ======= ================================= - -.. Important:: - - Reading the tach LSB locks the tach MSB. - The LSB Must be read first. - -How to convert the tach reading to RPM --------------------------------------- - -The tach reading (TCount) is given by: (Tach MSB * 256) + (Tach LSB) -The SIO counts the number of 90kHz (11.111us) pulses per revolution. -RPM = 60/(TCount * 11.111us) - -Example:: - - Reg 0x28 = 0x9B - Reg 0x29 = 0x08 - -TCount = 0x89B = 2203 - -RPM = 60 / (2203 * 11.11111 E-6) = 2451 RPM - -Obtaining the SIO version. - -Configuration Sequence ----------------------- - -To program the configuration registers, the following sequence must be followed: -1. Enter Configuration Mode -2. Configure the Configuration Registers -3. Exit Configuration Mode. - -Enter Configuration Mode -^^^^^^^^^^^^^^^^^^^^^^^^ - -To place the chip into the Configuration State The config key (0x55) is written -to the CONFIG PORT (0x2E). - -Configuration Mode -^^^^^^^^^^^^^^^^^^ - -In configuration mode, the INDEX PORT is located at the CONFIG PORT address and -the DATA PORT is at INDEX PORT address + 1. - -The desired configuration registers are accessed in two steps: - -a. Write the index of the Logical Device Number Configuration Register - (i.e., 0x07) to the INDEX PORT and then write the number of the - desired logical device to the DATA PORT. - -b. Write the address of the desired configuration register within the - logical device to the INDEX PORT and then write or read the config- - uration register through the DATA PORT. - -Note: - If accessing the Global Configuration Registers, step (a) is not required. - -Exit Configuration Mode -^^^^^^^^^^^^^^^^^^^^^^^ - -To exit the Configuration State the write 0xAA to the CONFIG PORT (0x2E). -The chip returns to the RUN State. (This is important). - -Programming Example -^^^^^^^^^^^^^^^^^^^ - -The following is an example of how to read the SIO Device ID located at 0x20: - - ; ENTER CONFIGURATION MODE - MOV DX,02EH - MOV AX,055H - OUT DX,AL - ; GLOBAL CONFIGURATION REGISTER - MOV DX,02EH - MOV AL,20H - OUT DX,AL - ; READ THE DATA - MOV DX,02FH - IN AL,DX - ; EXIT CONFIGURATION MODE - MOV DX,02EH - MOV AX,0AAH - OUT DX,AL - -The registers of interest for identifying the SIO on the dc7100 are Device ID -(0x20) and Device Rev (0x21). - -The Device ID will read 0x6F (0x81 for SCH5307-NS, and 0x85 for SCH5317) -The Device Rev currently reads 0x01 - -Obtaining the HWM Base Address ------------------------------- - -The following is an example of how to read the HWM Base Address located in -Logical Device 8:: - - ; ENTER CONFIGURATION MODE - MOV DX,02EH - MOV AX,055H - OUT DX,AL - ; CONFIGURE REGISTER CRE0, - ; LOGICAL DEVICE 8 - MOV DX,02EH - MOV AL,07H - OUT DX,AL ;Point to LD# Config Reg - MOV DX,02FH - MOV AL, 08H - OUT DX,AL;Point to Logical Device 8 - ; - MOV DX,02EH - MOV AL,60H - OUT DX,AL ; Point to HWM Base Addr MSB - MOV DX,02FH - IN AL,DX ; Get MSB of HWM Base Addr - ; EXIT CONFIGURATION MODE - MOV DX,02EH - MOV AX,0AAH - OUT DX,AL diff --git a/Documentation/hwmon/smsc47b397.rst b/Documentation/hwmon/smsc47b397.rst new file mode 100644 index 000000000000..600194cf1804 --- /dev/null +++ b/Documentation/hwmon/smsc47b397.rst @@ -0,0 +1,197 @@ +Kernel driver smsc47b397 +======================== + +Supported chips: + + * SMSC LPC47B397-NC + + * SMSC SCH5307-NS + + * SMSC SCH5317 + + Prefix: 'smsc47b397' + + Addresses scanned: none, address read from Super I/O config space + + Datasheet: In this file + +Authors: + + - Mark M. Hoffman + - Utilitek Systems, Inc. + +November 23, 2004 + +The following specification describes the SMSC LPC47B397-NC [1]_ sensor chip +(for which there is no public datasheet available). This document was +provided by Craig Kelly (In-Store Broadcast Network) and edited/corrected +by Mark M. Hoffman . + +.. [1] And SMSC SCH5307-NS and SCH5317, which have different device IDs but are + otherwise compatible. + +------------------------------------------------------------------------- + +Methods for detecting the HP SIO and reading the thermal data on a dc7100 +------------------------------------------------------------------------- + +The thermal information on the dc7100 is contained in the SIO Hardware Monitor +(HWM). The information is accessed through an index/data pair. The index/data +pair is located at the HWM Base Address + 0 and the HWM Base Address + 1. The +HWM Base address can be obtained from Logical Device 8, registers 0x60 (MSB) +and 0x61 (LSB). Currently we are using 0x480 for the HWM Base Address and +0x480 and 0x481 for the index/data pair. + +Reading temperature information. +The temperature information is located in the following registers: + +=============== ======= ======================================================= +Temp1 0x25 (Currently, this reflects the CPU temp on all systems). +Temp2 0x26 +Temp3 0x27 +Temp4 0x80 +=============== ======= ======================================================= + +Programming Example +The following is an example of how to read the HWM temperature registers:: + + MOV DX,480H + MOV AX,25H + OUT DX,AL + MOV DX,481H + IN AL,DX + +AL contains the data in hex, the temperature in Celsius is the decimal +equivalent. + +Ex: If AL contains 0x2A, the temperature is 42 degrees C. + +Reading tach information. +The fan speed information is located in the following registers: + +=============== ======= ======= ================================= + LSB MSB +Tach1 0x28 0x29 (Currently, this reflects the CPU + fan speed on all systems). +Tach2 0x2A 0x2B +Tach3 0x2C 0x2D +Tach4 0x2E 0x2F +=============== ======= ======= ================================= + +.. Important:: + + Reading the tach LSB locks the tach MSB. + The LSB Must be read first. + +How to convert the tach reading to RPM +-------------------------------------- + +The tach reading (TCount) is given by: (Tach MSB * 256) + (Tach LSB) +The SIO counts the number of 90kHz (11.111us) pulses per revolution. +RPM = 60/(TCount * 11.111us) + +Example:: + + Reg 0x28 = 0x9B + Reg 0x29 = 0x08 + +TCount = 0x89B = 2203 + +RPM = 60 / (2203 * 11.11111 E-6) = 2451 RPM + +Obtaining the SIO version. + +Configuration Sequence +---------------------- + +To program the configuration registers, the following sequence must be followed: +1. Enter Configuration Mode +2. Configure the Configuration Registers +3. Exit Configuration Mode. + +Enter Configuration Mode +^^^^^^^^^^^^^^^^^^^^^^^^ + +To place the chip into the Configuration State The config key (0x55) is written +to the CONFIG PORT (0x2E). + +Configuration Mode +^^^^^^^^^^^^^^^^^^ + +In configuration mode, the INDEX PORT is located at the CONFIG PORT address and +the DATA PORT is at INDEX PORT address + 1. + +The desired configuration registers are accessed in two steps: + +a. Write the index of the Logical Device Number Configuration Register + (i.e., 0x07) to the INDEX PORT and then write the number of the + desired logical device to the DATA PORT. + +b. Write the address of the desired configuration register within the + logical device to the INDEX PORT and then write or read the config- + uration register through the DATA PORT. + +Note: + If accessing the Global Configuration Registers, step (a) is not required. + +Exit Configuration Mode +^^^^^^^^^^^^^^^^^^^^^^^ + +To exit the Configuration State the write 0xAA to the CONFIG PORT (0x2E). +The chip returns to the RUN State. (This is important). + +Programming Example +^^^^^^^^^^^^^^^^^^^ + +The following is an example of how to read the SIO Device ID located at 0x20: + + ; ENTER CONFIGURATION MODE + MOV DX,02EH + MOV AX,055H + OUT DX,AL + ; GLOBAL CONFIGURATION REGISTER + MOV DX,02EH + MOV AL,20H + OUT DX,AL + ; READ THE DATA + MOV DX,02FH + IN AL,DX + ; EXIT CONFIGURATION MODE + MOV DX,02EH + MOV AX,0AAH + OUT DX,AL + +The registers of interest for identifying the SIO on the dc7100 are Device ID +(0x20) and Device Rev (0x21). + +The Device ID will read 0x6F (0x81 for SCH5307-NS, and 0x85 for SCH5317) +The Device Rev currently reads 0x01 + +Obtaining the HWM Base Address +------------------------------ + +The following is an example of how to read the HWM Base Address located in +Logical Device 8:: + + ; ENTER CONFIGURATION MODE + MOV DX,02EH + MOV AX,055H + OUT DX,AL + ; CONFIGURE REGISTER CRE0, + ; LOGICAL DEVICE 8 + MOV DX,02EH + MOV AL,07H + OUT DX,AL ;Point to LD# Config Reg + MOV DX,02FH + MOV AL, 08H + OUT DX,AL;Point to Logical Device 8 + ; + MOV DX,02EH + MOV AL,60H + OUT DX,AL ; Point to HWM Base Addr MSB + MOV DX,02FH + IN AL,DX ; Get MSB of HWM Base Addr + ; EXIT CONFIGURATION MODE + MOV DX,02EH + MOV AX,0AAH + OUT DX,AL diff --git a/Documentation/hwmon/smsc47m1 b/Documentation/hwmon/smsc47m1 deleted file mode 100644 index c54eabd5eb57..000000000000 --- a/Documentation/hwmon/smsc47m1 +++ /dev/null @@ -1,86 +0,0 @@ -Kernel driver smsc47m1 -====================== - -Supported chips: - - * SMSC LPC47B27x, LPC47M112, LPC47M10x, LPC47M13x, LPC47M14x, - - LPC47M15x and LPC47M192 - - Addresses scanned: none, address read from Super I/O config space - - Prefix: 'smsc47m1' - - Datasheets: - - http://www.smsc.com/media/Downloads_Public/Data_Sheets/47b272.pdf - - http://www.smsc.com/media/Downloads_Public/Data_Sheets/47m10x.pdf - - http://www.smsc.com/media/Downloads_Public/Data_Sheets/47m112.pdf - - http://www.smsc.com/ - - * SMSC LPC47M292 - - Addresses scanned: none, address read from Super I/O config space - - Prefix: 'smsc47m2' - - Datasheet: Not public - - * SMSC LPC47M997 - - Addresses scanned: none, address read from Super I/O config space - - Prefix: 'smsc47m1' - - Datasheet: none - - - -Authors: - - - Mark D. Studebaker , - - With assistance from Bruce Allen , and his - fan.c program: - - - http://www.lsc-group.phys.uwm.edu/%7Eballen/driver/ - - - Gabriele Gorla , - - Jean Delvare - -Description ------------ - -The Standard Microsystems Corporation (SMSC) 47M1xx Super I/O chips -contain monitoring and PWM control circuitry for two fans. - -The LPC47M15x, LPC47M192 and LPC47M292 chips contain a full 'hardware -monitoring block' in addition to the fan monitoring and control. The -hardware monitoring block is not supported by this driver, use the -smsc47m192 driver for that. - -No documentation is available for the 47M997, but it has the same device -ID as the 47M15x and 47M192 chips and seems to be compatible. - -Fan rotation speeds are reported in RPM (rotations per minute). An alarm is -triggered if the rotation speed has dropped below a programmable limit. Fan -readings can be divided by a programmable divider (1, 2, 4 or 8) to give -the readings more range or accuracy. Not all RPM values can accurately be -represented, so some rounding is done. With a divider of 2, the lowest -representable value is around 2600 RPM. - -PWM values are from 0 to 255. - -If an alarm triggers, it will remain triggered until the hardware register -is read at least once. This means that the cause for the alarm may -already have disappeared! Note that in the current implementation, all -hardware registers are read whenever any data is read (unless it is less -than 1.5 seconds since the last update). This means that you can easily -miss once-only alarms. - ------------------------------------------------------------------- - -The lm_sensors project gratefully acknowledges the support of -Intel in the development of this driver. diff --git a/Documentation/hwmon/smsc47m1.rst b/Documentation/hwmon/smsc47m1.rst new file mode 100644 index 000000000000..c54eabd5eb57 --- /dev/null +++ b/Documentation/hwmon/smsc47m1.rst @@ -0,0 +1,86 @@ +Kernel driver smsc47m1 +====================== + +Supported chips: + + * SMSC LPC47B27x, LPC47M112, LPC47M10x, LPC47M13x, LPC47M14x, + + LPC47M15x and LPC47M192 + + Addresses scanned: none, address read from Super I/O config space + + Prefix: 'smsc47m1' + + Datasheets: + + http://www.smsc.com/media/Downloads_Public/Data_Sheets/47b272.pdf + + http://www.smsc.com/media/Downloads_Public/Data_Sheets/47m10x.pdf + + http://www.smsc.com/media/Downloads_Public/Data_Sheets/47m112.pdf + + http://www.smsc.com/ + + * SMSC LPC47M292 + + Addresses scanned: none, address read from Super I/O config space + + Prefix: 'smsc47m2' + + Datasheet: Not public + + * SMSC LPC47M997 + + Addresses scanned: none, address read from Super I/O config space + + Prefix: 'smsc47m1' + + Datasheet: none + + + +Authors: + + - Mark D. Studebaker , + - With assistance from Bruce Allen , and his + fan.c program: + + - http://www.lsc-group.phys.uwm.edu/%7Eballen/driver/ + + - Gabriele Gorla , + - Jean Delvare + +Description +----------- + +The Standard Microsystems Corporation (SMSC) 47M1xx Super I/O chips +contain monitoring and PWM control circuitry for two fans. + +The LPC47M15x, LPC47M192 and LPC47M292 chips contain a full 'hardware +monitoring block' in addition to the fan monitoring and control. The +hardware monitoring block is not supported by this driver, use the +smsc47m192 driver for that. + +No documentation is available for the 47M997, but it has the same device +ID as the 47M15x and 47M192 chips and seems to be compatible. + +Fan rotation speeds are reported in RPM (rotations per minute). An alarm is +triggered if the rotation speed has dropped below a programmable limit. Fan +readings can be divided by a programmable divider (1, 2, 4 or 8) to give +the readings more range or accuracy. Not all RPM values can accurately be +represented, so some rounding is done. With a divider of 2, the lowest +representable value is around 2600 RPM. + +PWM values are from 0 to 255. + +If an alarm triggers, it will remain triggered until the hardware register +is read at least once. This means that the cause for the alarm may +already have disappeared! Note that in the current implementation, all +hardware registers are read whenever any data is read (unless it is less +than 1.5 seconds since the last update). This means that you can easily +miss once-only alarms. + +------------------------------------------------------------------ + +The lm_sensors project gratefully acknowledges the support of +Intel in the development of this driver. diff --git a/Documentation/hwmon/smsc47m192 b/Documentation/hwmon/smsc47m192 deleted file mode 100644 index a2e86ab67918..000000000000 --- a/Documentation/hwmon/smsc47m192 +++ /dev/null @@ -1,116 +0,0 @@ -Kernel driver smsc47m192 -======================== - -Supported chips: - - * SMSC LPC47M192, LPC47M15x, LPC47M292 and LPC47M997 - - Prefix: 'smsc47m192' - - Addresses scanned: I2C 0x2c - 0x2d - - Datasheet: The datasheet for LPC47M192 is publicly available from - - http://www.smsc.com/ - - The LPC47M15x, LPC47M292 and LPC47M997 are compatible for - - hardware monitoring. - - - -Author: - - Hartmut Rick - - - Special thanks to Jean Delvare for careful checking - of the code and many helpful comments and suggestions. - - -Description ------------ - -This driver implements support for the hardware sensor capabilities -of the SMSC LPC47M192 and compatible Super-I/O chips. - -These chips support 3 temperature channels and 8 voltage inputs -as well as CPU voltage VID input. - -They do also have fan monitoring and control capabilities, but the -these features are accessed via ISA bus and are not supported by this -driver. Use the 'smsc47m1' driver for fan monitoring and control. - -Voltages and temperatures are measured by an 8-bit ADC, the resolution -of the temperatures is 1 bit per degree C. -Voltages are scaled such that the nominal voltage corresponds to -192 counts, i.e. 3/4 of the full range. Thus the available range for -each voltage channel is 0V ... 255/192*(nominal voltage), the resolution -is 1 bit per (nominal voltage)/192. -Both voltage and temperature values are scaled by 1000, the sys files -show voltages in mV and temperatures in units of 0.001 degC. - -The +12V analog voltage input channel (in4_input) is multiplexed with -bit 4 of the encoded CPU voltage. This means that you either get -a +12V voltage measurement or a 5 bit CPU VID, but not both. -The default setting is to use the pin as 12V input, and use only 4 bit VID. -This driver assumes that the information in the configuration register -is correct, i.e. that the BIOS has updated the configuration if -the motherboard has this input wired to VID4. - -The temperature and voltage readings are updated once every 1.5 seconds. -Reading them more often repeats the same values. - - -sysfs interface ---------------- - -===================== ========================================================== -in0_input +2.5V voltage input -in1_input CPU voltage input (nominal 2.25V) -in2_input +3.3V voltage input -in3_input +5V voltage input -in4_input +12V voltage input (may be missing if used as VID4) -in5_input Vcc voltage input (nominal 3.3V) - This is the supply voltage of the sensor chip itself. -in6_input +1.5V voltage input -in7_input +1.8V voltage input - -in[0-7]_min, -in[0-7]_max lower and upper alarm thresholds for in[0-7]_input reading - - All voltages are read and written in mV. - -in[0-7]_alarm alarm flags for voltage inputs - These files read '1' in case of alarm, '0' otherwise. - -temp1_input chip temperature measured by on-chip diode -temp[2-3]_input temperature measured by external diodes (one of these - would typically be wired to the diode inside the CPU) - -temp[1-3]_min, -temp[1-3]_max lower and upper alarm thresholds for temperatures - -temp[1-3]_offset temperature offset registers - The chip adds the offsets stored in these registers to - the corresponding temperature readings. - Note that temp1 and temp2 offsets share the same register, - they cannot both be different from zero at the same time. - Writing a non-zero number to one of them will reset the other - offset to zero. - - All temperatures and offsets are read and written in - units of 0.001 degC. - -temp[1-3]_alarm alarm flags for temperature inputs, '1' in case of alarm, - '0' otherwise. -temp[2-3]_input_fault diode fault flags for temperature inputs 2 and 3. - A fault is detected if the two pins for the corresponding - sensor are open or shorted, or any of the two is shorted - to ground or Vcc. '1' indicates a diode fault. - -cpu0_vid CPU voltage as received from the CPU - -vrm CPU VID standard used for decoding CPU voltage -===================== ========================================================== - -The `*_min`, `*_max`, `*_offset` and `vrm` files can be read and written, -all others are read-only. diff --git a/Documentation/hwmon/smsc47m192.rst b/Documentation/hwmon/smsc47m192.rst new file mode 100644 index 000000000000..a2e86ab67918 --- /dev/null +++ b/Documentation/hwmon/smsc47m192.rst @@ -0,0 +1,116 @@ +Kernel driver smsc47m192 +======================== + +Supported chips: + + * SMSC LPC47M192, LPC47M15x, LPC47M292 and LPC47M997 + + Prefix: 'smsc47m192' + + Addresses scanned: I2C 0x2c - 0x2d + + Datasheet: The datasheet for LPC47M192 is publicly available from + + http://www.smsc.com/ + + The LPC47M15x, LPC47M292 and LPC47M997 are compatible for + + hardware monitoring. + + + +Author: + - Hartmut Rick + + - Special thanks to Jean Delvare for careful checking + of the code and many helpful comments and suggestions. + + +Description +----------- + +This driver implements support for the hardware sensor capabilities +of the SMSC LPC47M192 and compatible Super-I/O chips. + +These chips support 3 temperature channels and 8 voltage inputs +as well as CPU voltage VID input. + +They do also have fan monitoring and control capabilities, but the +these features are accessed via ISA bus and are not supported by this +driver. Use the 'smsc47m1' driver for fan monitoring and control. + +Voltages and temperatures are measured by an 8-bit ADC, the resolution +of the temperatures is 1 bit per degree C. +Voltages are scaled such that the nominal voltage corresponds to +192 counts, i.e. 3/4 of the full range. Thus the available range for +each voltage channel is 0V ... 255/192*(nominal voltage), the resolution +is 1 bit per (nominal voltage)/192. +Both voltage and temperature values are scaled by 1000, the sys files +show voltages in mV and temperatures in units of 0.001 degC. + +The +12V analog voltage input channel (in4_input) is multiplexed with +bit 4 of the encoded CPU voltage. This means that you either get +a +12V voltage measurement or a 5 bit CPU VID, but not both. +The default setting is to use the pin as 12V input, and use only 4 bit VID. +This driver assumes that the information in the configuration register +is correct, i.e. that the BIOS has updated the configuration if +the motherboard has this input wired to VID4. + +The temperature and voltage readings are updated once every 1.5 seconds. +Reading them more often repeats the same values. + + +sysfs interface +--------------- + +===================== ========================================================== +in0_input +2.5V voltage input +in1_input CPU voltage input (nominal 2.25V) +in2_input +3.3V voltage input +in3_input +5V voltage input +in4_input +12V voltage input (may be missing if used as VID4) +in5_input Vcc voltage input (nominal 3.3V) + This is the supply voltage of the sensor chip itself. +in6_input +1.5V voltage input +in7_input +1.8V voltage input + +in[0-7]_min, +in[0-7]_max lower and upper alarm thresholds for in[0-7]_input reading + + All voltages are read and written in mV. + +in[0-7]_alarm alarm flags for voltage inputs + These files read '1' in case of alarm, '0' otherwise. + +temp1_input chip temperature measured by on-chip diode +temp[2-3]_input temperature measured by external diodes (one of these + would typically be wired to the diode inside the CPU) + +temp[1-3]_min, +temp[1-3]_max lower and upper alarm thresholds for temperatures + +temp[1-3]_offset temperature offset registers + The chip adds the offsets stored in these registers to + the corresponding temperature readings. + Note that temp1 and temp2 offsets share the same register, + they cannot both be different from zero at the same time. + Writing a non-zero number to one of them will reset the other + offset to zero. + + All temperatures and offsets are read and written in + units of 0.001 degC. + +temp[1-3]_alarm alarm flags for temperature inputs, '1' in case of alarm, + '0' otherwise. +temp[2-3]_input_fault diode fault flags for temperature inputs 2 and 3. + A fault is detected if the two pins for the corresponding + sensor are open or shorted, or any of the two is shorted + to ground or Vcc. '1' indicates a diode fault. + +cpu0_vid CPU voltage as received from the CPU + +vrm CPU VID standard used for decoding CPU voltage +===================== ========================================================== + +The `*_min`, `*_max`, `*_offset` and `vrm` files can be read and written, +all others are read-only. diff --git a/Documentation/hwmon/submitting-patches b/Documentation/hwmon/submitting-patches deleted file mode 100644 index 12540b7d9b50..000000000000 --- a/Documentation/hwmon/submitting-patches +++ /dev/null @@ -1,146 +0,0 @@ -How to Get Your Patch Accepted Into the Hwmon Subsystem -======================================================= - -This text is a collection of suggestions for people writing patches or -drivers for the hwmon subsystem. Following these suggestions will greatly -increase the chances of your change being accepted. - - -1. General ----------- - -* It should be unnecessary to mention, but please read and follow: - - - Documentation/process/submit-checklist.rst - - Documentation/process/submitting-drivers.rst - - Documentation/process/submitting-patches.rst - - Documentation/process/coding-style.rst - -* Please run your patch through 'checkpatch --strict'. There should be no - errors, no warnings, and few if any check messages. If there are any - messages, please be prepared to explain. - -* If your patch generates checkpatch errors, warnings, or check messages, - please refrain from explanations such as "I prefer that coding style". - Keep in mind that each unnecessary message helps hiding a real problem, - and a consistent coding style makes it easier for others to understand - and review the code. - -* Please test your patch thoroughly. We are not your test group. - Sometimes a patch can not or not completely be tested because of missing - hardware. In such cases, you should test-build the code on at least one - architecture. If run-time testing was not achieved, it should be written - explicitly below the patch header. - -* If your patch (or the driver) is affected by configuration options such as - CONFIG_SMP, make sure it compiles for all configuration variants. - - -2. Adding functionality to existing drivers -------------------------------------------- - -* Make sure the documentation in Documentation/hwmon/ is up to - date. - -* Make sure the information in Kconfig is up to date. - -* If the added functionality requires some cleanup or structural changes, split - your patch into a cleanup part and the actual addition. This makes it easier - to review your changes, and to bisect any resulting problems. - -* Never mix bug fixes, cleanup, and functional enhancements in a single patch. - - -3. New drivers --------------- - -* Running your patch or driver file(s) through checkpatch does not mean its - formatting is clean. If unsure about formatting in your new driver, run it - through Lindent. Lindent is not perfect, and you may have to do some minor - cleanup, but it is a good start. - -* Consider adding yourself to MAINTAINERS. - -* Document the driver in Documentation/hwmon/. - -* Add the driver to Kconfig and Makefile in alphabetical order. - -* Make sure that all dependencies are listed in Kconfig. - -* Please list include files in alphabetic order. - -* Please align continuation lines with '(' on the previous line. - -* Avoid forward declarations if you can. Rearrange the code if necessary. - -* Avoid macros to generate groups of sensor attributes. It not only confuses - checkpatch, but also makes it more difficult to review the code. - -* Avoid calculations in macros and macro-generated functions. While such macros - may save a line or so in the source, it obfuscates the code and makes code - review more difficult. It may also result in code which is more complicated - than necessary. Use inline functions or just regular functions instead. - -* Limit the number of kernel log messages. In general, your driver should not - generate an error message just because a runtime operation failed. Report - errors to user space instead, using an appropriate error code. Keep in mind - that kernel error log messages not only fill up the kernel log, but also are - printed synchronously, most likely with interrupt disabled, often to a serial - console. Excessive logging can seriously affect system performance. - -* Use devres functions whenever possible to allocate resources. For rationale - and supported functions, please see Documentation/driver-model/devres.txt. - If a function is not supported by devres, consider using devm_add_action(). - -* If the driver has a detect function, make sure it is silent. Debug messages - and messages printed after a successful detection are acceptable, but it - must not print messages such as "Chip XXX not found/supported". - - Keep in mind that the detect function will run for all drivers supporting an - address if a chip is detected on that address. Unnecessary messages will just - pollute the kernel log and not provide any value. - -* Provide a detect function if and only if a chip can be detected reliably. - -* Only the following I2C addresses shall be probed: 0x18-0x1f, 0x28-0x2f, - 0x48-0x4f, 0x58, 0x5c, 0x73 and 0x77. Probing other addresses is strongly - discouraged as it is known to cause trouble with other (non-hwmon) I2C - chips. If your chip lives at an address which can't be probed then the - device will have to be instantiated explicitly (which is always better - anyway.) - -* Avoid writing to chip registers in the detect function. If you have to write, - only do it after you have already gathered enough data to be certain that the - detection is going to be successful. - - Keep in mind that the chip might not be what your driver believes it is, and - writing to it might cause a bad misconfiguration. - -* Make sure there are no race conditions in the probe function. Specifically, - completely initialize your chip and your driver first, then register with - the hwmon subsystem. - -* Use devm_hwmon_device_register_with_groups() or, if your driver needs a remove - function, hwmon_device_register_with_groups() to register your driver with the - hwmon subsystem. Try using devm_add_action() instead of a remove function if - possible. Do not use hwmon_device_register(). - -* Your driver should be buildable as module. If not, please be prepared to - explain why it has to be built into the kernel. - -* Do not provide support for deprecated sysfs attributes. - -* Do not create non-standard attributes unless really needed. If you have to use - non-standard attributes, or you believe you do, discuss it on the mailing list - first. Either case, provide a detailed explanation why you need the - non-standard attribute(s). - Standard attributes are specified in Documentation/hwmon/sysfs-interface. - -* When deciding which sysfs attributes to support, look at the chip's - capabilities. While we do not expect your driver to support everything the - chip may offer, it should at least support all limits and alarms. - -* Last but not least, please check if a driver for your chip already exists - before starting to write a new driver. Especially for temperature sensors, - new chips are often variants of previously released chips. In some cases, - a presumably new chip may simply have been relabeled. diff --git a/Documentation/hwmon/submitting-patches.rst b/Documentation/hwmon/submitting-patches.rst new file mode 100644 index 000000000000..f9796b9d9db6 --- /dev/null +++ b/Documentation/hwmon/submitting-patches.rst @@ -0,0 +1,146 @@ +How to Get Your Patch Accepted Into the Hwmon Subsystem +======================================================= + +This text is a collection of suggestions for people writing patches or +drivers for the hwmon subsystem. Following these suggestions will greatly +increase the chances of your change being accepted. + + +1. General +---------- + +* It should be unnecessary to mention, but please read and follow: + + - Documentation/process/submit-checklist.rst + - Documentation/process/submitting-drivers.rst + - Documentation/process/submitting-patches.rst + - Documentation/process/coding-style.rst + +* Please run your patch through 'checkpatch --strict'. There should be no + errors, no warnings, and few if any check messages. If there are any + messages, please be prepared to explain. + +* If your patch generates checkpatch errors, warnings, or check messages, + please refrain from explanations such as "I prefer that coding style". + Keep in mind that each unnecessary message helps hiding a real problem, + and a consistent coding style makes it easier for others to understand + and review the code. + +* Please test your patch thoroughly. We are not your test group. + Sometimes a patch can not or not completely be tested because of missing + hardware. In such cases, you should test-build the code on at least one + architecture. If run-time testing was not achieved, it should be written + explicitly below the patch header. + +* If your patch (or the driver) is affected by configuration options such as + CONFIG_SMP, make sure it compiles for all configuration variants. + + +2. Adding functionality to existing drivers +------------------------------------------- + +* Make sure the documentation in Documentation/hwmon/.rst is up to + date. + +* Make sure the information in Kconfig is up to date. + +* If the added functionality requires some cleanup or structural changes, split + your patch into a cleanup part and the actual addition. This makes it easier + to review your changes, and to bisect any resulting problems. + +* Never mix bug fixes, cleanup, and functional enhancements in a single patch. + + +3. New drivers +-------------- + +* Running your patch or driver file(s) through checkpatch does not mean its + formatting is clean. If unsure about formatting in your new driver, run it + through Lindent. Lindent is not perfect, and you may have to do some minor + cleanup, but it is a good start. + +* Consider adding yourself to MAINTAINERS. + +* Document the driver in Documentation/hwmon/.rst. + +* Add the driver to Kconfig and Makefile in alphabetical order. + +* Make sure that all dependencies are listed in Kconfig. + +* Please list include files in alphabetic order. + +* Please align continuation lines with '(' on the previous line. + +* Avoid forward declarations if you can. Rearrange the code if necessary. + +* Avoid macros to generate groups of sensor attributes. It not only confuses + checkpatch, but also makes it more difficult to review the code. + +* Avoid calculations in macros and macro-generated functions. While such macros + may save a line or so in the source, it obfuscates the code and makes code + review more difficult. It may also result in code which is more complicated + than necessary. Use inline functions or just regular functions instead. + +* Limit the number of kernel log messages. In general, your driver should not + generate an error message just because a runtime operation failed. Report + errors to user space instead, using an appropriate error code. Keep in mind + that kernel error log messages not only fill up the kernel log, but also are + printed synchronously, most likely with interrupt disabled, often to a serial + console. Excessive logging can seriously affect system performance. + +* Use devres functions whenever possible to allocate resources. For rationale + and supported functions, please see Documentation/driver-model/devres.txt. + If a function is not supported by devres, consider using devm_add_action(). + +* If the driver has a detect function, make sure it is silent. Debug messages + and messages printed after a successful detection are acceptable, but it + must not print messages such as "Chip XXX not found/supported". + + Keep in mind that the detect function will run for all drivers supporting an + address if a chip is detected on that address. Unnecessary messages will just + pollute the kernel log and not provide any value. + +* Provide a detect function if and only if a chip can be detected reliably. + +* Only the following I2C addresses shall be probed: 0x18-0x1f, 0x28-0x2f, + 0x48-0x4f, 0x58, 0x5c, 0x73 and 0x77. Probing other addresses is strongly + discouraged as it is known to cause trouble with other (non-hwmon) I2C + chips. If your chip lives at an address which can't be probed then the + device will have to be instantiated explicitly (which is always better + anyway.) + +* Avoid writing to chip registers in the detect function. If you have to write, + only do it after you have already gathered enough data to be certain that the + detection is going to be successful. + + Keep in mind that the chip might not be what your driver believes it is, and + writing to it might cause a bad misconfiguration. + +* Make sure there are no race conditions in the probe function. Specifically, + completely initialize your chip and your driver first, then register with + the hwmon subsystem. + +* Use devm_hwmon_device_register_with_groups() or, if your driver needs a remove + function, hwmon_device_register_with_groups() to register your driver with the + hwmon subsystem. Try using devm_add_action() instead of a remove function if + possible. Do not use hwmon_device_register(). + +* Your driver should be buildable as module. If not, please be prepared to + explain why it has to be built into the kernel. + +* Do not provide support for deprecated sysfs attributes. + +* Do not create non-standard attributes unless really needed. If you have to use + non-standard attributes, or you believe you do, discuss it on the mailing list + first. Either case, provide a detailed explanation why you need the + non-standard attribute(s). + Standard attributes are specified in Documentation/hwmon/sysfs-interface.rst. + +* When deciding which sysfs attributes to support, look at the chip's + capabilities. While we do not expect your driver to support everything the + chip may offer, it should at least support all limits and alarms. + +* Last but not least, please check if a driver for your chip already exists + before starting to write a new driver. Especially for temperature sensors, + new chips are often variants of previously released chips. In some cases, + a presumably new chip may simply have been relabeled. diff --git a/Documentation/hwmon/sysfs-interface b/Documentation/hwmon/sysfs-interface deleted file mode 100644 index fd590633bb14..000000000000 --- a/Documentation/hwmon/sysfs-interface +++ /dev/null @@ -1,1086 +0,0 @@ -Naming and data format standards for sysfs files -================================================ - -The libsensors library offers an interface to the raw sensors data -through the sysfs interface. Since lm-sensors 3.0.0, libsensors is -completely chip-independent. It assumes that all the kernel drivers -implement the standard sysfs interface described in this document. -This makes adding or updating support for any given chip very easy, as -libsensors, and applications using it, do not need to be modified. -This is a major improvement compared to lm-sensors 2. - -Note that motherboards vary widely in the connections to sensor chips. -There is no standard that ensures, for example, that the second -temperature sensor is connected to the CPU, or that the second fan is on -the CPU. Also, some values reported by the chips need some computation -before they make full sense. For example, most chips can only measure -voltages between 0 and +4V. Other voltages are scaled back into that -range using external resistors. Since the values of these resistors -can change from motherboard to motherboard, the conversions cannot be -hard coded into the driver and have to be done in user space. - -For this reason, even if we aim at a chip-independent libsensors, it will -still require a configuration file (e.g. /etc/sensors.conf) for proper -values conversion, labeling of inputs and hiding of unused inputs. - -An alternative method that some programs use is to access the sysfs -files directly. This document briefly describes the standards that the -drivers follow, so that an application program can scan for entries and -access this data in a simple and consistent way. That said, such programs -will have to implement conversion, labeling and hiding of inputs. For -this reason, it is still not recommended to bypass the library. - -Each chip gets its own directory in the sysfs /sys/devices tree. To -find all sensor chips, it is easier to follow the device symlinks from -`/sys/class/hwmon/hwmon*`. - -Up to lm-sensors 3.0.0, libsensors looks for hardware monitoring attributes -in the "physical" device directory. Since lm-sensors 3.0.1, attributes found -in the hwmon "class" device directory are also supported. Complex drivers -(e.g. drivers for multifunction chips) may want to use this possibility to -avoid namespace pollution. The only drawback will be that older versions of -libsensors won't support the driver in question. - -All sysfs values are fixed point numbers. - -There is only one value per file, unlike the older /proc specification. -The common scheme for files naming is: _. Usual -types for sensor chips are "in" (voltage), "temp" (temperature) and -"fan" (fan). Usual items are "input" (measured value), "max" (high -threshold, "min" (low threshold). Numbering usually starts from 1, -except for voltages which start from 0 (because most data sheets use -this). A number is always used for elements that can be present more -than once, even if there is a single element of the given type on the -specific chip. Other files do not refer to a specific element, so -they have a simple name, and no number. - -Alarms are direct indications read from the chips. The drivers do NOT -make comparisons of readings to thresholds. This allows violations -between readings to be caught and alarmed. The exact definition of an -alarm (for example, whether a threshold must be met or must be exceeded -to cause an alarm) is chip-dependent. - -When setting values of hwmon sysfs attributes, the string representation of -the desired value must be written, note that strings which are not a number -are interpreted as 0! For more on how written strings are interpreted see the -"sysfs attribute writes interpretation" section at the end of this file. - -------------------------------------------------------------------------- - -======= =========================================== -`[0-*]` denotes any positive number starting from 0 -`[1-*]` denotes any positive number starting from 1 -RO read only value -WO write only value -RW read/write value -======= =========================================== - -Read/write values may be read-only for some chips, depending on the -hardware implementation. - -All entries (except name) are optional, and should only be created in a -given driver if the chip has the feature. - - -***************** -Global attributes -***************** - -`name` - The chip name. - This should be a short, lowercase string, not containing - whitespace, dashes, or the wildcard character '*'. - This attribute represents the chip name. It is the only - mandatory attribute. - I2C devices get this attribute created automatically. - - RO - -`update_interval` - The interval at which the chip will update readings. - Unit: millisecond - - RW - - Some devices have a variable update rate or interval. - This attribute can be used to change it to the desired value. - - -******** -Voltages -******** - -`in[0-*]_min` - Voltage min value. - - Unit: millivolt - - RW - -`in[0-*]_lcrit` - Voltage critical min value. - - Unit: millivolt - - RW - - If voltage drops to or below this limit, the system may - take drastic action such as power down or reset. At the very - least, it should report a fault. - -`in[0-*]_max` - Voltage max value. - - Unit: millivolt - - RW - -`in[0-*]_crit` - Voltage critical max value. - - Unit: millivolt - - RW - - If voltage reaches or exceeds this limit, the system may - take drastic action such as power down or reset. At the very - least, it should report a fault. - -`in[0-*]_input` - Voltage input value. - - Unit: millivolt - - RO - - Voltage measured on the chip pin. - - Actual voltage depends on the scaling resistors on the - motherboard, as recommended in the chip datasheet. - - This varies by chip and by motherboard. - Because of this variation, values are generally NOT scaled - by the chip driver, and must be done by the application. - However, some drivers (notably lm87 and via686a) - do scale, because of internal resistors built into a chip. - These drivers will output the actual voltage. Rule of - thumb: drivers should report the voltage values at the - "pins" of the chip. - -`in[0-*]_average` - Average voltage - - Unit: millivolt - - RO - -`in[0-*]_lowest` - Historical minimum voltage - - Unit: millivolt - - RO - -`in[0-*]_highest` - Historical maximum voltage - - Unit: millivolt - - RO - -`in[0-*]_reset_history` - Reset inX_lowest and inX_highest - - WO - -`in_reset_history` - Reset inX_lowest and inX_highest for all sensors - - WO - -`in[0-*]_label` - Suggested voltage channel label. - - Text string - - Should only be created if the driver has hints about what - this voltage channel is being used for, and user-space - doesn't. In all other cases, the label is provided by - user-space. - - RO - -`in[0-*]_enable` - Enable or disable the sensors. - - When disabled the sensor read will return -ENODATA. - - - 1: Enable - - 0: Disable - - RW - -`cpu[0-*]_vid` - CPU core reference voltage. - - Unit: millivolt - - RO - - Not always correct. - -`vrm` - Voltage Regulator Module version number. - - RW (but changing it should no more be necessary) - - Originally the VRM standard version multiplied by 10, but now - an arbitrary number, as not all standards have a version - number. - - Affects the way the driver calculates the CPU core reference - voltage from the vid pins. - -Also see the Alarms section for status flags associated with voltages. - - -**** -Fans -**** - -`fan[1-*]_min` - Fan minimum value - - Unit: revolution/min (RPM) - - RW - -`fan[1-*]_max` - Fan maximum value - - Unit: revolution/min (RPM) - - Only rarely supported by the hardware. - RW - -`fan[1-*]_input` - Fan input value. - - Unit: revolution/min (RPM) - - RO - -`fan[1-*]_div` - Fan divisor. - - Integer value in powers of two (1, 2, 4, 8, 16, 32, 64, 128). - - RW - - Some chips only support values 1, 2, 4 and 8. - Note that this is actually an internal clock divisor, which - affects the measurable speed range, not the read value. - -`fan[1-*]_pulses` - Number of tachometer pulses per fan revolution. - - Integer value, typically between 1 and 4. - - RW - - This value is a characteristic of the fan connected to the - device's input, so it has to be set in accordance with the fan - model. - - Should only be created if the chip has a register to configure - the number of pulses. In the absence of such a register (and - thus attribute) the value assumed by all devices is 2 pulses - per fan revolution. - -`fan[1-*]_target` - Desired fan speed - - Unit: revolution/min (RPM) - - RW - - Only makes sense if the chip supports closed-loop fan speed - control based on the measured fan speed. - -`fan[1-*]_label` - Suggested fan channel label. - - Text string - - Should only be created if the driver has hints about what - this fan channel is being used for, and user-space doesn't. - In all other cases, the label is provided by user-space. - - RO - -`fan[1-*]_enable` - Enable or disable the sensors. - - When disabled the sensor read will return -ENODATA. - - - 1: Enable - - 0: Disable - - RW - -Also see the Alarms section for status flags associated with fans. - - -*** -PWM -*** - -`pwm[1-*]` - Pulse width modulation fan control. - - Integer value in the range 0 to 255 - - RW - - 255 is max or 100%. - -`pwm[1-*]_enable` - Fan speed control method: - - - 0: no fan speed control (i.e. fan at full speed) - - 1: manual fan speed control enabled (using `pwm[1-*]`) - - 2+: automatic fan speed control enabled - - Check individual chip documentation files for automatic mode - details. - - RW - -`pwm[1-*]_mode` - - 0: DC mode (direct current) - - 1: PWM mode (pulse-width modulation) - - RW - -`pwm[1-*]_freq` - Base PWM frequency in Hz. - - Only possibly available when pwmN_mode is PWM, but not always - present even then. - - RW - -`pwm[1-*]_auto_channels_temp` - Select which temperature channels affect this PWM output in - auto mode. - - Bitfield, 1 is temp1, 2 is temp2, 4 is temp3 etc... - Which values are possible depend on the chip used. - - RW - -`pwm[1-*]_auto_point[1-*]_pwm` / `pwm[1-*]_auto_point[1-*]_temp` / `pwm[1-*]_auto_point[1-*]_temp_hyst` - Define the PWM vs temperature curve. - - Number of trip points is chip-dependent. Use this for chips - which associate trip points to PWM output channels. - - RW - -`temp[1-*]_auto_point[1-*]_pwm` / `temp[1-*]_auto_point[1-*]_temp` / `temp[1-*]_auto_point[1-*]_temp_hyst` - Define the PWM vs temperature curve. - - Number of trip points is chip-dependent. Use this for chips - which associate trip points to temperature channels. - - RW - -There is a third case where trip points are associated to both PWM output -channels and temperature channels: the PWM values are associated to PWM -output channels while the temperature values are associated to temperature -channels. In that case, the result is determined by the mapping between -temperature inputs and PWM outputs. When several temperature inputs are -mapped to a given PWM output, this leads to several candidate PWM values. -The actual result is up to the chip, but in general the highest candidate -value (fastest fan speed) wins. - - -************ -Temperatures -************ - -`temp[1-*]_type` - Sensor type selection. - - Integers 1 to 6 - - RW - - - 1: CPU embedded diode - - 2: 3904 transistor - - 3: thermal diode - - 4: thermistor - - 5: AMD AMDSI - - 6: Intel PECI - - Not all types are supported by all chips - -`temp[1-*]_max` - Temperature max value. - - Unit: millidegree Celsius (or millivolt, see below) - - RW - -`temp[1-*]_min` - Temperature min value. - - Unit: millidegree Celsius - - RW - -`temp[1-*]_max_hyst` - Temperature hysteresis value for max limit. - - Unit: millidegree Celsius - - Must be reported as an absolute temperature, NOT a delta - from the max value. - - RW - -`temp[1-*]_min_hyst` - Temperature hysteresis value for min limit. - Unit: millidegree Celsius - - Must be reported as an absolute temperature, NOT a delta - from the min value. - - RW - -`temp[1-*]_input` - Temperature input value. - - Unit: millidegree Celsius - - RO - -`temp[1-*]_crit` - Temperature critical max value, typically greater than - corresponding temp_max values. - - Unit: millidegree Celsius - - RW - -`temp[1-*]_crit_hyst` - Temperature hysteresis value for critical limit. - - Unit: millidegree Celsius - - Must be reported as an absolute temperature, NOT a delta - from the critical value. - - RW - -`temp[1-*]_emergency` - Temperature emergency max value, for chips supporting more than - two upper temperature limits. Must be equal or greater than - corresponding temp_crit values. - - Unit: millidegree Celsius - - RW - -`temp[1-*]_emergency_hyst` - Temperature hysteresis value for emergency limit. - - Unit: millidegree Celsius - - Must be reported as an absolute temperature, NOT a delta - from the emergency value. - - RW - -`temp[1-*]_lcrit` - Temperature critical min value, typically lower than - corresponding temp_min values. - - Unit: millidegree Celsius - - RW - -`temp[1-*]_lcrit_hyst` - Temperature hysteresis value for critical min limit. - - Unit: millidegree Celsius - - Must be reported as an absolute temperature, NOT a delta - from the critical min value. - - RW - -`temp[1-*]_offset` - Temperature offset which is added to the temperature reading - by the chip. - - Unit: millidegree Celsius - - Read/Write value. - -`temp[1-*]_label` - Suggested temperature channel label. - - Text string - - Should only be created if the driver has hints about what - this temperature channel is being used for, and user-space - doesn't. In all other cases, the label is provided by - user-space. - - RO - -`temp[1-*]_lowest` - Historical minimum temperature - - Unit: millidegree Celsius - - RO - -`temp[1-*]_highest` - Historical maximum temperature - - Unit: millidegree Celsius - - RO - -`temp[1-*]_reset_history` - Reset temp_lowest and temp_highest - - WO - -`temp_reset_history` - Reset temp_lowest and temp_highest for all sensors - - WO - -`temp[1-*]_enable` - Enable or disable the sensors. - - When disabled the sensor read will return -ENODATA. - - - 1: Enable - - 0: Disable - - RW - -Some chips measure temperature using external thermistors and an ADC, and -report the temperature measurement as a voltage. Converting this voltage -back to a temperature (or the other way around for limits) requires -mathematical functions not available in the kernel, so the conversion -must occur in user space. For these chips, all temp* files described -above should contain values expressed in millivolt instead of millidegree -Celsius. In other words, such temperature channels are handled as voltage -channels by the driver. - -Also see the Alarms section for status flags associated with temperatures. - - -******** -Currents -******** - -`curr[1-*]_max` - Current max value - - Unit: milliampere - - RW - -`curr[1-*]_min` - Current min value. - - Unit: milliampere - - RW - -`curr[1-*]_lcrit` - Current critical low value - - Unit: milliampere - - RW - -`curr[1-*]_crit` - Current critical high value. - - Unit: milliampere - - RW - -`curr[1-*]_input` - Current input value - - Unit: milliampere - - RO - -`curr[1-*]_average` - Average current use - - Unit: milliampere - - RO - -`curr[1-*]_lowest` - Historical minimum current - - Unit: milliampere - - RO - -`curr[1-*]_highest` - Historical maximum current - Unit: milliampere - RO - -`curr[1-*]_reset_history` - Reset currX_lowest and currX_highest - - WO - -`curr_reset_history` - Reset currX_lowest and currX_highest for all sensors - - WO - -`curr[1-*]_enable` - Enable or disable the sensors. - - When disabled the sensor read will return -ENODATA. - - - 1: Enable - - 0: Disable - - RW - -Also see the Alarms section for status flags associated with currents. - -***** -Power -***** - -`power[1-*]_average` - Average power use - - Unit: microWatt - - RO - -`power[1-*]_average_interval` - Power use averaging interval. A poll - notification is sent to this file if the - hardware changes the averaging interval. - - Unit: milliseconds - - RW - -`power[1-*]_average_interval_max` - Maximum power use averaging interval - - Unit: milliseconds - - RO - -`power[1-*]_average_interval_min` - Minimum power use averaging interval - - Unit: milliseconds - - RO - -`power[1-*]_average_highest` - Historical average maximum power use - - Unit: microWatt - - RO - -`power[1-*]_average_lowest` - Historical average minimum power use - - Unit: microWatt - - RO - -`power[1-*]_average_max` - A poll notification is sent to - `power[1-*]_average` when power use - rises above this value. - - Unit: microWatt - - RW - -`power[1-*]_average_min` - A poll notification is sent to - `power[1-*]_average` when power use - sinks below this value. - - Unit: microWatt - - RW - -`power[1-*]_input` - Instantaneous power use - - Unit: microWatt - - RO - -`power[1-*]_input_highest` - Historical maximum power use - - Unit: microWatt - - RO - -`power[1-*]_input_lowest` - Historical minimum power use - - Unit: microWatt - - RO - -`power[1-*]_reset_history` - Reset input_highest, input_lowest, - average_highest and average_lowest. - - WO - -`power[1-*]_accuracy` - Accuracy of the power meter. - - Unit: Percent - - RO - -`power[1-*]_cap` - If power use rises above this limit, the - system should take action to reduce power use. - A poll notification is sent to this file if the - cap is changed by the hardware. The `*_cap` - files only appear if the cap is known to be - enforced by hardware. - - Unit: microWatt - - RW - -`power[1-*]_cap_hyst` - Margin of hysteresis built around capping and - notification. - - Unit: microWatt - - RW - -`power[1-*]_cap_max` - Maximum cap that can be set. - - Unit: microWatt - - RO - -`power[1-*]_cap_min` - Minimum cap that can be set. - - Unit: microWatt - - RO - -`power[1-*]_max` - Maximum power. - - Unit: microWatt - - RW - -`power[1-*]_crit` - Critical maximum power. - - If power rises to or above this limit, the - system is expected take drastic action to reduce - power consumption, such as a system shutdown or - a forced powerdown of some devices. - - Unit: microWatt - - RW - -`power[1-*]_enable` - Enable or disable the sensors. - - When disabled the sensor read will return - -ENODATA. - - - 1: Enable - - 0: Disable - - RW - -Also see the Alarms section for status flags associated with power readings. - -****** -Energy -****** - -`energy[1-*]_input` - Cumulative energy use - - Unit: microJoule - - RO - -`energy[1-*]_enable` - Enable or disable the sensors. - - When disabled the sensor read will return - -ENODATA. - - - 1: Enable - - 0: Disable - - RW - -******** -Humidity -******** - -`humidity[1-*]_input` - Humidity - - Unit: milli-percent (per cent mille, pcm) - - RO - - -`humidity[1-*]_enable` - Enable or disable the sensors - - When disabled the sensor read will return - -ENODATA. - - - 1: Enable - - 0: Disable - - RW - -****** -Alarms -****** - -Each channel or limit may have an associated alarm file, containing a -boolean value. 1 means than an alarm condition exists, 0 means no alarm. - -Usually a given chip will either use channel-related alarms, or -limit-related alarms, not both. The driver should just reflect the hardware -implementation. - -+-------------------------------+-----------------------+ -| **`in[0-*]_alarm`, | Channel alarm | -| `curr[1-*]_alarm`, | | -| `power[1-*]_alarm`, | - 0: no alarm | -| `fan[1-*]_alarm`, | - 1: alarm | -| `temp[1-*]_alarm`** | | -| | RO | -+-------------------------------+-----------------------+ - -**OR** - -+-------------------------------+-----------------------+ -| **`in[0-*]_min_alarm`, | Limit alarm | -| `in[0-*]_max_alarm`, | | -| `in[0-*]_lcrit_alarm`, | - 0: no alarm | -| `in[0-*]_crit_alarm`, | - 1: alarm | -| `curr[1-*]_min_alarm`, | | -| `curr[1-*]_max_alarm`, | RO | -| `curr[1-*]_lcrit_alarm`, | | -| `curr[1-*]_crit_alarm`, | | -| `power[1-*]_cap_alarm`, | | -| `power[1-*]_max_alarm`, | | -| `power[1-*]_crit_alarm`, | | -| `fan[1-*]_min_alarm`, | | -| `fan[1-*]_max_alarm`, | | -| `temp[1-*]_min_alarm`, | | -| `temp[1-*]_max_alarm`, | | -| `temp[1-*]_lcrit_alarm`, | | -| `temp[1-*]_crit_alarm`, | | -| `temp[1-*]_emergency_alarm`** | | -+-------------------------------+-----------------------+ - -Each input channel may have an associated fault file. This can be used -to notify open diodes, unconnected fans etc. where the hardware -supports it. When this boolean has value 1, the measurement for that -channel should not be trusted. - -`fan[1-*]_fault` / `temp[1-*]_fault` - Input fault condition - - - 0: no fault occurred - - 1: fault condition - - RO - -Some chips also offer the possibility to get beeped when an alarm occurs: - -`beep_enable` - Master beep enable - - - 0: no beeps - - 1: beeps - - RW - -`in[0-*]_beep`, `curr[1-*]_beep`, `fan[1-*]_beep`, `temp[1-*]_beep`, - Channel beep - - - 0: disable - - 1: enable - - RW - -In theory, a chip could provide per-limit beep masking, but no such chip -was seen so far. - -Old drivers provided a different, non-standard interface to alarms and -beeps. These interface files are deprecated, but will be kept around -for compatibility reasons: - -`alarms` - Alarm bitmask. - - RO - - Integer representation of one to four bytes. - - A '1' bit means an alarm. - - Chips should be programmed for 'comparator' mode so that - the alarm will 'come back' after you read the register - if it is still valid. - - Generally a direct representation of a chip's internal - alarm registers; there is no standard for the position - of individual bits. For this reason, the use of this - interface file for new drivers is discouraged. Use - `individual *_alarm` and `*_fault` files instead. - Bits are defined in kernel/include/sensors.h. - -`beep_mask` - Bitmask for beep. - Same format as 'alarms' with the same bit locations, - use discouraged for the same reason. Use individual - `*_beep` files instead. - RW - - -******************* -Intrusion detection -******************* - -`intrusion[0-*]_alarm` - Chassis intrusion detection - - - 0: OK - - 1: intrusion detected - - RW - - Contrary to regular alarm flags which clear themselves - automatically when read, this one sticks until cleared by - the user. This is done by writing 0 to the file. Writing - other values is unsupported. - -`intrusion[0-*]_beep` - Chassis intrusion beep - - 0: disable - 1: enable - - RW - -**************************** -Average sample configuration -**************************** - -Devices allowing for reading {in,power,curr,temp}_average values may export -attributes for controlling number of samples used to compute average. - -+--------------+---------------------------------------------------------------+ -| samples | Sets number of average samples for all types of measurements. | -| | | -| | RW | -+--------------+---------------------------------------------------------------+ -| in_samples | Sets number of average samples for specific type of | -| power_samples| measurements. | -| curr_samples | | -| temp_samples | Note that on some devices it won't be possible to set all of | -| | them to different values so changing one might also change | -| | some others. | -| | | -| | RW | -+--------------+---------------------------------------------------------------+ - -sysfs attribute writes interpretation -------------------------------------- - -hwmon sysfs attributes always contain numbers, so the first thing to do is to -convert the input to a number, there are 2 ways todo this depending whether -the number can be negative or not:: - - unsigned long u = simple_strtoul(buf, NULL, 10); - long s = simple_strtol(buf, NULL, 10); - -With buf being the buffer with the user input being passed by the kernel. -Notice that we do not use the second argument of strto[u]l, and thus cannot -tell when 0 is returned, if this was really 0 or is caused by invalid input. -This is done deliberately as checking this everywhere would add a lot of -code to the kernel. - -Notice that it is important to always store the converted value in an -unsigned long or long, so that no wrap around can happen before any further -checking. - -After the input string is converted to an (unsigned) long, the value should be -checked if its acceptable. Be careful with further conversions on the value -before checking it for validity, as these conversions could still cause a wrap -around before the check. For example do not multiply the result, and only -add/subtract if it has been divided before the add/subtract. - -What to do if a value is found to be invalid, depends on the type of the -sysfs attribute that is being set. If it is a continuous setting like a -tempX_max or inX_max attribute, then the value should be clamped to its -limits using clamp_val(value, min_limit, max_limit). If it is not continuous -like for example a tempX_type, then when an invalid value is written, --EINVAL should be returned. - -Example1, temp1_max, register is a signed 8 bit value (-128 - 127 degrees):: - - long v = simple_strtol(buf, NULL, 10) / 1000; - v = clamp_val(v, -128, 127); - /* write v to register */ - -Example2, fan divider setting, valid values 2, 4 and 8:: - - unsigned long v = simple_strtoul(buf, NULL, 10); - - switch (v) { - case 2: v = 1; break; - case 4: v = 2; break; - case 8: v = 3; break; - default: - return -EINVAL; - } - /* write v to register */ diff --git a/Documentation/hwmon/sysfs-interface.rst b/Documentation/hwmon/sysfs-interface.rst new file mode 100644 index 000000000000..fd590633bb14 --- /dev/null +++ b/Documentation/hwmon/sysfs-interface.rst @@ -0,0 +1,1086 @@ +Naming and data format standards for sysfs files +================================================ + +The libsensors library offers an interface to the raw sensors data +through the sysfs interface. Since lm-sensors 3.0.0, libsensors is +completely chip-independent. It assumes that all the kernel drivers +implement the standard sysfs interface described in this document. +This makes adding or updating support for any given chip very easy, as +libsensors, and applications using it, do not need to be modified. +This is a major improvement compared to lm-sensors 2. + +Note that motherboards vary widely in the connections to sensor chips. +There is no standard that ensures, for example, that the second +temperature sensor is connected to the CPU, or that the second fan is on +the CPU. Also, some values reported by the chips need some computation +before they make full sense. For example, most chips can only measure +voltages between 0 and +4V. Other voltages are scaled back into that +range using external resistors. Since the values of these resistors +can change from motherboard to motherboard, the conversions cannot be +hard coded into the driver and have to be done in user space. + +For this reason, even if we aim at a chip-independent libsensors, it will +still require a configuration file (e.g. /etc/sensors.conf) for proper +values conversion, labeling of inputs and hiding of unused inputs. + +An alternative method that some programs use is to access the sysfs +files directly. This document briefly describes the standards that the +drivers follow, so that an application program can scan for entries and +access this data in a simple and consistent way. That said, such programs +will have to implement conversion, labeling and hiding of inputs. For +this reason, it is still not recommended to bypass the library. + +Each chip gets its own directory in the sysfs /sys/devices tree. To +find all sensor chips, it is easier to follow the device symlinks from +`/sys/class/hwmon/hwmon*`. + +Up to lm-sensors 3.0.0, libsensors looks for hardware monitoring attributes +in the "physical" device directory. Since lm-sensors 3.0.1, attributes found +in the hwmon "class" device directory are also supported. Complex drivers +(e.g. drivers for multifunction chips) may want to use this possibility to +avoid namespace pollution. The only drawback will be that older versions of +libsensors won't support the driver in question. + +All sysfs values are fixed point numbers. + +There is only one value per file, unlike the older /proc specification. +The common scheme for files naming is: _. Usual +types for sensor chips are "in" (voltage), "temp" (temperature) and +"fan" (fan). Usual items are "input" (measured value), "max" (high +threshold, "min" (low threshold). Numbering usually starts from 1, +except for voltages which start from 0 (because most data sheets use +this). A number is always used for elements that can be present more +than once, even if there is a single element of the given type on the +specific chip. Other files do not refer to a specific element, so +they have a simple name, and no number. + +Alarms are direct indications read from the chips. The drivers do NOT +make comparisons of readings to thresholds. This allows violations +between readings to be caught and alarmed. The exact definition of an +alarm (for example, whether a threshold must be met or must be exceeded +to cause an alarm) is chip-dependent. + +When setting values of hwmon sysfs attributes, the string representation of +the desired value must be written, note that strings which are not a number +are interpreted as 0! For more on how written strings are interpreted see the +"sysfs attribute writes interpretation" section at the end of this file. + +------------------------------------------------------------------------- + +======= =========================================== +`[0-*]` denotes any positive number starting from 0 +`[1-*]` denotes any positive number starting from 1 +RO read only value +WO write only value +RW read/write value +======= =========================================== + +Read/write values may be read-only for some chips, depending on the +hardware implementation. + +All entries (except name) are optional, and should only be created in a +given driver if the chip has the feature. + + +***************** +Global attributes +***************** + +`name` + The chip name. + This should be a short, lowercase string, not containing + whitespace, dashes, or the wildcard character '*'. + This attribute represents the chip name. It is the only + mandatory attribute. + I2C devices get this attribute created automatically. + + RO + +`update_interval` + The interval at which the chip will update readings. + Unit: millisecond + + RW + + Some devices have a variable update rate or interval. + This attribute can be used to change it to the desired value. + + +******** +Voltages +******** + +`in[0-*]_min` + Voltage min value. + + Unit: millivolt + + RW + +`in[0-*]_lcrit` + Voltage critical min value. + + Unit: millivolt + + RW + + If voltage drops to or below this limit, the system may + take drastic action such as power down or reset. At the very + least, it should report a fault. + +`in[0-*]_max` + Voltage max value. + + Unit: millivolt + + RW + +`in[0-*]_crit` + Voltage critical max value. + + Unit: millivolt + + RW + + If voltage reaches or exceeds this limit, the system may + take drastic action such as power down or reset. At the very + least, it should report a fault. + +`in[0-*]_input` + Voltage input value. + + Unit: millivolt + + RO + + Voltage measured on the chip pin. + + Actual voltage depends on the scaling resistors on the + motherboard, as recommended in the chip datasheet. + + This varies by chip and by motherboard. + Because of this variation, values are generally NOT scaled + by the chip driver, and must be done by the application. + However, some drivers (notably lm87 and via686a) + do scale, because of internal resistors built into a chip. + These drivers will output the actual voltage. Rule of + thumb: drivers should report the voltage values at the + "pins" of the chip. + +`in[0-*]_average` + Average voltage + + Unit: millivolt + + RO + +`in[0-*]_lowest` + Historical minimum voltage + + Unit: millivolt + + RO + +`in[0-*]_highest` + Historical maximum voltage + + Unit: millivolt + + RO + +`in[0-*]_reset_history` + Reset inX_lowest and inX_highest + + WO + +`in_reset_history` + Reset inX_lowest and inX_highest for all sensors + + WO + +`in[0-*]_label` + Suggested voltage channel label. + + Text string + + Should only be created if the driver has hints about what + this voltage channel is being used for, and user-space + doesn't. In all other cases, the label is provided by + user-space. + + RO + +`in[0-*]_enable` + Enable or disable the sensors. + + When disabled the sensor read will return -ENODATA. + + - 1: Enable + - 0: Disable + + RW + +`cpu[0-*]_vid` + CPU core reference voltage. + + Unit: millivolt + + RO + + Not always correct. + +`vrm` + Voltage Regulator Module version number. + + RW (but changing it should no more be necessary) + + Originally the VRM standard version multiplied by 10, but now + an arbitrary number, as not all standards have a version + number. + + Affects the way the driver calculates the CPU core reference + voltage from the vid pins. + +Also see the Alarms section for status flags associated with voltages. + + +**** +Fans +**** + +`fan[1-*]_min` + Fan minimum value + + Unit: revolution/min (RPM) + + RW + +`fan[1-*]_max` + Fan maximum value + + Unit: revolution/min (RPM) + + Only rarely supported by the hardware. + RW + +`fan[1-*]_input` + Fan input value. + + Unit: revolution/min (RPM) + + RO + +`fan[1-*]_div` + Fan divisor. + + Integer value in powers of two (1, 2, 4, 8, 16, 32, 64, 128). + + RW + + Some chips only support values 1, 2, 4 and 8. + Note that this is actually an internal clock divisor, which + affects the measurable speed range, not the read value. + +`fan[1-*]_pulses` + Number of tachometer pulses per fan revolution. + + Integer value, typically between 1 and 4. + + RW + + This value is a characteristic of the fan connected to the + device's input, so it has to be set in accordance with the fan + model. + + Should only be created if the chip has a register to configure + the number of pulses. In the absence of such a register (and + thus attribute) the value assumed by all devices is 2 pulses + per fan revolution. + +`fan[1-*]_target` + Desired fan speed + + Unit: revolution/min (RPM) + + RW + + Only makes sense if the chip supports closed-loop fan speed + control based on the measured fan speed. + +`fan[1-*]_label` + Suggested fan channel label. + + Text string + + Should only be created if the driver has hints about what + this fan channel is being used for, and user-space doesn't. + In all other cases, the label is provided by user-space. + + RO + +`fan[1-*]_enable` + Enable or disable the sensors. + + When disabled the sensor read will return -ENODATA. + + - 1: Enable + - 0: Disable + + RW + +Also see the Alarms section for status flags associated with fans. + + +*** +PWM +*** + +`pwm[1-*]` + Pulse width modulation fan control. + + Integer value in the range 0 to 255 + + RW + + 255 is max or 100%. + +`pwm[1-*]_enable` + Fan speed control method: + + - 0: no fan speed control (i.e. fan at full speed) + - 1: manual fan speed control enabled (using `pwm[1-*]`) + - 2+: automatic fan speed control enabled + + Check individual chip documentation files for automatic mode + details. + + RW + +`pwm[1-*]_mode` + - 0: DC mode (direct current) + - 1: PWM mode (pulse-width modulation) + + RW + +`pwm[1-*]_freq` + Base PWM frequency in Hz. + + Only possibly available when pwmN_mode is PWM, but not always + present even then. + + RW + +`pwm[1-*]_auto_channels_temp` + Select which temperature channels affect this PWM output in + auto mode. + + Bitfield, 1 is temp1, 2 is temp2, 4 is temp3 etc... + Which values are possible depend on the chip used. + + RW + +`pwm[1-*]_auto_point[1-*]_pwm` / `pwm[1-*]_auto_point[1-*]_temp` / `pwm[1-*]_auto_point[1-*]_temp_hyst` + Define the PWM vs temperature curve. + + Number of trip points is chip-dependent. Use this for chips + which associate trip points to PWM output channels. + + RW + +`temp[1-*]_auto_point[1-*]_pwm` / `temp[1-*]_auto_point[1-*]_temp` / `temp[1-*]_auto_point[1-*]_temp_hyst` + Define the PWM vs temperature curve. + + Number of trip points is chip-dependent. Use this for chips + which associate trip points to temperature channels. + + RW + +There is a third case where trip points are associated to both PWM output +channels and temperature channels: the PWM values are associated to PWM +output channels while the temperature values are associated to temperature +channels. In that case, the result is determined by the mapping between +temperature inputs and PWM outputs. When several temperature inputs are +mapped to a given PWM output, this leads to several candidate PWM values. +The actual result is up to the chip, but in general the highest candidate +value (fastest fan speed) wins. + + +************ +Temperatures +************ + +`temp[1-*]_type` + Sensor type selection. + + Integers 1 to 6 + + RW + + - 1: CPU embedded diode + - 2: 3904 transistor + - 3: thermal diode + - 4: thermistor + - 5: AMD AMDSI + - 6: Intel PECI + + Not all types are supported by all chips + +`temp[1-*]_max` + Temperature max value. + + Unit: millidegree Celsius (or millivolt, see below) + + RW + +`temp[1-*]_min` + Temperature min value. + + Unit: millidegree Celsius + + RW + +`temp[1-*]_max_hyst` + Temperature hysteresis value for max limit. + + Unit: millidegree Celsius + + Must be reported as an absolute temperature, NOT a delta + from the max value. + + RW + +`temp[1-*]_min_hyst` + Temperature hysteresis value for min limit. + Unit: millidegree Celsius + + Must be reported as an absolute temperature, NOT a delta + from the min value. + + RW + +`temp[1-*]_input` + Temperature input value. + + Unit: millidegree Celsius + + RO + +`temp[1-*]_crit` + Temperature critical max value, typically greater than + corresponding temp_max values. + + Unit: millidegree Celsius + + RW + +`temp[1-*]_crit_hyst` + Temperature hysteresis value for critical limit. + + Unit: millidegree Celsius + + Must be reported as an absolute temperature, NOT a delta + from the critical value. + + RW + +`temp[1-*]_emergency` + Temperature emergency max value, for chips supporting more than + two upper temperature limits. Must be equal or greater than + corresponding temp_crit values. + + Unit: millidegree Celsius + + RW + +`temp[1-*]_emergency_hyst` + Temperature hysteresis value for emergency limit. + + Unit: millidegree Celsius + + Must be reported as an absolute temperature, NOT a delta + from the emergency value. + + RW + +`temp[1-*]_lcrit` + Temperature critical min value, typically lower than + corresponding temp_min values. + + Unit: millidegree Celsius + + RW + +`temp[1-*]_lcrit_hyst` + Temperature hysteresis value for critical min limit. + + Unit: millidegree Celsius + + Must be reported as an absolute temperature, NOT a delta + from the critical min value. + + RW + +`temp[1-*]_offset` + Temperature offset which is added to the temperature reading + by the chip. + + Unit: millidegree Celsius + + Read/Write value. + +`temp[1-*]_label` + Suggested temperature channel label. + + Text string + + Should only be created if the driver has hints about what + this temperature channel is being used for, and user-space + doesn't. In all other cases, the label is provided by + user-space. + + RO + +`temp[1-*]_lowest` + Historical minimum temperature + + Unit: millidegree Celsius + + RO + +`temp[1-*]_highest` + Historical maximum temperature + + Unit: millidegree Celsius + + RO + +`temp[1-*]_reset_history` + Reset temp_lowest and temp_highest + + WO + +`temp_reset_history` + Reset temp_lowest and temp_highest for all sensors + + WO + +`temp[1-*]_enable` + Enable or disable the sensors. + + When disabled the sensor read will return -ENODATA. + + - 1: Enable + - 0: Disable + + RW + +Some chips measure temperature using external thermistors and an ADC, and +report the temperature measurement as a voltage. Converting this voltage +back to a temperature (or the other way around for limits) requires +mathematical functions not available in the kernel, so the conversion +must occur in user space. For these chips, all temp* files described +above should contain values expressed in millivolt instead of millidegree +Celsius. In other words, such temperature channels are handled as voltage +channels by the driver. + +Also see the Alarms section for status flags associated with temperatures. + + +******** +Currents +******** + +`curr[1-*]_max` + Current max value + + Unit: milliampere + + RW + +`curr[1-*]_min` + Current min value. + + Unit: milliampere + + RW + +`curr[1-*]_lcrit` + Current critical low value + + Unit: milliampere + + RW + +`curr[1-*]_crit` + Current critical high value. + + Unit: milliampere + + RW + +`curr[1-*]_input` + Current input value + + Unit: milliampere + + RO + +`curr[1-*]_average` + Average current use + + Unit: milliampere + + RO + +`curr[1-*]_lowest` + Historical minimum current + + Unit: milliampere + + RO + +`curr[1-*]_highest` + Historical maximum current + Unit: milliampere + RO + +`curr[1-*]_reset_history` + Reset currX_lowest and currX_highest + + WO + +`curr_reset_history` + Reset currX_lowest and currX_highest for all sensors + + WO + +`curr[1-*]_enable` + Enable or disable the sensors. + + When disabled the sensor read will return -ENODATA. + + - 1: Enable + - 0: Disable + + RW + +Also see the Alarms section for status flags associated with currents. + +***** +Power +***** + +`power[1-*]_average` + Average power use + + Unit: microWatt + + RO + +`power[1-*]_average_interval` + Power use averaging interval. A poll + notification is sent to this file if the + hardware changes the averaging interval. + + Unit: milliseconds + + RW + +`power[1-*]_average_interval_max` + Maximum power use averaging interval + + Unit: milliseconds + + RO + +`power[1-*]_average_interval_min` + Minimum power use averaging interval + + Unit: milliseconds + + RO + +`power[1-*]_average_highest` + Historical average maximum power use + + Unit: microWatt + + RO + +`power[1-*]_average_lowest` + Historical average minimum power use + + Unit: microWatt + + RO + +`power[1-*]_average_max` + A poll notification is sent to + `power[1-*]_average` when power use + rises above this value. + + Unit: microWatt + + RW + +`power[1-*]_average_min` + A poll notification is sent to + `power[1-*]_average` when power use + sinks below this value. + + Unit: microWatt + + RW + +`power[1-*]_input` + Instantaneous power use + + Unit: microWatt + + RO + +`power[1-*]_input_highest` + Historical maximum power use + + Unit: microWatt + + RO + +`power[1-*]_input_lowest` + Historical minimum power use + + Unit: microWatt + + RO + +`power[1-*]_reset_history` + Reset input_highest, input_lowest, + average_highest and average_lowest. + + WO + +`power[1-*]_accuracy` + Accuracy of the power meter. + + Unit: Percent + + RO + +`power[1-*]_cap` + If power use rises above this limit, the + system should take action to reduce power use. + A poll notification is sent to this file if the + cap is changed by the hardware. The `*_cap` + files only appear if the cap is known to be + enforced by hardware. + + Unit: microWatt + + RW + +`power[1-*]_cap_hyst` + Margin of hysteresis built around capping and + notification. + + Unit: microWatt + + RW + +`power[1-*]_cap_max` + Maximum cap that can be set. + + Unit: microWatt + + RO + +`power[1-*]_cap_min` + Minimum cap that can be set. + + Unit: microWatt + + RO + +`power[1-*]_max` + Maximum power. + + Unit: microWatt + + RW + +`power[1-*]_crit` + Critical maximum power. + + If power rises to or above this limit, the + system is expected take drastic action to reduce + power consumption, such as a system shutdown or + a forced powerdown of some devices. + + Unit: microWatt + + RW + +`power[1-*]_enable` + Enable or disable the sensors. + + When disabled the sensor read will return + -ENODATA. + + - 1: Enable + - 0: Disable + + RW + +Also see the Alarms section for status flags associated with power readings. + +****** +Energy +****** + +`energy[1-*]_input` + Cumulative energy use + + Unit: microJoule + + RO + +`energy[1-*]_enable` + Enable or disable the sensors. + + When disabled the sensor read will return + -ENODATA. + + - 1: Enable + - 0: Disable + + RW + +******** +Humidity +******** + +`humidity[1-*]_input` + Humidity + + Unit: milli-percent (per cent mille, pcm) + + RO + + +`humidity[1-*]_enable` + Enable or disable the sensors + + When disabled the sensor read will return + -ENODATA. + + - 1: Enable + - 0: Disable + + RW + +****** +Alarms +****** + +Each channel or limit may have an associated alarm file, containing a +boolean value. 1 means than an alarm condition exists, 0 means no alarm. + +Usually a given chip will either use channel-related alarms, or +limit-related alarms, not both. The driver should just reflect the hardware +implementation. + ++-------------------------------+-----------------------+ +| **`in[0-*]_alarm`, | Channel alarm | +| `curr[1-*]_alarm`, | | +| `power[1-*]_alarm`, | - 0: no alarm | +| `fan[1-*]_alarm`, | - 1: alarm | +| `temp[1-*]_alarm`** | | +| | RO | ++-------------------------------+-----------------------+ + +**OR** + ++-------------------------------+-----------------------+ +| **`in[0-*]_min_alarm`, | Limit alarm | +| `in[0-*]_max_alarm`, | | +| `in[0-*]_lcrit_alarm`, | - 0: no alarm | +| `in[0-*]_crit_alarm`, | - 1: alarm | +| `curr[1-*]_min_alarm`, | | +| `curr[1-*]_max_alarm`, | RO | +| `curr[1-*]_lcrit_alarm`, | | +| `curr[1-*]_crit_alarm`, | | +| `power[1-*]_cap_alarm`, | | +| `power[1-*]_max_alarm`, | | +| `power[1-*]_crit_alarm`, | | +| `fan[1-*]_min_alarm`, | | +| `fan[1-*]_max_alarm`, | | +| `temp[1-*]_min_alarm`, | | +| `temp[1-*]_max_alarm`, | | +| `temp[1-*]_lcrit_alarm`, | | +| `temp[1-*]_crit_alarm`, | | +| `temp[1-*]_emergency_alarm`** | | ++-------------------------------+-----------------------+ + +Each input channel may have an associated fault file. This can be used +to notify open diodes, unconnected fans etc. where the hardware +supports it. When this boolean has value 1, the measurement for that +channel should not be trusted. + +`fan[1-*]_fault` / `temp[1-*]_fault` + Input fault condition + + - 0: no fault occurred + - 1: fault condition + + RO + +Some chips also offer the possibility to get beeped when an alarm occurs: + +`beep_enable` + Master beep enable + + - 0: no beeps + - 1: beeps + + RW + +`in[0-*]_beep`, `curr[1-*]_beep`, `fan[1-*]_beep`, `temp[1-*]_beep`, + Channel beep + + - 0: disable + - 1: enable + + RW + +In theory, a chip could provide per-limit beep masking, but no such chip +was seen so far. + +Old drivers provided a different, non-standard interface to alarms and +beeps. These interface files are deprecated, but will be kept around +for compatibility reasons: + +`alarms` + Alarm bitmask. + + RO + + Integer representation of one to four bytes. + + A '1' bit means an alarm. + + Chips should be programmed for 'comparator' mode so that + the alarm will 'come back' after you read the register + if it is still valid. + + Generally a direct representation of a chip's internal + alarm registers; there is no standard for the position + of individual bits. For this reason, the use of this + interface file for new drivers is discouraged. Use + `individual *_alarm` and `*_fault` files instead. + Bits are defined in kernel/include/sensors.h. + +`beep_mask` + Bitmask for beep. + Same format as 'alarms' with the same bit locations, + use discouraged for the same reason. Use individual + `*_beep` files instead. + RW + + +******************* +Intrusion detection +******************* + +`intrusion[0-*]_alarm` + Chassis intrusion detection + + - 0: OK + - 1: intrusion detected + + RW + + Contrary to regular alarm flags which clear themselves + automatically when read, this one sticks until cleared by + the user. This is done by writing 0 to the file. Writing + other values is unsupported. + +`intrusion[0-*]_beep` + Chassis intrusion beep + + 0: disable + 1: enable + + RW + +**************************** +Average sample configuration +**************************** + +Devices allowing for reading {in,power,curr,temp}_average values may export +attributes for controlling number of samples used to compute average. + ++--------------+---------------------------------------------------------------+ +| samples | Sets number of average samples for all types of measurements. | +| | | +| | RW | ++--------------+---------------------------------------------------------------+ +| in_samples | Sets number of average samples for specific type of | +| power_samples| measurements. | +| curr_samples | | +| temp_samples | Note that on some devices it won't be possible to set all of | +| | them to different values so changing one might also change | +| | some others. | +| | | +| | RW | ++--------------+---------------------------------------------------------------+ + +sysfs attribute writes interpretation +------------------------------------- + +hwmon sysfs attributes always contain numbers, so the first thing to do is to +convert the input to a number, there are 2 ways todo this depending whether +the number can be negative or not:: + + unsigned long u = simple_strtoul(buf, NULL, 10); + long s = simple_strtol(buf, NULL, 10); + +With buf being the buffer with the user input being passed by the kernel. +Notice that we do not use the second argument of strto[u]l, and thus cannot +tell when 0 is returned, if this was really 0 or is caused by invalid input. +This is done deliberately as checking this everywhere would add a lot of +code to the kernel. + +Notice that it is important to always store the converted value in an +unsigned long or long, so that no wrap around can happen before any further +checking. + +After the input string is converted to an (unsigned) long, the value should be +checked if its acceptable. Be careful with further conversions on the value +before checking it for validity, as these conversions could still cause a wrap +around before the check. For example do not multiply the result, and only +add/subtract if it has been divided before the add/subtract. + +What to do if a value is found to be invalid, depends on the type of the +sysfs attribute that is being set. If it is a continuous setting like a +tempX_max or inX_max attribute, then the value should be clamped to its +limits using clamp_val(value, min_limit, max_limit). If it is not continuous +like for example a tempX_type, then when an invalid value is written, +-EINVAL should be returned. + +Example1, temp1_max, register is a signed 8 bit value (-128 - 127 degrees):: + + long v = simple_strtol(buf, NULL, 10) / 1000; + v = clamp_val(v, -128, 127); + /* write v to register */ + +Example2, fan divider setting, valid values 2, 4 and 8:: + + unsigned long v = simple_strtoul(buf, NULL, 10); + + switch (v) { + case 2: v = 1; break; + case 4: v = 2; break; + case 8: v = 3; break; + default: + return -EINVAL; + } + /* write v to register */ diff --git a/Documentation/hwmon/tc654 b/Documentation/hwmon/tc654 deleted file mode 100644 index ce546ee6dfed..000000000000 --- a/Documentation/hwmon/tc654 +++ /dev/null @@ -1,34 +0,0 @@ -Kernel driver tc654 -=================== - -Supported chips: - - * Microchip TC654 and TC655 - - Prefix: 'tc654' - Datasheet: http://ww1.m - icrochip.com/downloads/en/DeviceDoc/20001734C.pdf - -Authors: - - Chris Packham - - Masahiko Iwamoto - -Description ------------ -This driver implements support for the Microchip TC654 and TC655. - -The TC654 uses the 2-wire interface compatible with the SMBUS 2.0 -specification. The TC654 has two (2) inputs for measuring fan RPM and -one (1) PWM output which can be used for fan control. - -Configuration Notes -------------------- -Ordinarily the pwm1_mode ABI is used for controlling the pwm output -mode. However, for this chip the output is always pwm, and the -pwm1_mode determines if the pwm output is controlled via the pwm1 value -or via the Vin analog input. - - -Setting pwm1_mode to 1 will cause the pwm output to be driven based on -the pwm1 value. Setting pwm1_mode to 0 will cause the pwm output to be -driven based on the Vin input. diff --git a/Documentation/hwmon/tc654.rst b/Documentation/hwmon/tc654.rst new file mode 100644 index 000000000000..ce546ee6dfed --- /dev/null +++ b/Documentation/hwmon/tc654.rst @@ -0,0 +1,34 @@ +Kernel driver tc654 +=================== + +Supported chips: + + * Microchip TC654 and TC655 + + Prefix: 'tc654' + Datasheet: http://ww1.m + icrochip.com/downloads/en/DeviceDoc/20001734C.pdf + +Authors: + - Chris Packham + - Masahiko Iwamoto + +Description +----------- +This driver implements support for the Microchip TC654 and TC655. + +The TC654 uses the 2-wire interface compatible with the SMBUS 2.0 +specification. The TC654 has two (2) inputs for measuring fan RPM and +one (1) PWM output which can be used for fan control. + +Configuration Notes +------------------- +Ordinarily the pwm1_mode ABI is used for controlling the pwm output +mode. However, for this chip the output is always pwm, and the +pwm1_mode determines if the pwm output is controlled via the pwm1 value +or via the Vin analog input. + + +Setting pwm1_mode to 1 will cause the pwm output to be driven based on +the pwm1 value. Setting pwm1_mode to 0 will cause the pwm output to be +driven based on the Vin input. diff --git a/Documentation/hwmon/tc74 b/Documentation/hwmon/tc74 deleted file mode 100644 index f1764211c129..000000000000 --- a/Documentation/hwmon/tc74 +++ /dev/null @@ -1,23 +0,0 @@ -Kernel driver tc74 -==================== - -Supported chips: - - * Microchip TC74 - - Prefix: 'tc74' - - Datasheet: Publicly available at Microchip website. - -Description ------------ - -Driver supports the above part. - -The tc74 has an 8-bit sensor, with 1 degree centigrade resolution -and +- 2 degrees centigrade accuracy. - -Notes ------ - -Currently entering low power standby mode is not supported. diff --git a/Documentation/hwmon/tc74.rst b/Documentation/hwmon/tc74.rst new file mode 100644 index 000000000000..f1764211c129 --- /dev/null +++ b/Documentation/hwmon/tc74.rst @@ -0,0 +1,23 @@ +Kernel driver tc74 +==================== + +Supported chips: + + * Microchip TC74 + + Prefix: 'tc74' + + Datasheet: Publicly available at Microchip website. + +Description +----------- + +Driver supports the above part. + +The tc74 has an 8-bit sensor, with 1 degree centigrade resolution +and +- 2 degrees centigrade accuracy. + +Notes +----- + +Currently entering low power standby mode is not supported. diff --git a/Documentation/hwmon/thmc50 b/Documentation/hwmon/thmc50 deleted file mode 100644 index 6dba1b59b20c..000000000000 --- a/Documentation/hwmon/thmc50 +++ /dev/null @@ -1,90 +0,0 @@ -Kernel driver thmc50 -===================== - -Supported chips: - - * Analog Devices ADM1022 - - Prefix: 'adm1022' - - Addresses scanned: I2C 0x2c - 0x2e - - Datasheet: http://www.analog.com/en/prod/0,2877,ADM1022,00.html - - * Texas Instruments THMC50 - - Prefix: 'thmc50' - - Addresses scanned: I2C 0x2c - 0x2e - - Datasheet: http://www.ti.com/ - - -Author: Krzysztof Helt - -This driver was derived from the 2.4 kernel thmc50.c source file. - -Credits: - - thmc50.c (2.4 kernel): - - - Frodo Looijaard - - Philip Edelbrock - -Module Parameters ------------------ - -* adm1022_temp3: short array - List of adapter,address pairs to force chips into ADM1022 mode with - second remote temperature. This does not work for original THMC50 chips. - -Description ------------ - -The THMC50 implements: an internal temperature sensor, support for an -external diode-type temperature sensor (compatible w/ the diode sensor inside -many processors), and a controllable fan/analog_out DAC. For the temperature -sensors, limits can be set through the appropriate Overtemperature Shutdown -register and Hysteresis register. Each value can be set and read to half-degree -accuracy. An alarm is issued (usually to a connected LM78) when the -temperature gets higher then the Overtemperature Shutdown value; it stays on -until the temperature falls below the Hysteresis value. All temperatures are in -degrees Celsius, and are guaranteed within a range of -55 to +125 degrees. - -The THMC50 only updates its values each 1.5 seconds; reading it more often -will do no harm, but will return 'old' values. - -The THMC50 is usually used in combination with LM78-like chips, to measure -the temperature of the processor(s). - -The ADM1022 works the same as THMC50 but it is faster (5 Hz instead of -1 Hz for THMC50). It can be also put in a new mode to handle additional -remote temperature sensor. The driver use the mode set by BIOS by default. - -In case the BIOS is broken and the mode is set incorrectly, you can force -the mode with additional remote temperature with adm1022_temp3 parameter. -A typical symptom of wrong setting is a fan forced to full speed. - -Driver Features ---------------- - -The driver provides up to three temperatures: - -temp1 - - internal -temp2 - - remote -temp3 - - 2nd remote only for ADM1022 - -pwm1 - - fan speed (0 = stop, 255 = full) -pwm1_mode - - always 0 (DC mode) - -The value of 0 for pwm1 also forces FAN_OFF signal from the chip, -so it stops fans even if the value 0 into the ANALOG_OUT register does not. - -The driver was tested on Compaq AP550 with two ADM1022 chips (one works -in the temp3 mode), five temperature readings and two fans. - diff --git a/Documentation/hwmon/thmc50.rst b/Documentation/hwmon/thmc50.rst new file mode 100644 index 000000000000..cfff3885287d --- /dev/null +++ b/Documentation/hwmon/thmc50.rst @@ -0,0 +1,89 @@ +Kernel driver thmc50 +===================== + +Supported chips: + + * Analog Devices ADM1022 + + Prefix: 'adm1022' + + Addresses scanned: I2C 0x2c - 0x2e + + Datasheet: http://www.analog.com/en/prod/0,2877,ADM1022,00.html + + * Texas Instruments THMC50 + + Prefix: 'thmc50' + + Addresses scanned: I2C 0x2c - 0x2e + + Datasheet: http://www.ti.com/ + + +Author: Krzysztof Helt + +This driver was derived from the 2.4 kernel thmc50.c source file. + +Credits: + + thmc50.c (2.4 kernel): + + - Frodo Looijaard + - Philip Edelbrock + +Module Parameters +----------------- + +* adm1022_temp3: short array + List of adapter,address pairs to force chips into ADM1022 mode with + second remote temperature. This does not work for original THMC50 chips. + +Description +----------- + +The THMC50 implements: an internal temperature sensor, support for an +external diode-type temperature sensor (compatible w/ the diode sensor inside +many processors), and a controllable fan/analog_out DAC. For the temperature +sensors, limits can be set through the appropriate Overtemperature Shutdown +register and Hysteresis register. Each value can be set and read to half-degree +accuracy. An alarm is issued (usually to a connected LM78) when the +temperature gets higher then the Overtemperature Shutdown value; it stays on +until the temperature falls below the Hysteresis value. All temperatures are in +degrees Celsius, and are guaranteed within a range of -55 to +125 degrees. + +The THMC50 only updates its values each 1.5 seconds; reading it more often +will do no harm, but will return 'old' values. + +The THMC50 is usually used in combination with LM78-like chips, to measure +the temperature of the processor(s). + +The ADM1022 works the same as THMC50 but it is faster (5 Hz instead of +1 Hz for THMC50). It can be also put in a new mode to handle additional +remote temperature sensor. The driver use the mode set by BIOS by default. + +In case the BIOS is broken and the mode is set incorrectly, you can force +the mode with additional remote temperature with adm1022_temp3 parameter. +A typical symptom of wrong setting is a fan forced to full speed. + +Driver Features +--------------- + +The driver provides up to three temperatures: + +temp1 + - internal +temp2 + - remote +temp3 + - 2nd remote only for ADM1022 + +pwm1 + - fan speed (0 = stop, 255 = full) +pwm1_mode + - always 0 (DC mode) + +The value of 0 for pwm1 also forces FAN_OFF signal from the chip, +so it stops fans even if the value 0 into the ANALOG_OUT register does not. + +The driver was tested on Compaq AP550 with two ADM1022 chips (one works +in the temp3 mode), five temperature readings and two fans. diff --git a/Documentation/hwmon/tmp102 b/Documentation/hwmon/tmp102 deleted file mode 100644 index 5e34821df4ab..000000000000 --- a/Documentation/hwmon/tmp102 +++ /dev/null @@ -1,31 +0,0 @@ -Kernel driver tmp102 -==================== - -Supported chips: - - * Texas Instruments TMP102 - - Prefix: 'tmp102' - - Addresses scanned: none - - Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp102.html - -Author: - - Steven King - -Description ------------ - -The Texas Instruments TMP102 implements one temperature sensor. Limits can be -set through the Overtemperature Shutdown register and Hysteresis register. The -sensor is accurate to 0.5 degree over the range of -25 to +85 C, and to 1.0 -degree from -40 to +125 C. Resolution of the sensor is 0.0625 degree. The -operating temperature has a minimum of -55 C and a maximum of +150 C. - -The TMP102 has a programmable update rate that can select between 8, 4, 1, and -0.5 Hz. (Currently the driver only supports the default of 4 Hz). - -The driver provides the common sysfs-interface for temperatures (see -Documentation/hwmon/sysfs-interface under Temperatures). diff --git a/Documentation/hwmon/tmp102.rst b/Documentation/hwmon/tmp102.rst new file mode 100644 index 000000000000..b1f585531a88 --- /dev/null +++ b/Documentation/hwmon/tmp102.rst @@ -0,0 +1,31 @@ +Kernel driver tmp102 +==================== + +Supported chips: + + * Texas Instruments TMP102 + + Prefix: 'tmp102' + + Addresses scanned: none + + Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp102.html + +Author: + + Steven King + +Description +----------- + +The Texas Instruments TMP102 implements one temperature sensor. Limits can be +set through the Overtemperature Shutdown register and Hysteresis register. The +sensor is accurate to 0.5 degree over the range of -25 to +85 C, and to 1.0 +degree from -40 to +125 C. Resolution of the sensor is 0.0625 degree. The +operating temperature has a minimum of -55 C and a maximum of +150 C. + +The TMP102 has a programmable update rate that can select between 8, 4, 1, and +0.5 Hz. (Currently the driver only supports the default of 4 Hz). + +The driver provides the common sysfs-interface for temperatures (see +Documentation/hwmon/sysfs-interface.rst under Temperatures). diff --git a/Documentation/hwmon/tmp103 b/Documentation/hwmon/tmp103 deleted file mode 100644 index 7682a795e38c..000000000000 --- a/Documentation/hwmon/tmp103 +++ /dev/null @@ -1,33 +0,0 @@ -Kernel driver tmp103 -==================== - -Supported chips: - - * Texas Instruments TMP103 - - Prefix: 'tmp103' - - Addresses scanned: none - - Product info and datasheet: http://www.ti.com/product/tmp103 - -Author: - - Heiko Schocher - -Description ------------ - -The TMP103 is a digital output temperature sensor in a four-ball -wafer chip-scale package (WCSP). The TMP103 is capable of reading -temperatures to a resolution of 1°C. The TMP103 is specified for -operation over a temperature range of –40°C to +125°C. - -Resolution: 8 Bits -Accuracy: ±1°C Typ (–10°C to +100°C) - -The driver provides the common sysfs-interface for temperatures (see -Documentation/hwmon/sysfs-interface under Temperatures). - -Please refer how to instantiate this driver: -Documentation/i2c/instantiating-devices diff --git a/Documentation/hwmon/tmp103.rst b/Documentation/hwmon/tmp103.rst new file mode 100644 index 000000000000..15d25806d585 --- /dev/null +++ b/Documentation/hwmon/tmp103.rst @@ -0,0 +1,33 @@ +Kernel driver tmp103 +==================== + +Supported chips: + + * Texas Instruments TMP103 + + Prefix: 'tmp103' + + Addresses scanned: none + + Product info and datasheet: http://www.ti.com/product/tmp103 + +Author: + + Heiko Schocher + +Description +----------- + +The TMP103 is a digital output temperature sensor in a four-ball +wafer chip-scale package (WCSP). The TMP103 is capable of reading +temperatures to a resolution of 1°C. The TMP103 is specified for +operation over a temperature range of –40°C to +125°C. + +Resolution: 8 Bits +Accuracy: ±1°C Typ (–10°C to +100°C) + +The driver provides the common sysfs-interface for temperatures (see +Documentation/hwmon/sysfs-interface.rst under Temperatures). + +Please refer how to instantiate this driver: +Documentation/i2c/instantiating-devices diff --git a/Documentation/hwmon/tmp108 b/Documentation/hwmon/tmp108 deleted file mode 100644 index 7e08b7ef1e2f..000000000000 --- a/Documentation/hwmon/tmp108 +++ /dev/null @@ -1,41 +0,0 @@ -Kernel driver tmp108 -==================== - -Supported chips: - - * Texas Instruments TMP108 - - Prefix: 'tmp108' - - Addresses scanned: none - - Datasheet: http://www.ti.com/product/tmp108 - -Author: - - John Muir - -Description ------------ - -The Texas Instruments TMP108 implements one temperature sensor. An alert pin -can be set when temperatures exceed minimum or maximum values plus or minus a -hysteresis value. (This driver does not support interrupts for the alert pin, -and the device runs in comparator mode.) - -The sensor is accurate to 0.75C over the range of -25 to +85 C, and to 1.0 -degree from -40 to +125 C. Resolution of the sensor is 0.0625 degree. The -operating temperature has a minimum of -55 C and a maximum of +150 C. -Hysteresis values can be set to 0, 1, 2, or 4C. - -The TMP108 has a programmable update rate that can select between 8, 4, 1, and -0.5 Hz. - -By default the TMP108 reads the temperature continuously. To conserve power, -the TMP108 has a one-shot mode where the device is normally shut-down. When a -one shot is requested the temperature is read, the result can be retrieved, -and then the device is shut down automatically. (This driver only supports -continuous mode.) - -The driver provides the common sysfs-interface for temperatures (see -Documentation/hwmon/sysfs-interface under Temperatures). diff --git a/Documentation/hwmon/tmp108.rst b/Documentation/hwmon/tmp108.rst new file mode 100644 index 000000000000..5f4266a16cb2 --- /dev/null +++ b/Documentation/hwmon/tmp108.rst @@ -0,0 +1,41 @@ +Kernel driver tmp108 +==================== + +Supported chips: + + * Texas Instruments TMP108 + + Prefix: 'tmp108' + + Addresses scanned: none + + Datasheet: http://www.ti.com/product/tmp108 + +Author: + + John Muir + +Description +----------- + +The Texas Instruments TMP108 implements one temperature sensor. An alert pin +can be set when temperatures exceed minimum or maximum values plus or minus a +hysteresis value. (This driver does not support interrupts for the alert pin, +and the device runs in comparator mode.) + +The sensor is accurate to 0.75C over the range of -25 to +85 C, and to 1.0 +degree from -40 to +125 C. Resolution of the sensor is 0.0625 degree. The +operating temperature has a minimum of -55 C and a maximum of +150 C. +Hysteresis values can be set to 0, 1, 2, or 4C. + +The TMP108 has a programmable update rate that can select between 8, 4, 1, and +0.5 Hz. + +By default the TMP108 reads the temperature continuously. To conserve power, +the TMP108 has a one-shot mode where the device is normally shut-down. When a +one shot is requested the temperature is read, the result can be retrieved, +and then the device is shut down automatically. (This driver only supports +continuous mode.) + +The driver provides the common sysfs-interface for temperatures (see +Documentation/hwmon/sysfs-interface.rst under Temperatures). diff --git a/Documentation/hwmon/tmp401 b/Documentation/hwmon/tmp401 deleted file mode 100644 index bd865bbdb38d..000000000000 --- a/Documentation/hwmon/tmp401 +++ /dev/null @@ -1,93 +0,0 @@ -Kernel driver tmp401 -==================== - -Supported chips: - - * Texas Instruments TMP401 - - Prefix: 'tmp401' - - Addresses scanned: I2C 0x4c - - Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp401.html - - * Texas Instruments TMP411 - - Prefix: 'tmp411' - - Addresses scanned: I2C 0x4c, 0x4d, 0x4e - - Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp411.html - - * Texas Instruments TMP431 - - Prefix: 'tmp431' - - Addresses scanned: I2C 0x4c, 0x4d - - Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp431.html - - * Texas Instruments TMP432 - - Prefix: 'tmp432' - - Addresses scanned: I2C 0x4c, 0x4d - - Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp432.html - - * Texas Instruments TMP435 - - Prefix: 'tmp435' - - Addresses scanned: I2C 0x48 - 0x4f - - Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp435.html - - * Texas Instruments TMP461 - - Prefix: 'tmp461' - - Datasheet: http://www.ti.com/product/tmp461 - - - -Authors: - - - Hans de Goede - - Andre Prendel - -Description ------------ - -This driver implements support for Texas Instruments TMP401, TMP411, -TMP431, TMP432, TMP435, and TMP461 chips. These chips implement one or two -remote and one local temperature sensors. Temperature is measured in degrees -Celsius. Resolution of the remote sensor is 0.0625 degree. Local -sensor resolution can be set to 0.5, 0.25, 0.125 or 0.0625 degree (not -supported by the driver so far, so using the default resolution of 0.5 -degree). - -The driver provides the common sysfs-interface for temperatures (see -Documentation/hwmon/sysfs-interface under Temperatures). - -The TMP411 and TMP431 chips are compatible with TMP401. TMP411 provides -some additional features. - -* Minimum and Maximum temperature measured since power-on, chip-reset - - Exported via sysfs attributes tempX_lowest and tempX_highest. - -* Reset of historical minimum/maximum temperature measurements - - Exported via sysfs attribute temp_reset_history. Writing 1 to this - file triggers a reset. - -TMP432 is compatible with TMP401 and TMP431. It supports two external -temperature sensors. - -TMP461 is compatible with TMP401. It supports offset correction -that is applied to the remote sensor. - -* Sensor offset values are temperature values - - Exported via sysfs attribute tempX_offset diff --git a/Documentation/hwmon/tmp401.rst b/Documentation/hwmon/tmp401.rst new file mode 100644 index 000000000000..6a05a0719bc7 --- /dev/null +++ b/Documentation/hwmon/tmp401.rst @@ -0,0 +1,93 @@ +Kernel driver tmp401 +==================== + +Supported chips: + + * Texas Instruments TMP401 + + Prefix: 'tmp401' + + Addresses scanned: I2C 0x4c + + Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp401.html + + * Texas Instruments TMP411 + + Prefix: 'tmp411' + + Addresses scanned: I2C 0x4c, 0x4d, 0x4e + + Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp411.html + + * Texas Instruments TMP431 + + Prefix: 'tmp431' + + Addresses scanned: I2C 0x4c, 0x4d + + Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp431.html + + * Texas Instruments TMP432 + + Prefix: 'tmp432' + + Addresses scanned: I2C 0x4c, 0x4d + + Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp432.html + + * Texas Instruments TMP435 + + Prefix: 'tmp435' + + Addresses scanned: I2C 0x48 - 0x4f + + Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp435.html + + * Texas Instruments TMP461 + + Prefix: 'tmp461' + + Datasheet: http://www.ti.com/product/tmp461 + + + +Authors: + + - Hans de Goede + - Andre Prendel + +Description +----------- + +This driver implements support for Texas Instruments TMP401, TMP411, +TMP431, TMP432, TMP435, and TMP461 chips. These chips implement one or two +remote and one local temperature sensors. Temperature is measured in degrees +Celsius. Resolution of the remote sensor is 0.0625 degree. Local +sensor resolution can be set to 0.5, 0.25, 0.125 or 0.0625 degree (not +supported by the driver so far, so using the default resolution of 0.5 +degree). + +The driver provides the common sysfs-interface for temperatures (see +Documentation/hwmon/sysfs-interface.rst under Temperatures). + +The TMP411 and TMP431 chips are compatible with TMP401. TMP411 provides +some additional features. + +* Minimum and Maximum temperature measured since power-on, chip-reset + + Exported via sysfs attributes tempX_lowest and tempX_highest. + +* Reset of historical minimum/maximum temperature measurements + + Exported via sysfs attribute temp_reset_history. Writing 1 to this + file triggers a reset. + +TMP432 is compatible with TMP401 and TMP431. It supports two external +temperature sensors. + +TMP461 is compatible with TMP401. It supports offset correction +that is applied to the remote sensor. + +* Sensor offset values are temperature values + + Exported via sysfs attribute tempX_offset diff --git a/Documentation/hwmon/tmp421 b/Documentation/hwmon/tmp421 deleted file mode 100644 index 1ba926a3605c..000000000000 --- a/Documentation/hwmon/tmp421 +++ /dev/null @@ -1,66 +0,0 @@ -Kernel driver tmp421 -==================== - -Supported chips: - - * Texas Instruments TMP421 - - Prefix: 'tmp421' - - Addresses scanned: I2C 0x2a, 0x4c, 0x4d, 0x4e and 0x4f - - Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp421.html - - * Texas Instruments TMP422 - - Prefix: 'tmp422' - - Addresses scanned: I2C 0x4c, 0x4d, 0x4e and 0x4f - - Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp421.html - - * Texas Instruments TMP423 - - Prefix: 'tmp423' - - Addresses scanned: I2C 0x4c and 0x4d - - Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp421.html - - * Texas Instruments TMP441 - - Prefix: 'tmp441' - - Addresses scanned: I2C 0x2a, 0x4c, 0x4d, 0x4e and 0x4f - - Datasheet: http://www.ti.com/product/tmp441 - - * Texas Instruments TMP442 - - Prefix: 'tmp442' - - Addresses scanned: I2C 0x4c and 0x4d - - Datasheet: http://www.ti.com/product/tmp442 - -Authors: - - Andre Prendel - -Description ------------ - -This driver implements support for Texas Instruments TMP421, TMP422, -TMP423, TMP441, and TMP442 temperature sensor chips. These chips -implement one local and up to one (TMP421, TMP441), up to two (TMP422, -TMP442) or up to three (TMP423) remote sensors. Temperature is measured -in degrees Celsius. The chips are wired over I2C/SMBus and specified -over a temperature range of -40 to +125 degrees Celsius. Resolution -for both the local and remote channels is 0.0625 degree C. - -The chips support only temperature measurement. The driver exports -the temperature values via the following sysfs files: - -**temp[1-4]_input** - -**temp[2-4]_fault** diff --git a/Documentation/hwmon/tmp421.rst b/Documentation/hwmon/tmp421.rst new file mode 100644 index 000000000000..1ba926a3605c --- /dev/null +++ b/Documentation/hwmon/tmp421.rst @@ -0,0 +1,66 @@ +Kernel driver tmp421 +==================== + +Supported chips: + + * Texas Instruments TMP421 + + Prefix: 'tmp421' + + Addresses scanned: I2C 0x2a, 0x4c, 0x4d, 0x4e and 0x4f + + Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp421.html + + * Texas Instruments TMP422 + + Prefix: 'tmp422' + + Addresses scanned: I2C 0x4c, 0x4d, 0x4e and 0x4f + + Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp421.html + + * Texas Instruments TMP423 + + Prefix: 'tmp423' + + Addresses scanned: I2C 0x4c and 0x4d + + Datasheet: http://focus.ti.com/docs/prod/folders/print/tmp421.html + + * Texas Instruments TMP441 + + Prefix: 'tmp441' + + Addresses scanned: I2C 0x2a, 0x4c, 0x4d, 0x4e and 0x4f + + Datasheet: http://www.ti.com/product/tmp441 + + * Texas Instruments TMP442 + + Prefix: 'tmp442' + + Addresses scanned: I2C 0x4c and 0x4d + + Datasheet: http://www.ti.com/product/tmp442 + +Authors: + + Andre Prendel + +Description +----------- + +This driver implements support for Texas Instruments TMP421, TMP422, +TMP423, TMP441, and TMP442 temperature sensor chips. These chips +implement one local and up to one (TMP421, TMP441), up to two (TMP422, +TMP442) or up to three (TMP423) remote sensors. Temperature is measured +in degrees Celsius. The chips are wired over I2C/SMBus and specified +over a temperature range of -40 to +125 degrees Celsius. Resolution +for both the local and remote channels is 0.0625 degree C. + +The chips support only temperature measurement. The driver exports +the temperature values via the following sysfs files: + +**temp[1-4]_input** + +**temp[2-4]_fault** diff --git a/Documentation/hwmon/tps40422 b/Documentation/hwmon/tps40422 deleted file mode 100644 index 359751eb5ed4..000000000000 --- a/Documentation/hwmon/tps40422 +++ /dev/null @@ -1,73 +0,0 @@ -Kernel driver tps40422 -====================== - -Supported chips: - - * TI TPS40422 - - Prefix: 'tps40422' - - Addresses scanned: - - - Datasheet: http://www.ti.com/lit/gpn/tps40422 - -Author: Zhu Laiwen - - -Description ------------ - -This driver supports TI TPS40422 Dual-Output or Two-Phase Synchronous Buck -Controller with PMBus - -The driver is a client driver to the core PMBus driver. -Please see Documentation/hwmon/pmbus for details on PMBus client drivers. - - -Usage Notes ------------ - -This driver does not auto-detect devices. You will have to instantiate the -devices explicitly. Please see Documentation/i2c/instantiating-devices for -details. - - -Platform data support ---------------------- - -The driver supports standard PMBus driver platform data. - - -Sysfs entries -------------- - -The following attributes are supported. - -======================= ======================================================= -in[1-2]_label "vout[1-2]" -in[1-2]_input Measured voltage. From READ_VOUT register. -in[1-2]_alarm voltage alarm. - -curr[1-2]_input Measured current. From READ_IOUT register. -curr[1-2]_label "iout[1-2]" -curr1_max Maximum current. From IOUT_OC_WARN_LIMIT register. -curr1_crit Critical maximum current. From IOUT_OC_FAULT_LIMIT - register. -curr1_max_alarm Current high alarm. From IOUT_OC_WARN_LIMIT status. -curr1_crit_alarm Current critical high alarm. From IOUT_OC_FAULT status. -curr2_alarm Current high alarm. From IOUT_OC_WARNING status. - -temp1_input Measured temperature. From READ_TEMPERATURE_2 register - on page 0. -temp1_max Maximum temperature. From OT_WARN_LIMIT register. -temp1_crit Critical high temperature. From OT_FAULT_LIMIT register. -temp1_max_alarm Chip temperature high alarm. Set by comparing - READ_TEMPERATURE_2 on page 0 with OT_WARN_LIMIT if - TEMP_OT_WARNING status is set. -temp1_crit_alarm Chip temperature critical high alarm. Set by comparing - READ_TEMPERATURE_2 on page 0 with OT_FAULT_LIMIT if - TEMP_OT_FAULT status is set. -temp2_input Measured temperature. From READ_TEMPERATURE_2 register - on page 1. -temp2_alarm Chip temperature alarm on page 1. -======================= ======================================================= diff --git a/Documentation/hwmon/tps40422.rst b/Documentation/hwmon/tps40422.rst new file mode 100644 index 000000000000..b691e30479dd --- /dev/null +++ b/Documentation/hwmon/tps40422.rst @@ -0,0 +1,73 @@ +Kernel driver tps40422 +====================== + +Supported chips: + + * TI TPS40422 + + Prefix: 'tps40422' + + Addresses scanned: - + + Datasheet: http://www.ti.com/lit/gpn/tps40422 + +Author: Zhu Laiwen + + +Description +----------- + +This driver supports TI TPS40422 Dual-Output or Two-Phase Synchronous Buck +Controller with PMBus + +The driver is a client driver to the core PMBus driver. +Please see Documentation/hwmon/pmbus.rst for details on PMBus client drivers. + + +Usage Notes +----------- + +This driver does not auto-detect devices. You will have to instantiate the +devices explicitly. Please see Documentation/i2c/instantiating-devices for +details. + + +Platform data support +--------------------- + +The driver supports standard PMBus driver platform data. + + +Sysfs entries +------------- + +The following attributes are supported. + +======================= ======================================================= +in[1-2]_label "vout[1-2]" +in[1-2]_input Measured voltage. From READ_VOUT register. +in[1-2]_alarm voltage alarm. + +curr[1-2]_input Measured current. From READ_IOUT register. +curr[1-2]_label "iout[1-2]" +curr1_max Maximum current. From IOUT_OC_WARN_LIMIT register. +curr1_crit Critical maximum current. From IOUT_OC_FAULT_LIMIT + register. +curr1_max_alarm Current high alarm. From IOUT_OC_WARN_LIMIT status. +curr1_crit_alarm Current critical high alarm. From IOUT_OC_FAULT status. +curr2_alarm Current high alarm. From IOUT_OC_WARNING status. + +temp1_input Measured temperature. From READ_TEMPERATURE_2 register + on page 0. +temp1_max Maximum temperature. From OT_WARN_LIMIT register. +temp1_crit Critical high temperature. From OT_FAULT_LIMIT register. +temp1_max_alarm Chip temperature high alarm. Set by comparing + READ_TEMPERATURE_2 on page 0 with OT_WARN_LIMIT if + TEMP_OT_WARNING status is set. +temp1_crit_alarm Chip temperature critical high alarm. Set by comparing + READ_TEMPERATURE_2 on page 0 with OT_FAULT_LIMIT if + TEMP_OT_FAULT status is set. +temp2_input Measured temperature. From READ_TEMPERATURE_2 register + on page 1. +temp2_alarm Chip temperature alarm on page 1. +======================= ======================================================= diff --git a/Documentation/hwmon/twl4030-madc-hwmon b/Documentation/hwmon/twl4030-madc-hwmon deleted file mode 100644 index 22c885383b11..000000000000 --- a/Documentation/hwmon/twl4030-madc-hwmon +++ /dev/null @@ -1,49 +0,0 @@ -Kernel driver twl4030-madc -========================== - -Supported chips: - - * Texas Instruments TWL4030 - - Prefix: 'twl4030-madc' - - -Authors: - J Keerthy - -Description ------------ - -The Texas Instruments TWL4030 is a Power Management and Audio Circuit. Among -other things it contains a 10-bit A/D converter MADC. The converter has 16 -channels which can be used in different modes. - - -See this table for the meaning of the different channels - -======= ========================================================== -Channel Signal -======= ========================================================== -0 Battery type(BTYPE) -1 BCI: Battery temperature (BTEMP) -2 GP analog input -3 GP analog input -4 GP analog input -5 GP analog input -6 GP analog input -7 GP analog input -8 BCI: VBUS voltage(VBUS) -9 Backup Battery voltage (VBKP) -10 BCI: Battery charger current (ICHG) -11 BCI: Battery charger voltage (VCHG) -12 BCI: Main battery voltage (VBAT) -13 Reserved -14 Reserved -15 VRUSB Supply/Speaker left/Speaker right polarization level -======= ========================================================== - - -The Sysfs nodes will represent the voltage in the units of mV, -the temperature channel shows the converted temperature in -degree Celsius. The Battery charging current channel represents -battery charging current in mA. diff --git a/Documentation/hwmon/twl4030-madc-hwmon.rst b/Documentation/hwmon/twl4030-madc-hwmon.rst new file mode 100644 index 000000000000..22c885383b11 --- /dev/null +++ b/Documentation/hwmon/twl4030-madc-hwmon.rst @@ -0,0 +1,49 @@ +Kernel driver twl4030-madc +========================== + +Supported chips: + + * Texas Instruments TWL4030 + + Prefix: 'twl4030-madc' + + +Authors: + J Keerthy + +Description +----------- + +The Texas Instruments TWL4030 is a Power Management and Audio Circuit. Among +other things it contains a 10-bit A/D converter MADC. The converter has 16 +channels which can be used in different modes. + + +See this table for the meaning of the different channels + +======= ========================================================== +Channel Signal +======= ========================================================== +0 Battery type(BTYPE) +1 BCI: Battery temperature (BTEMP) +2 GP analog input +3 GP analog input +4 GP analog input +5 GP analog input +6 GP analog input +7 GP analog input +8 BCI: VBUS voltage(VBUS) +9 Backup Battery voltage (VBKP) +10 BCI: Battery charger current (ICHG) +11 BCI: Battery charger voltage (VCHG) +12 BCI: Main battery voltage (VBAT) +13 Reserved +14 Reserved +15 VRUSB Supply/Speaker left/Speaker right polarization level +======= ========================================================== + + +The Sysfs nodes will represent the voltage in the units of mV, +the temperature channel shows the converted temperature in +degree Celsius. The Battery charging current channel represents +battery charging current in mA. diff --git a/Documentation/hwmon/ucd9000 b/Documentation/hwmon/ucd9000 deleted file mode 100644 index d69061b7312c..000000000000 --- a/Documentation/hwmon/ucd9000 +++ /dev/null @@ -1,129 +0,0 @@ -Kernel driver ucd9000 -===================== - -Supported chips: - - * TI UCD90120, UCD90124, UCD90160, UCD9090, and UCD90910 - - Prefixes: 'ucd90120', 'ucd90124', 'ucd90160', 'ucd9090', 'ucd90910' - - Addresses scanned: - - - Datasheets: - - - http://focus.ti.com/lit/ds/symlink/ucd90120.pdf - - http://focus.ti.com/lit/ds/symlink/ucd90124.pdf - - http://focus.ti.com/lit/ds/symlink/ucd90160.pdf - - http://focus.ti.com/lit/ds/symlink/ucd9090.pdf - - http://focus.ti.com/lit/ds/symlink/ucd90910.pdf - -Author: Guenter Roeck - - -Description ------------ - -From datasheets: - -The UCD90120 Power Supply Sequencer and System Health Monitor monitors and -sequences up to 12 independent voltage rails. The device integrates a 12-bit -ADC with a 2.5V internal reference for monitoring up to 13 power supply voltage, -current, or temperature inputs. - -The UCD90124 is a 12-rail PMBus/I2C addressable power-supply sequencer and -system-health monitor. The device integrates a 12-bit ADC for monitoring up to -13 power-supply voltage, current, or temperature inputs. Twenty-six GPIO pins -can be used for power supply enables, power-on reset signals, external -interrupts, cascading, or other system functions. Twelve of these pins offer PWM -functionality. Using these pins, the UCD90124 offers support for fan control, -margining, and general-purpose PWM functions. - -The UCD90160 is a 16-rail PMBus/I2C addressable power-supply sequencer and -monitor. The device integrates a 12-bit ADC for monitoring up to 16 power-supply -voltage inputs. Twenty-six GPIO pins can be used for power supply enables, -power-on reset signals, external interrupts, cascading, or other system -functions. Twelve of these pins offer PWM functionality. Using these pins, the -UCD90160 offers support for margining, and general-purpose PWM functions. - -The UCD9090 is a 10-rail PMBus/I2C addressable power-supply sequencer and -monitor. The device integrates a 12-bit ADC for monitoring up to 10 power-supply -voltage inputs. Twenty-three GPIO pins can be used for power supply enables, -power-on reset signals, external interrupts, cascading, or other system -functions. Ten of these pins offer PWM functionality. Using these pins, the -UCD9090 offers support for margining, and general-purpose PWM functions. - -The UCD90910 is a ten-rail I2C / PMBus addressable power-supply sequencer and -system-health monitor. The device integrates a 12-bit ADC for monitoring up to -13 power-supply voltage, current, or temperature inputs. - -This driver is a client driver to the core PMBus driver. Please see -Documentation/hwmon/pmbus for details on PMBus client drivers. - - -Usage Notes ------------ - -This driver does not auto-detect devices. You will have to instantiate the -devices explicitly. Please see Documentation/i2c/instantiating-devices for -details. - - -Platform data support ---------------------- - -The driver supports standard PMBus driver platform data. Please see -Documentation/hwmon/pmbus for details. - - -Sysfs entries -------------- - -The following attributes are supported. Limits are read-write; all other -attributes are read-only. - -======================= ======================================================== -in[1-12]_label "vout[1-12]". -in[1-12]_input Measured voltage. From READ_VOUT register. -in[1-12]_min Minimum Voltage. From VOUT_UV_WARN_LIMIT register. -in[1-12]_max Maximum voltage. From VOUT_OV_WARN_LIMIT register. -in[1-12]_lcrit Critical minimum Voltage. VOUT_UV_FAULT_LIMIT register. -in[1-12]_crit Critical maximum voltage. From VOUT_OV_FAULT_LIMIT - register. -in[1-12]_min_alarm Voltage low alarm. From VOLTAGE_UV_WARNING status. -in[1-12]_max_alarm Voltage high alarm. From VOLTAGE_OV_WARNING status. -in[1-12]_lcrit_alarm Voltage critical low alarm. From VOLTAGE_UV_FAULT - status. -in[1-12]_crit_alarm Voltage critical high alarm. From VOLTAGE_OV_FAULT - status. - -curr[1-12]_label "iout[1-12]". -curr[1-12]_input Measured current. From READ_IOUT register. -curr[1-12]_max Maximum current. From IOUT_OC_WARN_LIMIT register. -curr[1-12]_lcrit Critical minimum output current. From - IOUT_UC_FAULT_LIMIT register. -curr[1-12]_crit Critical maximum current. From IOUT_OC_FAULT_LIMIT - register. -curr[1-12]_max_alarm Current high alarm. From IOUT_OC_WARNING status. -curr[1-12]_crit_alarm Current critical high alarm. From IOUT_OC_FAULT status. - - For each attribute index, either voltage or current is - reported, but not both. If voltage or current is - reported depends on the chip configuration. - -temp[1-2]_input Measured temperatures. From READ_TEMPERATURE_1 and - READ_TEMPERATURE_2 registers. -temp[1-2]_max Maximum temperature. From OT_WARN_LIMIT register. -temp[1-2]_crit Critical high temperature. From OT_FAULT_LIMIT register. -temp[1-2]_max_alarm Temperature high alarm. -temp[1-2]_crit_alarm Temperature critical high alarm. - -fan[1-4]_input Fan RPM. -fan[1-4]_alarm Fan alarm. -fan[1-4]_fault Fan fault. - - Fan attributes are only available on chips supporting - fan control (UCD90124, UCD90910). Attribute files are - created only for enabled fans. - Note that even though UCD90910 supports up to 10 fans, - only up to four fans are currently supported. -======================= ======================================================== diff --git a/Documentation/hwmon/ucd9000.rst b/Documentation/hwmon/ucd9000.rst new file mode 100644 index 000000000000..ebc4f2b3bfea --- /dev/null +++ b/Documentation/hwmon/ucd9000.rst @@ -0,0 +1,129 @@ +Kernel driver ucd9000 +===================== + +Supported chips: + + * TI UCD90120, UCD90124, UCD90160, UCD9090, and UCD90910 + + Prefixes: 'ucd90120', 'ucd90124', 'ucd90160', 'ucd9090', 'ucd90910' + + Addresses scanned: - + + Datasheets: + + - http://focus.ti.com/lit/ds/symlink/ucd90120.pdf + - http://focus.ti.com/lit/ds/symlink/ucd90124.pdf + - http://focus.ti.com/lit/ds/symlink/ucd90160.pdf + - http://focus.ti.com/lit/ds/symlink/ucd9090.pdf + - http://focus.ti.com/lit/ds/symlink/ucd90910.pdf + +Author: Guenter Roeck + + +Description +----------- + +From datasheets: + +The UCD90120 Power Supply Sequencer and System Health Monitor monitors and +sequences up to 12 independent voltage rails. The device integrates a 12-bit +ADC with a 2.5V internal reference for monitoring up to 13 power supply voltage, +current, or temperature inputs. + +The UCD90124 is a 12-rail PMBus/I2C addressable power-supply sequencer and +system-health monitor. The device integrates a 12-bit ADC for monitoring up to +13 power-supply voltage, current, or temperature inputs. Twenty-six GPIO pins +can be used for power supply enables, power-on reset signals, external +interrupts, cascading, or other system functions. Twelve of these pins offer PWM +functionality. Using these pins, the UCD90124 offers support for fan control, +margining, and general-purpose PWM functions. + +The UCD90160 is a 16-rail PMBus/I2C addressable power-supply sequencer and +monitor. The device integrates a 12-bit ADC for monitoring up to 16 power-supply +voltage inputs. Twenty-six GPIO pins can be used for power supply enables, +power-on reset signals, external interrupts, cascading, or other system +functions. Twelve of these pins offer PWM functionality. Using these pins, the +UCD90160 offers support for margining, and general-purpose PWM functions. + +The UCD9090 is a 10-rail PMBus/I2C addressable power-supply sequencer and +monitor. The device integrates a 12-bit ADC for monitoring up to 10 power-supply +voltage inputs. Twenty-three GPIO pins can be used for power supply enables, +power-on reset signals, external interrupts, cascading, or other system +functions. Ten of these pins offer PWM functionality. Using these pins, the +UCD9090 offers support for margining, and general-purpose PWM functions. + +The UCD90910 is a ten-rail I2C / PMBus addressable power-supply sequencer and +system-health monitor. The device integrates a 12-bit ADC for monitoring up to +13 power-supply voltage, current, or temperature inputs. + +This driver is a client driver to the core PMBus driver. Please see +Documentation/hwmon/pmbus.rst for details on PMBus client drivers. + + +Usage Notes +----------- + +This driver does not auto-detect devices. You will have to instantiate the +devices explicitly. Please see Documentation/i2c/instantiating-devices for +details. + + +Platform data support +--------------------- + +The driver supports standard PMBus driver platform data. Please see +Documentation/hwmon/pmbus.rst for details. + + +Sysfs entries +------------- + +The following attributes are supported. Limits are read-write; all other +attributes are read-only. + +======================= ======================================================== +in[1-12]_label "vout[1-12]". +in[1-12]_input Measured voltage. From READ_VOUT register. +in[1-12]_min Minimum Voltage. From VOUT_UV_WARN_LIMIT register. +in[1-12]_max Maximum voltage. From VOUT_OV_WARN_LIMIT register. +in[1-12]_lcrit Critical minimum Voltage. VOUT_UV_FAULT_LIMIT register. +in[1-12]_crit Critical maximum voltage. From VOUT_OV_FAULT_LIMIT + register. +in[1-12]_min_alarm Voltage low alarm. From VOLTAGE_UV_WARNING status. +in[1-12]_max_alarm Voltage high alarm. From VOLTAGE_OV_WARNING status. +in[1-12]_lcrit_alarm Voltage critical low alarm. From VOLTAGE_UV_FAULT + status. +in[1-12]_crit_alarm Voltage critical high alarm. From VOLTAGE_OV_FAULT + status. + +curr[1-12]_label "iout[1-12]". +curr[1-12]_input Measured current. From READ_IOUT register. +curr[1-12]_max Maximum current. From IOUT_OC_WARN_LIMIT register. +curr[1-12]_lcrit Critical minimum output current. From + IOUT_UC_FAULT_LIMIT register. +curr[1-12]_crit Critical maximum current. From IOUT_OC_FAULT_LIMIT + register. +curr[1-12]_max_alarm Current high alarm. From IOUT_OC_WARNING status. +curr[1-12]_crit_alarm Current critical high alarm. From IOUT_OC_FAULT status. + + For each attribute index, either voltage or current is + reported, but not both. If voltage or current is + reported depends on the chip configuration. + +temp[1-2]_input Measured temperatures. From READ_TEMPERATURE_1 and + READ_TEMPERATURE_2 registers. +temp[1-2]_max Maximum temperature. From OT_WARN_LIMIT register. +temp[1-2]_crit Critical high temperature. From OT_FAULT_LIMIT register. +temp[1-2]_max_alarm Temperature high alarm. +temp[1-2]_crit_alarm Temperature critical high alarm. + +fan[1-4]_input Fan RPM. +fan[1-4]_alarm Fan alarm. +fan[1-4]_fault Fan fault. + + Fan attributes are only available on chips supporting + fan control (UCD90124, UCD90910). Attribute files are + created only for enabled fans. + Note that even though UCD90910 supports up to 10 fans, + only up to four fans are currently supported. +======================= ======================================================== diff --git a/Documentation/hwmon/ucd9200 b/Documentation/hwmon/ucd9200 deleted file mode 100644 index 44eda4a579b6..000000000000 --- a/Documentation/hwmon/ucd9200 +++ /dev/null @@ -1,124 +0,0 @@ -Kernel driver ucd9200 -===================== - -Supported chips: - - * TI UCD9220, UCD9222, UCD9224, UCD9240, UCD9244, UCD9246, and UCD9248 - - Prefixes: 'ucd9220', 'ucd9222', 'ucd9224', 'ucd9240', 'ucd9244', 'ucd9246', - 'ucd9248' - - Addresses scanned: - - - Datasheets: - - - http://focus.ti.com/lit/ds/symlink/ucd9220.pdf - - http://focus.ti.com/lit/ds/symlink/ucd9222.pdf - - http://focus.ti.com/lit/ds/symlink/ucd9224.pdf - - http://focus.ti.com/lit/ds/symlink/ucd9240.pdf - - http://focus.ti.com/lit/ds/symlink/ucd9244.pdf - - http://focus.ti.com/lit/ds/symlink/ucd9246.pdf - - http://focus.ti.com/lit/ds/symlink/ucd9248.pdf - -Author: Guenter Roeck - - -Description ------------ - -[From datasheets] UCD9220, UCD9222, UCD9224, UCD9240, UCD9244, UCD9246, and -UCD9248 are multi-rail, multi-phase synchronous buck digital PWM controllers -designed for non-isolated DC/DC power applications. The devices integrate -dedicated circuitry for DC/DC loop management with flash memory and a serial -interface to support configuration, monitoring and management. - -This driver is a client driver to the core PMBus driver. Please see -Documentation/hwmon/pmbus for details on PMBus client drivers. - - -Usage Notes ------------ - -This driver does not auto-detect devices. You will have to instantiate the -devices explicitly. Please see Documentation/i2c/instantiating-devices for -details. - - -Platform data support ---------------------- - -The driver supports standard PMBus driver platform data. Please see -Documentation/hwmon/pmbus for details. - - -Sysfs entries -------------- - -The following attributes are supported. Limits are read-write; all other -attributes are read-only. - -======================= ======================================================== -in1_label "vin". -in1_input Measured voltage. From READ_VIN register. -in1_min Minimum Voltage. From VIN_UV_WARN_LIMIT register. -in1_max Maximum voltage. From VIN_OV_WARN_LIMIT register. -in1_lcrit Critical minimum Voltage. VIN_UV_FAULT_LIMIT register. -in1_crit Critical maximum voltage. From VIN_OV_FAULT_LIMIT - register. -in1_min_alarm Voltage low alarm. From VIN_UV_WARNING status. -in1_max_alarm Voltage high alarm. From VIN_OV_WARNING status. -in1_lcrit_alarm Voltage critical low alarm. From VIN_UV_FAULT status. -in1_crit_alarm Voltage critical high alarm. From VIN_OV_FAULT status. - -in[2-5]_label "vout[1-4]". -in[2-5]_input Measured voltage. From READ_VOUT register. -in[2-5]_min Minimum Voltage. From VOUT_UV_WARN_LIMIT register. -in[2-5]_max Maximum voltage. From VOUT_OV_WARN_LIMIT register. -in[2-5]_lcrit Critical minimum Voltage. VOUT_UV_FAULT_LIMIT register. -in[2-5]_crit Critical maximum voltage. From VOUT_OV_FAULT_LIMIT - register. -in[2-5]_min_alarm Voltage low alarm. From VOLTAGE_UV_WARNING status. -in[2-5]_max_alarm Voltage high alarm. From VOLTAGE_OV_WARNING status. -in[2-5]_lcrit_alarm Voltage critical low alarm. From VOLTAGE_UV_FAULT - status. -in[2-5]_crit_alarm Voltage critical high alarm. From VOLTAGE_OV_FAULT - status. - -curr1_label "iin". -curr1_input Measured current. From READ_IIN register. - -curr[2-5]_label "iout[1-4]". -curr[2-5]_input Measured current. From READ_IOUT register. -curr[2-5]_max Maximum current. From IOUT_OC_WARN_LIMIT register. -curr[2-5]_lcrit Critical minimum output current. From - IOUT_UC_FAULT_LIMIT register. -curr[2-5]_crit Critical maximum current. From IOUT_OC_FAULT_LIMIT - register. -curr[2-5]_max_alarm Current high alarm. From IOUT_OC_WARNING status. -curr[2-5]_crit_alarm Current critical high alarm. From IOUT_OC_FAULT status. - -power1_input Measured input power. From READ_PIN register. -power1_label "pin" - -power[2-5]_input Measured output power. From READ_POUT register. -power[2-5]_label "pout[1-4]" - - The number of output voltage, current, and power - attribute sets is determined by the number of enabled - rails. See chip datasheets for details. - -temp[1-5]_input Measured temperatures. From READ_TEMPERATURE_1 and - READ_TEMPERATURE_2 registers. - temp1 is the chip internal temperature. temp[2-5] are - rail temperatures. temp[2-5] attributes are only - created for enabled rails. See chip datasheets for - details. -temp[1-5]_max Maximum temperature. From OT_WARN_LIMIT register. -temp[1-5]_crit Critical high temperature. From OT_FAULT_LIMIT register. -temp[1-5]_max_alarm Temperature high alarm. -temp[1-5]_crit_alarm Temperature critical high alarm. - -fan1_input Fan RPM. ucd9240 only. -fan1_alarm Fan alarm. ucd9240 only. -fan1_fault Fan fault. ucd9240 only. -======================= ======================================================== diff --git a/Documentation/hwmon/ucd9200.rst b/Documentation/hwmon/ucd9200.rst new file mode 100644 index 000000000000..b819dfd75f71 --- /dev/null +++ b/Documentation/hwmon/ucd9200.rst @@ -0,0 +1,124 @@ +Kernel driver ucd9200 +===================== + +Supported chips: + + * TI UCD9220, UCD9222, UCD9224, UCD9240, UCD9244, UCD9246, and UCD9248 + + Prefixes: 'ucd9220', 'ucd9222', 'ucd9224', 'ucd9240', 'ucd9244', 'ucd9246', + 'ucd9248' + + Addresses scanned: - + + Datasheets: + + - http://focus.ti.com/lit/ds/symlink/ucd9220.pdf + - http://focus.ti.com/lit/ds/symlink/ucd9222.pdf + - http://focus.ti.com/lit/ds/symlink/ucd9224.pdf + - http://focus.ti.com/lit/ds/symlink/ucd9240.pdf + - http://focus.ti.com/lit/ds/symlink/ucd9244.pdf + - http://focus.ti.com/lit/ds/symlink/ucd9246.pdf + - http://focus.ti.com/lit/ds/symlink/ucd9248.pdf + +Author: Guenter Roeck + + +Description +----------- + +[From datasheets] UCD9220, UCD9222, UCD9224, UCD9240, UCD9244, UCD9246, and +UCD9248 are multi-rail, multi-phase synchronous buck digital PWM controllers +designed for non-isolated DC/DC power applications. The devices integrate +dedicated circuitry for DC/DC loop management with flash memory and a serial +interface to support configuration, monitoring and management. + +This driver is a client driver to the core PMBus driver. Please see +Documentation/hwmon/pmbus.rst for details on PMBus client drivers. + + +Usage Notes +----------- + +This driver does not auto-detect devices. You will have to instantiate the +devices explicitly. Please see Documentation/i2c/instantiating-devices for +details. + + +Platform data support +--------------------- + +The driver supports standard PMBus driver platform data. Please see +Documentation/hwmon/pmbus.rst for details. + + +Sysfs entries +------------- + +The following attributes are supported. Limits are read-write; all other +attributes are read-only. + +======================= ======================================================== +in1_label "vin". +in1_input Measured voltage. From READ_VIN register. +in1_min Minimum Voltage. From VIN_UV_WARN_LIMIT register. +in1_max Maximum voltage. From VIN_OV_WARN_LIMIT register. +in1_lcrit Critical minimum Voltage. VIN_UV_FAULT_LIMIT register. +in1_crit Critical maximum voltage. From VIN_OV_FAULT_LIMIT + register. +in1_min_alarm Voltage low alarm. From VIN_UV_WARNING status. +in1_max_alarm Voltage high alarm. From VIN_OV_WARNING status. +in1_lcrit_alarm Voltage critical low alarm. From VIN_UV_FAULT status. +in1_crit_alarm Voltage critical high alarm. From VIN_OV_FAULT status. + +in[2-5]_label "vout[1-4]". +in[2-5]_input Measured voltage. From READ_VOUT register. +in[2-5]_min Minimum Voltage. From VOUT_UV_WARN_LIMIT register. +in[2-5]_max Maximum voltage. From VOUT_OV_WARN_LIMIT register. +in[2-5]_lcrit Critical minimum Voltage. VOUT_UV_FAULT_LIMIT register. +in[2-5]_crit Critical maximum voltage. From VOUT_OV_FAULT_LIMIT + register. +in[2-5]_min_alarm Voltage low alarm. From VOLTAGE_UV_WARNING status. +in[2-5]_max_alarm Voltage high alarm. From VOLTAGE_OV_WARNING status. +in[2-5]_lcrit_alarm Voltage critical low alarm. From VOLTAGE_UV_FAULT + status. +in[2-5]_crit_alarm Voltage critical high alarm. From VOLTAGE_OV_FAULT + status. + +curr1_label "iin". +curr1_input Measured current. From READ_IIN register. + +curr[2-5]_label "iout[1-4]". +curr[2-5]_input Measured current. From READ_IOUT register. +curr[2-5]_max Maximum current. From IOUT_OC_WARN_LIMIT register. +curr[2-5]_lcrit Critical minimum output current. From + IOUT_UC_FAULT_LIMIT register. +curr[2-5]_crit Critical maximum current. From IOUT_OC_FAULT_LIMIT + register. +curr[2-5]_max_alarm Current high alarm. From IOUT_OC_WARNING status. +curr[2-5]_crit_alarm Current critical high alarm. From IOUT_OC_FAULT status. + +power1_input Measured input power. From READ_PIN register. +power1_label "pin" + +power[2-5]_input Measured output power. From READ_POUT register. +power[2-5]_label "pout[1-4]" + + The number of output voltage, current, and power + attribute sets is determined by the number of enabled + rails. See chip datasheets for details. + +temp[1-5]_input Measured temperatures. From READ_TEMPERATURE_1 and + READ_TEMPERATURE_2 registers. + temp1 is the chip internal temperature. temp[2-5] are + rail temperatures. temp[2-5] attributes are only + created for enabled rails. See chip datasheets for + details. +temp[1-5]_max Maximum temperature. From OT_WARN_LIMIT register. +temp[1-5]_crit Critical high temperature. From OT_FAULT_LIMIT register. +temp[1-5]_max_alarm Temperature high alarm. +temp[1-5]_crit_alarm Temperature critical high alarm. + +fan1_input Fan RPM. ucd9240 only. +fan1_alarm Fan alarm. ucd9240 only. +fan1_fault Fan fault. ucd9240 only. +======================= ======================================================== diff --git a/Documentation/hwmon/userspace-tools b/Documentation/hwmon/userspace-tools deleted file mode 100644 index bf3797c8e734..000000000000 --- a/Documentation/hwmon/userspace-tools +++ /dev/null @@ -1,43 +0,0 @@ -Userspace tools -=============== - -Introduction ------------- - -Most mainboards have sensor chips to monitor system health (like temperatures, -voltages, fans speed). They are often connected through an I2C bus, but some -are also connected directly through the ISA bus. - -The kernel drivers make the data from the sensor chips available in the /sys -virtual filesystem. Userspace tools are then used to display the measured -values or configure the chips in a more friendly manner. - -Lm-sensors ----------- - -Core set of utilities that will allow you to obtain health information, -setup monitoring limits etc. You can get them on their homepage -http://www.lm-sensors.org/ or as a package from your Linux distribution. - -If from website: -Get lm-sensors from project web site. Please note, you need only userspace -part, so compile with "make user" and install with "make user_install". - -General hints to get things working: - -0) get lm-sensors userspace utils -1) compile all drivers in I2C and Hardware Monitoring sections as modules - in your kernel -2) run sensors-detect script, it will tell you what modules you need to load. -3) load them and run "sensors" command, you should see some results. -4) fix sensors.conf, labels, limits, fan divisors -5) if any more problems consult FAQ, or documentation - -Other utilities ---------------- - -If you want some graphical indicators of system health look for applications -like: gkrellm, ksensors, xsensors, wmtemp, wmsensors, wmgtemp, ksysguardd, -hardware-monitor - -If you are server administrator you can try snmpd or mrtgutils. diff --git a/Documentation/hwmon/userspace-tools.rst b/Documentation/hwmon/userspace-tools.rst new file mode 100644 index 000000000000..bf3797c8e734 --- /dev/null +++ b/Documentation/hwmon/userspace-tools.rst @@ -0,0 +1,43 @@ +Userspace tools +=============== + +Introduction +------------ + +Most mainboards have sensor chips to monitor system health (like temperatures, +voltages, fans speed). They are often connected through an I2C bus, but some +are also connected directly through the ISA bus. + +The kernel drivers make the data from the sensor chips available in the /sys +virtual filesystem. Userspace tools are then used to display the measured +values or configure the chips in a more friendly manner. + +Lm-sensors +---------- + +Core set of utilities that will allow you to obtain health information, +setup monitoring limits etc. You can get them on their homepage +http://www.lm-sensors.org/ or as a package from your Linux distribution. + +If from website: +Get lm-sensors from project web site. Please note, you need only userspace +part, so compile with "make user" and install with "make user_install". + +General hints to get things working: + +0) get lm-sensors userspace utils +1) compile all drivers in I2C and Hardware Monitoring sections as modules + in your kernel +2) run sensors-detect script, it will tell you what modules you need to load. +3) load them and run "sensors" command, you should see some results. +4) fix sensors.conf, labels, limits, fan divisors +5) if any more problems consult FAQ, or documentation + +Other utilities +--------------- + +If you want some graphical indicators of system health look for applications +like: gkrellm, ksensors, xsensors, wmtemp, wmsensors, wmgtemp, ksysguardd, +hardware-monitor + +If you are server administrator you can try snmpd or mrtgutils. diff --git a/Documentation/hwmon/vexpress b/Documentation/hwmon/vexpress deleted file mode 100644 index 8c861c8151ac..000000000000 --- a/Documentation/hwmon/vexpress +++ /dev/null @@ -1,41 +0,0 @@ -Kernel driver vexpress -====================== - -Supported systems: - - * ARM Ltd. Versatile Express platform - - Prefix: 'vexpress' - - Datasheets: - - * "Hardware Description" sections of the Technical Reference Manuals - for the Versatile Express boards: - - - http://infocenter.arm.com/help/topic/com.arm.doc.subset.boards.express/index.html - - * Section "4.4.14. System Configuration registers" of the V2M-P1 TRM: - - - http://infocenter.arm.com/help/index.jsp?topic=/com.arm.doc.dui0447-/index.html - -Author: Pawel Moll - -Description ------------ - -Versatile Express platform (http://www.arm.com/versatileexpress/) is a -reference & prototyping system for ARM Ltd. processors. It can be set up -from a wide range of boards, each of them containing (apart of the main -chip/FPGA) a number of microcontrollers responsible for platform -configuration and control. Theses microcontrollers can also monitor the -board and its environment by a number of internal and external sensors, -providing information about power lines voltages and currents, board -temperature and power usage. Some of them also calculate consumed energy -and provide a cumulative use counter. - -The configuration devices are _not_ memory mapped and must be accessed -via a custom interface, abstracted by the "vexpress_config" API. - -As these devices are non-discoverable, they must be described in a Device -Tree passed to the kernel. Details of the DT binding for them can be found -in Documentation/devicetree/bindings/hwmon/vexpress.txt. diff --git a/Documentation/hwmon/vexpress.rst b/Documentation/hwmon/vexpress.rst new file mode 100644 index 000000000000..8c861c8151ac --- /dev/null +++ b/Documentation/hwmon/vexpress.rst @@ -0,0 +1,41 @@ +Kernel driver vexpress +====================== + +Supported systems: + + * ARM Ltd. Versatile Express platform + + Prefix: 'vexpress' + + Datasheets: + + * "Hardware Description" sections of the Technical Reference Manuals + for the Versatile Express boards: + + - http://infocenter.arm.com/help/topic/com.arm.doc.subset.boards.express/index.html + + * Section "4.4.14. System Configuration registers" of the V2M-P1 TRM: + + - http://infocenter.arm.com/help/index.jsp?topic=/com.arm.doc.dui0447-/index.html + +Author: Pawel Moll + +Description +----------- + +Versatile Express platform (http://www.arm.com/versatileexpress/) is a +reference & prototyping system for ARM Ltd. processors. It can be set up +from a wide range of boards, each of them containing (apart of the main +chip/FPGA) a number of microcontrollers responsible for platform +configuration and control. Theses microcontrollers can also monitor the +board and its environment by a number of internal and external sensors, +providing information about power lines voltages and currents, board +temperature and power usage. Some of them also calculate consumed energy +and provide a cumulative use counter. + +The configuration devices are _not_ memory mapped and must be accessed +via a custom interface, abstracted by the "vexpress_config" API. + +As these devices are non-discoverable, they must be described in a Device +Tree passed to the kernel. Details of the DT binding for them can be found +in Documentation/devicetree/bindings/hwmon/vexpress.txt. diff --git a/Documentation/hwmon/via686a b/Documentation/hwmon/via686a deleted file mode 100644 index a343c35df740..000000000000 --- a/Documentation/hwmon/via686a +++ /dev/null @@ -1,84 +0,0 @@ -Kernel driver via686a -===================== - -Supported chips: - - * Via VT82C686A, VT82C686B Southbridge Integrated Hardware Monitor - - Prefix: 'via686a' - - Addresses scanned: ISA in PCI-space encoded address - - Datasheet: On request through web form (http://www.via.com.tw/en/resources/download-center/) - -Authors: - - Kyösti Mälkki , - - Mark D. Studebaker - - Bob Dougherty - - (Some conversion-factor data were contributed by - - Jonathan Teh Soon Yew - - and Alex van Kaam .) - -Module Parameters ------------------ - -======================= ======================================================= -force_addr=0xaddr Set the I/O base address. Useful for boards that - don't set the address in the BIOS. Look for a BIOS - upgrade before resorting to this. Does not do a - PCI force; the via686a must still be present in lspci. - Don't use this unless the driver complains that the - base address is not set. - Example: 'modprobe via686a force_addr=0x6000' -======================= ======================================================= - -Description ------------ - -The driver does not distinguish between the chips and reports -all as a 686A. - -The Via 686a southbridge has integrated hardware monitor functionality. -It also has an I2C bus, but this driver only supports the hardware monitor. -For the I2C bus driver, see - -The Via 686a implements three temperature sensors, two fan rotation speed -sensors, five voltage sensors and alarms. - -Temperatures are measured in degrees Celsius. An alarm is triggered once -when the Overtemperature Shutdown limit is crossed; it is triggered again -as soon as it drops below the hysteresis value. - -Fan rotation speeds are reported in RPM (rotations per minute). An alarm is -triggered if the rotation speed has dropped below a programmable limit. Fan -readings can be divided by a programmable divider (1, 2, 4 or 8) to give -the readings more range or accuracy. Not all RPM values can accurately be -represented, so some rounding is done. With a divider of 2, the lowest -representable value is around 2600 RPM. - -Voltage sensors (also known as IN sensors) report their values in volts. -An alarm is triggered if the voltage has crossed a programmable minimum -or maximum limit. Voltages are internally scalled, so each voltage channel -has a different resolution and range. - -If an alarm triggers, it will remain triggered until the hardware register -is read at least once. This means that the cause for the alarm may -already have disappeared! Note that in the current implementation, all -hardware registers are read whenever any data is read (unless it is less -than 1.5 seconds since the last update). This means that you can easily -miss once-only alarms. - -The driver only updates its values each 1.5 seconds; reading it more often -will do no harm, but will return 'old' values. - -Known Issues ------------- - -This driver handles sensors integrated in some VIA south bridges. It is -possible that a motherboard maker used a VT82C686A/B chip as part of a -product design but was not interested in its hardware monitoring features, -in which case the sensor inputs will not be wired. This is the case of -the Asus K7V, A7V and A7V133 motherboards, to name only a few of them. -So, if you need the force_addr parameter, and end up with values which -don't seem to make any sense, don't look any further: your chip is simply -not wired for hardware monitoring. diff --git a/Documentation/hwmon/via686a.rst b/Documentation/hwmon/via686a.rst new file mode 100644 index 000000000000..a343c35df740 --- /dev/null +++ b/Documentation/hwmon/via686a.rst @@ -0,0 +1,84 @@ +Kernel driver via686a +===================== + +Supported chips: + + * Via VT82C686A, VT82C686B Southbridge Integrated Hardware Monitor + + Prefix: 'via686a' + + Addresses scanned: ISA in PCI-space encoded address + + Datasheet: On request through web form (http://www.via.com.tw/en/resources/download-center/) + +Authors: + - Kyösti Mälkki , + - Mark D. Studebaker + - Bob Dougherty + - (Some conversion-factor data were contributed by + - Jonathan Teh Soon Yew + - and Alex van Kaam .) + +Module Parameters +----------------- + +======================= ======================================================= +force_addr=0xaddr Set the I/O base address. Useful for boards that + don't set the address in the BIOS. Look for a BIOS + upgrade before resorting to this. Does not do a + PCI force; the via686a must still be present in lspci. + Don't use this unless the driver complains that the + base address is not set. + Example: 'modprobe via686a force_addr=0x6000' +======================= ======================================================= + +Description +----------- + +The driver does not distinguish between the chips and reports +all as a 686A. + +The Via 686a southbridge has integrated hardware monitor functionality. +It also has an I2C bus, but this driver only supports the hardware monitor. +For the I2C bus driver, see + +The Via 686a implements three temperature sensors, two fan rotation speed +sensors, five voltage sensors and alarms. + +Temperatures are measured in degrees Celsius. An alarm is triggered once +when the Overtemperature Shutdown limit is crossed; it is triggered again +as soon as it drops below the hysteresis value. + +Fan rotation speeds are reported in RPM (rotations per minute). An alarm is +triggered if the rotation speed has dropped below a programmable limit. Fan +readings can be divided by a programmable divider (1, 2, 4 or 8) to give +the readings more range or accuracy. Not all RPM values can accurately be +represented, so some rounding is done. With a divider of 2, the lowest +representable value is around 2600 RPM. + +Voltage sensors (also known as IN sensors) report their values in volts. +An alarm is triggered if the voltage has crossed a programmable minimum +or maximum limit. Voltages are internally scalled, so each voltage channel +has a different resolution and range. + +If an alarm triggers, it will remain triggered until the hardware register +is read at least once. This means that the cause for the alarm may +already have disappeared! Note that in the current implementation, all +hardware registers are read whenever any data is read (unless it is less +than 1.5 seconds since the last update). This means that you can easily +miss once-only alarms. + +The driver only updates its values each 1.5 seconds; reading it more often +will do no harm, but will return 'old' values. + +Known Issues +------------ + +This driver handles sensors integrated in some VIA south bridges. It is +possible that a motherboard maker used a VT82C686A/B chip as part of a +product design but was not interested in its hardware monitoring features, +in which case the sensor inputs will not be wired. This is the case of +the Asus K7V, A7V and A7V133 motherboards, to name only a few of them. +So, if you need the force_addr parameter, and end up with values which +don't seem to make any sense, don't look any further: your chip is simply +not wired for hardware monitoring. diff --git a/Documentation/hwmon/vt1211 b/Documentation/hwmon/vt1211 deleted file mode 100644 index ddbcde7dd642..000000000000 --- a/Documentation/hwmon/vt1211 +++ /dev/null @@ -1,226 +0,0 @@ -Kernel driver vt1211 -==================== - -Supported chips: - - * VIA VT1211 - - Prefix: 'vt1211' - - Addresses scanned: none, address read from Super-I/O config space - - Datasheet: Provided by VIA upon request and under NDA - -Authors: Juerg Haefliger - -This driver is based on the driver for kernel 2.4 by Mark D. Studebaker and -its port to kernel 2.6 by Lars Ekman. - -Thanks to Joseph Chan and Fiona Gatt from VIA for providing documentation and -technical support. - - -Module Parameters ------------------ - - -* uch_config: int - Override the BIOS default universal channel (UCH) - configuration for channels 1-5. - Legal values are in the range of 0-31. Bit 0 maps to - UCH1, bit 1 maps to UCH2 and so on. Setting a bit to 1 - enables the thermal input of that particular UCH and - setting a bit to 0 enables the voltage input. - -* int_mode: int - Override the BIOS default temperature interrupt mode. - The only possible value is 0 which forces interrupt - mode 0. In this mode, any pending interrupt is cleared - when the status register is read but is regenerated as - long as the temperature stays above the hysteresis - limit. - -Be aware that overriding BIOS defaults might cause some unwanted side effects! - - -Description ------------ - -The VIA VT1211 Super-I/O chip includes complete hardware monitoring -capabilities. It monitors 2 dedicated temperature sensor inputs (temp1 and -temp2), 1 dedicated voltage (in5) and 2 fans. Additionally, the chip -implements 5 universal input channels (UCH1-5) that can be individually -programmed to either monitor a voltage or a temperature. - -This chip also provides manual and automatic control of fan speeds (according -to the datasheet). The driver only supports automatic control since the manual -mode doesn't seem to work as advertised in the datasheet. In fact I couldn't -get manual mode to work at all! Be aware that automatic mode hasn't been -tested very well (due to the fact that my EPIA M10000 doesn't have the fans -connected to the PWM outputs of the VT1211 :-(). - -The following table shows the relationship between the vt1211 inputs and the -sysfs nodes. - -=============== ============== =========== ================================ -Sensor Voltage Mode Temp Mode Default Use (from the datasheet) -=============== ============== =========== ================================ -Reading 1 temp1 Intel thermal diode -Reading 3 temp2 Internal thermal diode -UCH1/Reading2 in0 temp3 NTC type thermistor -UCH2 in1 temp4 +2.5V -UCH3 in2 temp5 VccP (processor core) -UCH4 in3 temp6 +5V -UCH5 in4 temp7 +12V -+3.3V in5 Internal VCC (+3.3V) -=============== ============== =========== ================================ - - -Voltage Monitoring ------------------- - -Voltages are sampled by an 8-bit ADC with a LSB of ~10mV. The supported input -range is thus from 0 to 2.60V. Voltage values outside of this range need -external scaling resistors. This external scaling needs to be compensated for -via compute lines in sensors.conf, like: - -compute inx @*(1+R1/R2), @/(1+R1/R2) - -The board level scaling resistors according to VIA's recommendation are as -follows. And this is of course totally dependent on the actual board -implementation :-) You will have to find documentation for your own -motherboard and edit sensors.conf accordingly. - -============= ====== ====== ========= ============ - Expected -Voltage R1 R2 Divider Raw Value -============= ====== ====== ========= ============ -+2.5V 2K 10K 1.2 2083 mV -VccP --- --- 1.0 1400 mV [1]_ -+5V 14K 10K 2.4 2083 mV -+12V 47K 10K 5.7 2105 mV -+3.3V (int) 2K 3.4K 1.588 3300 mV [2]_ -+3.3V (ext) 6.8K 10K 1.68 1964 mV -============= ====== ====== ========= ============ - -.. [1] Depending on the CPU (1.4V is for a VIA C3 Nehemiah). - -.. [2] R1 and R2 for 3.3V (int) are internal to the VT1211 chip and the driver - performs the scaling and returns the properly scaled voltage value. - -Each measured voltage has an associated low and high limit which triggers an -alarm when crossed. - - -Temperature Monitoring ----------------------- - -Temperatures are reported in millidegree Celsius. Each measured temperature -has a high limit which triggers an alarm if crossed. There is an associated -hysteresis value with each temperature below which the temperature has to drop -before the alarm is cleared (this is only true for interrupt mode 0). The -interrupt mode can be forced to 0 in case the BIOS doesn't do it -automatically. See the 'Module Parameters' section for details. - -All temperature channels except temp2 are external. Temp2 is the VT1211 -internal thermal diode and the driver does all the scaling for temp2 and -returns the temperature in millidegree Celsius. For the external channels -temp1 and temp3-temp7, scaling depends on the board implementation and needs -to be performed in userspace via sensors.conf. - -Temp1 is an Intel-type thermal diode which requires the following formula to -convert between sysfs readings and real temperatures: - -compute temp1 (@-Offset)/Gain, (@*Gain)+Offset - -According to the VIA VT1211 BIOS porting guide, the following gain and offset -values should be used: - -=============== ======== =========== -Diode Type Offset Gain -=============== ======== =========== -Intel CPU 88.638 0.9528 - 65.000 0.9686 [3]_ -VIA C3 Ezra 83.869 0.9528 -VIA C3 Ezra-T 73.869 0.9528 -=============== ======== =========== - -.. [3] This is the formula from the lm_sensors 2.10.0 sensors.conf file. I don't - know where it comes from or how it was derived, it's just listed here for - completeness. - -Temp3-temp7 support NTC thermistors. For these channels, the driver returns -the voltages as seen at the individual pins of UCH1-UCH5. The voltage at the -pin (Vpin) is formed by a voltage divider made of the thermistor (Rth) and a -scaling resistor (Rs):: - - Vpin = 2200 * Rth / (Rs + Rth) (2200 is the ADC max limit of 2200 mV) - -The equation for the thermistor is as follows (google it if you want to know -more about it):: - - Rth = Ro * exp(B * (1 / T - 1 / To)) (To is 298.15K (25C) and Ro is the - nominal resistance at 25C) - -Mingling the above two equations and assuming Rs = Ro and B = 3435 yields the -following formula for sensors.conf:: - - compute tempx 1 / (1 / 298.15 - (` (2200 / @ - 1)) / 3435) - 273.15, - 2200 / (1 + (^ (3435 / 298.15 - 3435 / (273.15 + @)))) - - -Fan Speed Control ------------------ - -The VT1211 provides 2 programmable PWM outputs to control the speeds of 2 -fans. Writing a 2 to any of the two pwm[1-2]_enable sysfs nodes will put the -PWM controller in automatic mode. There is only a single controller that -controls both PWM outputs but each PWM output can be individually enabled and -disabled. - -Each PWM has 4 associated distinct output duty-cycles: full, high, low and -off. Full and off are internally hard-wired to 255 (100%) and 0 (0%), -respectively. High and low can be programmed via -pwm[1-2]_auto_point[2-3]_pwm. Each PWM output can be associated with a -different thermal input but - and here's the weird part - only one set of -thermal thresholds exist that controls both PWMs output duty-cycles. The -thermal thresholds are accessible via pwm[1-2]_auto_point[1-4]_temp. Note -that even though there are 2 sets of 4 auto points each, they map to the same -registers in the VT1211 and programming one set is sufficient (actually only -the first set pwm1_auto_point[1-4]_temp is writable, the second set is -read-only). - -========================== ========================================= -PWM Auto Point PWM Output Duty-Cycle -========================== ========================================= -pwm[1-2]_auto_point4_pwm full speed duty-cycle (hard-wired to 255) -pwm[1-2]_auto_point3_pwm high speed duty-cycle -pwm[1-2]_auto_point2_pwm low speed duty-cycle -pwm[1-2]_auto_point1_pwm off duty-cycle (hard-wired to 0) -========================== ========================================= - -========================== ================= -Temp Auto Point Thermal Threshold -========================== ================= -pwm[1-2]_auto_point4_temp full speed temp -pwm[1-2]_auto_point3_temp high speed temp -pwm[1-2]_auto_point2_temp low speed temp -pwm[1-2]_auto_point1_temp off temp -========================== ================= - -Long story short, the controller implements the following algorithm to set the -PWM output duty-cycle based on the input temperature: - -=================== ======================= ======================== -Thermal Threshold Output Duty-Cycle Output Duty-Cycle - (Rising Temp) (Falling Temp) -=================== ======================= ======================== -- full speed duty-cycle full speed duty-cycle -full speed temp -- high speed duty-cycle full speed duty-cycle -high speed temp -- low speed duty-cycle high speed duty-cycle -low speed temp -- off duty-cycle low speed duty-cycle -off temp -=================== ======================= ======================== diff --git a/Documentation/hwmon/vt1211.rst b/Documentation/hwmon/vt1211.rst new file mode 100644 index 000000000000..ddbcde7dd642 --- /dev/null +++ b/Documentation/hwmon/vt1211.rst @@ -0,0 +1,226 @@ +Kernel driver vt1211 +==================== + +Supported chips: + + * VIA VT1211 + + Prefix: 'vt1211' + + Addresses scanned: none, address read from Super-I/O config space + + Datasheet: Provided by VIA upon request and under NDA + +Authors: Juerg Haefliger + +This driver is based on the driver for kernel 2.4 by Mark D. Studebaker and +its port to kernel 2.6 by Lars Ekman. + +Thanks to Joseph Chan and Fiona Gatt from VIA for providing documentation and +technical support. + + +Module Parameters +----------------- + + +* uch_config: int + Override the BIOS default universal channel (UCH) + configuration for channels 1-5. + Legal values are in the range of 0-31. Bit 0 maps to + UCH1, bit 1 maps to UCH2 and so on. Setting a bit to 1 + enables the thermal input of that particular UCH and + setting a bit to 0 enables the voltage input. + +* int_mode: int + Override the BIOS default temperature interrupt mode. + The only possible value is 0 which forces interrupt + mode 0. In this mode, any pending interrupt is cleared + when the status register is read but is regenerated as + long as the temperature stays above the hysteresis + limit. + +Be aware that overriding BIOS defaults might cause some unwanted side effects! + + +Description +----------- + +The VIA VT1211 Super-I/O chip includes complete hardware monitoring +capabilities. It monitors 2 dedicated temperature sensor inputs (temp1 and +temp2), 1 dedicated voltage (in5) and 2 fans. Additionally, the chip +implements 5 universal input channels (UCH1-5) that can be individually +programmed to either monitor a voltage or a temperature. + +This chip also provides manual and automatic control of fan speeds (according +to the datasheet). The driver only supports automatic control since the manual +mode doesn't seem to work as advertised in the datasheet. In fact I couldn't +get manual mode to work at all! Be aware that automatic mode hasn't been +tested very well (due to the fact that my EPIA M10000 doesn't have the fans +connected to the PWM outputs of the VT1211 :-(). + +The following table shows the relationship between the vt1211 inputs and the +sysfs nodes. + +=============== ============== =========== ================================ +Sensor Voltage Mode Temp Mode Default Use (from the datasheet) +=============== ============== =========== ================================ +Reading 1 temp1 Intel thermal diode +Reading 3 temp2 Internal thermal diode +UCH1/Reading2 in0 temp3 NTC type thermistor +UCH2 in1 temp4 +2.5V +UCH3 in2 temp5 VccP (processor core) +UCH4 in3 temp6 +5V +UCH5 in4 temp7 +12V ++3.3V in5 Internal VCC (+3.3V) +=============== ============== =========== ================================ + + +Voltage Monitoring +------------------ + +Voltages are sampled by an 8-bit ADC with a LSB of ~10mV. The supported input +range is thus from 0 to 2.60V. Voltage values outside of this range need +external scaling resistors. This external scaling needs to be compensated for +via compute lines in sensors.conf, like: + +compute inx @*(1+R1/R2), @/(1+R1/R2) + +The board level scaling resistors according to VIA's recommendation are as +follows. And this is of course totally dependent on the actual board +implementation :-) You will have to find documentation for your own +motherboard and edit sensors.conf accordingly. + +============= ====== ====== ========= ============ + Expected +Voltage R1 R2 Divider Raw Value +============= ====== ====== ========= ============ ++2.5V 2K 10K 1.2 2083 mV +VccP --- --- 1.0 1400 mV [1]_ ++5V 14K 10K 2.4 2083 mV ++12V 47K 10K 5.7 2105 mV ++3.3V (int) 2K 3.4K 1.588 3300 mV [2]_ ++3.3V (ext) 6.8K 10K 1.68 1964 mV +============= ====== ====== ========= ============ + +.. [1] Depending on the CPU (1.4V is for a VIA C3 Nehemiah). + +.. [2] R1 and R2 for 3.3V (int) are internal to the VT1211 chip and the driver + performs the scaling and returns the properly scaled voltage value. + +Each measured voltage has an associated low and high limit which triggers an +alarm when crossed. + + +Temperature Monitoring +---------------------- + +Temperatures are reported in millidegree Celsius. Each measured temperature +has a high limit which triggers an alarm if crossed. There is an associated +hysteresis value with each temperature below which the temperature has to drop +before the alarm is cleared (this is only true for interrupt mode 0). The +interrupt mode can be forced to 0 in case the BIOS doesn't do it +automatically. See the 'Module Parameters' section for details. + +All temperature channels except temp2 are external. Temp2 is the VT1211 +internal thermal diode and the driver does all the scaling for temp2 and +returns the temperature in millidegree Celsius. For the external channels +temp1 and temp3-temp7, scaling depends on the board implementation and needs +to be performed in userspace via sensors.conf. + +Temp1 is an Intel-type thermal diode which requires the following formula to +convert between sysfs readings and real temperatures: + +compute temp1 (@-Offset)/Gain, (@*Gain)+Offset + +According to the VIA VT1211 BIOS porting guide, the following gain and offset +values should be used: + +=============== ======== =========== +Diode Type Offset Gain +=============== ======== =========== +Intel CPU 88.638 0.9528 + 65.000 0.9686 [3]_ +VIA C3 Ezra 83.869 0.9528 +VIA C3 Ezra-T 73.869 0.9528 +=============== ======== =========== + +.. [3] This is the formula from the lm_sensors 2.10.0 sensors.conf file. I don't + know where it comes from or how it was derived, it's just listed here for + completeness. + +Temp3-temp7 support NTC thermistors. For these channels, the driver returns +the voltages as seen at the individual pins of UCH1-UCH5. The voltage at the +pin (Vpin) is formed by a voltage divider made of the thermistor (Rth) and a +scaling resistor (Rs):: + + Vpin = 2200 * Rth / (Rs + Rth) (2200 is the ADC max limit of 2200 mV) + +The equation for the thermistor is as follows (google it if you want to know +more about it):: + + Rth = Ro * exp(B * (1 / T - 1 / To)) (To is 298.15K (25C) and Ro is the + nominal resistance at 25C) + +Mingling the above two equations and assuming Rs = Ro and B = 3435 yields the +following formula for sensors.conf:: + + compute tempx 1 / (1 / 298.15 - (` (2200 / @ - 1)) / 3435) - 273.15, + 2200 / (1 + (^ (3435 / 298.15 - 3435 / (273.15 + @)))) + + +Fan Speed Control +----------------- + +The VT1211 provides 2 programmable PWM outputs to control the speeds of 2 +fans. Writing a 2 to any of the two pwm[1-2]_enable sysfs nodes will put the +PWM controller in automatic mode. There is only a single controller that +controls both PWM outputs but each PWM output can be individually enabled and +disabled. + +Each PWM has 4 associated distinct output duty-cycles: full, high, low and +off. Full and off are internally hard-wired to 255 (100%) and 0 (0%), +respectively. High and low can be programmed via +pwm[1-2]_auto_point[2-3]_pwm. Each PWM output can be associated with a +different thermal input but - and here's the weird part - only one set of +thermal thresholds exist that controls both PWMs output duty-cycles. The +thermal thresholds are accessible via pwm[1-2]_auto_point[1-4]_temp. Note +that even though there are 2 sets of 4 auto points each, they map to the same +registers in the VT1211 and programming one set is sufficient (actually only +the first set pwm1_auto_point[1-4]_temp is writable, the second set is +read-only). + +========================== ========================================= +PWM Auto Point PWM Output Duty-Cycle +========================== ========================================= +pwm[1-2]_auto_point4_pwm full speed duty-cycle (hard-wired to 255) +pwm[1-2]_auto_point3_pwm high speed duty-cycle +pwm[1-2]_auto_point2_pwm low speed duty-cycle +pwm[1-2]_auto_point1_pwm off duty-cycle (hard-wired to 0) +========================== ========================================= + +========================== ================= +Temp Auto Point Thermal Threshold +========================== ================= +pwm[1-2]_auto_point4_temp full speed temp +pwm[1-2]_auto_point3_temp high speed temp +pwm[1-2]_auto_point2_temp low speed temp +pwm[1-2]_auto_point1_temp off temp +========================== ================= + +Long story short, the controller implements the following algorithm to set the +PWM output duty-cycle based on the input temperature: + +=================== ======================= ======================== +Thermal Threshold Output Duty-Cycle Output Duty-Cycle + (Rising Temp) (Falling Temp) +=================== ======================= ======================== +- full speed duty-cycle full speed duty-cycle +full speed temp +- high speed duty-cycle full speed duty-cycle +high speed temp +- low speed duty-cycle high speed duty-cycle +low speed temp +- off duty-cycle low speed duty-cycle +off temp +=================== ======================= ======================== diff --git a/Documentation/hwmon/w83627ehf b/Documentation/hwmon/w83627ehf deleted file mode 100644 index 74d19ef11e1f..000000000000 --- a/Documentation/hwmon/w83627ehf +++ /dev/null @@ -1,248 +0,0 @@ -Kernel driver w83627ehf -======================= - -Supported chips: - - * Winbond W83627EHF/EHG (ISA access ONLY) - - Prefix: 'w83627ehf' - - Addresses scanned: ISA address retrieved from Super I/O registers - - Datasheet: not available - - * Winbond W83627DHG - - Prefix: 'w83627dhg' - - Addresses scanned: ISA address retrieved from Super I/O registers - - Datasheet: not available - - * Winbond W83627DHG-P - - Prefix: 'w83627dhg' - - Addresses scanned: ISA address retrieved from Super I/O registers - - Datasheet: not available - - * Winbond W83627UHG - - Prefix: 'w83627uhg' - - Addresses scanned: ISA address retrieved from Super I/O registers - - Datasheet: available from www.nuvoton.com - - * Winbond W83667HG - - Prefix: 'w83667hg' - - Addresses scanned: ISA address retrieved from Super I/O registers - - Datasheet: not available - - * Winbond W83667HG-B - - Prefix: 'w83667hg' - - Addresses scanned: ISA address retrieved from Super I/O registers - - Datasheet: Available from Nuvoton upon request - - * Nuvoton NCT6775F/W83667HG-I - - Prefix: 'nct6775' - - Addresses scanned: ISA address retrieved from Super I/O registers - - Datasheet: Available from Nuvoton upon request - - * Nuvoton NCT6776F - - Prefix: 'nct6776' - - Addresses scanned: ISA address retrieved from Super I/O registers - - Datasheet: Available from Nuvoton upon request - - -Authors: - - - Jean Delvare - - Yuan Mu (Winbond) - - Rudolf Marek - - David Hubbard - - Gong Jun - -Description ------------ - -This driver implements support for the Winbond W83627EHF, W83627EHG, -W83627DHG, W83627DHG-P, W83627UHG, W83667HG, W83667HG-B, W83667HG-I -(NCT6775F), and NCT6776F super I/O chips. We will refer to them collectively -as Winbond chips. - -The chips implement 3 to 4 temperature sensors (9 for NCT6775F and NCT6776F), -2 to 5 fan rotation speed sensors, 8 to 10 analog voltage sensors, one VID -(except for 627UHG), alarms with beep warnings (control unimplemented), -and some automatic fan regulation strategies (plus manual fan control mode). - -The temperature sensor sources on W82677HG-B, NCT6775F, and NCT6776F are -configurable. temp4 and higher attributes are only reported if its temperature -source differs from the temperature sources of the already reported temperature -sensors. The configured source for each of the temperature sensors is provided -in tempX_label. - -Temperatures are measured in degrees Celsius and measurement resolution is 1 -degC for temp1 and and 0.5 degC for temp2 and temp3. For temp4 and higher, -resolution is 1 degC for W83667HG-B and 0.0 degC for NCT6775F and NCT6776F. -An alarm is triggered when the temperature gets higher than high limit; -it stays on until the temperature falls below the hysteresis value. -Alarms are only supported for temp1, temp2, and temp3. - -Fan rotation speeds are reported in RPM (rotations per minute). An alarm is -triggered if the rotation speed has dropped below a programmable limit. Fan -readings can be divided by a programmable divider (1, 2, 4, 8, 16, 32, 64 or -128) to give the readings more range or accuracy. The driver sets the most -suitable fan divisor itself. Some fans might not be present because they -share pins with other functions. - -Voltage sensors (also known as IN sensors) report their values in millivolts. -An alarm is triggered if the voltage has crossed a programmable minimum -or maximum limit. - -The driver supports automatic fan control mode known as Thermal Cruise. -In this mode, the chip attempts to keep the measured temperature in a -predefined temperature range. If the temperature goes out of range, fan -is driven slower/faster to reach the predefined range again. - -The mode works for fan1-fan4. Mapping of temperatures to pwm outputs is as -follows:: - - temp1 -> pwm1 - temp2 -> pwm2 - temp3 -> pwm3 (not on 627UHG) - prog -> pwm4 (not on 667HG and 667HG-B; the programmable setting is not - supported by the driver) - -/sys files ----------- - -name - this is a standard hwmon device entry, it contains the name of - the device (see the prefix in the list of supported devices at - the top of this file) - -pwm[1-4] - this file stores PWM duty cycle or DC value (fan speed) in range: - - 0 (stop) to 255 (full) - -pwm[1-4]_enable - this file controls mode of fan/temperature control: - - * 1 Manual mode, write to pwm file any value 0-255 (full speed) - * 2 "Thermal Cruise" mode - * 3 "Fan Speed Cruise" mode - * 4 "Smart Fan III" mode - * 5 "Smart Fan IV" mode - - SmartFan III mode is not supported on NCT6776F. - - SmartFan IV mode is configurable only if it was configured at system - startup, and is only supported for W83677HG-B, NCT6775F, and NCT6776F. - SmartFan IV operational parameters can not be configured at this time, - and the various pwm attributes are not used in SmartFan IV mode. - The attributes can be written to, which is useful if you plan to - configure the system for a different pwm mode. However, the information - returned when reading pwm attributes is unrelated to SmartFan IV - operation. - -pwm[1-4]_mode - controls if output is PWM or DC level - - * 0 DC output (0 - 12v) - * 1 PWM output - -Thermal Cruise mode -------------------- - -If the temperature is in the range defined by: - -pwm[1-4]_target - set target temperature, unit millidegree Celsius - (range 0 - 127000) -pwm[1-4]_tolerance - tolerance, unit millidegree Celsius (range 0 - 15000) - -there are no changes to fan speed. Once the temperature leaves the interval, -fan speed increases (temp is higher) or decreases if lower than desired. -There are defined steps and times, but not exported by the driver yet. - -pwm[1-4]_min_output - minimum fan speed (range 1 - 255), when the temperature - is below defined range. -pwm[1-4]_stop_time - how many milliseconds [ms] must elapse to switch - corresponding fan off. (when the temperature was below - defined range). -pwm[1-4]_start_output - minimum fan speed (range 1 - 255) when spinning up -pwm[1-4]_step_output - rate of fan speed change (1 - 255) -pwm[1-4]_stop_output - minimum fan speed (range 1 - 255) when spinning down -pwm[1-4]_max_output - maximum fan speed (range 1 - 255), when the temperature - is above defined range. - -Note: last six functions are influenced by other control bits, not yet exported - by the driver, so a change might not have any effect. - -Implementation Details ----------------------- - -Future driver development should bear in mind that the following registers have -different functions on the 627EHF and the 627DHG. Some registers also have -different power-on default values, but BIOS should already be loading -appropriate defaults. Note that bank selection must be performed as is currently -done in the driver for all register addresses. - -========================= ===================================================== -Register(s) Meaning -========================= ===================================================== -0x49 only on DHG, selects temperature source for AUX fan, - CPU fan0 -0x4a not completely documented for the EHF and the DHG - documentation assigns different behavior to bits 7 - and 6, including extending the temperature input - selection to SmartFan I, not just SmartFan III. - Testing on the EHF will reveal whether they are - compatible or not. -0x58 Chip ID: 0xa1=EHF 0xc1=DHG -0x5e only on DHG, has bits to enable "current mode" - temperature detection and critical temperature - protection -0x45b only on EHF, bit 3, vin4 alarm (EHF supports 10 - inputs, only 9 on DHG) -0x552 only on EHF, vin4 -0x558 only on EHF, vin4 high limit -0x559 only on EHF, vin4 low limit -0x6b only on DHG, SYS fan critical temperature -0x6c only on DHG, CPU fan0 critical temperature -0x6d only on DHG, AUX fan critical temperature -0x6e only on DHG, CPU fan1 critical temperature -0x50-0x55 and 0x650-0x657 marked as: - - - "Test Register" for the EHF - - "Reserved Register" for the DHG -========================= ===================================================== - -The DHG also supports PECI, where the DHG queries Intel CPU temperatures, and -the ICH8 southbridge gets that data via PECI from the DHG, so that the -southbridge drives the fans. And the DHG supports SST, a one-wire serial bus. - -The DHG-P has an additional automatic fan speed control mode named Smart Fan -(TM) III+. This mode is not yet supported by the driver. diff --git a/Documentation/hwmon/w83627ehf.rst b/Documentation/hwmon/w83627ehf.rst new file mode 100644 index 000000000000..74d19ef11e1f --- /dev/null +++ b/Documentation/hwmon/w83627ehf.rst @@ -0,0 +1,248 @@ +Kernel driver w83627ehf +======================= + +Supported chips: + + * Winbond W83627EHF/EHG (ISA access ONLY) + + Prefix: 'w83627ehf' + + Addresses scanned: ISA address retrieved from Super I/O registers + + Datasheet: not available + + * Winbond W83627DHG + + Prefix: 'w83627dhg' + + Addresses scanned: ISA address retrieved from Super I/O registers + + Datasheet: not available + + * Winbond W83627DHG-P + + Prefix: 'w83627dhg' + + Addresses scanned: ISA address retrieved from Super I/O registers + + Datasheet: not available + + * Winbond W83627UHG + + Prefix: 'w83627uhg' + + Addresses scanned: ISA address retrieved from Super I/O registers + + Datasheet: available from www.nuvoton.com + + * Winbond W83667HG + + Prefix: 'w83667hg' + + Addresses scanned: ISA address retrieved from Super I/O registers + + Datasheet: not available + + * Winbond W83667HG-B + + Prefix: 'w83667hg' + + Addresses scanned: ISA address retrieved from Super I/O registers + + Datasheet: Available from Nuvoton upon request + + * Nuvoton NCT6775F/W83667HG-I + + Prefix: 'nct6775' + + Addresses scanned: ISA address retrieved from Super I/O registers + + Datasheet: Available from Nuvoton upon request + + * Nuvoton NCT6776F + + Prefix: 'nct6776' + + Addresses scanned: ISA address retrieved from Super I/O registers + + Datasheet: Available from Nuvoton upon request + + +Authors: + + - Jean Delvare + - Yuan Mu (Winbond) + - Rudolf Marek + - David Hubbard + - Gong Jun + +Description +----------- + +This driver implements support for the Winbond W83627EHF, W83627EHG, +W83627DHG, W83627DHG-P, W83627UHG, W83667HG, W83667HG-B, W83667HG-I +(NCT6775F), and NCT6776F super I/O chips. We will refer to them collectively +as Winbond chips. + +The chips implement 3 to 4 temperature sensors (9 for NCT6775F and NCT6776F), +2 to 5 fan rotation speed sensors, 8 to 10 analog voltage sensors, one VID +(except for 627UHG), alarms with beep warnings (control unimplemented), +and some automatic fan regulation strategies (plus manual fan control mode). + +The temperature sensor sources on W82677HG-B, NCT6775F, and NCT6776F are +configurable. temp4 and higher attributes are only reported if its temperature +source differs from the temperature sources of the already reported temperature +sensors. The configured source for each of the temperature sensors is provided +in tempX_label. + +Temperatures are measured in degrees Celsius and measurement resolution is 1 +degC for temp1 and and 0.5 degC for temp2 and temp3. For temp4 and higher, +resolution is 1 degC for W83667HG-B and 0.0 degC for NCT6775F and NCT6776F. +An alarm is triggered when the temperature gets higher than high limit; +it stays on until the temperature falls below the hysteresis value. +Alarms are only supported for temp1, temp2, and temp3. + +Fan rotation speeds are reported in RPM (rotations per minute). An alarm is +triggered if the rotation speed has dropped below a programmable limit. Fan +readings can be divided by a programmable divider (1, 2, 4, 8, 16, 32, 64 or +128) to give the readings more range or accuracy. The driver sets the most +suitable fan divisor itself. Some fans might not be present because they +share pins with other functions. + +Voltage sensors (also known as IN sensors) report their values in millivolts. +An alarm is triggered if the voltage has crossed a programmable minimum +or maximum limit. + +The driver supports automatic fan control mode known as Thermal Cruise. +In this mode, the chip attempts to keep the measured temperature in a +predefined temperature range. If the temperature goes out of range, fan +is driven slower/faster to reach the predefined range again. + +The mode works for fan1-fan4. Mapping of temperatures to pwm outputs is as +follows:: + + temp1 -> pwm1 + temp2 -> pwm2 + temp3 -> pwm3 (not on 627UHG) + prog -> pwm4 (not on 667HG and 667HG-B; the programmable setting is not + supported by the driver) + +/sys files +---------- + +name + this is a standard hwmon device entry, it contains the name of + the device (see the prefix in the list of supported devices at + the top of this file) + +pwm[1-4] + this file stores PWM duty cycle or DC value (fan speed) in range: + + 0 (stop) to 255 (full) + +pwm[1-4]_enable + this file controls mode of fan/temperature control: + + * 1 Manual mode, write to pwm file any value 0-255 (full speed) + * 2 "Thermal Cruise" mode + * 3 "Fan Speed Cruise" mode + * 4 "Smart Fan III" mode + * 5 "Smart Fan IV" mode + + SmartFan III mode is not supported on NCT6776F. + + SmartFan IV mode is configurable only if it was configured at system + startup, and is only supported for W83677HG-B, NCT6775F, and NCT6776F. + SmartFan IV operational parameters can not be configured at this time, + and the various pwm attributes are not used in SmartFan IV mode. + The attributes can be written to, which is useful if you plan to + configure the system for a different pwm mode. However, the information + returned when reading pwm attributes is unrelated to SmartFan IV + operation. + +pwm[1-4]_mode + controls if output is PWM or DC level + + * 0 DC output (0 - 12v) + * 1 PWM output + +Thermal Cruise mode +------------------- + +If the temperature is in the range defined by: + +pwm[1-4]_target + set target temperature, unit millidegree Celsius + (range 0 - 127000) +pwm[1-4]_tolerance + tolerance, unit millidegree Celsius (range 0 - 15000) + +there are no changes to fan speed. Once the temperature leaves the interval, +fan speed increases (temp is higher) or decreases if lower than desired. +There are defined steps and times, but not exported by the driver yet. + +pwm[1-4]_min_output + minimum fan speed (range 1 - 255), when the temperature + is below defined range. +pwm[1-4]_stop_time + how many milliseconds [ms] must elapse to switch + corresponding fan off. (when the temperature was below + defined range). +pwm[1-4]_start_output + minimum fan speed (range 1 - 255) when spinning up +pwm[1-4]_step_output + rate of fan speed change (1 - 255) +pwm[1-4]_stop_output + minimum fan speed (range 1 - 255) when spinning down +pwm[1-4]_max_output + maximum fan speed (range 1 - 255), when the temperature + is above defined range. + +Note: last six functions are influenced by other control bits, not yet exported + by the driver, so a change might not have any effect. + +Implementation Details +---------------------- + +Future driver development should bear in mind that the following registers have +different functions on the 627EHF and the 627DHG. Some registers also have +different power-on default values, but BIOS should already be loading +appropriate defaults. Note that bank selection must be performed as is currently +done in the driver for all register addresses. + +========================= ===================================================== +Register(s) Meaning +========================= ===================================================== +0x49 only on DHG, selects temperature source for AUX fan, + CPU fan0 +0x4a not completely documented for the EHF and the DHG + documentation assigns different behavior to bits 7 + and 6, including extending the temperature input + selection to SmartFan I, not just SmartFan III. + Testing on the EHF will reveal whether they are + compatible or not. +0x58 Chip ID: 0xa1=EHF 0xc1=DHG +0x5e only on DHG, has bits to enable "current mode" + temperature detection and critical temperature + protection +0x45b only on EHF, bit 3, vin4 alarm (EHF supports 10 + inputs, only 9 on DHG) +0x552 only on EHF, vin4 +0x558 only on EHF, vin4 high limit +0x559 only on EHF, vin4 low limit +0x6b only on DHG, SYS fan critical temperature +0x6c only on DHG, CPU fan0 critical temperature +0x6d only on DHG, AUX fan critical temperature +0x6e only on DHG, CPU fan1 critical temperature +0x50-0x55 and 0x650-0x657 marked as: + + - "Test Register" for the EHF + - "Reserved Register" for the DHG +========================= ===================================================== + +The DHG also supports PECI, where the DHG queries Intel CPU temperatures, and +the ICH8 southbridge gets that data via PECI from the DHG, so that the +southbridge drives the fans. And the DHG supports SST, a one-wire serial bus. + +The DHG-P has an additional automatic fan speed control mode named Smart Fan +(TM) III+. This mode is not yet supported by the driver. diff --git a/Documentation/hwmon/w83627hf b/Documentation/hwmon/w83627hf deleted file mode 100644 index d1406c28dee7..000000000000 --- a/Documentation/hwmon/w83627hf +++ /dev/null @@ -1,124 +0,0 @@ -Kernel driver w83627hf -====================== - -Supported chips: - * Winbond W83627HF (ISA accesses ONLY) - Prefix: 'w83627hf' - Addresses scanned: ISA address retrieved from Super I/O registers - * Winbond W83627THF - Prefix: 'w83627thf' - Addresses scanned: ISA address retrieved from Super I/O registers - * Winbond W83697HF - Prefix: 'w83697hf' - Addresses scanned: ISA address retrieved from Super I/O registers - * Winbond W83637HF - Prefix: 'w83637hf' - Addresses scanned: ISA address retrieved from Super I/O registers - * Winbond W83687THF - Prefix: 'w83687thf' - Addresses scanned: ISA address retrieved from Super I/O registers - Datasheet: Provided by Winbond on request(http://www.winbond.com/hq/enu) - -Authors: - Frodo Looijaard , - Philip Edelbrock , - Mark Studebaker , - Bernhard C. Schrenk - -Module Parameters ------------------ - -* force_i2c: int - Initialize the I2C address of the sensors -* init: int - (default is 1) - Use 'init=0' to bypass initializing the chip. - Try this if your computer crashes when you load the module. - -Description ------------ - -This driver implements support for ISA accesses *only* for -the Winbond W83627HF, W83627THF, W83697HF and W83637HF Super I/O chips. -We will refer to them collectively as Winbond chips. - -This driver supports ISA accesses, which should be more reliable -than i2c accesses. Also, for Tyan boards which contain both a -Super I/O chip and a second i2c-only Winbond chip (often a W83782D), -using this driver will avoid i2c address conflicts and complex -initialization that were required in the w83781d driver. - -If you really want i2c accesses for these Super I/O chips, -use the w83781d driver. However this is not the preferred method -now that this ISA driver has been developed. - -The `w83627_HF_` uses pins 110-106 as VID0-VID4. The `w83627_THF_` uses the -same pins as GPIO[0:4]. Technically, the `w83627_THF_` does not support a -VID reading. However the two chips have the identical 128 pin package. So, -it is possible or even likely for a w83627thf to have the VID signals routed -to these pins despite their not being labeled for that purpose. Therefore, -the w83627thf driver interprets these as VID. If the VID on your board -doesn't work, first see doc/vid in the lm_sensors package[1]. If that still -doesn't help, you may just ignore the bogus VID reading with no harm done. - -For further information on this driver see the w83781d driver documentation. - -[1] http://www.lm-sensors.org/browser/lm-sensors/trunk/doc/vid - -Forcing the address -------------------- - -The driver used to have a module parameter named force_addr, which could -be used to force the base I/O address of the hardware monitoring block. -This was meant as a workaround for mainboards with a broken BIOS. This -module parameter is gone for technical reasons. If you need this feature, -you can obtain the same result by using the isaset tool (part of -lm-sensors) before loading the driver: - -# Enter the Super I/O config space:: - - isaset -y -f 0x2e 0x87 - isaset -y -f 0x2e 0x87 - -# Select the hwmon logical device:: - - isaset -y 0x2e 0x2f 0x07 0x0b - -# Set the base I/O address (to 0x290 in this example):: - - isaset -y 0x2e 0x2f 0x60 0x02 - isaset -y 0x2e 0x2f 0x61 0x90 - -# Exit the Super-I/O config space:: - - isaset -y -f 0x2e 0xaa - -The above sequence assumes a Super-I/O config space at 0x2e/0x2f, but -0x4e/0x4f is also possible. - -Voltage pin mapping -------------------- - -Here is a summary of the voltage pin mapping for the W83627THF. This -can be useful to convert data provided by board manufacturers into -working libsensors configuration statements: - - -- W83627THF - - - ======== =============== =============== =============== - Pin Name Register Sysfs attribute - ======== =============== =============== =============== - 100 CPUVCORE 20h in0 - 99 VIN0 21h in1 - 98 VIN1 22h in2 - 97 VIN2 24h in4 - 114 AVCC 23h in3 - 61 5VSB 50h (bank 5) in7 - 74 VBAT 51h (bank 5) in8 - ======== =============== =============== =============== - -For other supported devices, you'll have to take the hard path and -look up the information in the datasheet yourself (and then add it -to this document please.) diff --git a/Documentation/hwmon/w83627hf.rst b/Documentation/hwmon/w83627hf.rst new file mode 100644 index 000000000000..d1406c28dee7 --- /dev/null +++ b/Documentation/hwmon/w83627hf.rst @@ -0,0 +1,124 @@ +Kernel driver w83627hf +====================== + +Supported chips: + * Winbond W83627HF (ISA accesses ONLY) + Prefix: 'w83627hf' + Addresses scanned: ISA address retrieved from Super I/O registers + * Winbond W83627THF + Prefix: 'w83627thf' + Addresses scanned: ISA address retrieved from Super I/O registers + * Winbond W83697HF + Prefix: 'w83697hf' + Addresses scanned: ISA address retrieved from Super I/O registers + * Winbond W83637HF + Prefix: 'w83637hf' + Addresses scanned: ISA address retrieved from Super I/O registers + * Winbond W83687THF + Prefix: 'w83687thf' + Addresses scanned: ISA address retrieved from Super I/O registers + Datasheet: Provided by Winbond on request(http://www.winbond.com/hq/enu) + +Authors: + Frodo Looijaard , + Philip Edelbrock , + Mark Studebaker , + Bernhard C. Schrenk + +Module Parameters +----------------- + +* force_i2c: int + Initialize the I2C address of the sensors +* init: int + (default is 1) + Use 'init=0' to bypass initializing the chip. + Try this if your computer crashes when you load the module. + +Description +----------- + +This driver implements support for ISA accesses *only* for +the Winbond W83627HF, W83627THF, W83697HF and W83637HF Super I/O chips. +We will refer to them collectively as Winbond chips. + +This driver supports ISA accesses, which should be more reliable +than i2c accesses. Also, for Tyan boards which contain both a +Super I/O chip and a second i2c-only Winbond chip (often a W83782D), +using this driver will avoid i2c address conflicts and complex +initialization that were required in the w83781d driver. + +If you really want i2c accesses for these Super I/O chips, +use the w83781d driver. However this is not the preferred method +now that this ISA driver has been developed. + +The `w83627_HF_` uses pins 110-106 as VID0-VID4. The `w83627_THF_` uses the +same pins as GPIO[0:4]. Technically, the `w83627_THF_` does not support a +VID reading. However the two chips have the identical 128 pin package. So, +it is possible or even likely for a w83627thf to have the VID signals routed +to these pins despite their not being labeled for that purpose. Therefore, +the w83627thf driver interprets these as VID. If the VID on your board +doesn't work, first see doc/vid in the lm_sensors package[1]. If that still +doesn't help, you may just ignore the bogus VID reading with no harm done. + +For further information on this driver see the w83781d driver documentation. + +[1] http://www.lm-sensors.org/browser/lm-sensors/trunk/doc/vid + +Forcing the address +------------------- + +The driver used to have a module parameter named force_addr, which could +be used to force the base I/O address of the hardware monitoring block. +This was meant as a workaround for mainboards with a broken BIOS. This +module parameter is gone for technical reasons. If you need this feature, +you can obtain the same result by using the isaset tool (part of +lm-sensors) before loading the driver: + +# Enter the Super I/O config space:: + + isaset -y -f 0x2e 0x87 + isaset -y -f 0x2e 0x87 + +# Select the hwmon logical device:: + + isaset -y 0x2e 0x2f 0x07 0x0b + +# Set the base I/O address (to 0x290 in this example):: + + isaset -y 0x2e 0x2f 0x60 0x02 + isaset -y 0x2e 0x2f 0x61 0x90 + +# Exit the Super-I/O config space:: + + isaset -y -f 0x2e 0xaa + +The above sequence assumes a Super-I/O config space at 0x2e/0x2f, but +0x4e/0x4f is also possible. + +Voltage pin mapping +------------------- + +Here is a summary of the voltage pin mapping for the W83627THF. This +can be useful to convert data provided by board manufacturers into +working libsensors configuration statements: + + +- W83627THF + + + ======== =============== =============== =============== + Pin Name Register Sysfs attribute + ======== =============== =============== =============== + 100 CPUVCORE 20h in0 + 99 VIN0 21h in1 + 98 VIN1 22h in2 + 97 VIN2 24h in4 + 114 AVCC 23h in3 + 61 5VSB 50h (bank 5) in7 + 74 VBAT 51h (bank 5) in8 + ======== =============== =============== =============== + +For other supported devices, you'll have to take the hard path and +look up the information in the datasheet yourself (and then add it +to this document please.) diff --git a/Documentation/hwmon/w83773g b/Documentation/hwmon/w83773g deleted file mode 100644 index cabaed391414..000000000000 --- a/Documentation/hwmon/w83773g +++ /dev/null @@ -1,35 +0,0 @@ -Kernel driver w83773g -===================== - -Supported chips: - - * Nuvoton W83773G - - Prefix: 'w83773g' - - Addresses scanned: I2C 0x4c and 0x4d - - Datasheet: https://www.nuvoton.com/resource-files/W83773G_SG_DatasheetV1_2.pdf - -Authors: - - Lei YU - -Description ------------ - -This driver implements support for Nuvoton W83773G temperature sensor -chip. This chip implements one local and two remote sensors. -The chip also features offsets for the two remote sensors which get added to -the input readings. The chip does all the scaling by itself and the driver -therefore reports true temperatures that don't need any user-space adjustments. -Temperature is measured in degrees Celsius. -The chip is wired over I2C/SMBus and specified over a temperature -range of -40 to +125 degrees Celsius (for local sensor) and -40 to +127 -degrees Celsius (for remote sensors). -Resolution for both the local and remote channels is 0.125 degree C. - -The chip supports only temperature measurement. The driver exports -the temperature values via the following sysfs files: - -**temp[1-3]_input, temp[2-3]_fault, temp[2-3]_offset, update_interval** diff --git a/Documentation/hwmon/w83773g.rst b/Documentation/hwmon/w83773g.rst new file mode 100644 index 000000000000..cabaed391414 --- /dev/null +++ b/Documentation/hwmon/w83773g.rst @@ -0,0 +1,35 @@ +Kernel driver w83773g +===================== + +Supported chips: + + * Nuvoton W83773G + + Prefix: 'w83773g' + + Addresses scanned: I2C 0x4c and 0x4d + + Datasheet: https://www.nuvoton.com/resource-files/W83773G_SG_DatasheetV1_2.pdf + +Authors: + + Lei YU + +Description +----------- + +This driver implements support for Nuvoton W83773G temperature sensor +chip. This chip implements one local and two remote sensors. +The chip also features offsets for the two remote sensors which get added to +the input readings. The chip does all the scaling by itself and the driver +therefore reports true temperatures that don't need any user-space adjustments. +Temperature is measured in degrees Celsius. +The chip is wired over I2C/SMBus and specified over a temperature +range of -40 to +125 degrees Celsius (for local sensor) and -40 to +127 +degrees Celsius (for remote sensors). +Resolution for both the local and remote channels is 0.125 degree C. + +The chip supports only temperature measurement. The driver exports +the temperature values via the following sysfs files: + +**temp[1-3]_input, temp[2-3]_fault, temp[2-3]_offset, update_interval** diff --git a/Documentation/hwmon/w83781d b/Documentation/hwmon/w83781d deleted file mode 100644 index f36d33dfb704..000000000000 --- a/Documentation/hwmon/w83781d +++ /dev/null @@ -1,513 +0,0 @@ -Kernel driver w83781d -===================== - -Supported chips: - - * Winbond W83781D - - Prefix: 'w83781d' - - Addresses scanned: I2C 0x28 - 0x2f, ISA 0x290 (8 I/O ports) - - Datasheet: http://www.winbond-usa.com/products/winbond_products/pdfs/PCIC/w83781d.pdf - - * Winbond W83782D - - Prefix: 'w83782d' - - Addresses scanned: I2C 0x28 - 0x2f, ISA 0x290 (8 I/O ports) - - Datasheet: http://www.winbond.com - - * Winbond W83783S - - Prefix: 'w83783s' - - Addresses scanned: I2C 0x2d - - Datasheet: http://www.winbond-usa.com/products/winbond_products/pdfs/PCIC/w83783s.pdf - - * Asus AS99127F - - Prefix: 'as99127f' - - Addresses scanned: I2C 0x28 - 0x2f - - Datasheet: Unavailable from Asus - - - -Authors: - - - Frodo Looijaard , - - Philip Edelbrock , - - Mark Studebaker - -Module parameters ------------------ - -* init int - (default 1) - - Use 'init=0' to bypass initializing the chip. - Try this if your computer crashes when you load the module. - -* reset int - (default 0) - The driver used to reset the chip on load, but does no more. Use - 'reset=1' to restore the old behavior. Report if you need to do this. - -force_subclients=bus,caddr,saddr,saddr - This is used to force the i2c addresses for subclients of - a certain chip. Typical usage is `force_subclients=0,0x2d,0x4a,0x4b` - to force the subclients of chip 0x2d on bus 0 to i2c addresses - 0x4a and 0x4b. This parameter is useful for certain Tyan boards. - -Description ------------ - -This driver implements support for the Winbond W83781D, W83782D, W83783S -chips, and the Asus AS99127F chips. We will refer to them collectively as -W8378* chips. - -There is quite some difference between these chips, but they are similar -enough that it was sensible to put them together in one driver. -The Asus chips are similar to an I2C-only W83782D. - -+----------+---------+--------+-------+-------+---------+--------+------+-----+ -| Chip | #vin | #fanin | #pwm | #temp | wchipid | vendid | i2c | ISA | -+----------+---------+--------+-------+-------+---------+--------+------+-----+ -| as99127f | 7 | 3 | 0 | 3 | 0x31 | 0x12c3 | yes | no | -+----------+---------+--------+-------+-------+---------+--------+------+-----+ -| as99127f rev.2 (type_name = as99127f) | 0x31 | 0x5ca3 | yes | no | -+----------+---------+--------+-------+-------+---------+--------+------+-----+ -| w83781d | 7 | 3 | 0 | 3 | 0x10-1 | 0x5ca3 | yes | yes | -+----------+---------+--------+-------+-------+---------+--------+------+-----+ -| w83782d | 9 | 3 | 2-4 | 3 | 0x30 | 0x5ca3 | yes | yes | -+----------+---------+--------+-------+-------+---------+--------+------+-----+ -| w83783s | 5-6 | 3 | 2 | 1-2 | 0x40 | 0x5ca3 | yes | no | -+----------+---------+--------+-------+-------+---------+--------+------+-----+ - -Detection of these chips can sometimes be foiled because they can be in -an internal state that allows no clean access. If you know the address -of the chip, use a 'force' parameter; this will put them into a more -well-behaved state first. - -The W8378* implements temperature sensors (three on the W83781D and W83782D, -two on the W83783S), three fan rotation speed sensors, voltage sensors -(seven on the W83781D, nine on the W83782D and six on the W83783S), VID -lines, alarms with beep warnings, and some miscellaneous stuff. - -Temperatures are measured in degrees Celsius. There is always one main -temperature sensor, and one (W83783S) or two (W83781D and W83782D) other -sensors. An alarm is triggered for the main sensor once when the -Overtemperature Shutdown limit is crossed; it is triggered again as soon as -it drops below the Hysteresis value. A more useful behavior -can be found by setting the Hysteresis value to +127 degrees Celsius; in -this case, alarms are issued during all the time when the actual temperature -is above the Overtemperature Shutdown value. The driver sets the -hysteresis value for temp1 to 127 at initialization. - -For the other temperature sensor(s), an alarm is triggered when the -temperature gets higher then the Overtemperature Shutdown value; it stays -on until the temperature falls below the Hysteresis value. But on the -W83781D, there is only one alarm that functions for both other sensors! -Temperatures are guaranteed within a range of -55 to +125 degrees. The -main temperature sensors has a resolution of 1 degree; the other sensor(s) -of 0.5 degree. - -Fan rotation speeds are reported in RPM (rotations per minute). An alarm is -triggered if the rotation speed has dropped below a programmable limit. Fan -readings can be divided by a programmable divider (1, 2, 4 or 8 for the -W83781D; 1, 2, 4, 8, 16, 32, 64 or 128 for the others) to give -the readings more range or accuracy. Not all RPM values can accurately -be represented, so some rounding is done. With a divider of 2, the lowest -representable value is around 2600 RPM. - -Voltage sensors (also known as IN sensors) report their values in volts. -An alarm is triggered if the voltage has crossed a programmable minimum -or maximum limit. Note that minimum in this case always means 'closest to -zero'; this is important for negative voltage measurements. All voltage -inputs can measure voltages between 0 and 4.08 volts, with a resolution -of 0.016 volt. - -The VID lines encode the core voltage value: the voltage level your processor -should work with. This is hardcoded by the mainboard and/or processor itself. -It is a value in volts. When it is unconnected, you will often find the -value 3.50 V here. - -The W83782D and W83783S temperature conversion machine understands about -several kinds of temperature probes. You can program the so-called -beta value in the sensor files. '1' is the PII/Celeron diode, '2' is the -TN3904 transistor, and 3435 the default thermistor value. Other values -are (not yet) supported. - -In addition to the alarms described above, there is a CHAS alarm on the -chips which triggers if your computer case is open. - -When an alarm goes off, you can be warned by a beeping signal through -your computer speaker. It is possible to enable all beeping globally, -or only the beeping for some alarms. - -Individual alarm and beep bits: - -======== ========================== -0x000001 in0 -0x000002 in1 -0x000004 in2 -0x000008 in3 -0x000010 temp1 -0x000020 temp2 (+temp3 on W83781D) -0x000040 fan1 -0x000080 fan2 -0x000100 in4 -0x000200 in5 -0x000400 in6 -0x000800 fan3 -0x001000 chassis -0x002000 temp3 (W83782D only) -0x010000 in7 (W83782D only) -0x020000 in8 (W83782D only) -======== ========================== - -If an alarm triggers, it will remain triggered until the hardware register -is read at least once. This means that the cause for the alarm may -already have disappeared! Note that in the current implementation, all -hardware registers are read whenever any data is read (unless it is less -than 1.5 seconds since the last update). This means that you can easily -miss once-only alarms. - -The chips only update values each 1.5 seconds; reading them more often -will do no harm, but will return 'old' values. - -AS99127F PROBLEMS ------------------ -The as99127f support was developed without the benefit of a datasheet. -In most cases it is treated as a w83781d (although revision 2 of the -AS99127F looks more like a w83782d). -This support will be BETA until a datasheet is released. -One user has reported problems with fans stopping -occasionally. - -Note that the individual beep bits are inverted from the other chips. -The driver now takes care of this so that user-space applications -don't have to know about it. - -Known problems: - - Problems with diode/thermistor settings (supported?) - - One user reports fans stopping under high server load. - - Revision 2 seems to have 2 PWM registers but we don't know - how to handle them. More details below. - -These will not be fixed unless we get a datasheet. -If you have problems, please lobby Asus to release a datasheet. -Unfortunately several others have without success. -Please do not send mail to us asking for better as99127f support. -We have done the best we can without a datasheet. -Please do not send mail to the author or the sensors group asking for -a datasheet or ideas on how to convince Asus. We can't help. - - -NOTES ------ - 783s has no in1 so that in[2-6] are compatible with the 781d/782d. - - 783s pin is programmable for -5V or temp1; defaults to -5V, - no control in driver so temp1 doesn't work. - - 782d and 783s datasheets differ on which is pwm1 and which is pwm2. - We chose to follow 782d. - - 782d and 783s pin is programmable for fan3 input or pwm2 output; - defaults to fan3 input. - If pwm2 is enabled (with echo 255 1 > pwm2), then - fan3 will report 0. - - 782d has pwm1-2 for ISA, pwm1-4 for i2c. (pwm3-4 share pins with - the ISA pins) - -Data sheet updates ------------------- - - PWM clock registers: - * 000: master / 512 - * 001: master / 1024 - * 010: master / 2048 - * 011: master / 4096 - * 100: master / 8192 - - -Answers from Winbond tech support ---------------------------------- - -:: - - > - > 1) In the W83781D data sheet section 7.2 last paragraph, it talks about - > reprogramming the R-T table if the Beta of the thermistor is not - > 3435K. The R-T table is described briefly in section 8.20. - > What formulas do I use to program a new R-T table for a given Beta? - > - - We are sorry that the calculation for R-T table value is - confidential. If you have another Beta value of thermistor, we can help - to calculate the R-T table for you. But you should give us real R-T - Table which can be gotten by thermistor vendor. Therefore we will calculate - them and obtain 32-byte data, and you can fill the 32-byte data to the - register in Bank0.CR51 of W83781D. - - - > 2) In the W83782D data sheet, it mentions that pins 38, 39, and 40 are - > programmable to be either thermistor or Pentium II diode inputs. - > How do I program them for diode inputs? I can't find any register - > to program these to be diode inputs. - - You may program Bank0 CR[5Dh] and CR[59h] registers. - - =============================== =============== ============== ============ - CR[5Dh] bit 1(VTIN1) bit 2(VTIN2) bit 3(VTIN3) - - thermistor 0 0 0 - diode 1 1 1 - - - (error) CR[59h] bit 4(VTIN1) bit 2(VTIN2) bit 3(VTIN3) - (right) CR[59h] bit 4(VTIN1) bit 5(VTIN2) bit 6(VTIN3) - - PII thermal diode 1 1 1 - 2N3904 diode 0 0 0 - =============================== =============== ============== ============ - - -Asus Clones ------------ - -We have no datasheets for the Asus clones (AS99127F and ASB100 Bach). -Here are some very useful information that were given to us by Alex Van -Kaam about how to detect these chips, and how to read their values. He -also gives advice for another Asus chipset, the Mozart-2 (which we -don't support yet). Thanks Alex! - -I reworded some parts and added personal comments. - -Detection -^^^^^^^^^ - -AS99127F rev.1, AS99127F rev.2 and ASB100: -- I2C address range: 0x29 - 0x2F -- If register 0x58 holds 0x31 then we have an Asus (either ASB100 or AS99127F) -- Which one depends on register 0x4F (manufacturer ID): - - - 0x06 or 0x94: ASB100 - - 0x12 or 0xC3: AS99127F rev.1 - - 0x5C or 0xA3: AS99127F rev.2 - - Note that 0x5CA3 is Winbond's ID (WEC), which let us think Asus get their - AS99127F rev.2 direct from Winbond. The other codes mean ATT and DVC, - respectively. ATT could stand for Asustek something (although it would be - very badly chosen IMHO), I don't know what DVC could stand for. Maybe - these codes simply aren't meant to be decoded that way. - -Mozart-2: -- I2C address: 0x77 -- If register 0x58 holds 0x56 or 0x10 then we have a Mozart-2 -- Of the Mozart there are 3 types: - - - 0x58=0x56, 0x4E=0x94, 0x4F=0x36: Asus ASM58 Mozart-2 - - 0x58=0x56, 0x4E=0x94, 0x4F=0x06: Asus AS2K129R Mozart-2 - - 0x58=0x10, 0x4E=0x5C, 0x4F=0xA3: Asus ??? Mozart-2 - - You can handle all 3 the exact same way :) - -Temperature sensors -^^^^^^^^^^^^^^^^^^^ - -ASB100: - - sensor 1: register 0x27 - - sensor 2 & 3 are the 2 LM75's on the SMBus - - sensor 4: register 0x17 - -Remark: - - I noticed that on Intel boards sensor 2 is used for the CPU - and 4 is ignored/stuck, on AMD boards sensor 4 is the CPU and sensor 2 is - either ignored or a socket temperature. - -AS99127F (rev.1 and 2 alike): - - sensor 1: register 0x27 - - sensor 2 & 3 are the 2 LM75's on the SMBus - -Remark: - - Register 0x5b is suspected to be temperature type selector. Bit 1 - would control temp1, bit 3 temp2 and bit 5 temp3. - -Mozart-2: - - sensor 1: register 0x27 - - sensor 2: register 0x13 - -Fan sensors -^^^^^^^^^^^ - -ASB100, AS99127F (rev.1 and 2 alike): - - 3 fans, identical to the W83781D - -Mozart-2: - - 2 fans only, 1350000/RPM/div - - fan 1: register 0x28, divisor on register 0xA1 (bits 4-5) - - fan 2: register 0x29, divisor on register 0xA1 (bits 6-7) - -Voltages -^^^^^^^^ - -This is where there is a difference between AS99127F rev.1 and 2. - -Remark: - - The difference is similar to the difference between - W83781D and W83782D. - -ASB100: - - in0=r(0x20)*0.016 - - in1=r(0x21)*0.016 - - in2=r(0x22)*0.016 - - in3=r(0x23)*0.016*1.68 - - in4=r(0x24)*0.016*3.8 - - in5=r(0x25)*(-0.016)*3.97 - - in6=r(0x26)*(-0.016)*1.666 - -AS99127F rev.1: - - in0=r(0x20)*0.016 - - in1=r(0x21)*0.016 - - in2=r(0x22)*0.016 - - in3=r(0x23)*0.016*1.68 - - in4=r(0x24)*0.016*3.8 - - in5=r(0x25)*(-0.016)*3.97 - - in6=r(0x26)*(-0.016)*1.503 - -AS99127F rev.2: - - in0=r(0x20)*0.016 - - in1=r(0x21)*0.016 - - in2=r(0x22)*0.016 - - in3=r(0x23)*0.016*1.68 - - in4=r(0x24)*0.016*3.8 - - in5=(r(0x25)*0.016-3.6)*5.14+3.6 - - in6=(r(0x26)*0.016-3.6)*3.14+3.6 - -Mozart-2: - - in0=r(0x20)*0.016 - - in1=255 - - in2=r(0x22)*0.016 - - in3=r(0x23)*0.016*1.68 - - in4=r(0x24)*0.016*4 - - in5=255 - - in6=255 - - -PWM -^^^ - -* Additional info about PWM on the AS99127F (may apply to other Asus - chips as well) by Jean Delvare as of 2004-04-09: - -AS99127F revision 2 seems to have two PWM registers at 0x59 and 0x5A, -and a temperature sensor type selector at 0x5B (which basically means -that they swapped registers 0x59 and 0x5B when you compare with Winbond -chips). -Revision 1 of the chip also has the temperature sensor type selector at -0x5B, but PWM registers have no effect. - -We don't know exactly how the temperature sensor type selection works. -Looks like bits 1-0 are for temp1, bits 3-2 for temp2 and bits 5-4 for -temp3, although it is possible that only the most significant bit matters -each time. So far, values other than 0 always broke the readings. - -PWM registers seem to be split in two parts: bit 7 is a mode selector, -while the other bits seem to define a value or threshold. - -When bit 7 is clear, bits 6-0 seem to hold a threshold value. If the value -is below a given limit, the fan runs at low speed. If the value is above -the limit, the fan runs at full speed. We have no clue as to what the limit -represents. Note that there seem to be some inertia in this mode, speed -changes may need some time to trigger. Also, an hysteresis mechanism is -suspected since walking through all the values increasingly and then -decreasingly led to slightly different limits. - -When bit 7 is set, bits 3-0 seem to hold a threshold value, while bits 6-4 -would not be significant. If the value is below a given limit, the fan runs -at full speed, while if it is above the limit it runs at low speed (so this -is the contrary of the other mode, in a way). Here again, we don't know -what the limit is supposed to represent. - -One remarkable thing is that the fans would only have two or three -different speeds (transitional states left apart), not a whole range as -you usually get with PWM. - -As a conclusion, you can write 0x00 or 0x8F to the PWM registers to make -fans run at low speed, and 0x7F or 0x80 to make them run at full speed. - -Please contact us if you can figure out how it is supposed to work. As -long as we don't know more, the w83781d driver doesn't handle PWM on -AS99127F chips at all. - -* Additional info about PWM on the AS99127F rev.1 by Hector Martin: - -I've been fiddling around with the (in)famous 0x59 register and -found out the following values do work as a form of coarse pwm: - -0x80 - - seems to turn fans off after some time(1-2 minutes)... might be - some form of auto-fan-control based on temp? hmm (Qfan? this mobo is an - old ASUS, it isn't marketed as Qfan. Maybe some beta pre-attempt at Qfan - that was dropped at the BIOS) -0x81 - - off -0x82 - - slightly "on-ner" than off, but my fans do not get to move. I can - hear the high-pitched PWM sound that motors give off at too-low-pwm. -0x83 - - now they do move. Estimate about 70% speed or so. -0x84-0x8f - - full on - -Changing the high nibble doesn't seem to do much except the high bit -(0x80) must be set for PWM to work, else the current pwm doesn't seem to -change. - -My mobo is an ASUS A7V266-E. This behavior is similar to what I got -with speedfan under Windows, where 0-15% would be off, 15-2x% (can't -remember the exact value) would be 70% and higher would be full on. - -* Additional info about PWM on the AS99127F rev.1 from lm-sensors - ticket #2350: - -I conducted some experiment on Asus P3B-F motherboard with AS99127F -(Ver. 1). - -I confirm that 0x59 register control the CPU_Fan Header on this -motherboard, and 0x5a register control PWR_Fan. - -In order to reduce the dependency of specific fan, the measurement is -conducted with a digital scope without fan connected. I found out that -P3B-F actually output variable DC voltage on fan header center pin, -looks like PWM is filtered on this motherboard. - -Here are some of measurements: - -==== ========= -0x80 20 mV -0x81 20 mV -0x82 232 mV -0x83 1.2 V -0x84 2.31 V -0x85 3.44 V -0x86 4.62 V -0x87 5.81 V -0x88 7.01 V -9x89 8.22 V -0x8a 9.42 V -0x8b 10.6 V -0x8c 11.9 V -0x8d 12.4 V -0x8e 12.4 V -0x8f 12.4 V -==== ========= diff --git a/Documentation/hwmon/w83781d.rst b/Documentation/hwmon/w83781d.rst new file mode 100644 index 000000000000..f36d33dfb704 --- /dev/null +++ b/Documentation/hwmon/w83781d.rst @@ -0,0 +1,513 @@ +Kernel driver w83781d +===================== + +Supported chips: + + * Winbond W83781D + + Prefix: 'w83781d' + + Addresses scanned: I2C 0x28 - 0x2f, ISA 0x290 (8 I/O ports) + + Datasheet: http://www.winbond-usa.com/products/winbond_products/pdfs/PCIC/w83781d.pdf + + * Winbond W83782D + + Prefix: 'w83782d' + + Addresses scanned: I2C 0x28 - 0x2f, ISA 0x290 (8 I/O ports) + + Datasheet: http://www.winbond.com + + * Winbond W83783S + + Prefix: 'w83783s' + + Addresses scanned: I2C 0x2d + + Datasheet: http://www.winbond-usa.com/products/winbond_products/pdfs/PCIC/w83783s.pdf + + * Asus AS99127F + + Prefix: 'as99127f' + + Addresses scanned: I2C 0x28 - 0x2f + + Datasheet: Unavailable from Asus + + + +Authors: + + - Frodo Looijaard , + - Philip Edelbrock , + - Mark Studebaker + +Module parameters +----------------- + +* init int + (default 1) + + Use 'init=0' to bypass initializing the chip. + Try this if your computer crashes when you load the module. + +* reset int + (default 0) + The driver used to reset the chip on load, but does no more. Use + 'reset=1' to restore the old behavior. Report if you need to do this. + +force_subclients=bus,caddr,saddr,saddr + This is used to force the i2c addresses for subclients of + a certain chip. Typical usage is `force_subclients=0,0x2d,0x4a,0x4b` + to force the subclients of chip 0x2d on bus 0 to i2c addresses + 0x4a and 0x4b. This parameter is useful for certain Tyan boards. + +Description +----------- + +This driver implements support for the Winbond W83781D, W83782D, W83783S +chips, and the Asus AS99127F chips. We will refer to them collectively as +W8378* chips. + +There is quite some difference between these chips, but they are similar +enough that it was sensible to put them together in one driver. +The Asus chips are similar to an I2C-only W83782D. + ++----------+---------+--------+-------+-------+---------+--------+------+-----+ +| Chip | #vin | #fanin | #pwm | #temp | wchipid | vendid | i2c | ISA | ++----------+---------+--------+-------+-------+---------+--------+------+-----+ +| as99127f | 7 | 3 | 0 | 3 | 0x31 | 0x12c3 | yes | no | ++----------+---------+--------+-------+-------+---------+--------+------+-----+ +| as99127f rev.2 (type_name = as99127f) | 0x31 | 0x5ca3 | yes | no | ++----------+---------+--------+-------+-------+---------+--------+------+-----+ +| w83781d | 7 | 3 | 0 | 3 | 0x10-1 | 0x5ca3 | yes | yes | ++----------+---------+--------+-------+-------+---------+--------+------+-----+ +| w83782d | 9 | 3 | 2-4 | 3 | 0x30 | 0x5ca3 | yes | yes | ++----------+---------+--------+-------+-------+---------+--------+------+-----+ +| w83783s | 5-6 | 3 | 2 | 1-2 | 0x40 | 0x5ca3 | yes | no | ++----------+---------+--------+-------+-------+---------+--------+------+-----+ + +Detection of these chips can sometimes be foiled because they can be in +an internal state that allows no clean access. If you know the address +of the chip, use a 'force' parameter; this will put them into a more +well-behaved state first. + +The W8378* implements temperature sensors (three on the W83781D and W83782D, +two on the W83783S), three fan rotation speed sensors, voltage sensors +(seven on the W83781D, nine on the W83782D and six on the W83783S), VID +lines, alarms with beep warnings, and some miscellaneous stuff. + +Temperatures are measured in degrees Celsius. There is always one main +temperature sensor, and one (W83783S) or two (W83781D and W83782D) other +sensors. An alarm is triggered for the main sensor once when the +Overtemperature Shutdown limit is crossed; it is triggered again as soon as +it drops below the Hysteresis value. A more useful behavior +can be found by setting the Hysteresis value to +127 degrees Celsius; in +this case, alarms are issued during all the time when the actual temperature +is above the Overtemperature Shutdown value. The driver sets the +hysteresis value for temp1 to 127 at initialization. + +For the other temperature sensor(s), an alarm is triggered when the +temperature gets higher then the Overtemperature Shutdown value; it stays +on until the temperature falls below the Hysteresis value. But on the +W83781D, there is only one alarm that functions for both other sensors! +Temperatures are guaranteed within a range of -55 to +125 degrees. The +main temperature sensors has a resolution of 1 degree; the other sensor(s) +of 0.5 degree. + +Fan rotation speeds are reported in RPM (rotations per minute). An alarm is +triggered if the rotation speed has dropped below a programmable limit. Fan +readings can be divided by a programmable divider (1, 2, 4 or 8 for the +W83781D; 1, 2, 4, 8, 16, 32, 64 or 128 for the others) to give +the readings more range or accuracy. Not all RPM values can accurately +be represented, so some rounding is done. With a divider of 2, the lowest +representable value is around 2600 RPM. + +Voltage sensors (also known as IN sensors) report their values in volts. +An alarm is triggered if the voltage has crossed a programmable minimum +or maximum limit. Note that minimum in this case always means 'closest to +zero'; this is important for negative voltage measurements. All voltage +inputs can measure voltages between 0 and 4.08 volts, with a resolution +of 0.016 volt. + +The VID lines encode the core voltage value: the voltage level your processor +should work with. This is hardcoded by the mainboard and/or processor itself. +It is a value in volts. When it is unconnected, you will often find the +value 3.50 V here. + +The W83782D and W83783S temperature conversion machine understands about +several kinds of temperature probes. You can program the so-called +beta value in the sensor files. '1' is the PII/Celeron diode, '2' is the +TN3904 transistor, and 3435 the default thermistor value. Other values +are (not yet) supported. + +In addition to the alarms described above, there is a CHAS alarm on the +chips which triggers if your computer case is open. + +When an alarm goes off, you can be warned by a beeping signal through +your computer speaker. It is possible to enable all beeping globally, +or only the beeping for some alarms. + +Individual alarm and beep bits: + +======== ========================== +0x000001 in0 +0x000002 in1 +0x000004 in2 +0x000008 in3 +0x000010 temp1 +0x000020 temp2 (+temp3 on W83781D) +0x000040 fan1 +0x000080 fan2 +0x000100 in4 +0x000200 in5 +0x000400 in6 +0x000800 fan3 +0x001000 chassis +0x002000 temp3 (W83782D only) +0x010000 in7 (W83782D only) +0x020000 in8 (W83782D only) +======== ========================== + +If an alarm triggers, it will remain triggered until the hardware register +is read at least once. This means that the cause for the alarm may +already have disappeared! Note that in the current implementation, all +hardware registers are read whenever any data is read (unless it is less +than 1.5 seconds since the last update). This means that you can easily +miss once-only alarms. + +The chips only update values each 1.5 seconds; reading them more often +will do no harm, but will return 'old' values. + +AS99127F PROBLEMS +----------------- +The as99127f support was developed without the benefit of a datasheet. +In most cases it is treated as a w83781d (although revision 2 of the +AS99127F looks more like a w83782d). +This support will be BETA until a datasheet is released. +One user has reported problems with fans stopping +occasionally. + +Note that the individual beep bits are inverted from the other chips. +The driver now takes care of this so that user-space applications +don't have to know about it. + +Known problems: + - Problems with diode/thermistor settings (supported?) + - One user reports fans stopping under high server load. + - Revision 2 seems to have 2 PWM registers but we don't know + how to handle them. More details below. + +These will not be fixed unless we get a datasheet. +If you have problems, please lobby Asus to release a datasheet. +Unfortunately several others have without success. +Please do not send mail to us asking for better as99127f support. +We have done the best we can without a datasheet. +Please do not send mail to the author or the sensors group asking for +a datasheet or ideas on how to convince Asus. We can't help. + + +NOTES +----- + 783s has no in1 so that in[2-6] are compatible with the 781d/782d. + + 783s pin is programmable for -5V or temp1; defaults to -5V, + no control in driver so temp1 doesn't work. + + 782d and 783s datasheets differ on which is pwm1 and which is pwm2. + We chose to follow 782d. + + 782d and 783s pin is programmable for fan3 input or pwm2 output; + defaults to fan3 input. + If pwm2 is enabled (with echo 255 1 > pwm2), then + fan3 will report 0. + + 782d has pwm1-2 for ISA, pwm1-4 for i2c. (pwm3-4 share pins with + the ISA pins) + +Data sheet updates +------------------ + - PWM clock registers: + * 000: master / 512 + * 001: master / 1024 + * 010: master / 2048 + * 011: master / 4096 + * 100: master / 8192 + + +Answers from Winbond tech support +--------------------------------- + +:: + + > + > 1) In the W83781D data sheet section 7.2 last paragraph, it talks about + > reprogramming the R-T table if the Beta of the thermistor is not + > 3435K. The R-T table is described briefly in section 8.20. + > What formulas do I use to program a new R-T table for a given Beta? + > + + We are sorry that the calculation for R-T table value is + confidential. If you have another Beta value of thermistor, we can help + to calculate the R-T table for you. But you should give us real R-T + Table which can be gotten by thermistor vendor. Therefore we will calculate + them and obtain 32-byte data, and you can fill the 32-byte data to the + register in Bank0.CR51 of W83781D. + + + > 2) In the W83782D data sheet, it mentions that pins 38, 39, and 40 are + > programmable to be either thermistor or Pentium II diode inputs. + > How do I program them for diode inputs? I can't find any register + > to program these to be diode inputs. + + You may program Bank0 CR[5Dh] and CR[59h] registers. + + =============================== =============== ============== ============ + CR[5Dh] bit 1(VTIN1) bit 2(VTIN2) bit 3(VTIN3) + + thermistor 0 0 0 + diode 1 1 1 + + + (error) CR[59h] bit 4(VTIN1) bit 2(VTIN2) bit 3(VTIN3) + (right) CR[59h] bit 4(VTIN1) bit 5(VTIN2) bit 6(VTIN3) + + PII thermal diode 1 1 1 + 2N3904 diode 0 0 0 + =============================== =============== ============== ============ + + +Asus Clones +----------- + +We have no datasheets for the Asus clones (AS99127F and ASB100 Bach). +Here are some very useful information that were given to us by Alex Van +Kaam about how to detect these chips, and how to read their values. He +also gives advice for another Asus chipset, the Mozart-2 (which we +don't support yet). Thanks Alex! + +I reworded some parts and added personal comments. + +Detection +^^^^^^^^^ + +AS99127F rev.1, AS99127F rev.2 and ASB100: +- I2C address range: 0x29 - 0x2F +- If register 0x58 holds 0x31 then we have an Asus (either ASB100 or AS99127F) +- Which one depends on register 0x4F (manufacturer ID): + + - 0x06 or 0x94: ASB100 + - 0x12 or 0xC3: AS99127F rev.1 + - 0x5C or 0xA3: AS99127F rev.2 + + Note that 0x5CA3 is Winbond's ID (WEC), which let us think Asus get their + AS99127F rev.2 direct from Winbond. The other codes mean ATT and DVC, + respectively. ATT could stand for Asustek something (although it would be + very badly chosen IMHO), I don't know what DVC could stand for. Maybe + these codes simply aren't meant to be decoded that way. + +Mozart-2: +- I2C address: 0x77 +- If register 0x58 holds 0x56 or 0x10 then we have a Mozart-2 +- Of the Mozart there are 3 types: + + - 0x58=0x56, 0x4E=0x94, 0x4F=0x36: Asus ASM58 Mozart-2 + - 0x58=0x56, 0x4E=0x94, 0x4F=0x06: Asus AS2K129R Mozart-2 + - 0x58=0x10, 0x4E=0x5C, 0x4F=0xA3: Asus ??? Mozart-2 + + You can handle all 3 the exact same way :) + +Temperature sensors +^^^^^^^^^^^^^^^^^^^ + +ASB100: + - sensor 1: register 0x27 + - sensor 2 & 3 are the 2 LM75's on the SMBus + - sensor 4: register 0x17 + +Remark: + + I noticed that on Intel boards sensor 2 is used for the CPU + and 4 is ignored/stuck, on AMD boards sensor 4 is the CPU and sensor 2 is + either ignored or a socket temperature. + +AS99127F (rev.1 and 2 alike): + - sensor 1: register 0x27 + - sensor 2 & 3 are the 2 LM75's on the SMBus + +Remark: + + Register 0x5b is suspected to be temperature type selector. Bit 1 + would control temp1, bit 3 temp2 and bit 5 temp3. + +Mozart-2: + - sensor 1: register 0x27 + - sensor 2: register 0x13 + +Fan sensors +^^^^^^^^^^^ + +ASB100, AS99127F (rev.1 and 2 alike): + - 3 fans, identical to the W83781D + +Mozart-2: + - 2 fans only, 1350000/RPM/div + - fan 1: register 0x28, divisor on register 0xA1 (bits 4-5) + - fan 2: register 0x29, divisor on register 0xA1 (bits 6-7) + +Voltages +^^^^^^^^ + +This is where there is a difference between AS99127F rev.1 and 2. + +Remark: + + The difference is similar to the difference between + W83781D and W83782D. + +ASB100: + - in0=r(0x20)*0.016 + - in1=r(0x21)*0.016 + - in2=r(0x22)*0.016 + - in3=r(0x23)*0.016*1.68 + - in4=r(0x24)*0.016*3.8 + - in5=r(0x25)*(-0.016)*3.97 + - in6=r(0x26)*(-0.016)*1.666 + +AS99127F rev.1: + - in0=r(0x20)*0.016 + - in1=r(0x21)*0.016 + - in2=r(0x22)*0.016 + - in3=r(0x23)*0.016*1.68 + - in4=r(0x24)*0.016*3.8 + - in5=r(0x25)*(-0.016)*3.97 + - in6=r(0x26)*(-0.016)*1.503 + +AS99127F rev.2: + - in0=r(0x20)*0.016 + - in1=r(0x21)*0.016 + - in2=r(0x22)*0.016 + - in3=r(0x23)*0.016*1.68 + - in4=r(0x24)*0.016*3.8 + - in5=(r(0x25)*0.016-3.6)*5.14+3.6 + - in6=(r(0x26)*0.016-3.6)*3.14+3.6 + +Mozart-2: + - in0=r(0x20)*0.016 + - in1=255 + - in2=r(0x22)*0.016 + - in3=r(0x23)*0.016*1.68 + - in4=r(0x24)*0.016*4 + - in5=255 + - in6=255 + + +PWM +^^^ + +* Additional info about PWM on the AS99127F (may apply to other Asus + chips as well) by Jean Delvare as of 2004-04-09: + +AS99127F revision 2 seems to have two PWM registers at 0x59 and 0x5A, +and a temperature sensor type selector at 0x5B (which basically means +that they swapped registers 0x59 and 0x5B when you compare with Winbond +chips). +Revision 1 of the chip also has the temperature sensor type selector at +0x5B, but PWM registers have no effect. + +We don't know exactly how the temperature sensor type selection works. +Looks like bits 1-0 are for temp1, bits 3-2 for temp2 and bits 5-4 for +temp3, although it is possible that only the most significant bit matters +each time. So far, values other than 0 always broke the readings. + +PWM registers seem to be split in two parts: bit 7 is a mode selector, +while the other bits seem to define a value or threshold. + +When bit 7 is clear, bits 6-0 seem to hold a threshold value. If the value +is below a given limit, the fan runs at low speed. If the value is above +the limit, the fan runs at full speed. We have no clue as to what the limit +represents. Note that there seem to be some inertia in this mode, speed +changes may need some time to trigger. Also, an hysteresis mechanism is +suspected since walking through all the values increasingly and then +decreasingly led to slightly different limits. + +When bit 7 is set, bits 3-0 seem to hold a threshold value, while bits 6-4 +would not be significant. If the value is below a given limit, the fan runs +at full speed, while if it is above the limit it runs at low speed (so this +is the contrary of the other mode, in a way). Here again, we don't know +what the limit is supposed to represent. + +One remarkable thing is that the fans would only have two or three +different speeds (transitional states left apart), not a whole range as +you usually get with PWM. + +As a conclusion, you can write 0x00 or 0x8F to the PWM registers to make +fans run at low speed, and 0x7F or 0x80 to make them run at full speed. + +Please contact us if you can figure out how it is supposed to work. As +long as we don't know more, the w83781d driver doesn't handle PWM on +AS99127F chips at all. + +* Additional info about PWM on the AS99127F rev.1 by Hector Martin: + +I've been fiddling around with the (in)famous 0x59 register and +found out the following values do work as a form of coarse pwm: + +0x80 + - seems to turn fans off after some time(1-2 minutes)... might be + some form of auto-fan-control based on temp? hmm (Qfan? this mobo is an + old ASUS, it isn't marketed as Qfan. Maybe some beta pre-attempt at Qfan + that was dropped at the BIOS) +0x81 + - off +0x82 + - slightly "on-ner" than off, but my fans do not get to move. I can + hear the high-pitched PWM sound that motors give off at too-low-pwm. +0x83 + - now they do move. Estimate about 70% speed or so. +0x84-0x8f + - full on + +Changing the high nibble doesn't seem to do much except the high bit +(0x80) must be set for PWM to work, else the current pwm doesn't seem to +change. + +My mobo is an ASUS A7V266-E. This behavior is similar to what I got +with speedfan under Windows, where 0-15% would be off, 15-2x% (can't +remember the exact value) would be 70% and higher would be full on. + +* Additional info about PWM on the AS99127F rev.1 from lm-sensors + ticket #2350: + +I conducted some experiment on Asus P3B-F motherboard with AS99127F +(Ver. 1). + +I confirm that 0x59 register control the CPU_Fan Header on this +motherboard, and 0x5a register control PWR_Fan. + +In order to reduce the dependency of specific fan, the measurement is +conducted with a digital scope without fan connected. I found out that +P3B-F actually output variable DC voltage on fan header center pin, +looks like PWM is filtered on this motherboard. + +Here are some of measurements: + +==== ========= +0x80 20 mV +0x81 20 mV +0x82 232 mV +0x83 1.2 V +0x84 2.31 V +0x85 3.44 V +0x86 4.62 V +0x87 5.81 V +0x88 7.01 V +9x89 8.22 V +0x8a 9.42 V +0x8b 10.6 V +0x8c 11.9 V +0x8d 12.4 V +0x8e 12.4 V +0x8f 12.4 V +==== ========= diff --git a/Documentation/hwmon/w83791d b/Documentation/hwmon/w83791d deleted file mode 100644 index a91f9e5fb0c6..000000000000 --- a/Documentation/hwmon/w83791d +++ /dev/null @@ -1,180 +0,0 @@ -Kernel driver w83791d -===================== - -Supported chips: - - * Winbond W83791D - - Prefix: 'w83791d' - - Addresses scanned: I2C 0x2c - 0x2f - - Datasheet: http://www.winbond-usa.com/products/winbond_products/pdfs/PCIC/W83791D_W83791Gb.pdf - -Author: Charles Spirakis - -This driver was derived from the w83781d.c and w83792d.c source files. - -Credits: - - w83781d.c: - - - Frodo Looijaard , - - Philip Edelbrock , - - Mark Studebaker - - w83792d.c: - - - Shane Huang (Winbond), - - Rudolf Marek - -Additional contributors: - - - Sven Anders - - Marc Hulsman - -Module Parameters ------------------ - -* init boolean - (default 0) - - Use 'init=1' to have the driver do extra software initializations. - The default behavior is to do the minimum initialization possible - and depend on the BIOS to properly setup the chip. If you know you - have a w83791d and you're having problems, try init=1 before trying - reset=1. - -* reset boolean - (default 0) - - Use 'reset=1' to reset the chip (via index 0x40, bit 7). The default - behavior is no chip reset to preserve BIOS settings. - -* force_subclients=bus,caddr,saddr,saddr - This is used to force the i2c addresses for subclients of - a certain chip. Example usage is `force_subclients=0,0x2f,0x4a,0x4b` - to force the subclients of chip 0x2f on bus 0 to i2c addresses - 0x4a and 0x4b. - - -Description ------------ - -This driver implements support for the Winbond W83791D chip. The W83791G -chip appears to be the same as the W83791D but is lead free. - -Detection of the chip can sometimes be foiled because it can be in an -internal state that allows no clean access (Bank with ID register is not -currently selected). If you know the address of the chip, use a 'force' -parameter; this will put it into a more well-behaved state first. - -The driver implements three temperature sensors, ten voltage sensors, -five fan rotation speed sensors and manual PWM control of each fan. - -Temperatures are measured in degrees Celsius and measurement resolution is 1 -degC for temp1 and 0.5 degC for temp2 and temp3. An alarm is triggered when -the temperature gets higher than the Overtemperature Shutdown value; it stays -on until the temperature falls below the Hysteresis value. - -Voltage sensors (also known as IN sensors) report their values in millivolts. -An alarm is triggered if the voltage has crossed a programmable minimum -or maximum limit. - -Fan rotation speeds are reported in RPM (rotations per minute). An alarm is -triggered if the rotation speed has dropped below a programmable limit. Fan -readings can be divided by a programmable divider (1, 2, 4, 8, 16, -32, 64 or 128 for all fans) to give the readings more range or accuracy. - -Each fan controlled is controlled by PWM. The PWM duty cycle can be read and -set for each fan separately. Valid values range from 0 (stop) to 255 (full). -PWM 1-3 support Thermal Cruise mode, in which the PWMs are automatically -regulated to keep respectively temp 1-3 at a certain target temperature. -See below for the description of the sysfs-interface. - -The w83791d has a global bit used to enable beeping from the speaker when an -alarm is triggered as well as a bitmask to enable or disable the beep for -specific alarms. You need both the global beep enable bit and the -corresponding beep bit to be on for a triggered alarm to sound a beep. - -The sysfs interface to the global enable is via the sysfs beep_enable file. -This file is used for both legacy and new code. - -The sysfs interface to the beep bitmask has migrated from the original legacy -method of a single sysfs beep_mask file to a newer method using multiple -`*_beep` files as described in `Documentation/hwmon/sysfs-interface`. - -A similar change has occurred for the bitmap corresponding to the alarms. The -original legacy method used a single sysfs alarms file containing a bitmap -of triggered alarms. The newer method uses multiple sysfs `*_alarm` files -(again following the pattern described in sysfs-interface). - -Since both methods read and write the underlying hardware, they can be used -interchangeably and changes in one will automatically be reflected by -the other. If you use the legacy bitmask method, your user-space code is -responsible for handling the fact that the alarms and beep_mask bitmaps -are not the same (see the table below). - -NOTE: All new code should be written to use the newer sysfs-interface -specification as that avoids bitmap problems and is the preferred interface -going forward. - -The driver reads the hardware chip values at most once every three seconds. -User mode code requesting values more often will receive cached values. - -/sys files ----------- -The sysfs-interface is documented in the 'sysfs-interface' file. Only -chip-specific options are documented here. - -======================= ======================================================= -pwm[1-3]_enable this file controls mode of fan/temperature control for - fan 1-3. Fan/PWM 4-5 only support manual mode. - - * 1 Manual mode - * 2 Thermal Cruise mode - * 3 Fan Speed Cruise mode (no further support) - -temp[1-3]_target defines the target temperature for Thermal Cruise mode. - Unit: millidegree Celsius - RW - -temp[1-3]_tolerance temperature tolerance for Thermal Cruise mode. - Specifies an interval around the target temperature - in which the fan speed is not changed. - Unit: millidegree Celsius - RW -======================= ======================================================= - -Alarms bitmap vs. beep_mask bitmask ------------------------------------ - -For legacy code using the alarms and beep_mask files: - -============= ======== ========= ========================== -Signal Alarms beep_mask Obs -============= ======== ========= ========================== -in0 (VCORE) 0x000001 0x000001 -in1 (VINR0) 0x000002 0x002000 <== mismatch -in2 (+3.3VIN) 0x000004 0x000004 -in3 (5VDD) 0x000008 0x000008 -in4 (+12VIN) 0x000100 0x000100 -in5 (-12VIN) 0x000200 0x000200 -in6 (-5VIN) 0x000400 0x000400 -in7 (VSB) 0x080000 0x010000 <== mismatch -in8 (VBAT) 0x100000 0x020000 <== mismatch -in9 (VINR1) 0x004000 0x004000 -temp1 0x000010 0x000010 -temp2 0x000020 0x000020 -temp3 0x002000 0x000002 <== mismatch -fan1 0x000040 0x000040 -fan2 0x000080 0x000080 -fan3 0x000800 0x000800 -fan4 0x200000 0x200000 -fan5 0x400000 0x400000 -tart1 0x010000 0x040000 <== mismatch -tart2 0x020000 0x080000 <== mismatch -tart3 0x040000 0x100000 <== mismatch -case_open 0x001000 0x001000 -global_enable - 0x800000 (modified via beep_enable) -============= ======== ========= ========================== diff --git a/Documentation/hwmon/w83791d.rst b/Documentation/hwmon/w83791d.rst new file mode 100644 index 000000000000..3adaed39b157 --- /dev/null +++ b/Documentation/hwmon/w83791d.rst @@ -0,0 +1,180 @@ +Kernel driver w83791d +===================== + +Supported chips: + + * Winbond W83791D + + Prefix: 'w83791d' + + Addresses scanned: I2C 0x2c - 0x2f + + Datasheet: http://www.winbond-usa.com/products/winbond_products/pdfs/PCIC/W83791D_W83791Gb.pdf + +Author: Charles Spirakis + +This driver was derived from the w83781d.c and w83792d.c source files. + +Credits: + + w83781d.c: + + - Frodo Looijaard , + - Philip Edelbrock , + - Mark Studebaker + + w83792d.c: + + - Shane Huang (Winbond), + - Rudolf Marek + +Additional contributors: + + - Sven Anders + - Marc Hulsman + +Module Parameters +----------------- + +* init boolean + (default 0) + + Use 'init=1' to have the driver do extra software initializations. + The default behavior is to do the minimum initialization possible + and depend on the BIOS to properly setup the chip. If you know you + have a w83791d and you're having problems, try init=1 before trying + reset=1. + +* reset boolean + (default 0) + + Use 'reset=1' to reset the chip (via index 0x40, bit 7). The default + behavior is no chip reset to preserve BIOS settings. + +* force_subclients=bus,caddr,saddr,saddr + This is used to force the i2c addresses for subclients of + a certain chip. Example usage is `force_subclients=0,0x2f,0x4a,0x4b` + to force the subclients of chip 0x2f on bus 0 to i2c addresses + 0x4a and 0x4b. + + +Description +----------- + +This driver implements support for the Winbond W83791D chip. The W83791G +chip appears to be the same as the W83791D but is lead free. + +Detection of the chip can sometimes be foiled because it can be in an +internal state that allows no clean access (Bank with ID register is not +currently selected). If you know the address of the chip, use a 'force' +parameter; this will put it into a more well-behaved state first. + +The driver implements three temperature sensors, ten voltage sensors, +five fan rotation speed sensors and manual PWM control of each fan. + +Temperatures are measured in degrees Celsius and measurement resolution is 1 +degC for temp1 and 0.5 degC for temp2 and temp3. An alarm is triggered when +the temperature gets higher than the Overtemperature Shutdown value; it stays +on until the temperature falls below the Hysteresis value. + +Voltage sensors (also known as IN sensors) report their values in millivolts. +An alarm is triggered if the voltage has crossed a programmable minimum +or maximum limit. + +Fan rotation speeds are reported in RPM (rotations per minute). An alarm is +triggered if the rotation speed has dropped below a programmable limit. Fan +readings can be divided by a programmable divider (1, 2, 4, 8, 16, +32, 64 or 128 for all fans) to give the readings more range or accuracy. + +Each fan controlled is controlled by PWM. The PWM duty cycle can be read and +set for each fan separately. Valid values range from 0 (stop) to 255 (full). +PWM 1-3 support Thermal Cruise mode, in which the PWMs are automatically +regulated to keep respectively temp 1-3 at a certain target temperature. +See below for the description of the sysfs-interface. + +The w83791d has a global bit used to enable beeping from the speaker when an +alarm is triggered as well as a bitmask to enable or disable the beep for +specific alarms. You need both the global beep enable bit and the +corresponding beep bit to be on for a triggered alarm to sound a beep. + +The sysfs interface to the global enable is via the sysfs beep_enable file. +This file is used for both legacy and new code. + +The sysfs interface to the beep bitmask has migrated from the original legacy +method of a single sysfs beep_mask file to a newer method using multiple +`*_beep` files as described in `Documentation/hwmon/sysfs-interface.rst`. + +A similar change has occurred for the bitmap corresponding to the alarms. The +original legacy method used a single sysfs alarms file containing a bitmap +of triggered alarms. The newer method uses multiple sysfs `*_alarm` files +(again following the pattern described in sysfs-interface). + +Since both methods read and write the underlying hardware, they can be used +interchangeably and changes in one will automatically be reflected by +the other. If you use the legacy bitmask method, your user-space code is +responsible for handling the fact that the alarms and beep_mask bitmaps +are not the same (see the table below). + +NOTE: All new code should be written to use the newer sysfs-interface +specification as that avoids bitmap problems and is the preferred interface +going forward. + +The driver reads the hardware chip values at most once every three seconds. +User mode code requesting values more often will receive cached values. + +/sys files +---------- +The sysfs-interface is documented in the 'sysfs-interface' file. Only +chip-specific options are documented here. + +======================= ======================================================= +pwm[1-3]_enable this file controls mode of fan/temperature control for + fan 1-3. Fan/PWM 4-5 only support manual mode. + + * 1 Manual mode + * 2 Thermal Cruise mode + * 3 Fan Speed Cruise mode (no further support) + +temp[1-3]_target defines the target temperature for Thermal Cruise mode. + Unit: millidegree Celsius + RW + +temp[1-3]_tolerance temperature tolerance for Thermal Cruise mode. + Specifies an interval around the target temperature + in which the fan speed is not changed. + Unit: millidegree Celsius + RW +======================= ======================================================= + +Alarms bitmap vs. beep_mask bitmask +----------------------------------- + +For legacy code using the alarms and beep_mask files: + +============= ======== ========= ========================== +Signal Alarms beep_mask Obs +============= ======== ========= ========================== +in0 (VCORE) 0x000001 0x000001 +in1 (VINR0) 0x000002 0x002000 <== mismatch +in2 (+3.3VIN) 0x000004 0x000004 +in3 (5VDD) 0x000008 0x000008 +in4 (+12VIN) 0x000100 0x000100 +in5 (-12VIN) 0x000200 0x000200 +in6 (-5VIN) 0x000400 0x000400 +in7 (VSB) 0x080000 0x010000 <== mismatch +in8 (VBAT) 0x100000 0x020000 <== mismatch +in9 (VINR1) 0x004000 0x004000 +temp1 0x000010 0x000010 +temp2 0x000020 0x000020 +temp3 0x002000 0x000002 <== mismatch +fan1 0x000040 0x000040 +fan2 0x000080 0x000080 +fan3 0x000800 0x000800 +fan4 0x200000 0x200000 +fan5 0x400000 0x400000 +tart1 0x010000 0x040000 <== mismatch +tart2 0x020000 0x080000 <== mismatch +tart3 0x040000 0x100000 <== mismatch +case_open 0x001000 0x001000 +global_enable - 0x800000 (modified via beep_enable) +============= ======== ========= ========================== diff --git a/Documentation/hwmon/w83792d b/Documentation/hwmon/w83792d deleted file mode 100644 index 92c4bfe4968c..000000000000 --- a/Documentation/hwmon/w83792d +++ /dev/null @@ -1,199 +0,0 @@ -Kernel driver w83792d -===================== - -Supported chips: - - * Winbond W83792D - - Prefix: 'w83792d' - - Addresses scanned: I2C 0x2c - 0x2f - - Datasheet: http://www.winbond.com.tw - -Author: Shane Huang (Winbond) -Updated: Roger Lucas - - -Module Parameters ------------------ - -* init int - (default 1) - - Use 'init=0' to bypass initializing the chip. - Try this if your computer crashes when you load the module. - -* force_subclients=bus,caddr,saddr,saddr - This is used to force the i2c addresses for subclients of - a certain chip. Example usage is `force_subclients=0,0x2f,0x4a,0x4b` - to force the subclients of chip 0x2f on bus 0 to i2c addresses - 0x4a and 0x4b. - - -Description ------------ - -This driver implements support for the Winbond W83792AD/D. - -Detection of the chip can sometimes be foiled because it can be in an -internal state that allows no clean access (Bank with ID register is not -currently selected). If you know the address of the chip, use a 'force' -parameter; this will put it into a more well-behaved state first. - -The driver implements three temperature sensors, seven fan rotation speed -sensors, nine voltage sensors, and two automatic fan regulation -strategies called: Smart Fan I (Thermal Cruise mode) and Smart Fan II. - -The driver also implements up to seven fan control outputs: pwm1-7. Pwm1-7 -can be configured to PWM output or Analogue DC output via their associated -pwmX_mode. Outputs pwm4 through pwm7 may or may not be present depending on -how the W83792AD/D was configured by the BIOS. - -Automatic fan control mode is possible only for fan1-fan3. - -For all pwmX outputs, a value of 0 means minimum fan speed and a value of -255 means maximum fan speed. - -Temperatures are measured in degrees Celsius and measurement resolution is 1 -degC for temp1 and 0.5 degC for temp2 and temp3. An alarm is triggered when -the temperature gets higher than the Overtemperature Shutdown value; it stays -on until the temperature falls below the Hysteresis value. - -Fan rotation speeds are reported in RPM (rotations per minute). An alarm is -triggered if the rotation speed has dropped below a programmable limit. Fan -readings can be divided by a programmable divider (1, 2, 4, 8, 16, 32, 64 or -128) to give the readings more range or accuracy. - -Voltage sensors (also known as IN sensors) report their values in millivolts. -An alarm is triggered if the voltage has crossed a programmable minimum -or maximum limit. - -Alarms are provided as output from "realtime status register". Following bits -are defined: - -==== ========== -bit alarm on -==== ========== -0 in0 -1 in1 -2 temp1 -3 temp2 -4 temp3 -5 fan1 -6 fan2 -7 fan3 -8 in2 -9 in3 -10 in4 -11 in5 -12 in6 -13 VID change -14 chassis -15 fan7 -16 tart1 -17 tart2 -18 tart3 -19 in7 -20 in8 -21 fan4 -22 fan5 -23 fan6 -==== ========== - -Tart will be asserted while target temperature cannot be achieved after 3 minutes -of full speed rotation of corresponding fan. - -In addition to the alarms described above, there is a CHAS alarm on the chips -which triggers if your computer case is open (This one is latched, contrary -to realtime alarms). - -The chips only update values each 3 seconds; reading them more often will -do no harm, but will return 'old' values. - - -W83792D PROBLEMS ----------------- -Known problems: - - This driver is only for Winbond W83792D C version device, there - are also some motherboards with B version W83792D device. The - calculation method to in6-in7(measured value, limits) is a little - different between C and B version. C or B version can be identified - by CR[0x49h]. - - The function of vid and vrm has not been finished, because I'm NOT - very familiar with them. Adding support is welcome. - - The function of chassis open detection needs more tests. - - If you have ASUS server board and chip was not found: Then you will - need to upgrade to latest (or beta) BIOS. If it does not help please - contact us. - -Fan control ------------ - -Manual mode ------------ - -Works as expected. You just need to specify desired PWM/DC value (fan speed) -in appropriate pwm# file. - -Thermal cruise --------------- - -In this mode, W83792D provides the Smart Fan system to automatically control -fan speed to keep the temperatures of CPU and the system within specific -range. At first a wanted temperature and interval must be set. This is done -via thermal_cruise# file. The tolerance# file serves to create T +- tolerance -interval. The fan speed will be lowered as long as the current temperature -remains below the thermal_cruise# +- tolerance# value. Once the temperature -exceeds the high limit (T+tolerance), the fan will be turned on with a -specific speed set by pwm# and automatically controlled its PWM duty cycle -with the temperature varying. Three conditions may occur: - -(1) If the temperature still exceeds the high limit, PWM duty -cycle will increase slowly. - -(2) If the temperature goes below the high limit, but still above the low -limit (T-tolerance), the fan speed will be fixed at the current speed because -the temperature is in the target range. - -(3) If the temperature goes below the low limit, PWM duty cycle will decrease -slowly to 0 or a preset stop value until the temperature exceeds the low -limit. (The preset stop value handling is not yet implemented in driver) - -Smart Fan II ------------- - -W83792D also provides a special mode for fan. Four temperature points are -available. When related temperature sensors detects the temperature in preset -temperature region (sf2_point@_fan# +- tolerance#) it will cause fans to run -on programmed value from sf2_level@_fan#. You need to set four temperatures -for each fan. - - -/sys files ----------- - -pwm[1-7] - - this file stores PWM duty cycle or DC value (fan speed) in range: - - 0 (stop) to 255 (full) -pwm[1-3]_enable - - this file controls mode of fan/temperature control: - - * 0 Disabled - * 1 Manual mode - * 2 Smart Fan II - * 3 Thermal Cruise -pwm[1-7]_mode - - Select PWM or DC mode - - * 0 DC - * 1 PWM -thermal_cruise[1-3] - - Selects the desired temperature for cruise (degC) -tolerance[1-3] - - Value in degrees of Celsius (degC) for +- T -sf2_point[1-4]_fan[1-3] - - four temperature points for each fan for Smart Fan II -sf2_level[1-3]_fan[1-3] - - three PWM/DC levels for each fan for Smart Fan II diff --git a/Documentation/hwmon/w83792d.rst b/Documentation/hwmon/w83792d.rst new file mode 100644 index 000000000000..92c4bfe4968c --- /dev/null +++ b/Documentation/hwmon/w83792d.rst @@ -0,0 +1,199 @@ +Kernel driver w83792d +===================== + +Supported chips: + + * Winbond W83792D + + Prefix: 'w83792d' + + Addresses scanned: I2C 0x2c - 0x2f + + Datasheet: http://www.winbond.com.tw + +Author: Shane Huang (Winbond) +Updated: Roger Lucas + + +Module Parameters +----------------- + +* init int + (default 1) + + Use 'init=0' to bypass initializing the chip. + Try this if your computer crashes when you load the module. + +* force_subclients=bus,caddr,saddr,saddr + This is used to force the i2c addresses for subclients of + a certain chip. Example usage is `force_subclients=0,0x2f,0x4a,0x4b` + to force the subclients of chip 0x2f on bus 0 to i2c addresses + 0x4a and 0x4b. + + +Description +----------- + +This driver implements support for the Winbond W83792AD/D. + +Detection of the chip can sometimes be foiled because it can be in an +internal state that allows no clean access (Bank with ID register is not +currently selected). If you know the address of the chip, use a 'force' +parameter; this will put it into a more well-behaved state first. + +The driver implements three temperature sensors, seven fan rotation speed +sensors, nine voltage sensors, and two automatic fan regulation +strategies called: Smart Fan I (Thermal Cruise mode) and Smart Fan II. + +The driver also implements up to seven fan control outputs: pwm1-7. Pwm1-7 +can be configured to PWM output or Analogue DC output via their associated +pwmX_mode. Outputs pwm4 through pwm7 may or may not be present depending on +how the W83792AD/D was configured by the BIOS. + +Automatic fan control mode is possible only for fan1-fan3. + +For all pwmX outputs, a value of 0 means minimum fan speed and a value of +255 means maximum fan speed. + +Temperatures are measured in degrees Celsius and measurement resolution is 1 +degC for temp1 and 0.5 degC for temp2 and temp3. An alarm is triggered when +the temperature gets higher than the Overtemperature Shutdown value; it stays +on until the temperature falls below the Hysteresis value. + +Fan rotation speeds are reported in RPM (rotations per minute). An alarm is +triggered if the rotation speed has dropped below a programmable limit. Fan +readings can be divided by a programmable divider (1, 2, 4, 8, 16, 32, 64 or +128) to give the readings more range or accuracy. + +Voltage sensors (also known as IN sensors) report their values in millivolts. +An alarm is triggered if the voltage has crossed a programmable minimum +or maximum limit. + +Alarms are provided as output from "realtime status register". Following bits +are defined: + +==== ========== +bit alarm on +==== ========== +0 in0 +1 in1 +2 temp1 +3 temp2 +4 temp3 +5 fan1 +6 fan2 +7 fan3 +8 in2 +9 in3 +10 in4 +11 in5 +12 in6 +13 VID change +14 chassis +15 fan7 +16 tart1 +17 tart2 +18 tart3 +19 in7 +20 in8 +21 fan4 +22 fan5 +23 fan6 +==== ========== + +Tart will be asserted while target temperature cannot be achieved after 3 minutes +of full speed rotation of corresponding fan. + +In addition to the alarms described above, there is a CHAS alarm on the chips +which triggers if your computer case is open (This one is latched, contrary +to realtime alarms). + +The chips only update values each 3 seconds; reading them more often will +do no harm, but will return 'old' values. + + +W83792D PROBLEMS +---------------- +Known problems: + - This driver is only for Winbond W83792D C version device, there + are also some motherboards with B version W83792D device. The + calculation method to in6-in7(measured value, limits) is a little + different between C and B version. C or B version can be identified + by CR[0x49h]. + - The function of vid and vrm has not been finished, because I'm NOT + very familiar with them. Adding support is welcome. + - The function of chassis open detection needs more tests. + - If you have ASUS server board and chip was not found: Then you will + need to upgrade to latest (or beta) BIOS. If it does not help please + contact us. + +Fan control +----------- + +Manual mode +----------- + +Works as expected. You just need to specify desired PWM/DC value (fan speed) +in appropriate pwm# file. + +Thermal cruise +-------------- + +In this mode, W83792D provides the Smart Fan system to automatically control +fan speed to keep the temperatures of CPU and the system within specific +range. At first a wanted temperature and interval must be set. This is done +via thermal_cruise# file. The tolerance# file serves to create T +- tolerance +interval. The fan speed will be lowered as long as the current temperature +remains below the thermal_cruise# +- tolerance# value. Once the temperature +exceeds the high limit (T+tolerance), the fan will be turned on with a +specific speed set by pwm# and automatically controlled its PWM duty cycle +with the temperature varying. Three conditions may occur: + +(1) If the temperature still exceeds the high limit, PWM duty +cycle will increase slowly. + +(2) If the temperature goes below the high limit, but still above the low +limit (T-tolerance), the fan speed will be fixed at the current speed because +the temperature is in the target range. + +(3) If the temperature goes below the low limit, PWM duty cycle will decrease +slowly to 0 or a preset stop value until the temperature exceeds the low +limit. (The preset stop value handling is not yet implemented in driver) + +Smart Fan II +------------ + +W83792D also provides a special mode for fan. Four temperature points are +available. When related temperature sensors detects the temperature in preset +temperature region (sf2_point@_fan# +- tolerance#) it will cause fans to run +on programmed value from sf2_level@_fan#. You need to set four temperatures +for each fan. + + +/sys files +---------- + +pwm[1-7] + - this file stores PWM duty cycle or DC value (fan speed) in range: + + 0 (stop) to 255 (full) +pwm[1-3]_enable + - this file controls mode of fan/temperature control: + + * 0 Disabled + * 1 Manual mode + * 2 Smart Fan II + * 3 Thermal Cruise +pwm[1-7]_mode + - Select PWM or DC mode + + * 0 DC + * 1 PWM +thermal_cruise[1-3] + - Selects the desired temperature for cruise (degC) +tolerance[1-3] + - Value in degrees of Celsius (degC) for +- T +sf2_point[1-4]_fan[1-3] + - four temperature points for each fan for Smart Fan II +sf2_level[1-3]_fan[1-3] + - three PWM/DC levels for each fan for Smart Fan II diff --git a/Documentation/hwmon/w83793 b/Documentation/hwmon/w83793 deleted file mode 100644 index 83bb40c48645..000000000000 --- a/Documentation/hwmon/w83793 +++ /dev/null @@ -1,113 +0,0 @@ -Kernel driver w83793 -==================== - -Supported chips: - - * Winbond W83793G/W83793R - - Prefix: 'w83793' - - Addresses scanned: I2C 0x2c - 0x2f - - Datasheet: Still not published - -Authors: - - Yuan Mu (Winbond Electronics) - - Rudolf Marek - - -Module parameters ------------------ - -* reset int - (default 0) - - This parameter is not recommended, it will lose motherboard specific - settings. Use 'reset=1' to reset the chip when loading this module. - -* force_subclients=bus,caddr,saddr1,saddr2 - This is used to force the i2c addresses for subclients of - a certain chip. Typical usage is `force_subclients=0,0x2f,0x4a,0x4b` - to force the subclients of chip 0x2f on bus 0 to i2c addresses - 0x4a and 0x4b. - - -Description ------------ - -This driver implements support for Winbond W83793G/W83793R chips. - -* Exported features - This driver exports 10 voltage sensors, up to 12 fan tachometer inputs, - 6 remote temperatures, up to 8 sets of PWM fan controls, SmartFan - (automatic fan speed control) on all temperature/PWM combinations, 2 - sets of 6-pin CPU VID input. - -* Sensor resolutions - If your motherboard maker used the reference design, the resolution of - voltage0-2 is 2mV, resolution of voltage3/4/5 is 16mV, 8mV for voltage6, - 24mV for voltage7/8. Temp1-4 have a 0.25 degree Celsius resolution, - temp5-6 have a 1 degree Celsiis resolution. - -* Temperature sensor types - Temp1-4 have 2 possible types. It can be read from (and written to) - temp[1-4]_type. - - - If the value is 3, it starts monitoring using a remote termal diode - (default). - - If the value is 6, it starts monitoring using the temperature sensor - in Intel CPU and get result by PECI. - - Temp5-6 can be connected to external thermistors (value of - temp[5-6]_type is 4). - -* Alarm mechanism - For voltage sensors, an alarm triggers if the measured value is below - the low voltage limit or over the high voltage limit. - For temperature sensors, an alarm triggers if the measured value goes - above the high temperature limit, and wears off only after the measured - value drops below the hysteresis value. - For fan sensors, an alarm triggers if the measured value is below the - low speed limit. - -* SmartFan/PWM control - If you want to set a pwm fan to manual mode, you just need to make sure it - is not controlled by any temp channel, for example, you want to set fan1 - to manual mode, you need to check the value of temp[1-6]_fan_map, make - sure bit 0 is cleared in the 6 values. And then set the pwm1 value to - control the fan. - - Each temperature channel can control all the 8 PWM outputs (by setting the - corresponding bit in tempX_fan_map), you can set the temperature channel - mode using temp[1-6]_pwm_enable, 2 is Thermal Cruise mode and 3 - is the SmartFanII mode. Temperature channels will try to speed up or - slow down all controlled fans, this means one fan can receive different - PWM value requests from different temperature channels, but the chip - will always pick the safest (max) PWM value for each fan. - - In Thermal Cruise mode, the chip attempts to keep the temperature at a - predefined value, within a tolerance margin. So if tempX_input > - thermal_cruiseX + toleranceX, the chip will increase the PWM value, - if tempX_input < thermal_cruiseX - toleranceX, the chip will decrease - the PWM value. If the temperature is within the tolerance range, the PWM - value is left unchanged. - - SmartFanII works differently, you have to define up to 7 PWM, temperature - trip points, defining a PWM/temperature curve which the chip will follow. - While not fundamentally different from the Thermal Cruise mode, the - implementation is quite different, giving you a finer-grained control. - -* Chassis - If the case open alarm triggers, it will stay in this state unless cleared - by writing 0 to the sysfs file "intrusion0_alarm". - -* VID and VRM - The VRM version is detected automatically, don't modify the it unless you - *do* know the cpu VRM version and it's not properly detected. - - -Notes ------ - - Only Fan1-5 and PWM1-3 are guaranteed to always exist, other fan inputs and - PWM outputs may or may not exist depending on the chip pin configuration. diff --git a/Documentation/hwmon/w83793.rst b/Documentation/hwmon/w83793.rst new file mode 100644 index 000000000000..83bb40c48645 --- /dev/null +++ b/Documentation/hwmon/w83793.rst @@ -0,0 +1,113 @@ +Kernel driver w83793 +==================== + +Supported chips: + + * Winbond W83793G/W83793R + + Prefix: 'w83793' + + Addresses scanned: I2C 0x2c - 0x2f + + Datasheet: Still not published + +Authors: + - Yuan Mu (Winbond Electronics) + - Rudolf Marek + + +Module parameters +----------------- + +* reset int + (default 0) + + This parameter is not recommended, it will lose motherboard specific + settings. Use 'reset=1' to reset the chip when loading this module. + +* force_subclients=bus,caddr,saddr1,saddr2 + This is used to force the i2c addresses for subclients of + a certain chip. Typical usage is `force_subclients=0,0x2f,0x4a,0x4b` + to force the subclients of chip 0x2f on bus 0 to i2c addresses + 0x4a and 0x4b. + + +Description +----------- + +This driver implements support for Winbond W83793G/W83793R chips. + +* Exported features + This driver exports 10 voltage sensors, up to 12 fan tachometer inputs, + 6 remote temperatures, up to 8 sets of PWM fan controls, SmartFan + (automatic fan speed control) on all temperature/PWM combinations, 2 + sets of 6-pin CPU VID input. + +* Sensor resolutions + If your motherboard maker used the reference design, the resolution of + voltage0-2 is 2mV, resolution of voltage3/4/5 is 16mV, 8mV for voltage6, + 24mV for voltage7/8. Temp1-4 have a 0.25 degree Celsius resolution, + temp5-6 have a 1 degree Celsiis resolution. + +* Temperature sensor types + Temp1-4 have 2 possible types. It can be read from (and written to) + temp[1-4]_type. + + - If the value is 3, it starts monitoring using a remote termal diode + (default). + - If the value is 6, it starts monitoring using the temperature sensor + in Intel CPU and get result by PECI. + + Temp5-6 can be connected to external thermistors (value of + temp[5-6]_type is 4). + +* Alarm mechanism + For voltage sensors, an alarm triggers if the measured value is below + the low voltage limit or over the high voltage limit. + For temperature sensors, an alarm triggers if the measured value goes + above the high temperature limit, and wears off only after the measured + value drops below the hysteresis value. + For fan sensors, an alarm triggers if the measured value is below the + low speed limit. + +* SmartFan/PWM control + If you want to set a pwm fan to manual mode, you just need to make sure it + is not controlled by any temp channel, for example, you want to set fan1 + to manual mode, you need to check the value of temp[1-6]_fan_map, make + sure bit 0 is cleared in the 6 values. And then set the pwm1 value to + control the fan. + + Each temperature channel can control all the 8 PWM outputs (by setting the + corresponding bit in tempX_fan_map), you can set the temperature channel + mode using temp[1-6]_pwm_enable, 2 is Thermal Cruise mode and 3 + is the SmartFanII mode. Temperature channels will try to speed up or + slow down all controlled fans, this means one fan can receive different + PWM value requests from different temperature channels, but the chip + will always pick the safest (max) PWM value for each fan. + + In Thermal Cruise mode, the chip attempts to keep the temperature at a + predefined value, within a tolerance margin. So if tempX_input > + thermal_cruiseX + toleranceX, the chip will increase the PWM value, + if tempX_input < thermal_cruiseX - toleranceX, the chip will decrease + the PWM value. If the temperature is within the tolerance range, the PWM + value is left unchanged. + + SmartFanII works differently, you have to define up to 7 PWM, temperature + trip points, defining a PWM/temperature curve which the chip will follow. + While not fundamentally different from the Thermal Cruise mode, the + implementation is quite different, giving you a finer-grained control. + +* Chassis + If the case open alarm triggers, it will stay in this state unless cleared + by writing 0 to the sysfs file "intrusion0_alarm". + +* VID and VRM + The VRM version is detected automatically, don't modify the it unless you + *do* know the cpu VRM version and it's not properly detected. + + +Notes +----- + + Only Fan1-5 and PWM1-3 are guaranteed to always exist, other fan inputs and + PWM outputs may or may not exist depending on the chip pin configuration. diff --git a/Documentation/hwmon/w83795 b/Documentation/hwmon/w83795 deleted file mode 100644 index d0615e2fabb9..000000000000 --- a/Documentation/hwmon/w83795 +++ /dev/null @@ -1,142 +0,0 @@ -Kernel driver w83795 -==================== - -Supported chips: - - * Winbond/Nuvoton W83795G - - Prefix: 'w83795g' - - Addresses scanned: I2C 0x2c - 0x2f - - Datasheet: Available for download on nuvoton.com - - * Winbond/Nuvoton W83795ADG - - Prefix: 'w83795adg' - - Addresses scanned: I2C 0x2c - 0x2f - - Datasheet: Available for download on nuvoton.com - -Authors: - - Wei Song (Nuvoton) - - Jean Delvare - - -Pin mapping ------------ - -Here is a summary of the pin mapping for the W83795G and W83795ADG. -This can be useful to convert data provided by board manufacturers -into working libsensors configuration statements. - - -- W83795G - -========= ======================= =============== ================ -Pin Name Register Sysfs attribute -========= ======================= =============== ================ - 13 VSEN1 (VCORE1) 10h in0 - 14 VSEN2 (VCORE2) 11h in1 - 15 VSEN3 (VCORE3) 12h in2 - 16 VSEN4 13h in3 - 17 VSEN5 14h in4 - 18 VSEN6 15h in5 - 19 VSEN7 16h in6 - 20 VSEN8 17h in7 - 21 VSEN9 18h in8 - 22 VSEN10 19h in9 - 23 VSEN11 1Ah in10 - 28 VTT 1Bh in11 - 24 3VDD 1Ch in12 - 25 3VSB 1Dh in13 - 26 VBAT 1Eh in14 - 3 VSEN12/TR5 1Fh in15/temp5 - 4 VSEN13/TR5 20h in16/temp6 - 5/ 6 VDSEN14/TR1/TD1 21h in17/temp1 - 7/ 8 VDSEN15/TR2/TD2 22h in18/temp2 - 9/ 10 VDSEN16/TR3/TD3 23h in19/temp3 - 11/ 12 VDSEN17/TR4/TD4 24h in20/temp4 - 40 FANIN1 2Eh fan1 - 42 FANIN2 2Fh fan2 - 44 FANIN3 30h fan3 - 46 FANIN4 31h fan4 - 48 FANIN5 32h fan5 - 50 FANIN6 33h fan6 - 52 FANIN7 34h fan7 - 54 FANIN8 35h fan8 - 57 FANIN9 36h fan9 - 58 FANIN10 37h fan10 - 59 FANIN11 38h fan11 - 60 FANIN12 39h fan12 - 31 FANIN13 3Ah fan13 - 35 FANIN14 3Bh fan14 - 41 FANCTL1 10h (bank 2) pwm1 - 43 FANCTL2 11h (bank 2) pwm2 - 45 FANCTL3 12h (bank 2) pwm3 - 47 FANCTL4 13h (bank 2) pwm4 - 49 FANCTL5 14h (bank 2) pwm5 - 51 FANCTL6 15h (bank 2) pwm6 - 53 FANCTL7 16h (bank 2) pwm7 - 55 FANCTL8 17h (bank 2) pwm8 - 29/ 30 PECI/TSI (DTS1) 26h temp7 - 29/ 30 PECI/TSI (DTS2) 27h temp8 - 29/ 30 PECI/TSI (DTS3) 28h temp9 - 29/ 30 PECI/TSI (DTS4) 29h temp10 - 29/ 30 PECI/TSI (DTS5) 2Ah temp11 - 29/ 30 PECI/TSI (DTS6) 2Bh temp12 - 29/ 30 PECI/TSI (DTS7) 2Ch temp13 - 29/ 30 PECI/TSI (DTS8) 2Dh temp14 - 27 CASEOPEN# 46h intrusion0 -========= ======================= =============== ================ - -- W83795ADG - -========= ======================= =============== ================ -Pin Name Register Sysfs attribute -========= ======================= =============== ================ - 10 VSEN1 (VCORE1) 10h in0 - 11 VSEN2 (VCORE2) 11h in1 - 12 VSEN3 (VCORE3) 12h in2 - 13 VSEN4 13h in3 - 14 VSEN5 14h in4 - 15 VSEN6 15h in5 - 16 VSEN7 16h in6 - 17 VSEN8 17h in7 - 22 VTT 1Bh in11 - 18 3VDD 1Ch in12 - 19 3VSB 1Dh in13 - 20 VBAT 1Eh in14 - 48 VSEN12/TR5 1Fh in15/temp5 - 1 VSEN13/TR5 20h in16/temp6 - 2/ 3 VDSEN14/TR1/TD1 21h in17/temp1 - 4/ 5 VDSEN15/TR2/TD2 22h in18/temp2 - 6/ 7 VDSEN16/TR3/TD3 23h in19/temp3 - 8/ 9 VDSEN17/TR4/TD4 24h in20/temp4 - 32 FANIN1 2Eh fan1 - 34 FANIN2 2Fh fan2 - 36 FANIN3 30h fan3 - 37 FANIN4 31h fan4 - 38 FANIN5 32h fan5 - 39 FANIN6 33h fan6 - 40 FANIN7 34h fan7 - 41 FANIN8 35h fan8 - 43 FANIN9 36h fan9 - 44 FANIN10 37h fan10 - 45 FANIN11 38h fan11 - 46 FANIN12 39h fan12 - 24 FANIN13 3Ah fan13 - 28 FANIN14 3Bh fan14 - 33 FANCTL1 10h (bank 2) pwm1 - 35 FANCTL2 11h (bank 2) pwm2 - 23 PECI (DTS1) 26h temp7 - 23 PECI (DTS2) 27h temp8 - 23 PECI (DTS3) 28h temp9 - 23 PECI (DTS4) 29h temp10 - 23 PECI (DTS5) 2Ah temp11 - 23 PECI (DTS6) 2Bh temp12 - 23 PECI (DTS7) 2Ch temp13 - 23 PECI (DTS8) 2Dh temp14 - 21 CASEOPEN# 46h intrusion0 -========= ======================= =============== ================ diff --git a/Documentation/hwmon/w83795.rst b/Documentation/hwmon/w83795.rst new file mode 100644 index 000000000000..d0615e2fabb9 --- /dev/null +++ b/Documentation/hwmon/w83795.rst @@ -0,0 +1,142 @@ +Kernel driver w83795 +==================== + +Supported chips: + + * Winbond/Nuvoton W83795G + + Prefix: 'w83795g' + + Addresses scanned: I2C 0x2c - 0x2f + + Datasheet: Available for download on nuvoton.com + + * Winbond/Nuvoton W83795ADG + + Prefix: 'w83795adg' + + Addresses scanned: I2C 0x2c - 0x2f + + Datasheet: Available for download on nuvoton.com + +Authors: + - Wei Song (Nuvoton) + - Jean Delvare + + +Pin mapping +----------- + +Here is a summary of the pin mapping for the W83795G and W83795ADG. +This can be useful to convert data provided by board manufacturers +into working libsensors configuration statements. + + +- W83795G + +========= ======================= =============== ================ +Pin Name Register Sysfs attribute +========= ======================= =============== ================ + 13 VSEN1 (VCORE1) 10h in0 + 14 VSEN2 (VCORE2) 11h in1 + 15 VSEN3 (VCORE3) 12h in2 + 16 VSEN4 13h in3 + 17 VSEN5 14h in4 + 18 VSEN6 15h in5 + 19 VSEN7 16h in6 + 20 VSEN8 17h in7 + 21 VSEN9 18h in8 + 22 VSEN10 19h in9 + 23 VSEN11 1Ah in10 + 28 VTT 1Bh in11 + 24 3VDD 1Ch in12 + 25 3VSB 1Dh in13 + 26 VBAT 1Eh in14 + 3 VSEN12/TR5 1Fh in15/temp5 + 4 VSEN13/TR5 20h in16/temp6 + 5/ 6 VDSEN14/TR1/TD1 21h in17/temp1 + 7/ 8 VDSEN15/TR2/TD2 22h in18/temp2 + 9/ 10 VDSEN16/TR3/TD3 23h in19/temp3 + 11/ 12 VDSEN17/TR4/TD4 24h in20/temp4 + 40 FANIN1 2Eh fan1 + 42 FANIN2 2Fh fan2 + 44 FANIN3 30h fan3 + 46 FANIN4 31h fan4 + 48 FANIN5 32h fan5 + 50 FANIN6 33h fan6 + 52 FANIN7 34h fan7 + 54 FANIN8 35h fan8 + 57 FANIN9 36h fan9 + 58 FANIN10 37h fan10 + 59 FANIN11 38h fan11 + 60 FANIN12 39h fan12 + 31 FANIN13 3Ah fan13 + 35 FANIN14 3Bh fan14 + 41 FANCTL1 10h (bank 2) pwm1 + 43 FANCTL2 11h (bank 2) pwm2 + 45 FANCTL3 12h (bank 2) pwm3 + 47 FANCTL4 13h (bank 2) pwm4 + 49 FANCTL5 14h (bank 2) pwm5 + 51 FANCTL6 15h (bank 2) pwm6 + 53 FANCTL7 16h (bank 2) pwm7 + 55 FANCTL8 17h (bank 2) pwm8 + 29/ 30 PECI/TSI (DTS1) 26h temp7 + 29/ 30 PECI/TSI (DTS2) 27h temp8 + 29/ 30 PECI/TSI (DTS3) 28h temp9 + 29/ 30 PECI/TSI (DTS4) 29h temp10 + 29/ 30 PECI/TSI (DTS5) 2Ah temp11 + 29/ 30 PECI/TSI (DTS6) 2Bh temp12 + 29/ 30 PECI/TSI (DTS7) 2Ch temp13 + 29/ 30 PECI/TSI (DTS8) 2Dh temp14 + 27 CASEOPEN# 46h intrusion0 +========= ======================= =============== ================ + +- W83795ADG + +========= ======================= =============== ================ +Pin Name Register Sysfs attribute +========= ======================= =============== ================ + 10 VSEN1 (VCORE1) 10h in0 + 11 VSEN2 (VCORE2) 11h in1 + 12 VSEN3 (VCORE3) 12h in2 + 13 VSEN4 13h in3 + 14 VSEN5 14h in4 + 15 VSEN6 15h in5 + 16 VSEN7 16h in6 + 17 VSEN8 17h in7 + 22 VTT 1Bh in11 + 18 3VDD 1Ch in12 + 19 3VSB 1Dh in13 + 20 VBAT 1Eh in14 + 48 VSEN12/TR5 1Fh in15/temp5 + 1 VSEN13/TR5 20h in16/temp6 + 2/ 3 VDSEN14/TR1/TD1 21h in17/temp1 + 4/ 5 VDSEN15/TR2/TD2 22h in18/temp2 + 6/ 7 VDSEN16/TR3/TD3 23h in19/temp3 + 8/ 9 VDSEN17/TR4/TD4 24h in20/temp4 + 32 FANIN1 2Eh fan1 + 34 FANIN2 2Fh fan2 + 36 FANIN3 30h fan3 + 37 FANIN4 31h fan4 + 38 FANIN5 32h fan5 + 39 FANIN6 33h fan6 + 40 FANIN7 34h fan7 + 41 FANIN8 35h fan8 + 43 FANIN9 36h fan9 + 44 FANIN10 37h fan10 + 45 FANIN11 38h fan11 + 46 FANIN12 39h fan12 + 24 FANIN13 3Ah fan13 + 28 FANIN14 3Bh fan14 + 33 FANCTL1 10h (bank 2) pwm1 + 35 FANCTL2 11h (bank 2) pwm2 + 23 PECI (DTS1) 26h temp7 + 23 PECI (DTS2) 27h temp8 + 23 PECI (DTS3) 28h temp9 + 23 PECI (DTS4) 29h temp10 + 23 PECI (DTS5) 2Ah temp11 + 23 PECI (DTS6) 2Bh temp12 + 23 PECI (DTS7) 2Ch temp13 + 23 PECI (DTS8) 2Dh temp14 + 21 CASEOPEN# 46h intrusion0 +========= ======================= =============== ================ diff --git a/Documentation/hwmon/w83l785ts b/Documentation/hwmon/w83l785ts deleted file mode 100644 index 7fa5418fed11..000000000000 --- a/Documentation/hwmon/w83l785ts +++ /dev/null @@ -1,45 +0,0 @@ -Kernel driver w83l785ts -======================= - -Supported chips: - - * Winbond W83L785TS-S - - Prefix: 'w83l785ts' - - Addresses scanned: I2C 0x2e - - Datasheet: Publicly available at the Winbond USA website - - http://www.winbond-usa.com/products/winbond_products/pdfs/PCIC/W83L785TS-S.pdf - -Authors: - Jean Delvare - -Description ------------ - -The W83L785TS-S is a digital temperature sensor. It senses the -temperature of a single external diode. The high limit is -theoretically defined as 85 or 100 degrees C through a combination -of external resistors, so the user cannot change it. Values seen so -far suggest that the two possible limits are actually 95 and 110 -degrees C. The datasheet is rather poor and obviously inaccurate -on several points including this one. - -All temperature values are given in degrees Celsius. Resolution -is 1.0 degree. See the datasheet for details. - -The w83l785ts driver will not update its values more frequently than -every other second; reading them more often will do no harm, but will -return 'old' values. - -Known Issues ------------- - -On some systems (Asus), the BIOS is known to interfere with the driver -and cause read errors. Or maybe the W83L785TS-S chip is simply unreliable, -we don't really know. The driver will retry a given number of times -(5 by default) and then give up, returning the old value (or 0 if -there is no old value). It seems to work well enough so that you should -not notice anything. Thanks to James Bolt for helping test this feature. diff --git a/Documentation/hwmon/w83l785ts.rst b/Documentation/hwmon/w83l785ts.rst new file mode 100644 index 000000000000..7fa5418fed11 --- /dev/null +++ b/Documentation/hwmon/w83l785ts.rst @@ -0,0 +1,45 @@ +Kernel driver w83l785ts +======================= + +Supported chips: + + * Winbond W83L785TS-S + + Prefix: 'w83l785ts' + + Addresses scanned: I2C 0x2e + + Datasheet: Publicly available at the Winbond USA website + + http://www.winbond-usa.com/products/winbond_products/pdfs/PCIC/W83L785TS-S.pdf + +Authors: + Jean Delvare + +Description +----------- + +The W83L785TS-S is a digital temperature sensor. It senses the +temperature of a single external diode. The high limit is +theoretically defined as 85 or 100 degrees C through a combination +of external resistors, so the user cannot change it. Values seen so +far suggest that the two possible limits are actually 95 and 110 +degrees C. The datasheet is rather poor and obviously inaccurate +on several points including this one. + +All temperature values are given in degrees Celsius. Resolution +is 1.0 degree. See the datasheet for details. + +The w83l785ts driver will not update its values more frequently than +every other second; reading them more often will do no harm, but will +return 'old' values. + +Known Issues +------------ + +On some systems (Asus), the BIOS is known to interfere with the driver +and cause read errors. Or maybe the W83L785TS-S chip is simply unreliable, +we don't really know. The driver will retry a given number of times +(5 by default) and then give up, returning the old value (or 0 if +there is no old value). It seems to work well enough so that you should +not notice anything. Thanks to James Bolt for helping test this feature. diff --git a/Documentation/hwmon/w83l786ng b/Documentation/hwmon/w83l786ng deleted file mode 100644 index 2b7776190de3..000000000000 --- a/Documentation/hwmon/w83l786ng +++ /dev/null @@ -1,66 +0,0 @@ -Kernel driver w83l786ng -======================= - -Supported chips: - - * Winbond W83L786NG/W83L786NR - - Prefix: 'w83l786ng' - - Addresses scanned: I2C 0x2e - 0x2f - - Datasheet: http://www.winbond-usa.com/products/winbond_products/pdfs/PCIC/W83L786NRNG09.pdf - -Author: Kevin Lo - - -Module Parameters ------------------ - -* reset boolean - (default 0) - - Use 'reset=1' to reset the chip (via index 0x40, bit 7). The default - behavior is no chip reset to preserve BIOS settings - - -Description ------------ - -This driver implements support for Winbond W83L786NG/W83L786NR chips. - -The driver implements two temperature sensors, two fan rotation speed -sensors, and three voltage sensors. - -Temperatures are measured in degrees Celsius and measurement resolution is 1 -degC for temp1 and temp2. - -Fan rotation speeds are reported in RPM (rotations per minute). Fan readings -readings can be divided by a programmable divider (1, 2, 4, 8, 16, 32, 64 -or 128 for fan 1/2) to give the readings more range or accuracy. - -Voltage sensors (also known as IN sensors) report their values in millivolts. -An alarm is triggered if the voltage has crossed a programmable minimum -or maximum limit. - -/sys files ----------- - -pwm[1-2] - - this file stores PWM duty cycle or DC value (fan speed) in range: - - 0 (stop) to 255 (full) -pwm[1-2]_enable - - this file controls mode of fan/temperature control: - - * 0 Manual Mode - * 1 Thermal Cruise - * 2 Smart Fan II - * 4 FAN_SET -pwm[1-2]_mode - - Select PWM of DC mode - - * 0 DC - * 1 PWM -tolerance[1-2] - - Value in degrees of Celsius (degC) for +- T diff --git a/Documentation/hwmon/w83l786ng.rst b/Documentation/hwmon/w83l786ng.rst new file mode 100644 index 000000000000..2b7776190de3 --- /dev/null +++ b/Documentation/hwmon/w83l786ng.rst @@ -0,0 +1,66 @@ +Kernel driver w83l786ng +======================= + +Supported chips: + + * Winbond W83L786NG/W83L786NR + + Prefix: 'w83l786ng' + + Addresses scanned: I2C 0x2e - 0x2f + + Datasheet: http://www.winbond-usa.com/products/winbond_products/pdfs/PCIC/W83L786NRNG09.pdf + +Author: Kevin Lo + + +Module Parameters +----------------- + +* reset boolean + (default 0) + + Use 'reset=1' to reset the chip (via index 0x40, bit 7). The default + behavior is no chip reset to preserve BIOS settings + + +Description +----------- + +This driver implements support for Winbond W83L786NG/W83L786NR chips. + +The driver implements two temperature sensors, two fan rotation speed +sensors, and three voltage sensors. + +Temperatures are measured in degrees Celsius and measurement resolution is 1 +degC for temp1 and temp2. + +Fan rotation speeds are reported in RPM (rotations per minute). Fan readings +readings can be divided by a programmable divider (1, 2, 4, 8, 16, 32, 64 +or 128 for fan 1/2) to give the readings more range or accuracy. + +Voltage sensors (also known as IN sensors) report their values in millivolts. +An alarm is triggered if the voltage has crossed a programmable minimum +or maximum limit. + +/sys files +---------- + +pwm[1-2] + - this file stores PWM duty cycle or DC value (fan speed) in range: + + 0 (stop) to 255 (full) +pwm[1-2]_enable + - this file controls mode of fan/temperature control: + + * 0 Manual Mode + * 1 Thermal Cruise + * 2 Smart Fan II + * 4 FAN_SET +pwm[1-2]_mode + - Select PWM of DC mode + + * 0 DC + * 1 PWM +tolerance[1-2] + - Value in degrees of Celsius (degC) for +- T diff --git a/Documentation/hwmon/wm831x b/Documentation/hwmon/wm831x deleted file mode 100644 index c56fb35a2fb3..000000000000 --- a/Documentation/hwmon/wm831x +++ /dev/null @@ -1,40 +0,0 @@ -Kernel driver wm831x-hwmon -========================== - -Supported chips: - * Wolfson Microelectronics WM831x PMICs - - Prefix: 'wm831x' - - Datasheet: - - - http://www.wolfsonmicro.com/products/WM8310 - - http://www.wolfsonmicro.com/products/WM8311 - - http://www.wolfsonmicro.com/products/WM8312 - -Authors: Mark Brown - -Description ------------ - -The WM831x series of PMICs include an AUXADC which can be used to -monitor a range of system operating parameters, including the voltages -of the major supplies within the system. Currently the driver provides -reporting of all the input values but does not provide any alarms. - -Voltage Monitoring ------------------- - -Voltages are sampled by a 12 bit ADC. Voltages in millivolts are 1.465 -times the ADC value. - -Temperature Monitoring ----------------------- - -Temperatures are sampled by a 12 bit ADC. Chip and battery temperatures -are available. The chip temperature is calculated as: - - Degrees celsius = (512.18 - data) / 1.0983 - -while the battery temperature calculation will depend on the NTC -thermistor component. diff --git a/Documentation/hwmon/wm831x.rst b/Documentation/hwmon/wm831x.rst new file mode 100644 index 000000000000..c56fb35a2fb3 --- /dev/null +++ b/Documentation/hwmon/wm831x.rst @@ -0,0 +1,40 @@ +Kernel driver wm831x-hwmon +========================== + +Supported chips: + * Wolfson Microelectronics WM831x PMICs + + Prefix: 'wm831x' + + Datasheet: + + - http://www.wolfsonmicro.com/products/WM8310 + - http://www.wolfsonmicro.com/products/WM8311 + - http://www.wolfsonmicro.com/products/WM8312 + +Authors: Mark Brown + +Description +----------- + +The WM831x series of PMICs include an AUXADC which can be used to +monitor a range of system operating parameters, including the voltages +of the major supplies within the system. Currently the driver provides +reporting of all the input values but does not provide any alarms. + +Voltage Monitoring +------------------ + +Voltages are sampled by a 12 bit ADC. Voltages in millivolts are 1.465 +times the ADC value. + +Temperature Monitoring +---------------------- + +Temperatures are sampled by a 12 bit ADC. Chip and battery temperatures +are available. The chip temperature is calculated as: + + Degrees celsius = (512.18 - data) / 1.0983 + +while the battery temperature calculation will depend on the NTC +thermistor component. diff --git a/Documentation/hwmon/wm8350 b/Documentation/hwmon/wm8350 deleted file mode 100644 index cec044ca5900..000000000000 --- a/Documentation/hwmon/wm8350 +++ /dev/null @@ -1,30 +0,0 @@ -Kernel driver wm8350-hwmon -========================== - -Supported chips: - - * Wolfson Microelectronics WM835x PMICs - - Prefix: 'wm8350' - - Datasheet: - - - http://www.wolfsonmicro.com/products/WM8350 - - http://www.wolfsonmicro.com/products/WM8351 - - http://www.wolfsonmicro.com/products/WM8352 - -Authors: Mark Brown - -Description ------------ - -The WM835x series of PMICs include an AUXADC which can be used to -monitor a range of system operating parameters, including the voltages -of the major supplies within the system. Currently the driver provides -simple access to these major supplies. - -Voltage Monitoring ------------------- - -Voltages are sampled by a 12 bit ADC. For the internal supplies the ADC -is referenced to the system VRTC. diff --git a/Documentation/hwmon/wm8350.rst b/Documentation/hwmon/wm8350.rst new file mode 100644 index 000000000000..cec044ca5900 --- /dev/null +++ b/Documentation/hwmon/wm8350.rst @@ -0,0 +1,30 @@ +Kernel driver wm8350-hwmon +========================== + +Supported chips: + + * Wolfson Microelectronics WM835x PMICs + + Prefix: 'wm8350' + + Datasheet: + + - http://www.wolfsonmicro.com/products/WM8350 + - http://www.wolfsonmicro.com/products/WM8351 + - http://www.wolfsonmicro.com/products/WM8352 + +Authors: Mark Brown + +Description +----------- + +The WM835x series of PMICs include an AUXADC which can be used to +monitor a range of system operating parameters, including the voltages +of the major supplies within the system. Currently the driver provides +simple access to these major supplies. + +Voltage Monitoring +------------------ + +Voltages are sampled by a 12 bit ADC. For the internal supplies the ADC +is referenced to the system VRTC. diff --git a/Documentation/hwmon/xgene-hwmon b/Documentation/hwmon/xgene-hwmon deleted file mode 100644 index 439b30b881b6..000000000000 --- a/Documentation/hwmon/xgene-hwmon +++ /dev/null @@ -1,36 +0,0 @@ -Kernel driver xgene-hwmon -========================= - -Supported chips: - - * APM X-Gene SoC - -Description ------------ - -This driver adds hardware temperature and power reading support for -APM X-Gene SoC using the mailbox communication interface. -For device tree, it is the standard DT mailbox. -For ACPI, it is the PCC mailbox. - -The following sensors are supported - - * Temperature - - SoC on-die temperature in milli-degree C - - Alarm when high/over temperature occurs - - * Power - - CPU power in uW - - IO power in uW - -sysfs-Interface ---------------- - -temp0_input - - SoC on-die temperature (milli-degree C) -temp0_critical_alarm - - An 1 would indicates on-die temperature exceeded threshold -power0_input - - CPU power in (uW) -power1_input - - IO power in (uW) diff --git a/Documentation/hwmon/xgene-hwmon.rst b/Documentation/hwmon/xgene-hwmon.rst new file mode 100644 index 000000000000..439b30b881b6 --- /dev/null +++ b/Documentation/hwmon/xgene-hwmon.rst @@ -0,0 +1,36 @@ +Kernel driver xgene-hwmon +========================= + +Supported chips: + + * APM X-Gene SoC + +Description +----------- + +This driver adds hardware temperature and power reading support for +APM X-Gene SoC using the mailbox communication interface. +For device tree, it is the standard DT mailbox. +For ACPI, it is the PCC mailbox. + +The following sensors are supported + + * Temperature + - SoC on-die temperature in milli-degree C + - Alarm when high/over temperature occurs + + * Power + - CPU power in uW + - IO power in uW + +sysfs-Interface +--------------- + +temp0_input + - SoC on-die temperature (milli-degree C) +temp0_critical_alarm + - An 1 would indicates on-die temperature exceeded threshold +power0_input + - CPU power in (uW) +power1_input + - IO power in (uW) diff --git a/Documentation/hwmon/zl6100 b/Documentation/hwmon/zl6100 deleted file mode 100644 index 4029970bace4..000000000000 --- a/Documentation/hwmon/zl6100 +++ /dev/null @@ -1,213 +0,0 @@ -Kernel driver zl6100 -==================== - -Supported chips: - - * Intersil / Zilker Labs ZL2004 - - Prefix: 'zl2004' - - Addresses scanned: - - - Datasheet: http://www.intersil.com/data/fn/fn6847.pdf - - * Intersil / Zilker Labs ZL2005 - - Prefix: 'zl2005' - - Addresses scanned: - - - Datasheet: http://www.intersil.com/data/fn/fn6848.pdf - - * Intersil / Zilker Labs ZL2006 - - Prefix: 'zl2006' - - Addresses scanned: - - - Datasheet: http://www.intersil.com/data/fn/fn6850.pdf - - * Intersil / Zilker Labs ZL2008 - - Prefix: 'zl2008' - - Addresses scanned: - - - Datasheet: http://www.intersil.com/data/fn/fn6859.pdf - - * Intersil / Zilker Labs ZL2105 - - Prefix: 'zl2105' - - Addresses scanned: - - - Datasheet: http://www.intersil.com/data/fn/fn6851.pdf - - * Intersil / Zilker Labs ZL2106 - - Prefix: 'zl2106' - - Addresses scanned: - - - Datasheet: http://www.intersil.com/data/fn/fn6852.pdf - - * Intersil / Zilker Labs ZL6100 - - Prefix: 'zl6100' - - Addresses scanned: - - - Datasheet: http://www.intersil.com/data/fn/fn6876.pdf - - * Intersil / Zilker Labs ZL6105 - - Prefix: 'zl6105' - - Addresses scanned: - - - Datasheet: http://www.intersil.com/data/fn/fn6906.pdf - - * Intersil / Zilker Labs ZL9101M - - Prefix: 'zl9101' - - Addresses scanned: - - - Datasheet: http://www.intersil.com/data/fn/fn7669.pdf - - * Intersil / Zilker Labs ZL9117M - - Prefix: 'zl9117' - - Addresses scanned: - - - Datasheet: http://www.intersil.com/data/fn/fn7914.pdf - - * Ericsson BMR450, BMR451 - - Prefix: 'bmr450', 'bmr451' - - Addresses scanned: - - - Datasheet: - -http://archive.ericsson.net/service/internet/picov/get?DocNo=28701-EN/LZT146401 - - * Ericsson BMR462, BMR463, BMR464 - - Prefixes: 'bmr462', 'bmr463', 'bmr464' - - Addresses scanned: - - - Datasheet: - - http://archive.ericsson.net/service/internet/picov/get?DocNo=28701-EN/LZT146256 - -Author: Guenter Roeck - - -Description ------------ - -This driver supports hardware monitoring for Intersil / Zilker Labs ZL6100 and -compatible digital DC-DC controllers. - -The driver is a client driver to the core PMBus driver. Please see -Documentation/hwmon/pmbus and Documentation.hwmon/pmbus-core for details -on PMBus client drivers. - - -Usage Notes ------------ - -This driver does not auto-detect devices. You will have to instantiate the -devices explicitly. Please see Documentation/i2c/instantiating-devices for -details. - -.. warning:: - - Do not access chip registers using the i2cdump command, and do not use - any of the i2ctools commands on a command register used to save and restore - configuration data (0x11, 0x12, 0x15, 0x16, and 0xf4). The chips supported by - this driver interpret any access to those command registers (including read - commands) as request to execute the command in question. Unless write accesses - to those registers are protected, this may result in power loss, board resets, - and/or Flash corruption. Worst case, your board may turn into a brick. - - -Platform data support ---------------------- - -The driver supports standard PMBus driver platform data. - - -Module parameters ------------------ - -delay ------ - -Intersil/Zilker Labs DC-DC controllers require a minimum interval between I2C -bus accesses. According to Intersil, the minimum interval is 2 ms, though 1 ms -appears to be sufficient and has not caused any problems in testing. The problem -is known to affect all currently supported chips. For manual override, the -driver provides a writeable module parameter, 'delay', which can be used to set -the interval to a value between 0 and 65,535 microseconds. - - -Sysfs entries -------------- - -The following attributes are supported. Limits are read-write; all other -attributes are read-only. - -======================= ======================================================== -in1_label "vin" -in1_input Measured input voltage. -in1_min Minimum input voltage. -in1_max Maximum input voltage. -in1_lcrit Critical minimum input voltage. -in1_crit Critical maximum input voltage. -in1_min_alarm Input voltage low alarm. -in1_max_alarm Input voltage high alarm. -in1_lcrit_alarm Input voltage critical low alarm. -in1_crit_alarm Input voltage critical high alarm. - -in2_label "vmon" -in2_input Measured voltage on VMON (ZL2004) or VDRV (ZL9101M, - ZL9117M) pin. Reported voltage is 16x the voltage on the - pin (adjusted internally by the chip). -in2_lcrit Critical minimum VMON/VDRV Voltage. -in2_crit Critical maximum VMON/VDRV voltage. -in2_lcrit_alarm VMON/VDRV voltage critical low alarm. -in2_crit_alarm VMON/VDRV voltage critical high alarm. - - vmon attributes are supported on ZL2004, ZL9101M, - and ZL9117M only. - -inX_label "vout1" -inX_input Measured output voltage. -inX_lcrit Critical minimum output Voltage. -inX_crit Critical maximum output voltage. -inX_lcrit_alarm Critical output voltage critical low alarm. -inX_crit_alarm Critical output voltage critical high alarm. - - X is 3 for ZL2004, ZL9101M, and ZL9117M, 2 otherwise. - -curr1_label "iout1" -curr1_input Measured output current. -curr1_lcrit Critical minimum output current. -curr1_crit Critical maximum output current. -curr1_lcrit_alarm Output current critical low alarm. -curr1_crit_alarm Output current critical high alarm. - -temp[12]_input Measured temperature. -temp[12]_min Minimum temperature. -temp[12]_max Maximum temperature. -temp[12]_lcrit Critical low temperature. -temp[12]_crit Critical high temperature. -temp[12]_min_alarm Chip temperature low alarm. -temp[12]_max_alarm Chip temperature high alarm. -temp[12]_lcrit_alarm Chip temperature critical low alarm. -temp[12]_crit_alarm Chip temperature critical high alarm. -======================= ======================================================== diff --git a/Documentation/hwmon/zl6100.rst b/Documentation/hwmon/zl6100.rst new file mode 100644 index 000000000000..41513bb7fe51 --- /dev/null +++ b/Documentation/hwmon/zl6100.rst @@ -0,0 +1,213 @@ +Kernel driver zl6100 +==================== + +Supported chips: + + * Intersil / Zilker Labs ZL2004 + + Prefix: 'zl2004' + + Addresses scanned: - + + Datasheet: http://www.intersil.com/data/fn/fn6847.pdf + + * Intersil / Zilker Labs ZL2005 + + Prefix: 'zl2005' + + Addresses scanned: - + + Datasheet: http://www.intersil.com/data/fn/fn6848.pdf + + * Intersil / Zilker Labs ZL2006 + + Prefix: 'zl2006' + + Addresses scanned: - + + Datasheet: http://www.intersil.com/data/fn/fn6850.pdf + + * Intersil / Zilker Labs ZL2008 + + Prefix: 'zl2008' + + Addresses scanned: - + + Datasheet: http://www.intersil.com/data/fn/fn6859.pdf + + * Intersil / Zilker Labs ZL2105 + + Prefix: 'zl2105' + + Addresses scanned: - + + Datasheet: http://www.intersil.com/data/fn/fn6851.pdf + + * Intersil / Zilker Labs ZL2106 + + Prefix: 'zl2106' + + Addresses scanned: - + + Datasheet: http://www.intersil.com/data/fn/fn6852.pdf + + * Intersil / Zilker Labs ZL6100 + + Prefix: 'zl6100' + + Addresses scanned: - + + Datasheet: http://www.intersil.com/data/fn/fn6876.pdf + + * Intersil / Zilker Labs ZL6105 + + Prefix: 'zl6105' + + Addresses scanned: - + + Datasheet: http://www.intersil.com/data/fn/fn6906.pdf + + * Intersil / Zilker Labs ZL9101M + + Prefix: 'zl9101' + + Addresses scanned: - + + Datasheet: http://www.intersil.com/data/fn/fn7669.pdf + + * Intersil / Zilker Labs ZL9117M + + Prefix: 'zl9117' + + Addresses scanned: - + + Datasheet: http://www.intersil.com/data/fn/fn7914.pdf + + * Ericsson BMR450, BMR451 + + Prefix: 'bmr450', 'bmr451' + + Addresses scanned: - + + Datasheet: + +http://archive.ericsson.net/service/internet/picov/get?DocNo=28701-EN/LZT146401 + + * Ericsson BMR462, BMR463, BMR464 + + Prefixes: 'bmr462', 'bmr463', 'bmr464' + + Addresses scanned: - + + Datasheet: + + http://archive.ericsson.net/service/internet/picov/get?DocNo=28701-EN/LZT146256 + +Author: Guenter Roeck + + +Description +----------- + +This driver supports hardware monitoring for Intersil / Zilker Labs ZL6100 and +compatible digital DC-DC controllers. + +The driver is a client driver to the core PMBus driver. Please see +Documentation/hwmon/pmbus.rst and Documentation.hwmon/pmbus-core for details +on PMBus client drivers. + + +Usage Notes +----------- + +This driver does not auto-detect devices. You will have to instantiate the +devices explicitly. Please see Documentation/i2c/instantiating-devices for +details. + +.. warning:: + + Do not access chip registers using the i2cdump command, and do not use + any of the i2ctools commands on a command register used to save and restore + configuration data (0x11, 0x12, 0x15, 0x16, and 0xf4). The chips supported by + this driver interpret any access to those command registers (including read + commands) as request to execute the command in question. Unless write accesses + to those registers are protected, this may result in power loss, board resets, + and/or Flash corruption. Worst case, your board may turn into a brick. + + +Platform data support +--------------------- + +The driver supports standard PMBus driver platform data. + + +Module parameters +----------------- + +delay +----- + +Intersil/Zilker Labs DC-DC controllers require a minimum interval between I2C +bus accesses. According to Intersil, the minimum interval is 2 ms, though 1 ms +appears to be sufficient and has not caused any problems in testing. The problem +is known to affect all currently supported chips. For manual override, the +driver provides a writeable module parameter, 'delay', which can be used to set +the interval to a value between 0 and 65,535 microseconds. + + +Sysfs entries +------------- + +The following attributes are supported. Limits are read-write; all other +attributes are read-only. + +======================= ======================================================== +in1_label "vin" +in1_input Measured input voltage. +in1_min Minimum input voltage. +in1_max Maximum input voltage. +in1_lcrit Critical minimum input voltage. +in1_crit Critical maximum input voltage. +in1_min_alarm Input voltage low alarm. +in1_max_alarm Input voltage high alarm. +in1_lcrit_alarm Input voltage critical low alarm. +in1_crit_alarm Input voltage critical high alarm. + +in2_label "vmon" +in2_input Measured voltage on VMON (ZL2004) or VDRV (ZL9101M, + ZL9117M) pin. Reported voltage is 16x the voltage on the + pin (adjusted internally by the chip). +in2_lcrit Critical minimum VMON/VDRV Voltage. +in2_crit Critical maximum VMON/VDRV voltage. +in2_lcrit_alarm VMON/VDRV voltage critical low alarm. +in2_crit_alarm VMON/VDRV voltage critical high alarm. + + vmon attributes are supported on ZL2004, ZL9101M, + and ZL9117M only. + +inX_label "vout1" +inX_input Measured output voltage. +inX_lcrit Critical minimum output Voltage. +inX_crit Critical maximum output voltage. +inX_lcrit_alarm Critical output voltage critical low alarm. +inX_crit_alarm Critical output voltage critical high alarm. + + X is 3 for ZL2004, ZL9101M, and ZL9117M, 2 otherwise. + +curr1_label "iout1" +curr1_input Measured output current. +curr1_lcrit Critical minimum output current. +curr1_crit Critical maximum output current. +curr1_lcrit_alarm Output current critical low alarm. +curr1_crit_alarm Output current critical high alarm. + +temp[12]_input Measured temperature. +temp[12]_min Minimum temperature. +temp[12]_max Maximum temperature. +temp[12]_lcrit Critical low temperature. +temp[12]_crit Critical high temperature. +temp[12]_min_alarm Chip temperature low alarm. +temp[12]_max_alarm Chip temperature high alarm. +temp[12]_lcrit_alarm Chip temperature critical low alarm. +temp[12]_crit_alarm Chip temperature critical high alarm. +======================= ======================================================== diff --git a/Documentation/index.rst b/Documentation/index.rst index 80a421cb935e..3a710dc24fc8 100644 --- a/Documentation/index.rst +++ b/Documentation/index.rst @@ -83,6 +83,7 @@ needed). media/index networking/index input/index + hwmon/index gpu/index security/index sound/index diff --git a/Documentation/thermal/sysfs-api.txt b/Documentation/thermal/sysfs-api.txt index 911399730c1c..c3fa500df92c 100644 --- a/Documentation/thermal/sysfs-api.txt +++ b/Documentation/thermal/sysfs-api.txt @@ -316,7 +316,7 @@ ACPI thermal zones. |---temp[1-*]_input: The current temperature of thermal zone [1-*] |---temp[1-*]_critical: The critical trip point of thermal zone [1-*] -Please read Documentation/hwmon/sysfs-interface for additional information. +Please read Documentation/hwmon/sysfs-interface.rst for additional information. *************************** * Thermal zone attributes * diff --git a/MAINTAINERS b/MAINTAINERS index cfd9884256af..317cc9933826 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -468,7 +468,7 @@ ADM1025 HARDWARE MONITOR DRIVER M: Jean Delvare L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/adm1025 +F: Documentation/hwmon/adm1025.rst F: drivers/hwmon/adm1025.c ADM1029 HARDWARE MONITOR DRIVER @@ -520,7 +520,7 @@ ADS1015 HARDWARE MONITOR DRIVER M: Dirk Eibach L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/ads1015 +F: Documentation/hwmon/ads1015.rst F: drivers/hwmon/ads1015.c F: include/linux/platform_data/ads1015.h @@ -533,7 +533,7 @@ ADT7475 HARDWARE MONITOR DRIVER M: Jean Delvare L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/adt7475 +F: Documentation/hwmon/adt7475.rst F: drivers/hwmon/adt7475.c ADVANSYS SCSI DRIVER @@ -764,7 +764,7 @@ AMD FAM15H PROCESSOR POWER MONITORING DRIVER M: Huang Rui L: linux-hwmon@vger.kernel.org S: Supported -F: Documentation/hwmon/fam15h_power +F: Documentation/hwmon/fam15h_power.rst F: drivers/hwmon/fam15h_power.c AMD FCH GPIO DRIVER @@ -2513,7 +2513,7 @@ ASC7621 HARDWARE MONITOR DRIVER M: George Joseph L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/asc7621 +F: Documentation/hwmon/asc7621.rst F: drivers/hwmon/asc7621.c ASPEED VIDEO ENGINE DRIVER @@ -4047,7 +4047,7 @@ CORETEMP HARDWARE MONITORING DRIVER M: Fenghua Yu L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/coretemp +F: Documentation/hwmon/coretemp.rst F: drivers/hwmon/coretemp.c COSA/SRP SYNC SERIAL DRIVER @@ -4602,7 +4602,7 @@ DIALOG SEMICONDUCTOR DRIVERS M: Support Opensource W: http://www.dialog-semiconductor.com/products S: Supported -F: Documentation/hwmon/da90?? +F: Documentation/hwmon/da90??.rst F: Documentation/devicetree/bindings/mfd/da90*.txt F: Documentation/devicetree/bindings/input/da90??-onkey.txt F: Documentation/devicetree/bindings/thermal/da90??-thermal.txt @@ -4753,7 +4753,7 @@ DME1737 HARDWARE MONITOR DRIVER M: Juerg Haefliger L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/dme1737 +F: Documentation/hwmon/dme1737.rst F: drivers/hwmon/dme1737.c DMI/SMBIOS SUPPORT @@ -5939,7 +5939,7 @@ F71805F HARDWARE MONITORING DRIVER M: Jean Delvare L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/f71805f +F: Documentation/hwmon/f71805f.rst F: drivers/hwmon/f71805f.c FADDR2LINE @@ -7621,7 +7621,7 @@ INA209 HARDWARE MONITOR DRIVER M: Guenter Roeck L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/ina209 +F: Documentation/hwmon/ina209.rst F: Documentation/devicetree/bindings/hwmon/ina2xx.txt F: drivers/hwmon/ina209.c @@ -7629,7 +7629,7 @@ INA2XX HARDWARE MONITOR DRIVER M: Guenter Roeck L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/ina2xx +F: Documentation/hwmon/ina2xx.rst F: drivers/hwmon/ina2xx.c F: include/linux/platform_data/ina2xx.h @@ -8257,7 +8257,7 @@ IT87 HARDWARE MONITORING DRIVER M: Jean Delvare L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/it87 +F: Documentation/hwmon/it87.rst F: drivers/hwmon/it87.c IT913X MEDIA DRIVER @@ -8301,7 +8301,7 @@ M: Guenter Roeck L: linux-hwmon@vger.kernel.org S: Maintained F: drivers/hwmon/jc42.c -F: Documentation/hwmon/jc42 +F: Documentation/hwmon/jc42.rst JFS FILESYSTEM M: Dave Kleikamp @@ -8349,14 +8349,14 @@ K10TEMP HARDWARE MONITORING DRIVER M: Clemens Ladisch L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/k10temp +F: Documentation/hwmon/k10temp.rst F: drivers/hwmon/k10temp.c K8TEMP HARDWARE MONITORING DRIVER M: Rudolf Marek L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/k8temp +F: Documentation/hwmon/k8temp.rst F: drivers/hwmon/k8temp.c KASAN @@ -9047,21 +9047,21 @@ LM78 HARDWARE MONITOR DRIVER M: Jean Delvare L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/lm78 +F: Documentation/hwmon/lm78.rst F: drivers/hwmon/lm78.c LM83 HARDWARE MONITOR DRIVER M: Jean Delvare L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/lm83 +F: Documentation/hwmon/lm83.rst F: drivers/hwmon/lm83.c LM90 HARDWARE MONITOR DRIVER M: Jean Delvare L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/lm90 +F: Documentation/hwmon/lm90.rst F: Documentation/devicetree/bindings/hwmon/lm90.txt F: drivers/hwmon/lm90.c F: include/dt-bindings/thermal/lm90.h @@ -9070,7 +9070,7 @@ LM95234 HARDWARE MONITOR DRIVER M: Guenter Roeck L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/lm95234 +F: Documentation/hwmon/lm95234.rst F: drivers/hwmon/lm95234.c LME2510 MEDIA DRIVER @@ -9144,7 +9144,7 @@ LTC4261 HARDWARE MONITOR DRIVER M: Guenter Roeck L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/ltc4261 +F: Documentation/hwmon/ltc4261.rst F: drivers/hwmon/ltc4261.c LTC4306 I2C MULTIPLEXER DRIVER @@ -9375,7 +9375,7 @@ MAX16065 HARDWARE MONITOR DRIVER M: Guenter Roeck L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/max16065 +F: Documentation/hwmon/max16065.rst F: drivers/hwmon/max16065.c MAX2175 SDR TUNER DRIVER @@ -9391,14 +9391,14 @@ F: include/uapi/linux/max2175.h MAX6650 HARDWARE MONITOR AND FAN CONTROLLER DRIVER L: linux-hwmon@vger.kernel.org S: Orphan -F: Documentation/hwmon/max6650 +F: Documentation/hwmon/max6650.rst F: drivers/hwmon/max6650.c MAX6697 HARDWARE MONITOR DRIVER M: Guenter Roeck L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/max6697 +F: Documentation/hwmon/max6697.rst F: Documentation/devicetree/bindings/hwmon/max6697.txt F: drivers/hwmon/max6697.c F: include/linux/platform_data/max6697.h @@ -10044,7 +10044,7 @@ F: drivers/mfd/menf21bmc.c F: drivers/watchdog/menf21bmc_wdt.c F: drivers/leds/leds-menf21bmc.c F: drivers/hwmon/menf21bmc_hwmon.c -F: Documentation/hwmon/menf21bmc +F: Documentation/hwmon/menf21bmc.rst MEN Z069 WATCHDOG DRIVER M: Johannes Thumshirn @@ -10672,7 +10672,7 @@ NCT6775 HARDWARE MONITOR DRIVER M: Guenter Roeck L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/nct6775 +F: Documentation/hwmon/nct6775.rst F: drivers/hwmon/nct6775.c NET_FAILOVER MODULE @@ -11766,7 +11766,7 @@ PC87360 HARDWARE MONITORING DRIVER M: Jim Cromie L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/pc87360 +F: Documentation/hwmon/pc87360.rst F: drivers/hwmon/pc87360.c PC8736x GPIO DRIVER @@ -11778,7 +11778,7 @@ PC87427 HARDWARE MONITORING DRIVER M: Jean Delvare L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/pc87427 +F: Documentation/hwmon/pc87427.rst F: drivers/hwmon/pc87427.c PCA9532 LED DRIVER @@ -12346,23 +12346,23 @@ S: Maintained F: Documentation/devicetree/bindings/hwmon/ibm,cffps1.txt F: Documentation/devicetree/bindings/hwmon/max31785.txt F: Documentation/devicetree/bindings/hwmon/ltc2978.txt -F: Documentation/hwmon/adm1275 -F: Documentation/hwmon/ibm-cffps -F: Documentation/hwmon/ir35221 -F: Documentation/hwmon/lm25066 -F: Documentation/hwmon/ltc2978 -F: Documentation/hwmon/ltc3815 -F: Documentation/hwmon/max16064 -F: Documentation/hwmon/max20751 -F: Documentation/hwmon/max31785 -F: Documentation/hwmon/max34440 -F: Documentation/hwmon/max8688 -F: Documentation/hwmon/pmbus -F: Documentation/hwmon/pmbus-core -F: Documentation/hwmon/tps40422 -F: Documentation/hwmon/ucd9000 -F: Documentation/hwmon/ucd9200 -F: Documentation/hwmon/zl6100 +F: Documentation/hwmon/adm1275.rst +F: Documentation/hwmon/ibm-cffps.rst +F: Documentation/hwmon/ir35221.rst +F: Documentation/hwmon/lm25066.rst +F: Documentation/hwmon/ltc2978.rst +F: Documentation/hwmon/ltc3815.rst +F: Documentation/hwmon/max16064.rst +F: Documentation/hwmon/max20751.rst +F: Documentation/hwmon/max31785.rst +F: Documentation/hwmon/max34440.rst +F: Documentation/hwmon/max8688.rst +F: Documentation/hwmon/pmbus.rst +F: Documentation/hwmon/pmbus-core.rst +F: Documentation/hwmon/tps40422.rst +F: Documentation/hwmon/ucd9000.rst +F: Documentation/hwmon/ucd9200.rst +F: Documentation/hwmon/zl6100.rst F: drivers/hwmon/pmbus/ F: include/linux/pmbus.h @@ -12626,7 +12626,7 @@ M: Bartlomiej Zolnierkiewicz L: linux-hwmon@vger.kernel.org S: Supported F: Documentation/devicetree/bindings/hwmon/pwm-fan.txt -F: Documentation/hwmon/pwm-fan +F: Documentation/hwmon/pwm-fan.rst F: drivers/hwmon/pwm-fan.c PWM IR Transmitter @@ -14291,21 +14291,21 @@ SMM665 HARDWARE MONITOR DRIVER M: Guenter Roeck L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/smm665 +F: Documentation/hwmon/smm665.rst F: drivers/hwmon/smm665.c SMSC EMC2103 HARDWARE MONITOR DRIVER M: Steve Glendinning L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/emc2103 +F: Documentation/hwmon/emc2103.rst F: drivers/hwmon/emc2103.c SMSC SCH5627 HARDWARE MONITOR DRIVER M: Hans de Goede L: linux-hwmon@vger.kernel.org S: Supported -F: Documentation/hwmon/sch5627 +F: Documentation/hwmon/sch5627.rst F: drivers/hwmon/sch5627.c SMSC UFX6000 and UFX7000 USB to VGA DRIVER @@ -14318,7 +14318,7 @@ SMSC47B397 HARDWARE MONITOR DRIVER M: Jean Delvare L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/smsc47b397 +F: Documentation/hwmon/smsc47b397.rst F: drivers/hwmon/smsc47b397.c SMSC911x ETHERNET DRIVER @@ -15664,7 +15664,7 @@ TMP401 HARDWARE MONITOR DRIVER M: Guenter Roeck L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/tmp401 +F: Documentation/hwmon/tmp401.rst F: drivers/hwmon/tmp401.c TMPFS (SHMEM FILESYSTEM) @@ -16689,7 +16689,7 @@ VT1211 HARDWARE MONITOR DRIVER M: Juerg Haefliger L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/vt1211 +F: Documentation/hwmon/vt1211.rst F: drivers/hwmon/vt1211.c VT8231 HARDWARE MONITOR DRIVER @@ -16717,14 +16717,14 @@ W83791D HARDWARE MONITORING DRIVER M: Marc Hulsman L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/w83791d +F: Documentation/hwmon/w83791d.rst F: drivers/hwmon/w83791d.c W83793 HARDWARE MONITORING DRIVER M: Rudolf Marek L: linux-hwmon@vger.kernel.org S: Maintained -F: Documentation/hwmon/w83793 +F: Documentation/hwmon/w83793.rst F: drivers/hwmon/w83793.c W83795 HARDWARE MONITORING DRIVER @@ -16833,7 +16833,7 @@ L: patches@opensource.cirrus.com T: git https://github.com/CirrusLogic/linux-drivers.git W: https://github.com/CirrusLogic/linux-drivers/wiki S: Supported -F: Documentation/hwmon/wm83?? +F: Documentation/hwmon/wm83??.rst F: Documentation/devicetree/bindings/extcon/extcon-arizona.txt F: Documentation/devicetree/bindings/regulator/arizona-regulator.txt F: Documentation/devicetree/bindings/mfd/arizona.txt diff --git a/drivers/hwmon/Kconfig b/drivers/hwmon/Kconfig index dedd5febd3aa..470ba66b18b0 100644 --- a/drivers/hwmon/Kconfig +++ b/drivers/hwmon/Kconfig @@ -17,7 +17,7 @@ menuconfig HWMON To find out which specific driver(s) you need, use the sensors-detect script from the lm_sensors package. Read - for details. + for details. This support can also be built as a module. If so, the module will be called hwmon. @@ -59,7 +59,7 @@ config SENSORS_ABITUGURU chip can be found on Abit uGuru featuring motherboards (most modern Abit motherboards from before end 2005). For more info and a list of which motherboards have which revision see - Documentation/hwmon/abituguru + Documentation/hwmon/abituguru.rst This driver can also be built as a module. If so, the module will be called abituguru. @@ -73,7 +73,7 @@ config SENSORS_ABITUGURU3 and their settings is supported. The third revision of the Abit uGuru chip can be found on recent Abit motherboards (since end 2005). For more info and a list of which motherboards have which - revision see Documentation/hwmon/abituguru3 + revision see Documentation/hwmon/abituguru3.rst This driver can also be built as a module. If so, the module will be called abituguru3. @@ -643,7 +643,7 @@ config SENSORS_CORETEMP help If you say yes here you get support for the temperature sensor inside your CPU. Most of the family 6 CPUs - are supported. Check Documentation/hwmon/coretemp for details. + are supported. Check Documentation/hwmon/coretemp.rst for details. config SENSORS_IT87 tristate "ITE IT87xx and compatibles" diff --git a/drivers/hwmon/ads7828.c b/drivers/hwmon/ads7828.c index e6be617e3fb2..03d6e782777a 100644 --- a/drivers/hwmon/ads7828.c +++ b/drivers/hwmon/ads7828.c @@ -8,7 +8,7 @@ * * ADS7830 support, by Guillaume Roguez * - * For further information, see the Documentation/hwmon/ads7828 file. + * For further information, see the Documentation/hwmon/ads7828.rst file. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by diff --git a/drivers/hwmon/max197.c b/drivers/hwmon/max197.c index 3d9e210beedf..dd6a35219a18 100644 --- a/drivers/hwmon/max197.c +++ b/drivers/hwmon/max197.c @@ -8,7 +8,7 @@ * it under the terms of the GNU General Public License version 2 as * published by the Free Software Foundation. * - * For further information, see the Documentation/hwmon/max197 file. + * For further information, see the Documentation/hwmon/max197.rst file. */ #include diff --git a/drivers/hwmon/sht15.c b/drivers/hwmon/sht15.c index 39b41e35c2bf..7f4a63959730 100644 --- a/drivers/hwmon/sht15.c +++ b/drivers/hwmon/sht15.c @@ -10,7 +10,7 @@ * * Copyright (c) 2007 Wouter Horre * - * For further information, see the Documentation/hwmon/sht15 file. + * For further information, see the Documentation/hwmon/sht15.rst file. */ #include diff --git a/include/linux/platform_data/ads7828.h b/include/linux/platform_data/ads7828.h index 3245f45f9d77..a3370a007702 100644 --- a/include/linux/platform_data/ads7828.h +++ b/include/linux/platform_data/ads7828.h @@ -4,7 +4,7 @@ * Copyright (c) 2012 Savoir-faire Linux Inc. * Vivien Didelot * - * For further information, see the Documentation/hwmon/ads7828 file. + * For further information, see the Documentation/hwmon/ads7828.rst file. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 as diff --git a/include/linux/platform_data/ds620.h b/include/linux/platform_data/ds620.h index 6ef58bb77e46..f0ce22a78bb8 100644 --- a/include/linux/platform_data/ds620.h +++ b/include/linux/platform_data/ds620.h @@ -14,7 +14,7 @@ struct ds620_platform_data { * 1 = PO_LOW * 2 = PO_HIGH * - * (see Documentation/hwmon/ds620) + * (see Documentation/hwmon/ds620.rst) */ int pomode; }; diff --git a/include/linux/platform_data/ina2xx.h b/include/linux/platform_data/ina2xx.h index 9f0aa1b48c78..dde59fd3590f 100644 --- a/include/linux/platform_data/ina2xx.h +++ b/include/linux/platform_data/ina2xx.h @@ -7,7 +7,7 @@ * it under the terms of the GNU General Public License version 2 as * published by the Free Software Foundation. * - * For further information, see the Documentation/hwmon/ina2xx file. + * For further information, see the Documentation/hwmon/ina2xx.rst file. */ /** diff --git a/include/linux/platform_data/max197.h b/include/linux/platform_data/max197.h index 8da8f94ee15c..2bbd0919bc89 100644 --- a/include/linux/platform_data/max197.h +++ b/include/linux/platform_data/max197.h @@ -8,7 +8,7 @@ * it under the terms of the GNU General Public License version 2 as * published by the Free Software Foundation. * - * For further information, see the Documentation/hwmon/max197 file. + * For further information, see the Documentation/hwmon/max197.rst file. */ #ifndef _PDATA_MAX197_H diff --git a/include/linux/platform_data/ntc_thermistor.h b/include/linux/platform_data/ntc_thermistor.h index ee03d429742b..5fa115d3ea4b 100644 --- a/include/linux/platform_data/ntc_thermistor.h +++ b/include/linux/platform_data/ntc_thermistor.h @@ -42,7 +42,7 @@ struct ntc_thermistor_platform_data { * read_uV() * * How to setup pullup_ohm, pulldown_ohm, and connect is - * described at Documentation/hwmon/ntc_thermistor + * described at Documentation/hwmon/ntc_thermistor.rst * * pullup/down_ohm: 0 for infinite / not-connected * -- cgit v1.2.3 From 98af8452945c55652de68536afdde3b520fec429 Mon Sep 17 00:00:00 2001 From: Josh Poimboeuf Date: Fri, 12 Apr 2019 15:39:28 -0500 Subject: cpu/speculation: Add 'mitigations=' cmdline option Keeping track of the number of mitigations for all the CPU speculation bugs has become overwhelming for many users. It's getting more and more complicated to decide which mitigations are needed for a given architecture. Complicating matters is the fact that each arch tends to have its own custom way to mitigate the same vulnerability. Most users fall into a few basic categories: a) they want all mitigations off; b) they want all reasonable mitigations on, with SMT enabled even if it's vulnerable; or c) they want all reasonable mitigations on, with SMT disabled if vulnerable. Define a set of curated, arch-independent options, each of which is an aggregation of existing options: - mitigations=off: Disable all mitigations. - mitigations=auto: [default] Enable all the default mitigations, but leave SMT enabled, even if it's vulnerable. - mitigations=auto,nosmt: Enable all the default mitigations, disabling SMT if needed by a mitigation. Currently, these options are placeholders which don't actually do anything. They will be fleshed out in upcoming patches. Signed-off-by: Josh Poimboeuf Signed-off-by: Thomas Gleixner Tested-by: Jiri Kosina (on x86) Reviewed-by: Jiri Kosina Cc: Borislav Petkov Cc: "H . Peter Anvin" Cc: Andy Lutomirski Cc: Peter Zijlstra Cc: Jiri Kosina Cc: Waiman Long Cc: Andrea Arcangeli Cc: Jon Masters Cc: Benjamin Herrenschmidt Cc: Paul Mackerras Cc: Michael Ellerman Cc: linuxppc-dev@lists.ozlabs.org Cc: Martin Schwidefsky Cc: Heiko Carstens Cc: linux-s390@vger.kernel.org Cc: Catalin Marinas Cc: Will Deacon Cc: linux-arm-kernel@lists.infradead.org Cc: linux-arch@vger.kernel.org Cc: Greg Kroah-Hartman Cc: Tyler Hicks Cc: Linus Torvalds Cc: Randy Dunlap Cc: Steven Price Cc: Phil Auld Link: https://lkml.kernel.org/r/b07a8ef9b7c5055c3a4637c87d07c296d5016fe0.1555085500.git.jpoimboe@redhat.com --- Documentation/admin-guide/kernel-parameters.txt | 24 ++++++++++++++++++++++++ include/linux/cpu.h | 24 ++++++++++++++++++++++++ kernel/cpu.c | 15 +++++++++++++++ 3 files changed, 63 insertions(+) (limited to 'Documentation') diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt index 858b6c0b9a15..720ffa9c4e04 100644 --- a/Documentation/admin-guide/kernel-parameters.txt +++ b/Documentation/admin-guide/kernel-parameters.txt @@ -2513,6 +2513,30 @@ in the "bleeding edge" mini2440 support kernel at http://repo.or.cz/w/linux-2.6/mini2440.git + mitigations= + Control optional mitigations for CPU vulnerabilities. + This is a set of curated, arch-independent options, each + of which is an aggregation of existing arch-specific + options. + + off + Disable all optional CPU mitigations. This + improves system performance, but it may also + expose users to several CPU vulnerabilities. + + auto (default) + Mitigate all CPU vulnerabilities, but leave SMT + enabled, even if it's vulnerable. This is for + users who don't want to be surprised by SMT + getting disabled across kernel upgrades, or who + have other ways of avoiding SMT-based attacks. + This is the default behavior. + + auto,nosmt + Mitigate all CPU vulnerabilities, disabling SMT + if needed. This is for users who always want to + be fully mitigated, even if it means losing SMT. + mminit_loglevel= [KNL] When CONFIG_DEBUG_MEMORY_INIT is set, this parameter allows control of the logging verbosity for diff --git a/include/linux/cpu.h b/include/linux/cpu.h index 5041357d0297..2d9c6f4b78f5 100644 --- a/include/linux/cpu.h +++ b/include/linux/cpu.h @@ -187,4 +187,28 @@ static inline void cpu_smt_disable(bool force) { } static inline void cpu_smt_check_topology(void) { } #endif +/* + * These are used for a global "mitigations=" cmdline option for toggling + * optional CPU mitigations. + */ +enum cpu_mitigations { + CPU_MITIGATIONS_OFF, + CPU_MITIGATIONS_AUTO, + CPU_MITIGATIONS_AUTO_NOSMT, +}; + +extern enum cpu_mitigations cpu_mitigations; + +/* mitigations=off */ +static inline bool cpu_mitigations_off(void) +{ + return cpu_mitigations == CPU_MITIGATIONS_OFF; +} + +/* mitigations=auto,nosmt */ +static inline bool cpu_mitigations_auto_nosmt(void) +{ + return cpu_mitigations == CPU_MITIGATIONS_AUTO_NOSMT; +} + #endif /* _LINUX_CPU_H_ */ diff --git a/kernel/cpu.c b/kernel/cpu.c index d1c6d152da89..e70a90634b41 100644 --- a/kernel/cpu.c +++ b/kernel/cpu.c @@ -2279,3 +2279,18 @@ void __init boot_cpu_hotplug_init(void) #endif this_cpu_write(cpuhp_state.state, CPUHP_ONLINE); } + +enum cpu_mitigations cpu_mitigations __ro_after_init = CPU_MITIGATIONS_AUTO; + +static int __init mitigations_parse_cmdline(char *arg) +{ + if (!strcmp(arg, "off")) + cpu_mitigations = CPU_MITIGATIONS_OFF; + else if (!strcmp(arg, "auto")) + cpu_mitigations = CPU_MITIGATIONS_AUTO; + else if (!strcmp(arg, "auto,nosmt")) + cpu_mitigations = CPU_MITIGATIONS_AUTO_NOSMT; + + return 0; +} +early_param("mitigations", mitigations_parse_cmdline); -- cgit v1.2.3 From d68be4c4d31295ff6ae34a8ddfaa4c1a8ff42812 Mon Sep 17 00:00:00 2001 From: Josh Poimboeuf Date: Fri, 12 Apr 2019 15:39:29 -0500 Subject: x86/speculation: Support 'mitigations=' cmdline option Configure x86 runtime CPU speculation bug mitigations in accordance with the 'mitigations=' cmdline option. This affects Meltdown, Spectre v2, Speculative Store Bypass, and L1TF. The default behavior is unchanged. Signed-off-by: Josh Poimboeuf Signed-off-by: Thomas Gleixner Tested-by: Jiri Kosina (on x86) Reviewed-by: Jiri Kosina Cc: Borislav Petkov Cc: "H . Peter Anvin" Cc: Andy Lutomirski Cc: Peter Zijlstra Cc: Jiri Kosina Cc: Waiman Long Cc: Andrea Arcangeli Cc: Jon Masters Cc: Benjamin Herrenschmidt Cc: Paul Mackerras Cc: Michael Ellerman Cc: linuxppc-dev@lists.ozlabs.org Cc: Martin Schwidefsky Cc: Heiko Carstens Cc: linux-s390@vger.kernel.org Cc: Catalin Marinas Cc: Will Deacon Cc: linux-arm-kernel@lists.infradead.org Cc: linux-arch@vger.kernel.org Cc: Greg Kroah-Hartman Cc: Tyler Hicks Cc: Linus Torvalds Cc: Randy Dunlap Cc: Steven Price Cc: Phil Auld Link: https://lkml.kernel.org/r/6616d0ae169308516cfdf5216bedd169f8a8291b.1555085500.git.jpoimboe@redhat.com --- Documentation/admin-guide/kernel-parameters.txt | 16 +++++++++++----- arch/x86/kernel/cpu/bugs.c | 11 +++++++++-- arch/x86/mm/pti.c | 4 +++- 3 files changed, 23 insertions(+), 8 deletions(-) (limited to 'Documentation') diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt index 720ffa9c4e04..779ddeb2929c 100644 --- a/Documentation/admin-guide/kernel-parameters.txt +++ b/Documentation/admin-guide/kernel-parameters.txt @@ -2514,15 +2514,20 @@ http://repo.or.cz/w/linux-2.6/mini2440.git mitigations= - Control optional mitigations for CPU vulnerabilities. - This is a set of curated, arch-independent options, each - of which is an aggregation of existing arch-specific - options. + [X86] Control optional mitigations for CPU + vulnerabilities. This is a set of curated, + arch-independent options, each of which is an + aggregation of existing arch-specific options. off Disable all optional CPU mitigations. This improves system performance, but it may also expose users to several CPU vulnerabilities. + Equivalent to: nopti [X86] + nospectre_v2 [X86] + spectre_v2_user=off [X86] + spec_store_bypass_disable=off [X86] + l1tf=off [X86] auto (default) Mitigate all CPU vulnerabilities, but leave SMT @@ -2530,12 +2535,13 @@ users who don't want to be surprised by SMT getting disabled across kernel upgrades, or who have other ways of avoiding SMT-based attacks. - This is the default behavior. + Equivalent to: (default behavior) auto,nosmt Mitigate all CPU vulnerabilities, disabling SMT if needed. This is for users who always want to be fully mitigated, even if it means losing SMT. + Equivalent to: l1tf=flush,nosmt [X86] mminit_loglevel= [KNL] When CONFIG_DEBUG_MEMORY_INIT is set, this diff --git a/arch/x86/kernel/cpu/bugs.c b/arch/x86/kernel/cpu/bugs.c index 01874d54f4fd..435c078c2948 100644 --- a/arch/x86/kernel/cpu/bugs.c +++ b/arch/x86/kernel/cpu/bugs.c @@ -440,7 +440,8 @@ static enum spectre_v2_mitigation_cmd __init spectre_v2_parse_cmdline(void) char arg[20]; int ret, i; - if (cmdline_find_option_bool(boot_command_line, "nospectre_v2")) + if (cmdline_find_option_bool(boot_command_line, "nospectre_v2") || + cpu_mitigations_off()) return SPECTRE_V2_CMD_NONE; ret = cmdline_find_option(boot_command_line, "spectre_v2", arg, sizeof(arg)); @@ -672,7 +673,8 @@ static enum ssb_mitigation_cmd __init ssb_parse_cmdline(void) char arg[20]; int ret, i; - if (cmdline_find_option_bool(boot_command_line, "nospec_store_bypass_disable")) { + if (cmdline_find_option_bool(boot_command_line, "nospec_store_bypass_disable") || + cpu_mitigations_off()) { return SPEC_STORE_BYPASS_CMD_NONE; } else { ret = cmdline_find_option(boot_command_line, "spec_store_bypass_disable", @@ -996,6 +998,11 @@ static void __init l1tf_select_mitigation(void) if (!boot_cpu_has_bug(X86_BUG_L1TF)) return; + if (cpu_mitigations_off()) + l1tf_mitigation = L1TF_MITIGATION_OFF; + else if (cpu_mitigations_auto_nosmt()) + l1tf_mitigation = L1TF_MITIGATION_FLUSH_NOSMT; + override_cache_bits(&boot_cpu_data); switch (l1tf_mitigation) { diff --git a/arch/x86/mm/pti.c b/arch/x86/mm/pti.c index 4fee5c3003ed..5890f09bfc19 100644 --- a/arch/x86/mm/pti.c +++ b/arch/x86/mm/pti.c @@ -35,6 +35,7 @@ #include #include #include +#include #include #include @@ -115,7 +116,8 @@ void __init pti_check_boottime_disable(void) } } - if (cmdline_find_option_bool(boot_command_line, "nopti")) { + if (cmdline_find_option_bool(boot_command_line, "nopti") || + cpu_mitigations_off()) { pti_mode = PTI_FORCE_OFF; pti_print_if_insecure("disabled on command line."); return; -- cgit v1.2.3 From 782e69efb3dfed6e8360bc612e8c7827a901a8f9 Mon Sep 17 00:00:00 2001 From: Josh Poimboeuf Date: Fri, 12 Apr 2019 15:39:30 -0500 Subject: powerpc/speculation: Support 'mitigations=' cmdline option Configure powerpc CPU runtime speculation bug mitigations in accordance with the 'mitigations=' cmdline option. This affects Meltdown, Spectre v1, Spectre v2, and Speculative Store Bypass. The default behavior is unchanged. Signed-off-by: Josh Poimboeuf Signed-off-by: Thomas Gleixner Tested-by: Jiri Kosina (on x86) Reviewed-by: Jiri Kosina Cc: Borislav Petkov Cc: "H . Peter Anvin" Cc: Andy Lutomirski Cc: Peter Zijlstra Cc: Jiri Kosina Cc: Waiman Long Cc: Andrea Arcangeli Cc: Jon Masters Cc: Benjamin Herrenschmidt Cc: Paul Mackerras Cc: Michael Ellerman Cc: linuxppc-dev@lists.ozlabs.org Cc: Martin Schwidefsky Cc: Heiko Carstens Cc: linux-s390@vger.kernel.org Cc: Catalin Marinas Cc: Will Deacon Cc: linux-arm-kernel@lists.infradead.org Cc: linux-arch@vger.kernel.org Cc: Greg Kroah-Hartman Cc: Tyler Hicks Cc: Linus Torvalds Cc: Randy Dunlap Cc: Steven Price Cc: Phil Auld Link: https://lkml.kernel.org/r/245a606e1a42a558a310220312d9b6adb9159df6.1555085500.git.jpoimboe@redhat.com --- Documentation/admin-guide/kernel-parameters.txt | 9 +++++---- arch/powerpc/kernel/security.c | 6 +++--- arch/powerpc/kernel/setup_64.c | 2 +- 3 files changed, 9 insertions(+), 8 deletions(-) (limited to 'Documentation') diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt index 779ddeb2929c..ac7150a25a7a 100644 --- a/Documentation/admin-guide/kernel-parameters.txt +++ b/Documentation/admin-guide/kernel-parameters.txt @@ -2514,7 +2514,7 @@ http://repo.or.cz/w/linux-2.6/mini2440.git mitigations= - [X86] Control optional mitigations for CPU + [X86,PPC] Control optional mitigations for CPU vulnerabilities. This is a set of curated, arch-independent options, each of which is an aggregation of existing arch-specific options. @@ -2523,10 +2523,11 @@ Disable all optional CPU mitigations. This improves system performance, but it may also expose users to several CPU vulnerabilities. - Equivalent to: nopti [X86] - nospectre_v2 [X86] + Equivalent to: nopti [X86,PPC] + nospectre_v1 [PPC] + nospectre_v2 [X86,PPC] spectre_v2_user=off [X86] - spec_store_bypass_disable=off [X86] + spec_store_bypass_disable=off [X86,PPC] l1tf=off [X86] auto (default) diff --git a/arch/powerpc/kernel/security.c b/arch/powerpc/kernel/security.c index 9b8631533e02..cdf3e73000e9 100644 --- a/arch/powerpc/kernel/security.c +++ b/arch/powerpc/kernel/security.c @@ -57,7 +57,7 @@ void setup_barrier_nospec(void) enable = security_ftr_enabled(SEC_FTR_FAVOUR_SECURITY) && security_ftr_enabled(SEC_FTR_BNDS_CHK_SPEC_BAR); - if (!no_nospec) + if (!no_nospec && !cpu_mitigations_off()) enable_barrier_nospec(enable); } @@ -116,7 +116,7 @@ static int __init handle_nospectre_v2(char *p) early_param("nospectre_v2", handle_nospectre_v2); void setup_spectre_v2(void) { - if (no_spectrev2) + if (no_spectrev2 || cpu_mitigations_off()) do_btb_flush_fixups(); else btb_flush_enabled = true; @@ -307,7 +307,7 @@ void setup_stf_barrier(void) stf_enabled_flush_types = type; - if (!no_stf_barrier) + if (!no_stf_barrier && !cpu_mitigations_off()) stf_barrier_enable(enable); } diff --git a/arch/powerpc/kernel/setup_64.c b/arch/powerpc/kernel/setup_64.c index 236c1151a3a7..c7ec27ba8926 100644 --- a/arch/powerpc/kernel/setup_64.c +++ b/arch/powerpc/kernel/setup_64.c @@ -958,7 +958,7 @@ void setup_rfi_flush(enum l1d_flush_type types, bool enable) enabled_flush_types = types; - if (!no_rfi_flush) + if (!no_rfi_flush && !cpu_mitigations_off()) rfi_flush_enable(enable); } -- cgit v1.2.3 From 0336e04a6520bdaefdb0769d2a70084fa52e81ed Mon Sep 17 00:00:00 2001 From: Josh Poimboeuf Date: Fri, 12 Apr 2019 15:39:31 -0500 Subject: s390/speculation: Support 'mitigations=' cmdline option Configure s390 runtime CPU speculation bug mitigations in accordance with the 'mitigations=' cmdline option. This affects Spectre v1 and Spectre v2. The default behavior is unchanged. Signed-off-by: Josh Poimboeuf Signed-off-by: Thomas Gleixner Tested-by: Jiri Kosina (on x86) Reviewed-by: Jiri Kosina Cc: Borislav Petkov Cc: "H . Peter Anvin" Cc: Andy Lutomirski Cc: Peter Zijlstra Cc: Jiri Kosina Cc: Waiman Long Cc: Andrea Arcangeli Cc: Jon Masters Cc: Benjamin Herrenschmidt Cc: Paul Mackerras Cc: Michael Ellerman Cc: linuxppc-dev@lists.ozlabs.org Cc: Martin Schwidefsky Cc: Heiko Carstens Cc: linux-s390@vger.kernel.org Cc: Catalin Marinas Cc: Will Deacon Cc: linux-arm-kernel@lists.infradead.org Cc: linux-arch@vger.kernel.org Cc: Greg Kroah-Hartman Cc: Tyler Hicks Cc: Linus Torvalds Cc: Randy Dunlap Cc: Steven Price Cc: Phil Auld Link: https://lkml.kernel.org/r/e4a161805458a5ec88812aac0307ae3908a030fc.1555085500.git.jpoimboe@redhat.com --- Documentation/admin-guide/kernel-parameters.txt | 5 +++-- arch/s390/kernel/nospec-branch.c | 3 ++- 2 files changed, 5 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt index ac7150a25a7a..1ae93872b79f 100644 --- a/Documentation/admin-guide/kernel-parameters.txt +++ b/Documentation/admin-guide/kernel-parameters.txt @@ -2514,7 +2514,7 @@ http://repo.or.cz/w/linux-2.6/mini2440.git mitigations= - [X86,PPC] Control optional mitigations for CPU + [X86,PPC,S390] Control optional mitigations for CPU vulnerabilities. This is a set of curated, arch-independent options, each of which is an aggregation of existing arch-specific options. @@ -2525,7 +2525,8 @@ expose users to several CPU vulnerabilities. Equivalent to: nopti [X86,PPC] nospectre_v1 [PPC] - nospectre_v2 [X86,PPC] + nobp=0 [S390] + nospectre_v2 [X86,PPC,S390] spectre_v2_user=off [X86] spec_store_bypass_disable=off [X86,PPC] l1tf=off [X86] diff --git a/arch/s390/kernel/nospec-branch.c b/arch/s390/kernel/nospec-branch.c index bdddaae96559..649135cbedd5 100644 --- a/arch/s390/kernel/nospec-branch.c +++ b/arch/s390/kernel/nospec-branch.c @@ -1,6 +1,7 @@ // SPDX-License-Identifier: GPL-2.0 #include #include +#include #include static int __init nobp_setup_early(char *str) @@ -58,7 +59,7 @@ early_param("nospectre_v2", nospectre_v2_setup_early); void __init nospec_auto_detect(void) { - if (test_facility(156)) { + if (test_facility(156) || cpu_mitigations_off()) { /* * The machine supports etokens. * Disable expolines and disable nobp. -- cgit v1.2.3 From 19fad20d15a6494f47f85d869f00b11343ee5c78 Mon Sep 17 00:00:00 2001 From: ZhangXiaoxu Date: Tue, 16 Apr 2019 09:47:24 +0800 Subject: ipv4: set the tcp_min_rtt_wlen range from 0 to one day There is a UBSAN report as below: UBSAN: Undefined behaviour in net/ipv4/tcp_input.c:2877:56 signed integer overflow: 2147483647 * 1000 cannot be represented in type 'int' CPU: 3 PID: 0 Comm: swapper/3 Not tainted 5.1.0-rc4-00058-g582549e #1 Call Trace: dump_stack+0x8c/0xba ubsan_epilogue+0x11/0x60 handle_overflow+0x12d/0x170 ? ttwu_do_wakeup+0x21/0x320 __ubsan_handle_mul_overflow+0x12/0x20 tcp_ack_update_rtt+0x76c/0x780 tcp_clean_rtx_queue+0x499/0x14d0 tcp_ack+0x69e/0x1240 ? __wake_up_sync_key+0x2c/0x50 ? update_group_capacity+0x50/0x680 tcp_rcv_established+0x4e2/0xe10 tcp_v4_do_rcv+0x22b/0x420 tcp_v4_rcv+0xfe8/0x1190 ip_protocol_deliver_rcu+0x36/0x180 ip_local_deliver+0x15b/0x1a0 ip_rcv+0xac/0xd0 __netif_receive_skb_one_core+0x7f/0xb0 __netif_receive_skb+0x33/0xc0 netif_receive_skb_internal+0x84/0x1c0 napi_gro_receive+0x2a0/0x300 receive_buf+0x3d4/0x2350 ? detach_buf_split+0x159/0x390 virtnet_poll+0x198/0x840 ? reweight_entity+0x243/0x4b0 net_rx_action+0x25c/0x770 __do_softirq+0x19b/0x66d irq_exit+0x1eb/0x230 do_IRQ+0x7a/0x150 common_interrupt+0xf/0xf It can be reproduced by: echo 2147483647 > /proc/sys/net/ipv4/tcp_min_rtt_wlen Fixes: f672258391b42 ("tcp: track min RTT using windowed min-filter") Signed-off-by: ZhangXiaoxu Signed-off-by: David S. Miller --- Documentation/networking/ip-sysctl.txt | 1 + net/ipv4/sysctl_net_ipv4.c | 5 ++++- 2 files changed, 5 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/networking/ip-sysctl.txt b/Documentation/networking/ip-sysctl.txt index acdfb5d2bcaa..e2142fe40cda 100644 --- a/Documentation/networking/ip-sysctl.txt +++ b/Documentation/networking/ip-sysctl.txt @@ -422,6 +422,7 @@ tcp_min_rtt_wlen - INTEGER minimum RTT when it is moved to a longer path (e.g., due to traffic engineering). A longer window makes the filter more resistant to RTT inflations such as transient congestion. The unit is seconds. + Possible values: 0 - 86400 (1 day) Default: 300 tcp_moderate_rcvbuf - BOOLEAN diff --git a/net/ipv4/sysctl_net_ipv4.c b/net/ipv4/sysctl_net_ipv4.c index ba0fc4b18465..eeb4041fa5f9 100644 --- a/net/ipv4/sysctl_net_ipv4.c +++ b/net/ipv4/sysctl_net_ipv4.c @@ -49,6 +49,7 @@ static int ip_ping_group_range_min[] = { 0, 0 }; static int ip_ping_group_range_max[] = { GID_T_MAX, GID_T_MAX }; static int comp_sack_nr_max = 255; static u32 u32_max_div_HZ = UINT_MAX / HZ; +static int one_day_secs = 24 * 3600; /* obsolete */ static int sysctl_tcp_low_latency __read_mostly; @@ -1151,7 +1152,9 @@ static struct ctl_table ipv4_net_table[] = { .data = &init_net.ipv4.sysctl_tcp_min_rtt_wlen, .maxlen = sizeof(int), .mode = 0644, - .proc_handler = proc_dointvec + .proc_handler = proc_dointvec_minmax, + .extra1 = &zero, + .extra2 = &one_day_secs }, { .procname = "tcp_autocorking", -- cgit v1.2.3 From 2e8c9d7bfab23419923e7ef52e53dd8cb288d9c4 Mon Sep 17 00:00:00 2001 From: Chen-Yu Tsai Date: Tue, 16 Apr 2019 14:40:18 +0800 Subject: dt-bindings: power: supply: axp20x_usb_power: add axp813 compatible This adds the "x-powers,axp813-usb-power-supply" to the list of compatibles for AXP20X VBUS power supply driver. Reviewed-by: Rob Herring Signed-off-by: Chen-Yu Tsai Signed-off-by: Sebastian Reichel --- Documentation/devicetree/bindings/power/supply/axp20x_usb_power.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/power/supply/axp20x_usb_power.txt b/Documentation/devicetree/bindings/power/supply/axp20x_usb_power.txt index ba8d35f66cbe..b2d4968fde7d 100644 --- a/Documentation/devicetree/bindings/power/supply/axp20x_usb_power.txt +++ b/Documentation/devicetree/bindings/power/supply/axp20x_usb_power.txt @@ -4,6 +4,7 @@ Required Properties: -compatible: One of: "x-powers,axp202-usb-power-supply" "x-powers,axp221-usb-power-supply" "x-powers,axp223-usb-power-supply" + "x-powers,axp813-usb-power-supply" The AXP223 PMIC shares most of its behaviour with the AXP221 but has slight variations such as the former being able to set the VBUS power supply max -- cgit v1.2.3 From d8e8fd0ebf8b1b8d26a160c2363479a88c1f72c2 Mon Sep 17 00:00:00 2001 From: Masahiro Yamada Date: Tue, 2 Apr 2019 13:03:07 +0900 Subject: mtd: rawnand: denali: decouple controller and NAND chips Currently, this driver sticks to the legacy NAND model because it was upstreamed before commit 2d472aba15ff ("mtd: nand: document the NAND controller/NAND chip DT representation"). However, relying on the dummy_controller is already deprecated. Switch over to the new controller/chip representation. The struct denali_nand_info has been split into denali_controller and denali_chip, to contain the controller data, per-chip data, respectively. One problem is, this commit changes the DT binding. So, as always, the backward compatibility must be taken into consideration. In the new binding, the controller node expects #address-cells = <1>; #size-cells = <0>; ... since the child nodes represent NAND chips. In the old binding, the controller node may have subnodes, but they are MTD partitions. The denali_dt_is_legacy_binding() exploits it to distinguish old/new platforms. Going forward, the old binding is only allowed for existing DT files. I updated the binding document. Signed-off-by: Masahiro Yamada Acked-by: Rob Herring Signed-off-by: Miquel Raynal --- .../devicetree/bindings/mtd/denali-nand.txt | 40 +- drivers/mtd/nand/raw/denali.c | 430 ++++++++++++--------- drivers/mtd/nand/raw/denali.h | 114 +++++- drivers/mtd/nand/raw/denali_dt.c | 98 ++++- drivers/mtd/nand/raw/denali_pci.c | 30 +- 5 files changed, 482 insertions(+), 230 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mtd/denali-nand.txt b/Documentation/devicetree/bindings/mtd/denali-nand.txt index f33da8782741..b14b6751c2f3 100644 --- a/Documentation/devicetree/bindings/mtd/denali-nand.txt +++ b/Documentation/devicetree/bindings/mtd/denali-nand.txt @@ -7,34 +7,48 @@ Required properties: "socionext,uniphier-denali-nand-v5b" - for Socionext UniPhier (v5b) - reg : should contain registers location and length for data and reg. - reg-names: Should contain the reg names "nand_data" and "denali_reg" + - #address-cells: should be 1. The cell encodes the chip select connection. + - #size-cells : should be 0. - interrupts : The interrupt number. - clocks: should contain phandle of the controller core clock, the bus interface clock, and the ECC circuit clock. - clock-names: should contain "nand", "nand_x", "ecc" -Optional properties: - - nand-ecc-step-size: see nand.txt for details. If present, the value must be - 512 for "altr,socfpga-denali-nand" - 1024 for "socionext,uniphier-denali-nand-v5a" - 1024 for "socionext,uniphier-denali-nand-v5b" - - nand-ecc-strength: see nand.txt for details. Valid values are: - 8, 15 for "altr,socfpga-denali-nand" - 8, 16, 24 for "socionext,uniphier-denali-nand-v5a" - 8, 16 for "socionext,uniphier-denali-nand-v5b" - - nand-ecc-maximize: see nand.txt for details - -The device tree may optionally contain sub-nodes describing partitions of the +Sub-nodes: + Sub-nodes represent available NAND chips. + + Required properties: + - reg: should contain the bank ID of the controller to which each chip + select is connected. + + Optional properties: + - nand-ecc-step-size: see nand.txt for details. + If present, the value must be + 512 for "altr,socfpga-denali-nand" + 1024 for "socionext,uniphier-denali-nand-v5a" + 1024 for "socionext,uniphier-denali-nand-v5b" + - nand-ecc-strength: see nand.txt for details. Valid values are: + 8, 15 for "altr,socfpga-denali-nand" + 8, 16, 24 for "socionext,uniphier-denali-nand-v5a" + 8, 16 for "socionext,uniphier-denali-nand-v5b" + - nand-ecc-maximize: see nand.txt for details + +The chip nodes may optionally contain sub-nodes describing partitions of the address space. See partition.txt for more detail. Examples: nand: nand@ff900000 { #address-cells = <1>; - #size-cells = <1>; + #size-cells = <0>; compatible = "altr,socfpga-denali-nand"; reg = <0xff900000 0x20>, <0xffb80000 0x1000>; reg-names = "nand_data", "denali_reg"; clocks = <&nand_clk>, <&nand_x_clk>, <&nand_ecc_clk>; clock-names = "nand", "nand_x", "ecc"; interrupts = <0 144 4>; + + nand@0 { + reg = <0>; + } }; diff --git a/drivers/mtd/nand/raw/denali.c b/drivers/mtd/nand/raw/denali.c index da3fcbaec0e2..d8c10444e284 100644 --- a/drivers/mtd/nand/raw/denali.c +++ b/drivers/mtd/nand/raw/denali.c @@ -3,7 +3,7 @@ * NAND Flash Controller Device Driver * Copyright © 2009-2010, Intel Corporation and its suppliers. * - * Copyright (c) 2017 Socionext Inc. + * Copyright (c) 2017-2019 Socionext Inc. * Reworked by Masahiro Yamada */ @@ -42,14 +42,15 @@ #define DENALI_INVALID_BANK -1 #define DENALI_NR_BANKS 4 -static inline struct denali_nand_info *mtd_to_denali(struct mtd_info *mtd) +static struct denali_chip *to_denali_chip(struct nand_chip *chip) { - return container_of(mtd_to_nand(mtd), struct denali_nand_info, nand); + return container_of(chip, struct denali_chip, chip); } -static struct denali_nand_info *to_denali(struct nand_chip *chip) +static struct denali_controller *to_denali_controller(struct nand_chip *chip) { - return container_of(chip, struct denali_nand_info, nand); + return container_of(chip->controller, struct denali_controller, + controller); } /* @@ -57,12 +58,12 @@ static struct denali_nand_info *to_denali(struct nand_chip *chip) * type, bank, block, and page address). The slave data is the actual data to * be transferred. This mode requires 28 bits of address region allocated. */ -static u32 denali_direct_read(struct denali_nand_info *denali, u32 addr) +static u32 denali_direct_read(struct denali_controller *denali, u32 addr) { return ioread32(denali->host + addr); } -static void denali_direct_write(struct denali_nand_info *denali, u32 addr, +static void denali_direct_write(struct denali_controller *denali, u32 addr, u32 data) { iowrite32(data, denali->host + addr); @@ -74,35 +75,20 @@ static void denali_direct_write(struct denali_nand_info *denali, u32 addr, * control information and transferred data are latched by the registers in * the translation module. */ -static u32 denali_indexed_read(struct denali_nand_info *denali, u32 addr) +static u32 denali_indexed_read(struct denali_controller *denali, u32 addr) { iowrite32(addr, denali->host + DENALI_INDEXED_CTRL); return ioread32(denali->host + DENALI_INDEXED_DATA); } -static void denali_indexed_write(struct denali_nand_info *denali, u32 addr, +static void denali_indexed_write(struct denali_controller *denali, u32 addr, u32 data) { iowrite32(addr, denali->host + DENALI_INDEXED_CTRL); iowrite32(data, denali->host + DENALI_INDEXED_DATA); } -/* - * Use the configuration feature register to determine the maximum number of - * banks that the hardware supports. - */ -static void denali_detect_max_banks(struct denali_nand_info *denali) -{ - uint32_t features = ioread32(denali->reg + FEATURES); - - denali->max_banks = 1 << FIELD_GET(FEATURES__N_BANKS, features); - - /* the encoding changed from rev 5.0 to 5.1 */ - if (denali->revision < 0x0501) - denali->max_banks <<= 1; -} - -static void denali_enable_irq(struct denali_nand_info *denali) +static void denali_enable_irq(struct denali_controller *denali) { int i; @@ -111,7 +97,7 @@ static void denali_enable_irq(struct denali_nand_info *denali) iowrite32(GLOBAL_INT_EN_FLAG, denali->reg + GLOBAL_INT_ENABLE); } -static void denali_disable_irq(struct denali_nand_info *denali) +static void denali_disable_irq(struct denali_controller *denali) { int i; @@ -120,14 +106,14 @@ static void denali_disable_irq(struct denali_nand_info *denali) iowrite32(0, denali->reg + GLOBAL_INT_ENABLE); } -static void denali_clear_irq(struct denali_nand_info *denali, +static void denali_clear_irq(struct denali_controller *denali, int bank, uint32_t irq_status) { /* write one to clear bits */ iowrite32(irq_status, denali->reg + INTR_STATUS(bank)); } -static void denali_clear_irq_all(struct denali_nand_info *denali) +static void denali_clear_irq_all(struct denali_controller *denali) { int i; @@ -137,7 +123,7 @@ static void denali_clear_irq_all(struct denali_nand_info *denali) static irqreturn_t denali_isr(int irq, void *dev_id) { - struct denali_nand_info *denali = dev_id; + struct denali_controller *denali = dev_id; irqreturn_t ret = IRQ_NONE; uint32_t irq_status; int i; @@ -165,7 +151,7 @@ static irqreturn_t denali_isr(int irq, void *dev_id) return ret; } -static void denali_reset_irq(struct denali_nand_info *denali) +static void denali_reset_irq(struct denali_controller *denali) { unsigned long flags; @@ -175,8 +161,7 @@ static void denali_reset_irq(struct denali_nand_info *denali) spin_unlock_irqrestore(&denali->irq_lock, flags); } -static uint32_t denali_wait_for_irq(struct denali_nand_info *denali, - uint32_t irq_mask) +static u32 denali_wait_for_irq(struct denali_controller *denali, u32 irq_mask) { unsigned long time_left, flags; uint32_t irq_status; @@ -208,9 +193,41 @@ static uint32_t denali_wait_for_irq(struct denali_nand_info *denali, static void denali_select_target(struct nand_chip *chip, int cs) { - struct denali_nand_info *denali = to_denali(chip); + struct denali_controller *denali = to_denali_controller(chip); + struct denali_chip_sel *sel = &to_denali_chip(chip)->sels[cs]; + struct mtd_info *mtd = nand_to_mtd(chip); + + denali->active_bank = sel->bank; - denali->active_bank = cs; + iowrite32(1 << (chip->phys_erase_shift - chip->page_shift), + denali->reg + PAGES_PER_BLOCK); + iowrite32(chip->options & NAND_BUSWIDTH_16 ? 1 : 0, + denali->reg + DEVICE_WIDTH); + iowrite32(mtd->writesize, denali->reg + DEVICE_MAIN_AREA_SIZE); + iowrite32(mtd->oobsize, denali->reg + DEVICE_SPARE_AREA_SIZE); + iowrite32(chip->options & NAND_ROW_ADDR_3 ? + 0 : TWO_ROW_ADDR_CYCLES__FLAG, + denali->reg + TWO_ROW_ADDR_CYCLES); + iowrite32(FIELD_PREP(ECC_CORRECTION__ERASE_THRESHOLD, 1) | + FIELD_PREP(ECC_CORRECTION__VALUE, chip->ecc.strength), + denali->reg + ECC_CORRECTION); + iowrite32(chip->ecc.size, denali->reg + CFG_DATA_BLOCK_SIZE); + iowrite32(chip->ecc.size, denali->reg + CFG_LAST_DATA_BLOCK_SIZE); + iowrite32(chip->ecc.steps, denali->reg + CFG_NUM_DATA_BLOCKS); + + if (chip->options & NAND_KEEP_TIMINGS) + return; + + /* update timing registers unless NAND_KEEP_TIMINGS is set */ + iowrite32(sel->hwhr2_and_we_2_re, denali->reg + TWHR2_AND_WE_2_RE); + iowrite32(sel->tcwaw_and_addr_2_data, + denali->reg + TCWAW_AND_ADDR_2_DATA); + iowrite32(sel->re_2_we, denali->reg + RE_2_WE); + iowrite32(sel->acc_clks, denali->reg + ACC_CLKS); + iowrite32(sel->rdwr_en_lo_cnt, denali->reg + RDWR_EN_LO_CNT); + iowrite32(sel->rdwr_en_hi_cnt, denali->reg + RDWR_EN_HI_CNT); + iowrite32(sel->cs_setup_cnt, denali->reg + CS_SETUP_CNT); + iowrite32(sel->re_2_re, denali->reg + RE_2_RE); } static int denali_change_column(struct nand_chip *chip, unsigned int offset, @@ -226,7 +243,7 @@ static int denali_change_column(struct nand_chip *chip, unsigned int offset, static int denali_payload_xfer(struct nand_chip *chip, void *buf, bool write) { - struct denali_nand_info *denali = to_denali(chip); + struct denali_controller *denali = to_denali_controller(chip); struct mtd_info *mtd = nand_to_mtd(chip); struct nand_ecc_ctrl *ecc = &chip->ecc; int writesize = mtd->writesize; @@ -263,7 +280,7 @@ static int denali_payload_xfer(struct nand_chip *chip, void *buf, bool write) static int denali_oob_xfer(struct nand_chip *chip, void *buf, bool write) { - struct denali_nand_info *denali = to_denali(chip); + struct denali_controller *denali = to_denali_controller(chip); struct mtd_info *mtd = nand_to_mtd(chip); struct nand_ecc_ctrl *ecc = &chip->ecc; int writesize = mtd->writesize; @@ -393,7 +410,7 @@ static int denali_check_erased_page(struct nand_chip *chip, u8 *buf, unsigned long uncor_ecc_flags, unsigned int max_bitflips) { - struct denali_nand_info *denali = to_denali(chip); + struct denali_controller *denali = to_denali_controller(chip); struct mtd_ecc_stats *ecc_stats = &nand_to_mtd(chip)->ecc_stats; uint8_t *ecc_code = chip->oob_poi + denali->oob_skip_bytes; int ecc_steps = chip->ecc.steps; @@ -426,7 +443,7 @@ static int denali_check_erased_page(struct nand_chip *chip, u8 *buf, static int denali_hw_ecc_fixup(struct nand_chip *chip, unsigned long *uncor_ecc_flags) { - struct denali_nand_info *denali = to_denali(chip); + struct denali_controller *denali = to_denali_controller(chip); struct mtd_ecc_stats *ecc_stats = &nand_to_mtd(chip)->ecc_stats; int bank = denali->active_bank; uint32_t ecc_cor; @@ -461,7 +478,7 @@ static int denali_hw_ecc_fixup(struct nand_chip *chip, static int denali_sw_ecc_fixup(struct nand_chip *chip, unsigned long *uncor_ecc_flags, uint8_t *buf) { - struct denali_nand_info *denali = to_denali(chip); + struct denali_controller *denali = to_denali_controller(chip); struct mtd_ecc_stats *ecc_stats = &nand_to_mtd(chip)->ecc_stats; unsigned int ecc_size = chip->ecc.size; unsigned int bitflips = 0; @@ -532,7 +549,7 @@ static int denali_sw_ecc_fixup(struct nand_chip *chip, return max_bitflips; } -static void denali_setup_dma64(struct denali_nand_info *denali, +static void denali_setup_dma64(struct denali_controller *denali, dma_addr_t dma_addr, int page, bool write) { uint32_t mode; @@ -557,7 +574,7 @@ static void denali_setup_dma64(struct denali_nand_info *denali, denali->host_write(denali, mode, upper_32_bits(dma_addr)); } -static void denali_setup_dma32(struct denali_nand_info *denali, +static void denali_setup_dma32(struct denali_controller *denali, dma_addr_t dma_addr, int page, bool write) { uint32_t mode; @@ -581,7 +598,7 @@ static void denali_setup_dma32(struct denali_nand_info *denali, denali->host_write(denali, mode | 0x14000, 0x2400); } -static int denali_pio_read(struct denali_nand_info *denali, u32 *buf, +static int denali_pio_read(struct denali_controller *denali, u32 *buf, size_t size, int page) { u32 addr = DENALI_MAP01 | DENALI_BANK(denali) | page; @@ -608,7 +625,7 @@ static int denali_pio_read(struct denali_nand_info *denali, u32 *buf, return irq_status & ecc_err_mask ? -EBADMSG : 0; } -static int denali_pio_write(struct denali_nand_info *denali, const u32 *buf, +static int denali_pio_write(struct denali_controller *denali, const u32 *buf, size_t size, int page) { u32 addr = DENALI_MAP01 | DENALI_BANK(denali) | page; @@ -628,7 +645,7 @@ static int denali_pio_write(struct denali_nand_info *denali, const u32 *buf, return 0; } -static int denali_pio_xfer(struct denali_nand_info *denali, void *buf, +static int denali_pio_xfer(struct denali_controller *denali, void *buf, size_t size, int page, bool write) { if (write) @@ -637,7 +654,7 @@ static int denali_pio_xfer(struct denali_nand_info *denali, void *buf, return denali_pio_read(denali, buf, size, page); } -static int denali_dma_xfer(struct denali_nand_info *denali, void *buf, +static int denali_dma_xfer(struct denali_controller *denali, void *buf, size_t size, int page, bool write) { dma_addr_t dma_addr; @@ -697,7 +714,7 @@ static int denali_dma_xfer(struct denali_nand_info *denali, void *buf, static int denali_page_xfer(struct nand_chip *chip, void *buf, size_t size, int page, bool write) { - struct denali_nand_info *denali = to_denali(chip); + struct denali_controller *denali = to_denali_controller(chip); denali_select_target(chip, chip->cur_cs); @@ -710,8 +727,8 @@ static int denali_page_xfer(struct nand_chip *chip, void *buf, size_t size, static int denali_read_page(struct nand_chip *chip, uint8_t *buf, int oob_required, int page) { + struct denali_controller *denali = to_denali_controller(chip); struct mtd_info *mtd = nand_to_mtd(chip); - struct denali_nand_info *denali = mtd_to_denali(mtd); unsigned long uncor_ecc_flags = 0; int stat = 0; int ret; @@ -751,7 +768,8 @@ static int denali_write_page(struct nand_chip *chip, const uint8_t *buf, static int denali_setup_data_interface(struct nand_chip *chip, int chipnr, const struct nand_data_interface *conf) { - struct denali_nand_info *denali = mtd_to_denali(nand_to_mtd(chip)); + struct denali_controller *denali = to_denali_controller(chip); + struct denali_chip_sel *sel; const struct nand_sdr_timings *timings; unsigned long t_x, mult_x; int acc_clks, re_2_we, re_2_re, we_2_re, addr_2_data; @@ -780,6 +798,8 @@ static int denali_setup_data_interface(struct nand_chip *chip, int chipnr, if (chipnr == NAND_DATA_IFACE_CHECK_ONLY) return 0; + sel = &to_denali_chip(chip)->sels[chipnr]; + /* tREA -> ACC_CLKS */ acc_clks = DIV_ROUND_UP(timings->tREA_max, t_x); acc_clks = min_t(int, acc_clks, ACC_CLKS__VALUE); @@ -787,7 +807,7 @@ static int denali_setup_data_interface(struct nand_chip *chip, int chipnr, tmp = ioread32(denali->reg + ACC_CLKS); tmp &= ~ACC_CLKS__VALUE; tmp |= FIELD_PREP(ACC_CLKS__VALUE, acc_clks); - iowrite32(tmp, denali->reg + ACC_CLKS); + sel->acc_clks = tmp; /* tRWH -> RE_2_WE */ re_2_we = DIV_ROUND_UP(timings->tRHW_min, t_x); @@ -796,7 +816,7 @@ static int denali_setup_data_interface(struct nand_chip *chip, int chipnr, tmp = ioread32(denali->reg + RE_2_WE); tmp &= ~RE_2_WE__VALUE; tmp |= FIELD_PREP(RE_2_WE__VALUE, re_2_we); - iowrite32(tmp, denali->reg + RE_2_WE); + sel->re_2_we = tmp; /* tRHZ -> RE_2_RE */ re_2_re = DIV_ROUND_UP(timings->tRHZ_max, t_x); @@ -805,7 +825,7 @@ static int denali_setup_data_interface(struct nand_chip *chip, int chipnr, tmp = ioread32(denali->reg + RE_2_RE); tmp &= ~RE_2_RE__VALUE; tmp |= FIELD_PREP(RE_2_RE__VALUE, re_2_re); - iowrite32(tmp, denali->reg + RE_2_RE); + sel->re_2_re = tmp; /* * tCCS, tWHR -> WE_2_RE @@ -819,7 +839,7 @@ static int denali_setup_data_interface(struct nand_chip *chip, int chipnr, tmp = ioread32(denali->reg + TWHR2_AND_WE_2_RE); tmp &= ~TWHR2_AND_WE_2_RE__WE_2_RE; tmp |= FIELD_PREP(TWHR2_AND_WE_2_RE__WE_2_RE, we_2_re); - iowrite32(tmp, denali->reg + TWHR2_AND_WE_2_RE); + sel->hwhr2_and_we_2_re = tmp; /* tADL -> ADDR_2_DATA */ @@ -834,7 +854,7 @@ static int denali_setup_data_interface(struct nand_chip *chip, int chipnr, tmp = ioread32(denali->reg + TCWAW_AND_ADDR_2_DATA); tmp &= ~TCWAW_AND_ADDR_2_DATA__ADDR_2_DATA; tmp |= FIELD_PREP(TCWAW_AND_ADDR_2_DATA__ADDR_2_DATA, addr_2_data); - iowrite32(tmp, denali->reg + TCWAW_AND_ADDR_2_DATA); + sel->tcwaw_and_addr_2_data = tmp; /* tREH, tWH -> RDWR_EN_HI_CNT */ rdwr_en_hi = DIV_ROUND_UP(max(timings->tREH_min, timings->tWH_min), @@ -844,7 +864,7 @@ static int denali_setup_data_interface(struct nand_chip *chip, int chipnr, tmp = ioread32(denali->reg + RDWR_EN_HI_CNT); tmp &= ~RDWR_EN_HI_CNT__VALUE; tmp |= FIELD_PREP(RDWR_EN_HI_CNT__VALUE, rdwr_en_hi); - iowrite32(tmp, denali->reg + RDWR_EN_HI_CNT); + sel->rdwr_en_hi_cnt = tmp; /* tRP, tWP -> RDWR_EN_LO_CNT */ rdwr_en_lo = DIV_ROUND_UP(max(timings->tRP_min, timings->tWP_min), t_x); @@ -857,7 +877,7 @@ static int denali_setup_data_interface(struct nand_chip *chip, int chipnr, tmp = ioread32(denali->reg + RDWR_EN_LO_CNT); tmp &= ~RDWR_EN_LO_CNT__VALUE; tmp |= FIELD_PREP(RDWR_EN_LO_CNT__VALUE, rdwr_en_lo); - iowrite32(tmp, denali->reg + RDWR_EN_LO_CNT); + sel->rdwr_en_lo_cnt = tmp; /* tCS, tCEA -> CS_SETUP_CNT */ cs_setup = max3((int)DIV_ROUND_UP(timings->tCS_min, t_x) - rdwr_en_lo, @@ -868,40 +888,11 @@ static int denali_setup_data_interface(struct nand_chip *chip, int chipnr, tmp = ioread32(denali->reg + CS_SETUP_CNT); tmp &= ~CS_SETUP_CNT__VALUE; tmp |= FIELD_PREP(CS_SETUP_CNT__VALUE, cs_setup); - iowrite32(tmp, denali->reg + CS_SETUP_CNT); + sel->cs_setup_cnt = tmp; return 0; } -static void denali_hw_init(struct denali_nand_info *denali) -{ - /* - * The REVISION register may not be reliable. Platforms are allowed to - * override it. - */ - if (!denali->revision) - denali->revision = swab16(ioread32(denali->reg + REVISION)); - - /* - * Set how many bytes should be skipped before writing data in OOB. - * If a non-zero value has already been set (by firmware or something), - * just use it. Otherwise, set the driver default. - */ - denali->oob_skip_bytes = ioread32(denali->reg + SPARE_AREA_SKIP_BYTES); - if (!denali->oob_skip_bytes) { - denali->oob_skip_bytes = DENALI_DEFAULT_OOB_SKIP_BYTES; - iowrite32(denali->oob_skip_bytes, - denali->reg + SPARE_AREA_SKIP_BYTES); - } - - denali_detect_max_banks(denali); - iowrite32(0, denali->reg + TRANSFER_SPARE_REG); - iowrite32(0x0F, denali->reg + RB_PIN_ENABLED); - iowrite32(CHIP_EN_DONT_CARE__FLAG, denali->reg + CHIP_ENABLE_DONT_CARE); - iowrite32(ECC_ENABLE__FLAG, denali->reg + ECC_ENABLE); - iowrite32(0xffff, denali->reg + SPARE_AREA_MARKER); -} - int denali_calc_ecc_bytes(int step_size, int strength) { /* BCH code. Denali requires ecc.bytes to be multiple of 2 */ @@ -912,10 +903,10 @@ EXPORT_SYMBOL(denali_calc_ecc_bytes); static int denali_ooblayout_ecc(struct mtd_info *mtd, int section, struct mtd_oob_region *oobregion) { - struct denali_nand_info *denali = mtd_to_denali(mtd); struct nand_chip *chip = mtd_to_nand(mtd); + struct denali_controller *denali = to_denali_controller(chip); - if (section) + if (section > 0) return -ERANGE; oobregion->offset = denali->oob_skip_bytes; @@ -927,10 +918,10 @@ static int denali_ooblayout_ecc(struct mtd_info *mtd, int section, static int denali_ooblayout_free(struct mtd_info *mtd, int section, struct mtd_oob_region *oobregion) { - struct denali_nand_info *denali = mtd_to_denali(mtd); struct nand_chip *chip = mtd_to_nand(mtd); + struct denali_controller *denali = to_denali_controller(chip); - if (section) + if (section > 0) return -ERANGE; oobregion->offset = chip->ecc.total + denali->oob_skip_bytes; @@ -946,7 +937,7 @@ static const struct mtd_ooblayout_ops denali_ooblayout_ops = { static int denali_multidev_fixup(struct nand_chip *chip) { - struct denali_nand_info *denali = to_denali(chip); + struct denali_controller *denali = to_denali_controller(chip); struct mtd_info *mtd = nand_to_mtd(chip); struct nand_memory_organization *memorg; @@ -1001,38 +992,10 @@ static int denali_multidev_fixup(struct nand_chip *chip) static int denali_attach_chip(struct nand_chip *chip) { + struct denali_controller *denali = to_denali_controller(chip); struct mtd_info *mtd = nand_to_mtd(chip); - struct denali_nand_info *denali = mtd_to_denali(mtd); int ret; - if (ioread32(denali->reg + FEATURES) & FEATURES__DMA) - denali->dma_avail = true; - - if (denali->dma_avail) { - int dma_bit = denali->caps & DENALI_CAP_DMA_64BIT ? 64 : 32; - - ret = dma_set_mask(denali->dev, DMA_BIT_MASK(dma_bit)); - if (ret) { - dev_info(denali->dev, - "Failed to set DMA mask. Disabling DMA.\n"); - denali->dma_avail = false; - } - } - - if (denali->dma_avail) { - chip->options |= NAND_USE_BOUNCE_BUFFER; - chip->buf_align = 16; - if (denali->caps & DENALI_CAP_DMA_64BIT) - denali->setup_dma = denali_setup_dma64; - else - denali->setup_dma = denali_setup_dma32; - } - - chip->bbt_options |= NAND_BBT_USE_FLASH; - chip->bbt_options |= NAND_BBT_NO_OOB; - chip->ecc.mode = NAND_ECC_HW_SYNDROME; - chip->options |= NAND_NO_SUBPAGE_WRITE; - ret = nand_ecc_choose_conf(chip, denali->ecc_caps, mtd->oobsize - denali->oob_skip_bytes); if (ret) { @@ -1044,33 +1007,6 @@ static int denali_attach_chip(struct nand_chip *chip) "chosen ECC settings: step=%d, strength=%d, bytes=%d\n", chip->ecc.size, chip->ecc.strength, chip->ecc.bytes); - iowrite32(FIELD_PREP(ECC_CORRECTION__ERASE_THRESHOLD, 1) | - FIELD_PREP(ECC_CORRECTION__VALUE, chip->ecc.strength), - denali->reg + ECC_CORRECTION); - iowrite32(mtd->erasesize / mtd->writesize, - denali->reg + PAGES_PER_BLOCK); - iowrite32(chip->options & NAND_BUSWIDTH_16 ? 1 : 0, - denali->reg + DEVICE_WIDTH); - iowrite32(chip->options & NAND_ROW_ADDR_3 ? 0 : TWO_ROW_ADDR_CYCLES__FLAG, - denali->reg + TWO_ROW_ADDR_CYCLES); - iowrite32(mtd->writesize, denali->reg + DEVICE_MAIN_AREA_SIZE); - iowrite32(mtd->oobsize, denali->reg + DEVICE_SPARE_AREA_SIZE); - - iowrite32(chip->ecc.size, denali->reg + CFG_DATA_BLOCK_SIZE); - iowrite32(chip->ecc.size, denali->reg + CFG_LAST_DATA_BLOCK_SIZE); - /* chip->ecc.steps is set by nand_scan_tail(); not available here */ - iowrite32(mtd->writesize / chip->ecc.size, - denali->reg + CFG_NUM_DATA_BLOCKS); - - mtd_set_ooblayout(mtd, &denali_ooblayout_ops); - - chip->ecc.read_page = denali_read_page; - chip->ecc.read_page_raw = denali_read_page_raw; - chip->ecc.write_page = denali_write_page; - chip->ecc.write_page_raw = denali_write_page_raw; - chip->ecc.read_oob = denali_read_oob; - chip->ecc.write_oob = denali_write_oob; - ret = denali_multidev_fixup(chip); if (ret) return ret; @@ -1078,7 +1014,7 @@ static int denali_attach_chip(struct nand_chip *chip) return 0; } -static void denali_exec_in8(struct denali_nand_info *denali, u32 type, +static void denali_exec_in8(struct denali_controller *denali, u32 type, u8 *buf, unsigned int len) { int i; @@ -1087,7 +1023,7 @@ static void denali_exec_in8(struct denali_nand_info *denali, u32 type, buf[i] = denali->host_read(denali, type | DENALI_BANK(denali)); } -static void denali_exec_in16(struct denali_nand_info *denali, u32 type, +static void denali_exec_in16(struct denali_controller *denali, u32 type, u8 *buf, unsigned int len) { u32 data; @@ -1101,7 +1037,7 @@ static void denali_exec_in16(struct denali_nand_info *denali, u32 type, } } -static void denali_exec_in(struct denali_nand_info *denali, u32 type, +static void denali_exec_in(struct denali_controller *denali, u32 type, u8 *buf, unsigned int len, bool width16) { if (width16) @@ -1110,7 +1046,7 @@ static void denali_exec_in(struct denali_nand_info *denali, u32 type, denali_exec_in8(denali, type, buf, len); } -static void denali_exec_out8(struct denali_nand_info *denali, u32 type, +static void denali_exec_out8(struct denali_controller *denali, u32 type, const u8 *buf, unsigned int len) { int i; @@ -1119,7 +1055,7 @@ static void denali_exec_out8(struct denali_nand_info *denali, u32 type, denali->host_write(denali, type | DENALI_BANK(denali), buf[i]); } -static void denali_exec_out16(struct denali_nand_info *denali, u32 type, +static void denali_exec_out16(struct denali_controller *denali, u32 type, const u8 *buf, unsigned int len) { int i; @@ -1129,7 +1065,7 @@ static void denali_exec_out16(struct denali_nand_info *denali, u32 type, buf[i + 1] << 16 | buf[i]); } -static void denali_exec_out(struct denali_nand_info *denali, u32 type, +static void denali_exec_out(struct denali_controller *denali, u32 type, const u8 *buf, unsigned int len, bool width16) { if (width16) @@ -1138,7 +1074,7 @@ static void denali_exec_out(struct denali_nand_info *denali, u32 type, denali_exec_out8(denali, type, buf, len); } -static int denali_exec_waitrdy(struct denali_nand_info *denali) +static int denali_exec_waitrdy(struct denali_controller *denali) { u32 irq_stat; @@ -1154,7 +1090,7 @@ static int denali_exec_waitrdy(struct denali_nand_info *denali) static int denali_exec_instr(struct nand_chip *chip, const struct nand_op_instr *instr) { - struct denali_nand_info *denali = to_denali(chip); + struct denali_controller *denali = to_denali_controller(chip); switch (instr->type) { case NAND_OP_CMD_INSTR: @@ -1204,7 +1140,7 @@ static int denali_exec_op(struct nand_chip *chip, * Some commands contain NAND_OP_WAITRDY_INSTR. * irq must be cleared here to catch the R/B# interrupt there. */ - denali_reset_irq(to_denali(chip)); + denali_reset_irq(to_denali_controller(chip)); for (i = 0; i < op->ninstrs; i++) { ret = denali_exec_instr(chip, &op->instrs[i]); @@ -1221,53 +1157,80 @@ static const struct nand_controller_ops denali_controller_ops = { .setup_data_interface = denali_setup_data_interface, }; -int denali_init(struct denali_nand_info *denali) +int denali_chip_init(struct denali_controller *denali, + struct denali_chip *dchip) { - struct nand_chip *chip = &denali->nand; + struct nand_chip *chip = &dchip->chip; struct mtd_info *mtd = nand_to_mtd(chip); - u32 features = ioread32(denali->reg + FEATURES); - int ret; + struct denali_chip *dchip2; + int i, j, ret; - mtd->dev.parent = denali->dev; - denali_hw_init(denali); + chip->controller = &denali->controller; - init_completion(&denali->complete); - spin_lock_init(&denali->irq_lock); + /* sanity checks for bank numbers */ + for (i = 0; i < dchip->nsels; i++) { + unsigned int bank = dchip->sels[i].bank; - denali_clear_irq_all(denali); + if (bank >= denali->nbanks) { + dev_err(denali->dev, "unsupported bank %d\n", bank); + return -EINVAL; + } - ret = devm_request_irq(denali->dev, denali->irq, denali_isr, - IRQF_SHARED, DENALI_NAND_NAME, denali); - if (ret) { - dev_err(denali->dev, "Unable to request IRQ\n"); - return ret; - } + for (j = 0; j < i; j++) { + if (bank == dchip->sels[j].bank) { + dev_err(denali->dev, + "bank %d is assigned twice in the same chip\n", + bank); + return -EINVAL; + } + } - denali_enable_irq(denali); + list_for_each_entry(dchip2, &denali->chips, node) { + for (j = 0; j < dchip2->nsels; j++) { + if (bank == dchip2->sels[j].bank) { + dev_err(denali->dev, + "bank %d is already used\n", + bank); + return -EINVAL; + } + } + } + } - denali->active_bank = DENALI_INVALID_BANK; + mtd->dev.parent = denali->dev; - nand_set_flash_node(chip, denali->dev->of_node); - /* Fallback to the default name if DT did not give "label" property */ - if (!mtd->name) + /* + * Fallback to the default name if DT did not give "label" property. + * Use "label" property if multiple chips are connected. + */ + if (!mtd->name && list_empty(&denali->chips)) mtd->name = "denali-nand"; - if (features & FEATURES__INDEX_ADDR) { - denali->host_read = denali_indexed_read; - denali->host_write = denali_indexed_write; - } else { - denali->host_read = denali_direct_read; - denali->host_write = denali_direct_write; + if (denali->dma_avail) { + chip->options |= NAND_USE_BOUNCE_BUFFER; + chip->buf_align = 16; } /* clk rate info is needed for setup_data_interface */ if (!denali->clk_rate || !denali->clk_x_rate) chip->options |= NAND_KEEP_TIMINGS; - chip->legacy.dummy_controller.ops = &denali_controller_ops; - ret = nand_scan(chip, denali->max_banks); + chip->bbt_options |= NAND_BBT_USE_FLASH; + chip->bbt_options |= NAND_BBT_NO_OOB; + chip->options |= NAND_NO_SUBPAGE_WRITE; + chip->ecc.mode = NAND_ECC_HW_SYNDROME; + chip->ecc.read_page = denali_read_page; + chip->ecc.write_page = denali_write_page; + chip->ecc.read_page_raw = denali_read_page_raw; + chip->ecc.write_page_raw = denali_write_page_raw; + chip->ecc.read_oob = denali_read_oob; + chip->ecc.write_oob = denali_write_oob; + + mtd_set_ooblayout(mtd, &denali_ooblayout_ops); + + ret = nand_scan(chip, dchip->nsels); if (ret) - goto disable_irq; + return ret; ret = mtd_device_register(mtd, NULL, 0); if (ret) { @@ -1275,20 +1238,111 @@ int denali_init(struct denali_nand_info *denali) goto cleanup_nand; } + list_add_tail(&dchip->node, &denali->chips); + return 0; cleanup_nand: nand_cleanup(chip); -disable_irq: - denali_disable_irq(denali); return ret; } +EXPORT_SYMBOL_GPL(denali_chip_init); + +int denali_init(struct denali_controller *denali) +{ + u32 features = ioread32(denali->reg + FEATURES); + int ret; + + nand_controller_init(&denali->controller); + denali->controller.ops = &denali_controller_ops; + init_completion(&denali->complete); + spin_lock_init(&denali->irq_lock); + INIT_LIST_HEAD(&denali->chips); + denali->active_bank = DENALI_INVALID_BANK; + + /* + * The REVISION register may not be reliable. Platforms are allowed to + * override it. + */ + if (!denali->revision) + denali->revision = swab16(ioread32(denali->reg + REVISION)); + + denali->nbanks = 1 << FIELD_GET(FEATURES__N_BANKS, features); + + /* the encoding changed from rev 5.0 to 5.1 */ + if (denali->revision < 0x0501) + denali->nbanks <<= 1; + + if (features & FEATURES__DMA) + denali->dma_avail = true; + + if (denali->dma_avail) { + int dma_bit = denali->caps & DENALI_CAP_DMA_64BIT ? 64 : 32; + + ret = dma_set_mask(denali->dev, DMA_BIT_MASK(dma_bit)); + if (ret) { + dev_info(denali->dev, + "Failed to set DMA mask. Disabling DMA.\n"); + denali->dma_avail = false; + } + } + + if (denali->dma_avail) { + if (denali->caps & DENALI_CAP_DMA_64BIT) + denali->setup_dma = denali_setup_dma64; + else + denali->setup_dma = denali_setup_dma32; + } + + if (features & FEATURES__INDEX_ADDR) { + denali->host_read = denali_indexed_read; + denali->host_write = denali_indexed_write; + } else { + denali->host_read = denali_direct_read; + denali->host_write = denali_direct_write; + } + + /* + * Set how many bytes should be skipped before writing data in OOB. + * If a non-zero value has already been set (by firmware or something), + * just use it. Otherwise, set the driver's default. + */ + denali->oob_skip_bytes = ioread32(denali->reg + SPARE_AREA_SKIP_BYTES); + if (!denali->oob_skip_bytes) { + denali->oob_skip_bytes = DENALI_DEFAULT_OOB_SKIP_BYTES; + iowrite32(denali->oob_skip_bytes, + denali->reg + SPARE_AREA_SKIP_BYTES); + } + + iowrite32(0, denali->reg + TRANSFER_SPARE_REG); + iowrite32(GENMASK(denali->nbanks - 1, 0), denali->reg + RB_PIN_ENABLED); + iowrite32(CHIP_EN_DONT_CARE__FLAG, denali->reg + CHIP_ENABLE_DONT_CARE); + iowrite32(ECC_ENABLE__FLAG, denali->reg + ECC_ENABLE); + iowrite32(0xffff, denali->reg + SPARE_AREA_MARKER); + + denali_clear_irq_all(denali); + + ret = devm_request_irq(denali->dev, denali->irq, denali_isr, + IRQF_SHARED, DENALI_NAND_NAME, denali); + if (ret) { + dev_err(denali->dev, "Unable to request IRQ\n"); + return ret; + } + + denali_enable_irq(denali); + + return 0; +} EXPORT_SYMBOL(denali_init); -void denali_remove(struct denali_nand_info *denali) +void denali_remove(struct denali_controller *denali) { - nand_release(&denali->nand); + struct denali_chip *dchip; + + list_for_each_entry(dchip, &denali->chips, node) + nand_release(&dchip->chip); + denali_disable_irq(denali); } EXPORT_SYMBOL(denali_remove); diff --git a/drivers/mtd/nand/raw/denali.h b/drivers/mtd/nand/raw/denali.h index d2603c67dd20..e5cdcda56d14 100644 --- a/drivers/mtd/nand/raw/denali.h +++ b/drivers/mtd/nand/raw/denali.h @@ -9,6 +9,7 @@ #include #include +#include #include #include #include @@ -290,29 +291,98 @@ #define CHNL_ACTIVE__CHANNEL2 BIT(2) #define CHNL_ACTIVE__CHANNEL3 BIT(3) -struct denali_nand_info { - struct nand_chip nand; - unsigned long clk_rate; /* core clock rate */ - unsigned long clk_x_rate; /* bus interface clock rate */ - int active_bank; /* currently selected bank */ +/** + * struct denali_chip_sel - per-CS data of Denali NAND + * + * @bank: bank id of the controller this CS is connected to + * @hwhr2_and_we_2_re: value of timing register HWHR2_AND_WE_2_RE + * @tcwaw_and_addr_2_data: value of timing register TCWAW_AND_ADDR_2_DATA + * @re_2_we: value of timing register RE_2_WE + * @acc_clks: value of timing register ACC_CLKS + * @rdwr_en_lo_cnt: value of timing register RDWR_EN_LO_CNT + * @rdwr_en_hi_cnt: value of timing register RDWR_EN_HI_CNT + * @cs_setup_cnt: value of timing register CS_SETUP_CNT + * @re_2_re: value of timing register RE_2_RE + */ +struct denali_chip_sel { + int bank; + u32 hwhr2_and_we_2_re; + u32 tcwaw_and_addr_2_data; + u32 re_2_we; + u32 acc_clks; + u32 rdwr_en_lo_cnt; + u32 rdwr_en_hi_cnt; + u32 cs_setup_cnt; + u32 re_2_re; +}; + +/** + * struct denali_chip - per-chip data of Denali NAND + * + * @chip: base NAND chip structure + * @node: node to be used to associate this chip with the controller + * @nsels: the number of CS lines of this chip + * @sels: the array of per-cs data + */ +struct denali_chip { + struct nand_chip chip; + struct list_head node; + unsigned int nsels; + struct denali_chip_sel sels[0]; +}; + +/** + * struct denali_controller - Denali NAND controller data + * + * @controller: base NAND controller structure + * @dev: device + * @chips: the list of chips attached to this controller + * @clk_rate: frequency of core clock + * @clk_x_rate: frequency of bus interface clock + * @reg: base of Register Interface + * @host: base of Host Data/Command interface + * @complete: completion used to wait for interrupts + * @irq: interrupt number + * @irq_mask: interrupt bits the controller is waiting for + * @irq_status: interrupt bits of events that have happened + * @irq_lock: lock to protect @irq_mask and @irq_status + * @dma_avail: set if DMA engine is available + * @devs_per_cs: number of devices connected in parallel + * @oob_skip_bytes: number of bytes in OOB skipped by the ECC engine + * @active_bank: active bank id + * @nbanks: the number of banks supported by this controller + * @revision: IP revision + * @caps: controller capabilities that cannot be detected run-time + * @ecc_caps: ECC engine capabilities + * @host_read: callback for read access of Host Data/Command Interface + * @host_write: callback for write access of Host Data/Command Interface + * @setup_dma: callback for setup of the Data DMA + */ +struct denali_controller { + struct nand_controller controller; struct device *dev; - void __iomem *reg; /* Register Interface */ - void __iomem *host; /* Host Data/Command Interface */ + struct list_head chips; + unsigned long clk_rate; + unsigned long clk_x_rate; + void __iomem *reg; + void __iomem *host; struct completion complete; - spinlock_t irq_lock; /* protect irq_mask and irq_status */ - u32 irq_mask; /* interrupts we are waiting for */ - u32 irq_status; /* interrupts that have happened */ int irq; - bool dma_avail; /* can support DMA? */ - int devs_per_cs; /* devices connected in parallel */ - int oob_skip_bytes; /* number of bytes reserved for BBM */ - int max_banks; - unsigned int revision; /* IP revision */ - unsigned int caps; /* IP capability (or quirk) */ + u32 irq_mask; + u32 irq_status; + spinlock_t irq_lock; + bool dma_avail; + int devs_per_cs; + int oob_skip_bytes; + int active_bank; + int nbanks; + unsigned int revision; + unsigned int caps; const struct nand_ecc_caps *ecc_caps; - u32 (*host_read)(struct denali_nand_info *denali, u32 addr); - void (*host_write)(struct denali_nand_info *denali, u32 addr, u32 data); - void (*setup_dma)(struct denali_nand_info *denali, dma_addr_t dma_addr, + u32 (*host_read)(struct denali_controller *denali, u32 addr); + void (*host_write)(struct denali_controller *denali, u32 addr, + u32 data); + void (*setup_dma)(struct denali_controller *denali, dma_addr_t dma_addr, int page, bool write); }; @@ -320,7 +390,9 @@ struct denali_nand_info { #define DENALI_CAP_DMA_64BIT BIT(1) int denali_calc_ecc_bytes(int step_size, int strength); -int denali_init(struct denali_nand_info *denali); -void denali_remove(struct denali_nand_info *denali); +int denali_chip_init(struct denali_controller *denali, + struct denali_chip *dchip); +int denali_init(struct denali_controller *denali); +void denali_remove(struct denali_controller *denali); #endif /* __DENALI_H__ */ diff --git a/drivers/mtd/nand/raw/denali_dt.c b/drivers/mtd/nand/raw/denali_dt.c index 0b5ae2418815..5e14836f6bd5 100644 --- a/drivers/mtd/nand/raw/denali_dt.c +++ b/drivers/mtd/nand/raw/denali_dt.c @@ -18,7 +18,7 @@ #include "denali.h" struct denali_dt { - struct denali_nand_info denali; + struct denali_controller controller; struct clk *clk; /* core clock */ struct clk *clk_x; /* bus interface clock */ struct clk *clk_ecc; /* ECC circuit clock */ @@ -71,19 +71,92 @@ static const struct of_device_id denali_nand_dt_ids[] = { }; MODULE_DEVICE_TABLE(of, denali_nand_dt_ids); +static int denali_dt_chip_init(struct denali_controller *denali, + struct device_node *chip_np) +{ + struct denali_chip *dchip; + u32 bank; + int nsels, i, ret; + + nsels = of_property_count_u32_elems(chip_np, "reg"); + if (nsels < 0) + return nsels; + + dchip = devm_kzalloc(denali->dev, struct_size(dchip, sels, nsels), + GFP_KERNEL); + if (!dchip) + return -ENOMEM; + + dchip->nsels = nsels; + + for (i = 0; i < nsels; i++) { + ret = of_property_read_u32_index(chip_np, "reg", i, &bank); + if (ret) + return ret; + + dchip->sels[i].bank = bank; + + nand_set_flash_node(&dchip->chip, chip_np); + } + + return denali_chip_init(denali, dchip); +} + +/* Backward compatibility for old platforms */ +static int denali_dt_legacy_chip_init(struct denali_controller *denali) +{ + struct denali_chip *dchip; + int nsels, i; + + nsels = denali->nbanks; + + dchip = devm_kzalloc(denali->dev, struct_size(dchip, sels, nsels), + GFP_KERNEL); + if (!dchip) + return -ENOMEM; + + dchip->nsels = nsels; + + for (i = 0; i < nsels; i++) + dchip->sels[i].bank = i; + + nand_set_flash_node(&dchip->chip, denali->dev->of_node); + + return denali_chip_init(denali, dchip); +} + +/* + * Check the DT binding. + * The new binding expects chip subnodes in the controller node. + * So, #address-cells = <1>; #size-cells = <0>; are required. + * Check the #size-cells to distinguish the binding. + */ +static bool denali_dt_is_legacy_binding(struct device_node *np) +{ + u32 cells; + int ret; + + ret = of_property_read_u32(np, "#size-cells", &cells); + if (ret) + return true; + + return cells != 0; +} + static int denali_dt_probe(struct platform_device *pdev) { struct device *dev = &pdev->dev; struct resource *res; struct denali_dt *dt; const struct denali_dt_data *data; - struct denali_nand_info *denali; + struct denali_controller *denali; + struct device_node *np; int ret; dt = devm_kzalloc(dev, sizeof(*dt), GFP_KERNEL); if (!dt) return -ENOMEM; - denali = &dt->denali; + denali = &dt->controller; data = of_device_get_match_data(dev); if (data) { @@ -140,9 +213,26 @@ static int denali_dt_probe(struct platform_device *pdev) if (ret) goto out_disable_clk_ecc; + if (denali_dt_is_legacy_binding(dev->of_node)) { + ret = denali_dt_legacy_chip_init(denali); + if (ret) + goto out_remove_denali; + } else { + for_each_child_of_node(dev->of_node, np) { + ret = denali_dt_chip_init(denali, np); + if (ret) { + of_node_put(np); + goto out_remove_denali; + } + } + } + platform_set_drvdata(pdev, dt); + return 0; +out_remove_denali: + denali_remove(denali); out_disable_clk_ecc: clk_disable_unprepare(dt->clk_ecc); out_disable_clk_x: @@ -157,7 +247,7 @@ static int denali_dt_remove(struct platform_device *pdev) { struct denali_dt *dt = platform_get_drvdata(pdev); - denali_remove(&dt->denali); + denali_remove(&dt->controller); clk_disable_unprepare(dt->clk_ecc); clk_disable_unprepare(dt->clk_x); clk_disable_unprepare(dt->clk); diff --git a/drivers/mtd/nand/raw/denali_pci.c b/drivers/mtd/nand/raw/denali_pci.c index 02eb5990a91e..d62aa5271753 100644 --- a/drivers/mtd/nand/raw/denali_pci.c +++ b/drivers/mtd/nand/raw/denali_pci.c @@ -29,10 +29,11 @@ NAND_ECC_CAPS_SINGLE(denali_pci_ecc_caps, denali_calc_ecc_bytes, 512, 8, 15); static int denali_pci_probe(struct pci_dev *dev, const struct pci_device_id *id) { - int ret; resource_size_t csr_base, mem_base; unsigned long csr_len, mem_len; - struct denali_nand_info *denali; + struct denali_controller *denali; + struct denali_chip *dchip; + int nsels, ret, i; denali = devm_kzalloc(&dev->dev, sizeof(*denali), GFP_KERNEL); if (!denali) @@ -64,7 +65,6 @@ static int denali_pci_probe(struct pci_dev *dev, const struct pci_device_id *id) denali->dev = &dev->dev; denali->irq = dev->irq; denali->ecc_caps = &denali_pci_ecc_caps; - denali->nand.ecc.options |= NAND_ECC_MAXIMIZE; denali->clk_rate = 50000000; /* 50 MHz */ denali->clk_x_rate = 200000000; /* 200 MHz */ @@ -91,10 +91,32 @@ static int denali_pci_probe(struct pci_dev *dev, const struct pci_device_id *id) if (ret) goto out_unmap_host; + nsels = denali->nbanks; + + dchip = devm_kzalloc(denali->dev, struct_size(dchip, sels, nsels), + GFP_KERNEL); + if (!dchip) { + ret = -ENOMEM; + goto out_remove_denali; + } + + dchip->chip.ecc.options |= NAND_ECC_MAXIMIZE; + + dchip->nsels = nsels; + + for (i = 0; i < nsels; i++) + dchip->sels[i].bank = i; + + ret = denali_chip_init(denali, dchip); + if (ret) + goto out_remove_denali; + pci_set_drvdata(dev, denali); return 0; +out_remove_denali: + denali_remove(denali); out_unmap_host: iounmap(denali->host); out_unmap_reg: @@ -104,7 +126,7 @@ out_unmap_reg: static void denali_pci_remove(struct pci_dev *dev) { - struct denali_nand_info *denali = pci_get_drvdata(dev); + struct denali_controller *denali = pci_get_drvdata(dev); denali_remove(denali); iounmap(denali->reg); -- cgit v1.2.3 From 212e4969359297e44c8ed879d56ab077f9a52454 Mon Sep 17 00:00:00 2001 From: Maxime Ripard Date: Wed, 3 Apr 2019 09:48:04 +0200 Subject: dt-bindings: mtd: Add YAML schemas for the generic NAND options The NAND chips in MTD have a bunch of generic options that are needed in a device tree. Add a YAML schemas for those. Signed-off-by: Maxime Ripard Reviewed-by: Rob Herring Signed-off-by: Miquel Raynal --- .../devicetree/bindings/mtd/nand-controller.yaml | 143 +++++++++++++++++++++ Documentation/devicetree/bindings/mtd/nand.txt | 75 ----------- 2 files changed, 143 insertions(+), 75 deletions(-) create mode 100644 Documentation/devicetree/bindings/mtd/nand-controller.yaml delete mode 100644 Documentation/devicetree/bindings/mtd/nand.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mtd/nand-controller.yaml b/Documentation/devicetree/bindings/mtd/nand-controller.yaml new file mode 100644 index 000000000000..199ba5ac2a06 --- /dev/null +++ b/Documentation/devicetree/bindings/mtd/nand-controller.yaml @@ -0,0 +1,143 @@ +# SPDX-License-Identifier: GPL-2.0 +%YAML 1.2 +--- +$id: http://devicetree.org/schemas/mtd/nand-controller.yaml# +$schema: http://devicetree.org/meta-schemas/core.yaml# + +title: NAND Chip and NAND Controller Generic Binding + +maintainers: + - Miquel Raynal + - Richard Weinberger + +description: | + The NAND controller should be represented with its own DT node, and + all NAND chips attached to this controller should be defined as + children nodes of the NAND controller. This representation should be + enforced even for simple controllers supporting only one chip. + + The ECC strength and ECC step size properties define the user + desires in terms of correction capability of a controller. Together, + they request the ECC engine to correct {strength} bit errors per + {size} bytes. + + The interpretation of these parameters is implementation-defined, so + not all implementations must support all possible + combinations. However, implementations are encouraged to further + specify the value(s) they support. + +properties: + $nodename: + pattern: "^nand-controller(@.*)?" + + "#address-cells": + const: 1 + + "#size-cells": + const: 0 + + ranges: true + +patternProperties: + "^nand@[a-f0-9]$": + properties: + reg: + description: + Contains the native Ready/Busy IDs. + + nand-ecc-mode: + allOf: + - $ref: /schemas/types.yaml#/definitions/string + - enum: [ none, soft, hw, hw_syndrome, hw_oob_first, on-die ] + description: + Desired ECC engine, either hardware (most of the time + embedded in the NAND controller) or software correction + (Linux will handle the calculations). soft_bch is deprecated + and should be replaced by soft and nand-ecc-algo. + + nand-ecc-algo: + allOf: + - $ref: /schemas/types.yaml#/definitions/string + - enum: [ hamming, bch, rs ] + description: + Desired ECC algorithm. + + nand-bus-width: + allOf: + - $ref: /schemas/types.yaml#/definitions/uint32 + - enum: [ 8, 16 ] + - default: 8 + description: + Bus width to the NAND chip + + nand-on-flash-bbt: + $ref: /schemas/types.yaml#/definitions/flag + description: + With this property, the OS will search the device for a Bad + Block Table (BBT). If not found, it will create one, reserve + a few blocks at the end of the device to store it and update + it as the device ages. Otherwise, the out-of-band area of a + few pages of all the blocks will be scanned at boot time to + find Bad Block Markers (BBM). These markers will help to + build a volatile BBT in RAM. + + nand-ecc-strength: + allOf: + - $ref: /schemas/types.yaml#/definitions/uint32 + - minimum: 1 + description: + Maximum number of bits that can be corrected per ECC step. + + nand-ecc-step-size: + allOf: + - $ref: /schemas/types.yaml#/definitions/uint32 + - minimum: 1 + description: + Number of data bytes covered by a single ECC step. + + nand-ecc-maximize: + $ref: /schemas/types.yaml#/definitions/flag + description: + Whether or not the ECC strength should be maximized. The + maximum ECC strength is both controller and chip + dependent. The ECC engine has to select the ECC config + providing the best strength and taking the OOB area size + constraint into account. This is particularly useful when + only the in-band area is used by the upper layers, and you + want to make your NAND as reliable as possible. + + nand-is-boot-medium: + $ref: /schemas/types.yaml#/definitions/flag + description: + Whether or not the NAND chip is a boot medium. Drivers might + use this information to select ECC algorithms supported by + the boot ROM or similar restrictions. + + nand-rb: + $ref: /schemas/types.yaml#/definitions/uint32-array + description: + Contains the native Ready/Busy IDs. + + required: + - reg + +required: + - "#address-cells" + - "#size-cells" + +examples: + - | + nand-controller { + #address-cells = <1>; + #size-cells = <0>; + + /* controller specific properties */ + + nand@0 { + reg = <0>; + nand-ecc-mode = "soft"; + nand-ecc-algo = "bch"; + + /* controller specific properties */ + }; + }; diff --git a/Documentation/devicetree/bindings/mtd/nand.txt b/Documentation/devicetree/bindings/mtd/nand.txt deleted file mode 100644 index e949c778e983..000000000000 --- a/Documentation/devicetree/bindings/mtd/nand.txt +++ /dev/null @@ -1,75 +0,0 @@ -* NAND chip and NAND controller generic binding - -NAND controller/NAND chip representation: - -The NAND controller should be represented with its own DT node, and all -NAND chips attached to this controller should be defined as children nodes -of the NAND controller. This representation should be enforced even for -simple controllers supporting only one chip. - -Mandatory NAND controller properties: -- #address-cells: depends on your controller. Should at least be 1 to - encode the CS line id. -- #size-cells: depends on your controller. Put zero unless you need a - mapping between CS lines and dedicated memory regions - -Optional NAND controller properties -- ranges: only needed if you need to define a mapping between CS lines and - memory regions - -Optional NAND chip properties: - -- nand-ecc-mode : String, operation mode of the NAND ecc mode. - Supported values are: "none", "soft", "hw", "hw_syndrome", - "hw_oob_first", "on-die". - Deprecated values: - "soft_bch": use "soft" and nand-ecc-algo instead -- nand-ecc-algo: string, algorithm of NAND ECC. - Valid values are: "hamming", "bch", "rs". -- nand-bus-width : 8 or 16 bus width if not present 8 -- nand-on-flash-bbt: boolean to enable on flash bbt option if not present false - -- nand-ecc-strength: integer representing the number of bits to correct - per ECC step. - -- nand-ecc-step-size: integer representing the number of data bytes - that are covered by a single ECC step. - -- nand-ecc-maximize: boolean used to specify that you want to maximize ECC - strength. The maximum ECC strength is both controller and - chip dependent. The controller side has to select the ECC - config providing the best strength and taking the OOB area - size constraint into account. - This is particularly useful when only the in-band area is - used by the upper layers, and you want to make your NAND - as reliable as possible. -- nand-is-boot-medium: Whether the NAND chip is a boot medium. Drivers might use - this information to select ECC algorithms supported by - the boot ROM or similar restrictions. - -- nand-rb: shall contain the native Ready/Busy ids. - -The ECC strength and ECC step size properties define the correction capability -of a controller. Together, they say a controller can correct "{strength} bit -errors per {size} bytes". - -The interpretation of these parameters is implementation-defined, so not all -implementations must support all possible combinations. However, implementations -are encouraged to further specify the value(s) they support. - -Example: - - nand-controller { - #address-cells = <1>; - #size-cells = <0>; - - /* controller specific properties */ - - nand@0 { - reg = <0>; - nand-ecc-mode = "soft"; - nand-ecc-algo = "bch"; - - /* controller specific properties */ - }; - }; -- cgit v1.2.3 From a3c5a11dc82255c126a749d1e82d5de6605e9b26 Mon Sep 17 00:00:00 2001 From: Maxime Ripard Date: Wed, 3 Apr 2019 09:48:05 +0200 Subject: dt-bindings: mtd: sunxi-nand: Add YAML schemas Switch the DT binding to a YAML schema to enable the DT validation. Reviewed-by: Rob Herring Signed-off-by: Maxime Ripard Signed-off-by: Miquel Raynal --- .../bindings/mtd/allwinner,sun4i-a10-nand.yaml | 96 ++++++++++++++++++++++ .../devicetree/bindings/mtd/sunxi-nand.txt | 48 ----------- 2 files changed, 96 insertions(+), 48 deletions(-) create mode 100644 Documentation/devicetree/bindings/mtd/allwinner,sun4i-a10-nand.yaml delete mode 100644 Documentation/devicetree/bindings/mtd/sunxi-nand.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mtd/allwinner,sun4i-a10-nand.yaml b/Documentation/devicetree/bindings/mtd/allwinner,sun4i-a10-nand.yaml new file mode 100644 index 000000000000..d5834b197e96 --- /dev/null +++ b/Documentation/devicetree/bindings/mtd/allwinner,sun4i-a10-nand.yaml @@ -0,0 +1,96 @@ +# SPDX-License-Identifier: GPL-2.0 +%YAML 1.2 +--- +$id: http://devicetree.org/schemas/mtd/allwinner,sun4i-a10-nand.yaml# +$schema: http://devicetree.org/meta-schemas/core.yaml# + +title: Allwinner A10 NAND Controller Device Tree Bindings + +allOf: + - $ref: "nand-controller.yaml" + +maintainers: + - Chen-Yu Tsai + - Maxime Ripard + +properties: + "#address-cells": true + "#size-cells": true + + compatible: + const: allwinner,sun4i-a10-nand + + reg: + maxItems: 1 + + interrupts: + maxItems: 1 + + clocks: + items: + - description: Bus Clock + - description: Module Clock + + clock-names: + items: + - const: ahb + - const: mod + + resets: + maxItems: 1 + + reset-names: + const: ahb + + dmas: + maxItems: 1 + + dma-names: + const: rxtx + + pinctrl-names: true + +patternProperties: + "^pinctrl-[0-9]+$": true + + "^nand@[a-f0-9]+$": + properties: + reg: + maxItems: 1 + minimum: 0 + maximum: 7 + + nand-ecc-mode: true + + nand-ecc-algo: + const: bch + + nand-ecc-step-size: + enum: [ 512, 1024 ] + + nand-ecc-strength: + maximum: 80 + + allwinner,rb: + description: + Contains the native Ready/Busy IDs. + allOf: + - $ref: /schemas/types.yaml#/definitions/uint32-array + - minItems: 1 + maxItems: 2 + items: + minimum: 0 + maximum: 1 + + additionalProperties: false + +required: + - compatible + - reg + - interrupts + - clocks + - clock-names + +additionalProperties: false + +... diff --git a/Documentation/devicetree/bindings/mtd/sunxi-nand.txt b/Documentation/devicetree/bindings/mtd/sunxi-nand.txt deleted file mode 100644 index dcd5a5d80dc0..000000000000 --- a/Documentation/devicetree/bindings/mtd/sunxi-nand.txt +++ /dev/null @@ -1,48 +0,0 @@ -Allwinner NAND Flash Controller (NFC) - -Required properties: -- compatible : "allwinner,sun4i-a10-nand". -- reg : shall contain registers location and length for data and reg. -- interrupts : shall define the nand controller interrupt. -- #address-cells: shall be set to 1. Encode the nand CS. -- #size-cells : shall be set to 0. -- clocks : shall reference nand controller clocks. -- clock-names : nand controller internal clock names. Shall contain : - * "ahb" : AHB gating clock - * "mod" : nand controller clock - -Optional properties: -- dmas : shall reference DMA channel associated to the NAND controller. -- dma-names : shall be "rxtx". - -Optional children nodes: -Children nodes represent the available nand chips. - -Optional properties: -- reset : phandle + reset specifier pair -- reset-names : must contain "ahb" -- allwinner,rb : shall contain the native Ready/Busy ids. -- nand-ecc-mode : one of the supported ECC modes ("hw", "soft", "soft_bch" or - "none") - -see Documentation/devicetree/bindings/mtd/nand.txt for generic bindings. - - -Examples: -nfc: nand@1c03000 { - compatible = "allwinner,sun4i-a10-nand"; - reg = <0x01c03000 0x1000>; - interrupts = <0 37 1>; - clocks = <&ahb_gates 13>, <&nand_clk>; - clock-names = "ahb", "mod"; - #address-cells = <1>; - #size-cells = <0>; - pinctrl-names = "default"; - pinctrl-0 = <&nand_pins_a &nand_cs0_pins_a &nand_rb0_pins_a>; - - nand@0 { - reg = <0>; - allwinner,rb = <0>; - nand-ecc-mode = "soft_bch"; - }; -}; -- cgit v1.2.3 From aee02f82e19a5df848861e0883a394a4996b5bd4 Mon Sep 17 00:00:00 2001 From: Miquel Raynal Date: Mon, 8 Apr 2019 09:41:44 +0200 Subject: dt-bindings: mtd: sunxi: Add new compatible The A23/A33 NAND controller is slightly different than the A10+ ones, eg. DMA handling is a bit different and a few register offsets changed. Introduce a new compatible to represent this version of the IP. Also append '-controller' to the new compatible (which is required for new compatibles) as this is describing a NAND controller and not a NAND chip. Signed-off-by: Miquel Raynal --- Documentation/devicetree/bindings/mtd/allwinner,sun4i-a10-nand.yaml | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mtd/allwinner,sun4i-a10-nand.yaml b/Documentation/devicetree/bindings/mtd/allwinner,sun4i-a10-nand.yaml index d5834b197e96..fbd4da3684fc 100644 --- a/Documentation/devicetree/bindings/mtd/allwinner,sun4i-a10-nand.yaml +++ b/Documentation/devicetree/bindings/mtd/allwinner,sun4i-a10-nand.yaml @@ -18,8 +18,9 @@ properties: "#size-cells": true compatible: - const: allwinner,sun4i-a10-nand - + enum: + - allwinner,sun4i-a10-nand + - allwinner,sun8i-a23-nand-controller reg: maxItems: 1 -- cgit v1.2.3 From 13209ad0395c4de7fa48108b1dac72e341d5c089 Mon Sep 17 00:00:00 2001 From: Christian Borntraeger Date: Fri, 28 Dec 2018 09:33:35 +0100 Subject: KVM: s390: add MSA9 to cpumodel This enables stfle.155 and adds the subfunctions for KDSA. Bit 155 is added to the list of facilities that will be enabled when there is no cpu model involved as MSA9 requires no additional handling from userspace, e.g. for migration. Please note that a cpu model enabled user space can and will have the final decision on the facility bits for a guests. Signed-off-by: Christian Borntraeger Acked-by: Janosch Frank Reviewed-by: Collin Walling Reviewed-by: David Hildenbrand --- Documentation/virtual/kvm/devices/vm.txt | 3 ++- arch/s390/include/asm/cpacf.h | 1 + arch/s390/include/uapi/asm/kvm.h | 3 ++- arch/s390/kvm/kvm-s390.c | 13 +++++++++++++ arch/s390/tools/gen_facilities.c | 1 + tools/arch/s390/include/uapi/asm/kvm.h | 3 ++- 6 files changed, 21 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/devices/vm.txt b/Documentation/virtual/kvm/devices/vm.txt index 95ca68d663a4..4ffb82b02468 100644 --- a/Documentation/virtual/kvm/devices/vm.txt +++ b/Documentation/virtual/kvm/devices/vm.txt @@ -141,7 +141,8 @@ struct kvm_s390_vm_cpu_subfunc { u8 pcc[16]; # valid with Message-Security-Assist-Extension 4 u8 ppno[16]; # valid with Message-Security-Assist-Extension 5 u8 kma[16]; # valid with Message-Security-Assist-Extension 8 - u8 reserved[1808]; # reserved for future instructions + u8 kdsa[16]; # valid with Message-Security-Assist-Extension 9 + u8 reserved[1792]; # reserved for future instructions }; Parameters: address of a buffer to load the subfunction blocks from. diff --git a/arch/s390/include/asm/cpacf.h b/arch/s390/include/asm/cpacf.h index 3cc52e37b4b2..ce2770743cc5 100644 --- a/arch/s390/include/asm/cpacf.h +++ b/arch/s390/include/asm/cpacf.h @@ -28,6 +28,7 @@ #define CPACF_KMCTR 0xb92d /* MSA4 */ #define CPACF_PRNO 0xb93c /* MSA5 */ #define CPACF_KMA 0xb929 /* MSA8 */ +#define CPACF_KDSA 0xb93a /* MSA9 */ /* * En/decryption modifier bits diff --git a/arch/s390/include/uapi/asm/kvm.h b/arch/s390/include/uapi/asm/kvm.h index 16511d97e8dc..09652eabe769 100644 --- a/arch/s390/include/uapi/asm/kvm.h +++ b/arch/s390/include/uapi/asm/kvm.h @@ -152,7 +152,8 @@ struct kvm_s390_vm_cpu_subfunc { __u8 pcc[16]; /* with MSA4 */ __u8 ppno[16]; /* with MSA5 */ __u8 kma[16]; /* with MSA8 */ - __u8 reserved[1808]; + __u8 kdsa[16]; /* with MSA9 */ + __u8 reserved[1792]; }; /* kvm attributes for crypto */ diff --git a/arch/s390/kvm/kvm-s390.c b/arch/s390/kvm/kvm-s390.c index d3f3e63bb164..0dad61ccde3d 100644 --- a/arch/s390/kvm/kvm-s390.c +++ b/arch/s390/kvm/kvm-s390.c @@ -368,6 +368,10 @@ static void kvm_s390_cpu_feat_init(void) __cpacf_query(CPACF_KMA, (cpacf_mask_t *) kvm_s390_available_subfunc.kma); + if (test_facility(155)) /* MSA9 */ + __cpacf_query(CPACF_KDSA, (cpacf_mask_t *) + kvm_s390_available_subfunc.kdsa); + if (MACHINE_HAS_ESOP) allow_cpu_feat(KVM_S390_VM_CPU_FEAT_ESOP); /* @@ -1331,6 +1335,9 @@ static int kvm_s390_set_processor_subfunc(struct kvm *kvm, VM_EVENT(kvm, 3, "SET: guest KMA subfunc 0x%16.16lx.%16.16lx", ((unsigned long *) &kvm->arch.model.subfuncs.kma)[0], ((unsigned long *) &kvm->arch.model.subfuncs.kma)[1]); + VM_EVENT(kvm, 3, "SET: guest KDSA subfunc 0x%16.16lx.%16.16lx", + ((unsigned long *) &kvm->arch.model.subfuncs.kdsa)[0], + ((unsigned long *) &kvm->arch.model.subfuncs.kdsa)[1]); return 0; } @@ -1499,6 +1506,9 @@ static int kvm_s390_get_processor_subfunc(struct kvm *kvm, VM_EVENT(kvm, 3, "GET: guest KMA subfunc 0x%16.16lx.%16.16lx", ((unsigned long *) &kvm->arch.model.subfuncs.kma)[0], ((unsigned long *) &kvm->arch.model.subfuncs.kma)[1]); + VM_EVENT(kvm, 3, "GET: guest KDSA subfunc 0x%16.16lx.%16.16lx", + ((unsigned long *) &kvm->arch.model.subfuncs.kdsa)[0], + ((unsigned long *) &kvm->arch.model.subfuncs.kdsa)[1]); return 0; } @@ -1554,6 +1564,9 @@ static int kvm_s390_get_machine_subfunc(struct kvm *kvm, VM_EVENT(kvm, 3, "GET: host KMA subfunc 0x%16.16lx.%16.16lx", ((unsigned long *) &kvm_s390_available_subfunc.kma)[0], ((unsigned long *) &kvm_s390_available_subfunc.kma)[1]); + VM_EVENT(kvm, 3, "GET: host KDSA subfunc 0x%16.16lx.%16.16lx", + ((unsigned long *) &kvm_s390_available_subfunc.kdsa)[0], + ((unsigned long *) &kvm_s390_available_subfunc.kdsa)[1]); return 0; } diff --git a/arch/s390/tools/gen_facilities.c b/arch/s390/tools/gen_facilities.c index fd788e0f2e5b..e952cb3b75b2 100644 --- a/arch/s390/tools/gen_facilities.c +++ b/arch/s390/tools/gen_facilities.c @@ -93,6 +93,7 @@ static struct facility_def facility_defs[] = { 131, /* enhanced-SOP 2 and side-effect */ 139, /* multiple epoch facility */ 146, /* msa extension 8 */ + 155, /* msa extension 9 */ -1 /* END */ } }, diff --git a/tools/arch/s390/include/uapi/asm/kvm.h b/tools/arch/s390/include/uapi/asm/kvm.h index 16511d97e8dc..09652eabe769 100644 --- a/tools/arch/s390/include/uapi/asm/kvm.h +++ b/tools/arch/s390/include/uapi/asm/kvm.h @@ -152,7 +152,8 @@ struct kvm_s390_vm_cpu_subfunc { __u8 pcc[16]; /* with MSA4 */ __u8 ppno[16]; /* with MSA5 */ __u8 kma[16]; /* with MSA8 */ - __u8 reserved[1808]; + __u8 kdsa[16]; /* with MSA9 */ + __u8 reserved[1792]; }; /* kvm attributes for crypto */ -- cgit v1.2.3 From 5c14068f87d04adc73ba3f41c2a303d3c3d1fa12 Mon Sep 17 00:00:00 2001 From: Josh Poimboeuf Date: Wed, 17 Apr 2019 16:39:02 -0500 Subject: x86/speculation/mds: Add 'mitigations=' support for MDS Add MDS to the new 'mitigations=' cmdline option. Signed-off-by: Josh Poimboeuf Signed-off-by: Thomas Gleixner --- Documentation/admin-guide/kernel-parameters.txt | 2 ++ arch/x86/kernel/cpu/bugs.c | 5 +++-- 2 files changed, 5 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt index 9aa3543a8723..18cad2b0392a 100644 --- a/Documentation/admin-guide/kernel-parameters.txt +++ b/Documentation/admin-guide/kernel-parameters.txt @@ -2556,6 +2556,7 @@ spectre_v2_user=off [X86] spec_store_bypass_disable=off [X86,PPC] l1tf=off [X86] + mds=off [X86] auto (default) Mitigate all CPU vulnerabilities, but leave SMT @@ -2570,6 +2571,7 @@ if needed. This is for users who always want to be fully mitigated, even if it means losing SMT. Equivalent to: l1tf=flush,nosmt [X86] + mds=full,nosmt [X86] mminit_loglevel= [KNL] When CONFIG_DEBUG_MEMORY_INIT is set, this diff --git a/arch/x86/kernel/cpu/bugs.c b/arch/x86/kernel/cpu/bugs.c index 3c5c3c3ba734..667c273a66d7 100644 --- a/arch/x86/kernel/cpu/bugs.c +++ b/arch/x86/kernel/cpu/bugs.c @@ -233,7 +233,7 @@ static const char * const mds_strings[] = { static void __init mds_select_mitigation(void) { - if (!boot_cpu_has_bug(X86_BUG_MDS)) { + if (!boot_cpu_has_bug(X86_BUG_MDS) || cpu_mitigations_off()) { mds_mitigation = MDS_MITIGATION_OFF; return; } @@ -244,7 +244,8 @@ static void __init mds_select_mitigation(void) static_branch_enable(&mds_user_clear); - if (mds_nosmt && !boot_cpu_has(X86_BUG_MSBDS_ONLY)) + if (!boot_cpu_has(X86_BUG_MSBDS_ONLY) && + (mds_nosmt || cpu_mitigations_auto_nosmt())) cpu_smt_disable(false); } -- cgit v1.2.3 From 023912dbb80f5faf7a028aad6562774472d82a5a Mon Sep 17 00:00:00 2001 From: Nicolin Chen Date: Wed, 17 Apr 2019 16:12:10 -0700 Subject: hwmon: (ina3221) Add voltage conversion time settings The CONFIG register has two 3-bit fields for conversion time settings of Bus-voltage and Shunt-voltage, respectively. The conversion settings, along with averaging mode, allow users to optimize available timing requirement. This patch adds an 'update_interval' sysfs node through the hwmon_chip_info of hwmon core. It reflects a total hardware conversion time: samples * channels * (Bus + Shunt conversion times) Though INA3221 supports different conversion time setups for Bus and Shunt voltages, this patch only adds the support of a unified setting for both conversion times, by dividing the conversion time into two equal values. Signed-off-by: Nicolin Chen [groeck: .rst related formatting changes in documentation] Signed-off-by: Guenter Roeck --- Documentation/hwmon/ina3221.rst | 13 +++++++++ drivers/hwmon/ina3221.c | 58 +++++++++++++++++++++++++++++++++++------ 2 files changed, 63 insertions(+), 8 deletions(-) (limited to 'Documentation') diff --git a/Documentation/hwmon/ina3221.rst b/Documentation/hwmon/ina3221.rst index 1e34abb38b59..f6007ae8f4e2 100644 --- a/Documentation/hwmon/ina3221.rst +++ b/Documentation/hwmon/ina3221.rst @@ -46,4 +46,17 @@ samples Number of samples using in the averaging mode. Supports the list of number of samples: 1, 4, 16, 64, 128, 256, 512, 1024 + +update_interval Data conversion time in millisecond, following: + + update_interval = C x S x (BC + SC) + + * C: number of enabled channels + * S: number of samples + * BC: bus-voltage conversion time in millisecond + * SC: shunt-voltage conversion time in millisecond + + Affects both Bus- and Shunt-voltage conversion time. + Note that setting update_interval to 0ms sets both BC + and SC to 140 us (minimum conversion time). ======================= ======================================================= diff --git a/drivers/hwmon/ina3221.c b/drivers/hwmon/ina3221.c index 62040aac653c..e0637fed9585 100644 --- a/drivers/hwmon/ina3221.c +++ b/drivers/hwmon/ina3221.c @@ -144,19 +144,37 @@ static const int ina3221_avg_samples[] = { 1, 4, 16, 64, 128, 256, 512, 1024, }; -static inline int ina3221_wait_for_data(struct ina3221_data *ina) +/* Converting update_interval in msec to conversion time in usec */ +static inline u32 ina3221_interval_ms_to_conv_time(u16 config, int interval) +{ + u32 channels = hweight16(config & INA3221_CONFIG_CHs_EN_MASK); + u32 samples_idx = INA3221_CONFIG_AVG(config); + u32 samples = ina3221_avg_samples[samples_idx]; + + /* Bisect the result to Bus and Shunt conversion times */ + return DIV_ROUND_CLOSEST(interval * 1000 / 2, channels * samples); +} + +/* Converting CONFIG register value to update_interval in usec */ +static inline u32 ina3221_reg_to_interval_us(u16 config) { - u32 channels = hweight16(ina->reg_config & INA3221_CONFIG_CHs_EN_MASK); - u32 vbus_ct_idx = INA3221_CONFIG_VBUS_CT(ina->reg_config); - u32 vsh_ct_idx = INA3221_CONFIG_VSH_CT(ina->reg_config); - u32 samples_idx = INA3221_CONFIG_AVG(ina->reg_config); + u32 channels = hweight16(config & INA3221_CONFIG_CHs_EN_MASK); + u32 vbus_ct_idx = INA3221_CONFIG_VBUS_CT(config); + u32 vsh_ct_idx = INA3221_CONFIG_VSH_CT(config); + u32 samples_idx = INA3221_CONFIG_AVG(config); u32 samples = ina3221_avg_samples[samples_idx]; u32 vbus_ct = ina3221_conv_time[vbus_ct_idx]; u32 vsh_ct = ina3221_conv_time[vsh_ct_idx]; - u32 wait, cvrf; /* Calculate total conversion time */ - wait = channels * (vbus_ct + vsh_ct) * samples; + return channels * (vbus_ct + vsh_ct) * samples; +} + +static inline int ina3221_wait_for_data(struct ina3221_data *ina) +{ + u32 wait, cvrf; + + wait = ina3221_reg_to_interval_us(ina->reg_config); /* Polling the CVRF bit to make sure read data is ready */ return regmap_field_read_poll_timeout(ina->fields[F_CVRF], @@ -197,6 +215,11 @@ static int ina3221_read_chip(struct device *dev, u32 attr, long *val) regval = INA3221_CONFIG_AVG(ina->reg_config); *val = ina3221_avg_samples[regval]; return 0; + case hwmon_chip_update_interval: + /* Return in msec */ + *val = ina3221_reg_to_interval_us(ina->reg_config); + *val = DIV_ROUND_CLOSEST(*val, 1000); + return 0; default: return -EOPNOTSUPP; } @@ -322,6 +345,23 @@ static int ina3221_write_chip(struct device *dev, u32 attr, long val) if (ret) return ret; + /* Update reg_config accordingly */ + ina->reg_config = tmp; + return 0; + case hwmon_chip_update_interval: + tmp = ina3221_interval_ms_to_conv_time(ina->reg_config, val); + idx = find_closest(tmp, ina3221_conv_time, + ARRAY_SIZE(ina3221_conv_time)); + + /* Update Bus and Shunt voltage conversion times */ + tmp = INA3221_CONFIG_VBUS_CT_MASK | INA3221_CONFIG_VSH_CT_MASK; + tmp = (ina->reg_config & ~tmp) | + (idx << INA3221_CONFIG_VBUS_CT_SHIFT) | + (idx << INA3221_CONFIG_VSH_CT_SHIFT); + ret = regmap_write(ina->regmap, INA3221_CONFIG, tmp); + if (ret) + return ret; + /* Update reg_config accordingly */ ina->reg_config = tmp; return 0; @@ -483,6 +523,7 @@ static umode_t ina3221_is_visible(const void *drvdata, case hwmon_chip: switch (attr) { case hwmon_chip_samples: + case hwmon_chip_update_interval: return 0644; default: return 0; @@ -528,7 +569,8 @@ static umode_t ina3221_is_visible(const void *drvdata, static const struct hwmon_channel_info *ina3221_info[] = { HWMON_CHANNEL_INFO(chip, - HWMON_C_SAMPLES), + HWMON_C_SAMPLES, + HWMON_C_UPDATE_INTERVAL), HWMON_CHANNEL_INFO(in, /* 0: dummy, skipped in is_visible */ HWMON_I_INPUT, -- cgit v1.2.3 From b779ceadf548b2fc13ce6694d9a480d6a4330b35 Mon Sep 17 00:00:00 2001 From: Colin Ian King Date: Thu, 18 Apr 2019 11:15:02 +0100 Subject: char/ipmi: fix spelling mistake "receieved_messages" -> "received_messages" There is a spelling mistake in the documentation. Fix it. Signed-off-by: Colin Ian King Message-Id: <20190418101502.9748-1-colin.king@canonical.com> Reviewed-by: Mukesh Ojha Signed-off-by: Corey Minyard --- Documentation/ABI/testing/sysfs-devices-platform-ipmi | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/ABI/testing/sysfs-devices-platform-ipmi b/Documentation/ABI/testing/sysfs-devices-platform-ipmi index 2a781e7513b7..afb5db856e1c 100644 --- a/Documentation/ABI/testing/sysfs-devices-platform-ipmi +++ b/Documentation/ABI/testing/sysfs-devices-platform-ipmi @@ -212,7 +212,7 @@ Description: Messages may be broken into parts if they are long. - receieved_messages: (RO) Number of message responses + received_messages: (RO) Number of message responses received. received_message_parts: (RO) Number of message fragments -- cgit v1.2.3 From 4bd774e57b29f5bbf296d1daf69cc761e1e75fa8 Mon Sep 17 00:00:00 2001 From: Dave Martin Date: Thu, 11 Apr 2019 17:09:59 +0100 Subject: KVM: arm64/sve: Simplify KVM_REG_ARM64_SVE_VLS array sizing A complicated DIV_ROUND_UP() expression is currently written out explicitly in multiple places in order to specify the size of the bitmap exchanged with userspace to represent the value of the KVM_REG_ARM64_SVE_VLS pseudo-register. Userspace currently has no direct way to work this out either: for documentation purposes, the size is just quoted as 8 u64s. To make this more intuitive, this patch replaces these with a single define, which is also exported to userspace as KVM_ARM64_SVE_VLS_WORDS. Since the number of words in a bitmap is just the index of the last word used + 1, this patch expresses the bound that way instead. This should make it clearer what is being expressed. For userspace convenience, the minimum and maximum possible vector lengths relevant to the KVM ABI are exposed to UAPI as KVM_ARM64_SVE_VQ_MIN, KVM_ARM64_SVE_VQ_MAX. Since the only direct use for these at present is manipulation of KVM_REG_ARM64_SVE_VLS, no corresponding _VL_ macros are defined. They could be added later if a need arises. Since use of DIV_ROUND_UP() was the only reason for including in guest.c, this patch also removes that #include. Suggested-by: Andrew Jones Signed-off-by: Dave Martin Reviewed-by: Andrew Jones Signed-off-by: Marc Zyngier --- Documentation/virtual/kvm/api.txt | 10 ++++++---- arch/arm64/include/uapi/asm/kvm.h | 5 +++++ arch/arm64/kvm/guest.c | 7 +++---- 3 files changed, 14 insertions(+), 8 deletions(-) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/api.txt b/Documentation/virtual/kvm/api.txt index 68509dee23e8..03df379a02b0 100644 --- a/Documentation/virtual/kvm/api.txt +++ b/Documentation/virtual/kvm/api.txt @@ -2171,13 +2171,15 @@ and KVM_ARM_VCPU_FINALIZE for more information about this procedure. KVM_REG_ARM64_SVE_VLS is a pseudo-register that allows the set of vector lengths supported by the vcpu to be discovered and configured by userspace. When transferred to or from user memory via KVM_GET_ONE_REG -or KVM_SET_ONE_REG, the value of this register is of type __u64[8], and -encodes the set of vector lengths as follows: +or KVM_SET_ONE_REG, the value of this register is of type +__u64[KVM_ARM64_SVE_VLS_WORDS], and encodes the set of vector lengths as +follows: -__u64 vector_lengths[8]; +__u64 vector_lengths[KVM_ARM64_SVE_VLS_WORDS]; if (vq >= SVE_VQ_MIN && vq <= SVE_VQ_MAX && - ((vector_lengths[(vq - 1) / 64] >> ((vq - 1) % 64)) & 1)) + ((vector_lengths[(vq - KVM_ARM64_SVE_VQ_MIN) / 64] >> + ((vq - KVM_ARM64_SVE_VQ_MIN) % 64)) & 1)) /* Vector length vq * 16 bytes supported */ else /* Vector length vq * 16 bytes not supported */ diff --git a/arch/arm64/include/uapi/asm/kvm.h b/arch/arm64/include/uapi/asm/kvm.h index 2a04ef015469..edd2db8e5160 100644 --- a/arch/arm64/include/uapi/asm/kvm.h +++ b/arch/arm64/include/uapi/asm/kvm.h @@ -258,9 +258,14 @@ struct kvm_vcpu_events { KVM_REG_SIZE_U256 | \ ((i) & (KVM_ARM64_SVE_MAX_SLICES - 1))) +#define KVM_ARM64_SVE_VQ_MIN __SVE_VQ_MIN +#define KVM_ARM64_SVE_VQ_MAX __SVE_VQ_MAX + /* Vector lengths pseudo-register: */ #define KVM_REG_ARM64_SVE_VLS (KVM_REG_ARM64 | KVM_REG_ARM64_SVE | \ KVM_REG_SIZE_U512 | 0xffff) +#define KVM_ARM64_SVE_VLS_WORDS \ + ((KVM_ARM64_SVE_VQ_MAX - KVM_ARM64_SVE_VQ_MIN) / 64 + 1) /* Device Control API: ARM VGIC */ #define KVM_DEV_ARM_VGIC_GRP_ADDR 0 diff --git a/arch/arm64/kvm/guest.c b/arch/arm64/kvm/guest.c index 73044e3f8706..5bb909c3ff7c 100644 --- a/arch/arm64/kvm/guest.c +++ b/arch/arm64/kvm/guest.c @@ -23,7 +23,6 @@ #include #include #include -#include #include #include #include @@ -210,7 +209,7 @@ out: #define vq_mask(vq) ((u64)1 << ((vq) - SVE_VQ_MIN) % 64) static bool vq_present( - const u64 (*const vqs)[DIV_ROUND_UP(SVE_VQ_MAX - SVE_VQ_MIN + 1, 64)], + const u64 (*const vqs)[KVM_ARM64_SVE_VLS_WORDS], unsigned int vq) { return (*vqs)[vq_word(vq)] & vq_mask(vq); @@ -219,7 +218,7 @@ static bool vq_present( static int get_sve_vls(struct kvm_vcpu *vcpu, const struct kvm_one_reg *reg) { unsigned int max_vq, vq; - u64 vqs[DIV_ROUND_UP(SVE_VQ_MAX - SVE_VQ_MIN + 1, 64)]; + u64 vqs[KVM_ARM64_SVE_VLS_WORDS]; if (!vcpu_has_sve(vcpu)) return -ENOENT; @@ -243,7 +242,7 @@ static int get_sve_vls(struct kvm_vcpu *vcpu, const struct kvm_one_reg *reg) static int set_sve_vls(struct kvm_vcpu *vcpu, const struct kvm_one_reg *reg) { unsigned int max_vq, vq; - u64 vqs[DIV_ROUND_UP(SVE_VQ_MAX - SVE_VQ_MIN + 1, 64)]; + u64 vqs[KVM_ARM64_SVE_VLS_WORDS]; if (!vcpu_has_sve(vcpu)) return -ENOENT; -- cgit v1.2.3 From 9df2d660c7f37aed7244ec0b920c0749dbb69167 Mon Sep 17 00:00:00 2001 From: Dave Martin Date: Fri, 12 Apr 2019 13:28:05 +0100 Subject: KVM: Clarify capability requirements for KVM_ARM_VCPU_FINALIZE Userspace is only supposed to use KVM_ARM_VCPU_FINALIZE when there is some vcpu feature that can actually be finalized. This means that documenting KVM_ARM_VCPU_FINALIZE as available or not depending on the capabilities present is not helpful. This patch amends the documentation to describe availability in terms of which capability is required for each finalizable feature instead. In any case, userspace sees the same error (EINVAL) regardless of whether the given feature is not present or KVM_ARM_VCPU_FINALIZE is not implemented at all. No functional change. Suggested-by: Andrew Jones Signed-off-by: Dave Martin Reviewed-by: Andrew Jones Signed-off-by: Marc Zyngier --- Documentation/virtual/kvm/api.txt | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/api.txt b/Documentation/virtual/kvm/api.txt index 03df379a02b0..5519df0d3ed0 100644 --- a/Documentation/virtual/kvm/api.txt +++ b/Documentation/virtual/kvm/api.txt @@ -3999,17 +3999,16 @@ userspace should not expect to get any particular value there. 4.119 KVM_ARM_VCPU_FINALIZE -Capability: KVM_CAP_ARM_SVE Architectures: arm, arm64 Type: vcpu ioctl Parameters: int feature (in) Returns: 0 on success, -1 on error Errors: EPERM: feature not enabled, needs configuration, or already finalized - EINVAL: unknown feature + EINVAL: feature unknown or not present Recognised values for feature: - arm64 KVM_ARM_VCPU_SVE + arm64 KVM_ARM_VCPU_SVE (requires KVM_CAP_ARM_SVE) Finalizes the configuration of the specified vcpu feature. -- cgit v1.2.3 From fe365b4ea6c0df3eb44d636c32c5210ae1e58364 Mon Sep 17 00:00:00 2001 From: Dave Martin Date: Fri, 12 Apr 2019 12:59:47 +0100 Subject: KVM: Clarify KVM_{SET,GET}_ONE_REG error code documentation The current error code documentation for KVM_GET_ONE_REG and KVM_SET_ONE_REG could be read as implying that all architectures implement these error codes, or that KVM guarantees which error code is returned in a particular situation. Because this is not really the case, this patch waters down the documentation explicitly to remove such guarantees. EPERM is marked as arm64-specific, since for now arm64 really is the only architecture that yields this error code for the finalization-required case. Keeping this as a distinct error code is useful however for debugging due to the statefulness of the API in this instance. No functional change. Suggested-by: Andrew Jones Fixes: 395f562f2b4c ("KVM: Document errors for KVM_GET_ONE_REG and KVM_SET_ONE_REG") Fixes: 50036ad06b7f ("KVM: arm64/sve: Document KVM API extensions for SVE") Signed-off-by: Dave Martin Reviewed-by: Andrew Jones Signed-off-by: Marc Zyngier --- Documentation/virtual/kvm/api.txt | 14 +++++++++----- 1 file changed, 9 insertions(+), 5 deletions(-) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/api.txt b/Documentation/virtual/kvm/api.txt index 5519df0d3ed0..818ac97fdabc 100644 --- a/Documentation/virtual/kvm/api.txt +++ b/Documentation/virtual/kvm/api.txt @@ -1873,8 +1873,10 @@ Parameters: struct kvm_one_reg (in) Returns: 0 on success, negative value on failure Errors:  ENOENT:   no such register -  EPERM:    register access forbidden for architecture-dependent reasons -  EINVAL:   other errors, such as bad size encoding for a known register +  EINVAL:   invalid register ID, or no such register +  EPERM:    (arm64) register access not allowed before vcpu finalization +(These error codes are indicative only: do not rely on a specific error +code being returned in a specific situation.) struct kvm_one_reg { __u64 id; @@ -2260,10 +2262,12 @@ Architectures: all Type: vcpu ioctl Parameters: struct kvm_one_reg (in and out) Returns: 0 on success, negative value on failure -Errors: +Errors include:  ENOENT:   no such register -  EPERM:    register access forbidden for architecture-dependent reasons -  EINVAL:   other errors, such as bad size encoding for a known register +  EINVAL:   invalid register ID, or no such register +  EPERM:    (arm64) register access not allowed before vcpu finalization +(These error codes are indicative only: do not rely on a specific error +code being returned in a specific situation.) This ioctl allows to receive the value of a single register implemented in a vcpu. The register to read is indicated by the "id" field of the -- cgit v1.2.3 From 43b8e1f08938c0fd3b8924e846dba89863badc2f Mon Sep 17 00:00:00 2001 From: Dave Martin Date: Fri, 12 Apr 2019 13:25:38 +0100 Subject: KVM: arm64: Clarify access behaviour for out-of-range SVE register slice IDs The existing documentation for which SVE register slice IDs are considered out-of-range, and what happens when userspace tries to access them, is cryptic. This patch rewords the text with the aim of making it a bit easier to understand. No functional change. Suggested-by: Andrew Jones Signed-off-by: Dave Martin Reviewed-by: Andrew Jones Signed-off-by: Marc Zyngier --- Documentation/virtual/kvm/api.txt | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/api.txt b/Documentation/virtual/kvm/api.txt index 818ac97fdabc..e410a9f0f0d4 100644 --- a/Documentation/virtual/kvm/api.txt +++ b/Documentation/virtual/kvm/api.txt @@ -2159,8 +2159,9 @@ arm64 SVE registers have the following bit patterns: 0x6050 0000 0015 060 FFR bits[256*slice + 255 : 256*slice] 0x6060 0000 0015 ffff KVM_REG_ARM64_SVE_VLS pseudo-register -Access to slices beyond the maximum vector length configured for the -vcpu (i.e., where 16 * slice >= max_vq (**)) will fail with ENOENT. +Access to register IDs where 2048 * slice >= 128 * max_vq will fail with +ENOENT. max_vq is the vcpu's maximum supported vector length in 128-bit +quadwords: see (**) below. These registers are only accessible on vcpus for which SVE is enabled. See KVM_ARM_VCPU_INIT for details. -- cgit v1.2.3 From 29c6584f333149157c7ec72aa5dca18aa9253e10 Mon Sep 17 00:00:00 2001 From: Lucas Stach Date: Thu, 4 Apr 2019 18:41:47 +0200 Subject: dt-bindings: phy-imx8mq-usb: add optional vbus supply regulator Add a vbus supply regulator phandle, so the PHY can enable the VBUS voltage rail when powering up. Signed-off-by: Lucas Stach Signed-off-by: Kishon Vijay Abraham I --- Documentation/devicetree/bindings/phy/fsl,imx8mq-usb-phy.txt | 3 +++ 1 file changed, 3 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/phy/fsl,imx8mq-usb-phy.txt b/Documentation/devicetree/bindings/phy/fsl,imx8mq-usb-phy.txt index a22e853d710c..ed47e5cd067e 100644 --- a/Documentation/devicetree/bindings/phy/fsl,imx8mq-usb-phy.txt +++ b/Documentation/devicetree/bindings/phy/fsl,imx8mq-usb-phy.txt @@ -7,6 +7,9 @@ Required properties: - clocks: phandles to the clocks for each clock listed in clock-names - clock-names: must contain "phy" +Optional properties: +- vbus-supply: A phandle to the regulator for USB VBUS. + Example: usb3_phy0: phy@381f0040 { compatible = "fsl,imx8mq-usb-phy"; -- cgit v1.2.3 From e4d0cf63f24306d1e16262482fb05a3fc69653e2 Mon Sep 17 00:00:00 2001 From: Yu Chen Date: Fri, 29 Mar 2019 12:13:57 +0800 Subject: dt-bindings: phy: Add support for HiSilicon's hi3660 USB PHY This patch adds binding documentation for supporting the hi3660 usb phy on boards like the HiKey960. Cc: Rob Herring Cc: Mark Rutland Cc: John Stultz Cc: Binghui Wang Reviewed-by: Rob Herring Signed-off-by: Yu Chen Signed-off-by: Kishon Vijay Abraham I --- .../devicetree/bindings/phy/phy-hi3660-usb3.txt | 26 ++++++++++++++++++++++ 1 file changed, 26 insertions(+) create mode 100644 Documentation/devicetree/bindings/phy/phy-hi3660-usb3.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/phy/phy-hi3660-usb3.txt b/Documentation/devicetree/bindings/phy/phy-hi3660-usb3.txt new file mode 100644 index 000000000000..e88ba7d92dcb --- /dev/null +++ b/Documentation/devicetree/bindings/phy/phy-hi3660-usb3.txt @@ -0,0 +1,26 @@ +Hisilicon hi3660 USB PHY +----------------------- + +Required properties: +- compatible: should be "hisilicon,hi3660-usb-phy" +- #phy-cells: must be 0 +- hisilicon,pericrg-syscon: phandle of syscon used to control phy. +- hisilicon,pctrl-syscon: phandle of syscon used to control phy. +- hisilicon,eye-diagram-param: parameter set for phy +Refer to phy/phy-bindings.txt for the generic PHY binding properties + +This is a subnode of usb3_otg_bc register node. + +Example: + usb3_otg_bc: usb3_otg_bc@ff200000 { + compatible = "syscon", "simple-mfd"; + reg = <0x0 0xff200000 0x0 0x1000>; + + usb-phy { + compatible = "hisilicon,hi3660-usb-phy"; + #phy-cells = <0>; + hisilicon,pericrg-syscon = <&crg_ctrl>; + hisilicon,pctrl-syscon = <&pctrl>; + hisilicon,eye-diagram-param = <0x22466e4>; + }; + }; -- cgit v1.2.3 From 513eff7fdc77bc85826c2b54b5a08ce1be2ebf5b Mon Sep 17 00:00:00 2001 From: Marc Gonzalez Date: Tue, 9 Apr 2019 14:49:00 +0200 Subject: dt-bindings: phy-qcom-qmp: Add qcom,msm8998-qmp-pcie-phy Add compatible string for QMP PCIe phy on msm8998. Signed-off-by: Marc Gonzalez Signed-off-by: Kishon Vijay Abraham I --- Documentation/devicetree/bindings/phy/qcom-qmp-phy.txt | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/phy/qcom-qmp-phy.txt b/Documentation/devicetree/bindings/phy/qcom-qmp-phy.txt index 4a78ba8b85bc..5fca57b12534 100644 --- a/Documentation/devicetree/bindings/phy/qcom-qmp-phy.txt +++ b/Documentation/devicetree/bindings/phy/qcom-qmp-phy.txt @@ -11,6 +11,7 @@ Required properties: "qcom,msm8996-qmp-usb3-phy" for 14nm USB3 phy on msm8996, "qcom,msm8998-qmp-usb3-phy" for USB3 QMP V3 phy on msm8998, "qcom,msm8998-qmp-ufs-phy" for UFS QMP phy on msm8998, + "qcom,msm8998-qmp-pcie-phy" for PCIe QMP phy on msm8998, "qcom,sdm845-qmp-usb3-phy" for USB3 QMP V3 phy on sdm845, "qcom,sdm845-qmp-usb3-uni-phy" for USB3 QMP V3 UNI phy on sdm845, "qcom,sdm845-qmp-ufs-phy" for UFS QMP phy on sdm845. @@ -48,6 +49,8 @@ Required properties: "aux", "cfg_ahb", "ref". For "qcom,msm8998-qmp-ufs-phy" must contain: "ref", "ref_aux". + For "qcom,msm8998-qmp-pcie-phy" must contain: + "aux", "cfg_ahb", "ref". For "qcom,sdm845-qmp-usb3-phy" must contain: "aux", "cfg_ahb", "ref", "com_aux". For "qcom,sdm845-qmp-usb3-uni-phy" must contain: @@ -71,6 +74,8 @@ Required properties: For "qcom,msm8998-qmp-usb3-phy" must contain "phy", "common". For "qcom,msm8998-qmp-ufs-phy": no resets are listed. + For "qcom,msm8998-qmp-pcie-phy" must contain: + "phy", "common". For "qcom,sdm845-qmp-usb3-phy" must contain: "phy", "common". For "qcom,sdm845-qmp-usb3-uni-phy" must contain: -- cgit v1.2.3 From bbdfeea2c6da271813a29344c8515220d0413daf Mon Sep 17 00:00:00 2001 From: Artur Rojek Date: Sat, 23 Mar 2019 18:28:08 +0100 Subject: dt-bindings: power: supply: Add docs for Ingenic JZ47xx SoCs battery. Add documentation for the ingenic-battery driver, used on JZ47xx SoCs. Signed-off-by: Artur Rojek Acked-by: Jonathan Cameron Signed-off-by: Sebastian Reichel --- .../bindings/power/supply/ingenic,battery.txt | 31 ++++++++++++++++++++++ 1 file changed, 31 insertions(+) create mode 100644 Documentation/devicetree/bindings/power/supply/ingenic,battery.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/power/supply/ingenic,battery.txt b/Documentation/devicetree/bindings/power/supply/ingenic,battery.txt new file mode 100644 index 000000000000..66430bf73815 --- /dev/null +++ b/Documentation/devicetree/bindings/power/supply/ingenic,battery.txt @@ -0,0 +1,31 @@ +* Ingenic JZ47xx battery bindings + +Required properties: + +- compatible: Must be "ingenic,jz4740-battery". +- io-channels: phandle and IIO specifier pair to the IIO device. + Format described in iio-bindings.txt. +- monitored-battery: phandle to a "simple-battery" compatible node. + +The "monitored-battery" property must be a phandle to a node using the format +described in battery.txt, with the following properties being required: + +- voltage-min-design-microvolt: Drained battery voltage. +- voltage-max-design-microvolt: Fully charged battery voltage. + +Example: + +#include + +simple_battery: battery { + compatible = "simple-battery"; + voltage-min-design-microvolt = <3600000>; + voltage-max-design-microvolt = <4200000>; +}; + +ingenic_battery { + compatible = "ingenic,jz4740-battery"; + io-channels = <&adc INGENIC_ADC_BATTERY>; + io-channel-names = "battery"; + monitored-battery = <&simple_battery>; +}; -- cgit v1.2.3 From d25ad7fdfb2bedbd6e8e0214bff1acbe7cdab3f1 Mon Sep 17 00:00:00 2001 From: Lubomir Rintel Date: Thu, 18 Apr 2019 16:46:46 +0200 Subject: dt-bindings: olpc_battery: Add XO-1.5 battery The XO-1 and XO-1.5 batteries apparently differ in an ability to report ambient temperature. Signed-off-by: Lubomir Rintel Reviewed-by: Rob Herring Acked-by: Pavel Machek Signed-off-by: Sebastian Reichel --- Documentation/devicetree/bindings/power/supply/olpc_battery.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/power/supply/olpc_battery.txt b/Documentation/devicetree/bindings/power/supply/olpc_battery.txt index c8901b3992d9..8d87d6b35a98 100644 --- a/Documentation/devicetree/bindings/power/supply/olpc_battery.txt +++ b/Documentation/devicetree/bindings/power/supply/olpc_battery.txt @@ -2,4 +2,4 @@ OLPC battery ~~~~~~~~~~~~ Required properties: - - compatible : "olpc,xo1-battery" + - compatible : "olpc,xo1-battery" or "olpc,xo1.5-battery" -- cgit v1.2.3 From da70314917862d4da4a8d7601cd47339df8b3c23 Mon Sep 17 00:00:00 2001 From: Andrey Ignatov Date: Wed, 17 Apr 2019 22:28:57 -0700 Subject: bpf: Document BPF_PROG_TYPE_CGROUP_SYSCTL Add documentation for BPF_PROG_TYPE_CGROUP_SYSCTL, including general info, attach type, context, return code, helpers, example and usage considerations. A separate file prog_cgroup_sysctl.rst is added to Documentation/bpf/. In the future more program types can be documented in their own prog_.rst files. Another way to place program type specific documentation would be to group program types somehow (e.g. cgroup.rst for all cgroup-bpf programs), but it may not scale well since some program types may belong to different groups, e.g. BPF_PROG_TYPE_CGROUP_SKB can be documented together with either cgroup-bpf programs or programs that access skb. The new file is added to the index and verified by `make htmldocs` / sanity-check by lynx. Signed-off-by: Andrey Ignatov Acked-by: Yonghong Song Signed-off-by: Alexei Starovoitov --- Documentation/bpf/index.rst | 9 +++ Documentation/bpf/prog_cgroup_sysctl.rst | 125 +++++++++++++++++++++++++++++++ 2 files changed, 134 insertions(+) create mode 100644 Documentation/bpf/prog_cgroup_sysctl.rst (limited to 'Documentation') diff --git a/Documentation/bpf/index.rst b/Documentation/bpf/index.rst index 4e77932959cc..dadcaa9a9f5f 100644 --- a/Documentation/bpf/index.rst +++ b/Documentation/bpf/index.rst @@ -36,6 +36,15 @@ Two sets of Questions and Answers (Q&A) are maintained. bpf_devel_QA +Program types +============= + +.. toctree:: + :maxdepth: 1 + + prog_cgroup_sysctl + + .. Links: .. _Documentation/networking/filter.txt: ../networking/filter.txt .. _man-pages: https://www.kernel.org/doc/man-pages/ diff --git a/Documentation/bpf/prog_cgroup_sysctl.rst b/Documentation/bpf/prog_cgroup_sysctl.rst new file mode 100644 index 000000000000..677d6c637cf3 --- /dev/null +++ b/Documentation/bpf/prog_cgroup_sysctl.rst @@ -0,0 +1,125 @@ +.. SPDX-License-Identifier: (LGPL-2.1 OR BSD-2-Clause) + +=========================== +BPF_PROG_TYPE_CGROUP_SYSCTL +=========================== + +This document describes ``BPF_PROG_TYPE_CGROUP_SYSCTL`` program type that +provides cgroup-bpf hook for sysctl. + +The hook has to be attached to a cgroup and will be called every time a +process inside that cgroup tries to read from or write to sysctl knob in proc. + +1. Attach type +************** + +``BPF_CGROUP_SYSCTL`` attach type has to be used to attach +``BPF_PROG_TYPE_CGROUP_SYSCTL`` program to a cgroup. + +2. Context +********** + +``BPF_PROG_TYPE_CGROUP_SYSCTL`` provides access to the following context from +BPF program:: + + struct bpf_sysctl { + __u32 write; + __u32 file_pos; + }; + +* ``write`` indicates whether sysctl value is being read (``0``) or written + (``1``). This field is read-only. + +* ``file_pos`` indicates file position sysctl is being accessed at, read + or written. This field is read-write. Writing to the field sets the starting + position in sysctl proc file ``read(2)`` will be reading from or ``write(2)`` + will be writing to. Writing zero to the field can be used e.g. to override + whole sysctl value by ``bpf_sysctl_set_new_value()`` on ``write(2)`` even + when it's called by user space on ``file_pos > 0``. Writing non-zero + value to the field can be used to access part of sysctl value starting from + specified ``file_pos``. Not all sysctl support access with ``file_pos != + 0``, e.g. writes to numeric sysctl entries must always be at file position + ``0``. See also ``kernel.sysctl_writes_strict`` sysctl. + +See `linux/bpf.h`_ for more details on how context field can be accessed. + +3. Return code +************** + +``BPF_PROG_TYPE_CGROUP_SYSCTL`` program must return one of the following +return codes: + +* ``0`` means "reject access to sysctl"; +* ``1`` means "proceed with access". + +If program returns ``0`` user space will get ``-1`` from ``read(2)`` or +``write(2)`` and ``errno`` will be set to ``EPERM``. + +4. Helpers +********** + +Since sysctl knob is represented by a name and a value, sysctl specific BPF +helpers focus on providing access to these properties: + +* ``bpf_sysctl_get_name()`` to get sysctl name as it is visible in + ``/proc/sys`` into provided by BPF program buffer; + +* ``bpf_sysctl_get_current_value()`` to get string value currently held by + sysctl into provided by BPF program buffer. This helper is available on both + ``read(2)`` from and ``write(2)`` to sysctl; + +* ``bpf_sysctl_get_new_value()`` to get new string value currently being + written to sysctl before actual write happens. This helper can be used only + on ``ctx->write == 1``; + +* ``bpf_sysctl_set_new_value()`` to override new string value currently being + written to sysctl before actual write happens. Sysctl value will be + overridden starting from the current ``ctx->file_pos``. If the whole value + has to be overridden BPF program can set ``file_pos`` to zero before calling + to the helper. This helper can be used only on ``ctx->write == 1``. New + string value set by the helper is treated and verified by kernel same way as + an equivalent string passed by user space. + +BPF program sees sysctl value same way as user space does in proc filesystem, +i.e. as a string. Since many sysctl values represent an integer or a vector +of integers, the following helpers can be used to get numeric value from the +string: + +* ``bpf_strtol()`` to convert initial part of the string to long integer + similar to user space `strtol(3)`_; +* ``bpf_strtoul()`` to convert initial part of the string to unsigned long + integer similar to user space `strtoul(3)`_; + +See `linux/bpf.h`_ for more details on helpers described here. + +5. Examples +*********** + +See `test_sysctl_prog.c`_ for an example of BPF program in C that access +sysctl name and value, parses string value to get vector of integers and uses +the result to make decision whether to allow or deny access to sysctl. + +6. Notes +******** + +``BPF_PROG_TYPE_CGROUP_SYSCTL`` is intended to be used in **trusted** root +environment, for example to monitor sysctl usage or catch unreasonable values +an application, running as root in a separate cgroup, is trying to set. + +Since `task_dfl_cgroup(current)` is called at `sys_read` / `sys_write` time it +may return results different from that at `sys_open` time, i.e. process that +opened sysctl file in proc filesystem may differ from process that is trying +to read from / write to it and two such processes may run in different +cgroups, what means ``BPF_PROG_TYPE_CGROUP_SYSCTL`` should not be used as a +security mechanism to limit sysctl usage. + +As with any cgroup-bpf program additional care should be taken if an +application running as root in a cgroup should not be allowed to +detach/replace BPF program attached by administrator. + +.. Links +.. _linux/bpf.h: ../../include/uapi/linux/bpf.h +.. _strtol(3): http://man7.org/linux/man-pages/man3/strtol.3p.html +.. _strtoul(3): http://man7.org/linux/man-pages/man3/strtoul.3p.html +.. _test_sysctl_prog.c: + ../../tools/testing/selftests/bpf/progs/test_sysctl_prog.c -- cgit v1.2.3 From 0bc199854405543b0debe67c735c0aae94f1d319 Mon Sep 17 00:00:00 2001 From: Stephen Suryaputra Date: Wed, 17 Apr 2019 16:35:49 -0400 Subject: ipv6: Add rate limit mask for ICMPv6 messages To make ICMPv6 closer to ICMPv4, add ratemask parameter. Since the ICMP message types use larger numeric values, a simple bitmask doesn't fit. I use large bitmap. The input and output are the in form of list of ranges. Set the default to rate limit all error messages but Packet Too Big. For Packet Too Big, use ratemask instead of hard-coded. There are functions where icmpv6_xrlim_allow() and icmpv6_global_allow() aren't called. This patch only adds them to icmpv6_echo_reply(). Rate limiting error messages is mandated by RFC 4443 but RFC 4890 says that it is also acceptable to rate limit informational messages. Thus, I removed the current hard-coded behavior of icmpv6_mask_allow() that doesn't rate limit informational messages. v2: Add dummy function proc_do_large_bitmap() if CONFIG_PROC_SYSCTL isn't defined, expand the description in ip-sysctl.txt and remove unnecessary conditional before kfree(). v3: Inline the bitmap instead of dynamically allocated. Still is a pointer to it is needed because of the way proc_do_large_bitmap work. Signed-off-by: Stephen Suryaputra Signed-off-by: David S. Miller --- Documentation/networking/ip-sysctl.txt | 17 ++++++++++++++++- include/net/netns/ipv6.h | 3 +++ include/uapi/linux/icmpv6.h | 4 ++++ kernel/sysctl.c | 6 ++++++ net/ipv6/af_inet6.c | 9 +++++++++ net/ipv6/icmp.c | 31 ++++++++++++++++++++++--------- 6 files changed, 60 insertions(+), 10 deletions(-) (limited to 'Documentation') diff --git a/Documentation/networking/ip-sysctl.txt b/Documentation/networking/ip-sysctl.txt index 5eedc6941ce5..8a5e59ba223f 100644 --- a/Documentation/networking/ip-sysctl.txt +++ b/Documentation/networking/ip-sysctl.txt @@ -1913,11 +1913,26 @@ enhanced_dad - BOOLEAN icmp/*: ratelimit - INTEGER - Limit the maximal rates for sending ICMPv6 packets. + Limit the maximal rates for sending ICMPv6 messages. 0 to disable any limiting, otherwise the minimal space between responses in milliseconds. Default: 1000 +ratemask - list of comma separated ranges + For ICMPv6 message types matching the ranges in the ratemask, limit + the sending of the message according to ratelimit parameter. + + The format used for both input and output is a comma separated + list of ranges (e.g. "0-127,129" for ICMPv6 message type 0 to 127 and + 129). Writing to the file will clear all previous ranges of ICMPv6 + message types and update the current list with the input. + + Refer to: https://www.iana.org/assignments/icmpv6-parameters/icmpv6-parameters.xhtml + for numerical values of ICMPv6 message types, e.g. echo request is 128 + and echo reply is 129. + + Default: 0-1,3-127 (rate limit ICMPv6 errors except Packet Too Big) + echo_ignore_all - BOOLEAN If set non-zero, then the kernel will ignore all ICMP ECHO requests sent to it over the IPv6 protocol. diff --git a/include/net/netns/ipv6.h b/include/net/netns/ipv6.h index 64e29b58bb5e..5e61b5a8635d 100644 --- a/include/net/netns/ipv6.h +++ b/include/net/netns/ipv6.h @@ -8,6 +8,7 @@ #ifndef __NETNS_IPV6_H__ #define __NETNS_IPV6_H__ #include +#include struct ctl_table_header; @@ -35,6 +36,8 @@ struct netns_sysctl_ipv6 { int icmpv6_echo_ignore_all; int icmpv6_echo_ignore_multicast; int icmpv6_echo_ignore_anycast; + DECLARE_BITMAP(icmpv6_ratemask, ICMPV6_MSG_MAX + 1); + unsigned long *icmpv6_ratemask_ptr; int anycast_src_echo_reply; int ip_nonlocal_bind; int fwmark_reflect; diff --git a/include/uapi/linux/icmpv6.h b/include/uapi/linux/icmpv6.h index 325395f56bfa..2622b5a3e616 100644 --- a/include/uapi/linux/icmpv6.h +++ b/include/uapi/linux/icmpv6.h @@ -90,6 +90,8 @@ struct icmp6hdr { #define ICMPV6_TIME_EXCEED 3 #define ICMPV6_PARAMPROB 4 +#define ICMPV6_ERRMSG_MAX 127 + #define ICMPV6_INFOMSG_MASK 0x80 #define ICMPV6_ECHO_REQUEST 128 @@ -110,6 +112,8 @@ struct icmp6hdr { #define ICMPV6_MRDISC_ADV 151 +#define ICMPV6_MSG_MAX 255 + /* * Codes for Destination Unreachable */ diff --git a/kernel/sysctl.c b/kernel/sysctl.c index c9ec050bcf46..599510a3355e 100644 --- a/kernel/sysctl.c +++ b/kernel/sysctl.c @@ -3326,6 +3326,11 @@ int proc_doulongvec_ms_jiffies_minmax(struct ctl_table *table, int write, return -ENOSYS; } +int proc_do_large_bitmap(struct ctl_table *table, int write, + void __user *buffer, size_t *lenp, loff_t *ppos) +{ + return -ENOSYS; +} #endif /* CONFIG_PROC_SYSCTL */ @@ -3366,3 +3371,4 @@ EXPORT_SYMBOL(proc_dointvec_ms_jiffies); EXPORT_SYMBOL(proc_dostring); EXPORT_SYMBOL(proc_doulongvec_minmax); EXPORT_SYMBOL(proc_doulongvec_ms_jiffies_minmax); +EXPORT_SYMBOL(proc_do_large_bitmap); diff --git a/net/ipv6/af_inet6.c b/net/ipv6/af_inet6.c index d8587ca4fbeb..3d1de28aaa9e 100644 --- a/net/ipv6/af_inet6.c +++ b/net/ipv6/af_inet6.c @@ -850,6 +850,15 @@ static int __net_init inet6_net_init(struct net *net) net->ipv6.sysctl.icmpv6_echo_ignore_all = 0; net->ipv6.sysctl.icmpv6_echo_ignore_multicast = 0; net->ipv6.sysctl.icmpv6_echo_ignore_anycast = 0; + + /* By default, rate limit error messages. + * Except for pmtu discovery, it would break it. + * proc_do_large_bitmap needs pointer to the bitmap. + */ + bitmap_set(net->ipv6.sysctl.icmpv6_ratemask, 0, ICMPV6_ERRMSG_MAX + 1); + bitmap_clear(net->ipv6.sysctl.icmpv6_ratemask, ICMPV6_PKT_TOOBIG, 1); + net->ipv6.sysctl.icmpv6_ratemask_ptr = net->ipv6.sysctl.icmpv6_ratemask; + net->ipv6.sysctl.flowlabel_consistency = 1; net->ipv6.sysctl.auto_flowlabels = IP6_DEFAULT_AUTO_FLOW_LABELS; net->ipv6.sysctl.idgen_retries = 3; diff --git a/net/ipv6/icmp.c b/net/ipv6/icmp.c index cc14b9998941..afb915807cd0 100644 --- a/net/ipv6/icmp.c +++ b/net/ipv6/icmp.c @@ -168,22 +168,21 @@ static bool is_ineligible(const struct sk_buff *skb) return false; } -static bool icmpv6_mask_allow(int type) +static bool icmpv6_mask_allow(struct net *net, int type) { - /* Informational messages are not limited. */ - if (type & ICMPV6_INFOMSG_MASK) + if (type > ICMPV6_MSG_MAX) return true; - /* Do not limit pmtu discovery, it would break it. */ - if (type == ICMPV6_PKT_TOOBIG) + /* Limit if icmp type is set in ratemask. */ + if (!test_bit(type, net->ipv6.sysctl.icmpv6_ratemask)) return true; return false; } -static bool icmpv6_global_allow(int type) +static bool icmpv6_global_allow(struct net *net, int type) { - if (icmpv6_mask_allow(type)) + if (icmpv6_mask_allow(net, type)) return true; if (icmp_global_allow()) @@ -202,7 +201,7 @@ static bool icmpv6_xrlim_allow(struct sock *sk, u8 type, struct dst_entry *dst; bool res = false; - if (icmpv6_mask_allow(type)) + if (icmpv6_mask_allow(net, type)) return true; /* @@ -511,7 +510,7 @@ static void icmp6_send(struct sk_buff *skb, u8 type, u8 code, __u32 info, local_bh_disable(); /* Check global sysctl_icmp_msgs_per_sec ratelimit */ - if (!(skb->dev->flags&IFF_LOOPBACK) && !icmpv6_global_allow(type)) + if (!(skb->dev->flags & IFF_LOOPBACK) && !icmpv6_global_allow(net, type)) goto out_bh_enable; mip6_addr_swap(skb); @@ -731,6 +730,11 @@ static void icmpv6_echo_reply(struct sk_buff *skb) if (IS_ERR(dst)) goto out; + /* Check the ratelimit */ + if ((!(skb->dev->flags & IFF_LOOPBACK) && !icmpv6_global_allow(net, ICMPV6_ECHO_REPLY)) || + !icmpv6_xrlim_allow(sk, ICMPV6_ECHO_REPLY, &fl6)) + goto out_dst_release; + idev = __in6_dev_get(skb->dev); msg.skb = skb; @@ -751,6 +755,7 @@ static void icmpv6_echo_reply(struct sk_buff *skb) icmpv6_push_pending_frames(sk, &fl6, &tmp_hdr, skb->len + sizeof(struct icmp6hdr)); } +out_dst_release: dst_release(dst); out: icmpv6_xmit_unlock(sk); @@ -1137,6 +1142,13 @@ static struct ctl_table ipv6_icmp_table_template[] = { .mode = 0644, .proc_handler = proc_dointvec, }, + { + .procname = "ratemask", + .data = &init_net.ipv6.sysctl.icmpv6_ratemask_ptr, + .maxlen = ICMPV6_MSG_MAX + 1, + .mode = 0644, + .proc_handler = proc_do_large_bitmap, + }, { }, }; @@ -1153,6 +1165,7 @@ struct ctl_table * __net_init ipv6_icmp_sysctl_init(struct net *net) table[1].data = &net->ipv6.sysctl.icmpv6_echo_ignore_all; table[2].data = &net->ipv6.sysctl.icmpv6_echo_ignore_multicast; table[3].data = &net->ipv6.sysctl.icmpv6_echo_ignore_anycast; + table[4].data = &net->ipv6.sysctl.icmpv6_ratemask_ptr; } return table; } -- cgit v1.2.3 From 80695946737dff4cfc1ecdefd4ebf300f132d8ee Mon Sep 17 00:00:00 2001 From: Stanislav Fomichev Date: Thu, 18 Apr 2019 16:47:52 -0700 Subject: bpf: move BPF_PROG_TYPE_FLOW_DISSECTOR documentation to a new common place In commit da7031491786 ("bpf: Document BPF_PROG_TYPE_CGROUP_SYSCTL") Andrey proposes to put per-prog type docs under Documentation/bpf/ Let's move flow dissector documentation there as well. Signed-off-by: Stanislav Fomichev Signed-off-by: Alexei Starovoitov --- Documentation/bpf/index.rst | 1 + Documentation/bpf/prog_flow_dissector.rst | 126 ++++++++++++++++++++++++ Documentation/networking/bpf_flow_dissector.rst | 126 ------------------------ Documentation/networking/index.rst | 1 - 4 files changed, 127 insertions(+), 127 deletions(-) create mode 100644 Documentation/bpf/prog_flow_dissector.rst delete mode 100644 Documentation/networking/bpf_flow_dissector.rst (limited to 'Documentation') diff --git a/Documentation/bpf/index.rst b/Documentation/bpf/index.rst index dadcaa9a9f5f..d3fe4cac0c90 100644 --- a/Documentation/bpf/index.rst +++ b/Documentation/bpf/index.rst @@ -43,6 +43,7 @@ Program types :maxdepth: 1 prog_cgroup_sysctl + prog_flow_dissector .. Links: diff --git a/Documentation/bpf/prog_flow_dissector.rst b/Documentation/bpf/prog_flow_dissector.rst new file mode 100644 index 000000000000..ed343abe541e --- /dev/null +++ b/Documentation/bpf/prog_flow_dissector.rst @@ -0,0 +1,126 @@ +.. SPDX-License-Identifier: GPL-2.0 + +============================ +BPF_PROG_TYPE_FLOW_DISSECTOR +============================ + +Overview +======== + +Flow dissector is a routine that parses metadata out of the packets. It's +used in the various places in the networking subsystem (RFS, flow hash, etc). + +BPF flow dissector is an attempt to reimplement C-based flow dissector logic +in BPF to gain all the benefits of BPF verifier (namely, limits on the +number of instructions and tail calls). + +API +=== + +BPF flow dissector programs operate on an ``__sk_buff``. However, only the +limited set of fields is allowed: ``data``, ``data_end`` and ``flow_keys``. +``flow_keys`` is ``struct bpf_flow_keys`` and contains flow dissector input +and output arguments. + +The inputs are: + * ``nhoff`` - initial offset of the networking header + * ``thoff`` - initial offset of the transport header, initialized to nhoff + * ``n_proto`` - L3 protocol type, parsed out of L2 header + +Flow dissector BPF program should fill out the rest of the ``struct +bpf_flow_keys`` fields. Input arguments ``nhoff/thoff/n_proto`` should be +also adjusted accordingly. + +The return code of the BPF program is either BPF_OK to indicate successful +dissection, or BPF_DROP to indicate parsing error. + +__sk_buff->data +=============== + +In the VLAN-less case, this is what the initial state of the BPF flow +dissector looks like:: + + +------+------+------------+-----------+ + | DMAC | SMAC | ETHER_TYPE | L3_HEADER | + +------+------+------------+-----------+ + ^ + | + +-- flow dissector starts here + + +.. code:: c + + skb->data + flow_keys->nhoff point to the first byte of L3_HEADER + flow_keys->thoff = nhoff + flow_keys->n_proto = ETHER_TYPE + +In case of VLAN, flow dissector can be called with the two different states. + +Pre-VLAN parsing:: + + +------+------+------+-----+-----------+-----------+ + | DMAC | SMAC | TPID | TCI |ETHER_TYPE | L3_HEADER | + +------+------+------+-----+-----------+-----------+ + ^ + | + +-- flow dissector starts here + +.. code:: c + + skb->data + flow_keys->nhoff point the to first byte of TCI + flow_keys->thoff = nhoff + flow_keys->n_proto = TPID + +Please note that TPID can be 802.1AD and, hence, BPF program would +have to parse VLAN information twice for double tagged packets. + + +Post-VLAN parsing:: + + +------+------+------+-----+-----------+-----------+ + | DMAC | SMAC | TPID | TCI |ETHER_TYPE | L3_HEADER | + +------+------+------+-----+-----------+-----------+ + ^ + | + +-- flow dissector starts here + +.. code:: c + + skb->data + flow_keys->nhoff point the to first byte of L3_HEADER + flow_keys->thoff = nhoff + flow_keys->n_proto = ETHER_TYPE + +In this case VLAN information has been processed before the flow dissector +and BPF flow dissector is not required to handle it. + + +The takeaway here is as follows: BPF flow dissector program can be called with +the optional VLAN header and should gracefully handle both cases: when single +or double VLAN is present and when it is not present. The same program +can be called for both cases and would have to be written carefully to +handle both cases. + + +Reference Implementation +======================== + +See ``tools/testing/selftests/bpf/progs/bpf_flow.c`` for the reference +implementation and ``tools/testing/selftests/bpf/flow_dissector_load.[hc]`` +for the loader. bpftool can be used to load BPF flow dissector program as well. + +The reference implementation is organized as follows: + * ``jmp_table`` map that contains sub-programs for each supported L3 protocol + * ``_dissect`` routine - entry point; it does input ``n_proto`` parsing and + does ``bpf_tail_call`` to the appropriate L3 handler + +Since BPF at this point doesn't support looping (or any jumping back), +jmp_table is used instead to handle multiple levels of encapsulation (and +IPv6 options). + + +Current Limitations +=================== +BPF flow dissector doesn't support exporting all the metadata that in-kernel +C-based implementation can export. Notable example is single VLAN (802.1Q) +and double VLAN (802.1AD) tags. Please refer to the ``struct bpf_flow_keys`` +for a set of information that's currently can be exported from the BPF context. diff --git a/Documentation/networking/bpf_flow_dissector.rst b/Documentation/networking/bpf_flow_dissector.rst deleted file mode 100644 index b375ae2ec2c4..000000000000 --- a/Documentation/networking/bpf_flow_dissector.rst +++ /dev/null @@ -1,126 +0,0 @@ -.. SPDX-License-Identifier: GPL-2.0 - -================== -BPF Flow Dissector -================== - -Overview -======== - -Flow dissector is a routine that parses metadata out of the packets. It's -used in the various places in the networking subsystem (RFS, flow hash, etc). - -BPF flow dissector is an attempt to reimplement C-based flow dissector logic -in BPF to gain all the benefits of BPF verifier (namely, limits on the -number of instructions and tail calls). - -API -=== - -BPF flow dissector programs operate on an ``__sk_buff``. However, only the -limited set of fields is allowed: ``data``, ``data_end`` and ``flow_keys``. -``flow_keys`` is ``struct bpf_flow_keys`` and contains flow dissector input -and output arguments. - -The inputs are: - * ``nhoff`` - initial offset of the networking header - * ``thoff`` - initial offset of the transport header, initialized to nhoff - * ``n_proto`` - L3 protocol type, parsed out of L2 header - -Flow dissector BPF program should fill out the rest of the ``struct -bpf_flow_keys`` fields. Input arguments ``nhoff/thoff/n_proto`` should be -also adjusted accordingly. - -The return code of the BPF program is either BPF_OK to indicate successful -dissection, or BPF_DROP to indicate parsing error. - -__sk_buff->data -=============== - -In the VLAN-less case, this is what the initial state of the BPF flow -dissector looks like:: - - +------+------+------------+-----------+ - | DMAC | SMAC | ETHER_TYPE | L3_HEADER | - +------+------+------------+-----------+ - ^ - | - +-- flow dissector starts here - - -.. code:: c - - skb->data + flow_keys->nhoff point to the first byte of L3_HEADER - flow_keys->thoff = nhoff - flow_keys->n_proto = ETHER_TYPE - -In case of VLAN, flow dissector can be called with the two different states. - -Pre-VLAN parsing:: - - +------+------+------+-----+-----------+-----------+ - | DMAC | SMAC | TPID | TCI |ETHER_TYPE | L3_HEADER | - +------+------+------+-----+-----------+-----------+ - ^ - | - +-- flow dissector starts here - -.. code:: c - - skb->data + flow_keys->nhoff point the to first byte of TCI - flow_keys->thoff = nhoff - flow_keys->n_proto = TPID - -Please note that TPID can be 802.1AD and, hence, BPF program would -have to parse VLAN information twice for double tagged packets. - - -Post-VLAN parsing:: - - +------+------+------+-----+-----------+-----------+ - | DMAC | SMAC | TPID | TCI |ETHER_TYPE | L3_HEADER | - +------+------+------+-----+-----------+-----------+ - ^ - | - +-- flow dissector starts here - -.. code:: c - - skb->data + flow_keys->nhoff point the to first byte of L3_HEADER - flow_keys->thoff = nhoff - flow_keys->n_proto = ETHER_TYPE - -In this case VLAN information has been processed before the flow dissector -and BPF flow dissector is not required to handle it. - - -The takeaway here is as follows: BPF flow dissector program can be called with -the optional VLAN header and should gracefully handle both cases: when single -or double VLAN is present and when it is not present. The same program -can be called for both cases and would have to be written carefully to -handle both cases. - - -Reference Implementation -======================== - -See ``tools/testing/selftests/bpf/progs/bpf_flow.c`` for the reference -implementation and ``tools/testing/selftests/bpf/flow_dissector_load.[hc]`` -for the loader. bpftool can be used to load BPF flow dissector program as well. - -The reference implementation is organized as follows: - * ``jmp_table`` map that contains sub-programs for each supported L3 protocol - * ``_dissect`` routine - entry point; it does input ``n_proto`` parsing and - does ``bpf_tail_call`` to the appropriate L3 handler - -Since BPF at this point doesn't support looping (or any jumping back), -jmp_table is used instead to handle multiple levels of encapsulation (and -IPv6 options). - - -Current Limitations -=================== -BPF flow dissector doesn't support exporting all the metadata that in-kernel -C-based implementation can export. Notable example is single VLAN (802.1Q) -and double VLAN (802.1AD) tags. Please refer to the ``struct bpf_flow_keys`` -for a set of information that's currently can be exported from the BPF context. diff --git a/Documentation/networking/index.rst b/Documentation/networking/index.rst index 984e68f9e026..5449149be496 100644 --- a/Documentation/networking/index.rst +++ b/Documentation/networking/index.rst @@ -9,7 +9,6 @@ Contents: netdev-FAQ af_xdp batman-adv - bpf_flow_dissector can can_ucan_protocol device_drivers/freescale/dpaa2/index -- cgit v1.2.3 From b54dd90cab00f5b64ed8ce533991c20bf781a3cd Mon Sep 17 00:00:00 2001 From: David Bauer Date: Wed, 17 Apr 2019 23:59:20 +0200 Subject: dt-bindings: net: add PHY reset controller binding Add the documentation for PHY reset lines controlled by a reset controller. Signed-off-by: David Bauer Reviewed-by: Andrew Lunn Signed-off-by: David S. Miller --- Documentation/devicetree/bindings/net/phy.txt | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/net/phy.txt b/Documentation/devicetree/bindings/net/phy.txt index 17c1d2bd00f6..9b9e5b1765dd 100644 --- a/Documentation/devicetree/bindings/net/phy.txt +++ b/Documentation/devicetree/bindings/net/phy.txt @@ -51,6 +51,10 @@ Optional Properties: to ensure the integrated PHY is used. The absence of this property indicates the muxers should be configured so that the external PHY is used. +- resets: The reset-controller phandle and specifier for the PHY reset signal. + +- reset-names: Must be "phy" for the PHY reset signal. + - reset-gpios: The GPIO phandle and specifier for the PHY reset signal. - reset-assert-us: Delay after the reset was asserted in microseconds. @@ -67,6 +71,8 @@ ethernet-phy@0 { interrupts = <35 IRQ_TYPE_EDGE_RISING>; reg = <0>; + resets = <&rst 8>; + reset-names = "phy"; reset-gpios = <&gpio1 4 GPIO_ACTIVE_LOW>; reset-assert-us = <1000>; reset-deassert-us = <2000>; -- cgit v1.2.3 From ef7c7727f2c18338fa77b339f10ab923a4c0b0f4 Mon Sep 17 00:00:00 2001 From: Len Brown Date: Tue, 26 Feb 2019 01:19:59 -0500 Subject: x86/topology: Fix documentation typo Syntax only, no functional or semantic change. reflect actual cpuinfo_x86 field name: s/logical_id/logical_proc_id/ Signed-off-by: Len Brown Cc: Andrew Morton Cc: Linus Torvalds Cc: Paul E. McKenney Cc: Peter Zijlstra Cc: Thomas Gleixner Cc: Will Deacon Cc: linux-doc@vger.kernel.org Link: http://lkml.kernel.org/r/e2810a5317d3a109a98204e883fd1461f77b9339.1551160674.git.len.brown@intel.com Signed-off-by: Ingo Molnar --- Documentation/x86/topology.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/x86/topology.txt b/Documentation/x86/topology.txt index 2953e3ec9a02..06b3cdbc4048 100644 --- a/Documentation/x86/topology.txt +++ b/Documentation/x86/topology.txt @@ -51,7 +51,7 @@ The topology of a system is described in the units of: The physical ID of the package. This information is retrieved via CPUID and deduced from the APIC IDs of the cores in the package. - - cpuinfo_x86.logical_id: + - cpuinfo_x86.logical_proc_id: The logical ID of the package. As we do not trust BIOSes to enumerate the packages in a consistent way, we introduced the concept of logical package -- cgit v1.2.3 From 3a1c779fb8f71e772e2145e68c262936ada815ed Mon Sep 17 00:00:00 2001 From: Len Brown Date: Tue, 26 Feb 2019 01:20:00 -0500 Subject: topology: Simplify cputopology.txt formatting and wording Syntax only, no functional or semantic change. Signed-off-by: Len Brown Cc: Andrew Morton Cc: Linus Torvalds Cc: Paul E. McKenney Cc: Peter Zijlstra Cc: Thomas Gleixner Cc: Will Deacon Cc: linux-doc@vger.kernel.org Link: http://lkml.kernel.org/r/1ca56f8ea922a67f0017bd645912ea02a65a85ec.1551160674.git.len.brown@intel.com Signed-off-by: Ingo Molnar --- Documentation/cputopology.txt | 46 +++++++++++++++++++++---------------------- 1 file changed, 23 insertions(+), 23 deletions(-) (limited to 'Documentation') diff --git a/Documentation/cputopology.txt b/Documentation/cputopology.txt index c6e7e9196a8b..cb61277e2308 100644 --- a/Documentation/cputopology.txt +++ b/Documentation/cputopology.txt @@ -3,79 +3,79 @@ How CPU topology info is exported via sysfs =========================================== Export CPU topology info via sysfs. Items (attributes) are similar -to /proc/cpuinfo output of some architectures: +to /proc/cpuinfo output of some architectures. They reside in +/sys/devices/system/cpu/cpuX/topology/: -1) /sys/devices/system/cpu/cpuX/topology/physical_package_id: +physical_package_id: physical package id of cpuX. Typically corresponds to a physical socket number, but the actual value is architecture and platform dependent. -2) /sys/devices/system/cpu/cpuX/topology/core_id: +core_id: the CPU core ID of cpuX. Typically it is the hardware platform's identifier (rather than the kernel's). The actual value is architecture and platform dependent. -3) /sys/devices/system/cpu/cpuX/topology/book_id: +book_id: the book ID of cpuX. Typically it is the hardware platform's identifier (rather than the kernel's). The actual value is architecture and platform dependent. -4) /sys/devices/system/cpu/cpuX/topology/drawer_id: +drawer_id: the drawer ID of cpuX. Typically it is the hardware platform's identifier (rather than the kernel's). The actual value is architecture and platform dependent. -5) /sys/devices/system/cpu/cpuX/topology/thread_siblings: +thread_siblings: internal kernel map of cpuX's hardware threads within the same core as cpuX. -6) /sys/devices/system/cpu/cpuX/topology/thread_siblings_list: +thread_siblings_list: human-readable list of cpuX's hardware threads within the same core as cpuX. -7) /sys/devices/system/cpu/cpuX/topology/core_siblings: +core_siblings: internal kernel map of cpuX's hardware threads within the same physical_package_id. -8) /sys/devices/system/cpu/cpuX/topology/core_siblings_list: +core_siblings_list: human-readable list of cpuX's hardware threads within the same physical_package_id. -9) /sys/devices/system/cpu/cpuX/topology/book_siblings: +book_siblings: internal kernel map of cpuX's hardware threads within the same book_id. -10) /sys/devices/system/cpu/cpuX/topology/book_siblings_list: +book_siblings_list: human-readable list of cpuX's hardware threads within the same book_id. -11) /sys/devices/system/cpu/cpuX/topology/drawer_siblings: +drawer_siblings: internal kernel map of cpuX's hardware threads within the same drawer_id. -12) /sys/devices/system/cpu/cpuX/topology/drawer_siblings_list: +drawer_siblings_list: human-readable list of cpuX's hardware threads within the same drawer_id. -To implement it in an architecture-neutral way, a new source file, -drivers/base/topology.c, is to export the 6 to 12 attributes. The book -and drawer related sysfs files will only be created if CONFIG_SCHED_BOOK -and CONFIG_SCHED_DRAWER are selected. +Architecture-neutral, drivers/base/topology.c, exports these attributes. +However, the book and drawer related sysfs files will only be created if +CONFIG_SCHED_BOOK and CONFIG_SCHED_DRAWER are selected, respectively. -CONFIG_SCHED_BOOK and CONFIG_DRAWER are currently only used on s390, where -they reflect the cpu and cache hierarchy. +CONFIG_SCHED_BOOK and CONFIG_SCHED_DRAWER are currently only used on s390, +where they reflect the cpu and cache hierarchy. For an architecture to support this feature, it must define some of these macros in include/asm-XXX/topology.h:: @@ -98,10 +98,10 @@ To be consistent on all architectures, include/linux/topology.h provides default definitions for any of the above macros that are not defined by include/asm-XXX/topology.h: -1) physical_package_id: -1 -2) core_id: 0 -3) sibling_cpumask: just the given CPU -4) core_cpumask: just the given CPU +1) topology_physical_package_id: -1 +2) topology_core_id: 0 +3) topology_sibling_cpumask: just the given CPU +4) topology_core_cpumask: just the given CPU For architectures that don't support books (CONFIG_SCHED_BOOK) there are no default definitions for topology_book_id() and topology_book_cpumask(). -- cgit v1.2.3 From afe471ea2d6fcd439c3a7a1fe2df0389e07a67c8 Mon Sep 17 00:00:00 2001 From: Roman Gushchin Date: Fri, 19 Apr 2019 10:03:09 -0700 Subject: cgroup: document cgroup v2 freezer interface Describe cgroup v2 freezer interface in the cgroup v2 admin guide. Signed-off-by: Roman Gushchin Reviewed-by: Mike Rapoport Signed-off-by: Tejun Heo Cc: linux-doc@vger.kernel.org Cc: kernel-team@fb.com --- Documentation/admin-guide/cgroup-v2.rst | 27 +++++++++++++++++++++++++++ 1 file changed, 27 insertions(+) (limited to 'Documentation') diff --git a/Documentation/admin-guide/cgroup-v2.rst b/Documentation/admin-guide/cgroup-v2.rst index 20f92c16ffbf..88e746074252 100644 --- a/Documentation/admin-guide/cgroup-v2.rst +++ b/Documentation/admin-guide/cgroup-v2.rst @@ -864,6 +864,8 @@ All cgroup core files are prefixed with "cgroup." populated 1 if the cgroup or its descendants contains any live processes; otherwise, 0. + frozen + 1 if the cgroup is frozen; otherwise, 0. cgroup.max.descendants A read-write single value files. The default is "max". @@ -897,6 +899,31 @@ All cgroup core files are prefixed with "cgroup." A dying cgroup can consume system resources not exceeding limits, which were active at the moment of cgroup deletion. + cgroup.freeze + A read-write single value file which exists on non-root cgroups. + Allowed values are "0" and "1". The default is "0". + + Writing "1" to the file causes freezing of the cgroup and all + descendant cgroups. This means that all belonging processes will + be stopped and will not run until the cgroup will be explicitly + unfrozen. Freezing of the cgroup may take some time; when this action + is completed, the "frozen" value in the cgroup.events control file + will be updated to "1" and the corresponding notification will be + issued. + + A cgroup can be frozen either by its own settings, or by settings + of any ancestor cgroups. If any of ancestor cgroups is frozen, the + cgroup will remain frozen. + + Processes in the frozen cgroup can be killed by a fatal signal. + They also can enter and leave a frozen cgroup: either by an explicit + move by a user, or if freezing of the cgroup races with fork(). + If a process is moved to a frozen cgroup, it stops. If a process is + moved out of a frozen cgroup, it becomes running. + + Frozen status of a cgroup doesn't affect any cgroup tree operations: + it's possible to delete a frozen (and empty) cgroup, as well as + create new sub-cgroups. Controllers =========== -- cgit v1.2.3 From 9f436194f98547a847ab2529861d7cf22273f32c Mon Sep 17 00:00:00 2001 From: Shuah Khan Date: Wed, 17 Apr 2019 17:34:03 -0600 Subject: doc: kselftest: Fix KBUILD_OUTPUT usage instructions Fix KBUILD_OUTPUT usage instructions. The current documentation is incorrect. Update and fix outdated information about summary option. Add a reference to kselftest wiki for additional information on the framework and tips on writing new tests. Signed-off-by: Shuah Khan Signed-off-by: Jonathan Corbet --- Documentation/dev-tools/kselftest.rst | 42 ++++++++++++++++++++++++----------- 1 file changed, 29 insertions(+), 13 deletions(-) (limited to 'Documentation') diff --git a/Documentation/dev-tools/kselftest.rst b/Documentation/dev-tools/kselftest.rst index 7756f7a7c23b..79d15421e9a5 100644 --- a/Documentation/dev-tools/kselftest.rst +++ b/Documentation/dev-tools/kselftest.rst @@ -7,6 +7,11 @@ directory. These are intended to be small tests to exercise individual code paths in the kernel. Tests are intended to be run after building, installing and booting a kernel. +You can find additional information on Kselftest framework, how to +write new tests using the framework on Kselftest wiki: + +https://kselftest.wiki.kernel.org/ + On some systems, hot-plug tests could hang forever waiting for cpu and memory to be ready to be offlined. A special hot-plug target is created to run the full range of hot-plug tests. In default mode, hot-plug tests run @@ -31,17 +36,32 @@ To build and run the tests with a single command, use:: Note that some tests will require root privileges. -Build and run from user specific object directory (make O=dir):: +Kselftest supports saving output files in a separate directory and then +running tests. To locate output files in a separate directory two syntaxes +are supported. In both cases the working directory must be the root of the +kernel src. This is applicable to "Running a subset of selftests" section +below. + +To build, save output files in a separate directory with O= :: $ make O=/tmp/kselftest kselftest -Build and run KBUILD_OUTPUT directory (make KBUILD_OUTPUT=):: +To build, save output files in a separate directory with KBUILD_OUTPUT :: + + $ export KBUILD_OUTPUT=/tmp/kselftest; make kselftest - $ make KBUILD_OUTPUT=/tmp/kselftest kselftest +The O= assignment takes precedence over the KBUILD_OUTPUT environment +variable. -The above commands run the tests and print pass/fail summary to make it -easier to understand the test results. Please find the detailed individual -test results for each test in /tmp/testname file(s). +The above commands by default run the tests and print full pass/fail report. +Kselftest supports "summary" option to make it easier to understand the test +results. Please find the detailed individual test results for each test in +/tmp/testname file(s) when summary option is specified. This is applicable +to "Running a subset of selftests" section below. + +To run kselftest with summary option enabled :: + + $ make summary=1 kselftest Running a subset of selftests ============================= @@ -57,17 +77,13 @@ You can specify multiple tests to build and run:: $ make TARGETS="size timers" kselftest -Build and run from user specific object directory (make O=dir):: +To build, save output files in a separate directory with O= :: $ make O=/tmp/kselftest TARGETS="size timers" kselftest -Build and run KBUILD_OUTPUT directory (make KBUILD_OUTPUT=):: - - $ make KBUILD_OUTPUT=/tmp/kselftest TARGETS="size timers" kselftest +To build, save output files in a separate directory with KBUILD_OUTPUT :: -The above commands run the tests and print pass/fail summary to make it -easier to understand the test results. Please find the detailed individual -test results for each test in /tmp/testname file(s). + $ export KBUILD_OUTPUT=/tmp/kselftest; make TARGETS="size timers" kselftest See the top-level tools/testing/selftests/Makefile for the list of all possible targets. -- cgit v1.2.3 From d8e8bcc3d8de530da43de16bf9cd89aa553ae290 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Fri, 19 Apr 2019 07:30:51 -0300 Subject: docs: doc-guide: remove the extension from .rst files On almost all places, we're including ReST files without the extension. Let's remove the extension here as well, in order to use just one standard. Suggested-by: Jani Nikula Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/doc-guide/index.rst | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/doc-guide/index.rst b/Documentation/doc-guide/index.rst index a7f95d7d3a63..603f3ff55d5a 100644 --- a/Documentation/doc-guide/index.rst +++ b/Documentation/doc-guide/index.rst @@ -7,9 +7,9 @@ How to write kernel documentation .. toctree:: :maxdepth: 1 - sphinx.rst - kernel-doc.rst - parse-headers.rst + sphinx + kernel-doc + parse-headers .. only:: subproject and html -- cgit v1.2.3 From a496696ab56917baf813dacb4f4837f1ef516c50 Mon Sep 17 00:00:00 2001 From: Yang Shi Date: Fri, 19 Apr 2019 04:17:04 +0800 Subject: doc: mm: migration doesn't use FOLL_SPLIT anymore When demonstrating FOLL_SPLIT in transhuge document, migration is used as an example. But, since commit 94723aafb9e7 ("mm: unclutter THP migration"), the way of THP migration is totally changed. FOLL_SPLIT is not used by migration anymore due to the change. Remove the obsolete example to avoid confusion. Cc: Michal Hocko Cc: Kirill A. Shutemov Cc: Mike Rapoport Signed-off-by: Yang Shi Reviewed-by: Zi Yan Signed-off-by: Jonathan Corbet --- Documentation/vm/transhuge.rst | 8 +------- 1 file changed, 1 insertion(+), 7 deletions(-) (limited to 'Documentation') diff --git a/Documentation/vm/transhuge.rst b/Documentation/vm/transhuge.rst index a8cf6809e36e..8df380657430 100644 --- a/Documentation/vm/transhuge.rst +++ b/Documentation/vm/transhuge.rst @@ -55,13 +55,7 @@ prevent page from being split by anyone. In case you can't handle compound pages if they're returned by follow_page, the FOLL_SPLIT bit can be specified as parameter to follow_page, so that it will split the hugepages before returning -them. Migration for example passes FOLL_SPLIT as parameter to -follow_page because it's not hugepage aware and in fact it can't work -at all on hugetlbfs (but it instead works fine on transparent -hugepages thanks to FOLL_SPLIT). migration simply can't deal with -hugepages being returned (as it's not only checking the pfn of the -page and pinning it during the copy but it pretends to migrate the -memory in regular page sizes and with regular pte/pmd mappings). +them. Graceful fallback ================= -- cgit v1.2.3 From 36ad7022536e0c65f8baeeaa5efde11dec44808a Mon Sep 17 00:00:00 2001 From: Petr Štetiar Date: Wed, 17 Apr 2019 22:09:12 +0200 Subject: of_net: Fix residues after of_get_nvmem_mac_address removal MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit I've discovered following discrepancy in the bindings/net/ethernet.txt documentation, where it states following: - nvmem-cells: phandle, reference to an nvmem node for the MAC address; - nvmem-cell-names: string, should be "mac-address" if nvmem is to be.. which is actually misleading and confusing. There are only two ethernet drivers in the tree, cadence/macb and davinci which supports this properties. This nvmem-cell* properties were introduced in commit 9217e566bdee ("of_net: Implement of_get_nvmem_mac_address helper"), but commit afa64a72b862 ("of: net: kill of_get_nvmem_mac_address()") forget to properly clean up this parts. So this patch fixes the documentation by moving the nvmem-cell* properties at the appropriate places. While at it, I've removed unused include as well. Cc: Bartosz Golaszewski Fixes: afa64a72b862 ("of: net: kill of_get_nvmem_mac_address()") Signed-off-by: Petr Štetiar Signed-off-by: David S. Miller --- Documentation/devicetree/bindings/net/davinci_emac.txt | 2 ++ Documentation/devicetree/bindings/net/ethernet.txt | 2 -- Documentation/devicetree/bindings/net/macb.txt | 4 ++++ drivers/of/of_net.c | 1 - 4 files changed, 6 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/net/davinci_emac.txt b/Documentation/devicetree/bindings/net/davinci_emac.txt index 24c5cdaba8d2..ca83dcc84fb8 100644 --- a/Documentation/devicetree/bindings/net/davinci_emac.txt +++ b/Documentation/devicetree/bindings/net/davinci_emac.txt @@ -20,6 +20,8 @@ Required properties: Optional properties: - phy-handle: See ethernet.txt file in the same directory. If absent, davinci_emac driver defaults to 100/FULL. +- nvmem-cells: phandle, reference to an nvmem node for the MAC address +- nvmem-cell-names: string, should be "mac-address" if nvmem is to be used - ti,davinci-rmii-en: 1 byte, 1 means use RMII - ti,davinci-no-bd-ram: boolean, does EMAC have BD RAM? diff --git a/Documentation/devicetree/bindings/net/ethernet.txt b/Documentation/devicetree/bindings/net/ethernet.txt index cfc376bc977a..2974e63ba311 100644 --- a/Documentation/devicetree/bindings/net/ethernet.txt +++ b/Documentation/devicetree/bindings/net/ethernet.txt @@ -10,8 +10,6 @@ Documentation/devicetree/bindings/phy/phy-bindings.txt. the boot program; should be used in cases where the MAC address assigned to the device by the boot program is different from the "local-mac-address" property; -- nvmem-cells: phandle, reference to an nvmem node for the MAC address; -- nvmem-cell-names: string, should be "mac-address" if nvmem is to be used; - max-speed: number, specifies maximum speed in Mbit/s supported by the device; - max-frame-size: number, maximum transfer unit (IEEE defined MTU), rather than the maximum frame size (there's contradiction in the Devicetree diff --git a/Documentation/devicetree/bindings/net/macb.txt b/Documentation/devicetree/bindings/net/macb.txt index 174f292d8a3e..8b80515729d7 100644 --- a/Documentation/devicetree/bindings/net/macb.txt +++ b/Documentation/devicetree/bindings/net/macb.txt @@ -26,6 +26,10 @@ Required properties: Optional elements: 'tsu_clk' - clocks: Phandles to input clocks. +Optional properties: +- nvmem-cells: phandle, reference to an nvmem node for the MAC address +- nvmem-cell-names: string, should be "mac-address" if nvmem is to be used + Optional properties for PHY child node: - reset-gpios : Should specify the gpio for phy reset - magic-packet : If present, indicates that the hardware supports waking diff --git a/drivers/of/of_net.c b/drivers/of/of_net.c index 810ab0fbcccb..d820f3edd431 100644 --- a/drivers/of/of_net.c +++ b/drivers/of/of_net.c @@ -7,7 +7,6 @@ */ #include #include -#include #include #include #include -- cgit v1.2.3 From c2b71462d294cf517a0bc6e4fd6424d7cee5596f Mon Sep 17 00:00:00 2001 From: Alan Stern Date: Fri, 19 Apr 2019 13:52:38 -0400 Subject: USB: core: Fix bug caused by duplicate interface PM usage counter The syzkaller fuzzer reported a bug in the USB hub driver which turned out to be caused by a negative runtime-PM usage counter. This allowed a hub to be runtime suspended at a time when the driver did not expect it. The symptom is a WARNING issued because the hub's status URB is submitted while it is already active: URB 0000000031fb463e submitted while active WARNING: CPU: 0 PID: 2917 at drivers/usb/core/urb.c:363 The negative runtime-PM usage count was caused by an unfortunate design decision made when runtime PM was first implemented for USB. At that time, USB class drivers were allowed to unbind from their interfaces without balancing the usage counter (i.e., leaving it with a positive count). The core code would take care of setting the counter back to 0 before allowing another driver to bind to the interface. Later on when runtime PM was implemented for the entire kernel, the opposite decision was made: Drivers were required to balance their runtime-PM get and put calls. In order to maintain backward compatibility, however, the USB subsystem adapted to the new implementation by keeping an independent usage counter for each interface and using it to automatically adjust the normal usage counter back to 0 whenever a driver was unbound. This approach involves duplicating information, but what is worse, it doesn't work properly in cases where a USB class driver delays decrementing the usage counter until after the driver's disconnect() routine has returned and the counter has been adjusted back to 0. Doing so would cause the usage counter to become negative. There's even a warning about this in the USB power management documentation! As it happens, this is exactly what the hub driver does. The kick_hub_wq() routine increments the runtime-PM usage counter, and the corresponding decrement is carried out by hub_event() in the context of the hub_wq work-queue thread. This work routine may sometimes run after the driver has been unbound from its interface, and when it does it causes the usage counter to go negative. It is not possible for hub_disconnect() to wait for a pending hub_event() call to finish, because hub_disconnect() is called with the device lock held and hub_event() acquires that lock. The only feasible fix is to reverse the original design decision: remove the duplicate interface-specific usage counter and require USB drivers to balance their runtime PM gets and puts. As far as I know, all existing drivers currently do this. Signed-off-by: Alan Stern Reported-and-tested-by: syzbot+7634edaea4d0b341c625@syzkaller.appspotmail.com CC: Signed-off-by: Greg Kroah-Hartman --- Documentation/driver-api/usb/power-management.rst | 14 +++++++++----- drivers/usb/core/driver.c | 13 ------------- drivers/usb/storage/realtek_cr.c | 13 +++++-------- include/linux/usb.h | 2 -- 4 files changed, 14 insertions(+), 28 deletions(-) (limited to 'Documentation') diff --git a/Documentation/driver-api/usb/power-management.rst b/Documentation/driver-api/usb/power-management.rst index 79beb807996b..4a74cf6f2797 100644 --- a/Documentation/driver-api/usb/power-management.rst +++ b/Documentation/driver-api/usb/power-management.rst @@ -370,11 +370,15 @@ autosuspend the interface's device. When the usage counter is = 0 then the interface is considered to be idle, and the kernel may autosuspend the device. -Drivers need not be concerned about balancing changes to the usage -counter; the USB core will undo any remaining "get"s when a driver -is unbound from its interface. As a corollary, drivers must not call -any of the ``usb_autopm_*`` functions after their ``disconnect`` -routine has returned. +Drivers must be careful to balance their overall changes to the usage +counter. Unbalanced "get"s will remain in effect when a driver is +unbound from its interface, preventing the device from going into +runtime suspend should the interface be bound to a driver again. On +the other hand, drivers are allowed to achieve this balance by calling +the ``usb_autopm_*`` functions even after their ``disconnect`` routine +has returned -- say from within a work-queue routine -- provided they +retain an active reference to the interface (via ``usb_get_intf`` and +``usb_put_intf``). Drivers using the async routines are responsible for their own synchronization and mutual exclusion. diff --git a/drivers/usb/core/driver.c b/drivers/usb/core/driver.c index 8987cec9549d..ebcadaad89d1 100644 --- a/drivers/usb/core/driver.c +++ b/drivers/usb/core/driver.c @@ -473,11 +473,6 @@ static int usb_unbind_interface(struct device *dev) pm_runtime_disable(dev); pm_runtime_set_suspended(dev); - /* Undo any residual pm_autopm_get_interface_* calls */ - for (r = atomic_read(&intf->pm_usage_cnt); r > 0; --r) - usb_autopm_put_interface_no_suspend(intf); - atomic_set(&intf->pm_usage_cnt, 0); - if (!error) usb_autosuspend_device(udev); @@ -1633,7 +1628,6 @@ void usb_autopm_put_interface(struct usb_interface *intf) int status; usb_mark_last_busy(udev); - atomic_dec(&intf->pm_usage_cnt); status = pm_runtime_put_sync(&intf->dev); dev_vdbg(&intf->dev, "%s: cnt %d -> %d\n", __func__, atomic_read(&intf->dev.power.usage_count), @@ -1662,7 +1656,6 @@ void usb_autopm_put_interface_async(struct usb_interface *intf) int status; usb_mark_last_busy(udev); - atomic_dec(&intf->pm_usage_cnt); status = pm_runtime_put(&intf->dev); dev_vdbg(&intf->dev, "%s: cnt %d -> %d\n", __func__, atomic_read(&intf->dev.power.usage_count), @@ -1684,7 +1677,6 @@ void usb_autopm_put_interface_no_suspend(struct usb_interface *intf) struct usb_device *udev = interface_to_usbdev(intf); usb_mark_last_busy(udev); - atomic_dec(&intf->pm_usage_cnt); pm_runtime_put_noidle(&intf->dev); } EXPORT_SYMBOL_GPL(usb_autopm_put_interface_no_suspend); @@ -1715,8 +1707,6 @@ int usb_autopm_get_interface(struct usb_interface *intf) status = pm_runtime_get_sync(&intf->dev); if (status < 0) pm_runtime_put_sync(&intf->dev); - else - atomic_inc(&intf->pm_usage_cnt); dev_vdbg(&intf->dev, "%s: cnt %d -> %d\n", __func__, atomic_read(&intf->dev.power.usage_count), status); @@ -1750,8 +1740,6 @@ int usb_autopm_get_interface_async(struct usb_interface *intf) status = pm_runtime_get(&intf->dev); if (status < 0 && status != -EINPROGRESS) pm_runtime_put_noidle(&intf->dev); - else - atomic_inc(&intf->pm_usage_cnt); dev_vdbg(&intf->dev, "%s: cnt %d -> %d\n", __func__, atomic_read(&intf->dev.power.usage_count), status); @@ -1775,7 +1763,6 @@ void usb_autopm_get_interface_no_resume(struct usb_interface *intf) struct usb_device *udev = interface_to_usbdev(intf); usb_mark_last_busy(udev); - atomic_inc(&intf->pm_usage_cnt); pm_runtime_get_noresume(&intf->dev); } EXPORT_SYMBOL_GPL(usb_autopm_get_interface_no_resume); diff --git a/drivers/usb/storage/realtek_cr.c b/drivers/usb/storage/realtek_cr.c index 31b024441938..cc794e25a0b6 100644 --- a/drivers/usb/storage/realtek_cr.c +++ b/drivers/usb/storage/realtek_cr.c @@ -763,18 +763,16 @@ static void rts51x_suspend_timer_fn(struct timer_list *t) break; case RTS51X_STAT_IDLE: case RTS51X_STAT_SS: - usb_stor_dbg(us, "RTS51X_STAT_SS, intf->pm_usage_cnt:%d, power.usage:%d\n", - atomic_read(&us->pusb_intf->pm_usage_cnt), + usb_stor_dbg(us, "RTS51X_STAT_SS, power.usage:%d\n", atomic_read(&us->pusb_intf->dev.power.usage_count)); - if (atomic_read(&us->pusb_intf->pm_usage_cnt) > 0) { + if (atomic_read(&us->pusb_intf->dev.power.usage_count) > 0) { usb_stor_dbg(us, "Ready to enter SS state\n"); rts51x_set_stat(chip, RTS51X_STAT_SS); /* ignore mass storage interface's children */ pm_suspend_ignore_children(&us->pusb_intf->dev, true); usb_autopm_put_interface_async(us->pusb_intf); - usb_stor_dbg(us, "RTS51X_STAT_SS 01, intf->pm_usage_cnt:%d, power.usage:%d\n", - atomic_read(&us->pusb_intf->pm_usage_cnt), + usb_stor_dbg(us, "RTS51X_STAT_SS 01, power.usage:%d\n", atomic_read(&us->pusb_intf->dev.power.usage_count)); } break; @@ -807,11 +805,10 @@ static void rts51x_invoke_transport(struct scsi_cmnd *srb, struct us_data *us) int ret; if (working_scsi(srb)) { - usb_stor_dbg(us, "working scsi, intf->pm_usage_cnt:%d, power.usage:%d\n", - atomic_read(&us->pusb_intf->pm_usage_cnt), + usb_stor_dbg(us, "working scsi, power.usage:%d\n", atomic_read(&us->pusb_intf->dev.power.usage_count)); - if (atomic_read(&us->pusb_intf->pm_usage_cnt) <= 0) { + if (atomic_read(&us->pusb_intf->dev.power.usage_count) <= 0) { ret = usb_autopm_get_interface(us->pusb_intf); usb_stor_dbg(us, "working scsi, ret=%d\n", ret); } diff --git a/include/linux/usb.h b/include/linux/usb.h index 5e49e82c4368..ff010d1fd1c7 100644 --- a/include/linux/usb.h +++ b/include/linux/usb.h @@ -200,7 +200,6 @@ usb_find_last_int_out_endpoint(struct usb_host_interface *alt, * @dev: driver model's view of this device * @usb_dev: if an interface is bound to the USB major, this will point * to the sysfs representation for that device. - * @pm_usage_cnt: PM usage counter for this interface * @reset_ws: Used for scheduling resets from atomic context. * @resetting_device: USB core reset the device, so use alt setting 0 as * current; needs bandwidth alloc after reset. @@ -257,7 +256,6 @@ struct usb_interface { struct device dev; /* interface specific device info */ struct device *usb_dev; - atomic_t pm_usage_cnt; /* usage counter for autosuspend */ struct work_struct reset_ws; /* for resets in atomic context */ }; #define to_usb_interface(d) container_of(d, struct usb_interface, dev) -- cgit v1.2.3 From 40845f9f80217d0cdc8dd1687d161dd959e6acea Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Tue, 16 Apr 2019 10:28:24 +0800 Subject: docs/zh_CN: redirect CoC docs to Chinese version That gives more natural reading experience for Chinese. Signed-off-by: Alex Shi Cc: Harry Wei Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Jonathan Corbet --- .../translations/zh_CN/process/code-of-conduct-interpretation.rst | 2 +- Documentation/translations/zh_CN/process/code-of-conduct.rst | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/code-of-conduct-interpretation.rst b/Documentation/translations/zh_CN/process/code-of-conduct-interpretation.rst index a1daec0482e2..c323ce76e0cb 100644 --- a/Documentation/translations/zh_CN/process/code-of-conduct-interpretation.rst +++ b/Documentation/translations/zh_CN/process/code-of-conduct-interpretation.rst @@ -8,7 +8,7 @@ Linux内核贡献者契约行为准则解释 =============================== -:ref:`code_of_conduct` 准则是一个通用文档,旨在为几乎所有开源社区提供一套规则。 +:ref:`cn_code_of_conduct` 准则是一个通用文档,旨在为几乎所有开源社区提供一套规则。 每个开源社区都是独一无二的,Linux内核也不例外。因此,本文描述了Linux内核社区中 如何解释它。我们也不希望这种解释随着时间的推移是静态的,并将根据需要进行调整。 diff --git a/Documentation/translations/zh_CN/process/code-of-conduct.rst b/Documentation/translations/zh_CN/process/code-of-conduct.rst index 4054daafedf1..99024df058e9 100644 --- a/Documentation/translations/zh_CN/process/code-of-conduct.rst +++ b/Documentation/translations/zh_CN/process/code-of-conduct.rst @@ -69,4 +69,4 @@ https://www.contributor-covenant.org/version/1/4/code-of-conduct.html 获取。 解释 ==== -有关Linux内核社区如何解释此文档,请参阅 :ref:`code_of_conduct_interpretation` +有关Linux内核社区如何解释此文档,请参阅 :ref:`cn_code_of_conduct_interpretation` -- cgit v1.2.3 From 03f8264c9b60727ac2cb576c30d47beb2fc929eb Mon Sep 17 00:00:00 2001 From: Alex Shi Date: Tue, 16 Apr 2019 10:28:25 +0800 Subject: docs/zh_CN: fix typos in 1.Intro.rst file MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Fixed uncapital issues, thanks for Jonathan Neuschäfer, I am insensitive on captial custom as a non-captial native language reader. Sorry. Also fix a typo. And replace more colloquial words in Chinese. Signed-off-by: Alex Shi Reviewed-by: Jonathan Neuschäfer Signed-off-by: Jonathan Corbet --- Documentation/translations/zh_CN/process/1.Intro.rst | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/zh_CN/process/1.Intro.rst b/Documentation/translations/zh_CN/process/1.Intro.rst index 03bbafc00bd2..10a15f3dc282 100644 --- a/Documentation/translations/zh_CN/process/1.Intro.rst +++ b/Documentation/translations/zh_CN/process/1.Intro.rst @@ -79,13 +79,13 @@ Linux最引人注目的特性之一是这些开发人员可以访问它;任何 致谢 ---- -本文件由jonathan corbet撰写,corbet@lwn.net。以下人员的建议使之更为完善: +本文件由Jonathan Corbet撰写,corbet@lwn.net。以下人员的建议使之更为完善: Johannes Berg, James Berry, Alex Chiang, Roland Dreier, Randy Dunlap, Jake Edge, Jiri Kosina, Matt Mackall, Arthur Marsh, Amanda McPherson, Andrew Morton, Andrew Price, Tsugikazu Shibata, 和 Jochen Voß. -这项工作得到了Linux基金会的支持,特别感谢Amanda McPherson,他看到了这香工作 -的价值并使之发生。 +这项工作得到了Linux基金会的支持,特别感谢Amanda McPherson,他看到了这项工作 +的价值并把它变成现实。 代码进入主线的重要性 -------------------- -- cgit v1.2.3 From c1fe190c06723322f2dfac31d3b982c581e434ef Mon Sep 17 00:00:00 2001 From: Michael Neuling Date: Mon, 1 Apr 2019 17:03:12 +1100 Subject: powerpc: Add force enable of DAWR on P9 option This adds a flag so that the DAWR can be enabled on P9 via: echo Y > /sys/kernel/debug/powerpc/dawr_enable_dangerous The DAWR was previously force disabled on POWER9 in: 9654153158 powerpc: Disable DAWR in the base POWER9 CPU features Also see Documentation/powerpc/DAWR-POWER9.txt This is a dangerous setting, USE AT YOUR OWN RISK. Some users may not care about a bad user crashing their box (ie. single user/desktop systems) and really want the DAWR. This allows them to force enable DAWR. This flag can also be used to disable DAWR access. Once this is cleared, all DAWR access should be cleared immediately and your machine once again safe from crashing. Userspace may get confused by toggling this. If DAWR is force enabled/disabled between getting the number of breakpoints (via PTRACE_GETHWDBGINFO) and setting the breakpoint, userspace will get an inconsistent view of what's available. Similarly for guests. For the DAWR to be enabled in a KVM guest, the DAWR needs to be force enabled in the host AND the guest. For this reason, this won't work on POWERVM as it doesn't allow the HCALL to work. Writes of 'Y' to the dawr_enable_dangerous file will fail if the hypervisor doesn't support writing the DAWR. To double check the DAWR is working, run this kernel selftest: tools/testing/selftests/powerpc/ptrace/ptrace-hwbreak.c Any errors/failures/skips mean something is wrong. Signed-off-by: Michael Neuling Signed-off-by: Michael Ellerman --- Documentation/powerpc/DAWR-POWER9.txt | 32 +++++++++++++++++ arch/powerpc/include/asm/hw_breakpoint.h | 8 +++++ arch/powerpc/kernel/hw_breakpoint.c | 62 +++++++++++++++++++++++++++++++- arch/powerpc/kernel/process.c | 9 ++--- arch/powerpc/kernel/ptrace.c | 3 +- arch/powerpc/kvm/book3s_hv.c | 3 +- arch/powerpc/kvm/book3s_hv_rmhandlers.S | 23 ++++++------ 7 files changed, 123 insertions(+), 17 deletions(-) (limited to 'Documentation') diff --git a/Documentation/powerpc/DAWR-POWER9.txt b/Documentation/powerpc/DAWR-POWER9.txt index 2feaa6619658..bdec03650941 100644 --- a/Documentation/powerpc/DAWR-POWER9.txt +++ b/Documentation/powerpc/DAWR-POWER9.txt @@ -56,3 +56,35 @@ POWER9. Loads and stores to the watchpoint locations will not be trapped in GDB. The watchpoint is remembered, so if the guest is migrated back to the POWER8 host, it will start working again. +Force enabling the DAWR +============================= +Kernels (since ~v5.2) have an option to force enable the DAWR via: + + echo Y > /sys/kernel/debug/powerpc/dawr_enable_dangerous + +This enables the DAWR even on POWER9. + +This is a dangerous setting, USE AT YOUR OWN RISK. + +Some users may not care about a bad user crashing their box +(ie. single user/desktop systems) and really want the DAWR. This +allows them to force enable DAWR. + +This flag can also be used to disable DAWR access. Once this is +cleared, all DAWR access should be cleared immediately and your +machine once again safe from crashing. + +Userspace may get confused by toggling this. If DAWR is force +enabled/disabled between getting the number of breakpoints (via +PTRACE_GETHWDBGINFO) and setting the breakpoint, userspace will get an +inconsistent view of what's available. Similarly for guests. + +For the DAWR to be enabled in a KVM guest, the DAWR needs to be force +enabled in the host AND the guest. For this reason, this won't work on +POWERVM as it doesn't allow the HCALL to work. Writes of 'Y' to the +dawr_enable_dangerous file will fail if the hypervisor doesn't support +writing the DAWR. + +To double check the DAWR is working, run this kernel selftest: + tools/testing/selftests/powerpc/ptrace/ptrace-hwbreak.c +Any errors/failures/skips mean something is wrong. diff --git a/arch/powerpc/include/asm/hw_breakpoint.h b/arch/powerpc/include/asm/hw_breakpoint.h index ece4dc89c90b..0fe8c1e46bbc 100644 --- a/arch/powerpc/include/asm/hw_breakpoint.h +++ b/arch/powerpc/include/asm/hw_breakpoint.h @@ -90,10 +90,18 @@ static inline void hw_breakpoint_disable(void) extern void thread_change_pc(struct task_struct *tsk, struct pt_regs *regs); int hw_breakpoint_handler(struct die_args *args); +extern int set_dawr(struct arch_hw_breakpoint *brk); +extern bool dawr_force_enable; +static inline bool dawr_enabled(void) +{ + return dawr_force_enable; +} + #else /* CONFIG_HAVE_HW_BREAKPOINT */ static inline void hw_breakpoint_disable(void) { } static inline void thread_change_pc(struct task_struct *tsk, struct pt_regs *regs) { } +static inline bool dawr_enabled(void) { return false; } #endif /* CONFIG_HAVE_HW_BREAKPOINT */ #endif /* __KERNEL__ */ #endif /* _PPC_BOOK3S_64_HW_BREAKPOINT_H */ diff --git a/arch/powerpc/kernel/hw_breakpoint.c b/arch/powerpc/kernel/hw_breakpoint.c index fec8a6773119..da307dd93ee3 100644 --- a/arch/powerpc/kernel/hw_breakpoint.c +++ b/arch/powerpc/kernel/hw_breakpoint.c @@ -29,11 +29,15 @@ #include #include #include +#include +#include #include #include #include #include +#include +#include #include /* @@ -174,7 +178,7 @@ int hw_breakpoint_arch_parse(struct perf_event *bp, if (!ppc_breakpoint_available()) return -ENODEV; length_max = 8; /* DABR */ - if (cpu_has_feature(CPU_FTR_DAWR)) { + if (dawr_enabled()) { length_max = 512 ; /* 64 doublewords */ /* DAWR region can't cross 512 boundary */ if ((attr->bp_addr >> 9) != @@ -376,3 +380,59 @@ void hw_breakpoint_pmu_read(struct perf_event *bp) { /* TODO */ } + +bool dawr_force_enable; +EXPORT_SYMBOL_GPL(dawr_force_enable); + +static ssize_t dawr_write_file_bool(struct file *file, + const char __user *user_buf, + size_t count, loff_t *ppos) +{ + struct arch_hw_breakpoint null_brk = {0, 0, 0}; + size_t rc; + + /* Send error to user if they hypervisor won't allow us to write DAWR */ + if ((!dawr_force_enable) && + (firmware_has_feature(FW_FEATURE_LPAR)) && + (set_dawr(&null_brk) != H_SUCCESS)) + return -1; + + rc = debugfs_write_file_bool(file, user_buf, count, ppos); + if (rc) + return rc; + + /* If we are clearing, make sure all CPUs have the DAWR cleared */ + if (!dawr_force_enable) + smp_call_function((smp_call_func_t)set_dawr, &null_brk, 0); + + return rc; +} + +static const struct file_operations dawr_enable_fops = { + .read = debugfs_read_file_bool, + .write = dawr_write_file_bool, + .open = simple_open, + .llseek = default_llseek, +}; + +static int __init dawr_force_setup(void) +{ + dawr_force_enable = false; + + if (cpu_has_feature(CPU_FTR_DAWR)) { + /* Don't setup sysfs file for user control on P8 */ + dawr_force_enable = true; + return 0; + } + + if (PVR_VER(mfspr(SPRN_PVR)) == PVR_POWER9) { + /* Turn DAWR off by default, but allow admin to turn it on */ + dawr_force_enable = false; + debugfs_create_file_unsafe("dawr_enable_dangerous", 0600, + powerpc_debugfs_root, + &dawr_force_enable, + &dawr_enable_fops); + } + return 0; +} +arch_initcall(dawr_force_setup); diff --git a/arch/powerpc/kernel/process.c b/arch/powerpc/kernel/process.c index dd9e0d5386ee..225705aac814 100644 --- a/arch/powerpc/kernel/process.c +++ b/arch/powerpc/kernel/process.c @@ -67,6 +67,7 @@ #include #include #include +#include #include #include @@ -784,7 +785,7 @@ static inline int set_dabr(struct arch_hw_breakpoint *brk) return __set_dabr(dabr, dabrx); } -static inline int set_dawr(struct arch_hw_breakpoint *brk) +int set_dawr(struct arch_hw_breakpoint *brk) { unsigned long dawr, dawrx, mrd; @@ -816,7 +817,7 @@ void __set_breakpoint(struct arch_hw_breakpoint *brk) { memcpy(this_cpu_ptr(¤t_brk), brk, sizeof(*brk)); - if (cpu_has_feature(CPU_FTR_DAWR)) + if (dawr_enabled()) // Power8 or later set_dawr(brk); else if (!cpu_has_feature(CPU_FTR_ARCH_207S)) @@ -830,8 +831,8 @@ void __set_breakpoint(struct arch_hw_breakpoint *brk) /* Check if we have DAWR or DABR hardware */ bool ppc_breakpoint_available(void) { - if (cpu_has_feature(CPU_FTR_DAWR)) - return true; /* POWER8 DAWR */ + if (dawr_enabled()) + return true; /* POWER8 DAWR or POWER9 forced DAWR */ if (cpu_has_feature(CPU_FTR_ARCH_207S)) return false; /* POWER9 with DAWR disabled */ /* DABR: Everything but POWER8 and POWER9 */ diff --git a/arch/powerpc/kernel/ptrace.c b/arch/powerpc/kernel/ptrace.c index d9ac7d94656e..684b0b315c32 100644 --- a/arch/powerpc/kernel/ptrace.c +++ b/arch/powerpc/kernel/ptrace.c @@ -43,6 +43,7 @@ #include #include #include +#include #define CREATE_TRACE_POINTS #include @@ -3088,7 +3089,7 @@ long arch_ptrace(struct task_struct *child, long request, dbginfo.sizeof_condition = 0; #ifdef CONFIG_HAVE_HW_BREAKPOINT dbginfo.features = PPC_DEBUG_FEATURE_DATA_BP_RANGE; - if (cpu_has_feature(CPU_FTR_DAWR)) + if (dawr_enabled()) dbginfo.features |= PPC_DEBUG_FEATURE_DATA_BP_DAWR; #else dbginfo.features = 0; diff --git a/arch/powerpc/kvm/book3s_hv.c b/arch/powerpc/kvm/book3s_hv.c index 06964350b97a..0fab0a201027 100644 --- a/arch/powerpc/kvm/book3s_hv.c +++ b/arch/powerpc/kvm/book3s_hv.c @@ -74,6 +74,7 @@ #include #include #include +#include #include "book3s.h" @@ -3374,7 +3375,7 @@ static int kvmhv_load_hv_regs_and_go(struct kvm_vcpu *vcpu, u64 time_limit, mtspr(SPRN_PURR, vcpu->arch.purr); mtspr(SPRN_SPURR, vcpu->arch.spurr); - if (cpu_has_feature(CPU_FTR_DAWR)) { + if (dawr_enabled()) { mtspr(SPRN_DAWR, vcpu->arch.dawr); mtspr(SPRN_DAWRX, vcpu->arch.dawrx); } diff --git a/arch/powerpc/kvm/book3s_hv_rmhandlers.S b/arch/powerpc/kvm/book3s_hv_rmhandlers.S index 3a5e719ef032..139027c62dc2 100644 --- a/arch/powerpc/kvm/book3s_hv_rmhandlers.S +++ b/arch/powerpc/kvm/book3s_hv_rmhandlers.S @@ -822,18 +822,21 @@ END_FTR_SECTION_IFCLR(CPU_FTR_ARCH_207S) mtspr SPRN_IAMR, r5 mtspr SPRN_PSPB, r6 mtspr SPRN_FSCR, r7 - ld r5, VCPU_DAWR(r4) - ld r6, VCPU_DAWRX(r4) - ld r7, VCPU_CIABR(r4) - ld r8, VCPU_TAR(r4) /* * Handle broken DAWR case by not writing it. This means we * can still store the DAWR register for migration. */ -BEGIN_FTR_SECTION + LOAD_REG_ADDR(r5, dawr_force_enable) + lbz r5, 0(r5) + cmpdi r5, 0 + beq 1f + ld r5, VCPU_DAWR(r4) + ld r6, VCPU_DAWRX(r4) mtspr SPRN_DAWR, r5 mtspr SPRN_DAWRX, r6 -END_FTR_SECTION_IFSET(CPU_FTR_DAWR) +1: + ld r7, VCPU_CIABR(r4) + ld r8, VCPU_TAR(r4) mtspr SPRN_CIABR, r7 mtspr SPRN_TAR, r8 ld r5, VCPU_IC(r4) @@ -2513,11 +2516,11 @@ END_FTR_SECTION_IFSET(CPU_FTR_ARCH_207S) blr 2: -BEGIN_FTR_SECTION - /* POWER9 with disabled DAWR */ + LOAD_REG_ADDR(r11, dawr_force_enable) + lbz r11, 0(r11) + cmpdi r11, 0 li r3, H_HARDWARE - blr -END_FTR_SECTION_IFCLR(CPU_FTR_DAWR) + beqlr /* Emulate H_SET_DABR/X on P8 for the sake of compat mode guests */ rlwimi r5, r4, 5, DAWRX_DR | DAWRX_DW rlwimi r5, r4, 2, DAWRX_WT -- cgit v1.2.3 From 4f158e11b14bb08ed18b33d5a73415bfb605408f Mon Sep 17 00:00:00 2001 From: Marek Vasut Date: Fri, 12 Apr 2019 12:49:51 +0200 Subject: dt-bindings: arm: fsl: Add devicetree binding for M53 Menlo board. Add devicetree binding for iMX53 SoC based M53 Menlo board. Signed-off-by: Marek Vasut Cc: Rob Herring Cc: Shawn Guo Cc: Fabio Estevam Cc: NXP Linux Team Cc: devicetree@vger.kernel.org To: linux-arm-kernel@lists.infradead.org Signed-off-by: Shawn Guo --- Documentation/devicetree/bindings/arm/fsl.yaml | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/fsl.yaml b/Documentation/devicetree/bindings/arm/fsl.yaml index 06762fe57227..b3c5de542123 100644 --- a/Documentation/devicetree/bindings/arm/fsl.yaml +++ b/Documentation/devicetree/bindings/arm/fsl.yaml @@ -74,6 +74,7 @@ properties: - fsl,imx53-evk - fsl,imx53-qsb - fsl,imx53-smd + - menlo,m53menlo - const: fsl,imx53 - description: i.MX6Q based Boards -- cgit v1.2.3 From 0fb1c25ab523614b056ace11be67aac8f8ccabb1 Mon Sep 17 00:00:00 2001 From: Christophe Leroy Date: Thu, 18 Apr 2019 16:51:19 +1000 Subject: powerpc: Add skeleton for Kernel Userspace Execution Prevention This patch adds a skeleton for Kernel Userspace Execution Prevention. Then subarches implementing it have to define CONFIG_PPC_HAVE_KUEP and provide setup_kuep() function. Signed-off-by: Christophe Leroy [mpe: Don't split strings, use pr_crit_ratelimited()] Signed-off-by: Michael Ellerman --- Documentation/admin-guide/kernel-parameters.txt | 2 +- arch/powerpc/include/asm/kup.h | 6 ++++++ arch/powerpc/mm/fault.c | 9 ++++----- arch/powerpc/mm/init-common.c | 11 +++++++++++ arch/powerpc/platforms/Kconfig.cputype | 12 ++++++++++++ 5 files changed, 34 insertions(+), 6 deletions(-) (limited to 'Documentation') diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt index 2b8ee90bb644..a53df74589e5 100644 --- a/Documentation/admin-guide/kernel-parameters.txt +++ b/Documentation/admin-guide/kernel-parameters.txt @@ -2843,7 +2843,7 @@ Disable SMAP (Supervisor Mode Access Prevention) even if it is supported by processor. - nosmep [X86] + nosmep [X86,PPC] Disable SMEP (Supervisor Mode Execution Prevention) even if it is supported by processor. diff --git a/arch/powerpc/include/asm/kup.h b/arch/powerpc/include/asm/kup.h index 7a88b8b9b54d..a2a959cb4e36 100644 --- a/arch/powerpc/include/asm/kup.h +++ b/arch/powerpc/include/asm/kup.h @@ -6,6 +6,12 @@ void setup_kup(void); +#ifdef CONFIG_PPC_KUEP +void setup_kuep(bool disabled); +#else +static inline void setup_kuep(bool disabled) { } +#endif /* CONFIG_PPC_KUEP */ + #endif /* !__ASSEMBLY__ */ #endif /* _ASM_POWERPC_KUP_H_ */ diff --git a/arch/powerpc/mm/fault.c b/arch/powerpc/mm/fault.c index 887f11bcf330..3384354abc1d 100644 --- a/arch/powerpc/mm/fault.c +++ b/arch/powerpc/mm/fault.c @@ -229,11 +229,10 @@ static bool bad_kernel_fault(bool is_exec, unsigned long error_code, /* NX faults set DSISR_PROTFAULT on the 8xx, DSISR_NOEXEC_OR_G on others */ if (is_exec && (error_code & (DSISR_NOEXEC_OR_G | DSISR_KEYFAULT | DSISR_PROTFAULT))) { - printk_ratelimited(KERN_CRIT "kernel tried to execute" - " exec-protected page (%lx) -" - "exploit attempt? (uid: %d)\n", - address, from_kuid(&init_user_ns, - current_uid())); + pr_crit_ratelimited("kernel tried to execute %s page (%lx) - exploit attempt? (uid: %d)\n", + address >= TASK_SIZE ? "exec-protected" : "user", + address, + from_kuid(&init_user_ns, current_uid())); } return is_exec || (address >= TASK_SIZE); } diff --git a/arch/powerpc/mm/init-common.c b/arch/powerpc/mm/init-common.c index 36d28e872289..83f95a5565d6 100644 --- a/arch/powerpc/mm/init-common.c +++ b/arch/powerpc/mm/init-common.c @@ -26,8 +26,19 @@ #include #include +static bool disable_kuep = !IS_ENABLED(CONFIG_PPC_KUEP); + +static int __init parse_nosmep(char *p) +{ + disable_kuep = true; + pr_warn("Disabling Kernel Userspace Execution Prevention\n"); + return 0; +} +early_param("nosmep", parse_nosmep); + void __init setup_kup(void) { + setup_kuep(disable_kuep); } #define CTOR(shift) static void ctor_##shift(void *addr) \ diff --git a/arch/powerpc/platforms/Kconfig.cputype b/arch/powerpc/platforms/Kconfig.cputype index 842b2c7e156a..7d30bbbaa3c1 100644 --- a/arch/powerpc/platforms/Kconfig.cputype +++ b/arch/powerpc/platforms/Kconfig.cputype @@ -345,6 +345,18 @@ config PPC_RADIX_MMU_DEFAULT If you're unsure, say Y. +config PPC_HAVE_KUEP + bool + +config PPC_KUEP + bool "Kernel Userspace Execution Prevention" + depends on PPC_HAVE_KUEP + default y + help + Enable support for Kernel Userspace Execution Prevention (KUEP) + + If you're unsure, say Y. + config ARCH_ENABLE_HUGEPAGE_MIGRATION def_bool y depends on PPC_BOOK3S_64 && HUGETLB_PAGE && MIGRATION -- cgit v1.2.3 From de78a9c42a790011f179bc94a7da3f5d8721f4cc Mon Sep 17 00:00:00 2001 From: Christophe Leroy Date: Thu, 18 Apr 2019 16:51:20 +1000 Subject: powerpc: Add a framework for Kernel Userspace Access Protection This patch implements a framework for Kernel Userspace Access Protection. Then subarches will have the possibility to provide their own implementation by providing setup_kuap() and allow/prevent_user_access(). Some platforms will need to know the area accessed and whether it is accessed from read, write or both. Therefore source, destination and size and handed over to the two functions. mpe: Rename to allow/prevent rather than unlock/lock, and add read/write wrappers. Drop the 32-bit code for now until we have an implementation for it. Add kuap to pt_regs for 64-bit as well as 32-bit. Don't split strings, use pr_crit_ratelimited(). Signed-off-by: Christophe Leroy Signed-off-by: Russell Currey Signed-off-by: Michael Ellerman --- Documentation/admin-guide/kernel-parameters.txt | 2 +- arch/powerpc/include/asm/futex.h | 4 +++ arch/powerpc/include/asm/kup.h | 32 +++++++++++++++++++++ arch/powerpc/include/asm/ptrace.h | 11 +++++-- arch/powerpc/include/asm/uaccess.h | 38 +++++++++++++++++++------ arch/powerpc/kernel/asm-offsets.c | 4 +++ arch/powerpc/lib/checksum_wrappers.c | 4 +++ arch/powerpc/mm/fault.c | 19 ++++++++++--- arch/powerpc/mm/init-common.c | 10 +++++++ arch/powerpc/platforms/Kconfig.cputype | 12 ++++++++ 10 files changed, 121 insertions(+), 15 deletions(-) (limited to 'Documentation') diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt index a53df74589e5..c45a19d654f3 100644 --- a/Documentation/admin-guide/kernel-parameters.txt +++ b/Documentation/admin-guide/kernel-parameters.txt @@ -2839,7 +2839,7 @@ noexec=on: enable non-executable mappings (default) noexec=off: disable non-executable mappings - nosmap [X86] + nosmap [X86,PPC] Disable SMAP (Supervisor Mode Access Prevention) even if it is supported by processor. diff --git a/arch/powerpc/include/asm/futex.h b/arch/powerpc/include/asm/futex.h index 88b38b37c21b..3a6aa57b9d90 100644 --- a/arch/powerpc/include/asm/futex.h +++ b/arch/powerpc/include/asm/futex.h @@ -35,6 +35,7 @@ static inline int arch_futex_atomic_op_inuser(int op, int oparg, int *oval, { int oldval = 0, ret; + allow_write_to_user(uaddr, sizeof(*uaddr)); pagefault_disable(); switch (op) { @@ -62,6 +63,7 @@ static inline int arch_futex_atomic_op_inuser(int op, int oparg, int *oval, if (!ret) *oval = oldval; + prevent_write_to_user(uaddr, sizeof(*uaddr)); return ret; } @@ -75,6 +77,7 @@ futex_atomic_cmpxchg_inatomic(u32 *uval, u32 __user *uaddr, if (!access_ok(uaddr, sizeof(u32))) return -EFAULT; + allow_write_to_user(uaddr, sizeof(*uaddr)); __asm__ __volatile__ ( PPC_ATOMIC_ENTRY_BARRIER "1: lwarx %1,0,%3 # futex_atomic_cmpxchg_inatomic\n\ @@ -95,6 +98,7 @@ futex_atomic_cmpxchg_inatomic(u32 *uval, u32 __user *uaddr, : "cc", "memory"); *uval = prev; + prevent_write_to_user(uaddr, sizeof(*uaddr)); return ret; } diff --git a/arch/powerpc/include/asm/kup.h b/arch/powerpc/include/asm/kup.h index a2a959cb4e36..4d78b9d8c99c 100644 --- a/arch/powerpc/include/asm/kup.h +++ b/arch/powerpc/include/asm/kup.h @@ -4,6 +4,8 @@ #ifndef __ASSEMBLY__ +#include + void setup_kup(void); #ifdef CONFIG_PPC_KUEP @@ -12,6 +14,36 @@ void setup_kuep(bool disabled); static inline void setup_kuep(bool disabled) { } #endif /* CONFIG_PPC_KUEP */ +#ifdef CONFIG_PPC_KUAP +void setup_kuap(bool disabled); +#else +static inline void setup_kuap(bool disabled) { } +static inline void allow_user_access(void __user *to, const void __user *from, + unsigned long size) { } +static inline void prevent_user_access(void __user *to, const void __user *from, + unsigned long size) { } +#endif /* CONFIG_PPC_KUAP */ + +static inline void allow_read_from_user(const void __user *from, unsigned long size) +{ + allow_user_access(NULL, from, size); +} + +static inline void allow_write_to_user(void __user *to, unsigned long size) +{ + allow_user_access(to, NULL, size); +} + +static inline void prevent_read_from_user(const void __user *from, unsigned long size) +{ + prevent_user_access(NULL, from, size); +} + +static inline void prevent_write_to_user(void __user *to, unsigned long size) +{ + prevent_user_access(to, NULL, size); +} + #endif /* !__ASSEMBLY__ */ #endif /* _ASM_POWERPC_KUP_H_ */ diff --git a/arch/powerpc/include/asm/ptrace.h b/arch/powerpc/include/asm/ptrace.h index 64271e562fed..6f047730e642 100644 --- a/arch/powerpc/include/asm/ptrace.h +++ b/arch/powerpc/include/asm/ptrace.h @@ -52,10 +52,17 @@ struct pt_regs }; }; + union { + struct { #ifdef CONFIG_PPC64 - unsigned long ppr; - unsigned long __pad; /* Maintain 16 byte interrupt stack alignment */ + unsigned long ppr; +#endif +#ifdef CONFIG_PPC_KUAP + unsigned long kuap; #endif + }; + unsigned long __pad[2]; /* Maintain 16 byte interrupt stack alignment */ + }; }; #endif diff --git a/arch/powerpc/include/asm/uaccess.h b/arch/powerpc/include/asm/uaccess.h index 4d6d905e9138..76f34346b642 100644 --- a/arch/powerpc/include/asm/uaccess.h +++ b/arch/powerpc/include/asm/uaccess.h @@ -6,6 +6,7 @@ #include #include #include +#include /* * The fs value determines whether argument validity checking should be @@ -140,6 +141,7 @@ extern long __put_user_bad(void); #define __put_user_size(x, ptr, size, retval) \ do { \ retval = 0; \ + allow_write_to_user(ptr, size); \ switch (size) { \ case 1: __put_user_asm(x, ptr, retval, "stb"); break; \ case 2: __put_user_asm(x, ptr, retval, "sth"); break; \ @@ -147,6 +149,7 @@ do { \ case 8: __put_user_asm2(x, ptr, retval); break; \ default: __put_user_bad(); \ } \ + prevent_write_to_user(ptr, size); \ } while (0) #define __put_user_nocheck(x, ptr, size) \ @@ -239,6 +242,7 @@ do { \ __chk_user_ptr(ptr); \ if (size > sizeof(x)) \ (x) = __get_user_bad(); \ + allow_read_from_user(ptr, size); \ switch (size) { \ case 1: __get_user_asm(x, ptr, retval, "lbz"); break; \ case 2: __get_user_asm(x, ptr, retval, "lhz"); break; \ @@ -246,6 +250,7 @@ do { \ case 8: __get_user_asm2(x, ptr, retval); break; \ default: (x) = __get_user_bad(); \ } \ + prevent_read_from_user(ptr, size); \ } while (0) /* @@ -305,15 +310,21 @@ extern unsigned long __copy_tofrom_user(void __user *to, static inline unsigned long raw_copy_in_user(void __user *to, const void __user *from, unsigned long n) { - return __copy_tofrom_user(to, from, n); + unsigned long ret; + + allow_user_access(to, from, n); + ret = __copy_tofrom_user(to, from, n); + prevent_user_access(to, from, n); + return ret; } #endif /* __powerpc64__ */ static inline unsigned long raw_copy_from_user(void *to, const void __user *from, unsigned long n) { + unsigned long ret; if (__builtin_constant_p(n) && (n <= 8)) { - unsigned long ret = 1; + ret = 1; switch (n) { case 1: @@ -338,14 +349,18 @@ static inline unsigned long raw_copy_from_user(void *to, } barrier_nospec(); - return __copy_tofrom_user((__force void __user *)to, from, n); + allow_read_from_user(from, n); + ret = __copy_tofrom_user((__force void __user *)to, from, n); + prevent_read_from_user(from, n); + return ret; } static inline unsigned long raw_copy_to_user(void __user *to, const void *from, unsigned long n) { + unsigned long ret; if (__builtin_constant_p(n) && (n <= 8)) { - unsigned long ret = 1; + ret = 1; switch (n) { case 1: @@ -365,17 +380,24 @@ static inline unsigned long raw_copy_to_user(void __user *to, return 0; } - return __copy_tofrom_user(to, (__force const void __user *)from, n); + allow_write_to_user(to, n); + ret = __copy_tofrom_user(to, (__force const void __user *)from, n); + prevent_write_to_user(to, n); + return ret; } extern unsigned long __clear_user(void __user *addr, unsigned long size); static inline unsigned long clear_user(void __user *addr, unsigned long size) { + unsigned long ret = size; might_fault(); - if (likely(access_ok(addr, size))) - return __clear_user(addr, size); - return size; + if (likely(access_ok(addr, size))) { + allow_write_to_user(addr, size); + ret = __clear_user(addr, size); + prevent_write_to_user(addr, size); + } + return ret; } extern long strncpy_from_user(char *dst, const char __user *src, long count); diff --git a/arch/powerpc/kernel/asm-offsets.c b/arch/powerpc/kernel/asm-offsets.c index 86a61e5f8285..66202e02fee2 100644 --- a/arch/powerpc/kernel/asm-offsets.c +++ b/arch/powerpc/kernel/asm-offsets.c @@ -332,6 +332,10 @@ int main(void) STACK_PT_REGS_OFFSET(_PPR, ppr); #endif /* CONFIG_PPC64 */ +#ifdef CONFIG_PPC_KUAP + STACK_PT_REGS_OFFSET(STACK_REGS_KUAP, kuap); +#endif + #if defined(CONFIG_PPC32) #if defined(CONFIG_BOOKE) || defined(CONFIG_40x) DEFINE(EXC_LVL_SIZE, STACK_EXC_LVL_FRAME_SIZE); diff --git a/arch/powerpc/lib/checksum_wrappers.c b/arch/powerpc/lib/checksum_wrappers.c index 890d4ddd91d6..bb9307ce2440 100644 --- a/arch/powerpc/lib/checksum_wrappers.c +++ b/arch/powerpc/lib/checksum_wrappers.c @@ -29,6 +29,7 @@ __wsum csum_and_copy_from_user(const void __user *src, void *dst, unsigned int csum; might_sleep(); + allow_read_from_user(src, len); *err_ptr = 0; @@ -60,6 +61,7 @@ __wsum csum_and_copy_from_user(const void __user *src, void *dst, } out: + prevent_read_from_user(src, len); return (__force __wsum)csum; } EXPORT_SYMBOL(csum_and_copy_from_user); @@ -70,6 +72,7 @@ __wsum csum_and_copy_to_user(const void *src, void __user *dst, int len, unsigned int csum; might_sleep(); + allow_write_to_user(dst, len); *err_ptr = 0; @@ -97,6 +100,7 @@ __wsum csum_and_copy_to_user(const void *src, void __user *dst, int len, } out: + prevent_write_to_user(dst, len); return (__force __wsum)csum; } EXPORT_SYMBOL(csum_and_copy_to_user); diff --git a/arch/powerpc/mm/fault.c b/arch/powerpc/mm/fault.c index 3384354abc1d..463d1e9d026e 100644 --- a/arch/powerpc/mm/fault.c +++ b/arch/powerpc/mm/fault.c @@ -223,9 +223,11 @@ static int mm_fault_error(struct pt_regs *regs, unsigned long addr, } /* Is this a bad kernel fault ? */ -static bool bad_kernel_fault(bool is_exec, unsigned long error_code, +static bool bad_kernel_fault(struct pt_regs *regs, unsigned long error_code, unsigned long address) { + int is_exec = TRAP(regs) == 0x400; + /* NX faults set DSISR_PROTFAULT on the 8xx, DSISR_NOEXEC_OR_G on others */ if (is_exec && (error_code & (DSISR_NOEXEC_OR_G | DSISR_KEYFAULT | DSISR_PROTFAULT))) { @@ -234,7 +236,15 @@ static bool bad_kernel_fault(bool is_exec, unsigned long error_code, address, from_kuid(&init_user_ns, current_uid())); } - return is_exec || (address >= TASK_SIZE); + + if (!is_exec && address < TASK_SIZE && (error_code & DSISR_PROTFAULT) && + !search_exception_tables(regs->nip)) { + pr_crit_ratelimited("Kernel attempted to access user page (%lx) - exploit attempt? (uid: %d)\n", + address, + from_kuid(&init_user_ns, current_uid())); + } + + return is_exec || (address >= TASK_SIZE) || !search_exception_tables(regs->nip); } static bool bad_stack_expansion(struct pt_regs *regs, unsigned long address, @@ -454,9 +464,10 @@ static int __do_page_fault(struct pt_regs *regs, unsigned long address, /* * The kernel should never take an execute fault nor should it - * take a page fault to a kernel address. + * take a page fault to a kernel address or a page fault to a user + * address outside of dedicated places */ - if (unlikely(!is_user && bad_kernel_fault(is_exec, error_code, address))) + if (unlikely(!is_user && bad_kernel_fault(regs, error_code, address))) return SIGSEGV; /* diff --git a/arch/powerpc/mm/init-common.c b/arch/powerpc/mm/init-common.c index 83f95a5565d6..ecaedfff9992 100644 --- a/arch/powerpc/mm/init-common.c +++ b/arch/powerpc/mm/init-common.c @@ -27,6 +27,7 @@ #include static bool disable_kuep = !IS_ENABLED(CONFIG_PPC_KUEP); +static bool disable_kuap = !IS_ENABLED(CONFIG_PPC_KUAP); static int __init parse_nosmep(char *p) { @@ -36,9 +37,18 @@ static int __init parse_nosmep(char *p) } early_param("nosmep", parse_nosmep); +static int __init parse_nosmap(char *p) +{ + disable_kuap = true; + pr_warn("Disabling Kernel Userspace Access Protection\n"); + return 0; +} +early_param("nosmap", parse_nosmap); + void __init setup_kup(void) { setup_kuep(disable_kuep); + setup_kuap(disable_kuap); } #define CTOR(shift) static void ctor_##shift(void *addr) \ diff --git a/arch/powerpc/platforms/Kconfig.cputype b/arch/powerpc/platforms/Kconfig.cputype index 7d30bbbaa3c1..457fc3a5ed93 100644 --- a/arch/powerpc/platforms/Kconfig.cputype +++ b/arch/powerpc/platforms/Kconfig.cputype @@ -357,6 +357,18 @@ config PPC_KUEP If you're unsure, say Y. +config PPC_HAVE_KUAP + bool + +config PPC_KUAP + bool "Kernel Userspace Access Protection" + depends on PPC_HAVE_KUAP + default y + help + Enable support for Kernel Userspace Access Protection (KUAP) + + If you're unsure, say Y. + config ARCH_ENABLE_HUGEPAGE_MIGRATION def_bool y depends on PPC_BOOK3S_64 && HUGETLB_PAGE && MIGRATION -- cgit v1.2.3 From 39420fe04f093c15e1674ef56dbae0df109738ec Mon Sep 17 00:00:00 2001 From: Corentin Labbe Date: Sat, 20 Apr 2019 18:14:33 +0000 Subject: dt-bindings: add an explanation for internal phy-mode When working on the Allwinner internal PHY, the first work was to use the "internal" mode, but some answer was made my mail on what are really internal mean for PHY. This patch write that in the doc. Signed-off-by: Corentin Labbe Reviewed-by: Andrew Lunn Signed-off-by: David S. Miller --- Documentation/devicetree/bindings/net/ethernet.txt | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/net/ethernet.txt b/Documentation/devicetree/bindings/net/ethernet.txt index 2974e63ba311..a68621580584 100644 --- a/Documentation/devicetree/bindings/net/ethernet.txt +++ b/Documentation/devicetree/bindings/net/ethernet.txt @@ -16,7 +16,8 @@ Documentation/devicetree/bindings/phy/phy-bindings.txt. Specification). - phy-mode: string, operation mode of the PHY interface. This is now a de-facto standard property; supported values are: - * "internal" + * "internal" (Internal means there is not a standard bus between the MAC and + the PHY, something proprietary is being used to embed the PHY in the MAC.) * "mii" * "gmii" * "sgmii" -- cgit v1.2.3 From 26d1b8586b4fe14814ff4fd471cfc56014359e59 Mon Sep 17 00:00:00 2001 From: Corentin Labbe Date: Sat, 20 Apr 2019 16:43:01 +0000 Subject: Documentation: decnet: remove reference to CONFIG_DECNET_ROUTE_FWMARK CONFIG_DECNET_ROUTE_FWMARK was removed in commit 47dcf0cb1005 ("[NET]: Rethink mark field in struct flowi") Since nothing replace it (and nothindg need to replace it, simply remove it from documentation. Signed-off-by: Corentin Labbe Signed-off-by: David S. Miller --- Documentation/networking/decnet.txt | 2 -- 1 file changed, 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/networking/decnet.txt b/Documentation/networking/decnet.txt index e12a4900cf72..d192f8b9948b 100644 --- a/Documentation/networking/decnet.txt +++ b/Documentation/networking/decnet.txt @@ -22,8 +22,6 @@ you'll need the following options as well... CONFIG_DECNET_ROUTER (to be able to add/delete routes) CONFIG_NETFILTER (will be required for the DECnet routing daemon) - CONFIG_DECNET_ROUTE_FWMARK is optional - Don't turn on SIOCGIFCONF support for DECnet unless you are really sure that you need it, in general you won't and it can cause ifconfig to malfunction. -- cgit v1.2.3 From f1fb64b04bf414ab04e31ac107bb28137105c5fd Mon Sep 17 00:00:00 2001 From: Robert Shearman Date: Thu, 28 Feb 2019 11:43:43 +0000 Subject: i2c: mux: pca954x: allow management of device idle state via sysfs The behaviour, by default, to not deselect after each transfer is unsafe when there is a device with an address that conflicts with another device on another mux on the same parent bus, and it may not be convenient to use devicetree to set the deselect mux, e.g. when running on x86_64 when ACPI is used to discover most of the device hierarchy. Therefore, provide the ability to set the idle state behaviour using a new sysfs file, idle_state as a complement to the method of instantiating the device via sysfs. The possible behaviours are disconnect, i.e. to deselect all channels from the mux, as-is (the default), i.e. leave the last channel selected, and set a predetermined channel. The current behaviour of leaving the channel as-is after each transaction is preserved. Signed-off-by: Robert Shearman Signed-off-by: Peter Rosin --- .../ABI/testing/sysfs-bus-i2c-devices-pca954x | 20 +++++ drivers/i2c/muxes/i2c-mux-pca954x.c | 85 ++++++++++++++++++++-- 2 files changed, 97 insertions(+), 8 deletions(-) create mode 100644 Documentation/ABI/testing/sysfs-bus-i2c-devices-pca954x (limited to 'Documentation') diff --git a/Documentation/ABI/testing/sysfs-bus-i2c-devices-pca954x b/Documentation/ABI/testing/sysfs-bus-i2c-devices-pca954x new file mode 100644 index 000000000000..0b0de8cd0d13 --- /dev/null +++ b/Documentation/ABI/testing/sysfs-bus-i2c-devices-pca954x @@ -0,0 +1,20 @@ +What: /sys/bus/i2c/.../idle_state +Date: January 2019 +KernelVersion: 5.2 +Contact: Robert Shearman +Description: + Value that exists only for mux devices that can be + written to control the behaviour of the multiplexer on + idle. Possible values: + -2 - disconnect on idle, i.e. deselect the last used + channel, which is useful when there is a device + with an address that conflicts with another + device on another mux on the same parent bus. + -1 - leave the mux as-is, which is the most optimal + setting in terms of I2C operations and is the + default mode. + 0.. - set the mux to a predetermined channel, + which is useful if there is one channel that is + used almost always, and you want to reduce the + latency for normal operations after rare + transactions on other channels diff --git a/drivers/i2c/muxes/i2c-mux-pca954x.c b/drivers/i2c/muxes/i2c-mux-pca954x.c index e32fef560684..923aa3a5a3dc 100644 --- a/drivers/i2c/muxes/i2c-mux-pca954x.c +++ b/drivers/i2c/muxes/i2c-mux-pca954x.c @@ -49,6 +49,7 @@ #include #include #include +#include #define PCA954X_MAX_NCHANS 8 @@ -84,7 +85,9 @@ struct pca954x { const struct chip_desc *chip; u8 last_chan; /* last register value */ - u8 deselect; + /* MUX_IDLE_AS_IS, MUX_IDLE_DISCONNECT or >= 0 for channel */ + s8 idle_state; + struct i2c_client *client; struct irq_domain *irq; @@ -253,15 +256,71 @@ static int pca954x_deselect_mux(struct i2c_mux_core *muxc, u32 chan) { struct pca954x *data = i2c_mux_priv(muxc); struct i2c_client *client = data->client; + s8 idle_state; + + idle_state = READ_ONCE(data->idle_state); + if (idle_state >= 0) + /* Set the mux back to a predetermined channel */ + return pca954x_select_chan(muxc, idle_state); + + if (idle_state == MUX_IDLE_DISCONNECT) { + /* Deselect active channel */ + data->last_chan = 0; + return pca954x_reg_write(muxc->parent, client, + data->last_chan); + } - if (!(data->deselect & (1 << chan))) - return 0; + /* otherwise leave as-is */ - /* Deselect active channel */ - data->last_chan = 0; - return pca954x_reg_write(muxc->parent, client, data->last_chan); + return 0; +} + +static ssize_t idle_state_show(struct device *dev, + struct device_attribute *attr, + char *buf) +{ + struct i2c_client *client = to_i2c_client(dev); + struct i2c_mux_core *muxc = i2c_get_clientdata(client); + struct pca954x *data = i2c_mux_priv(muxc); + + return sprintf(buf, "%d\n", READ_ONCE(data->idle_state)); +} + +static ssize_t idle_state_store(struct device *dev, + struct device_attribute *attr, + const char *buf, size_t count) +{ + struct i2c_client *client = to_i2c_client(dev); + struct i2c_mux_core *muxc = i2c_get_clientdata(client); + struct pca954x *data = i2c_mux_priv(muxc); + int val; + int ret; + + ret = kstrtoint(buf, 0, &val); + if (ret < 0) + return ret; + + if (val != MUX_IDLE_AS_IS && val != MUX_IDLE_DISCONNECT && + (val < 0 || val >= data->chip->nchans)) + return -EINVAL; + + i2c_lock_bus(muxc->parent, I2C_LOCK_SEGMENT); + + WRITE_ONCE(data->idle_state, val); + /* + * Set the mux into a state consistent with the new + * idle_state. + */ + if (data->last_chan || val != MUX_IDLE_DISCONNECT) + ret = pca954x_deselect_mux(muxc, 0); + + i2c_unlock_bus(muxc->parent, I2C_LOCK_SEGMENT); + + return ret < 0 ? ret : count; } +static DEVICE_ATTR_RW(idle_state); + static irqreturn_t pca954x_irq_handler(int irq, void *dev_id) { struct pca954x *data = dev_id; @@ -328,8 +387,11 @@ static int pca954x_irq_setup(struct i2c_mux_core *muxc) static void pca954x_cleanup(struct i2c_mux_core *muxc) { struct pca954x *data = i2c_mux_priv(muxc); + struct i2c_client *client = data->client; int c, irq; + device_remove_file(&client->dev, &dev_attr_idle_state); + if (data->irq) { for (c = 0; c < data->chip->nchans; c++) { irq = irq_find_mapping(data->irq, c); @@ -410,9 +472,12 @@ static int pca954x_probe(struct i2c_client *client, } data->last_chan = 0; /* force the first selection */ + data->idle_state = MUX_IDLE_AS_IS; idle_disconnect_dt = np && of_property_read_bool(np, "i2c-mux-idle-disconnect"); + if (idle_disconnect_dt) + data->idle_state = MUX_IDLE_DISCONNECT; ret = pca954x_irq_setup(muxc); if (ret) @@ -420,8 +485,6 @@ static int pca954x_probe(struct i2c_client *client, /* Now create an adapter for each channel */ for (num = 0; num < data->chip->nchans; num++) { - data->deselect |= idle_disconnect_dt << num; - ret = i2c_mux_add_adapter(muxc, 0, num, 0); if (ret) goto fail_cleanup; @@ -436,6 +499,12 @@ static int pca954x_probe(struct i2c_client *client, goto fail_cleanup; } + /* + * The attr probably isn't going to be needed in most cases, + * so don't fail completely on error. + */ + device_create_file(dev, &dev_attr_idle_state); + dev_info(dev, "registered %d multiplexed busses for I2C %s %s\n", num, data->chip->muxtype == pca954x_ismux ? "mux" : "switch", client->name); -- cgit v1.2.3 From f0e79eaf310c61cf4dee08dc9783dda55ac9f9ce Mon Sep 17 00:00:00 2001 From: Andrey Smirnov Date: Mon, 22 Apr 2019 09:00:45 +0800 Subject: dt-bindings: arm: fsl: Add support for ZII i.MX7 RPU2 board Add support for ZII i.MX7 RPU2 board. Signed-off-by: Andrey Smirnov Reviewed-by: Rob Herring Signed-off-by: Shawn Guo --- Documentation/devicetree/bindings/arm/fsl.yaml | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/fsl.yaml b/Documentation/devicetree/bindings/arm/fsl.yaml index b3c5de542123..407138ebc0d0 100644 --- a/Documentation/devicetree/bindings/arm/fsl.yaml +++ b/Documentation/devicetree/bindings/arm/fsl.yaml @@ -157,6 +157,7 @@ properties: - enum: - fsl,imx7d-sdb # i.MX7 SabreSD Board - tq,imx7d-mba7 # i.MX7D TQ MBa7 with TQMa7D SoM + - zii,imx7d-rpu2 # ZII RPU2 Board - const: fsl,imx7d - description: -- cgit v1.2.3 From b9ac3849af412fd3887d7652bdbabf29d2aecc16 Mon Sep 17 00:00:00 2001 From: Dave Young Date: Mon, 22 Apr 2019 11:19:05 +0800 Subject: x86/kdump: Fall back to reserve high crashkernel memory crashkernel=xM tries to reserve memory for the crash kernel under 4G, which is enough, usually. But this could fail sometimes, for example when one tries to reserve a big chunk like 2G, for example. So let the crashkernel=xM just fall back to use high memory in case it fails to find a suitable low range. Do not set the ,high as default because it allocates extra low memory for DMA buffers and swiotlb, and this is not always necessary for all machines. Typically, crashkernel=128M usually works with low reservation under 4G, so keep <4G as default. [ bp: Massage. ] Signed-off-by: Dave Young Signed-off-by: Borislav Petkov Reviewed-by: Ingo Molnar Acked-by: Baoquan He Cc: Dave Young Cc: David Howells Cc: Eric Biederman Cc: Greg Kroah-Hartman Cc: "H. Peter Anvin" Cc: Ingo Molnar Cc: Jiri Kosina Cc: Jonathan Corbet Cc: Juergen Gross Cc: Kees Cook Cc: Konrad Rzeszutek Wilk Cc: linux-doc@vger.kernel.org Cc: "Paul E. McKenney" Cc: Petr Tesarik Cc: piliu@redhat.com Cc: Ram Pai Cc: Sinan Kaya Cc: Thomas Gleixner Cc: Thymo van Beers Cc: vgoyal@redhat.com Cc: x86-ml Cc: Yinghai Lu Cc: Zhimin Gu Link: https://lkml.kernel.org/r/20190422031905.GA8387@dhcp-128-65.nay.redhat.com --- Documentation/admin-guide/kernel-parameters.txt | 7 +++++-- arch/x86/kernel/setup.c | 22 ++++++++++++++-------- 2 files changed, 19 insertions(+), 10 deletions(-) (limited to 'Documentation') diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt index 2b8ee90bb644..24d01648edeb 100644 --- a/Documentation/admin-guide/kernel-parameters.txt +++ b/Documentation/admin-guide/kernel-parameters.txt @@ -704,8 +704,11 @@ upon panic. This parameter reserves the physical memory region [offset, offset + size] for that kernel image. If '@offset' is omitted, then a suitable offset - is selected automatically. Check - Documentation/kdump/kdump.txt for further details. + is selected automatically. + [KNL, x86_64] select a region under 4G first, and + fall back to reserve region above 4G when '@offset' + hasn't been specified. + See Documentation/kdump/kdump.txt for further details. crashkernel=range1:size1[,range2:size2,...][@offset] [KNL] Same as above, but depends on the memory diff --git a/arch/x86/kernel/setup.c b/arch/x86/kernel/setup.c index daf7c5650c18..c15f362a2516 100644 --- a/arch/x86/kernel/setup.c +++ b/arch/x86/kernel/setup.c @@ -541,21 +541,27 @@ static void __init reserve_crashkernel(void) } /* 0 means: find the address automatically */ - if (crash_base <= 0) { + if (!crash_base) { /* * Set CRASH_ADDR_LOW_MAX upper bound for crash memory, - * as old kexec-tools loads bzImage below that, unless - * "crashkernel=size[KMG],high" is specified. + * crashkernel=x,high reserves memory over 4G, also allocates + * 256M extra low memory for DMA buffers and swiotlb. + * But the extra memory is not required for all machines. + * So try low memory first and fall back to high memory + * unless "crashkernel=size[KMG],high" is specified. */ - crash_base = memblock_find_in_range(CRASH_ALIGN, - high ? CRASH_ADDR_HIGH_MAX - : CRASH_ADDR_LOW_MAX, - crash_size, CRASH_ALIGN); + if (!high) + crash_base = memblock_find_in_range(CRASH_ALIGN, + CRASH_ADDR_LOW_MAX, + crash_size, CRASH_ALIGN); + if (!crash_base) + crash_base = memblock_find_in_range(CRASH_ALIGN, + CRASH_ADDR_HIGH_MAX, + crash_size, CRASH_ALIGN); if (!crash_base) { pr_info("crashkernel reservation failed - No suitable area found.\n"); return; } - } else { unsigned long long start; -- cgit v1.2.3 From 65c7a3d2cf0bcd528df88033580039b32db04a40 Mon Sep 17 00:00:00 2001 From: Gregory CLEMENT Date: Fri, 12 Apr 2019 11:15:36 +0200 Subject: dt-bindings: iio: adc: Add bindings for TI ADS8344 A/DC chips This adds device tree bindings for the TI ADS8344 A/DC chips. Signed-off-by: Gregory CLEMENT Reviewed-by: Rob Herring Signed-off-by: Jonathan Cameron --- .../devicetree/bindings/iio/adc/ti-ads8344.txt | 19 +++++++++++++++++++ 1 file changed, 19 insertions(+) create mode 100644 Documentation/devicetree/bindings/iio/adc/ti-ads8344.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/adc/ti-ads8344.txt b/Documentation/devicetree/bindings/iio/adc/ti-ads8344.txt new file mode 100644 index 000000000000..e47c3759a82b --- /dev/null +++ b/Documentation/devicetree/bindings/iio/adc/ti-ads8344.txt @@ -0,0 +1,19 @@ +* Texas Instruments ADS8344 A/DC chip + +Required properties: + - compatible: Must be "ti,ads8344" + - reg: SPI chip select number for the device + - vref-supply: phandle to a regulator node that supplies the + reference voltage + +Recommended properties: + - spi-max-frequency: Definition as per + Documentation/devicetree/bindings/spi/spi-bus.txt + +Example: +adc@0 { + compatible = "ti,ads8344"; + reg = <0>; + vref-supply = <&refin_supply>; + spi-max-frequency = <10000000>; +}; -- cgit v1.2.3 From 708310711e6cdc1f5d8fb1d3fb531fba09ebae2e Mon Sep 17 00:00:00 2001 From: Marc Gonzalez Date: Mon, 1 Apr 2019 16:42:24 +0200 Subject: dt-bindings: phy-qcom-qmp: Tweak qcom,msm8998-qmp-ufs-phy Fixup MSM8998 UFS binding now that Evan's reset series has landed. https://lore.kernel.org/lkml/20190321171800.104681-1-evgreen@chromium.org/ Signed-off-by: Marc Gonzalez Signed-off-by: Kishon Vijay Abraham I --- Documentation/devicetree/bindings/phy/qcom-qmp-phy.txt | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/phy/qcom-qmp-phy.txt b/Documentation/devicetree/bindings/phy/qcom-qmp-phy.txt index 5fca57b12534..085fbd676cfc 100644 --- a/Documentation/devicetree/bindings/phy/qcom-qmp-phy.txt +++ b/Documentation/devicetree/bindings/phy/qcom-qmp-phy.txt @@ -73,7 +73,8 @@ Required properties: "phy", "common". For "qcom,msm8998-qmp-usb3-phy" must contain "phy", "common". - For "qcom,msm8998-qmp-ufs-phy": no resets are listed. + For "qcom,msm8998-qmp-ufs-phy": must contain: + "ufsphy". For "qcom,msm8998-qmp-pcie-phy" must contain: "phy", "common". For "qcom,sdm845-qmp-usb3-phy" must contain: -- cgit v1.2.3 From 87effaae9e90474546d441b9123bca824e670a0b Mon Sep 17 00:00:00 2001 From: Fish Lin Date: Thu, 28 Mar 2019 23:20:46 -0400 Subject: media: v4l: add I / P frame min max QP definitions Add following V4L2 QP parameters for H.264: * V4L2_CID_MPEG_VIDEO_H264_I_FRAME_MIN_QP * V4L2_CID_MPEG_VIDEO_H264_I_FRAME_MAX_QP * V4L2_CID_MPEG_VIDEO_H264_P_FRAME_MIN_QP * V4L2_CID_MPEG_VIDEO_H264_P_FRAME_MAX_QP These controls will limit QP range for intra and inter frame, provide more manual control to improve video encode quality. Signed-off-by: Fish Lin Signed-off-by: Hans Verkuil Signed-off-by: Mauro Carvalho Chehab --- Documentation/media/uapi/v4l/ext-ctrls-codec.rst | 24 ++++++++++++++++++++++++ drivers/media/v4l2-core/v4l2-ctrls.c | 4 ++++ include/uapi/linux/v4l2-controls.h | 4 ++++ 3 files changed, 32 insertions(+) (limited to 'Documentation') diff --git a/Documentation/media/uapi/v4l/ext-ctrls-codec.rst b/Documentation/media/uapi/v4l/ext-ctrls-codec.rst index 67a122339c0e..4a8446203085 100644 --- a/Documentation/media/uapi/v4l/ext-ctrls-codec.rst +++ b/Documentation/media/uapi/v4l/ext-ctrls-codec.rst @@ -1055,6 +1055,30 @@ enum v4l2_mpeg_video_h264_entropy_mode - Quantization parameter for an B frame for H264. Valid range: from 0 to 51. +``V4L2_CID_MPEG_VIDEO_H264_I_FRAME_MIN_QP (integer)`` + Minimum quantization parameter for the H264 I frame to limit I frame + quality to a range. Valid range: from 0 to 51. If + V4L2_CID_MPEG_VIDEO_H264_MIN_QP is also set, the quantization parameter + should be chosen to meet both requirements. + +``V4L2_CID_MPEG_VIDEO_H264_I_FRAME_MAX_QP (integer)`` + Maximum quantization parameter for the H264 I frame to limit I frame + quality to a range. Valid range: from 0 to 51. If + V4L2_CID_MPEG_VIDEO_H264_MAX_QP is also set, the quantization parameter + should be chosen to meet both requirements. + +``V4L2_CID_MPEG_VIDEO_H264_P_FRAME_MIN_QP (integer)`` + Minimum quantization parameter for the H264 P frame to limit P frame + quality to a range. Valid range: from 0 to 51. If + V4L2_CID_MPEG_VIDEO_H264_MIN_QP is also set, the quantization parameter + should be chosen to meet both requirements. + +``V4L2_CID_MPEG_VIDEO_H264_P_FRAME_MAX_QP (integer)`` + Maximum quantization parameter for the H264 P frame to limit P frame + quality to a range. Valid range: from 0 to 51. If + V4L2_CID_MPEG_VIDEO_H264_MAX_QP is also set, the quantization parameter + should be chosen to meet both requirements. + ``V4L2_CID_MPEG_VIDEO_MPEG4_I_FRAME_QP (integer)`` Quantization parameter for an I frame for MPEG4. Valid range: from 1 to 31. diff --git a/drivers/media/v4l2-core/v4l2-ctrls.c b/drivers/media/v4l2-core/v4l2-ctrls.c index b1ae2e555c68..89a1fe564675 100644 --- a/drivers/media/v4l2-core/v4l2-ctrls.c +++ b/drivers/media/v4l2-core/v4l2-ctrls.c @@ -828,6 +828,10 @@ const char *v4l2_ctrl_get_name(u32 id) case V4L2_CID_MPEG_VIDEO_H264_CONSTRAINED_INTRA_PREDICTION: return "H264 Constrained Intra Pred"; case V4L2_CID_MPEG_VIDEO_H264_CHROMA_QP_INDEX_OFFSET: return "H264 Chroma QP Index Offset"; + case V4L2_CID_MPEG_VIDEO_H264_I_FRAME_MIN_QP: return "H264 I-Frame Minimum QP Value"; + case V4L2_CID_MPEG_VIDEO_H264_I_FRAME_MAX_QP: return "H264 I-Frame Maximum QP Value"; + case V4L2_CID_MPEG_VIDEO_H264_P_FRAME_MIN_QP: return "H264 P-Frame Minimum QP Value"; + case V4L2_CID_MPEG_VIDEO_H264_P_FRAME_MAX_QP: return "H264 P-Frame Maximum QP Value"; case V4L2_CID_MPEG_VIDEO_MPEG4_I_FRAME_QP: return "MPEG4 I-Frame QP Value"; case V4L2_CID_MPEG_VIDEO_MPEG4_P_FRAME_QP: return "MPEG4 P-Frame QP Value"; case V4L2_CID_MPEG_VIDEO_MPEG4_B_FRAME_QP: return "MPEG4 B-Frame QP Value"; diff --git a/include/uapi/linux/v4l2-controls.h b/include/uapi/linux/v4l2-controls.h index 78816ec88751..37807f23231e 100644 --- a/include/uapi/linux/v4l2-controls.h +++ b/include/uapi/linux/v4l2-controls.h @@ -539,6 +539,10 @@ enum v4l2_mpeg_video_h264_hierarchical_coding_type { #define V4L2_CID_MPEG_VIDEO_H264_HIERARCHICAL_CODING_LAYER_QP (V4L2_CID_MPEG_BASE+382) #define V4L2_CID_MPEG_VIDEO_H264_CONSTRAINED_INTRA_PREDICTION (V4L2_CID_MPEG_BASE+383) #define V4L2_CID_MPEG_VIDEO_H264_CHROMA_QP_INDEX_OFFSET (V4L2_CID_MPEG_BASE+384) +#define V4L2_CID_MPEG_VIDEO_H264_I_FRAME_MIN_QP (V4L2_CID_MPEG_BASE+385) +#define V4L2_CID_MPEG_VIDEO_H264_I_FRAME_MAX_QP (V4L2_CID_MPEG_BASE+386) +#define V4L2_CID_MPEG_VIDEO_H264_P_FRAME_MIN_QP (V4L2_CID_MPEG_BASE+387) +#define V4L2_CID_MPEG_VIDEO_H264_P_FRAME_MAX_QP (V4L2_CID_MPEG_BASE+388) #define V4L2_CID_MPEG_VIDEO_MPEG4_I_FRAME_QP (V4L2_CID_MPEG_BASE+400) #define V4L2_CID_MPEG_VIDEO_MPEG4_P_FRAME_QP (V4L2_CID_MPEG_BASE+401) #define V4L2_CID_MPEG_VIDEO_MPEG4_B_FRAME_QP (V4L2_CID_MPEG_BASE+402) -- cgit v1.2.3 From b4ccd7fd062a0b8514a6f04cdd8f8cbb336a3f65 Mon Sep 17 00:00:00 2001 From: Sergei Shtylyov Date: Tue, 26 Mar 2019 12:12:19 -0400 Subject: media: dt-bindings: media: Renesas R-Car IMR bindings The image renderer (IMR), or the distortion correction engine, is a drawing processor with a simple instruction system capable of referencing video capture data or data in an external memory as the 2D texture data and performing texture mapping and drawing with respect to any shape that is split into triangular objects. Document the device tree bindings for the image renderer light extended 4 (IMR-LX4) found in the R-Car gen3 SoCs... Signed-off-by: Sergei Shtylyov Acked-by: Rob Herring Signed-off-by: Hans Verkuil Signed-off-by: Mauro Carvalho Chehab --- .../devicetree/bindings/media/rcar_imr.txt | 31 ++++++++++++++++++++++ 1 file changed, 31 insertions(+) create mode 100644 Documentation/devicetree/bindings/media/rcar_imr.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/media/rcar_imr.txt b/Documentation/devicetree/bindings/media/rcar_imr.txt new file mode 100644 index 000000000000..b0614153ed36 --- /dev/null +++ b/Documentation/devicetree/bindings/media/rcar_imr.txt @@ -0,0 +1,31 @@ +Renesas R-Car Image Renderer (Distortion Correction Engine) +----------------------------------------------------------- + +The image renderer, or the distortion correction engine, is a drawing processor +with a simple instruction system capable of referencing video capture data or +data in an external memory as 2D texture data and performing texture mapping +and drawing with respect to any shape that is split into triangular objects. + +Required properties: + +- compatible: "renesas,-imr-lx4", "renesas,imr-lx4" as a fallback for + the image renderer light extended 4 (IMR-LX4) found in the R-Car gen3 SoCs, + where the examples with are: + - "renesas,r8a7795-imr-lx4" for R-Car H3, + - "renesas,r8a7796-imr-lx4" for R-Car M3-W. +- reg: offset and length of the register block; +- interrupts: single interrupt specifier; +- clocks: single clock phandle/specifier pair; +- power-domains: power domain phandle/specifier pair; +- resets: reset phandle/specifier pair. + +Example: + + imr-lx4@fe860000 { + compatible = "renesas,r8a7795-imr-lx4", "renesas,imr-lx4"; + reg = <0 0xfe860000 0 0x2000>; + interrupts = ; + clocks = <&cpg CPG_MOD 823>; + power-domains = <&sysc R8A7795_PD_A3VC>; + resets = <&cpg 823>; + }; -- cgit v1.2.3 From 6e1d824e7a1d324f7fdd276fb7133013109d3764 Mon Sep 17 00:00:00 2001 From: Shuah Khan Date: Mon, 1 Apr 2019 20:40:19 -0400 Subject: media: Media Device Allocator API Media Device Allocator API to allows multiple drivers share a media device. This API solves a very common use-case for media devices where one physical device (an USB stick) provides both audio and video. When such media device exposes a standard USB Audio class, a proprietary Video class, two or more independent drivers will share a single physical USB bridge. In such cases, it is necessary to coordinate access to the shared resource. Using this API, drivers can allocate a media device with the shared struct device as the key. Once the media device is allocated by a driver, other drivers can get a reference to it. The media device is released when all the references are released. Signed-off-by: Shuah Khan Signed-off-by: Hans Verkuil Signed-off-by: Mauro Carvalho Chehab --- Documentation/media/kapi/mc-core.rst | 41 +++++++++++ drivers/media/Makefile | 6 ++ drivers/media/media-dev-allocator.c | 135 +++++++++++++++++++++++++++++++++++ include/media/media-dev-allocator.h | 63 ++++++++++++++++ 4 files changed, 245 insertions(+) create mode 100644 drivers/media/media-dev-allocator.c create mode 100644 include/media/media-dev-allocator.h (limited to 'Documentation') diff --git a/Documentation/media/kapi/mc-core.rst b/Documentation/media/kapi/mc-core.rst index f930725e0d6b..05bba0b61748 100644 --- a/Documentation/media/kapi/mc-core.rst +++ b/Documentation/media/kapi/mc-core.rst @@ -259,6 +259,45 @@ Subsystems should facilitate link validation by providing subsystem specific helper functions to provide easy access for commonly needed information, and in the end provide a way to use driver-specific callbacks. +Media Controller Device Allocator API +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +When the media device belongs to more than one driver, the shared media +device is allocated with the shared struct device as the key for look ups. + +The shared media device should stay in registered state until the last +driver unregisters it. In addition, the media device should be released when +all the references are released. Each driver gets a reference to the media +device during probe, when it allocates the media device. If media device is +already allocated, the allocate API bumps up the refcount and returns the +existing media device. The driver puts the reference back in its disconnect +routine when it calls :c:func:`media_device_delete()`. + +The media device is unregistered and cleaned up from the kref put handler to +ensure that the media device stays in registered state until the last driver +unregisters the media device. + +**Driver Usage** + +Drivers should use the appropriate media-core routines to manage the shared +media device life-time handling the two states: +1. allocate -> register -> delete +2. get reference to already registered device -> delete + +call :c:func:`media_device_delete()` routine to make sure the shared media +device delete is handled correctly. + +**driver probe:** +Call :c:func:`media_device_usb_allocate()` to allocate or get a reference +Call :c:func:`media_device_register()`, if media devnode isn't registered + +**driver disconnect:** +Call :c:func:`media_device_delete()` to free the media_device. Freeing is +handled by the kref put handler. + +API Definitions +^^^^^^^^^^^^^^^ + .. kernel-doc:: include/media/media-device.h .. kernel-doc:: include/media/media-devnode.h @@ -266,3 +305,5 @@ in the end provide a way to use driver-specific callbacks. .. kernel-doc:: include/media/media-entity.h .. kernel-doc:: include/media/media-request.h + +.. kernel-doc:: include/media/media-dev-allocator.h diff --git a/drivers/media/Makefile b/drivers/media/Makefile index 985d35ec6b29..4a330d0e5e40 100644 --- a/drivers/media/Makefile +++ b/drivers/media/Makefile @@ -6,6 +6,12 @@ media-objs := media-device.o media-devnode.o media-entity.o \ media-request.o +ifeq ($(CONFIG_MEDIA_CONTROLLER),y) + ifeq ($(CONFIG_USB),y) + media-objs += media-dev-allocator.o + endif +endif + # # I2C drivers should come before other drivers, otherwise they'll fail # when compiled as builtin drivers diff --git a/drivers/media/media-dev-allocator.c b/drivers/media/media-dev-allocator.c new file mode 100644 index 000000000000..ae17887dec59 --- /dev/null +++ b/drivers/media/media-dev-allocator.c @@ -0,0 +1,135 @@ +// SPDX-License-Identifier: GPL-2.0 +/* + * media-dev-allocator.c - Media Controller Device Allocator API + * + * Copyright (c) 2019 Shuah Khan + * + * Credits: Suggested by Laurent Pinchart + */ + +/* + * This file adds a global refcounted Media Controller Device Instance API. + * A system wide global media device list is managed and each media device + * includes a kref count. The last put on the media device releases the media + * device instance. + * + */ + +#include +#include +#include +#include + +#include +#include + +static LIST_HEAD(media_device_list); +static DEFINE_MUTEX(media_device_lock); + +struct media_device_instance { + struct media_device mdev; + struct module *owner; + struct list_head list; + struct kref refcount; +}; + +static inline struct media_device_instance * +to_media_device_instance(struct media_device *mdev) +{ + return container_of(mdev, struct media_device_instance, mdev); +} + +static void media_device_instance_release(struct kref *kref) +{ + struct media_device_instance *mdi = + container_of(kref, struct media_device_instance, refcount); + + dev_dbg(mdi->mdev.dev, "%s: releasing Media Device\n", __func__); + + mutex_lock(&media_device_lock); + + media_device_unregister(&mdi->mdev); + media_device_cleanup(&mdi->mdev); + + list_del(&mdi->list); + mutex_unlock(&media_device_lock); + + kfree(mdi); +} + +/* Callers should hold media_device_lock when calling this function */ +static struct media_device *__media_device_get(struct device *dev, + const char *module_name, + struct module *owner) +{ + struct media_device_instance *mdi; + + list_for_each_entry(mdi, &media_device_list, list) { + if (mdi->mdev.dev != dev) + continue; + + kref_get(&mdi->refcount); + + /* get module reference for the media_device owner */ + if (owner != mdi->owner && !try_module_get(mdi->owner)) + dev_err(dev, + "%s: module %s get owner reference error\n", + __func__, module_name); + else + dev_dbg(dev, "%s: module %s got owner reference\n", + __func__, module_name); + return &mdi->mdev; + } + + mdi = kzalloc(sizeof(*mdi), GFP_KERNEL); + if (!mdi) + return NULL; + + mdi->owner = owner; + kref_init(&mdi->refcount); + list_add_tail(&mdi->list, &media_device_list); + + dev_dbg(dev, "%s: Allocated media device for owner %s\n", + __func__, module_name); + return &mdi->mdev; +} + +struct media_device *media_device_usb_allocate(struct usb_device *udev, + const char *module_name, + struct module *owner) +{ + struct media_device *mdev; + + mutex_lock(&media_device_lock); + mdev = __media_device_get(&udev->dev, module_name, owner); + if (!mdev) { + mutex_unlock(&media_device_lock); + return ERR_PTR(-ENOMEM); + } + + /* check if media device is already initialized */ + if (!mdev->dev) + __media_device_usb_init(mdev, udev, udev->product, + module_name); + mutex_unlock(&media_device_lock); + return mdev; +} +EXPORT_SYMBOL_GPL(media_device_usb_allocate); + +void media_device_delete(struct media_device *mdev, const char *module_name, + struct module *owner) +{ + struct media_device_instance *mdi = to_media_device_instance(mdev); + + mutex_lock(&media_device_lock); + /* put module reference for the media_device owner */ + if (mdi->owner != owner) { + module_put(mdi->owner); + dev_dbg(mdi->mdev.dev, + "%s: module %s put owner module reference\n", + __func__, module_name); + } + mutex_unlock(&media_device_lock); + kref_put(&mdi->refcount, media_device_instance_release); +} +EXPORT_SYMBOL_GPL(media_device_delete); diff --git a/include/media/media-dev-allocator.h b/include/media/media-dev-allocator.h new file mode 100644 index 000000000000..b35ea6062596 --- /dev/null +++ b/include/media/media-dev-allocator.h @@ -0,0 +1,63 @@ +/* SPDX-License-Identifier: GPL-2.0+ */ +/* + * media-dev-allocator.h - Media Controller Device Allocator API + * + * Copyright (c) 2019 Shuah Khan + * + * Credits: Suggested by Laurent Pinchart + */ + +/* + * This file adds a global ref-counted Media Controller Device Instance API. + * A system wide global media device list is managed and each media device + * includes a kref count. The last put on the media device releases the media + * device instance. + */ + +#ifndef _MEDIA_DEV_ALLOCATOR_H +#define _MEDIA_DEV_ALLOCATOR_H + +struct usb_device; + +#if defined(CONFIG_MEDIA_CONTROLLER) && defined(CONFIG_USB) +/** + * media_device_usb_allocate() - Allocate and return struct &media device + * + * @udev: struct &usb_device pointer + * @module_name: should be filled with %KBUILD_MODNAME + * @owner: struct module pointer %THIS_MODULE for the driver. + * %THIS_MODULE is null for a built-in driver. + * It is safe even when %THIS_MODULE is null. + * + * This interface should be called to allocate a Media Device when multiple + * drivers share usb_device and the media device. This interface allocates + * &media_device structure and calls media_device_usb_init() to initialize + * it. + * + */ +struct media_device *media_device_usb_allocate(struct usb_device *udev, + const char *module_name, + struct module *owner); +/** + * media_device_delete() - Release media device. Calls kref_put(). + * + * @mdev: struct &media_device pointer + * @module_name: should be filled with %KBUILD_MODNAME + * @owner: struct module pointer %THIS_MODULE for the driver. + * %THIS_MODULE is null for a built-in driver. + * It is safe even when %THIS_MODULE is null. + * + * This interface should be called to put Media Device Instance kref. + */ +void media_device_delete(struct media_device *mdev, const char *module_name, + struct module *owner); +#else +static inline struct media_device *media_device_usb_allocate( + struct usb_device *udev, const char *module_name, + struct module *owner) + { return NULL; } +static inline void media_device_delete( + struct media_device *mdev, const char *module_name, + struct module *owner) { } +#endif /* CONFIG_MEDIA_CONTROLLER && CONFIG_USB */ +#endif /* _MEDIA_DEV_ALLOCATOR_H */ -- cgit v1.2.3 From e3521f5687b34f5e007d170f029d98f3cb846955 Mon Sep 17 00:00:00 2001 From: Mickael Guene Date: Tue, 9 Apr 2019 02:15:47 -0400 Subject: media: uapi: Add MEDIA_BUS_FMT_BGR888_3X8 media bus format This patch adds MEDIA_BUS_FMT_BGR888_3X8 used by STM MIPID02 CSI-2 to PARALLEL bridge driver when input format is MEDIA_BUS_FMT_BGR888_1X24. Signed-off-by: Mickael Guene Signed-off-by: Sakari Ailus Signed-off-by: Mauro Carvalho Chehab --- Documentation/media/uapi/v4l/subdev-formats.rst | 107 ++++++++++++++++++++++++ include/uapi/linux/media-bus-format.h | 3 +- 2 files changed, 109 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/media/uapi/v4l/subdev-formats.rst b/Documentation/media/uapi/v4l/subdev-formats.rst index bf1dbb68eebc..ab1a48a5ae80 100644 --- a/Documentation/media/uapi/v4l/subdev-formats.rst +++ b/Documentation/media/uapi/v4l/subdev-formats.rst @@ -980,6 +980,113 @@ The following tables list existing packed RGB formats. - r\ :sub:`2` - r\ :sub:`1` - r\ :sub:`0` + * .. _MEDIA-BUS-FMT-BGR888-3X8: + + - MEDIA_BUS_FMT_BGR888_3X8 + - 0x101b + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - b\ :sub:`7` + - b\ :sub:`6` + - b\ :sub:`5` + - b\ :sub:`4` + - b\ :sub:`3` + - b\ :sub:`2` + - b\ :sub:`1` + - b\ :sub:`0` + * - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - g\ :sub:`7` + - g\ :sub:`6` + - g\ :sub:`5` + - g\ :sub:`4` + - g\ :sub:`3` + - g\ :sub:`2` + - g\ :sub:`1` + - g\ :sub:`0` + * - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - + - r\ :sub:`7` + - r\ :sub:`6` + - r\ :sub:`5` + - r\ :sub:`4` + - r\ :sub:`3` + - r\ :sub:`2` + - r\ :sub:`1` + - r\ :sub:`0` * .. _MEDIA-BUS-FMT-GBR888-1X24: - MEDIA_BUS_FMT_GBR888_1X24 diff --git a/include/uapi/linux/media-bus-format.h b/include/uapi/linux/media-bus-format.h index d6a5a3bfe6c4..2a6b253cfb05 100644 --- a/include/uapi/linux/media-bus-format.h +++ b/include/uapi/linux/media-bus-format.h @@ -34,7 +34,7 @@ #define MEDIA_BUS_FMT_FIXED 0x0001 -/* RGB - next is 0x101b */ +/* RGB - next is 0x101c */ #define MEDIA_BUS_FMT_RGB444_1X12 0x1016 #define MEDIA_BUS_FMT_RGB444_2X8_PADHI_BE 0x1001 #define MEDIA_BUS_FMT_RGB444_2X8_PADHI_LE 0x1002 @@ -50,6 +50,7 @@ #define MEDIA_BUS_FMT_RGB666_1X24_CPADHI 0x1015 #define MEDIA_BUS_FMT_RGB666_1X7X3_SPWG 0x1010 #define MEDIA_BUS_FMT_BGR888_1X24 0x1013 +#define MEDIA_BUS_FMT_BGR888_3X8 0x101b #define MEDIA_BUS_FMT_GBR888_1X24 0x1014 #define MEDIA_BUS_FMT_RGB888_1X24 0x100a #define MEDIA_BUS_FMT_RGB888_2X12_BE 0x100b -- cgit v1.2.3 From cffc3df28450390f0de4d6907387d7c40459acab Mon Sep 17 00:00:00 2001 From: Mickael Guene Date: Tue, 9 Apr 2019 02:15:48 -0400 Subject: media: dt-bindings: Document MIPID02 bindings This adds documentation of device tree for MIPID02 CSI-2 to PARALLEL bridge. Reviewed-by: Rob Herring Signed-off-by: Mickael Guene Signed-off-by: Sakari Ailus Signed-off-by: Mauro Carvalho Chehab --- .../bindings/media/i2c/st,st-mipid02.txt | 82 ++++++++++++++++++++++ MAINTAINERS | 7 ++ 2 files changed, 89 insertions(+) create mode 100644 Documentation/devicetree/bindings/media/i2c/st,st-mipid02.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/media/i2c/st,st-mipid02.txt b/Documentation/devicetree/bindings/media/i2c/st,st-mipid02.txt new file mode 100644 index 000000000000..7976e6c40a80 --- /dev/null +++ b/Documentation/devicetree/bindings/media/i2c/st,st-mipid02.txt @@ -0,0 +1,82 @@ +STMicroelectronics MIPID02 CSI-2 to PARALLEL bridge + +MIPID02 has two CSI-2 input ports, only one of those ports can be active at a +time. Active port input stream will be de-serialized and its content outputted +through PARALLEL output port. +CSI-2 first input port is a dual lane 800Mbps per lane whereas CSI-2 second +input port is a single lane 800Mbps. Both ports support clock and data lane +polarity swap. First port also supports data lane swap. +PARALLEL output port has a maximum width of 12 bits. +Supported formats are RAW6, RAW7, RAW8, RAW10, RAW12, RGB565, RGB888, RGB444, +YUV420 8-bit, YUV422 8-bit and YUV420 10-bit. + +Required Properties: +- compatible: shall be "st,st-mipid02" +- clocks: reference to the xclk input clock. +- clock-names: shall be "xclk". +- VDDE-supply: sensor digital IO supply. Must be 1.8 volts. +- VDDIN-supply: sensor internal regulator supply. Must be 1.8 volts. + +Optional Properties: +- reset-gpios: reference to the GPIO connected to the xsdn pin, if any. + This is an active low signal to the mipid02. + +Required subnodes: + - ports: A ports node with one port child node per device input and output + port, in accordance with the video interface bindings defined in + Documentation/devicetree/bindings/media/video-interfaces.txt. The + port nodes are numbered as follows: + + Port Description + ----------------------------- + 0 CSI-2 first input port + 1 CSI-2 second input port + 2 PARALLEL output + +Endpoint node required property for CSI-2 connection is: +- data-lanes: shall be <1> for Port 1. for Port 0 dual-lane operation shall be +<1 2> or <2 1>. For Port 0 single-lane operation shall be <1> or <2>. +Endpoint node optional property for CSI-2 connection is: +- lane-polarities: any lane can be inverted or not. + +Endpoint node required property for PARALLEL connection is: +- bus-width: shall be set to <6>, <7>, <8>, <10> or <12>. +Endpoint node optional properties for PARALLEL connection are: +- hsync-active: active state of the HSYNC signal, 0/1 for LOW/HIGH respectively. +LOW being the default. +- vsync-active: active state of the VSYNC signal, 0/1 for LOW/HIGH respectively. +LOW being the default. + +Example: + +mipid02: csi2rx@14 { + compatible = "st,st-mipid02"; + reg = <0x14>; + status = "okay"; + clocks = <&clk_ext_camera_12>; + clock-names = "xclk"; + VDDE-supply = <&vdd>; + VDDIN-supply = <&vdd>; + ports { + #address-cells = <1>; + #size-cells = <0>; + port@0 { + reg = <0>; + + ep0: endpoint { + data-lanes = <1 2>; + remote-endpoint = <&mipi_csi2_in>; + }; + }; + port@2 { + reg = <2>; + + ep2: endpoint { + bus-width = <8>; + hsync-active = <0>; + vsync-active = <0>; + remote-endpoint = <¶llel_out>; + }; + }; + }; +}; diff --git a/MAINTAINERS b/MAINTAINERS index c6c15de0583f..fbcbdf839a15 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -14667,6 +14667,13 @@ S: Maintained F: drivers/iio/imu/st_lsm6dsx/ F: Documentation/devicetree/bindings/iio/imu/st_lsm6dsx.txt +ST MIPID02 CSI-2 TO PARALLEL BRIDGE DRIVER +M: Mickael Guene +L: linux-media@vger.kernel.org +T: git git://linuxtv.org/media_tree.git +S: Maintained +F: Documentation/devicetree/bindings/media/i2c/st,st-mipid02.txt + ST STM32 I2C/SMBUS DRIVER M: Pierre-Yves MORDRET L: linux-i2c@vger.kernel.org -- cgit v1.2.3 From ffaebccddef0a6320643a9d1c911190db579c09f Mon Sep 17 00:00:00 2001 From: Niklas Söderlund Date: Tue, 12 Mar 2019 19:49:29 -0400 Subject: media: dt-bindings: rcar-csi2: List resets as a mandatory property MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The resets property will become mandatory to operate the device, list it as such. All device tree source files have always included the reset property so making it mandatory will not introduce any regressions. While at it improve the description for the clocks property. Signed-off-by: Niklas Söderlund Reviewed-by: Laurent Pinchart Reviewed-by: Rob Herring Signed-off-by: Hans Verkuil Signed-off-by: Mauro Carvalho Chehab --- Documentation/devicetree/bindings/media/renesas,rcar-csi2.txt | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/media/renesas,rcar-csi2.txt b/Documentation/devicetree/bindings/media/renesas,rcar-csi2.txt index 9932458a0a45..331409259752 100644 --- a/Documentation/devicetree/bindings/media/renesas,rcar-csi2.txt +++ b/Documentation/devicetree/bindings/media/renesas,rcar-csi2.txt @@ -19,7 +19,8 @@ Mandatory properties - reg: the register base and size for the device registers - interrupts: the interrupt for the device - - clocks: reference to the parent clock + - clocks: A phandle + clock specifier for the module clock + - resets: A phandle + reset specifier for the module reset The device node shall contain two 'port' child nodes according to the bindings defined in Documentation/devicetree/bindings/media/ -- cgit v1.2.3 From 172876928f98e187daa8c7777361670ce2654b28 Mon Sep 17 00:00:00 2001 From: Matthias Reichl Date: Sun, 24 Mar 2019 05:43:51 -0400 Subject: media: rc: xbox_remote: add protocol and set timeout The timestamps in ir-keytable -t output showed that the Xbox DVD IR dongle decodes scancodes every 64ms. The last scancode of a longer button press is decodes 64ms after the last-but-one which indicates the decoder doesn't use a timeout but decodes on the last edge of the signal. 267.042629: lirc protocol(unknown): scancode = 0xace 267.042665: event type EV_MSC(0x04): scancode = 0xace 267.042665: event type EV_KEY(0x01) key_down: KEY_1(0x0002) 267.042665: event type EV_SYN(0x00). 267.106625: lirc protocol(unknown): scancode = 0xace 267.106643: event type EV_MSC(0x04): scancode = 0xace 267.106643: event type EV_SYN(0x00). 267.170623: lirc protocol(unknown): scancode = 0xace 267.170638: event type EV_MSC(0x04): scancode = 0xace 267.170638: event type EV_SYN(0x00). 267.234621: lirc protocol(unknown): scancode = 0xace 267.234636: event type EV_MSC(0x04): scancode = 0xace 267.234636: event type EV_SYN(0x00). 267.298623: lirc protocol(unknown): scancode = 0xace 267.298638: event type EV_MSC(0x04): scancode = 0xace 267.298638: event type EV_SYN(0x00). 267.543345: event type EV_KEY(0x01) key_down: KEY_1(0x0002) 267.543345: event type EV_SYN(0x00). 267.570015: event type EV_KEY(0x01) key_up: KEY_1(0x0002) 267.570015: event type EV_SYN(0x00). Add a protocol with the repeat value and set the timeout in the driver to 10ms (to have a bit of headroom for delays) so the Xbox DVD remote performs more responsive. Signed-off-by: Matthias Reichl Acked-by: Benjamin Valentin Signed-off-by: Sean Young Signed-off-by: Mauro Carvalho Chehab --- Documentation/media/lirc.h.rst.exceptions | 1 + drivers/media/rc/keymaps/rc-xbox-dvd.c | 2 +- drivers/media/rc/rc-main.c | 2 ++ drivers/media/rc/xbox_remote.c | 6 ++++-- include/media/rc-map.h | 4 +++- include/uapi/linux/lirc.h | 2 ++ 6 files changed, 13 insertions(+), 4 deletions(-) (limited to 'Documentation') diff --git a/Documentation/media/lirc.h.rst.exceptions b/Documentation/media/lirc.h.rst.exceptions index 7a8b8ff4f076..ac768d769113 100644 --- a/Documentation/media/lirc.h.rst.exceptions +++ b/Documentation/media/lirc.h.rst.exceptions @@ -63,6 +63,7 @@ ignore symbol RC_PROTO_IMON ignore symbol RC_PROTO_RCMM12 ignore symbol RC_PROTO_RCMM24 ignore symbol RC_PROTO_RCMM32 +ignore symbol RC_PROTO_XBOX_DVD # Undocumented macros diff --git a/drivers/media/rc/keymaps/rc-xbox-dvd.c b/drivers/media/rc/keymaps/rc-xbox-dvd.c index af387244636b..42815ab57bff 100644 --- a/drivers/media/rc/keymaps/rc-xbox-dvd.c +++ b/drivers/media/rc/keymaps/rc-xbox-dvd.c @@ -42,7 +42,7 @@ static struct rc_map_list xbox_dvd_map = { .map = { .scan = xbox_dvd, .size = ARRAY_SIZE(xbox_dvd), - .rc_proto = RC_PROTO_UNKNOWN, + .rc_proto = RC_PROTO_XBOX_DVD, .name = RC_MAP_XBOX_DVD, } }; diff --git a/drivers/media/rc/rc-main.c b/drivers/media/rc/rc-main.c index e8fa28e20192..be5fd129d728 100644 --- a/drivers/media/rc/rc-main.c +++ b/drivers/media/rc/rc-main.c @@ -76,6 +76,7 @@ static const struct { .scancode_bits = 0x00ffffff, .repeat_period = 114 }, [RC_PROTO_RCMM32] = { .name = "rc-mm-32", .scancode_bits = 0xffffffff, .repeat_period = 114 }, + [RC_PROTO_XBOX_DVD] = { .name = "xbox-dvd", .repeat_period = 64 }, }; /* Used to keep track of known keymaps */ @@ -1027,6 +1028,7 @@ static const struct { { RC_PROTO_BIT_RCMM12 | RC_PROTO_BIT_RCMM24 | RC_PROTO_BIT_RCMM32, "rc-mm", "ir-rcmm-decoder" }, + { RC_PROTO_BIT_XBOX_DVD, "xbox-dvd", NULL }, }; /** diff --git a/drivers/media/rc/xbox_remote.c b/drivers/media/rc/xbox_remote.c index f959cbb94744..4a3f2cc4ef18 100644 --- a/drivers/media/rc/xbox_remote.c +++ b/drivers/media/rc/xbox_remote.c @@ -107,7 +107,7 @@ static void xbox_remote_input_report(struct urb *urb) return; } - rc_keydown(xbox_remote->rdev, RC_PROTO_UNKNOWN, + rc_keydown(xbox_remote->rdev, RC_PROTO_XBOX_DVD, le16_to_cpup((__le16 *)(data + 2)), 0); } @@ -148,7 +148,7 @@ static void xbox_remote_rc_init(struct xbox_remote *xbox_remote) struct rc_dev *rdev = xbox_remote->rdev; rdev->priv = xbox_remote; - rdev->allowed_protocols = RC_PROTO_BIT_UNKNOWN; + rdev->allowed_protocols = RC_PROTO_BIT_XBOX_DVD; rdev->driver_name = "xbox_remote"; rdev->open = xbox_remote_rc_open; @@ -157,6 +157,8 @@ static void xbox_remote_rc_init(struct xbox_remote *xbox_remote) rdev->device_name = xbox_remote->rc_name; rdev->input_phys = xbox_remote->rc_phys; + rdev->timeout = MS_TO_NS(10); + usb_to_input_id(xbox_remote->udev, &rdev->input_id); rdev->dev.parent = &xbox_remote->interface->dev; } diff --git a/include/media/rc-map.h b/include/media/rc-map.h index 5e684bb0d64c..367d983188f7 100644 --- a/include/media/rc-map.h +++ b/include/media/rc-map.h @@ -40,6 +40,7 @@ #define RC_PROTO_BIT_RCMM12 BIT_ULL(RC_PROTO_RCMM12) #define RC_PROTO_BIT_RCMM24 BIT_ULL(RC_PROTO_RCMM24) #define RC_PROTO_BIT_RCMM32 BIT_ULL(RC_PROTO_RCMM32) +#define RC_PROTO_BIT_XBOX_DVD BIT_ULL(RC_PROTO_XBOX_DVD) #define RC_PROTO_BIT_ALL \ (RC_PROTO_BIT_UNKNOWN | RC_PROTO_BIT_OTHER | \ @@ -55,7 +56,8 @@ RC_PROTO_BIT_RC6_MCE | RC_PROTO_BIT_SHARP | \ RC_PROTO_BIT_XMP | RC_PROTO_BIT_CEC | \ RC_PROTO_BIT_IMON | RC_PROTO_BIT_RCMM12 | \ - RC_PROTO_BIT_RCMM24 | RC_PROTO_BIT_RCMM32) + RC_PROTO_BIT_RCMM24 | RC_PROTO_BIT_RCMM32 | \ + RC_PROTO_BIT_XBOX_DVD) /* All rc protocols for which we have decoders */ #define RC_PROTO_BIT_ALL_IR_DECODER \ (RC_PROTO_BIT_RC5 | RC_PROTO_BIT_RC5X_20 | \ diff --git a/include/uapi/linux/lirc.h b/include/uapi/linux/lirc.h index 45fcbf99d72e..f99d9dcae667 100644 --- a/include/uapi/linux/lirc.h +++ b/include/uapi/linux/lirc.h @@ -195,6 +195,7 @@ struct lirc_scancode { * @RC_PROTO_RCMM12: RC-MM protocol 12 bits * @RC_PROTO_RCMM24: RC-MM protocol 24 bits * @RC_PROTO_RCMM32: RC-MM protocol 32 bits + * @RC_PROTO_XBOX_DVD: Xbox DVD Movie Playback Kit protocol */ enum rc_proto { RC_PROTO_UNKNOWN = 0, @@ -224,6 +225,7 @@ enum rc_proto { RC_PROTO_RCMM12 = 24, RC_PROTO_RCMM24 = 25, RC_PROTO_RCMM32 = 26, + RC_PROTO_XBOX_DVD = 27, }; #endif -- cgit v1.2.3 From 3473ba384de7cf5df33f0ea3650aa4c7aaf1c995 Mon Sep 17 00:00:00 2001 From: Neil Armstrong Date: Fri, 12 Apr 2019 04:30:58 -0400 Subject: media: dt-bindings: media: meson-ao-cec: Add G12A AO-CEC-B Compatible The Amlogic G12A embeds a second CEC controller named AO-CEC-B, and the other one is AO-CEC-A described by the current bindings. The register interface is very close but the internal architecture is totally different. The other difference is the clock source, the AO-CEC-B takes the "oscin", the Always-On Oscillator clock, as input and embeds a dual-divider clock divider to provide the precise 32768Hz base clock for CEC communication. Signed-off-by: Neil Armstrong Reviewed-by: Rob Herring Signed-off-by: Hans Verkuil Signed-off-by: Mauro Carvalho Chehab --- Documentation/devicetree/bindings/media/meson-ao-cec.txt | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/media/meson-ao-cec.txt b/Documentation/devicetree/bindings/media/meson-ao-cec.txt index 8671bdb08080..c67fc41d4aa2 100644 --- a/Documentation/devicetree/bindings/media/meson-ao-cec.txt +++ b/Documentation/devicetree/bindings/media/meson-ao-cec.txt @@ -4,16 +4,23 @@ The Amlogic Meson AO-CEC module is present is Amlogic SoCs and its purpose is to handle communication between HDMI connected devices over the CEC bus. Required properties: - - compatible : value should be following + - compatible : value should be following depending on the SoC : + For GXBB, GXL, GXM and G12A (AO_CEC_A module) : "amlogic,meson-gx-ao-cec" + For G12A (AO_CEC_B module) : + "amlogic,meson-g12a-ao-cec" - reg : Physical base address of the IP registers and length of memory mapped region. - interrupts : AO-CEC interrupt number to the CPU. - clocks : from common clock binding: handle to AO-CEC clock. - - clock-names : from common clock binding: must contain "core", - corresponding to entry in the clocks property. + - clock-names : from common clock binding, must contain : + For GXBB, GXL, GXM and G12A (AO_CEC_A module) : + - "core" + For G12A (AO_CEC_B module) : + - "oscin" + corresponding to entry in the clocks property. - hdmi-phandle: phandle to the HDMI controller Example: -- cgit v1.2.3 From 8dce4b265a5357731058f69645840dabc718c687 Mon Sep 17 00:00:00 2001 From: Hans Verkuil Date: Wed, 10 Apr 2019 07:02:49 -0400 Subject: media: zoran: remove deprecated driver The zoran driver has been marked deprecated for a year now without any interest to update this driver to the vb2 framework. Time to remove it altogether. Signed-off-by: Hans Verkuil Signed-off-by: Mauro Carvalho Chehab --- Documentation/media/v4l-drivers/index.rst | 1 - Documentation/media/v4l-drivers/zoran.rst | 583 ------ drivers/staging/media/Kconfig | 2 - drivers/staging/media/Makefile | 1 - drivers/staging/media/zoran/Kconfig | 75 - drivers/staging/media/zoran/Makefile | 7 - drivers/staging/media/zoran/TODO | 4 - drivers/staging/media/zoran/videocodec.c | 391 ---- drivers/staging/media/zoran/videocodec.h | 349 ---- drivers/staging/media/zoran/zoran.h | 402 ---- drivers/staging/media/zoran/zoran_card.c | 1524 --------------- drivers/staging/media/zoran/zoran_card.h | 50 - drivers/staging/media/zoran/zoran_device.c | 1619 ---------------- drivers/staging/media/zoran/zoran_device.h | 91 - drivers/staging/media/zoran/zoran_driver.c | 2850 ---------------------------- drivers/staging/media/zoran/zoran_procfs.c | 221 --- drivers/staging/media/zoran/zoran_procfs.h | 32 - drivers/staging/media/zoran/zr36016.c | 516 ----- drivers/staging/media/zoran/zr36016.h | 107 -- drivers/staging/media/zoran/zr36050.c | 896 --------- drivers/staging/media/zoran/zr36050.h | 179 -- drivers/staging/media/zoran/zr36057.h | 164 -- drivers/staging/media/zoran/zr36060.c | 1006 ---------- drivers/staging/media/zoran/zr36060.h | 216 --- 24 files changed, 11286 deletions(-) delete mode 100644 Documentation/media/v4l-drivers/zoran.rst delete mode 100644 drivers/staging/media/zoran/Kconfig delete mode 100644 drivers/staging/media/zoran/Makefile delete mode 100644 drivers/staging/media/zoran/TODO delete mode 100644 drivers/staging/media/zoran/videocodec.c delete mode 100644 drivers/staging/media/zoran/videocodec.h delete mode 100644 drivers/staging/media/zoran/zoran.h delete mode 100644 drivers/staging/media/zoran/zoran_card.c delete mode 100644 drivers/staging/media/zoran/zoran_card.h delete mode 100644 drivers/staging/media/zoran/zoran_device.c delete mode 100644 drivers/staging/media/zoran/zoran_device.h delete mode 100644 drivers/staging/media/zoran/zoran_driver.c delete mode 100644 drivers/staging/media/zoran/zoran_procfs.c delete mode 100644 drivers/staging/media/zoran/zoran_procfs.h delete mode 100644 drivers/staging/media/zoran/zr36016.c delete mode 100644 drivers/staging/media/zoran/zr36016.h delete mode 100644 drivers/staging/media/zoran/zr36050.c delete mode 100644 drivers/staging/media/zoran/zr36050.h delete mode 100644 drivers/staging/media/zoran/zr36057.h delete mode 100644 drivers/staging/media/zoran/zr36060.c delete mode 100644 drivers/staging/media/zoran/zr36060.h (limited to 'Documentation') diff --git a/Documentation/media/v4l-drivers/index.rst b/Documentation/media/v4l-drivers/index.rst index dfd4b205937c..33a055907258 100644 --- a/Documentation/media/v4l-drivers/index.rst +++ b/Documentation/media/v4l-drivers/index.rst @@ -65,5 +65,4 @@ For more details see the file COPYING in the source distribution of Linux. soc-camera uvcvideo vivid - zoran zr364xx diff --git a/Documentation/media/v4l-drivers/zoran.rst b/Documentation/media/v4l-drivers/zoran.rst deleted file mode 100644 index d2724a863d1d..000000000000 --- a/Documentation/media/v4l-drivers/zoran.rst +++ /dev/null @@ -1,583 +0,0 @@ -.. SPDX-License-Identifier: GPL-2.0 - -The Zoran driver -================ - -unified zoran driver (zr360x7, zoran, buz, dc10(+), dc30(+), lml33) - -website: http://mjpeg.sourceforge.net/driver-zoran/ - - -Frequently Asked Questions --------------------------- - -What cards are supported ------------------------- - -Iomega Buz, Linux Media Labs LML33/LML33R10, Pinnacle/Miro -DC10/DC10+/DC30/DC30+ and related boards (available under various names). - -Iomega Buz -~~~~~~~~~~ - -* Zoran zr36067 PCI controller -* Zoran zr36060 MJPEG codec -* Philips saa7111 TV decoder -* Philips saa7185 TV encoder - -Drivers to use: videodev, i2c-core, i2c-algo-bit, -videocodec, saa7111, saa7185, zr36060, zr36067 - -Inputs/outputs: Composite and S-video - -Norms: PAL, SECAM (720x576 @ 25 fps), NTSC (720x480 @ 29.97 fps) - -Card number: 7 - -AverMedia 6 Eyes AVS6EYES -~~~~~~~~~~~~~~~~~~~~~~~~~ - -* Zoran zr36067 PCI controller -* Zoran zr36060 MJPEG codec -* Samsung ks0127 TV decoder -* Conexant bt866 TV encoder - -Drivers to use: videodev, i2c-core, i2c-algo-bit, -videocodec, ks0127, bt866, zr36060, zr36067 - -Inputs/outputs: - Six physical inputs. 1-6 are composite, - 1-2, 3-4, 5-6 doubles as S-video, - 1-3 triples as component. - One composite output. - -Norms: PAL, SECAM (720x576 @ 25 fps), NTSC (720x480 @ 29.97 fps) - -Card number: 8 - -.. note:: - - Not autodetected, card=8 is necessary. - -Linux Media Labs LML33 -~~~~~~~~~~~~~~~~~~~~~~ - -* Zoran zr36067 PCI controller -* Zoran zr36060 MJPEG codec -* Brooktree bt819 TV decoder -* Brooktree bt856 TV encoder - -Drivers to use: videodev, i2c-core, i2c-algo-bit, -videocodec, bt819, bt856, zr36060, zr36067 - -Inputs/outputs: Composite and S-video - -Norms: PAL (720x576 @ 25 fps), NTSC (720x480 @ 29.97 fps) - -Card number: 5 - -Linux Media Labs LML33R10 -~~~~~~~~~~~~~~~~~~~~~~~~~ - -* Zoran zr36067 PCI controller -* Zoran zr36060 MJPEG codec -* Philips saa7114 TV decoder -* Analog Devices adv7170 TV encoder - -Drivers to use: videodev, i2c-core, i2c-algo-bit, -videocodec, saa7114, adv7170, zr36060, zr36067 - -Inputs/outputs: Composite and S-video - -Norms: PAL (720x576 @ 25 fps), NTSC (720x480 @ 29.97 fps) - -Card number: 6 - -Pinnacle/Miro DC10(new) -~~~~~~~~~~~~~~~~~~~~~~~ - -* Zoran zr36057 PCI controller -* Zoran zr36060 MJPEG codec -* Philips saa7110a TV decoder -* Analog Devices adv7176 TV encoder - -Drivers to use: videodev, i2c-core, i2c-algo-bit, -videocodec, saa7110, adv7175, zr36060, zr36067 - -Inputs/outputs: Composite, S-video and Internal - -Norms: PAL, SECAM (768x576 @ 25 fps), NTSC (640x480 @ 29.97 fps) - -Card number: 1 - -Pinnacle/Miro DC10+ -~~~~~~~~~~~~~~~~~~~ - -* Zoran zr36067 PCI controller -* Zoran zr36060 MJPEG codec -* Philips saa7110a TV decoder -* Analog Devices adv7176 TV encoder - -Drivers to use: videodev, i2c-core, i2c-algo-bit, -videocodec, sa7110, adv7175, zr36060, zr36067 - -Inputs/outputs: Composite, S-video and Internal - -Norms: PAL, SECAM (768x576 @ 25 fps), NTSC (640x480 @ 29.97 fps) - -Card number: 2 - -Pinnacle/Miro DC10(old) -~~~~~~~~~~~~~~~~~~~~~~~ - -* Zoran zr36057 PCI controller -* Zoran zr36050 MJPEG codec -* Zoran zr36016 Video Front End or Fuji md0211 Video Front End (clone?) -* Micronas vpx3220a TV decoder -* mse3000 TV encoder or Analog Devices adv7176 TV encoder - -Drivers to use: videodev, i2c-core, i2c-algo-bit, -videocodec, vpx3220, mse3000/adv7175, zr36050, zr36016, zr36067 - -Inputs/outputs: Composite, S-video and Internal - -Norms: PAL, SECAM (768x576 @ 25 fps), NTSC (640x480 @ 29.97 fps) - -Card number: 0 - -Pinnacle/Miro DC30 -~~~~~~~~~~~~~~~~~~ - -* Zoran zr36057 PCI controller -* Zoran zr36050 MJPEG codec -* Zoran zr36016 Video Front End -* Micronas vpx3225d/vpx3220a/vpx3216b TV decoder -* Analog Devices adv7176 TV encoder - -Drivers to use: videodev, i2c-core, i2c-algo-bit, -videocodec, vpx3220/vpx3224, adv7175, zr36050, zr36016, zr36067 - -Inputs/outputs: Composite, S-video and Internal - -Norms: PAL, SECAM (768x576 @ 25 fps), NTSC (640x480 @ 29.97 fps) - -Card number: 3 - -Pinnacle/Miro DC30+ -~~~~~~~~~~~~~~~~~~~ - -* Zoran zr36067 PCI controller -* Zoran zr36050 MJPEG codec -* Zoran zr36016 Video Front End -* Micronas vpx3225d/vpx3220a/vpx3216b TV decoder -* Analog Devices adv7176 TV encoder - -Drivers to use: videodev, i2c-core, i2c-algo-bit, -videocodec, vpx3220/vpx3224, adv7175, zr36050, zr36015, zr36067 - -Inputs/outputs: Composite, S-video and Internal - -Norms: PAL, SECAM (768x576 @ 25 fps), NTSC (640x480 @ 29.97 fps) - -Card number: 4 - -.. note:: - - #) No module for the mse3000 is available yet - #) No module for the vpx3224 is available yet - -1.1 What the TV decoder can do an what not ------------------------------------------- - -The best know TV standards are NTSC/PAL/SECAM. but for decoding a frame that -information is not enough. There are several formats of the TV standards. -And not every TV decoder is able to handle every format. Also the every -combination is supported by the driver. There are currently 11 different -tv broadcast formats all aver the world. - -The CCIR defines parameters needed for broadcasting the signal. -The CCIR has defined different standards: A,B,D,E,F,G,D,H,I,K,K1,L,M,N,... -The CCIR says not much about the colorsystem used !!! -And talking about a colorsystem says not to much about how it is broadcast. - -The CCIR standards A,E,F are not used any more. - -When you speak about NTSC, you usually mean the standard: CCIR - M using -the NTSC colorsystem which is used in the USA, Japan, Mexico, Canada -and a few others. - -When you talk about PAL, you usually mean: CCIR - B/G using the PAL -colorsystem which is used in many Countries. - -When you talk about SECAM, you mean: CCIR - L using the SECAM Colorsystem -which is used in France, and a few others. - -There the other version of SECAM, CCIR - D/K is used in Bulgaria, China, -Slovakai, Hungary, Korea (Rep.), Poland, Rumania and a others. - -The CCIR - H uses the PAL colorsystem (sometimes SECAM) and is used in -Egypt, Libya, Sri Lanka, Syrain Arab. Rep. - -The CCIR - I uses the PAL colorsystem, and is used in Great Britain, Hong Kong, -Ireland, Nigeria, South Africa. - -The CCIR - N uses the PAL colorsystem and PAL frame size but the NTSC framerate, -and is used in Argentinia, Uruguay, an a few others - -We do not talk about how the audio is broadcast ! - -A rather good sites about the TV standards are: -http://www.sony.jp/support/ -http://info.electronicwerkstatt.de/bereiche/fernsehtechnik/frequenzen_und_normen/Fernsehnormen/ -and http://www.cabl.com/restaurant/channel.html - -Other weird things around: NTSC 4.43 is a modificated NTSC, which is mainly -used in PAL VCR's that are able to play back NTSC. PAL 60 seems to be the same -as NTSC 4.43 . The Datasheets also talk about NTSC 44, It seems as if it would -be the same as NTSC 4.43. -NTSC Combs seems to be a decoder mode where the decoder uses a comb filter -to split coma and luma instead of a Delay line. - -But I did not defiantly find out what NTSC Comb is. - -Philips saa7111 TV decoder -~~~~~~~~~~~~~~~~~~~~~~~~~~ - -- was introduced in 1997, is used in the BUZ and -- can handle: PAL B/G/H/I, PAL N, PAL M, NTSC M, NTSC N, NTSC 4.43 and SECAM - -Philips saa7110a TV decoder -~~~~~~~~~~~~~~~~~~~~~~~~~~~ - -- was introduced in 1995, is used in the Pinnacle/Miro DC10(new), DC10+ and -- can handle: PAL B/G, NTSC M and SECAM - -Philips saa7114 TV decoder -~~~~~~~~~~~~~~~~~~~~~~~~~~ - -- was introduced in 2000, is used in the LML33R10 and -- can handle: PAL B/G/D/H/I/N, PAL N, PAL M, NTSC M, NTSC 4.43 and SECAM - -Brooktree bt819 TV decoder -~~~~~~~~~~~~~~~~~~~~~~~~~~ - -- was introduced in 1996, and is used in the LML33 and -- can handle: PAL B/D/G/H/I, NTSC M - -Micronas vpx3220a TV decoder -~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - -- was introduced in 1996, is used in the DC30 and DC30+ and -- can handle: PAL B/G/H/I, PAL N, PAL M, NTSC M, NTSC 44, PAL 60, SECAM,NTSC Comb - -Samsung ks0127 TV decoder -~~~~~~~~~~~~~~~~~~~~~~~~~ - -- is used in the AVS6EYES card and -- can handle: NTSC-M/N/44, PAL-M/N/B/G/H/I/D/K/L and SECAM - - -What the TV encoder can do an what not --------------------------------------- - -The TV encoder are doing the "same" as the decoder, but in the oder direction. -You feed them digital data and the generate a Composite or SVHS signal. -For information about the colorsystems and TV norm take a look in the -TV decoder section. - -Philips saa7185 TV Encoder -~~~~~~~~~~~~~~~~~~~~~~~~~~ - -- was introduced in 1996, is used in the BUZ -- can generate: PAL B/G, NTSC M - -Brooktree bt856 TV Encoder -~~~~~~~~~~~~~~~~~~~~~~~~~~ - -- was introduced in 1994, is used in the LML33 -- can generate: PAL B/D/G/H/I/N, PAL M, NTSC M, PAL-N (Argentina) - -Analog Devices adv7170 TV Encoder -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - -- was introduced in 2000, is used in the LML300R10 -- can generate: PAL B/D/G/H/I/N, PAL M, NTSC M, PAL 60 - -Analog Devices adv7175 TV Encoder -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - -- was introduced in 1996, is used in the DC10, DC10+, DC10 old, DC30, DC30+ -- can generate: PAL B/D/G/H/I/N, PAL M, NTSC M - -ITT mse3000 TV encoder -~~~~~~~~~~~~~~~~~~~~~~ - -- was introduced in 1991, is used in the DC10 old -- can generate: PAL , NTSC , SECAM - -Conexant bt866 TV encoder -~~~~~~~~~~~~~~~~~~~~~~~~~ - -- is used in AVS6EYES, and -- can generate: NTSC/PAL, PAL­M, PAL­N - -The adv717x, should be able to produce PAL N. But you find nothing PAL N -specific in the registers. Seem that you have to reuse a other standard -to generate PAL N, maybe it would work if you use the PAL M settings. - -How do I get this damn thing to work ------------------------------------- - -Load zr36067.o. If it can't autodetect your card, use the card=X insmod -option with X being the card number as given in the previous section. -To have more than one card, use card=X1[,X2[,X3,[X4[..]]]] - -To automate this, add the following to your /etc/modprobe.d/zoran.conf: - -options zr36067 card=X1[,X2[,X3[,X4[..]]]] -alias char-major-81-0 zr36067 - -One thing to keep in mind is that this doesn't load zr36067.o itself yet. It -just automates loading. If you start using xawtv, the device won't load on -some systems, since you're trying to load modules as a user, which is not -allowed ("permission denied"). A quick workaround is to add 'Load "v4l"' to -XF86Config-4 when you use X by default, or to run 'v4l-conf -c ' in -one of your startup scripts (normally rc.local) if you don't use X. Both -make sure that the modules are loaded on startup, under the root account. - -What mainboard should I use (or why doesn't my card work) ---------------------------------------------------------- - - -. In short: good=SiS/Intel, bad=VIA. - -Experience tells us that people with a Buz, on average, have more problems -than users with a DC10+/LML33. Also, it tells us that people owning a VIA- -based mainboard (ktXXX, MVP3) have more problems than users with a mainboard -based on a different chipset. Here's some notes from Andrew Stevens: - -Here's my experience of using LML33 and Buz on various motherboards: - -- VIA MVP3 - - Forget it. Pointless. Doesn't work. -- Intel 430FX (Pentium 200) - - LML33 perfect, Buz tolerable (3 or 4 frames dropped per movie) -- Intel 440BX (early stepping) - - LML33 tolerable. Buz starting to get annoying (6-10 frames/hour) -- Intel 440BX (late stepping) - - Buz tolerable, LML3 almost perfect (occasional single frame drops) -- SiS735 - - LML33 perfect, Buz tolerable. -- VIA KT133(*) - - LML33 starting to get annoying, Buz poor enough that I have up. - -- Both 440BX boards were dual CPU versions. - -Bernhard Praschinger later added: - -- AMD 751 - - Buz perfect-tolerable -- AMD 760 - - Buz perfect-tolerable - -In general, people on the user mailinglist won't give you much of a chance -if you have a VIA-based motherboard. They may be cheap, but sometimes, you'd -rather want to spend some more money on better boards. In general, VIA -mainboard's IDE/PCI performance will also suck badly compared to others. -You'll noticed the DC10+/DC30+ aren't mentioned anywhere in the overview. -Basically, you can assume that if the Buz works, the LML33 will work too. If -the LML33 works, the DC10+/DC30+ will work too. They're most tolerant to -different mainboard chipsets from all of the supported cards. - -If you experience timeouts during capture, buy a better mainboard or lower -the quality/buffersize during capture (see 'Concerning buffer sizes, quality, -output size etc.'). If it hangs, there's little we can do as of now. Check -your IRQs and make sure the card has its own interrupts. - -Programming interface ---------------------- - -This driver conforms to video4linux2. Support for V4L1 and for the custom -zoran ioctls has been removed in kernel 2.6.38. - -For programming example, please, look at lavrec.c and lavplay.c code in -the MJPEG-tools (http://mjpeg.sf.net/). - -Additional notes for software developers: - - The driver returns maxwidth and maxheight parameters according to - the current TV standard (norm). Therefore, the software which - communicates with the driver and "asks" for these parameters should - first set the correct norm. Well, it seems logically correct: TV - standard is "more constant" for current country than geometry - settings of a variety of TV capture cards which may work in ITU or - square pixel format. - -Applications ------------- - -Applications known to work with this driver: - -TV viewing: - -* xawtv -* kwintv -* probably any TV application that supports video4linux or video4linux2. - -MJPEG capture/playback: - -* mjpegtools/lavtools (or Linux Video Studio) -* gstreamer -* mplayer - -General raw capture: - -* xawtv -* gstreamer -* probably any application that supports video4linux or video4linux2 - -Video editing: - -* Cinelerra -* MainActor -* mjpegtools (or Linux Video Studio) - - -Concerning buffer sizes, quality, output size etc. --------------------------------------------------- - - -The zr36060 can do 1:2 JPEG compression. This is really the theoretical -maximum that the chipset can reach. The driver can, however, limit compression -to a maximum (size) of 1:4. The reason for this is that some cards (e.g. Buz) -can't handle 1:2 compression without stopping capture after only a few minutes. -With 1:4, it'll mostly work. If you have a Buz, use 'low_bitrate=1' to go into -1:4 max. compression mode. - -100% JPEG quality is thus 1:2 compression in practice. So for a full PAL frame -(size 720x576). The JPEG fields are stored in YUY2 format, so the size of the -fields are 720x288x16/2 bits/field (2 fields/frame) = 207360 bytes/field x 2 = -414720 bytes/frame (add some more bytes for headers and DHT (huffman)/DQT -(quantization) tables, and you'll get to something like 512kB per frame for -1:2 compression. For 1:4 compression, you'd have frames of half this size. - -Some additional explanation by Martin Samuelsson, which also explains the -importance of buffer sizes: --- -> Hmm, I do not think it is really that way. With the current (downloaded -> at 18:00 Monday) driver I get that output sizes for 10 sec: -> -q 50 -b 128 : 24.283.332 Bytes -> -q 50 -b 256 : 48.442.368 -> -q 25 -b 128 : 24.655.992 -> -q 25 -b 256 : 25.859.820 - -I woke up, and can't go to sleep again. I'll kill some time explaining why -this doesn't look strange to me. - -Let's do some math using a width of 704 pixels. I'm not sure whether the Buz -actually use that number or not, but that's not too important right now. - -704x288 pixels, one field, is 202752 pixels. Divided by 64 pixels per block; -3168 blocks per field. Each pixel consist of two bytes; 128 bytes per block; -1024 bits per block. 100% in the new driver mean 1:2 compression; the maximum -output becomes 512 bits per block. Actually 510, but 512 is simpler to use -for calculations. - -Let's say that we specify d1q50. We thus want 256 bits per block; times 3168 -becomes 811008 bits; 101376 bytes per field. We're talking raw bits and bytes -here, so we don't need to do any fancy corrections for bits-per-pixel or such -things. 101376 bytes per field. - -d1 video contains two fields per frame. Those sum up to 202752 bytes per -frame, and one of those frames goes into each buffer. - -But wait a second! -b128 gives 128kB buffers! It's not possible to cram -202752 bytes of JPEG data into 128kB! - -This is what the driver notice and automatically compensate for in your -examples. Let's do some math using this information: - -128kB is 131072 bytes. In this buffer, we want to store two fields, which -leaves 65536 bytes for each field. Using 3168 blocks per field, we get -20.68686868... available bytes per block; 165 bits. We can't allow the -request for 256 bits per block when there's only 165 bits available! The -q50 -option is silently overridden, and the -b128 option takes precedence, leaving -us with the equivalence of -q32. - -This gives us a data rate of 165 bits per block, which, times 3168, sums up -to 65340 bytes per field, out of the allowed 65536. The current driver has -another level of rate limiting; it won't accept -q values that fill more than -6/8 of the specified buffers. (I'm not sure why. "Playing it safe" seem to be -a safe bet. Personally, I think I would have lowered requested-bits-per-block -by one, or something like that.) We can't use 165 bits per block, but have to -lower it again, to 6/8 of the available buffer space: We end up with 124 bits -per block, the equivalence of -q24. With 128kB buffers, you can't use greater -than -q24 at -d1. (And PAL, and 704 pixels width...) - -The third example is limited to -q24 through the same process. The second -example, using very similar calculations, is limited to -q48. The only -example that actually grab at the specified -q value is the last one, which -is clearly visible, looking at the file size. --- - -Conclusion: the quality of the resulting movie depends on buffer size, quality, -whether or not you use 'low_bitrate=1' as insmod option for the zr36060.c -module to do 1:4 instead of 1:2 compression, etc. - -If you experience timeouts, lowering the quality/buffersize or using -'low_bitrate=1 as insmod option for zr36060.o might actually help, as is -proven by the Buz. - -It hangs/crashes/fails/whatevers! Help! ---------------------------------------- - -Make sure that the card has its own interrupts (see /proc/interrupts), check -the output of dmesg at high verbosity (load zr36067.o with debug=2, -load all other modules with debug=1). Check that your mainboard is favorable -(see question 2) and if not, test the card in another computer. Also see the -notes given in question 3 and try lowering quality/buffersize/capturesize -if recording fails after a period of time. - -If all this doesn't help, give a clear description of the problem including -detailed hardware information (memory+brand, mainboard+chipset+brand, which -MJPEG card, processor, other PCI cards that might be of interest), give the -system PnP information (/proc/interrupts, /proc/dma, /proc/devices), and give -the kernel version, driver version, glibc version, gcc version and any other -information that might possibly be of interest. Also provide the dmesg output -at high verbosity. See 'Contacting' on how to contact the developers. - -Maintainers/Contacting ----------------------- - -The driver is currently maintained by Laurent Pinchart and Ronald Bultje -( and ). For bug -reports or questions, please contact the mailinglist instead of the developers -individually. For user questions (i.e. bug reports or how-to questions), send -an email to , for developers (i.e. if you want to -help programming), send an email to . See -http://www.sf.net/projects/mjpeg/ for subscription information. - -For bug reports, be sure to include all the information as described in -the section 'It hangs/crashes/fails/whatevers! Help!'. Please make sure -you're using the latest version (http://mjpeg.sf.net/driver-zoran/). - -Previous maintainers/developers of this driver include Serguei Miridonov -, Wolfgang Scherr , Dave Perks - and Rainer Johanni . - -Driver's License ----------------- - - This driver is distributed under the terms of the General Public License. - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - -See http://www.gnu.org/ for more information. diff --git a/drivers/staging/media/Kconfig b/drivers/staging/media/Kconfig index 277df2b39384..5486cf5d998f 100644 --- a/drivers/staging/media/Kconfig +++ b/drivers/staging/media/Kconfig @@ -33,8 +33,6 @@ source "drivers/staging/media/sunxi/Kconfig" source "drivers/staging/media/tegra-vde/Kconfig" -source "drivers/staging/media/zoran/Kconfig" - source "drivers/staging/media/ipu3/Kconfig" source "drivers/staging/media/soc_camera/Kconfig" diff --git a/drivers/staging/media/Makefile b/drivers/staging/media/Makefile index 0355e3030504..99218bfc997f 100644 --- a/drivers/staging/media/Makefile +++ b/drivers/staging/media/Makefile @@ -5,7 +5,6 @@ obj-$(CONFIG_VIDEO_DM365_VPFE) += davinci_vpfe/ obj-$(CONFIG_VIDEO_OMAP4) += omap4iss/ obj-$(CONFIG_VIDEO_SUNXI) += sunxi/ obj-$(CONFIG_TEGRA_VDE) += tegra-vde/ -obj-$(CONFIG_VIDEO_ZORAN) += zoran/ obj-$(CONFIG_VIDEO_ROCKCHIP_VPU) += rockchip/vpu/ obj-$(CONFIG_VIDEO_IPU3_IMGU) += ipu3/ obj-$(CONFIG_SOC_CAMERA) += soc_camera/ diff --git a/drivers/staging/media/zoran/Kconfig b/drivers/staging/media/zoran/Kconfig deleted file mode 100644 index 34a18135ede0..000000000000 --- a/drivers/staging/media/zoran/Kconfig +++ /dev/null @@ -1,75 +0,0 @@ -config VIDEO_ZORAN - tristate "Zoran ZR36057/36067 Video For Linux (Deprecated)" - depends on PCI && I2C_ALGOBIT && VIDEO_V4L2 && VIRT_TO_BUS - depends on !ALPHA - help - Say Y for support for MJPEG capture cards based on the Zoran - 36057/36067 PCI controller chipset. This includes the Iomega - Buz, Pinnacle DC10+ and the Linux Media Labs LML33. There is - a driver homepage at . For - more information, check . - - To compile this driver as a module, choose M here: the - module will be called zr36067. - -config VIDEO_ZORAN_DC30 - tristate "Pinnacle/Miro DC30(+) support" - depends on VIDEO_ZORAN - select VIDEO_ADV7175 if MEDIA_SUBDRV_AUTOSELECT - select VIDEO_VPX3220 if MEDIA_SUBDRV_AUTOSELECT - help - Support for the Pinnacle/Miro DC30(+) MJPEG capture/playback - card. This also supports really old DC10 cards based on the - zr36050 MJPEG codec and zr36016 VFE. - -config VIDEO_ZORAN_ZR36060 - tristate "Zoran ZR36060" - depends on VIDEO_ZORAN - help - Say Y to support Zoran boards based on 36060 chips. - This includes Iomega Buz, Pinnacle DC10, Linux media Labs 33 - and 33 R10 and AverMedia 6 boards. - -config VIDEO_ZORAN_BUZ - tristate "Iomega Buz support" - depends on VIDEO_ZORAN_ZR36060 - select VIDEO_SAA711X if MEDIA_SUBDRV_AUTOSELECT - select VIDEO_SAA7185 if MEDIA_SUBDRV_AUTOSELECT - help - Support for the Iomega Buz MJPEG capture/playback card. - -config VIDEO_ZORAN_DC10 - tristate "Pinnacle/Miro DC10(+) support" - depends on VIDEO_ZORAN_ZR36060 - select VIDEO_SAA7110 if MEDIA_SUBDRV_AUTOSELECT - select VIDEO_ADV7175 if MEDIA_SUBDRV_AUTOSELECT - help - Support for the Pinnacle/Miro DC10(+) MJPEG capture/playback - card. - -config VIDEO_ZORAN_LML33 - tristate "Linux Media Labs LML33 support" - depends on VIDEO_ZORAN_ZR36060 - select VIDEO_BT819 if MEDIA_SUBDRV_AUTOSELECT - select VIDEO_BT856 if MEDIA_SUBDRV_AUTOSELECT - help - Support for the Linux Media Labs LML33 MJPEG capture/playback - card. - -config VIDEO_ZORAN_LML33R10 - tristate "Linux Media Labs LML33R10 support" - depends on VIDEO_ZORAN_ZR36060 - select VIDEO_SAA711X if MEDIA_SUBDRV_AUTOSELECT - select VIDEO_ADV7170 if MEDIA_SUBDRV_AUTOSELECT - help - support for the Linux Media Labs LML33R10 MJPEG capture/playback - card. - -config VIDEO_ZORAN_AVS6EYES - tristate "AverMedia 6 Eyes support" - depends on VIDEO_ZORAN_ZR36060 - select VIDEO_BT856 if MEDIA_SUBDRV_AUTOSELECT - select VIDEO_BT866 if MEDIA_SUBDRV_AUTOSELECT - select VIDEO_KS0127 if MEDIA_SUBDRV_AUTOSELECT - help - Support for the AverMedia 6 Eyes video surveillance card. diff --git a/drivers/staging/media/zoran/Makefile b/drivers/staging/media/zoran/Makefile deleted file mode 100644 index 21ac29a71458..000000000000 --- a/drivers/staging/media/zoran/Makefile +++ /dev/null @@ -1,7 +0,0 @@ -# SPDX-License-Identifier: GPL-2.0 -zr36067-objs := zoran_procfs.o zoran_device.o \ - zoran_driver.o zoran_card.o - -obj-$(CONFIG_VIDEO_ZORAN) += zr36067.o videocodec.o -obj-$(CONFIG_VIDEO_ZORAN_DC30) += zr36050.o zr36016.o -obj-$(CONFIG_VIDEO_ZORAN_ZR36060) += zr36060.o diff --git a/drivers/staging/media/zoran/TODO b/drivers/staging/media/zoran/TODO deleted file mode 100644 index 54464095d0d7..000000000000 --- a/drivers/staging/media/zoran/TODO +++ /dev/null @@ -1,4 +0,0 @@ -The zoran driver is marked deprecated. It will be removed -around May 2019 unless someone is willing to update this -driver to the latest V4L2 frameworks (especially the vb2 -framework). diff --git a/drivers/staging/media/zoran/videocodec.c b/drivers/staging/media/zoran/videocodec.c deleted file mode 100644 index 044ef8455ba8..000000000000 --- a/drivers/staging/media/zoran/videocodec.c +++ /dev/null @@ -1,391 +0,0 @@ -/* - * VIDEO MOTION CODECs internal API for video devices - * - * Interface for MJPEG (and maybe later MPEG/WAVELETS) codec's - * bound to a master device. - * - * (c) 2002 Wolfgang Scherr - * - * $Id: videocodec.c,v 1.1.2.8 2003/03/29 07:16:04 rbultje Exp $ - * - * ------------------------------------------------------------------------ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * ------------------------------------------------------------------------ - */ - -#define VIDEOCODEC_VERSION "v0.2" - -#include -#include -#include -#include -#include - -// kernel config is here (procfs flag) - -#ifdef CONFIG_PROC_FS -#include -#include -#include -#endif - -#include "videocodec.h" - -static int debug; -module_param(debug, int, 0); -MODULE_PARM_DESC(debug, "Debug level (0-4)"); - -#define dprintk(num, format, args...) \ - do { \ - if (debug >= num) \ - printk(format, ##args); \ - } while (0) - -struct attached_list { - struct videocodec *codec; - struct attached_list *next; -}; - -struct codec_list { - const struct videocodec *codec; - int attached; - struct attached_list *list; - struct codec_list *next; -}; - -static struct codec_list *codeclist_top; - -/* ================================================= */ -/* function prototypes of the master/slave interface */ -/* ================================================= */ - -struct videocodec * -videocodec_attach (struct videocodec_master *master) -{ - struct codec_list *h = codeclist_top; - struct attached_list *a, *ptr; - struct videocodec *codec; - int res; - - if (!master) { - dprintk(1, KERN_ERR "videocodec_attach: no data\n"); - return NULL; - } - - dprintk(2, - "videocodec_attach: '%s', flags %lx, magic %lx\n", - master->name, master->flags, master->magic); - - if (!h) { - dprintk(1, - KERN_ERR - "videocodec_attach: no device available\n"); - return NULL; - } - - while (h) { - // attach only if the slave has at least the flags - // expected by the master - if ((master->flags & h->codec->flags) == master->flags) { - dprintk(4, "videocodec_attach: try '%s'\n", - h->codec->name); - - if (!try_module_get(h->codec->owner)) - return NULL; - - codec = kmemdup(h->codec, sizeof(struct videocodec), - GFP_KERNEL); - if (!codec) { - dprintk(1, - KERN_ERR - "videocodec_attach: no mem\n"); - goto out_module_put; - } - - res = strlen(codec->name); - snprintf(codec->name + res, sizeof(codec->name) - res, - "[%d]", h->attached); - codec->master_data = master; - res = codec->setup(codec); - if (res == 0) { - dprintk(3, "videocodec_attach '%s'\n", - codec->name); - ptr = kzalloc(sizeof(struct attached_list), GFP_KERNEL); - if (!ptr) { - dprintk(1, - KERN_ERR - "videocodec_attach: no memory\n"); - goto out_kfree; - } - ptr->codec = codec; - - a = h->list; - if (!a) { - h->list = ptr; - dprintk(4, - "videocodec: first element\n"); - } else { - while (a->next) - a = a->next; // find end - a->next = ptr; - dprintk(4, - "videocodec: in after '%s'\n", - h->codec->name); - } - - h->attached += 1; - return codec; - } else { - kfree(codec); - } - } - h = h->next; - } - - dprintk(1, KERN_ERR "videocodec_attach: no codec found!\n"); - return NULL; - - out_module_put: - module_put(h->codec->owner); - out_kfree: - kfree(codec); - return NULL; -} - -int -videocodec_detach (struct videocodec *codec) -{ - struct codec_list *h = codeclist_top; - struct attached_list *a, *prev; - int res; - - if (!codec) { - dprintk(1, KERN_ERR "videocodec_detach: no data\n"); - return -EINVAL; - } - - dprintk(2, - "videocodec_detach: '%s', type: %x, flags %lx, magic %lx\n", - codec->name, codec->type, codec->flags, codec->magic); - - if (!h) { - dprintk(1, - KERN_ERR "videocodec_detach: no device left...\n"); - return -ENXIO; - } - - while (h) { - a = h->list; - prev = NULL; - while (a) { - if (codec == a->codec) { - res = a->codec->unset(a->codec); - if (res >= 0) { - dprintk(3, - "videocodec_detach: '%s'\n", - a->codec->name); - a->codec->master_data = NULL; - } else { - dprintk(1, - KERN_ERR - "videocodec_detach: '%s'\n", - a->codec->name); - a->codec->master_data = NULL; - } - if (prev == NULL) { - h->list = a->next; - dprintk(4, - "videocodec: delete first\n"); - } else { - prev->next = a->next; - dprintk(4, - "videocodec: delete middle\n"); - } - module_put(a->codec->owner); - kfree(a->codec); - kfree(a); - h->attached -= 1; - return 0; - } - prev = a; - a = a->next; - } - h = h->next; - } - - dprintk(1, KERN_ERR "videocodec_detach: given codec not found!\n"); - return -EINVAL; -} - -int -videocodec_register (const struct videocodec *codec) -{ - struct codec_list *ptr, *h = codeclist_top; - - if (!codec) { - dprintk(1, KERN_ERR "videocodec_register: no data!\n"); - return -EINVAL; - } - - dprintk(2, - "videocodec: register '%s', type: %x, flags %lx, magic %lx\n", - codec->name, codec->type, codec->flags, codec->magic); - - ptr = kzalloc(sizeof(struct codec_list), GFP_KERNEL); - if (!ptr) { - dprintk(1, KERN_ERR "videocodec_register: no memory\n"); - return -ENOMEM; - } - ptr->codec = codec; - - if (!h) { - codeclist_top = ptr; - dprintk(4, "videocodec: hooked in as first element\n"); - } else { - while (h->next) - h = h->next; // find the end - h->next = ptr; - dprintk(4, "videocodec: hooked in after '%s'\n", - h->codec->name); - } - - return 0; -} - -int -videocodec_unregister (const struct videocodec *codec) -{ - struct codec_list *prev = NULL, *h = codeclist_top; - - if (!codec) { - dprintk(1, KERN_ERR "videocodec_unregister: no data!\n"); - return -EINVAL; - } - - dprintk(2, - "videocodec: unregister '%s', type: %x, flags %lx, magic %lx\n", - codec->name, codec->type, codec->flags, codec->magic); - - if (!h) { - dprintk(1, - KERN_ERR - "videocodec_unregister: no device left...\n"); - return -ENXIO; - } - - while (h) { - if (codec == h->codec) { - if (h->attached) { - dprintk(1, - KERN_ERR - "videocodec: '%s' is used\n", - h->codec->name); - return -EBUSY; - } - dprintk(3, "videocodec: unregister '%s' is ok.\n", - h->codec->name); - if (prev == NULL) { - codeclist_top = h->next; - dprintk(4, - "videocodec: delete first element\n"); - } else { - prev->next = h->next; - dprintk(4, - "videocodec: delete middle element\n"); - } - kfree(h); - return 0; - } - prev = h; - h = h->next; - } - - dprintk(1, - KERN_ERR - "videocodec_unregister: given codec not found!\n"); - return -EINVAL; -} - -#ifdef CONFIG_PROC_FS -static int proc_videocodecs_show(struct seq_file *m, void *v) -{ - struct codec_list *h = codeclist_top; - struct attached_list *a; - - seq_printf(m, "lave or attached aster name type flags magic "); - seq_printf(m, "(connected as)\n"); - - while (h) { - seq_printf(m, "S %32s %04x %08lx %08lx (TEMPLATE)\n", - h->codec->name, h->codec->type, - h->codec->flags, h->codec->magic); - a = h->list; - while (a) { - seq_printf(m, "M %32s %04x %08lx %08lx (%s)\n", - a->codec->master_data->name, - a->codec->master_data->type, - a->codec->master_data->flags, - a->codec->master_data->magic, - a->codec->name); - a = a->next; - } - h = h->next; - } - - return 0; -} -#endif - -/* ===================== */ -/* hook in driver module */ -/* ===================== */ -static int __init -videocodec_init (void) -{ -#ifdef CONFIG_PROC_FS - static struct proc_dir_entry *videocodec_proc_entry; -#endif - - printk(KERN_INFO "Linux video codec intermediate layer: %s\n", - VIDEOCODEC_VERSION); - -#ifdef CONFIG_PROC_FS - videocodec_proc_entry = proc_create_single("videocodecs", 0, NULL, - proc_videocodecs_show); - if (!videocodec_proc_entry) { - dprintk(1, KERN_ERR "videocodec: can't init procfs.\n"); - } -#endif - return 0; -} - -static void __exit -videocodec_exit (void) -{ -#ifdef CONFIG_PROC_FS - remove_proc_entry("videocodecs", NULL); -#endif -} - -EXPORT_SYMBOL(videocodec_attach); -EXPORT_SYMBOL(videocodec_detach); -EXPORT_SYMBOL(videocodec_register); -EXPORT_SYMBOL(videocodec_unregister); - -module_init(videocodec_init); -module_exit(videocodec_exit); - -MODULE_AUTHOR("Wolfgang Scherr "); -MODULE_DESCRIPTION("Intermediate API module for video codecs " - VIDEOCODEC_VERSION); -MODULE_LICENSE("GPL"); diff --git a/drivers/staging/media/zoran/videocodec.h b/drivers/staging/media/zoran/videocodec.h deleted file mode 100644 index 8ed5a0f7ac01..000000000000 --- a/drivers/staging/media/zoran/videocodec.h +++ /dev/null @@ -1,349 +0,0 @@ -/* - * VIDEO MOTION CODECs internal API for video devices - * - * Interface for MJPEG (and maybe later MPEG/WAVELETS) codec's - * bound to a master device. - * - * (c) 2002 Wolfgang Scherr - * - * $Id: videocodec.h,v 1.1.2.4 2003/01/14 21:15:03 rbultje Exp $ - * - * ------------------------------------------------------------------------ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * ------------------------------------------------------------------------ - */ - -/* =================== */ -/* general description */ -/* =================== */ - -/* Should ease the (re-)usage of drivers supporting cards with (different) - video codecs. The codecs register to this module their functionality, - and the processors (masters) can attach to them if they fit. - - The codecs are typically have a "strong" binding to their master - so I - don't think it makes sense to have a full blown interfacing as with e.g. - i2c. If you have an other opinion, let's discuss & implement it :-))) - - Usage: - - The slave has just to setup the videocodec structure and use two functions: - videocodec_register(codecdata); - videocodec_unregister(codecdata); - The best is just calling them at module (de-)initialisation. - - The master sets up the structure videocodec_master and calls: - codecdata=videocodec_attach(master_codecdata); - videocodec_detach(codecdata); - - The slave is called during attach/detach via functions setup previously - during register. At that time, the master_data pointer is set up - and the slave can access any io registers of the master device (in the case - the slave is bound to it). Otherwise it doesn't need this functions and - therfor they may not be initialized. - - The other functions are just for convenience, as they are for sure used by - most/all of the codecs. The last ones may be omitted, too. - - See the structure declaration below for more information and which data has - to be set up for the master and the slave. - - ---------------------------------------------------------------------------- - The master should have "knowledge" of the slave and vice versa. So the data - structures sent to/from slave via set_data/get_data set_image/get_image are - device dependent and vary between MJPEG/MPEG/WAVELET/... devices. (!!!!) - ---------------------------------------------------------------------------- -*/ - - -/* ========================================== */ -/* description of the videocodec_io structure */ -/* ========================================== */ - -/* - ==== master setup ==== - name -> name of the device structure for reference and debugging - master_data -> data ref. for the master (e.g. the zr36055,57,67) - readreg -> ref. to read-fn from register (setup by master, used by slave) - writereg -> ref. to write-fn to register (setup by master, used by slave) - this two functions do the lowlevel I/O job - - ==== slave functionality setup ==== - slave_data -> data ref. for the slave (e.g. the zr36050,60) - check -> fn-ref. checks availability of an device, returns -EIO on failure or - the type on success - this makes espcecially sense if a driver module supports more than - one codec which may be quite similar to access, nevertheless it - is good for a first functionality check - - -- main functions you always need for compression/decompression -- - - set_mode -> this fn-ref. resets the entire codec, and sets up the mode - with the last defined norm/size (or device default if not - available) - it returns 0 if the mode is possible - set_size -> this fn-ref. sets the norm and image size for - compression/decompression (returns 0 on success) - the norm param is defined in videodev2.h (V4L2_STD_*) - - additional setup may be available, too - but the codec should work with - some default values even without this - - set_data -> sets device-specific data (tables, quality etc.) - get_data -> query device-specific data (tables, quality etc.) - - if the device delivers interrupts, they may be setup/handled here - setup_interrupt -> codec irq setup (not needed for 36050/60) - handle_interrupt -> codec irq handling (not needed for 36050/60) - - if the device delivers pictures, they may be handled here - put_image -> puts image data to the codec (not needed for 36050/60) - get_image -> gets image data from the codec (not needed for 36050/60) - the calls include frame numbers and flags (even/odd/...) - if needed and a flag which allows blocking until its ready -*/ - -/* ============== */ -/* user interface */ -/* ============== */ - -/* - Currently there is only a information display planned, as the layer - is not visible for the user space at all. - - Information is available via procfs. The current entry is "/proc/videocodecs" - but it makes sense to "hide" it in the /proc/video tree of v4l(2) --TODO--. - -A example for such an output is: - -lave or attached aster name type flags magic (connected as) -S zr36050 0002 0000d001 00000000 (TEMPLATE) -M zr36055[0] 0001 0000c001 00000000 (zr36050[0]) -M zr36055[1] 0001 0000c001 00000000 (zr36050[1]) - -*/ - - -/* =============================================== */ -/* special defines for the videocodec_io structure */ -/* =============================================== */ - -#ifndef __LINUX_VIDEOCODEC_H -#define __LINUX_VIDEOCODEC_H - -#include - -#define CODEC_DO_COMPRESSION 0 -#define CODEC_DO_EXPANSION 1 - -/* this are the current codec flags I think they are needed */ -/* -> type value in structure */ -#define CODEC_FLAG_JPEG 0x00000001L // JPEG codec -#define CODEC_FLAG_MPEG 0x00000002L // MPEG1/2/4 codec -#define CODEC_FLAG_DIVX 0x00000004L // DIVX codec -#define CODEC_FLAG_WAVELET 0x00000008L // WAVELET codec - // room for other types - -#define CODEC_FLAG_MAGIC 0x00000800L // magic key must match -#define CODEC_FLAG_HARDWARE 0x00001000L // is a hardware codec -#define CODEC_FLAG_VFE 0x00002000L // has direct video frontend -#define CODEC_FLAG_ENCODER 0x00004000L // compression capability -#define CODEC_FLAG_DECODER 0x00008000L // decompression capability -#define CODEC_FLAG_NEEDIRQ 0x00010000L // needs irq handling -#define CODEC_FLAG_RDWRPIC 0x00020000L // handles picture I/O - -/* a list of modes, some are just examples (is there any HW?) */ -#define CODEC_MODE_BJPG 0x0001 // Baseline JPEG -#define CODEC_MODE_LJPG 0x0002 // Lossless JPEG -#define CODEC_MODE_MPEG1 0x0003 // MPEG 1 -#define CODEC_MODE_MPEG2 0x0004 // MPEG 2 -#define CODEC_MODE_MPEG4 0x0005 // MPEG 4 -#define CODEC_MODE_MSDIVX 0x0006 // MS DivX -#define CODEC_MODE_ODIVX 0x0007 // Open DivX -#define CODEC_MODE_WAVELET 0x0008 // Wavelet - -/* this are the current codec types I want to implement */ -/* -> type value in structure */ -#define CODEC_TYPE_NONE 0 -#define CODEC_TYPE_L64702 1 -#define CODEC_TYPE_ZR36050 2 -#define CODEC_TYPE_ZR36016 3 -#define CODEC_TYPE_ZR36060 4 - -/* the type of data may be enhanced by future implementations (data-fn.'s) */ -/* -> used in command */ -#define CODEC_G_STATUS 0x0000 /* codec status (query only) */ -#define CODEC_S_CODEC_MODE 0x0001 /* codec mode (baseline JPEG, MPEG1,... */ -#define CODEC_G_CODEC_MODE 0x8001 -#define CODEC_S_VFE 0x0002 /* additional video frontend setup */ -#define CODEC_G_VFE 0x8002 -#define CODEC_S_MMAP 0x0003 /* MMAP setup (if available) */ - -#define CODEC_S_JPEG_TDS_BYTE 0x0010 /* target data size in bytes */ -#define CODEC_G_JPEG_TDS_BYTE 0x8010 -#define CODEC_S_JPEG_SCALE 0x0011 /* scaling factor for quant. tables */ -#define CODEC_G_JPEG_SCALE 0x8011 -#define CODEC_S_JPEG_HDT_DATA 0x0018 /* huffman-tables */ -#define CODEC_G_JPEG_HDT_DATA 0x8018 -#define CODEC_S_JPEG_QDT_DATA 0x0019 /* quantizing-tables */ -#define CODEC_G_JPEG_QDT_DATA 0x8019 -#define CODEC_S_JPEG_APP_DATA 0x001A /* APP marker */ -#define CODEC_G_JPEG_APP_DATA 0x801A -#define CODEC_S_JPEG_COM_DATA 0x001B /* COM marker */ -#define CODEC_G_JPEG_COM_DATA 0x801B - -#define CODEC_S_PRIVATE 0x1000 /* "private" commands start here */ -#define CODEC_G_PRIVATE 0x9000 - -#define CODEC_G_FLAG 0x8000 /* this is how 'get' is detected */ - -/* types of transfer, directly user space or a kernel buffer (image-fn.'s) */ -/* -> used in get_image, put_image */ -#define CODEC_TRANSFER_KERNEL 0 /* use "memcopy" */ -#define CODEC_TRANSFER_USER 1 /* use "to/from_user" */ - - -/* ========================= */ -/* the structures itself ... */ -/* ========================= */ - -struct vfe_polarity { - unsigned int vsync_pol:1; - unsigned int hsync_pol:1; - unsigned int field_pol:1; - unsigned int blank_pol:1; - unsigned int subimg_pol:1; - unsigned int poe_pol:1; - unsigned int pvalid_pol:1; - unsigned int vclk_pol:1; -}; - -struct vfe_settings { - __u32 x, y; /* Offsets into image */ - __u32 width, height; /* Area to capture */ - __u16 decimation; /* Decimation divider */ - __u16 flags; /* Flags for capture */ - __u16 quality; /* quality of the video */ -}; - -struct tvnorm { - u16 Wt, Wa, HStart, HSyncStart, Ht, Ha, VStart; -}; - -struct jpeg_com_marker { - int len; /* number of usable bytes in data */ - char data[60]; -}; - -struct jpeg_app_marker { - int appn; /* number app segment */ - int len; /* number of usable bytes in data */ - char data[60]; -}; - -struct videocodec { - struct module *owner; - /* -- filled in by slave device during register -- */ - char name[32]; - unsigned long magic; /* may be used for client<->master attaching */ - unsigned long flags; /* functionality flags */ - unsigned int type; /* codec type */ - - /* -- these is filled in later during master device attach -- */ - - struct videocodec_master *master_data; - - /* -- these are filled in by the slave device during register -- */ - - void *data; /* private slave data */ - - /* attach/detach client functions (indirect call) */ - int (*setup) (struct videocodec * codec); - int (*unset) (struct videocodec * codec); - - /* main functions, every client needs them for sure! */ - // set compression or decompression (or freeze, stop, standby, etc) - int (*set_mode) (struct videocodec * codec, - int mode); - // setup picture size and norm (for the codec's video frontend) - int (*set_video) (struct videocodec * codec, - struct tvnorm * norm, - struct vfe_settings * cap, - struct vfe_polarity * pol); - // other control commands, also mmap setup etc. - int (*control) (struct videocodec * codec, - int type, - int size, - void *data); - - /* additional setup/query/processing (may be NULL pointer) */ - // interrupt setup / handling (for irq's delivered by master) - int (*setup_interrupt) (struct videocodec * codec, - long mode); - int (*handle_interrupt) (struct videocodec * codec, - int source, - long flag); - // picture interface (if any) - long (*put_image) (struct videocodec * codec, - int tr_type, - int block, - long *fr_num, - long *flag, - long size, - void *buf); - long (*get_image) (struct videocodec * codec, - int tr_type, - int block, - long *fr_num, - long *flag, - long size, - void *buf); -}; - -struct videocodec_master { - /* -- filled in by master device for registration -- */ - char name[32]; - unsigned long magic; /* may be used for client<->master attaching */ - unsigned long flags; /* functionality flags */ - unsigned int type; /* master type */ - - void *data; /* private master data */ - - __u32(*readreg) (struct videocodec * codec, - __u16 reg); - void (*writereg) (struct videocodec * codec, - __u16 reg, - __u32 value); -}; - - -/* ================================================= */ -/* function prototypes of the master/slave interface */ -/* ================================================= */ - -/* attach and detach commands for the master */ -// * master structure needs to be kmalloc'ed before calling attach -// and free'd after calling detach -// * returns pointer on success, NULL on failure -extern struct videocodec *videocodec_attach(struct videocodec_master *); -// * 0 on success, <0 (errno) on failure -extern int videocodec_detach(struct videocodec *); - -/* register and unregister commands for the slaves */ -// * 0 on success, <0 (errno) on failure -extern int videocodec_register(const struct videocodec *); -// * 0 on success, <0 (errno) on failure -extern int videocodec_unregister(const struct videocodec *); - -/* the other calls are directly done via the videocodec structure! */ - -#endif /*ifndef __LINUX_VIDEOCODEC_H */ diff --git a/drivers/staging/media/zoran/zoran.h b/drivers/staging/media/zoran/zoran.h deleted file mode 100644 index e84fb604a689..000000000000 --- a/drivers/staging/media/zoran/zoran.h +++ /dev/null @@ -1,402 +0,0 @@ -/* - * zoran - Iomega Buz driver - * - * Copyright (C) 1999 Rainer Johanni - * - * based on - * - * zoran.0.0.3 Copyright (C) 1998 Dave Perks - * - * and - * - * bttv - Bt848 frame grabber driver - * Copyright (C) 1996,97,98 Ralph Metzler (rjkm@thp.uni-koeln.de) - * & Marcus Metzler (mocm@thp.uni-koeln.de) - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - */ - -#ifndef _BUZ_H_ -#define _BUZ_H_ - -#include -#include -#include - -struct zoran_sync { - unsigned long frame; /* number of buffer that has been free'd */ - unsigned long length; /* number of code bytes in buffer (capture only) */ - unsigned long seq; /* frame sequence number */ - u64 ts; /* timestamp */ -}; - - -#define ZORAN_NAME "ZORAN" /* name of the device */ - -#define ZR_DEVNAME(zr) ((zr)->name) - -#define BUZ_MAX_WIDTH (zr->timing->Wa) -#define BUZ_MAX_HEIGHT (zr->timing->Ha) -#define BUZ_MIN_WIDTH 32 /* never display less than 32 pixels */ -#define BUZ_MIN_HEIGHT 24 /* never display less than 24 rows */ - -#define BUZ_NUM_STAT_COM 4 -#define BUZ_MASK_STAT_COM 3 - -#define BUZ_MAX_FRAME 256 /* Must be a power of 2 */ -#define BUZ_MASK_FRAME 255 /* Must be BUZ_MAX_FRAME-1 */ - -#define BUZ_MAX_INPUT 16 - -#if VIDEO_MAX_FRAME <= 32 -# define V4L_MAX_FRAME 32 -#elif VIDEO_MAX_FRAME <= 64 -# define V4L_MAX_FRAME 64 -#else -# error "Too many video frame buffers to handle" -#endif -#define V4L_MASK_FRAME (V4L_MAX_FRAME - 1) - -#define MAX_FRAME (BUZ_MAX_FRAME > VIDEO_MAX_FRAME ? BUZ_MAX_FRAME : VIDEO_MAX_FRAME) - -#include "zr36057.h" - -enum card_type { - UNKNOWN = -1, - - /* Pinnacle/Miro */ - DC10_old, /* DC30 like */ - DC10_new, /* DC10plus like */ - DC10plus, - DC30, - DC30plus, - - /* Linux Media Labs */ - LML33, - LML33R10, - - /* Iomega */ - BUZ, - - /* AverMedia */ - AVS6EYES, - - /* total number of cards */ - NUM_CARDS -}; - -enum zoran_codec_mode { - BUZ_MODE_IDLE, /* nothing going on */ - BUZ_MODE_MOTION_COMPRESS, /* grabbing frames */ - BUZ_MODE_MOTION_DECOMPRESS, /* playing frames */ - BUZ_MODE_STILL_COMPRESS, /* still frame conversion */ - BUZ_MODE_STILL_DECOMPRESS /* still frame conversion */ -}; - -enum zoran_buffer_state { - BUZ_STATE_USER, /* buffer is owned by application */ - BUZ_STATE_PEND, /* buffer is queued in pend[] ready to feed to I/O */ - BUZ_STATE_DMA, /* buffer is queued in dma[] for I/O */ - BUZ_STATE_DONE /* buffer is ready to return to application */ -}; - -enum zoran_map_mode { - ZORAN_MAP_MODE_RAW, - ZORAN_MAP_MODE_JPG_REC, -#define ZORAN_MAP_MODE_JPG ZORAN_MAP_MODE_JPG_REC - ZORAN_MAP_MODE_JPG_PLAY, -}; - -enum gpio_type { - ZR_GPIO_JPEG_SLEEP = 0, - ZR_GPIO_JPEG_RESET, - ZR_GPIO_JPEG_FRAME, - ZR_GPIO_VID_DIR, - ZR_GPIO_VID_EN, - ZR_GPIO_VID_RESET, - ZR_GPIO_CLK_SEL1, - ZR_GPIO_CLK_SEL2, - ZR_GPIO_MAX, -}; - -enum gpcs_type { - GPCS_JPEG_RESET = 0, - GPCS_JPEG_START, - GPCS_MAX, -}; - -struct zoran_format { - char *name; - __u32 fourcc; - int colorspace; - int depth; - __u32 flags; - __u32 vfespfr; -}; -/* flags */ -#define ZORAN_FORMAT_COMPRESSED 1<<0 -#define ZORAN_FORMAT_OVERLAY 1<<1 -#define ZORAN_FORMAT_CAPTURE 1<<2 -#define ZORAN_FORMAT_PLAYBACK 1<<3 - -/* overlay-settings */ -struct zoran_overlay_settings { - int is_set; - int x, y, width, height; /* position */ - int clipcount; /* position and number of clips */ - const struct zoran_format *format; /* overlay format */ -}; - -/* v4l-capture settings */ -struct zoran_v4l_settings { - int width, height, bytesperline; /* capture size */ - const struct zoran_format *format; /* capture format */ -}; - -/* jpg-capture/-playback settings */ -struct zoran_jpg_settings { - int decimation; /* this bit is used to set everything to default */ - int HorDcm, VerDcm, TmpDcm; /* capture decimation settings (TmpDcm=1 means both fields) */ - int field_per_buff, odd_even; /* field-settings (odd_even=1 (+TmpDcm=1) means top-field-first) */ - int img_x, img_y, img_width, img_height; /* crop settings (subframe capture) */ - struct v4l2_jpegcompression jpg_comp; /* JPEG-specific capture settings */ -}; - -struct zoran_fh; - -struct zoran_mapping { - struct zoran_fh *fh; - atomic_t count; -}; - -struct zoran_buffer { - struct zoran_mapping *map; - enum zoran_buffer_state state; /* state: unused/pending/dma/done */ - struct zoran_sync bs; /* DONE: info to return to application */ - union { - struct { - __le32 *frag_tab; /* addresses of frag table */ - u32 frag_tab_bus; /* same value cached to save time in ISR */ - } jpg; - struct { - char *fbuffer; /* virtual address of frame buffer */ - unsigned long fbuffer_phys;/* physical address of frame buffer */ - unsigned long fbuffer_bus;/* bus address of frame buffer */ - } v4l; - }; -}; - -enum zoran_lock_activity { - ZORAN_FREE, /* free for use */ - ZORAN_ACTIVE, /* active but unlocked */ - ZORAN_LOCKED, /* locked */ -}; - -/* buffer collections */ -struct zoran_buffer_col { - enum zoran_lock_activity active; /* feature currently in use? */ - unsigned int num_buffers, buffer_size; - struct zoran_buffer buffer[MAX_FRAME]; /* buffers */ - u8 allocated; /* Flag if buffers are allocated */ - u8 need_contiguous; /* Flag if contiguous buffers are needed */ - /* only applies to jpg buffers, raw buffers are always contiguous */ -}; - -struct zoran; - -/* zoran_fh contains per-open() settings */ -struct zoran_fh { - struct v4l2_fh fh; - struct zoran *zr; - - enum zoran_map_mode map_mode; /* Flag which bufferset will map by next mmap() */ - - struct zoran_overlay_settings overlay_settings; - u32 *overlay_mask; /* overlay mask */ - enum zoran_lock_activity overlay_active;/* feature currently in use? */ - - struct zoran_buffer_col buffers; /* buffers' info */ - - struct zoran_v4l_settings v4l_settings; /* structure with a lot of things to play with */ - struct zoran_jpg_settings jpg_settings; /* structure with a lot of things to play with */ -}; - -struct card_info { - enum card_type type; - char name[32]; - const char *i2c_decoder; /* i2c decoder device */ - const unsigned short *addrs_decoder; - const char *i2c_encoder; /* i2c encoder device */ - const unsigned short *addrs_encoder; - u16 video_vfe, video_codec; /* videocodec types */ - u16 audio_chip; /* audio type */ - - int inputs; /* number of video inputs */ - struct input { - int muxsel; - char name[32]; - } input[BUZ_MAX_INPUT]; - - v4l2_std_id norms; - struct tvnorm *tvn[3]; /* supported TV norms */ - - u32 jpeg_int; /* JPEG interrupt */ - u32 vsync_int; /* VSYNC interrupt */ - s8 gpio[ZR_GPIO_MAX]; - u8 gpcs[GPCS_MAX]; - - struct vfe_polarity vfe_pol; - u8 gpio_pol[ZR_GPIO_MAX]; - - /* is the /GWS line connected? */ - u8 gws_not_connected; - - /* avs6eyes mux setting */ - u8 input_mux; - - void (*init) (struct zoran * zr); -}; - -struct zoran { - struct v4l2_device v4l2_dev; - struct v4l2_ctrl_handler hdl; - struct video_device *video_dev; - - struct i2c_adapter i2c_adapter; /* */ - struct i2c_algo_bit_data i2c_algo; /* */ - u32 i2cbr; - - struct v4l2_subdev *decoder; /* video decoder sub-device */ - struct v4l2_subdev *encoder; /* video encoder sub-device */ - - struct videocodec *codec; /* video codec */ - struct videocodec *vfe; /* video front end */ - - struct mutex lock; /* file ops serialize lock */ - - u8 initialized; /* flag if zoran has been correctly initialized */ - int user; /* number of current users */ - struct card_info card; - struct tvnorm *timing; - - unsigned short id; /* number of this device */ - char name[32]; /* name of this device */ - struct pci_dev *pci_dev; /* PCI device */ - unsigned char revision; /* revision of zr36057 */ - unsigned char __iomem *zr36057_mem;/* pointer to mapped IO memory */ - - spinlock_t spinlock; /* Spinlock */ - - /* Video for Linux parameters */ - int input; /* card's norm and input */ - v4l2_std_id norm; - - /* Current buffer params */ - void *vbuf_base; - int vbuf_height, vbuf_width; - int vbuf_depth; - int vbuf_bytesperline; - - struct zoran_overlay_settings overlay_settings; - u32 *overlay_mask; /* overlay mask */ - enum zoran_lock_activity overlay_active; /* feature currently in use? */ - - wait_queue_head_t v4l_capq; - - int v4l_overlay_active; /* Overlay grab is activated */ - int v4l_memgrab_active; /* Memory grab is activated */ - - int v4l_grab_frame; /* Frame number being currently grabbed */ -#define NO_GRAB_ACTIVE (-1) - unsigned long v4l_grab_seq; /* Number of frames grabbed */ - struct zoran_v4l_settings v4l_settings; /* structure with a lot of things to play with */ - - /* V4L grab queue of frames pending */ - unsigned long v4l_pend_head; - unsigned long v4l_pend_tail; - unsigned long v4l_sync_tail; - int v4l_pend[V4L_MAX_FRAME]; - struct zoran_buffer_col v4l_buffers; /* V4L buffers' info */ - - /* Buz MJPEG parameters */ - enum zoran_codec_mode codec_mode; /* status of codec */ - struct zoran_jpg_settings jpg_settings; /* structure with a lot of things to play with */ - - wait_queue_head_t jpg_capq; /* wait here for grab to finish */ - - /* grab queue counts/indices, mask with BUZ_MASK_STAT_COM before using as index */ - /* (dma_head - dma_tail) is number active in DMA, must be <= BUZ_NUM_STAT_COM */ - /* (value & BUZ_MASK_STAT_COM) corresponds to index in stat_com table */ - unsigned long jpg_que_head; /* Index where to put next buffer which is queued */ - unsigned long jpg_dma_head; /* Index of next buffer which goes into stat_com */ - unsigned long jpg_dma_tail; /* Index of last buffer in stat_com */ - unsigned long jpg_que_tail; /* Index of last buffer in queue */ - unsigned long jpg_seq_num; /* count of frames since grab/play started */ - unsigned long jpg_err_seq; /* last seq_num before error */ - unsigned long jpg_err_shift; - unsigned long jpg_queued_num; /* count of frames queued since grab/play started */ - - /* zr36057's code buffer table */ - __le32 *stat_com; /* stat_com[i] is indexed by dma_head/tail & BUZ_MASK_STAT_COM */ - - /* (value & BUZ_MASK_FRAME) corresponds to index in pend[] queue */ - int jpg_pend[BUZ_MAX_FRAME]; - - /* array indexed by frame number */ - struct zoran_buffer_col jpg_buffers; /* MJPEG buffers' info */ - - /* Additional stuff for testing */ -#ifdef CONFIG_PROC_FS - struct proc_dir_entry *zoran_proc; -#else - void *zoran_proc; -#endif - int testing; - int jpeg_error; - int intr_counter_GIRQ1; - int intr_counter_GIRQ0; - int intr_counter_CodRepIRQ; - int intr_counter_JPEGRepIRQ; - int field_counter; - int IRQ1_in; - int IRQ1_out; - int JPEG_in; - int JPEG_out; - int JPEG_0; - int JPEG_1; - int END_event_missed; - int JPEG_missed; - int JPEG_error; - int num_errors; - int JPEG_max_missed; - int JPEG_min_missed; - - u32 last_isr; - unsigned long frame_num; - - wait_queue_head_t test_q; -}; - -static inline struct zoran *to_zoran(struct v4l2_device *v4l2_dev) -{ - return container_of(v4l2_dev, struct zoran, v4l2_dev); -} - -/* There was something called _ALPHA_BUZ that used the PCI address instead of - * the kernel iomapped address for btread/btwrite. */ -#define btwrite(dat,adr) writel((dat), zr->zr36057_mem+(adr)) -#define btread(adr) readl(zr->zr36057_mem+(adr)) - -#define btand(dat,adr) btwrite((dat) & btread(adr), adr) -#define btor(dat,adr) btwrite((dat) | btread(adr), adr) -#define btaor(dat,mask,adr) btwrite((dat) | ((mask) & btread(adr)), adr) - -#endif diff --git a/drivers/staging/media/zoran/zoran_card.c b/drivers/staging/media/zoran/zoran_card.c deleted file mode 100644 index ea10523194e8..000000000000 --- a/drivers/staging/media/zoran/zoran_card.c +++ /dev/null @@ -1,1524 +0,0 @@ -/* - * Zoran zr36057/zr36067 PCI controller driver, for the - * Pinnacle/Miro DC10/DC10+/DC30/DC30+, Iomega Buz, Linux - * Media Labs LML33/LML33R10. - * - * This part handles card-specific data and detection - * - * Copyright (C) 2000 Serguei Miridonov - * - * Currently maintained by: - * Ronald Bultje - * Laurent Pinchart - * Mailinglist - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - */ - -#include - -#include -#include -#include -#include -#include -#include - -#include -#include -#include -#include -#include -#include -#include -#include - -#include -#include -#include -#include -#include -#include - -#include "videocodec.h" -#include "zoran.h" -#include "zoran_card.h" -#include "zoran_device.h" -#include "zoran_procfs.h" - -extern const struct zoran_format zoran_formats[]; - -static int card[BUZ_MAX] = { [0 ... (BUZ_MAX-1)] = -1 }; -module_param_array(card, int, NULL, 0444); -MODULE_PARM_DESC(card, "Card type"); - -/* - The video mem address of the video card. - The driver has a little database for some videocards - to determine it from there. If your video card is not in there - you have either to give it to the driver as a parameter - or set in in a VIDIOCSFBUF ioctl - */ - -static unsigned long vidmem; /* default = 0 - Video memory base address */ -module_param_hw(vidmem, ulong, iomem, 0444); -MODULE_PARM_DESC(vidmem, "Default video memory base address"); - -/* - Default input and video norm at startup of the driver. -*/ - -static unsigned int default_input; /* default 0 = Composite, 1 = S-Video */ -module_param(default_input, uint, 0444); -MODULE_PARM_DESC(default_input, - "Default input (0=Composite, 1=S-Video, 2=Internal)"); - -static int default_mux = 1; /* 6 Eyes input selection */ -module_param(default_mux, int, 0644); -MODULE_PARM_DESC(default_mux, - "Default 6 Eyes mux setting (Input selection)"); - -static int default_norm; /* default 0 = PAL, 1 = NTSC 2 = SECAM */ -module_param(default_norm, int, 0444); -MODULE_PARM_DESC(default_norm, "Default norm (0=PAL, 1=NTSC, 2=SECAM)"); - -/* /dev/videoN, -1 for autodetect */ -static int video_nr[BUZ_MAX] = { [0 ... (BUZ_MAX-1)] = -1 }; -module_param_array(video_nr, int, NULL, 0444); -MODULE_PARM_DESC(video_nr, "Video device number (-1=Auto)"); - -int v4l_nbufs = 4; -int v4l_bufsize = 864; /* Everybody should be able to work with this setting */ -module_param(v4l_nbufs, int, 0644); -MODULE_PARM_DESC(v4l_nbufs, "Maximum number of V4L buffers to use"); -module_param(v4l_bufsize, int, 0644); -MODULE_PARM_DESC(v4l_bufsize, "Maximum size per V4L buffer (in kB)"); - -int jpg_nbufs = 32; -int jpg_bufsize = 512; /* max size for 100% quality full-PAL frame */ -module_param(jpg_nbufs, int, 0644); -MODULE_PARM_DESC(jpg_nbufs, "Maximum number of JPG buffers to use"); -module_param(jpg_bufsize, int, 0644); -MODULE_PARM_DESC(jpg_bufsize, "Maximum size per JPG buffer (in kB)"); - -int pass_through = 0; /* 1=Pass through TV signal when device is not used */ - /* 0=Show color bar when device is not used (LML33: only if lml33dpath=1) */ -module_param(pass_through, int, 0644); -MODULE_PARM_DESC(pass_through, - "Pass TV signal through to TV-out when idling"); - -int zr36067_debug = 1; -module_param_named(debug, zr36067_debug, int, 0644); -MODULE_PARM_DESC(debug, "Debug level (0-5)"); - -#define ZORAN_VERSION "0.10.1" - -MODULE_DESCRIPTION("Zoran-36057/36067 JPEG codec driver"); -MODULE_AUTHOR("Serguei Miridonov"); -MODULE_LICENSE("GPL"); -MODULE_VERSION(ZORAN_VERSION); - -#define ZR_DEVICE(subven, subdev, data) { \ - .vendor = PCI_VENDOR_ID_ZORAN, .device = PCI_DEVICE_ID_ZORAN_36057, \ - .subvendor = (subven), .subdevice = (subdev), .driver_data = (data) } - -static const struct pci_device_id zr36067_pci_tbl[] = { - ZR_DEVICE(PCI_VENDOR_ID_MIRO, PCI_DEVICE_ID_MIRO_DC10PLUS, DC10plus), - ZR_DEVICE(PCI_VENDOR_ID_MIRO, PCI_DEVICE_ID_MIRO_DC30PLUS, DC30plus), - ZR_DEVICE(PCI_VENDOR_ID_ELECTRONICDESIGNGMBH, PCI_DEVICE_ID_LML_33R10, LML33R10), - ZR_DEVICE(PCI_VENDOR_ID_IOMEGA, PCI_DEVICE_ID_IOMEGA_BUZ, BUZ), - ZR_DEVICE(PCI_ANY_ID, PCI_ANY_ID, NUM_CARDS), - {0} -}; -MODULE_DEVICE_TABLE(pci, zr36067_pci_tbl); - -static unsigned int zoran_num; /* number of cards found */ - -/* videocodec bus functions ZR36060 */ -static u32 -zr36060_read (struct videocodec *codec, - u16 reg) -{ - struct zoran *zr = (struct zoran *) codec->master_data->data; - __u32 data; - - if (post_office_wait(zr) - || post_office_write(zr, 0, 1, reg >> 8) - || post_office_write(zr, 0, 2, reg & 0xff)) { - return -1; - } - - data = post_office_read(zr, 0, 3) & 0xff; - return data; -} - -static void -zr36060_write (struct videocodec *codec, - u16 reg, - u32 val) -{ - struct zoran *zr = (struct zoran *) codec->master_data->data; - - if (post_office_wait(zr) - || post_office_write(zr, 0, 1, reg >> 8) - || post_office_write(zr, 0, 2, reg & 0xff)) { - return; - } - - post_office_write(zr, 0, 3, val & 0xff); -} - -/* videocodec bus functions ZR36050 */ -static u32 -zr36050_read (struct videocodec *codec, - u16 reg) -{ - struct zoran *zr = (struct zoran *) codec->master_data->data; - __u32 data; - - if (post_office_wait(zr) - || post_office_write(zr, 1, 0, reg >> 2)) { // reg. HIGHBYTES - return -1; - } - - data = post_office_read(zr, 0, reg & 0x03) & 0xff; // reg. LOWBYTES + read - return data; -} - -static void -zr36050_write (struct videocodec *codec, - u16 reg, - u32 val) -{ - struct zoran *zr = (struct zoran *) codec->master_data->data; - - if (post_office_wait(zr) - || post_office_write(zr, 1, 0, reg >> 2)) { // reg. HIGHBYTES - return; - } - - post_office_write(zr, 0, reg & 0x03, val & 0xff); // reg. LOWBYTES + wr. data -} - -/* videocodec bus functions ZR36016 */ -static u32 -zr36016_read (struct videocodec *codec, - u16 reg) -{ - struct zoran *zr = (struct zoran *) codec->master_data->data; - __u32 data; - - if (post_office_wait(zr)) { - return -1; - } - - data = post_office_read(zr, 2, reg & 0x03) & 0xff; // read - return data; -} - -/* hack for in zoran_device.c */ -void -zr36016_write (struct videocodec *codec, - u16 reg, - u32 val) -{ - struct zoran *zr = (struct zoran *) codec->master_data->data; - - if (post_office_wait(zr)) { - return; - } - - post_office_write(zr, 2, reg & 0x03, val & 0x0ff); // wr. data -} - -/* - * Board specific information - */ - -static void -dc10_init (struct zoran *zr) -{ - dprintk(3, KERN_DEBUG "%s: %s\n", ZR_DEVNAME(zr), __func__); - - /* Pixel clock selection */ - GPIO(zr, 4, 0); - GPIO(zr, 5, 1); - /* Enable the video bus sync signals */ - GPIO(zr, 7, 0); -} - -static void -dc10plus_init (struct zoran *zr) -{ - dprintk(3, KERN_DEBUG "%s: %s\n", ZR_DEVNAME(zr), __func__); -} - -static void -buz_init (struct zoran *zr) -{ - dprintk(3, KERN_DEBUG "%s: %s\n", ZR_DEVNAME(zr), __func__); - - /* some stuff from Iomega */ - pci_write_config_dword(zr->pci_dev, 0xfc, 0x90680f15); - pci_write_config_dword(zr->pci_dev, 0x0c, 0x00012020); - pci_write_config_dword(zr->pci_dev, 0xe8, 0xc0200000); -} - -static void -lml33_init (struct zoran *zr) -{ - dprintk(3, KERN_DEBUG "%s: %s\n", ZR_DEVNAME(zr), __func__); - - GPIO(zr, 2, 1); // Set Composite input/output -} - -static void -avs6eyes_init (struct zoran *zr) -{ - // AverMedia 6-Eyes original driver by Christer Weinigel - - // Lifted straight from Christer's old driver and - // modified slightly by Martin Samuelsson. - - int mux = default_mux; /* 1 = BT866, 7 = VID1 */ - - GPIO(zr, 4, 1); /* Bt866 SLEEP on */ - udelay(2); - - GPIO(zr, 0, 1); /* ZR36060 /RESET on */ - GPIO(zr, 1, 0); /* ZR36060 /SLEEP on */ - GPIO(zr, 2, mux & 1); /* MUX S0 */ - GPIO(zr, 3, 0); /* /FRAME on */ - GPIO(zr, 4, 0); /* Bt866 SLEEP off */ - GPIO(zr, 5, mux & 2); /* MUX S1 */ - GPIO(zr, 6, 0); /* ? */ - GPIO(zr, 7, mux & 4); /* MUX S2 */ - -} - -static char * -codecid_to_modulename (u16 codecid) -{ - char *name = NULL; - - switch (codecid) { - case CODEC_TYPE_ZR36060: - name = "zr36060"; - break; - case CODEC_TYPE_ZR36050: - name = "zr36050"; - break; - case CODEC_TYPE_ZR36016: - name = "zr36016"; - break; - } - - return name; -} - -// struct tvnorm { -// u16 Wt, Wa, HStart, HSyncStart, Ht, Ha, VStart; -// }; - -static struct tvnorm f50sqpixel = { 944, 768, 83, 880, 625, 576, 16 }; -static struct tvnorm f60sqpixel = { 780, 640, 51, 716, 525, 480, 12 }; -static struct tvnorm f50ccir601 = { 864, 720, 75, 804, 625, 576, 18 }; -static struct tvnorm f60ccir601 = { 858, 720, 57, 788, 525, 480, 16 }; - -static struct tvnorm f50ccir601_lml33 = { 864, 720, 75+34, 804, 625, 576, 18 }; -static struct tvnorm f60ccir601_lml33 = { 858, 720, 57+34, 788, 525, 480, 16 }; - -/* The DC10 (57/16/50) uses VActive as HSync, so HStart must be 0 */ -static struct tvnorm f50sqpixel_dc10 = { 944, 768, 0, 880, 625, 576, 0 }; -static struct tvnorm f60sqpixel_dc10 = { 780, 640, 0, 716, 525, 480, 12 }; - -/* FIXME: I cannot swap U and V in saa7114, so i do one - * pixel left shift in zoran (75 -> 74) - * (Maxim Yevtyushkin ) */ -static struct tvnorm f50ccir601_lm33r10 = { 864, 720, 74+54, 804, 625, 576, 18 }; -static struct tvnorm f60ccir601_lm33r10 = { 858, 720, 56+54, 788, 525, 480, 16 }; - -/* FIXME: The ks0127 seem incapable of swapping U and V, too, which is why I - * copy Maxim's left shift hack for the 6 Eyes. - * - * Christer's driver used the unshifted norms, though... - * /Sam */ -static struct tvnorm f50ccir601_avs6eyes = { 864, 720, 74, 804, 625, 576, 18 }; -static struct tvnorm f60ccir601_avs6eyes = { 858, 720, 56, 788, 525, 480, 16 }; - -static const unsigned short vpx3220_addrs[] = { 0x43, 0x47, I2C_CLIENT_END }; -static const unsigned short saa7110_addrs[] = { 0x4e, 0x4f, I2C_CLIENT_END }; -static const unsigned short saa7111_addrs[] = { 0x25, 0x24, I2C_CLIENT_END }; -static const unsigned short saa7114_addrs[] = { 0x21, 0x20, I2C_CLIENT_END }; -static const unsigned short adv717x_addrs[] = { 0x6a, 0x6b, 0x2a, 0x2b, I2C_CLIENT_END }; -static const unsigned short ks0127_addrs[] = { 0x6c, 0x6d, I2C_CLIENT_END }; -static const unsigned short saa7185_addrs[] = { 0x44, I2C_CLIENT_END }; -static const unsigned short bt819_addrs[] = { 0x45, I2C_CLIENT_END }; -static const unsigned short bt856_addrs[] = { 0x44, I2C_CLIENT_END }; -static const unsigned short bt866_addrs[] = { 0x44, I2C_CLIENT_END }; - -static struct card_info zoran_cards[NUM_CARDS] = { - { - .type = DC10_old, - .name = "DC10(old)", - .i2c_decoder = "vpx3220a", - .addrs_decoder = vpx3220_addrs, - .video_codec = CODEC_TYPE_ZR36050, - .video_vfe = CODEC_TYPE_ZR36016, - - .inputs = 3, - .input = { - { 1, "Composite" }, - { 2, "S-Video" }, - { 0, "Internal/comp" } - }, - .norms = V4L2_STD_NTSC|V4L2_STD_PAL|V4L2_STD_SECAM, - .tvn = { - &f50sqpixel_dc10, - &f60sqpixel_dc10, - &f50sqpixel_dc10 - }, - .jpeg_int = 0, - .vsync_int = ZR36057_ISR_GIRQ1, - .gpio = { 2, 1, -1, 3, 7, 0, 4, 5 }, - .gpio_pol = { 0, 0, 0, 1, 0, 0, 0, 0 }, - .gpcs = { -1, 0 }, - .vfe_pol = { 0, 0, 0, 0, 0, 0, 0, 0 }, - .gws_not_connected = 0, - .input_mux = 0, - .init = &dc10_init, - }, { - .type = DC10_new, - .name = "DC10(new)", - .i2c_decoder = "saa7110", - .addrs_decoder = saa7110_addrs, - .i2c_encoder = "adv7175", - .addrs_encoder = adv717x_addrs, - .video_codec = CODEC_TYPE_ZR36060, - - .inputs = 3, - .input = { - { 0, "Composite" }, - { 7, "S-Video" }, - { 5, "Internal/comp" } - }, - .norms = V4L2_STD_NTSC|V4L2_STD_PAL|V4L2_STD_SECAM, - .tvn = { - &f50sqpixel, - &f60sqpixel, - &f50sqpixel}, - .jpeg_int = ZR36057_ISR_GIRQ0, - .vsync_int = ZR36057_ISR_GIRQ1, - .gpio = { 3, 0, 6, 1, 2, -1, 4, 5 }, - .gpio_pol = { 0, 0, 0, 0, 0, 0, 0, 0 }, - .gpcs = { -1, 1}, - .vfe_pol = { 1, 1, 1, 1, 0, 0, 0, 0 }, - .gws_not_connected = 0, - .input_mux = 0, - .init = &dc10plus_init, - }, { - .type = DC10plus, - .name = "DC10plus", - .i2c_decoder = "saa7110", - .addrs_decoder = saa7110_addrs, - .i2c_encoder = "adv7175", - .addrs_encoder = adv717x_addrs, - .video_codec = CODEC_TYPE_ZR36060, - - .inputs = 3, - .input = { - { 0, "Composite" }, - { 7, "S-Video" }, - { 5, "Internal/comp" } - }, - .norms = V4L2_STD_NTSC|V4L2_STD_PAL|V4L2_STD_SECAM, - .tvn = { - &f50sqpixel, - &f60sqpixel, - &f50sqpixel - }, - .jpeg_int = ZR36057_ISR_GIRQ0, - .vsync_int = ZR36057_ISR_GIRQ1, - .gpio = { 3, 0, 6, 1, 2, -1, 4, 5 }, - .gpio_pol = { 0, 0, 0, 0, 0, 0, 0, 0 }, - .gpcs = { -1, 1 }, - .vfe_pol = { 1, 1, 1, 1, 0, 0, 0, 0 }, - .gws_not_connected = 0, - .input_mux = 0, - .init = &dc10plus_init, - }, { - .type = DC30, - .name = "DC30", - .i2c_decoder = "vpx3220a", - .addrs_decoder = vpx3220_addrs, - .i2c_encoder = "adv7175", - .addrs_encoder = adv717x_addrs, - .video_codec = CODEC_TYPE_ZR36050, - .video_vfe = CODEC_TYPE_ZR36016, - - .inputs = 3, - .input = { - { 1, "Composite" }, - { 2, "S-Video" }, - { 0, "Internal/comp" } - }, - .norms = V4L2_STD_NTSC|V4L2_STD_PAL|V4L2_STD_SECAM, - .tvn = { - &f50sqpixel_dc10, - &f60sqpixel_dc10, - &f50sqpixel_dc10 - }, - .jpeg_int = 0, - .vsync_int = ZR36057_ISR_GIRQ1, - .gpio = { 2, 1, -1, 3, 7, 0, 4, 5 }, - .gpio_pol = { 0, 0, 0, 1, 0, 0, 0, 0 }, - .gpcs = { -1, 0 }, - .vfe_pol = { 0, 0, 0, 0, 0, 0, 0, 0 }, - .gws_not_connected = 0, - .input_mux = 0, - .init = &dc10_init, - }, { - .type = DC30plus, - .name = "DC30plus", - .i2c_decoder = "vpx3220a", - .addrs_decoder = vpx3220_addrs, - .i2c_encoder = "adv7175", - .addrs_encoder = adv717x_addrs, - .video_codec = CODEC_TYPE_ZR36050, - .video_vfe = CODEC_TYPE_ZR36016, - - .inputs = 3, - .input = { - { 1, "Composite" }, - { 2, "S-Video" }, - { 0, "Internal/comp" } - }, - .norms = V4L2_STD_NTSC|V4L2_STD_PAL|V4L2_STD_SECAM, - .tvn = { - &f50sqpixel_dc10, - &f60sqpixel_dc10, - &f50sqpixel_dc10 - }, - .jpeg_int = 0, - .vsync_int = ZR36057_ISR_GIRQ1, - .gpio = { 2, 1, -1, 3, 7, 0, 4, 5 }, - .gpio_pol = { 0, 0, 0, 1, 0, 0, 0, 0 }, - .gpcs = { -1, 0 }, - .vfe_pol = { 0, 0, 0, 0, 0, 0, 0, 0 }, - .gws_not_connected = 0, - .input_mux = 0, - .init = &dc10_init, - }, { - .type = LML33, - .name = "LML33", - .i2c_decoder = "bt819a", - .addrs_decoder = bt819_addrs, - .i2c_encoder = "bt856", - .addrs_encoder = bt856_addrs, - .video_codec = CODEC_TYPE_ZR36060, - - .inputs = 2, - .input = { - { 0, "Composite" }, - { 7, "S-Video" } - }, - .norms = V4L2_STD_NTSC|V4L2_STD_PAL, - .tvn = { - &f50ccir601_lml33, - &f60ccir601_lml33, - NULL - }, - .jpeg_int = ZR36057_ISR_GIRQ1, - .vsync_int = ZR36057_ISR_GIRQ0, - .gpio = { 1, -1, 3, 5, 7, -1, -1, -1 }, - .gpio_pol = { 0, 0, 0, 0, 1, 0, 0, 0 }, - .gpcs = { 3, 1 }, - .vfe_pol = { 1, 1, 0, 0, 0, 1, 0, 0 }, - .gws_not_connected = 1, - .input_mux = 0, - .init = &lml33_init, - }, { - .type = LML33R10, - .name = "LML33R10", - .i2c_decoder = "saa7114", - .addrs_decoder = saa7114_addrs, - .i2c_encoder = "adv7170", - .addrs_encoder = adv717x_addrs, - .video_codec = CODEC_TYPE_ZR36060, - - .inputs = 2, - .input = { - { 0, "Composite" }, - { 7, "S-Video" } - }, - .norms = V4L2_STD_NTSC|V4L2_STD_PAL, - .tvn = { - &f50ccir601_lm33r10, - &f60ccir601_lm33r10, - NULL - }, - .jpeg_int = ZR36057_ISR_GIRQ1, - .vsync_int = ZR36057_ISR_GIRQ0, - .gpio = { 1, -1, 3, 5, 7, -1, -1, -1 }, - .gpio_pol = { 0, 0, 0, 0, 1, 0, 0, 0 }, - .gpcs = { 3, 1 }, - .vfe_pol = { 1, 1, 0, 0, 0, 1, 0, 0 }, - .gws_not_connected = 1, - .input_mux = 0, - .init = &lml33_init, - }, { - .type = BUZ, - .name = "Buz", - .i2c_decoder = "saa7111", - .addrs_decoder = saa7111_addrs, - .i2c_encoder = "saa7185", - .addrs_encoder = saa7185_addrs, - .video_codec = CODEC_TYPE_ZR36060, - - .inputs = 2, - .input = { - { 3, "Composite" }, - { 7, "S-Video" } - }, - .norms = V4L2_STD_NTSC|V4L2_STD_PAL|V4L2_STD_SECAM, - .tvn = { - &f50ccir601, - &f60ccir601, - &f50ccir601 - }, - .jpeg_int = ZR36057_ISR_GIRQ1, - .vsync_int = ZR36057_ISR_GIRQ0, - .gpio = { 1, -1, 3, -1, -1, -1, -1, -1 }, - .gpio_pol = { 0, 0, 0, 0, 0, 0, 0, 0 }, - .gpcs = { 3, 1 }, - .vfe_pol = { 1, 1, 0, 0, 0, 1, 0, 0 }, - .gws_not_connected = 1, - .input_mux = 0, - .init = &buz_init, - }, { - .type = AVS6EYES, - .name = "6-Eyes", - /* AverMedia chose not to brand the 6-Eyes. Thus it - can't be autodetected, and requires card=x. */ - .i2c_decoder = "ks0127", - .addrs_decoder = ks0127_addrs, - .i2c_encoder = "bt866", - .addrs_encoder = bt866_addrs, - .video_codec = CODEC_TYPE_ZR36060, - - .inputs = 10, - .input = { - { 0, "Composite 1" }, - { 1, "Composite 2" }, - { 2, "Composite 3" }, - { 4, "Composite 4" }, - { 5, "Composite 5" }, - { 6, "Composite 6" }, - { 8, "S-Video 1" }, - { 9, "S-Video 2" }, - {10, "S-Video 3" }, - {15, "YCbCr" } - }, - .norms = V4L2_STD_NTSC|V4L2_STD_PAL, - .tvn = { - &f50ccir601_avs6eyes, - &f60ccir601_avs6eyes, - NULL - }, - .jpeg_int = ZR36057_ISR_GIRQ1, - .vsync_int = ZR36057_ISR_GIRQ0, - .gpio = { 1, 0, 3, -1, -1, -1, -1, -1 },// Validity unknown /Sam - .gpio_pol = { 0, 0, 0, 0, 0, 0, 0, 0 }, // Validity unknown /Sam - .gpcs = { 3, 1 }, // Validity unknown /Sam - .vfe_pol = { 1, 0, 0, 0, 0, 1, 0, 0 }, // Validity unknown /Sam - .gws_not_connected = 1, - .input_mux = 1, - .init = &avs6eyes_init, - } - -}; - -/* - * I2C functions - */ -/* software I2C functions */ -static int -zoran_i2c_getsda (void *data) -{ - struct zoran *zr = (struct zoran *) data; - - return (btread(ZR36057_I2CBR) >> 1) & 1; -} - -static int -zoran_i2c_getscl (void *data) -{ - struct zoran *zr = (struct zoran *) data; - - return btread(ZR36057_I2CBR) & 1; -} - -static void -zoran_i2c_setsda (void *data, - int state) -{ - struct zoran *zr = (struct zoran *) data; - - if (state) - zr->i2cbr |= 2; - else - zr->i2cbr &= ~2; - btwrite(zr->i2cbr, ZR36057_I2CBR); -} - -static void -zoran_i2c_setscl (void *data, - int state) -{ - struct zoran *zr = (struct zoran *) data; - - if (state) - zr->i2cbr |= 1; - else - zr->i2cbr &= ~1; - btwrite(zr->i2cbr, ZR36057_I2CBR); -} - -static const struct i2c_algo_bit_data zoran_i2c_bit_data_template = { - .setsda = zoran_i2c_setsda, - .setscl = zoran_i2c_setscl, - .getsda = zoran_i2c_getsda, - .getscl = zoran_i2c_getscl, - .udelay = 10, - .timeout = 100, -}; - -static int -zoran_register_i2c (struct zoran *zr) -{ - zr->i2c_algo = zoran_i2c_bit_data_template; - zr->i2c_algo.data = zr; - strscpy(zr->i2c_adapter.name, ZR_DEVNAME(zr), - sizeof(zr->i2c_adapter.name)); - i2c_set_adapdata(&zr->i2c_adapter, &zr->v4l2_dev); - zr->i2c_adapter.algo_data = &zr->i2c_algo; - zr->i2c_adapter.dev.parent = &zr->pci_dev->dev; - return i2c_bit_add_bus(&zr->i2c_adapter); -} - -static void -zoran_unregister_i2c (struct zoran *zr) -{ - i2c_del_adapter(&zr->i2c_adapter); -} - -/* Check a zoran_params struct for correctness, insert default params */ - -int -zoran_check_jpg_settings (struct zoran *zr, - struct zoran_jpg_settings *settings, - int try) -{ - int err = 0, err0 = 0; - - dprintk(4, - KERN_DEBUG - "%s: %s - dec: %d, Hdcm: %d, Vdcm: %d, Tdcm: %d\n", - ZR_DEVNAME(zr), __func__, settings->decimation, settings->HorDcm, - settings->VerDcm, settings->TmpDcm); - dprintk(4, - KERN_DEBUG - "%s: %s - x: %d, y: %d, w: %d, y: %d\n", - ZR_DEVNAME(zr), __func__, settings->img_x, settings->img_y, - settings->img_width, settings->img_height); - /* Check decimation, set default values for decimation = 1, 2, 4 */ - switch (settings->decimation) { - case 1: - - settings->HorDcm = 1; - settings->VerDcm = 1; - settings->TmpDcm = 1; - settings->field_per_buff = 2; - settings->img_x = 0; - settings->img_y = 0; - settings->img_width = BUZ_MAX_WIDTH; - settings->img_height = BUZ_MAX_HEIGHT / 2; - break; - case 2: - - settings->HorDcm = 2; - settings->VerDcm = 1; - settings->TmpDcm = 2; - settings->field_per_buff = 1; - settings->img_x = (BUZ_MAX_WIDTH == 720) ? 8 : 0; - settings->img_y = 0; - settings->img_width = - (BUZ_MAX_WIDTH == 720) ? 704 : BUZ_MAX_WIDTH; - settings->img_height = BUZ_MAX_HEIGHT / 2; - break; - case 4: - - if (zr->card.type == DC10_new) { - dprintk(1, - KERN_DEBUG - "%s: %s - HDec by 4 is not supported on the DC10\n", - ZR_DEVNAME(zr), __func__); - err0++; - break; - } - - settings->HorDcm = 4; - settings->VerDcm = 2; - settings->TmpDcm = 2; - settings->field_per_buff = 1; - settings->img_x = (BUZ_MAX_WIDTH == 720) ? 8 : 0; - settings->img_y = 0; - settings->img_width = - (BUZ_MAX_WIDTH == 720) ? 704 : BUZ_MAX_WIDTH; - settings->img_height = BUZ_MAX_HEIGHT / 2; - break; - case 0: - - /* We have to check the data the user has set */ - - if (settings->HorDcm != 1 && settings->HorDcm != 2 && - (zr->card.type == DC10_new || settings->HorDcm != 4)) { - settings->HorDcm = clamp(settings->HorDcm, 1, 2); - err0++; - } - if (settings->VerDcm != 1 && settings->VerDcm != 2) { - settings->VerDcm = clamp(settings->VerDcm, 1, 2); - err0++; - } - if (settings->TmpDcm != 1 && settings->TmpDcm != 2) { - settings->TmpDcm = clamp(settings->TmpDcm, 1, 2); - err0++; - } - if (settings->field_per_buff != 1 && - settings->field_per_buff != 2) { - settings->field_per_buff = clamp(settings->field_per_buff, 1, 2); - err0++; - } - if (settings->img_x < 0) { - settings->img_x = 0; - err0++; - } - if (settings->img_y < 0) { - settings->img_y = 0; - err0++; - } - if (settings->img_width < 0 || settings->img_width > BUZ_MAX_WIDTH) { - settings->img_width = clamp(settings->img_width, 0, (int)BUZ_MAX_WIDTH); - err0++; - } - if (settings->img_height < 0 || settings->img_height > BUZ_MAX_HEIGHT / 2) { - settings->img_height = clamp(settings->img_height, 0, BUZ_MAX_HEIGHT / 2); - err0++; - } - if (settings->img_x + settings->img_width > BUZ_MAX_WIDTH) { - settings->img_x = BUZ_MAX_WIDTH - settings->img_width; - err0++; - } - if (settings->img_y + settings->img_height > BUZ_MAX_HEIGHT / 2) { - settings->img_y = BUZ_MAX_HEIGHT / 2 - settings->img_height; - err0++; - } - if (settings->img_width % (16 * settings->HorDcm) != 0) { - settings->img_width -= settings->img_width % (16 * settings->HorDcm); - if (settings->img_width == 0) - settings->img_width = 16 * settings->HorDcm; - err0++; - } - if (settings->img_height % (8 * settings->VerDcm) != 0) { - settings->img_height -= settings->img_height % (8 * settings->VerDcm); - if (settings->img_height == 0) - settings->img_height = 8 * settings->VerDcm; - err0++; - } - - if (!try && err0) { - dprintk(1, - KERN_ERR - "%s: %s - error in params for decimation = 0\n", - ZR_DEVNAME(zr), __func__); - err++; - } - break; - default: - dprintk(1, - KERN_ERR - "%s: %s - decimation = %d, must be 0, 1, 2 or 4\n", - ZR_DEVNAME(zr), __func__, settings->decimation); - err++; - break; - } - - if (settings->jpg_comp.quality > 100) - settings->jpg_comp.quality = 100; - if (settings->jpg_comp.quality < 5) - settings->jpg_comp.quality = 5; - if (settings->jpg_comp.APPn < 0) - settings->jpg_comp.APPn = 0; - if (settings->jpg_comp.APPn > 15) - settings->jpg_comp.APPn = 15; - if (settings->jpg_comp.APP_len < 0) - settings->jpg_comp.APP_len = 0; - if (settings->jpg_comp.APP_len > 60) - settings->jpg_comp.APP_len = 60; - if (settings->jpg_comp.COM_len < 0) - settings->jpg_comp.COM_len = 0; - if (settings->jpg_comp.COM_len > 60) - settings->jpg_comp.COM_len = 60; - if (err) - return -EINVAL; - return 0; -} - -void -zoran_open_init_params (struct zoran *zr) -{ - int i; - - /* User must explicitly set a window */ - zr->overlay_settings.is_set = 0; - zr->overlay_mask = NULL; - zr->overlay_active = ZORAN_FREE; - - zr->v4l_memgrab_active = 0; - zr->v4l_overlay_active = 0; - zr->v4l_grab_frame = NO_GRAB_ACTIVE; - zr->v4l_grab_seq = 0; - zr->v4l_settings.width = 192; - zr->v4l_settings.height = 144; - zr->v4l_settings.format = &zoran_formats[7]; /* YUY2 - YUV-4:2:2 packed */ - zr->v4l_settings.bytesperline = - zr->v4l_settings.width * - ((zr->v4l_settings.format->depth + 7) / 8); - - /* DMA ring stuff for V4L */ - zr->v4l_pend_tail = 0; - zr->v4l_pend_head = 0; - zr->v4l_sync_tail = 0; - zr->v4l_buffers.active = ZORAN_FREE; - for (i = 0; i < VIDEO_MAX_FRAME; i++) { - zr->v4l_buffers.buffer[i].state = BUZ_STATE_USER; /* nothing going on */ - } - zr->v4l_buffers.allocated = 0; - - for (i = 0; i < BUZ_MAX_FRAME; i++) { - zr->jpg_buffers.buffer[i].state = BUZ_STATE_USER; /* nothing going on */ - } - zr->jpg_buffers.active = ZORAN_FREE; - zr->jpg_buffers.allocated = 0; - /* Set necessary params and call zoran_check_jpg_settings to set the defaults */ - zr->jpg_settings.decimation = 1; - zr->jpg_settings.jpg_comp.quality = 50; /* default compression factor 8 */ - if (zr->card.type != BUZ) - zr->jpg_settings.odd_even = 1; - else - zr->jpg_settings.odd_even = 0; - zr->jpg_settings.jpg_comp.APPn = 0; - zr->jpg_settings.jpg_comp.APP_len = 0; /* No APPn marker */ - memset(zr->jpg_settings.jpg_comp.APP_data, 0, - sizeof(zr->jpg_settings.jpg_comp.APP_data)); - zr->jpg_settings.jpg_comp.COM_len = 0; /* No COM marker */ - memset(zr->jpg_settings.jpg_comp.COM_data, 0, - sizeof(zr->jpg_settings.jpg_comp.COM_data)); - zr->jpg_settings.jpg_comp.jpeg_markers = - V4L2_JPEG_MARKER_DHT | V4L2_JPEG_MARKER_DQT; - i = zoran_check_jpg_settings(zr, &zr->jpg_settings, 0); - if (i) - dprintk(1, KERN_ERR "%s: %s internal error\n", - ZR_DEVNAME(zr), __func__); - - clear_interrupt_counters(zr); - zr->testing = 0; -} - -static void test_interrupts (struct zoran *zr) -{ - DEFINE_WAIT(wait); - int timeout, icr; - - clear_interrupt_counters(zr); - - zr->testing = 1; - icr = btread(ZR36057_ICR); - btwrite(0x78000000 | ZR36057_ICR_IntPinEn, ZR36057_ICR); - prepare_to_wait(&zr->test_q, &wait, TASK_INTERRUPTIBLE); - timeout = schedule_timeout(HZ); - finish_wait(&zr->test_q, &wait); - btwrite(0, ZR36057_ICR); - btwrite(0x78000000, ZR36057_ISR); - zr->testing = 0; - dprintk(5, KERN_INFO "%s: Testing interrupts...\n", ZR_DEVNAME(zr)); - if (timeout) { - dprintk(1, ": time spent: %d\n", 1 * HZ - timeout); - } - if (zr36067_debug > 1) - print_interrupts(zr); - btwrite(icr, ZR36057_ICR); -} - -static int zr36057_init (struct zoran *zr) -{ - int j, err; - - dprintk(1, - KERN_INFO - "%s: %s - initializing card[%d], zr=%p\n", - ZR_DEVNAME(zr), __func__, zr->id, zr); - - /* default setup of all parameters which will persist between opens */ - zr->user = 0; - - init_waitqueue_head(&zr->v4l_capq); - init_waitqueue_head(&zr->jpg_capq); - init_waitqueue_head(&zr->test_q); - zr->jpg_buffers.allocated = 0; - zr->v4l_buffers.allocated = 0; - - zr->vbuf_base = (void *) vidmem; - zr->vbuf_width = 0; - zr->vbuf_height = 0; - zr->vbuf_depth = 0; - zr->vbuf_bytesperline = 0; - - /* Avoid nonsense settings from user for default input/norm */ - if (default_norm < 0 || default_norm > 2) - default_norm = 0; - if (default_norm == 0) { - zr->norm = V4L2_STD_PAL; - zr->timing = zr->card.tvn[0]; - } else if (default_norm == 1) { - zr->norm = V4L2_STD_NTSC; - zr->timing = zr->card.tvn[1]; - } else { - zr->norm = V4L2_STD_SECAM; - zr->timing = zr->card.tvn[2]; - } - if (zr->timing == NULL) { - dprintk(1, - KERN_WARNING - "%s: %s - default TV standard not supported by hardware. PAL will be used.\n", - ZR_DEVNAME(zr), __func__); - zr->norm = V4L2_STD_PAL; - zr->timing = zr->card.tvn[0]; - } - - if (default_input > zr->card.inputs-1) { - dprintk(1, - KERN_WARNING - "%s: default_input value %d out of range (0-%d)\n", - ZR_DEVNAME(zr), default_input, zr->card.inputs-1); - default_input = 0; - } - zr->input = default_input; - - /* default setup (will be repeated at every open) */ - zoran_open_init_params(zr); - - /* allocate memory *before* doing anything to the hardware - * in case allocation fails */ - zr->stat_com = kzalloc(BUZ_NUM_STAT_COM * 4, GFP_KERNEL); - zr->video_dev = video_device_alloc(); - if (!zr->stat_com || !zr->video_dev) { - dprintk(1, - KERN_ERR - "%s: %s - kmalloc (STAT_COM) failed\n", - ZR_DEVNAME(zr), __func__); - err = -ENOMEM; - goto exit_free; - } - for (j = 0; j < BUZ_NUM_STAT_COM; j++) { - zr->stat_com[j] = cpu_to_le32(1); /* mark as unavailable to zr36057 */ - } - - /* - * Now add the template and register the device unit. - */ - *zr->video_dev = zoran_template; - zr->video_dev->v4l2_dev = &zr->v4l2_dev; - zr->video_dev->lock = &zr->lock; - strscpy(zr->video_dev->name, ZR_DEVNAME(zr), sizeof(zr->video_dev->name)); - /* It's not a mem2mem device, but you can both capture and output from - one and the same device. This should really be split up into two - device nodes, but that's a job for another day. */ - zr->video_dev->vfl_dir = VFL_DIR_M2M; - err = video_register_device(zr->video_dev, VFL_TYPE_GRABBER, video_nr[zr->id]); - if (err < 0) - goto exit_free; - video_set_drvdata(zr->video_dev, zr); - - zoran_init_hardware(zr); - if (zr36067_debug > 2) - detect_guest_activity(zr); - test_interrupts(zr); - if (!pass_through) { - decoder_call(zr, video, s_stream, 0); - encoder_call(zr, video, s_routing, 2, 0, 0); - } - - zr->zoran_proc = NULL; - zr->initialized = 1; - return 0; - -exit_free: - kfree(zr->stat_com); - kfree(zr->video_dev); - return err; -} - -static void zoran_remove(struct pci_dev *pdev) -{ - struct v4l2_device *v4l2_dev = dev_get_drvdata(&pdev->dev); - struct zoran *zr = to_zoran(v4l2_dev); - - if (!zr->initialized) - goto exit_free; - - /* unregister videocodec bus */ - if (zr->codec) { - struct videocodec_master *master = zr->codec->master_data; - - videocodec_detach(zr->codec); - kfree(master); - } - if (zr->vfe) { - struct videocodec_master *master = zr->vfe->master_data; - - videocodec_detach(zr->vfe); - kfree(master); - } - - /* unregister i2c bus */ - zoran_unregister_i2c(zr); - /* disable PCI bus-mastering */ - zoran_set_pci_master(zr, 0); - /* put chip into reset */ - btwrite(0, ZR36057_SPGPPCR); - free_irq(zr->pci_dev->irq, zr); - /* unmap and free memory */ - kfree(zr->stat_com); - zoran_proc_cleanup(zr); - iounmap(zr->zr36057_mem); - pci_disable_device(zr->pci_dev); - video_unregister_device(zr->video_dev); -exit_free: - v4l2_ctrl_handler_free(&zr->hdl); - v4l2_device_unregister(&zr->v4l2_dev); - kfree(zr); -} - -void -zoran_vdev_release (struct video_device *vdev) -{ - kfree(vdev); -} - -static struct videocodec_master *zoran_setup_videocodec(struct zoran *zr, - int type) -{ - struct videocodec_master *m = NULL; - - m = kmalloc(sizeof(struct videocodec_master), GFP_KERNEL); - if (!m) { - dprintk(1, KERN_ERR "%s: %s - no memory\n", - ZR_DEVNAME(zr), __func__); - return m; - } - - /* magic and type are unused for master struct. Makes sense only at - codec structs. - In the past, .type were initialized to the old V4L1 .hardware - value, as VID_HARDWARE_ZR36067 - */ - m->magic = 0L; - m->type = 0; - - m->flags = CODEC_FLAG_ENCODER | CODEC_FLAG_DECODER; - strscpy(m->name, ZR_DEVNAME(zr), sizeof(m->name)); - m->data = zr; - - switch (type) - { - case CODEC_TYPE_ZR36060: - m->readreg = zr36060_read; - m->writereg = zr36060_write; - m->flags |= CODEC_FLAG_JPEG | CODEC_FLAG_VFE; - break; - case CODEC_TYPE_ZR36050: - m->readreg = zr36050_read; - m->writereg = zr36050_write; - m->flags |= CODEC_FLAG_JPEG; - break; - case CODEC_TYPE_ZR36016: - m->readreg = zr36016_read; - m->writereg = zr36016_write; - m->flags |= CODEC_FLAG_VFE; - break; - } - - return m; -} - -static void zoran_subdev_notify(struct v4l2_subdev *sd, unsigned int cmd, void *arg) -{ - struct zoran *zr = to_zoran(sd->v4l2_dev); - - /* Bt819 needs to reset its FIFO buffer using #FRST pin and - LML33 card uses GPIO(7) for that. */ - if (cmd == BT819_FIFO_RESET_LOW) - GPIO(zr, 7, 0); - else if (cmd == BT819_FIFO_RESET_HIGH) - GPIO(zr, 7, 1); -} - -/* - * Scan for a Buz card (actually for the PCI controller ZR36057), - * request the irq and map the io memory - */ -static int zoran_probe(struct pci_dev *pdev, const struct pci_device_id *ent) -{ - unsigned char latency, need_latency; - struct zoran *zr; - int result; - struct videocodec_master *master_vfe = NULL; - struct videocodec_master *master_codec = NULL; - int card_num; - char *codec_name, *vfe_name; - unsigned int nr; - - - nr = zoran_num++; - if (nr >= BUZ_MAX) { - dprintk(1, KERN_ERR "%s: driver limited to %d card(s) maximum\n", - ZORAN_NAME, BUZ_MAX); - return -ENOENT; - } - - zr = kzalloc(sizeof(struct zoran), GFP_KERNEL); - if (!zr) { - dprintk(1, KERN_ERR "%s: %s - kzalloc failed\n", - ZORAN_NAME, __func__); - return -ENOMEM; - } - zr->v4l2_dev.notify = zoran_subdev_notify; - if (v4l2_device_register(&pdev->dev, &zr->v4l2_dev)) - goto zr_free_mem; - zr->pci_dev = pdev; - zr->id = nr; - snprintf(ZR_DEVNAME(zr), sizeof(ZR_DEVNAME(zr)), "MJPEG[%u]", zr->id); - if (v4l2_ctrl_handler_init(&zr->hdl, 10)) - goto zr_unreg; - zr->v4l2_dev.ctrl_handler = &zr->hdl; - spin_lock_init(&zr->spinlock); - mutex_init(&zr->lock); - if (pci_enable_device(pdev)) - goto zr_unreg; - zr->revision = zr->pci_dev->revision; - - dprintk(1, - KERN_INFO - "%s: Zoran ZR360%c7 (rev %d), irq: %d, memory: 0x%08llx\n", - ZR_DEVNAME(zr), zr->revision < 2 ? '5' : '6', zr->revision, - zr->pci_dev->irq, (uint64_t)pci_resource_start(zr->pci_dev, 0)); - if (zr->revision >= 2) { - dprintk(1, - KERN_INFO - "%s: Subsystem vendor=0x%04x id=0x%04x\n", - ZR_DEVNAME(zr), zr->pci_dev->subsystem_vendor, - zr->pci_dev->subsystem_device); - } - - /* Use auto-detected card type? */ - if (card[nr] == -1) { - if (zr->revision < 2) { - dprintk(1, - KERN_ERR - "%s: No card type specified, please use the card=X module parameter\n", - ZR_DEVNAME(zr)); - dprintk(1, - KERN_ERR - "%s: It is not possible to auto-detect ZR36057 based cards\n", - ZR_DEVNAME(zr)); - goto zr_unreg; - } - - card_num = ent->driver_data; - if (card_num >= NUM_CARDS) { - dprintk(1, - KERN_ERR - "%s: Unknown card, try specifying card=X module parameter\n", - ZR_DEVNAME(zr)); - goto zr_unreg; - } - dprintk(3, - KERN_DEBUG - "%s: %s() - card %s detected\n", - ZR_DEVNAME(zr), __func__, zoran_cards[card_num].name); - } else { - card_num = card[nr]; - if (card_num >= NUM_CARDS || card_num < 0) { - dprintk(1, - KERN_ERR - "%s: User specified card type %d out of range (0 .. %d)\n", - ZR_DEVNAME(zr), card_num, NUM_CARDS - 1); - goto zr_unreg; - } - } - - /* even though we make this a non pointer and thus - * theoretically allow for making changes to this struct - * on a per-individual card basis at runtime, this is - * strongly discouraged. This structure is intended to - * keep general card information, no settings or anything */ - zr->card = zoran_cards[card_num]; - snprintf(ZR_DEVNAME(zr), sizeof(ZR_DEVNAME(zr)), - "%s[%u]", zr->card.name, zr->id); - - zr->zr36057_mem = pci_ioremap_bar(zr->pci_dev, 0); - if (!zr->zr36057_mem) { - dprintk(1, KERN_ERR "%s: %s() - ioremap failed\n", - ZR_DEVNAME(zr), __func__); - goto zr_unreg; - } - - result = request_irq(zr->pci_dev->irq, zoran_irq, - IRQF_SHARED, ZR_DEVNAME(zr), zr); - if (result < 0) { - if (result == -EINVAL) { - dprintk(1, - KERN_ERR - "%s: %s - bad irq number or handler\n", - ZR_DEVNAME(zr), __func__); - } else if (result == -EBUSY) { - dprintk(1, - KERN_ERR - "%s: %s - IRQ %d busy, change your PnP config in BIOS\n", - ZR_DEVNAME(zr), __func__, zr->pci_dev->irq); - } else { - dprintk(1, - KERN_ERR - "%s: %s - can't assign irq, error code %d\n", - ZR_DEVNAME(zr), __func__, result); - } - goto zr_unmap; - } - - /* set PCI latency timer */ - pci_read_config_byte(zr->pci_dev, PCI_LATENCY_TIMER, - &latency); - need_latency = zr->revision > 1 ? 32 : 48; - if (latency != need_latency) { - dprintk(2, KERN_INFO "%s: Changing PCI latency from %d to %d\n", - ZR_DEVNAME(zr), latency, need_latency); - pci_write_config_byte(zr->pci_dev, PCI_LATENCY_TIMER, - need_latency); - } - - zr36057_restart(zr); - /* i2c */ - dprintk(2, KERN_INFO "%s: Initializing i2c bus...\n", - ZR_DEVNAME(zr)); - - if (zoran_register_i2c(zr) < 0) { - dprintk(1, KERN_ERR "%s: %s - can't initialize i2c bus\n", - ZR_DEVNAME(zr), __func__); - goto zr_free_irq; - } - - zr->decoder = v4l2_i2c_new_subdev(&zr->v4l2_dev, - &zr->i2c_adapter, zr->card.i2c_decoder, - 0, zr->card.addrs_decoder); - - if (zr->card.i2c_encoder) - zr->encoder = v4l2_i2c_new_subdev(&zr->v4l2_dev, - &zr->i2c_adapter, zr->card.i2c_encoder, - 0, zr->card.addrs_encoder); - - dprintk(2, - KERN_INFO "%s: Initializing videocodec bus...\n", - ZR_DEVNAME(zr)); - - if (zr->card.video_codec) { - codec_name = codecid_to_modulename(zr->card.video_codec); - if (codec_name) { - result = request_module(codec_name); - if (result) { - dprintk(1, - KERN_ERR - "%s: failed to load modules %s: %d\n", - ZR_DEVNAME(zr), codec_name, result); - } - } - } - if (zr->card.video_vfe) { - vfe_name = codecid_to_modulename(zr->card.video_vfe); - if (vfe_name) { - result = request_module(vfe_name); - if (result < 0) { - dprintk(1, - KERN_ERR - "%s: failed to load modules %s: %d\n", - ZR_DEVNAME(zr), vfe_name, result); - } - } - } - - /* reset JPEG codec */ - jpeg_codec_sleep(zr, 1); - jpeg_codec_reset(zr); - /* video bus enabled */ - /* display codec revision */ - if (zr->card.video_codec != 0) { - master_codec = zoran_setup_videocodec(zr, zr->card.video_codec); - if (!master_codec) - goto zr_unreg_i2c; - zr->codec = videocodec_attach(master_codec); - if (!zr->codec) { - dprintk(1, KERN_ERR "%s: %s - no codec found\n", - ZR_DEVNAME(zr), __func__); - goto zr_free_codec; - } - if (zr->codec->type != zr->card.video_codec) { - dprintk(1, KERN_ERR "%s: %s - wrong codec\n", - ZR_DEVNAME(zr), __func__); - goto zr_detach_codec; - } - } - if (zr->card.video_vfe != 0) { - master_vfe = zoran_setup_videocodec(zr, zr->card.video_vfe); - if (!master_vfe) - goto zr_detach_codec; - zr->vfe = videocodec_attach(master_vfe); - if (!zr->vfe) { - dprintk(1, KERN_ERR "%s: %s - no VFE found\n", - ZR_DEVNAME(zr), __func__); - goto zr_free_vfe; - } - if (zr->vfe->type != zr->card.video_vfe) { - dprintk(1, KERN_ERR "%s: %s = wrong VFE\n", - ZR_DEVNAME(zr), __func__); - goto zr_detach_vfe; - } - } - - /* take care of Natoma chipset and a revision 1 zr36057 */ - if ((pci_pci_problems & PCIPCI_NATOMA) && zr->revision <= 1) { - zr->jpg_buffers.need_contiguous = 1; - dprintk(1, KERN_INFO - "%s: ZR36057/Natoma bug, max. buffer size is 128K\n", - ZR_DEVNAME(zr)); - } - - if (zr36057_init(zr) < 0) - goto zr_detach_vfe; - - zoran_proc_init(zr); - - return 0; - -zr_detach_vfe: - videocodec_detach(zr->vfe); -zr_free_vfe: - kfree(master_vfe); -zr_detach_codec: - videocodec_detach(zr->codec); -zr_free_codec: - kfree(master_codec); -zr_unreg_i2c: - zoran_unregister_i2c(zr); -zr_free_irq: - btwrite(0, ZR36057_SPGPPCR); - free_irq(zr->pci_dev->irq, zr); -zr_unmap: - iounmap(zr->zr36057_mem); -zr_unreg: - v4l2_ctrl_handler_free(&zr->hdl); - v4l2_device_unregister(&zr->v4l2_dev); -zr_free_mem: - kfree(zr); - - return -ENODEV; -} - -static struct pci_driver zoran_driver = { - .name = "zr36067", - .id_table = zr36067_pci_tbl, - .probe = zoran_probe, - .remove = zoran_remove, -}; - -static int __init zoran_init(void) -{ - int res; - - printk(KERN_INFO "Zoran MJPEG board driver version %s\n", - ZORAN_VERSION); - - /* check the parameters we have been given, adjust if necessary */ - if (v4l_nbufs < 2) - v4l_nbufs = 2; - if (v4l_nbufs > VIDEO_MAX_FRAME) - v4l_nbufs = VIDEO_MAX_FRAME; - /* The user specifies the in KB, we want them in byte - * (and page aligned) */ - v4l_bufsize = PAGE_ALIGN(v4l_bufsize * 1024); - if (v4l_bufsize < 32768) - v4l_bufsize = 32768; - /* 2 MB is arbitrary but sufficient for the maximum possible images */ - if (v4l_bufsize > 2048 * 1024) - v4l_bufsize = 2048 * 1024; - if (jpg_nbufs < 4) - jpg_nbufs = 4; - if (jpg_nbufs > BUZ_MAX_FRAME) - jpg_nbufs = BUZ_MAX_FRAME; - jpg_bufsize = PAGE_ALIGN(jpg_bufsize * 1024); - if (jpg_bufsize < 8192) - jpg_bufsize = 8192; - if (jpg_bufsize > (512 * 1024)) - jpg_bufsize = 512 * 1024; - /* Use parameter for vidmem or try to find a video card */ - if (vidmem) { - dprintk(1, - KERN_INFO - "%s: Using supplied video memory base address @ 0x%lx\n", - ZORAN_NAME, vidmem); - } - - /* some mainboards might not do PCI-PCI data transfer well */ - if (pci_pci_problems & (PCIPCI_FAIL|PCIAGP_FAIL|PCIPCI_ALIMAGIK)) { - dprintk(1, - KERN_WARNING - "%s: chipset does not support reliable PCI-PCI DMA\n", - ZORAN_NAME); - } - - res = pci_register_driver(&zoran_driver); - if (res) { - dprintk(1, - KERN_ERR - "%s: Unable to register ZR36057 driver\n", - ZORAN_NAME); - return res; - } - - return 0; -} - -static void __exit zoran_exit(void) -{ - pci_unregister_driver(&zoran_driver); -} - -module_init(zoran_init); -module_exit(zoran_exit); diff --git a/drivers/staging/media/zoran/zoran_card.h b/drivers/staging/media/zoran/zoran_card.h deleted file mode 100644 index 0cdb7d34926d..000000000000 --- a/drivers/staging/media/zoran/zoran_card.h +++ /dev/null @@ -1,50 +0,0 @@ -/* - * Zoran zr36057/zr36067 PCI controller driver, for the - * Pinnacle/Miro DC10/DC10+/DC30/DC30+, Iomega Buz, Linux - * Media Labs LML33/LML33R10. - * - * This part handles card-specific data and detection - * - * Copyright (C) 2000 Serguei Miridonov - * - * Currently maintained by: - * Ronald Bultje - * Laurent Pinchart - * Mailinglist - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - */ - -#ifndef __ZORAN_CARD_H__ -#define __ZORAN_CARD_H__ - -extern int zr36067_debug; - -#define dprintk(num, format, args...) \ - do { \ - if (zr36067_debug >= num) \ - printk(format, ##args); \ - } while (0) - -/* Anybody who uses more than four? */ -#define BUZ_MAX 4 - -extern const struct video_device zoran_template; - -extern int zoran_check_jpg_settings(struct zoran *zr, - struct zoran_jpg_settings *settings, - int try); -extern void zoran_open_init_params(struct zoran *zr); -extern void zoran_vdev_release(struct video_device *vdev); - -void zr36016_write(struct videocodec *codec, u16 reg, u32 val); - -#endif /* __ZORAN_CARD_H__ */ diff --git a/drivers/staging/media/zoran/zoran_device.c b/drivers/staging/media/zoran/zoran_device.c deleted file mode 100644 index 22b27632762d..000000000000 --- a/drivers/staging/media/zoran/zoran_device.c +++ /dev/null @@ -1,1619 +0,0 @@ -/* - * Zoran zr36057/zr36067 PCI controller driver, for the - * Pinnacle/Miro DC10/DC10+/DC30/DC30+, Iomega Buz, Linux - * Media Labs LML33/LML33R10. - * - * This part handles device access (PCI/I2C/codec/...) - * - * Copyright (C) 2000 Serguei Miridonov - * - * Currently maintained by: - * Ronald Bultje - * Laurent Pinchart - * Mailinglist - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - */ - -#include -#include -#include -#include -#include -#include - -#include -#include -#include -#include -#include -#include -#include -#include - -#include -#include -#include - -#include -#include - -#include "videocodec.h" -#include "zoran.h" -#include "zoran_device.h" -#include "zoran_card.h" - -#define IRQ_MASK ( ZR36057_ISR_GIRQ0 | \ - ZR36057_ISR_GIRQ1 | \ - ZR36057_ISR_JPEGRepIRQ ) - -static bool lml33dpath; /* default = 0 - * 1 will use digital path in capture - * mode instead of analog. It can be - * used for picture adjustments using - * tool like xawtv while watching image - * on TV monitor connected to the output. - * However, due to absence of 75 Ohm - * load on Bt819 input, there will be - * some image imperfections */ - -module_param(lml33dpath, bool, 0644); -MODULE_PARM_DESC(lml33dpath, - "Use digital path capture mode (on LML33 cards)"); - -static void -zr36057_init_vfe (struct zoran *zr); - -/* - * General Purpose I/O and Guest bus access - */ - -/* - * This is a bit tricky. When a board lacks a GPIO function, the corresponding - * GPIO bit number in the card_info structure is set to 0. - */ - -void -GPIO (struct zoran *zr, - int bit, - unsigned int value) -{ - u32 reg; - u32 mask; - - /* Make sure the bit number is legal - * A bit number of -1 (lacking) gives a mask of 0, - * making it harmless */ - mask = (1 << (24 + bit)) & 0xff000000; - reg = btread(ZR36057_GPPGCR1) & ~mask; - if (value) { - reg |= mask; - } - btwrite(reg, ZR36057_GPPGCR1); - udelay(1); -} - -/* - * Wait til post office is no longer busy - */ - -int -post_office_wait (struct zoran *zr) -{ - u32 por; - -// while (((por = btread(ZR36057_POR)) & (ZR36057_POR_POPen | ZR36057_POR_POTime)) == ZR36057_POR_POPen) { - while ((por = btread(ZR36057_POR)) & ZR36057_POR_POPen) { - /* wait for something to happen */ - } - if ((por & ZR36057_POR_POTime) && !zr->card.gws_not_connected) { - /* In LML33/BUZ \GWS line is not connected, so it has always timeout set */ - dprintk(1, KERN_INFO "%s: pop timeout %08x\n", ZR_DEVNAME(zr), - por); - return -1; - } - - return 0; -} - -int -post_office_write (struct zoran *zr, - unsigned int guest, - unsigned int reg, - unsigned int value) -{ - u32 por; - - por = - ZR36057_POR_PODir | ZR36057_POR_POTime | ((guest & 7) << 20) | - ((reg & 7) << 16) | (value & 0xFF); - btwrite(por, ZR36057_POR); - - return post_office_wait(zr); -} - -int -post_office_read (struct zoran *zr, - unsigned int guest, - unsigned int reg) -{ - u32 por; - - por = ZR36057_POR_POTime | ((guest & 7) << 20) | ((reg & 7) << 16); - btwrite(por, ZR36057_POR); - if (post_office_wait(zr) < 0) { - return -1; - } - - return btread(ZR36057_POR) & 0xFF; -} - -/* - * detect guests - */ - -static void -dump_guests (struct zoran *zr) -{ - if (zr36067_debug > 2) { - int i, guest[8]; - - for (i = 1; i < 8; i++) { // Don't read jpeg codec here - guest[i] = post_office_read(zr, i, 0); - } - - printk(KERN_INFO "%s: Guests: %*ph\n", - ZR_DEVNAME(zr), 8, guest); - } -} - -void -detect_guest_activity (struct zoran *zr) -{ - int timeout, i, j, res, guest[8], guest0[8], change[8][3]; - ktime_t t0, t1; - - dump_guests(zr); - printk(KERN_INFO "%s: Detecting guests activity, please wait...\n", - ZR_DEVNAME(zr)); - for (i = 1; i < 8; i++) { // Don't read jpeg codec here - guest0[i] = guest[i] = post_office_read(zr, i, 0); - } - - timeout = 0; - j = 0; - t0 = ktime_get(); - while (timeout < 10000) { - udelay(10); - timeout++; - for (i = 1; (i < 8) && (j < 8); i++) { - res = post_office_read(zr, i, 0); - if (res != guest[i]) { - t1 = ktime_get(); - change[j][0] = ktime_to_us(ktime_sub(t1, t0)); - t0 = t1; - change[j][1] = i; - change[j][2] = res; - j++; - guest[i] = res; - } - } - if (j >= 8) - break; - } - - printk(KERN_INFO "%s: Guests: %*ph\n", ZR_DEVNAME(zr), 8, guest0); - - if (j == 0) { - printk(KERN_INFO "%s: No activity detected.\n", ZR_DEVNAME(zr)); - return; - } - for (i = 0; i < j; i++) { - printk(KERN_INFO "%s: %6d: %d => 0x%02x\n", ZR_DEVNAME(zr), - change[i][0], change[i][1], change[i][2]); - } -} - -/* - * JPEG Codec access - */ - -void -jpeg_codec_sleep (struct zoran *zr, - int sleep) -{ - GPIO(zr, zr->card.gpio[ZR_GPIO_JPEG_SLEEP], !sleep); - if (!sleep) { - dprintk(3, - KERN_DEBUG - "%s: jpeg_codec_sleep() - wake GPIO=0x%08x\n", - ZR_DEVNAME(zr), btread(ZR36057_GPPGCR1)); - udelay(500); - } else { - dprintk(3, - KERN_DEBUG - "%s: jpeg_codec_sleep() - sleep GPIO=0x%08x\n", - ZR_DEVNAME(zr), btread(ZR36057_GPPGCR1)); - udelay(2); - } -} - -int -jpeg_codec_reset (struct zoran *zr) -{ - /* Take the codec out of sleep */ - jpeg_codec_sleep(zr, 0); - - if (zr->card.gpcs[GPCS_JPEG_RESET] != 0xff) { - post_office_write(zr, zr->card.gpcs[GPCS_JPEG_RESET], 0, - 0); - udelay(2); - } else { - GPIO(zr, zr->card.gpio[ZR_GPIO_JPEG_RESET], 0); - udelay(2); - GPIO(zr, zr->card.gpio[ZR_GPIO_JPEG_RESET], 1); - udelay(2); - } - - return 0; -} - -/* - * Set the registers for the size we have specified. Don't bother - * trying to understand this without the ZR36057 manual in front of - * you [AC]. - * - * PS: The manual is free for download in .pdf format from - * www.zoran.com - nicely done those folks. - */ - -static void -zr36057_adjust_vfe (struct zoran *zr, - enum zoran_codec_mode mode) -{ - u32 reg; - - switch (mode) { - case BUZ_MODE_MOTION_DECOMPRESS: - btand(~ZR36057_VFESPFR_ExtFl, ZR36057_VFESPFR); - reg = btread(ZR36057_VFEHCR); - if ((reg & (1 << 10)) && zr->card.type != LML33R10) { - reg += ((1 << 10) | 1); - } - btwrite(reg, ZR36057_VFEHCR); - break; - case BUZ_MODE_MOTION_COMPRESS: - case BUZ_MODE_IDLE: - default: - if ((zr->norm & V4L2_STD_NTSC) || - (zr->card.type == LML33R10 && - (zr->norm & V4L2_STD_PAL))) - btand(~ZR36057_VFESPFR_ExtFl, ZR36057_VFESPFR); - else - btor(ZR36057_VFESPFR_ExtFl, ZR36057_VFESPFR); - reg = btread(ZR36057_VFEHCR); - if (!(reg & (1 << 10)) && zr->card.type != LML33R10) { - reg -= ((1 << 10) | 1); - } - btwrite(reg, ZR36057_VFEHCR); - break; - } -} - -/* - * set geometry - */ - -static void -zr36057_set_vfe (struct zoran *zr, - int video_width, - int video_height, - const struct zoran_format *format) -{ - struct tvnorm *tvn; - unsigned HStart, HEnd, VStart, VEnd; - unsigned DispMode; - unsigned VidWinWid, VidWinHt; - unsigned hcrop1, hcrop2, vcrop1, vcrop2; - unsigned Wa, We, Ha, He; - unsigned X, Y, HorDcm, VerDcm; - u32 reg; - unsigned mask_line_size; - - tvn = zr->timing; - - Wa = tvn->Wa; - Ha = tvn->Ha; - - dprintk(2, KERN_INFO "%s: set_vfe() - width = %d, height = %d\n", - ZR_DEVNAME(zr), video_width, video_height); - - if (video_width < BUZ_MIN_WIDTH || - video_height < BUZ_MIN_HEIGHT || - video_width > Wa || video_height > Ha) { - dprintk(1, KERN_ERR "%s: set_vfe: w=%d h=%d not valid\n", - ZR_DEVNAME(zr), video_width, video_height); - return; - } - - /**** zr36057 ****/ - - /* horizontal */ - VidWinWid = video_width; - X = DIV_ROUND_UP(VidWinWid * 64, tvn->Wa); - We = (VidWinWid * 64) / X; - HorDcm = 64 - X; - hcrop1 = 2 * ((tvn->Wa - We) / 4); - hcrop2 = tvn->Wa - We - hcrop1; - HStart = tvn->HStart ? tvn->HStart : 1; - /* (Ronald) Original comment: - * "| 1 Doesn't have any effect, tested on both a DC10 and a DC10+" - * this is false. It inverses chroma values on the LML33R10 (so Cr - * suddenly is shown as Cb and reverse, really cool effect if you - * want to see blue faces, not useful otherwise). So don't use |1. - * However, the DC10 has '0' as HStart, but does need |1, so we - * use a dirty check... - */ - HEnd = HStart + tvn->Wa - 1; - HStart += hcrop1; - HEnd -= hcrop2; - reg = ((HStart & ZR36057_VFEHCR_Hmask) << ZR36057_VFEHCR_HStart) - | ((HEnd & ZR36057_VFEHCR_Hmask) << ZR36057_VFEHCR_HEnd); - if (zr->card.vfe_pol.hsync_pol) - reg |= ZR36057_VFEHCR_HSPol; - btwrite(reg, ZR36057_VFEHCR); - - /* Vertical */ - DispMode = !(video_height > BUZ_MAX_HEIGHT / 2); - VidWinHt = DispMode ? video_height : video_height / 2; - Y = DIV_ROUND_UP(VidWinHt * 64 * 2, tvn->Ha); - He = (VidWinHt * 64) / Y; - VerDcm = 64 - Y; - vcrop1 = (tvn->Ha / 2 - He) / 2; - vcrop2 = tvn->Ha / 2 - He - vcrop1; - VStart = tvn->VStart; - VEnd = VStart + tvn->Ha / 2; // - 1; FIXME SnapShot times out with -1 in 768*576 on the DC10 - LP - VStart += vcrop1; - VEnd -= vcrop2; - reg = ((VStart & ZR36057_VFEVCR_Vmask) << ZR36057_VFEVCR_VStart) - | ((VEnd & ZR36057_VFEVCR_Vmask) << ZR36057_VFEVCR_VEnd); - if (zr->card.vfe_pol.vsync_pol) - reg |= ZR36057_VFEVCR_VSPol; - btwrite(reg, ZR36057_VFEVCR); - - /* scaler and pixel format */ - reg = 0; - reg |= (HorDcm << ZR36057_VFESPFR_HorDcm); - reg |= (VerDcm << ZR36057_VFESPFR_VerDcm); - reg |= (DispMode << ZR36057_VFESPFR_DispMode); - /* RJ: I don't know, why the following has to be the opposite - * of the corresponding ZR36060 setting, but only this way - * we get the correct colors when uncompressing to the screen */ - //reg |= ZR36057_VFESPFR_VCLKPol; /**/ - /* RJ: Don't know if that is needed for NTSC also */ - if (!(zr->norm & V4L2_STD_NTSC)) - reg |= ZR36057_VFESPFR_ExtFl; // NEEDED!!!!!!! Wolfgang - reg |= ZR36057_VFESPFR_TopField; - if (HorDcm >= 48) { - reg |= 3 << ZR36057_VFESPFR_HFilter; /* 5 tap filter */ - } else if (HorDcm >= 32) { - reg |= 2 << ZR36057_VFESPFR_HFilter; /* 4 tap filter */ - } else if (HorDcm >= 16) { - reg |= 1 << ZR36057_VFESPFR_HFilter; /* 3 tap filter */ - } - reg |= format->vfespfr; - btwrite(reg, ZR36057_VFESPFR); - - /* display configuration */ - reg = (16 << ZR36057_VDCR_MinPix) - | (VidWinHt << ZR36057_VDCR_VidWinHt) - | (VidWinWid << ZR36057_VDCR_VidWinWid); - if (pci_pci_problems & PCIPCI_TRITON) - // || zr->revision < 1) // Revision 1 has also Triton support - reg &= ~ZR36057_VDCR_Triton; - else - reg |= ZR36057_VDCR_Triton; - btwrite(reg, ZR36057_VDCR); - - /* (Ronald) don't write this if overlay_mask = NULL */ - if (zr->overlay_mask) { - /* Write overlay clipping mask data, but don't enable overlay clipping */ - /* RJ: since this makes only sense on the screen, we use - * zr->overlay_settings.width instead of video_width */ - - mask_line_size = (BUZ_MAX_WIDTH + 31) / 32; - reg = virt_to_bus(zr->overlay_mask); - btwrite(reg, ZR36057_MMTR); - reg = virt_to_bus(zr->overlay_mask + mask_line_size); - btwrite(reg, ZR36057_MMBR); - reg = - mask_line_size - (zr->overlay_settings.width + - 31) / 32; - if (DispMode == 0) - reg += mask_line_size; - reg <<= ZR36057_OCR_MaskStride; - btwrite(reg, ZR36057_OCR); - } - - zr36057_adjust_vfe(zr, zr->codec_mode); -} - -/* - * Switch overlay on or off - */ - -void -zr36057_overlay (struct zoran *zr, - int on) -{ - u32 reg; - - if (on) { - /* do the necessary settings ... */ - btand(~ZR36057_VDCR_VidEn, ZR36057_VDCR); /* switch it off first */ - - zr36057_set_vfe(zr, - zr->overlay_settings.width, - zr->overlay_settings.height, - zr->overlay_settings.format); - - /* Start and length of each line MUST be 4-byte aligned. - * This should be already checked before the call to this routine. - * All error messages are internal driver checking only! */ - - /* video display top and bottom registers */ - reg = (long) zr->vbuf_base + - zr->overlay_settings.x * - ((zr->overlay_settings.format->depth + 7) / 8) + - zr->overlay_settings.y * - zr->vbuf_bytesperline; - btwrite(reg, ZR36057_VDTR); - if (reg & 3) - dprintk(1, - KERN_ERR - "%s: zr36057_overlay() - video_address not aligned\n", - ZR_DEVNAME(zr)); - if (zr->overlay_settings.height > BUZ_MAX_HEIGHT / 2) - reg += zr->vbuf_bytesperline; - btwrite(reg, ZR36057_VDBR); - - /* video stride, status, and frame grab register */ - reg = zr->vbuf_bytesperline - - zr->overlay_settings.width * - ((zr->overlay_settings.format->depth + 7) / 8); - if (zr->overlay_settings.height > BUZ_MAX_HEIGHT / 2) - reg += zr->vbuf_bytesperline; - if (reg & 3) - dprintk(1, - KERN_ERR - "%s: zr36057_overlay() - video_stride not aligned\n", - ZR_DEVNAME(zr)); - reg = (reg << ZR36057_VSSFGR_DispStride); - reg |= ZR36057_VSSFGR_VidOvf; /* clear overflow status */ - btwrite(reg, ZR36057_VSSFGR); - - /* Set overlay clipping */ - if (zr->overlay_settings.clipcount > 0) - btor(ZR36057_OCR_OvlEnable, ZR36057_OCR); - - /* ... and switch it on */ - btor(ZR36057_VDCR_VidEn, ZR36057_VDCR); - } else { - /* Switch it off */ - btand(~ZR36057_VDCR_VidEn, ZR36057_VDCR); - } -} - -/* - * The overlay mask has one bit for each pixel on a scan line, - * and the maximum window size is BUZ_MAX_WIDTH * BUZ_MAX_HEIGHT pixels. - */ - -void write_overlay_mask(struct zoran_fh *fh, struct v4l2_clip *vp, int count) -{ - struct zoran *zr = fh->zr; - unsigned mask_line_size = (BUZ_MAX_WIDTH + 31) / 32; - u32 *mask; - int x, y, width, height; - unsigned i, j, k; - - /* fill mask with one bits */ - memset(fh->overlay_mask, ~0, mask_line_size * 4 * BUZ_MAX_HEIGHT); - - for (i = 0; i < count; ++i) { - /* pick up local copy of clip */ - x = vp[i].c.left; - y = vp[i].c.top; - width = vp[i].c.width; - height = vp[i].c.height; - - /* trim clips that extend beyond the window */ - if (x < 0) { - width += x; - x = 0; - } - if (y < 0) { - height += y; - y = 0; - } - if (x + width > fh->overlay_settings.width) { - width = fh->overlay_settings.width - x; - } - if (y + height > fh->overlay_settings.height) { - height = fh->overlay_settings.height - y; - } - - /* ignore degenerate clips */ - if (height <= 0) { - continue; - } - if (width <= 0) { - continue; - } - - /* apply clip for each scan line */ - for (j = 0; j < height; ++j) { - /* reset bit for each pixel */ - /* this can be optimized later if need be */ - mask = fh->overlay_mask + (y + j) * mask_line_size; - for (k = 0; k < width; ++k) { - mask[(x + k) / 32] &= - ~((u32) 1 << (x + k) % 32); - } - } - } -} - -/* Enable/Disable uncompressed memory grabbing of the 36057 */ - -void -zr36057_set_memgrab (struct zoran *zr, - int mode) -{ - if (mode) { - /* We only check SnapShot and not FrameGrab here. SnapShot==1 - * means a capture is already in progress, but FrameGrab==1 - * doesn't necessary mean that. It's more correct to say a 1 - * to 0 transition indicates a capture completed. If a - * capture is pending when capturing is tuned off, FrameGrab - * will be stuck at 1 until capturing is turned back on. - */ - if (btread(ZR36057_VSSFGR) & ZR36057_VSSFGR_SnapShot) - dprintk(1, - KERN_WARNING - "%s: zr36057_set_memgrab(1) with SnapShot on!?\n", - ZR_DEVNAME(zr)); - - /* switch on VSync interrupts */ - btwrite(IRQ_MASK, ZR36057_ISR); // Clear Interrupts - btor(zr->card.vsync_int, ZR36057_ICR); // SW - - /* enable SnapShot */ - btor(ZR36057_VSSFGR_SnapShot, ZR36057_VSSFGR); - - /* Set zr36057 video front end and enable video */ - zr36057_set_vfe(zr, zr->v4l_settings.width, - zr->v4l_settings.height, - zr->v4l_settings.format); - - zr->v4l_memgrab_active = 1; - } else { - /* switch off VSync interrupts */ - btand(~zr->card.vsync_int, ZR36057_ICR); // SW - - zr->v4l_memgrab_active = 0; - zr->v4l_grab_frame = NO_GRAB_ACTIVE; - - /* re-enable grabbing to screen if it was running */ - if (zr->v4l_overlay_active) { - zr36057_overlay(zr, 1); - } else { - btand(~ZR36057_VDCR_VidEn, ZR36057_VDCR); - btand(~ZR36057_VSSFGR_SnapShot, ZR36057_VSSFGR); - } - } -} - -int -wait_grab_pending (struct zoran *zr) -{ - unsigned long flags; - - /* wait until all pending grabs are finished */ - - if (!zr->v4l_memgrab_active) - return 0; - - wait_event_interruptible(zr->v4l_capq, - (zr->v4l_pend_tail == zr->v4l_pend_head)); - if (signal_pending(current)) - return -ERESTARTSYS; - - spin_lock_irqsave(&zr->spinlock, flags); - zr36057_set_memgrab(zr, 0); - spin_unlock_irqrestore(&zr->spinlock, flags); - - return 0; -} - -/***************************************************************************** - * * - * Set up the Buz-specific MJPEG part * - * * - *****************************************************************************/ - -static inline void -set_frame (struct zoran *zr, - int val) -{ - GPIO(zr, zr->card.gpio[ZR_GPIO_JPEG_FRAME], val); -} - -static void -set_videobus_dir (struct zoran *zr, - int val) -{ - switch (zr->card.type) { - case LML33: - case LML33R10: - if (!lml33dpath) - GPIO(zr, 5, val); - else - GPIO(zr, 5, 1); - break; - default: - GPIO(zr, zr->card.gpio[ZR_GPIO_VID_DIR], - zr->card.gpio_pol[ZR_GPIO_VID_DIR] ? !val : val); - break; - } -} - -static void -init_jpeg_queue (struct zoran *zr) -{ - int i; - - /* re-initialize DMA ring stuff */ - zr->jpg_que_head = 0; - zr->jpg_dma_head = 0; - zr->jpg_dma_tail = 0; - zr->jpg_que_tail = 0; - zr->jpg_seq_num = 0; - zr->JPEG_error = 0; - zr->num_errors = 0; - zr->jpg_err_seq = 0; - zr->jpg_err_shift = 0; - zr->jpg_queued_num = 0; - for (i = 0; i < zr->jpg_buffers.num_buffers; i++) { - zr->jpg_buffers.buffer[i].state = BUZ_STATE_USER; /* nothing going on */ - } - for (i = 0; i < BUZ_NUM_STAT_COM; i++) { - zr->stat_com[i] = cpu_to_le32(1); /* mark as unavailable to zr36057 */ - } -} - -static void -zr36057_set_jpg (struct zoran *zr, - enum zoran_codec_mode mode) -{ - struct tvnorm *tvn; - u32 reg; - - tvn = zr->timing; - - /* assert P_Reset, disable code transfer, deassert Active */ - btwrite(0, ZR36057_JPC); - - /* MJPEG compression mode */ - switch (mode) { - - case BUZ_MODE_MOTION_COMPRESS: - default: - reg = ZR36057_JMC_MJPGCmpMode; - break; - - case BUZ_MODE_MOTION_DECOMPRESS: - reg = ZR36057_JMC_MJPGExpMode; - reg |= ZR36057_JMC_SyncMstr; - /* RJ: The following is experimental - improves the output to screen */ - //if(zr->jpg_settings.VFIFO_FB) reg |= ZR36057_JMC_VFIFO_FB; // No, it doesn't. SM - break; - - case BUZ_MODE_STILL_COMPRESS: - reg = ZR36057_JMC_JPGCmpMode; - break; - - case BUZ_MODE_STILL_DECOMPRESS: - reg = ZR36057_JMC_JPGExpMode; - break; - - } - reg |= ZR36057_JMC_JPG; - if (zr->jpg_settings.field_per_buff == 1) - reg |= ZR36057_JMC_Fld_per_buff; - btwrite(reg, ZR36057_JMC); - - /* vertical */ - btor(ZR36057_VFEVCR_VSPol, ZR36057_VFEVCR); - reg = (6 << ZR36057_VSP_VsyncSize) | - (tvn->Ht << ZR36057_VSP_FrmTot); - btwrite(reg, ZR36057_VSP); - reg = ((zr->jpg_settings.img_y + tvn->VStart) << ZR36057_FVAP_NAY) | - (zr->jpg_settings.img_height << ZR36057_FVAP_PAY); - btwrite(reg, ZR36057_FVAP); - - /* horizontal */ - if (zr->card.vfe_pol.hsync_pol) - btor(ZR36057_VFEHCR_HSPol, ZR36057_VFEHCR); - else - btand(~ZR36057_VFEHCR_HSPol, ZR36057_VFEHCR); - reg = ((tvn->HSyncStart) << ZR36057_HSP_HsyncStart) | - (tvn->Wt << ZR36057_HSP_LineTot); - btwrite(reg, ZR36057_HSP); - reg = ((zr->jpg_settings.img_x + - tvn->HStart + 4) << ZR36057_FHAP_NAX) | - (zr->jpg_settings.img_width << ZR36057_FHAP_PAX); - btwrite(reg, ZR36057_FHAP); - - /* field process parameters */ - if (zr->jpg_settings.odd_even) - reg = ZR36057_FPP_Odd_Even; - else - reg = 0; - - btwrite(reg, ZR36057_FPP); - - /* Set proper VCLK Polarity, else colors will be wrong during playback */ - //btor(ZR36057_VFESPFR_VCLKPol, ZR36057_VFESPFR); - - /* code base address */ - reg = virt_to_bus(zr->stat_com); - btwrite(reg, ZR36057_JCBA); - - /* FIFO threshold (FIFO is 160. double words) */ - /* NOTE: decimal values here */ - switch (mode) { - - case BUZ_MODE_STILL_COMPRESS: - case BUZ_MODE_MOTION_COMPRESS: - if (zr->card.type != BUZ) - reg = 140; - else - reg = 60; - break; - - case BUZ_MODE_STILL_DECOMPRESS: - case BUZ_MODE_MOTION_DECOMPRESS: - reg = 20; - break; - - default: - reg = 80; - break; - - } - btwrite(reg, ZR36057_JCFT); - zr36057_adjust_vfe(zr, mode); - -} - -void -print_interrupts (struct zoran *zr) -{ - int res, noerr = 0; - - printk(KERN_INFO "%s: interrupts received:", ZR_DEVNAME(zr)); - if ((res = zr->field_counter) < -1 || res > 1) { - printk(KERN_CONT " FD:%d", res); - } - if ((res = zr->intr_counter_GIRQ1) != 0) { - printk(KERN_CONT " GIRQ1:%d", res); - noerr++; - } - if ((res = zr->intr_counter_GIRQ0) != 0) { - printk(KERN_CONT " GIRQ0:%d", res); - noerr++; - } - if ((res = zr->intr_counter_CodRepIRQ) != 0) { - printk(KERN_CONT " CodRepIRQ:%d", res); - noerr++; - } - if ((res = zr->intr_counter_JPEGRepIRQ) != 0) { - printk(KERN_CONT " JPEGRepIRQ:%d", res); - noerr++; - } - if (zr->JPEG_max_missed) { - printk(KERN_CONT " JPEG delays: max=%d min=%d", zr->JPEG_max_missed, - zr->JPEG_min_missed); - } - if (zr->END_event_missed) { - printk(KERN_CONT " ENDs missed: %d", zr->END_event_missed); - } - //if (zr->jpg_queued_num) { - printk(KERN_CONT " queue_state=%ld/%ld/%ld/%ld", zr->jpg_que_tail, - zr->jpg_dma_tail, zr->jpg_dma_head, zr->jpg_que_head); - //} - if (!noerr) { - printk(KERN_CONT ": no interrupts detected."); - } - printk(KERN_CONT "\n"); -} - -void -clear_interrupt_counters (struct zoran *zr) -{ - zr->intr_counter_GIRQ1 = 0; - zr->intr_counter_GIRQ0 = 0; - zr->intr_counter_CodRepIRQ = 0; - zr->intr_counter_JPEGRepIRQ = 0; - zr->field_counter = 0; - zr->IRQ1_in = 0; - zr->IRQ1_out = 0; - zr->JPEG_in = 0; - zr->JPEG_out = 0; - zr->JPEG_0 = 0; - zr->JPEG_1 = 0; - zr->END_event_missed = 0; - zr->JPEG_missed = 0; - zr->JPEG_max_missed = 0; - zr->JPEG_min_missed = 0x7fffffff; -} - -static u32 -count_reset_interrupt (struct zoran *zr) -{ - u32 isr; - - if ((isr = btread(ZR36057_ISR) & 0x78000000)) { - if (isr & ZR36057_ISR_GIRQ1) { - btwrite(ZR36057_ISR_GIRQ1, ZR36057_ISR); - zr->intr_counter_GIRQ1++; - } - if (isr & ZR36057_ISR_GIRQ0) { - btwrite(ZR36057_ISR_GIRQ0, ZR36057_ISR); - zr->intr_counter_GIRQ0++; - } - if (isr & ZR36057_ISR_CodRepIRQ) { - btwrite(ZR36057_ISR_CodRepIRQ, ZR36057_ISR); - zr->intr_counter_CodRepIRQ++; - } - if (isr & ZR36057_ISR_JPEGRepIRQ) { - btwrite(ZR36057_ISR_JPEGRepIRQ, ZR36057_ISR); - zr->intr_counter_JPEGRepIRQ++; - } - } - return isr; -} - -void -jpeg_start (struct zoran *zr) -{ - int reg; - - zr->frame_num = 0; - - /* deassert P_reset, disable code transfer, deassert Active */ - btwrite(ZR36057_JPC_P_Reset, ZR36057_JPC); - /* stop flushing the internal code buffer */ - btand(~ZR36057_MCTCR_CFlush, ZR36057_MCTCR); - /* enable code transfer */ - btor(ZR36057_JPC_CodTrnsEn, ZR36057_JPC); - - /* clear IRQs */ - btwrite(IRQ_MASK, ZR36057_ISR); - /* enable the JPEG IRQs */ - btwrite(zr->card.jpeg_int | - ZR36057_ICR_JPEGRepIRQ | - ZR36057_ICR_IntPinEn, - ZR36057_ICR); - - set_frame(zr, 0); // \FRAME - - /* set the JPEG codec guest ID */ - reg = (zr->card.gpcs[1] << ZR36057_JCGI_JPEGuestID) | - (0 << ZR36057_JCGI_JPEGuestReg); - btwrite(reg, ZR36057_JCGI); - - if (zr->card.video_vfe == CODEC_TYPE_ZR36016 && - zr->card.video_codec == CODEC_TYPE_ZR36050) { - /* Enable processing on the ZR36016 */ - if (zr->vfe) - zr36016_write(zr->vfe, 0, 1); - - /* load the address of the GO register in the ZR36050 latch */ - post_office_write(zr, 0, 0, 0); - } - - /* assert Active */ - btor(ZR36057_JPC_Active, ZR36057_JPC); - - /* enable the Go generation */ - btor(ZR36057_JMC_Go_en, ZR36057_JMC); - udelay(30); - - set_frame(zr, 1); // /FRAME - - dprintk(3, KERN_DEBUG "%s: jpeg_start\n", ZR_DEVNAME(zr)); -} - -void -zr36057_enable_jpg (struct zoran *zr, - enum zoran_codec_mode mode) -{ - struct vfe_settings cap; - int field_size = - zr->jpg_buffers.buffer_size / zr->jpg_settings.field_per_buff; - - zr->codec_mode = mode; - - cap.x = zr->jpg_settings.img_x; - cap.y = zr->jpg_settings.img_y; - cap.width = zr->jpg_settings.img_width; - cap.height = zr->jpg_settings.img_height; - cap.decimation = - zr->jpg_settings.HorDcm | (zr->jpg_settings.VerDcm << 8); - cap.quality = zr->jpg_settings.jpg_comp.quality; - - switch (mode) { - - case BUZ_MODE_MOTION_COMPRESS: { - struct jpeg_app_marker app; - struct jpeg_com_marker com; - - /* In motion compress mode, the decoder output must be enabled, and - * the video bus direction set to input. - */ - set_videobus_dir(zr, 0); - decoder_call(zr, video, s_stream, 1); - encoder_call(zr, video, s_routing, 0, 0, 0); - - /* Take the JPEG codec and the VFE out of sleep */ - jpeg_codec_sleep(zr, 0); - - /* set JPEG app/com marker */ - app.appn = zr->jpg_settings.jpg_comp.APPn; - app.len = zr->jpg_settings.jpg_comp.APP_len; - memcpy(app.data, zr->jpg_settings.jpg_comp.APP_data, 60); - zr->codec->control(zr->codec, CODEC_S_JPEG_APP_DATA, - sizeof(struct jpeg_app_marker), &app); - - com.len = zr->jpg_settings.jpg_comp.COM_len; - memcpy(com.data, zr->jpg_settings.jpg_comp.COM_data, 60); - zr->codec->control(zr->codec, CODEC_S_JPEG_COM_DATA, - sizeof(struct jpeg_com_marker), &com); - - /* Setup the JPEG codec */ - zr->codec->control(zr->codec, CODEC_S_JPEG_TDS_BYTE, - sizeof(int), &field_size); - zr->codec->set_video(zr->codec, zr->timing, &cap, - &zr->card.vfe_pol); - zr->codec->set_mode(zr->codec, CODEC_DO_COMPRESSION); - - /* Setup the VFE */ - if (zr->vfe) { - zr->vfe->control(zr->vfe, CODEC_S_JPEG_TDS_BYTE, - sizeof(int), &field_size); - zr->vfe->set_video(zr->vfe, zr->timing, &cap, - &zr->card.vfe_pol); - zr->vfe->set_mode(zr->vfe, CODEC_DO_COMPRESSION); - } - - init_jpeg_queue(zr); - zr36057_set_jpg(zr, mode); // \P_Reset, ... Video param, FIFO - - clear_interrupt_counters(zr); - dprintk(2, KERN_INFO "%s: enable_jpg(MOTION_COMPRESS)\n", - ZR_DEVNAME(zr)); - break; - } - - case BUZ_MODE_MOTION_DECOMPRESS: - /* In motion decompression mode, the decoder output must be disabled, and - * the video bus direction set to output. - */ - decoder_call(zr, video, s_stream, 0); - set_videobus_dir(zr, 1); - encoder_call(zr, video, s_routing, 1, 0, 0); - - /* Take the JPEG codec and the VFE out of sleep */ - jpeg_codec_sleep(zr, 0); - /* Setup the VFE */ - if (zr->vfe) { - zr->vfe->set_video(zr->vfe, zr->timing, &cap, - &zr->card.vfe_pol); - zr->vfe->set_mode(zr->vfe, CODEC_DO_EXPANSION); - } - /* Setup the JPEG codec */ - zr->codec->set_video(zr->codec, zr->timing, &cap, - &zr->card.vfe_pol); - zr->codec->set_mode(zr->codec, CODEC_DO_EXPANSION); - - init_jpeg_queue(zr); - zr36057_set_jpg(zr, mode); // \P_Reset, ... Video param, FIFO - - clear_interrupt_counters(zr); - dprintk(2, KERN_INFO "%s: enable_jpg(MOTION_DECOMPRESS)\n", - ZR_DEVNAME(zr)); - break; - - case BUZ_MODE_IDLE: - default: - /* shut down processing */ - btand(~(zr->card.jpeg_int | ZR36057_ICR_JPEGRepIRQ), - ZR36057_ICR); - btwrite(zr->card.jpeg_int | ZR36057_ICR_JPEGRepIRQ, - ZR36057_ISR); - btand(~ZR36057_JMC_Go_en, ZR36057_JMC); // \Go_en - - msleep(50); - - set_videobus_dir(zr, 0); - set_frame(zr, 1); // /FRAME - btor(ZR36057_MCTCR_CFlush, ZR36057_MCTCR); // /CFlush - btwrite(0, ZR36057_JPC); // \P_Reset,\CodTrnsEn,\Active - btand(~ZR36057_JMC_VFIFO_FB, ZR36057_JMC); - btand(~ZR36057_JMC_SyncMstr, ZR36057_JMC); - jpeg_codec_reset(zr); - jpeg_codec_sleep(zr, 1); - zr36057_adjust_vfe(zr, mode); - - decoder_call(zr, video, s_stream, 1); - encoder_call(zr, video, s_routing, 0, 0, 0); - - dprintk(2, KERN_INFO "%s: enable_jpg(IDLE)\n", ZR_DEVNAME(zr)); - break; - - } -} - -/* when this is called the spinlock must be held */ -void -zoran_feed_stat_com (struct zoran *zr) -{ - /* move frames from pending queue to DMA */ - - int frame, i, max_stat_com; - - max_stat_com = - (zr->jpg_settings.TmpDcm == - 1) ? BUZ_NUM_STAT_COM : (BUZ_NUM_STAT_COM >> 1); - - while ((zr->jpg_dma_head - zr->jpg_dma_tail) < max_stat_com && - zr->jpg_dma_head < zr->jpg_que_head) { - - frame = zr->jpg_pend[zr->jpg_dma_head & BUZ_MASK_FRAME]; - if (zr->jpg_settings.TmpDcm == 1) { - /* fill 1 stat_com entry */ - i = (zr->jpg_dma_head - - zr->jpg_err_shift) & BUZ_MASK_STAT_COM; - if (!(zr->stat_com[i] & cpu_to_le32(1))) - break; - zr->stat_com[i] = - cpu_to_le32(zr->jpg_buffers.buffer[frame].jpg.frag_tab_bus); - } else { - /* fill 2 stat_com entries */ - i = ((zr->jpg_dma_head - - zr->jpg_err_shift) & 1) * 2; - if (!(zr->stat_com[i] & cpu_to_le32(1))) - break; - zr->stat_com[i] = - cpu_to_le32(zr->jpg_buffers.buffer[frame].jpg.frag_tab_bus); - zr->stat_com[i + 1] = - cpu_to_le32(zr->jpg_buffers.buffer[frame].jpg.frag_tab_bus); - } - zr->jpg_buffers.buffer[frame].state = BUZ_STATE_DMA; - zr->jpg_dma_head++; - - } - if (zr->codec_mode == BUZ_MODE_MOTION_DECOMPRESS) - zr->jpg_queued_num++; -} - -/* when this is called the spinlock must be held */ -static void -zoran_reap_stat_com (struct zoran *zr) -{ - /* move frames from DMA queue to done queue */ - - int i; - u32 stat_com; - unsigned int seq; - unsigned int dif; - struct zoran_buffer *buffer; - int frame; - - /* In motion decompress we don't have a hardware frame counter, - * we just count the interrupts here */ - - if (zr->codec_mode == BUZ_MODE_MOTION_DECOMPRESS) { - zr->jpg_seq_num++; - } - while (zr->jpg_dma_tail < zr->jpg_dma_head) { - if (zr->jpg_settings.TmpDcm == 1) - i = (zr->jpg_dma_tail - - zr->jpg_err_shift) & BUZ_MASK_STAT_COM; - else - i = ((zr->jpg_dma_tail - - zr->jpg_err_shift) & 1) * 2 + 1; - - stat_com = le32_to_cpu(zr->stat_com[i]); - - if ((stat_com & 1) == 0) { - return; - } - frame = zr->jpg_pend[zr->jpg_dma_tail & BUZ_MASK_FRAME]; - buffer = &zr->jpg_buffers.buffer[frame]; - buffer->bs.ts = ktime_get_ns(); - - if (zr->codec_mode == BUZ_MODE_MOTION_COMPRESS) { - buffer->bs.length = (stat_com & 0x7fffff) >> 1; - - /* update sequence number with the help of the counter in stat_com */ - - seq = ((stat_com >> 24) + zr->jpg_err_seq) & 0xff; - dif = (seq - zr->jpg_seq_num) & 0xff; - zr->jpg_seq_num += dif; - } else { - buffer->bs.length = 0; - } - buffer->bs.seq = - zr->jpg_settings.TmpDcm == - 2 ? (zr->jpg_seq_num >> 1) : zr->jpg_seq_num; - buffer->state = BUZ_STATE_DONE; - - zr->jpg_dma_tail++; - } -} - -static void zoran_restart(struct zoran *zr) -{ - /* Now the stat_comm buffer is ready for restart */ - unsigned int status = 0; - int mode; - - if (zr->codec_mode == BUZ_MODE_MOTION_COMPRESS) { - decoder_call(zr, video, g_input_status, &status); - mode = CODEC_DO_COMPRESSION; - } else { - status = V4L2_IN_ST_NO_SIGNAL; - mode = CODEC_DO_EXPANSION; - } - if (zr->codec_mode == BUZ_MODE_MOTION_DECOMPRESS || - !(status & V4L2_IN_ST_NO_SIGNAL)) { - /********** RESTART code *************/ - jpeg_codec_reset(zr); - zr->codec->set_mode(zr->codec, mode); - zr36057_set_jpg(zr, zr->codec_mode); - jpeg_start(zr); - - if (zr->num_errors <= 8) - dprintk(2, KERN_INFO "%s: Restart\n", - ZR_DEVNAME(zr)); - - zr->JPEG_missed = 0; - zr->JPEG_error = 2; - /********** End RESTART code ***********/ - } -} - -static void -error_handler (struct zoran *zr, - u32 astat, - u32 stat) -{ - int i; - - /* This is JPEG error handling part */ - if (zr->codec_mode != BUZ_MODE_MOTION_COMPRESS && - zr->codec_mode != BUZ_MODE_MOTION_DECOMPRESS) { - return; - } - - if ((stat & 1) == 0 && - zr->codec_mode == BUZ_MODE_MOTION_COMPRESS && - zr->jpg_dma_tail - zr->jpg_que_tail >= zr->jpg_buffers.num_buffers) { - /* No free buffers... */ - zoran_reap_stat_com(zr); - zoran_feed_stat_com(zr); - wake_up_interruptible(&zr->jpg_capq); - zr->JPEG_missed = 0; - return; - } - - if (zr->JPEG_error == 1) { - zoran_restart(zr); - return; - } - - /* - * First entry: error just happened during normal operation - * - * In BUZ_MODE_MOTION_COMPRESS: - * - * Possible glitch in TV signal. In this case we should - * stop the codec and wait for good quality signal before - * restarting it to avoid further problems - * - * In BUZ_MODE_MOTION_DECOMPRESS: - * - * Bad JPEG frame: we have to mark it as processed (codec crashed - * and was not able to do it itself), and to remove it from queue. - */ - btand(~ZR36057_JMC_Go_en, ZR36057_JMC); - udelay(1); - stat = stat | (post_office_read(zr, 7, 0) & 3) << 8; - btwrite(0, ZR36057_JPC); - btor(ZR36057_MCTCR_CFlush, ZR36057_MCTCR); - jpeg_codec_reset(zr); - jpeg_codec_sleep(zr, 1); - zr->JPEG_error = 1; - zr->num_errors++; - - /* Report error */ - if (zr36067_debug > 1 && zr->num_errors <= 8) { - long frame; - int j; - - frame = zr->jpg_pend[zr->jpg_dma_tail & BUZ_MASK_FRAME]; - printk(KERN_ERR - "%s: JPEG error stat=0x%08x(0x%08x) queue_state=%ld/%ld/%ld/%ld seq=%ld frame=%ld. Codec stopped. ", - ZR_DEVNAME(zr), stat, zr->last_isr, - zr->jpg_que_tail, zr->jpg_dma_tail, - zr->jpg_dma_head, zr->jpg_que_head, - zr->jpg_seq_num, frame); - printk(KERN_INFO "stat_com frames:"); - for (j = 0; j < BUZ_NUM_STAT_COM; j++) { - for (i = 0; i < zr->jpg_buffers.num_buffers; i++) { - if (le32_to_cpu(zr->stat_com[j]) == zr->jpg_buffers.buffer[i].jpg.frag_tab_bus) - printk(KERN_CONT "% d->%d", j, i); - } - } - printk(KERN_CONT "\n"); - } - /* Find an entry in stat_com and rotate contents */ - if (zr->jpg_settings.TmpDcm == 1) - i = (zr->jpg_dma_tail - zr->jpg_err_shift) & BUZ_MASK_STAT_COM; - else - i = ((zr->jpg_dma_tail - zr->jpg_err_shift) & 1) * 2; - if (zr->codec_mode == BUZ_MODE_MOTION_DECOMPRESS) { - /* Mimic zr36067 operation */ - zr->stat_com[i] |= cpu_to_le32(1); - if (zr->jpg_settings.TmpDcm != 1) - zr->stat_com[i + 1] |= cpu_to_le32(1); - /* Refill */ - zoran_reap_stat_com(zr); - zoran_feed_stat_com(zr); - wake_up_interruptible(&zr->jpg_capq); - /* Find an entry in stat_com again after refill */ - if (zr->jpg_settings.TmpDcm == 1) - i = (zr->jpg_dma_tail - zr->jpg_err_shift) & BUZ_MASK_STAT_COM; - else - i = ((zr->jpg_dma_tail - zr->jpg_err_shift) & 1) * 2; - } - if (i) { - /* Rotate stat_comm entries to make current entry first */ - int j; - __le32 bus_addr[BUZ_NUM_STAT_COM]; - - /* Here we are copying the stat_com array, which - * is already in little endian format, so - * no endian conversions here - */ - memcpy(bus_addr, zr->stat_com, sizeof(bus_addr)); - - for (j = 0; j < BUZ_NUM_STAT_COM; j++) - zr->stat_com[j] = bus_addr[(i + j) & BUZ_MASK_STAT_COM]; - - zr->jpg_err_shift += i; - zr->jpg_err_shift &= BUZ_MASK_STAT_COM; - } - if (zr->codec_mode == BUZ_MODE_MOTION_COMPRESS) - zr->jpg_err_seq = zr->jpg_seq_num; /* + 1; */ - zoran_restart(zr); -} - -irqreturn_t -zoran_irq (int irq, - void *dev_id) -{ - u32 stat, astat; - int count; - struct zoran *zr; - unsigned long flags; - - zr = dev_id; - count = 0; - - if (zr->testing) { - /* Testing interrupts */ - spin_lock_irqsave(&zr->spinlock, flags); - while ((stat = count_reset_interrupt(zr))) { - if (count++ > 100) { - btand(~ZR36057_ICR_IntPinEn, ZR36057_ICR); - dprintk(1, - KERN_ERR - "%s: IRQ lockup while testing, isr=0x%08x, cleared int mask\n", - ZR_DEVNAME(zr), stat); - wake_up_interruptible(&zr->test_q); - } - } - zr->last_isr = stat; - spin_unlock_irqrestore(&zr->spinlock, flags); - return IRQ_HANDLED; - } - - spin_lock_irqsave(&zr->spinlock, flags); - while (1) { - /* get/clear interrupt status bits */ - stat = count_reset_interrupt(zr); - astat = stat & IRQ_MASK; - if (!astat) { - break; - } - dprintk(4, - KERN_DEBUG - "zoran_irq: astat: 0x%08x, mask: 0x%08x\n", - astat, btread(ZR36057_ICR)); - if (astat & zr->card.vsync_int) { // SW - - if (zr->codec_mode == BUZ_MODE_MOTION_DECOMPRESS || - zr->codec_mode == BUZ_MODE_MOTION_COMPRESS) { - /* count missed interrupts */ - zr->JPEG_missed++; - } - //post_office_read(zr,1,0); - /* Interrupts may still happen when - * zr->v4l_memgrab_active is switched off. - * We simply ignore them */ - - if (zr->v4l_memgrab_active) { - /* A lot more checks should be here ... */ - if ((btread(ZR36057_VSSFGR) & ZR36057_VSSFGR_SnapShot) == 0) - dprintk(1, - KERN_WARNING - "%s: BuzIRQ with SnapShot off ???\n", - ZR_DEVNAME(zr)); - - if (zr->v4l_grab_frame != NO_GRAB_ACTIVE) { - /* There is a grab on a frame going on, check if it has finished */ - if ((btread(ZR36057_VSSFGR) & ZR36057_VSSFGR_FrameGrab) == 0) { - /* it is finished, notify the user */ - - zr->v4l_buffers.buffer[zr->v4l_grab_frame].state = BUZ_STATE_DONE; - zr->v4l_buffers.buffer[zr->v4l_grab_frame].bs.seq = zr->v4l_grab_seq; - zr->v4l_buffers.buffer[zr->v4l_grab_frame].bs.ts = ktime_get_ns(); - zr->v4l_grab_frame = NO_GRAB_ACTIVE; - zr->v4l_pend_tail++; - } - } - - if (zr->v4l_grab_frame == NO_GRAB_ACTIVE) - wake_up_interruptible(&zr->v4l_capq); - - /* Check if there is another grab queued */ - - if (zr->v4l_grab_frame == NO_GRAB_ACTIVE && - zr->v4l_pend_tail != zr->v4l_pend_head) { - int frame = zr->v4l_pend[zr->v4l_pend_tail & V4L_MASK_FRAME]; - u32 reg; - - zr->v4l_grab_frame = frame; - - /* Set zr36057 video front end and enable video */ - - /* Buffer address */ - - reg = zr->v4l_buffers.buffer[frame].v4l.fbuffer_bus; - btwrite(reg, ZR36057_VDTR); - if (zr->v4l_settings.height > BUZ_MAX_HEIGHT / 2) - reg += zr->v4l_settings.bytesperline; - btwrite(reg, ZR36057_VDBR); - - /* video stride, status, and frame grab register */ - reg = 0; - if (zr->v4l_settings.height > BUZ_MAX_HEIGHT / 2) - reg += zr->v4l_settings.bytesperline; - reg = (reg << ZR36057_VSSFGR_DispStride); - reg |= ZR36057_VSSFGR_VidOvf; - reg |= ZR36057_VSSFGR_SnapShot; - reg |= ZR36057_VSSFGR_FrameGrab; - btwrite(reg, ZR36057_VSSFGR); - - btor(ZR36057_VDCR_VidEn, - ZR36057_VDCR); - } - } - - /* even if we don't grab, we do want to increment - * the sequence counter to see lost frames */ - zr->v4l_grab_seq++; - } -#if (IRQ_MASK & ZR36057_ISR_CodRepIRQ) - if (astat & ZR36057_ISR_CodRepIRQ) { - zr->intr_counter_CodRepIRQ++; - IDEBUG(printk(KERN_DEBUG "%s: ZR36057_ISR_CodRepIRQ\n", - ZR_DEVNAME(zr))); - btand(~ZR36057_ICR_CodRepIRQ, ZR36057_ICR); - } -#endif /* (IRQ_MASK & ZR36057_ISR_CodRepIRQ) */ - -#if (IRQ_MASK & ZR36057_ISR_JPEGRepIRQ) - if ((astat & ZR36057_ISR_JPEGRepIRQ) && - (zr->codec_mode == BUZ_MODE_MOTION_DECOMPRESS || - zr->codec_mode == BUZ_MODE_MOTION_COMPRESS)) { - if (zr36067_debug > 1 && (!zr->frame_num || zr->JPEG_error)) { - char sv[BUZ_NUM_STAT_COM + 1]; - int i; - - printk(KERN_INFO - "%s: first frame ready: state=0x%08x odd_even=%d field_per_buff=%d delay=%d\n", - ZR_DEVNAME(zr), stat, - zr->jpg_settings.odd_even, - zr->jpg_settings.field_per_buff, - zr->JPEG_missed); - - for (i = 0; i < BUZ_NUM_STAT_COM; i++) - sv[i] = le32_to_cpu(zr->stat_com[i]) & 1 ? '1' : '0'; - sv[BUZ_NUM_STAT_COM] = 0; - printk(KERN_INFO - "%s: stat_com=%s queue_state=%ld/%ld/%ld/%ld\n", - ZR_DEVNAME(zr), sv, - zr->jpg_que_tail, - zr->jpg_dma_tail, - zr->jpg_dma_head, - zr->jpg_que_head); - } else { - /* Get statistics */ - if (zr->JPEG_missed > zr->JPEG_max_missed) - zr->JPEG_max_missed = zr->JPEG_missed; - if (zr->JPEG_missed < zr->JPEG_min_missed) - zr->JPEG_min_missed = zr->JPEG_missed; - } - - if (zr36067_debug > 2 && zr->frame_num < 6) { - int i; - - printk(KERN_INFO "%s: seq=%ld stat_com:", - ZR_DEVNAME(zr), zr->jpg_seq_num); - for (i = 0; i < 4; i++) { - printk(KERN_CONT " %08x", - le32_to_cpu(zr->stat_com[i])); - } - printk(KERN_CONT "\n"); - } - zr->frame_num++; - zr->JPEG_missed = 0; - zr->JPEG_error = 0; - zoran_reap_stat_com(zr); - zoran_feed_stat_com(zr); - wake_up_interruptible(&zr->jpg_capq); - } -#endif /* (IRQ_MASK & ZR36057_ISR_JPEGRepIRQ) */ - - /* DATERR, too many fields missed, error processing */ - if ((astat & zr->card.jpeg_int) || - zr->JPEG_missed > 25 || - zr->JPEG_error == 1 || - ((zr->codec_mode == BUZ_MODE_MOTION_DECOMPRESS) && - (zr->frame_num && (zr->JPEG_missed > zr->jpg_settings.field_per_buff)))) { - error_handler(zr, astat, stat); - } - - count++; - if (count > 10) { - dprintk(2, KERN_WARNING "%s: irq loop %d\n", - ZR_DEVNAME(zr), count); - if (count > 20) { - btand(~ZR36057_ICR_IntPinEn, ZR36057_ICR); - dprintk(2, - KERN_ERR - "%s: IRQ lockup, cleared int mask\n", - ZR_DEVNAME(zr)); - break; - } - } - zr->last_isr = stat; - } - spin_unlock_irqrestore(&zr->spinlock, flags); - - return IRQ_HANDLED; -} - -void -zoran_set_pci_master (struct zoran *zr, - int set_master) -{ - if (set_master) { - pci_set_master(zr->pci_dev); - } else { - u16 command; - - pci_read_config_word(zr->pci_dev, PCI_COMMAND, &command); - command &= ~PCI_COMMAND_MASTER; - pci_write_config_word(zr->pci_dev, PCI_COMMAND, command); - } -} - -void -zoran_init_hardware (struct zoran *zr) -{ - /* Enable bus-mastering */ - zoran_set_pci_master(zr, 1); - - /* Initialize the board */ - if (zr->card.init) { - zr->card.init(zr); - } - - decoder_call(zr, core, init, 0); - decoder_call(zr, video, s_std, zr->norm); - decoder_call(zr, video, s_routing, - zr->card.input[zr->input].muxsel, 0, 0); - - encoder_call(zr, core, init, 0); - encoder_call(zr, video, s_std_output, zr->norm); - encoder_call(zr, video, s_routing, 0, 0, 0); - - /* toggle JPEG codec sleep to sync PLL */ - jpeg_codec_sleep(zr, 1); - jpeg_codec_sleep(zr, 0); - - /* - * set individual interrupt enables (without GIRQ1) - * but don't global enable until zoran_open() - */ - zr36057_init_vfe(zr); - - zr36057_enable_jpg(zr, BUZ_MODE_IDLE); - - btwrite(IRQ_MASK, ZR36057_ISR); // Clears interrupts -} - -void -zr36057_restart (struct zoran *zr) -{ - btwrite(0, ZR36057_SPGPPCR); - mdelay(1); - btor(ZR36057_SPGPPCR_SoftReset, ZR36057_SPGPPCR); - mdelay(1); - - /* assert P_Reset */ - btwrite(0, ZR36057_JPC); - /* set up GPIO direction - all output */ - btwrite(ZR36057_SPGPPCR_SoftReset | 0, ZR36057_SPGPPCR); - - /* set up GPIO pins and guest bus timing */ - btwrite((0x81 << 24) | 0x8888, ZR36057_GPPGCR1); -} - -/* - * initialize video front end - */ - -static void -zr36057_init_vfe (struct zoran *zr) -{ - u32 reg; - - reg = btread(ZR36057_VFESPFR); - reg |= ZR36057_VFESPFR_LittleEndian; - reg &= ~ZR36057_VFESPFR_VCLKPol; - reg |= ZR36057_VFESPFR_ExtFl; - reg |= ZR36057_VFESPFR_TopField; - btwrite(reg, ZR36057_VFESPFR); - reg = btread(ZR36057_VDCR); - if (pci_pci_problems & PCIPCI_TRITON) - // || zr->revision < 1) // Revision 1 has also Triton support - reg &= ~ZR36057_VDCR_Triton; - else - reg |= ZR36057_VDCR_Triton; - btwrite(reg, ZR36057_VDCR); -} diff --git a/drivers/staging/media/zoran/zoran_device.h b/drivers/staging/media/zoran/zoran_device.h deleted file mode 100644 index a507aaad4ebb..000000000000 --- a/drivers/staging/media/zoran/zoran_device.h +++ /dev/null @@ -1,91 +0,0 @@ -/* - * Zoran zr36057/zr36067 PCI controller driver, for the - * Pinnacle/Miro DC10/DC10+/DC30/DC30+, Iomega Buz, Linux - * Media Labs LML33/LML33R10. - * - * This part handles card-specific data and detection - * - * Copyright (C) 2000 Serguei Miridonov - * - * Currently maintained by: - * Ronald Bultje - * Laurent Pinchart - * Mailinglist - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - */ - -#ifndef __ZORAN_DEVICE_H__ -#define __ZORAN_DEVICE_H__ - -/* general purpose I/O */ -extern void GPIO(struct zoran *zr, - int bit, - unsigned int value); - -/* codec (or actually: guest bus) access */ -extern int post_office_wait(struct zoran *zr); -extern int post_office_write(struct zoran *zr, - unsigned guest, - unsigned reg, - unsigned value); -extern int post_office_read(struct zoran *zr, - unsigned guest, - unsigned reg); - -extern void detect_guest_activity(struct zoran *zr); - -extern void jpeg_codec_sleep(struct zoran *zr, - int sleep); -extern int jpeg_codec_reset(struct zoran *zr); - -/* zr360x7 access to raw capture */ -extern void zr36057_overlay(struct zoran *zr, - int on); -extern void write_overlay_mask(struct zoran_fh *fh, - struct v4l2_clip *vp, - int count); -extern void zr36057_set_memgrab(struct zoran *zr, - int mode); -extern int wait_grab_pending(struct zoran *zr); - -/* interrupts */ -extern void print_interrupts(struct zoran *zr); -extern void clear_interrupt_counters(struct zoran *zr); -extern irqreturn_t zoran_irq(int irq, void *dev_id); - -/* JPEG codec access */ -extern void jpeg_start(struct zoran *zr); -extern void zr36057_enable_jpg(struct zoran *zr, - enum zoran_codec_mode mode); -extern void zoran_feed_stat_com(struct zoran *zr); - -/* general */ -extern void zoran_set_pci_master(struct zoran *zr, - int set_master); -extern void zoran_init_hardware(struct zoran *zr); -extern void zr36057_restart(struct zoran *zr); - -extern const struct zoran_format zoran_formats[]; - -extern int v4l_nbufs; -extern int v4l_bufsize; -extern int jpg_nbufs; -extern int jpg_bufsize; -extern int pass_through; - -/* i2c */ -#define decoder_call(zr, o, f, args...) \ - v4l2_subdev_call(zr->decoder, o, f, ##args) -#define encoder_call(zr, o, f, args...) \ - v4l2_subdev_call(zr->encoder, o, f, ##args) - -#endif /* __ZORAN_DEVICE_H__ */ diff --git a/drivers/staging/media/zoran/zoran_driver.c b/drivers/staging/media/zoran/zoran_driver.c deleted file mode 100644 index c998aa4dc73b..000000000000 --- a/drivers/staging/media/zoran/zoran_driver.c +++ /dev/null @@ -1,2850 +0,0 @@ -/* - * Zoran zr36057/zr36067 PCI controller driver, for the - * Pinnacle/Miro DC10/DC10+/DC30/DC30+, Iomega Buz, Linux - * Media Labs LML33/LML33R10. - * - * Copyright (C) 2000 Serguei Miridonov - * - * Changes for BUZ by Wolfgang Scherr - * - * Changes for DC10/DC30 by Laurent Pinchart - * - * Changes for LML33R10 by Maxim Yevtyushkin - * - * Changes for videodev2/v4l2 by Ronald Bultje - * - * Based on - * - * Miro DC10 driver - * Copyright (C) 1999 Wolfgang Scherr - * - * Iomega Buz driver version 1.0 - * Copyright (C) 1999 Rainer Johanni - * - * buz.0.0.3 - * Copyright (C) 1998 Dave Perks - * - * bttv - Bt848 frame grabber driver - * Copyright (C) 1996,97,98 Ralph Metzler (rjkm@thp.uni-koeln.de) - * & Marcus Metzler (mocm@thp.uni-koeln.de) - * - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - */ - -#include -#include -#include -#include -#include -#include -#include - -#include -#include -#include - -#include - -#include -#include -#include -#include -#include "videocodec.h" - -#include -#include -#include -#include - -#include -#include "zoran.h" -#include "zoran_device.h" -#include "zoran_card.h" - - -const struct zoran_format zoran_formats[] = { - { - .name = "15-bit RGB LE", - .fourcc = V4L2_PIX_FMT_RGB555, - .colorspace = V4L2_COLORSPACE_SRGB, - .depth = 15, - .flags = ZORAN_FORMAT_CAPTURE | - ZORAN_FORMAT_OVERLAY, - .vfespfr = ZR36057_VFESPFR_RGB555|ZR36057_VFESPFR_ErrDif| - ZR36057_VFESPFR_LittleEndian, - }, { - .name = "15-bit RGB BE", - .fourcc = V4L2_PIX_FMT_RGB555X, - .colorspace = V4L2_COLORSPACE_SRGB, - .depth = 15, - .flags = ZORAN_FORMAT_CAPTURE | - ZORAN_FORMAT_OVERLAY, - .vfespfr = ZR36057_VFESPFR_RGB555|ZR36057_VFESPFR_ErrDif, - }, { - .name = "16-bit RGB LE", - .fourcc = V4L2_PIX_FMT_RGB565, - .colorspace = V4L2_COLORSPACE_SRGB, - .depth = 16, - .flags = ZORAN_FORMAT_CAPTURE | - ZORAN_FORMAT_OVERLAY, - .vfespfr = ZR36057_VFESPFR_RGB565|ZR36057_VFESPFR_ErrDif| - ZR36057_VFESPFR_LittleEndian, - }, { - .name = "16-bit RGB BE", - .fourcc = V4L2_PIX_FMT_RGB565X, - .colorspace = V4L2_COLORSPACE_SRGB, - .depth = 16, - .flags = ZORAN_FORMAT_CAPTURE | - ZORAN_FORMAT_OVERLAY, - .vfespfr = ZR36057_VFESPFR_RGB565|ZR36057_VFESPFR_ErrDif, - }, { - .name = "24-bit RGB", - .fourcc = V4L2_PIX_FMT_BGR24, - .colorspace = V4L2_COLORSPACE_SRGB, - .depth = 24, - .flags = ZORAN_FORMAT_CAPTURE | - ZORAN_FORMAT_OVERLAY, - .vfespfr = ZR36057_VFESPFR_RGB888|ZR36057_VFESPFR_Pack24, - }, { - .name = "32-bit RGB LE", - .fourcc = V4L2_PIX_FMT_BGR32, - .colorspace = V4L2_COLORSPACE_SRGB, - .depth = 32, - .flags = ZORAN_FORMAT_CAPTURE | - ZORAN_FORMAT_OVERLAY, - .vfespfr = ZR36057_VFESPFR_RGB888|ZR36057_VFESPFR_LittleEndian, - }, { - .name = "32-bit RGB BE", - .fourcc = V4L2_PIX_FMT_RGB32, - .colorspace = V4L2_COLORSPACE_SRGB, - .depth = 32, - .flags = ZORAN_FORMAT_CAPTURE | - ZORAN_FORMAT_OVERLAY, - .vfespfr = ZR36057_VFESPFR_RGB888, - }, { - .name = "4:2:2, packed, YUYV", - .fourcc = V4L2_PIX_FMT_YUYV, - .colorspace = V4L2_COLORSPACE_SMPTE170M, - .depth = 16, - .flags = ZORAN_FORMAT_CAPTURE | - ZORAN_FORMAT_OVERLAY, - .vfespfr = ZR36057_VFESPFR_YUV422, - }, { - .name = "4:2:2, packed, UYVY", - .fourcc = V4L2_PIX_FMT_UYVY, - .colorspace = V4L2_COLORSPACE_SMPTE170M, - .depth = 16, - .flags = ZORAN_FORMAT_CAPTURE | - ZORAN_FORMAT_OVERLAY, - .vfespfr = ZR36057_VFESPFR_YUV422|ZR36057_VFESPFR_LittleEndian, - }, { - .name = "Hardware-encoded Motion-JPEG", - .fourcc = V4L2_PIX_FMT_MJPEG, - .colorspace = V4L2_COLORSPACE_SMPTE170M, - .depth = 0, - .flags = ZORAN_FORMAT_CAPTURE | - ZORAN_FORMAT_PLAYBACK | - ZORAN_FORMAT_COMPRESSED, - } -}; -#define NUM_FORMATS ARRAY_SIZE(zoran_formats) - - /* small helper function for calculating buffersizes for v4l2 - * we calculate the nearest higher power-of-two, which - * will be the recommended buffersize */ -static __u32 -zoran_v4l2_calc_bufsize (struct zoran_jpg_settings *settings) -{ - __u8 div = settings->VerDcm * settings->HorDcm * settings->TmpDcm; - __u32 num = (1024 * 512) / (div); - __u32 result = 2; - - num--; - while (num) { - num >>= 1; - result <<= 1; - } - - if (result > jpg_bufsize) - return jpg_bufsize; - if (result < 8192) - return 8192; - return result; -} - -/* forward references */ -static void v4l_fbuffer_free(struct zoran_fh *fh); -static void jpg_fbuffer_free(struct zoran_fh *fh); - -/* Set mapping mode */ -static void map_mode_raw(struct zoran_fh *fh) -{ - fh->map_mode = ZORAN_MAP_MODE_RAW; - fh->buffers.buffer_size = v4l_bufsize; - fh->buffers.num_buffers = v4l_nbufs; -} -static void map_mode_jpg(struct zoran_fh *fh, int play) -{ - fh->map_mode = play ? ZORAN_MAP_MODE_JPG_PLAY : ZORAN_MAP_MODE_JPG_REC; - fh->buffers.buffer_size = jpg_bufsize; - fh->buffers.num_buffers = jpg_nbufs; -} -static inline const char *mode_name(enum zoran_map_mode mode) -{ - return mode == ZORAN_MAP_MODE_RAW ? "V4L" : "JPG"; -} - -/* - * Allocate the V4L grab buffers - * - * These have to be pysically contiguous. - */ - -static int v4l_fbuffer_alloc(struct zoran_fh *fh) -{ - struct zoran *zr = fh->zr; - int i, off; - unsigned char *mem; - - for (i = 0; i < fh->buffers.num_buffers; i++) { - if (fh->buffers.buffer[i].v4l.fbuffer) - dprintk(2, - KERN_WARNING - "%s: %s - buffer %d already allocated!?\n", - ZR_DEVNAME(zr), __func__, i); - - //udelay(20); - mem = kmalloc(fh->buffers.buffer_size, - GFP_KERNEL | __GFP_NOWARN); - if (!mem) { - dprintk(1, - KERN_ERR - "%s: %s - kmalloc for V4L buf %d failed\n", - ZR_DEVNAME(zr), __func__, i); - v4l_fbuffer_free(fh); - return -ENOBUFS; - } - fh->buffers.buffer[i].v4l.fbuffer = mem; - fh->buffers.buffer[i].v4l.fbuffer_phys = virt_to_phys(mem); - fh->buffers.buffer[i].v4l.fbuffer_bus = virt_to_bus(mem); - for (off = 0; off < fh->buffers.buffer_size; - off += PAGE_SIZE) - SetPageReserved(virt_to_page(mem + off)); - dprintk(4, - KERN_INFO - "%s: %s - V4L frame %d mem %p (bus: 0x%llx)\n", - ZR_DEVNAME(zr), __func__, i, mem, - (unsigned long long)virt_to_bus(mem)); - } - - fh->buffers.allocated = 1; - - return 0; -} - -/* free the V4L grab buffers */ -static void v4l_fbuffer_free(struct zoran_fh *fh) -{ - struct zoran *zr = fh->zr; - int i, off; - unsigned char *mem; - - dprintk(4, KERN_INFO "%s: %s\n", ZR_DEVNAME(zr), __func__); - - for (i = 0; i < fh->buffers.num_buffers; i++) { - if (!fh->buffers.buffer[i].v4l.fbuffer) - continue; - - mem = fh->buffers.buffer[i].v4l.fbuffer; - for (off = 0; off < fh->buffers.buffer_size; - off += PAGE_SIZE) - ClearPageReserved(virt_to_page(mem + off)); - kfree(fh->buffers.buffer[i].v4l.fbuffer); - fh->buffers.buffer[i].v4l.fbuffer = NULL; - } - - fh->buffers.allocated = 0; -} - -/* - * Allocate the MJPEG grab buffers. - * - * If a Natoma chipset is present and this is a revision 1 zr36057, - * each MJPEG buffer needs to be physically contiguous. - * (RJ: This statement is from Dave Perks' original driver, - * I could never check it because I have a zr36067) - * - * RJ: The contents grab buffers needs never be accessed in the driver. - * Therefore there is no need to allocate them with vmalloc in order - * to get a contiguous virtual memory space. - * I don't understand why many other drivers first allocate them with - * vmalloc (which uses internally also get_zeroed_page, but delivers you - * virtual addresses) and then again have to make a lot of efforts - * to get the physical address. - * - * Ben Capper: - * On big-endian architectures (such as ppc) some extra steps - * are needed. When reading and writing to the stat_com array - * and fragment buffers, the device expects to see little- - * endian values. The use of cpu_to_le32() and le32_to_cpu() - * in this function (and one or two others in zoran_device.c) - * ensure that these values are always stored in little-endian - * form, regardless of architecture. The zr36057 does Very Bad - * Things on big endian architectures if the stat_com array - * and fragment buffers are not little-endian. - */ - -static int jpg_fbuffer_alloc(struct zoran_fh *fh) -{ - struct zoran *zr = fh->zr; - int i, j, off; - u8 *mem; - - for (i = 0; i < fh->buffers.num_buffers; i++) { - if (fh->buffers.buffer[i].jpg.frag_tab) - dprintk(2, - KERN_WARNING - "%s: %s - buffer %d already allocated!?\n", - ZR_DEVNAME(zr), __func__, i); - - /* Allocate fragment table for this buffer */ - - mem = (void *)get_zeroed_page(GFP_KERNEL); - if (!mem) { - dprintk(1, - KERN_ERR - "%s: %s - get_zeroed_page (frag_tab) failed for buffer %d\n", - ZR_DEVNAME(zr), __func__, i); - jpg_fbuffer_free(fh); - return -ENOBUFS; - } - fh->buffers.buffer[i].jpg.frag_tab = (__le32 *)mem; - fh->buffers.buffer[i].jpg.frag_tab_bus = virt_to_bus(mem); - - if (fh->buffers.need_contiguous) { - mem = kmalloc(fh->buffers.buffer_size, GFP_KERNEL); - if (mem == NULL) { - dprintk(1, - KERN_ERR - "%s: %s - kmalloc failed for buffer %d\n", - ZR_DEVNAME(zr), __func__, i); - jpg_fbuffer_free(fh); - return -ENOBUFS; - } - fh->buffers.buffer[i].jpg.frag_tab[0] = - cpu_to_le32(virt_to_bus(mem)); - fh->buffers.buffer[i].jpg.frag_tab[1] = - cpu_to_le32((fh->buffers.buffer_size >> 1) | 1); - for (off = 0; off < fh->buffers.buffer_size; off += PAGE_SIZE) - SetPageReserved(virt_to_page(mem + off)); - } else { - /* jpg_bufsize is already page aligned */ - for (j = 0; j < fh->buffers.buffer_size / PAGE_SIZE; j++) { - mem = (void *)get_zeroed_page(GFP_KERNEL); - if (mem == NULL) { - dprintk(1, - KERN_ERR - "%s: %s - get_zeroed_page failed for buffer %d\n", - ZR_DEVNAME(zr), __func__, i); - jpg_fbuffer_free(fh); - return -ENOBUFS; - } - - fh->buffers.buffer[i].jpg.frag_tab[2 * j] = - cpu_to_le32(virt_to_bus(mem)); - fh->buffers.buffer[i].jpg.frag_tab[2 * j + 1] = - cpu_to_le32((PAGE_SIZE >> 2) << 1); - SetPageReserved(virt_to_page(mem)); - } - - fh->buffers.buffer[i].jpg.frag_tab[2 * j - 1] |= cpu_to_le32(1); - } - } - - dprintk(4, - KERN_DEBUG "%s: %s - %d KB allocated\n", - ZR_DEVNAME(zr), __func__, - (fh->buffers.num_buffers * fh->buffers.buffer_size) >> 10); - - fh->buffers.allocated = 1; - - return 0; -} - -/* free the MJPEG grab buffers */ -static void jpg_fbuffer_free(struct zoran_fh *fh) -{ - struct zoran *zr = fh->zr; - int i, j, off; - unsigned char *mem; - __le32 frag_tab; - struct zoran_buffer *buffer; - - dprintk(4, KERN_DEBUG "%s: %s\n", ZR_DEVNAME(zr), __func__); - - for (i = 0, buffer = &fh->buffers.buffer[0]; - i < fh->buffers.num_buffers; i++, buffer++) { - if (!buffer->jpg.frag_tab) - continue; - - if (fh->buffers.need_contiguous) { - frag_tab = buffer->jpg.frag_tab[0]; - - if (frag_tab) { - mem = bus_to_virt(le32_to_cpu(frag_tab)); - for (off = 0; off < fh->buffers.buffer_size; off += PAGE_SIZE) - ClearPageReserved(virt_to_page(mem + off)); - kfree(mem); - buffer->jpg.frag_tab[0] = 0; - buffer->jpg.frag_tab[1] = 0; - } - } else { - for (j = 0; j < fh->buffers.buffer_size / PAGE_SIZE; j++) { - frag_tab = buffer->jpg.frag_tab[2 * j]; - - if (!frag_tab) - break; - ClearPageReserved(virt_to_page(bus_to_virt(le32_to_cpu(frag_tab)))); - free_page((unsigned long)bus_to_virt(le32_to_cpu(frag_tab))); - buffer->jpg.frag_tab[2 * j] = 0; - buffer->jpg.frag_tab[2 * j + 1] = 0; - } - } - - free_page((unsigned long)buffer->jpg.frag_tab); - buffer->jpg.frag_tab = NULL; - } - - fh->buffers.allocated = 0; -} - -/* - * V4L Buffer grabbing - */ - -static int -zoran_v4l_set_format (struct zoran_fh *fh, - int width, - int height, - const struct zoran_format *format) -{ - struct zoran *zr = fh->zr; - int bpp; - - /* Check size and format of the grab wanted */ - - if (height < BUZ_MIN_HEIGHT || width < BUZ_MIN_WIDTH || - height > BUZ_MAX_HEIGHT || width > BUZ_MAX_WIDTH) { - dprintk(1, - KERN_ERR - "%s: %s - wrong frame size (%dx%d)\n", - ZR_DEVNAME(zr), __func__, width, height); - return -EINVAL; - } - - bpp = (format->depth + 7) / 8; - - /* Check against available buffer size */ - if (height * width * bpp > fh->buffers.buffer_size) { - dprintk(1, - KERN_ERR - "%s: %s - video buffer size (%d kB) is too small\n", - ZR_DEVNAME(zr), __func__, fh->buffers.buffer_size >> 10); - return -EINVAL; - } - - /* The video front end needs 4-byte alinged line sizes */ - - if ((bpp == 2 && (width & 1)) || (bpp == 3 && (width & 3))) { - dprintk(1, - KERN_ERR - "%s: %s - wrong frame alignment\n", - ZR_DEVNAME(zr), __func__); - return -EINVAL; - } - - fh->v4l_settings.width = width; - fh->v4l_settings.height = height; - fh->v4l_settings.format = format; - fh->v4l_settings.bytesperline = bpp * fh->v4l_settings.width; - - return 0; -} - -static int zoran_v4l_queue_frame(struct zoran_fh *fh, int num) -{ - struct zoran *zr = fh->zr; - unsigned long flags; - int res = 0; - - if (!fh->buffers.allocated) { - dprintk(1, - KERN_ERR - "%s: %s - buffers not yet allocated\n", - ZR_DEVNAME(zr), __func__); - res = -ENOMEM; - } - - /* No grabbing outside the buffer range! */ - if (num >= fh->buffers.num_buffers || num < 0) { - dprintk(1, - KERN_ERR - "%s: %s - buffer %d is out of range\n", - ZR_DEVNAME(zr), __func__, num); - res = -EINVAL; - } - - spin_lock_irqsave(&zr->spinlock, flags); - - if (fh->buffers.active == ZORAN_FREE) { - if (zr->v4l_buffers.active == ZORAN_FREE) { - zr->v4l_buffers = fh->buffers; - fh->buffers.active = ZORAN_ACTIVE; - } else { - dprintk(1, - KERN_ERR - "%s: %s - another session is already capturing\n", - ZR_DEVNAME(zr), __func__); - res = -EBUSY; - } - } - - /* make sure a grab isn't going on currently with this buffer */ - if (!res) { - switch (zr->v4l_buffers.buffer[num].state) { - default: - case BUZ_STATE_PEND: - if (zr->v4l_buffers.active == ZORAN_FREE) { - fh->buffers.active = ZORAN_FREE; - zr->v4l_buffers.allocated = 0; - } - res = -EBUSY; /* what are you doing? */ - break; - case BUZ_STATE_DONE: - dprintk(2, - KERN_WARNING - "%s: %s - queueing buffer %d in state DONE!?\n", - ZR_DEVNAME(zr), __func__, num); - /* fall through */ - case BUZ_STATE_USER: - /* since there is at least one unused buffer there's room for at least - * one more pend[] entry */ - zr->v4l_pend[zr->v4l_pend_head++ & V4L_MASK_FRAME] = num; - zr->v4l_buffers.buffer[num].state = BUZ_STATE_PEND; - zr->v4l_buffers.buffer[num].bs.length = - fh->v4l_settings.bytesperline * - zr->v4l_settings.height; - fh->buffers.buffer[num] = zr->v4l_buffers.buffer[num]; - break; - } - } - - spin_unlock_irqrestore(&zr->spinlock, flags); - - if (!res && zr->v4l_buffers.active == ZORAN_FREE) - zr->v4l_buffers.active = fh->buffers.active; - - return res; -} - -/* - * Sync on a V4L buffer - */ - -static int v4l_sync(struct zoran_fh *fh, int frame) -{ - struct zoran *zr = fh->zr; - unsigned long flags; - - if (fh->buffers.active == ZORAN_FREE) { - dprintk(1, - KERN_ERR - "%s: %s - no grab active for this session\n", - ZR_DEVNAME(zr), __func__); - return -EINVAL; - } - - /* check passed-in frame number */ - if (frame >= fh->buffers.num_buffers || frame < 0) { - dprintk(1, - KERN_ERR "%s: %s - frame %d is invalid\n", - ZR_DEVNAME(zr), __func__, frame); - return -EINVAL; - } - - /* Check if is buffer was queued at all */ - if (zr->v4l_buffers.buffer[frame].state == BUZ_STATE_USER) { - dprintk(1, - KERN_ERR - "%s: %s - attempt to sync on a buffer which was not queued?\n", - ZR_DEVNAME(zr), __func__); - return -EPROTO; - } - - mutex_unlock(&zr->lock); - /* wait on this buffer to get ready */ - if (!wait_event_interruptible_timeout(zr->v4l_capq, - (zr->v4l_buffers.buffer[frame].state != BUZ_STATE_PEND), 10*HZ)) { - mutex_lock(&zr->lock); - return -ETIME; - } - mutex_lock(&zr->lock); - if (signal_pending(current)) - return -ERESTARTSYS; - - /* buffer should now be in BUZ_STATE_DONE */ - if (zr->v4l_buffers.buffer[frame].state != BUZ_STATE_DONE) - dprintk(2, - KERN_ERR "%s: %s - internal state error\n", - ZR_DEVNAME(zr), __func__); - - zr->v4l_buffers.buffer[frame].state = BUZ_STATE_USER; - fh->buffers.buffer[frame] = zr->v4l_buffers.buffer[frame]; - - spin_lock_irqsave(&zr->spinlock, flags); - - /* Check if streaming capture has finished */ - if (zr->v4l_pend_tail == zr->v4l_pend_head) { - zr36057_set_memgrab(zr, 0); - if (zr->v4l_buffers.active == ZORAN_ACTIVE) { - fh->buffers.active = zr->v4l_buffers.active = ZORAN_FREE; - zr->v4l_buffers.allocated = 0; - } - } - - spin_unlock_irqrestore(&zr->spinlock, flags); - - return 0; -} - -/* - * Queue a MJPEG buffer for capture/playback - */ - -static int zoran_jpg_queue_frame(struct zoran_fh *fh, int num, - enum zoran_codec_mode mode) -{ - struct zoran *zr = fh->zr; - unsigned long flags; - int res = 0; - - /* Check if buffers are allocated */ - if (!fh->buffers.allocated) { - dprintk(1, - KERN_ERR - "%s: %s - buffers not yet allocated\n", - ZR_DEVNAME(zr), __func__); - return -ENOMEM; - } - - /* No grabbing outside the buffer range! */ - if (num >= fh->buffers.num_buffers || num < 0) { - dprintk(1, - KERN_ERR - "%s: %s - buffer %d out of range\n", - ZR_DEVNAME(zr), __func__, num); - return -EINVAL; - } - - /* what is the codec mode right now? */ - if (zr->codec_mode == BUZ_MODE_IDLE) { - zr->jpg_settings = fh->jpg_settings; - } else if (zr->codec_mode != mode) { - /* wrong codec mode active - invalid */ - dprintk(1, - KERN_ERR - "%s: %s - codec in wrong mode\n", - ZR_DEVNAME(zr), __func__); - return -EINVAL; - } - - if (fh->buffers.active == ZORAN_FREE) { - if (zr->jpg_buffers.active == ZORAN_FREE) { - zr->jpg_buffers = fh->buffers; - fh->buffers.active = ZORAN_ACTIVE; - } else { - dprintk(1, - KERN_ERR - "%s: %s - another session is already capturing\n", - ZR_DEVNAME(zr), __func__); - res = -EBUSY; - } - } - - if (!res && zr->codec_mode == BUZ_MODE_IDLE) { - /* Ok load up the jpeg codec */ - zr36057_enable_jpg(zr, mode); - } - - spin_lock_irqsave(&zr->spinlock, flags); - - if (!res) { - switch (zr->jpg_buffers.buffer[num].state) { - case BUZ_STATE_DONE: - dprintk(2, - KERN_WARNING - "%s: %s - queuing frame in BUZ_STATE_DONE state!?\n", - ZR_DEVNAME(zr), __func__); - /* fall through */ - case BUZ_STATE_USER: - /* since there is at least one unused buffer there's room for at - *least one more pend[] entry */ - zr->jpg_pend[zr->jpg_que_head++ & BUZ_MASK_FRAME] = num; - zr->jpg_buffers.buffer[num].state = BUZ_STATE_PEND; - fh->buffers.buffer[num] = zr->jpg_buffers.buffer[num]; - zoran_feed_stat_com(zr); - break; - default: - case BUZ_STATE_DMA: - case BUZ_STATE_PEND: - if (zr->jpg_buffers.active == ZORAN_FREE) { - fh->buffers.active = ZORAN_FREE; - zr->jpg_buffers.allocated = 0; - } - res = -EBUSY; /* what are you doing? */ - break; - } - } - - spin_unlock_irqrestore(&zr->spinlock, flags); - - if (!res && zr->jpg_buffers.active == ZORAN_FREE) - zr->jpg_buffers.active = fh->buffers.active; - - return res; -} - -static int jpg_qbuf(struct zoran_fh *fh, int frame, enum zoran_codec_mode mode) -{ - struct zoran *zr = fh->zr; - int res = 0; - - /* Does the user want to stop streaming? */ - if (frame < 0) { - if (zr->codec_mode == mode) { - if (fh->buffers.active == ZORAN_FREE) { - dprintk(1, - KERN_ERR - "%s: %s(-1) - session not active\n", - ZR_DEVNAME(zr), __func__); - return -EINVAL; - } - fh->buffers.active = zr->jpg_buffers.active = ZORAN_FREE; - zr->jpg_buffers.allocated = 0; - zr36057_enable_jpg(zr, BUZ_MODE_IDLE); - return 0; - } else { - dprintk(1, - KERN_ERR - "%s: %s - stop streaming but not in streaming mode\n", - ZR_DEVNAME(zr), __func__); - return -EINVAL; - } - } - - if ((res = zoran_jpg_queue_frame(fh, frame, mode))) - return res; - - /* Start the jpeg codec when the first frame is queued */ - if (!res && zr->jpg_que_head == 1) - jpeg_start(zr); - - return res; -} - -/* - * Sync on a MJPEG buffer - */ - -static int jpg_sync(struct zoran_fh *fh, struct zoran_sync *bs) -{ - struct zoran *zr = fh->zr; - unsigned long flags; - int frame; - - if (fh->buffers.active == ZORAN_FREE) { - dprintk(1, - KERN_ERR - "%s: %s - capture is not currently active\n", - ZR_DEVNAME(zr), __func__); - return -EINVAL; - } - if (zr->codec_mode != BUZ_MODE_MOTION_DECOMPRESS && - zr->codec_mode != BUZ_MODE_MOTION_COMPRESS) { - dprintk(1, - KERN_ERR - "%s: %s - codec not in streaming mode\n", - ZR_DEVNAME(zr), __func__); - return -EINVAL; - } - mutex_unlock(&zr->lock); - if (!wait_event_interruptible_timeout(zr->jpg_capq, - (zr->jpg_que_tail != zr->jpg_dma_tail || - zr->jpg_dma_tail == zr->jpg_dma_head), - 10*HZ)) { - int isr; - - btand(~ZR36057_JMC_Go_en, ZR36057_JMC); - udelay(1); - zr->codec->control(zr->codec, CODEC_G_STATUS, - sizeof(isr), &isr); - mutex_lock(&zr->lock); - dprintk(1, - KERN_ERR - "%s: %s - timeout: codec isr=0x%02x\n", - ZR_DEVNAME(zr), __func__, isr); - - return -ETIME; - - } - mutex_lock(&zr->lock); - if (signal_pending(current)) - return -ERESTARTSYS; - - spin_lock_irqsave(&zr->spinlock, flags); - - if (zr->jpg_dma_tail != zr->jpg_dma_head) - frame = zr->jpg_pend[zr->jpg_que_tail++ & BUZ_MASK_FRAME]; - else - frame = zr->jpg_pend[zr->jpg_que_tail & BUZ_MASK_FRAME]; - - /* buffer should now be in BUZ_STATE_DONE */ - if (zr->jpg_buffers.buffer[frame].state != BUZ_STATE_DONE) - dprintk(2, - KERN_ERR "%s: %s - internal state error\n", - ZR_DEVNAME(zr), __func__); - - *bs = zr->jpg_buffers.buffer[frame].bs; - bs->frame = frame; - zr->jpg_buffers.buffer[frame].state = BUZ_STATE_USER; - fh->buffers.buffer[frame] = zr->jpg_buffers.buffer[frame]; - - spin_unlock_irqrestore(&zr->spinlock, flags); - - return 0; -} - -static void zoran_open_init_session(struct zoran_fh *fh) -{ - int i; - struct zoran *zr = fh->zr; - - /* Per default, map the V4L Buffers */ - map_mode_raw(fh); - - /* take over the card's current settings */ - fh->overlay_settings = zr->overlay_settings; - fh->overlay_settings.is_set = 0; - fh->overlay_settings.format = zr->overlay_settings.format; - fh->overlay_active = ZORAN_FREE; - - /* v4l settings */ - fh->v4l_settings = zr->v4l_settings; - /* jpg settings */ - fh->jpg_settings = zr->jpg_settings; - - /* buffers */ - memset(&fh->buffers, 0, sizeof(fh->buffers)); - for (i = 0; i < MAX_FRAME; i++) { - fh->buffers.buffer[i].state = BUZ_STATE_USER; /* nothing going on */ - fh->buffers.buffer[i].bs.frame = i; - } - fh->buffers.allocated = 0; - fh->buffers.active = ZORAN_FREE; -} - -static void zoran_close_end_session(struct zoran_fh *fh) -{ - struct zoran *zr = fh->zr; - - /* overlay */ - if (fh->overlay_active != ZORAN_FREE) { - fh->overlay_active = zr->overlay_active = ZORAN_FREE; - zr->v4l_overlay_active = 0; - if (!zr->v4l_memgrab_active) - zr36057_overlay(zr, 0); - zr->overlay_mask = NULL; - } - - if (fh->map_mode == ZORAN_MAP_MODE_RAW) { - /* v4l capture */ - if (fh->buffers.active != ZORAN_FREE) { - unsigned long flags; - - spin_lock_irqsave(&zr->spinlock, flags); - zr36057_set_memgrab(zr, 0); - zr->v4l_buffers.allocated = 0; - zr->v4l_buffers.active = fh->buffers.active = ZORAN_FREE; - spin_unlock_irqrestore(&zr->spinlock, flags); - } - - /* v4l buffers */ - if (fh->buffers.allocated) - v4l_fbuffer_free(fh); - } else { - /* jpg capture */ - if (fh->buffers.active != ZORAN_FREE) { - zr36057_enable_jpg(zr, BUZ_MODE_IDLE); - zr->jpg_buffers.allocated = 0; - zr->jpg_buffers.active = fh->buffers.active = ZORAN_FREE; - } - - /* jpg buffers */ - if (fh->buffers.allocated) - jpg_fbuffer_free(fh); - } -} - -/* - * Open a zoran card. Right now the flags stuff is just playing - */ - -static int zoran_open(struct file *file) -{ - struct zoran *zr = video_drvdata(file); - struct zoran_fh *fh; - int res, first_open = 0; - - dprintk(2, KERN_INFO "%s: %s(%s, pid=[%d]), users(-)=%d\n", - ZR_DEVNAME(zr), __func__, current->comm, task_pid_nr(current), zr->user + 1); - - mutex_lock(&zr->lock); - - if (zr->user >= 2048) { - dprintk(1, KERN_ERR "%s: too many users (%d) on device\n", - ZR_DEVNAME(zr), zr->user); - res = -EBUSY; - goto fail_unlock; - } - - /* now, create the open()-specific file_ops struct */ - fh = kzalloc(sizeof(struct zoran_fh), GFP_KERNEL); - if (!fh) { - dprintk(1, - KERN_ERR - "%s: %s - allocation of zoran_fh failed\n", - ZR_DEVNAME(zr), __func__); - res = -ENOMEM; - goto fail_unlock; - } - v4l2_fh_init(&fh->fh, video_devdata(file)); - - /* used to be BUZ_MAX_WIDTH/HEIGHT, but that gives overflows - * on norm-change! */ - fh->overlay_mask = - kmalloc(array3_size((768 + 31) / 32, 576, 4), GFP_KERNEL); - if (!fh->overlay_mask) { - dprintk(1, - KERN_ERR - "%s: %s - allocation of overlay_mask failed\n", - ZR_DEVNAME(zr), __func__); - res = -ENOMEM; - goto fail_fh; - } - - if (zr->user++ == 0) - first_open = 1; - - /* default setup - TODO: look at flags */ - if (first_open) { /* First device open */ - zr36057_restart(zr); - zoran_open_init_params(zr); - zoran_init_hardware(zr); - - btor(ZR36057_ICR_IntPinEn, ZR36057_ICR); - } - - /* set file_ops stuff */ - file->private_data = fh; - fh->zr = zr; - zoran_open_init_session(fh); - v4l2_fh_add(&fh->fh); - mutex_unlock(&zr->lock); - - return 0; - -fail_fh: - v4l2_fh_exit(&fh->fh); - kfree(fh); -fail_unlock: - mutex_unlock(&zr->lock); - - dprintk(2, KERN_INFO "%s: open failed (%d), users(-)=%d\n", - ZR_DEVNAME(zr), res, zr->user); - - return res; -} - -static int -zoran_close(struct file *file) -{ - struct zoran_fh *fh = file->private_data; - struct zoran *zr = fh->zr; - - dprintk(2, KERN_INFO "%s: %s(%s, pid=[%d]), users(+)=%d\n", - ZR_DEVNAME(zr), __func__, current->comm, task_pid_nr(current), zr->user - 1); - - /* kernel locks (fs/device.c), so don't do that ourselves - * (prevents deadlocks) */ - mutex_lock(&zr->lock); - - zoran_close_end_session(fh); - - if (zr->user-- == 1) { /* Last process */ - /* Clean up JPEG process */ - wake_up_interruptible(&zr->jpg_capq); - zr36057_enable_jpg(zr, BUZ_MODE_IDLE); - zr->jpg_buffers.allocated = 0; - zr->jpg_buffers.active = ZORAN_FREE; - - /* disable interrupts */ - btand(~ZR36057_ICR_IntPinEn, ZR36057_ICR); - - if (zr36067_debug > 1) - print_interrupts(zr); - - /* Overlay off */ - zr->v4l_overlay_active = 0; - zr36057_overlay(zr, 0); - zr->overlay_mask = NULL; - - /* capture off */ - wake_up_interruptible(&zr->v4l_capq); - zr36057_set_memgrab(zr, 0); - zr->v4l_buffers.allocated = 0; - zr->v4l_buffers.active = ZORAN_FREE; - zoran_set_pci_master(zr, 0); - - if (!pass_through) { /* Switch to color bar */ - decoder_call(zr, video, s_stream, 0); - encoder_call(zr, video, s_routing, 2, 0, 0); - } - } - mutex_unlock(&zr->lock); - - v4l2_fh_del(&fh->fh); - v4l2_fh_exit(&fh->fh); - kfree(fh->overlay_mask); - kfree(fh); - - dprintk(4, KERN_INFO "%s: %s done\n", ZR_DEVNAME(zr), __func__); - - return 0; -} - -static int setup_fbuffer(struct zoran_fh *fh, - void *base, - const struct zoran_format *fmt, - int width, - int height, - int bytesperline) -{ - struct zoran *zr = fh->zr; - - /* (Ronald) v4l/v4l2 guidelines */ - if (!capable(CAP_SYS_ADMIN) && !capable(CAP_SYS_RAWIO)) - return -EPERM; - - /* Don't allow frame buffer overlay if PCI or AGP is buggy, or on - ALi Magik (that needs very low latency while the card needs a - higher value always) */ - - if (pci_pci_problems & (PCIPCI_FAIL | PCIAGP_FAIL | PCIPCI_ALIMAGIK)) - return -ENXIO; - - /* we need a bytesperline value, even if not given */ - if (!bytesperline) - bytesperline = width * ((fmt->depth + 7) & ~7) / 8; - -#if 0 - if (zr->overlay_active) { - /* dzjee... stupid users... don't even bother to turn off - * overlay before changing the memory location... - * normally, we would return errors here. However, one of - * the tools that does this is... xawtv! and since xawtv - * is used by +/- 99% of the users, we'd rather be user- - * friendly and silently do as if nothing went wrong */ - dprintk(3, - KERN_ERR - "%s: %s - forced overlay turnoff because framebuffer changed\n", - ZR_DEVNAME(zr), __func__); - zr36057_overlay(zr, 0); - } -#endif - - if (!(fmt->flags & ZORAN_FORMAT_OVERLAY)) { - dprintk(1, - KERN_ERR - "%s: %s - no valid overlay format given\n", - ZR_DEVNAME(zr), __func__); - return -EINVAL; - } - if (height <= 0 || width <= 0 || bytesperline <= 0) { - dprintk(1, - KERN_ERR - "%s: %s - invalid height/width/bpl value (%d|%d|%d)\n", - ZR_DEVNAME(zr), __func__, width, height, bytesperline); - return -EINVAL; - } - if (bytesperline & 3) { - dprintk(1, - KERN_ERR - "%s: %s - bytesperline (%d) must be 4-byte aligned\n", - ZR_DEVNAME(zr), __func__, bytesperline); - return -EINVAL; - } - - zr->vbuf_base = (void *) ((unsigned long) base & ~3); - zr->vbuf_height = height; - zr->vbuf_width = width; - zr->vbuf_depth = fmt->depth; - zr->overlay_settings.format = fmt; - zr->vbuf_bytesperline = bytesperline; - - /* The user should set new window parameters */ - zr->overlay_settings.is_set = 0; - - return 0; -} - - -static int setup_window(struct zoran_fh *fh, - int x, - int y, - int width, - int height, - struct v4l2_clip __user *clips, - unsigned int clipcount, - void __user *bitmap) -{ - struct zoran *zr = fh->zr; - struct v4l2_clip *vcp = NULL; - int on, end; - - - if (!zr->vbuf_base) { - dprintk(1, - KERN_ERR - "%s: %s - frame buffer has to be set first\n", - ZR_DEVNAME(zr), __func__); - return -EINVAL; - } - - if (!fh->overlay_settings.format) { - dprintk(1, - KERN_ERR - "%s: %s - no overlay format set\n", - ZR_DEVNAME(zr), __func__); - return -EINVAL; - } - - if (clipcount > 2048) { - dprintk(1, - KERN_ERR - "%s: %s - invalid clipcount\n", - ZR_DEVNAME(zr), __func__); - return -EINVAL; - } - - /* - * The video front end needs 4-byte alinged line sizes, we correct that - * silently here if necessary - */ - if (zr->vbuf_depth == 15 || zr->vbuf_depth == 16) { - end = (x + width) & ~1; /* round down */ - x = (x + 1) & ~1; /* round up */ - width = end - x; - } - - if (zr->vbuf_depth == 24) { - end = (x + width) & ~3; /* round down */ - x = (x + 3) & ~3; /* round up */ - width = end - x; - } - - if (width > BUZ_MAX_WIDTH) - width = BUZ_MAX_WIDTH; - if (height > BUZ_MAX_HEIGHT) - height = BUZ_MAX_HEIGHT; - - /* Check for invalid parameters */ - if (width < BUZ_MIN_WIDTH || height < BUZ_MIN_HEIGHT || - width > BUZ_MAX_WIDTH || height > BUZ_MAX_HEIGHT) { - dprintk(1, - KERN_ERR - "%s: %s - width = %d or height = %d invalid\n", - ZR_DEVNAME(zr), __func__, width, height); - return -EINVAL; - } - - fh->overlay_settings.x = x; - fh->overlay_settings.y = y; - fh->overlay_settings.width = width; - fh->overlay_settings.height = height; - fh->overlay_settings.clipcount = clipcount; - - /* - * If an overlay is running, we have to switch it off - * and switch it on again in order to get the new settings in effect. - * - * We also want to avoid that the overlay mask is written - * when an overlay is running. - */ - - on = zr->v4l_overlay_active && !zr->v4l_memgrab_active && - zr->overlay_active != ZORAN_FREE && - fh->overlay_active != ZORAN_FREE; - if (on) - zr36057_overlay(zr, 0); - - /* - * Write the overlay mask if clips are wanted. - * We prefer a bitmap. - */ - if (bitmap) { - /* fake value - it just means we want clips */ - fh->overlay_settings.clipcount = 1; - - if (copy_from_user(fh->overlay_mask, bitmap, - (width * height + 7) / 8)) { - return -EFAULT; - } - } else if (clipcount) { - /* write our own bitmap from the clips */ - vcp = vmalloc(array_size(sizeof(struct v4l2_clip), - clipcount + 4)); - if (vcp == NULL) { - dprintk(1, - KERN_ERR - "%s: %s - Alloc of clip mask failed\n", - ZR_DEVNAME(zr), __func__); - return -ENOMEM; - } - if (copy_from_user - (vcp, clips, sizeof(struct v4l2_clip) * clipcount)) { - vfree(vcp); - return -EFAULT; - } - write_overlay_mask(fh, vcp, clipcount); - vfree(vcp); - } - - fh->overlay_settings.is_set = 1; - if (fh->overlay_active != ZORAN_FREE && - zr->overlay_active != ZORAN_FREE) - zr->overlay_settings = fh->overlay_settings; - - if (on) - zr36057_overlay(zr, 1); - - /* Make sure the changes come into effect */ - return wait_grab_pending(zr); -} - -static int setup_overlay(struct zoran_fh *fh, int on) -{ - struct zoran *zr = fh->zr; - - /* If there is nothing to do, return immediately */ - if ((on && fh->overlay_active != ZORAN_FREE) || - (!on && fh->overlay_active == ZORAN_FREE)) - return 0; - - /* check whether we're touching someone else's overlay */ - if (on && zr->overlay_active != ZORAN_FREE && - fh->overlay_active == ZORAN_FREE) { - dprintk(1, - KERN_ERR - "%s: %s - overlay is already active for another session\n", - ZR_DEVNAME(zr), __func__); - return -EBUSY; - } - if (!on && zr->overlay_active != ZORAN_FREE && - fh->overlay_active == ZORAN_FREE) { - dprintk(1, - KERN_ERR - "%s: %s - you cannot cancel someone else's session\n", - ZR_DEVNAME(zr), __func__); - return -EPERM; - } - - if (on == 0) { - zr->overlay_active = fh->overlay_active = ZORAN_FREE; - zr->v4l_overlay_active = 0; - /* When a grab is running, the video simply - * won't be switched on any more */ - if (!zr->v4l_memgrab_active) - zr36057_overlay(zr, 0); - zr->overlay_mask = NULL; - } else { - if (!zr->vbuf_base || !fh->overlay_settings.is_set) { - dprintk(1, - KERN_ERR - "%s: %s - buffer or window not set\n", - ZR_DEVNAME(zr), __func__); - return -EINVAL; - } - if (!fh->overlay_settings.format) { - dprintk(1, - KERN_ERR - "%s: %s - no overlay format set\n", - ZR_DEVNAME(zr), __func__); - return -EINVAL; - } - zr->overlay_active = fh->overlay_active = ZORAN_LOCKED; - zr->v4l_overlay_active = 1; - zr->overlay_mask = fh->overlay_mask; - zr->overlay_settings = fh->overlay_settings; - if (!zr->v4l_memgrab_active) - zr36057_overlay(zr, 1); - /* When a grab is running, the video will be - * switched on when grab is finished */ - } - - /* Make sure the changes come into effect */ - return wait_grab_pending(zr); -} - -/* get the status of a buffer in the clients buffer queue */ -static int zoran_v4l2_buffer_status(struct zoran_fh *fh, - struct v4l2_buffer *buf, int num) -{ - struct zoran *zr = fh->zr; - unsigned long flags; - - buf->flags = V4L2_BUF_FLAG_MAPPED | V4L2_BUF_FLAG_TIMESTAMP_MONOTONIC; - - switch (fh->map_mode) { - case ZORAN_MAP_MODE_RAW: - /* check range */ - if (num < 0 || num >= fh->buffers.num_buffers || - !fh->buffers.allocated) { - dprintk(1, - KERN_ERR - "%s: %s - wrong number or buffers not allocated\n", - ZR_DEVNAME(zr), __func__); - return -EINVAL; - } - - spin_lock_irqsave(&zr->spinlock, flags); - dprintk(3, - KERN_DEBUG - "%s: %s() - raw active=%c, buffer %d: state=%c, map=%c\n", - ZR_DEVNAME(zr), __func__, - "FAL"[fh->buffers.active], num, - "UPMD"[zr->v4l_buffers.buffer[num].state], - fh->buffers.buffer[num].map ? 'Y' : 'N'); - spin_unlock_irqrestore(&zr->spinlock, flags); - - buf->type = V4L2_BUF_TYPE_VIDEO_CAPTURE; - buf->length = fh->buffers.buffer_size; - - /* get buffer */ - buf->bytesused = fh->buffers.buffer[num].bs.length; - if (fh->buffers.buffer[num].state == BUZ_STATE_DONE || - fh->buffers.buffer[num].state == BUZ_STATE_USER) { - buf->sequence = fh->buffers.buffer[num].bs.seq; - buf->flags |= V4L2_BUF_FLAG_DONE; - buf->timestamp = ns_to_timeval(fh->buffers.buffer[num].bs.ts); - } else { - buf->flags |= V4L2_BUF_FLAG_QUEUED; - } - - if (fh->v4l_settings.height <= BUZ_MAX_HEIGHT / 2) - buf->field = V4L2_FIELD_TOP; - else - buf->field = V4L2_FIELD_INTERLACED; - - break; - - case ZORAN_MAP_MODE_JPG_REC: - case ZORAN_MAP_MODE_JPG_PLAY: - - /* check range */ - if (num < 0 || num >= fh->buffers.num_buffers || - !fh->buffers.allocated) { - dprintk(1, - KERN_ERR - "%s: %s - wrong number or buffers not allocated\n", - ZR_DEVNAME(zr), __func__); - return -EINVAL; - } - - buf->type = (fh->map_mode == ZORAN_MAP_MODE_JPG_REC) ? - V4L2_BUF_TYPE_VIDEO_CAPTURE : - V4L2_BUF_TYPE_VIDEO_OUTPUT; - buf->length = fh->buffers.buffer_size; - - /* these variables are only written after frame has been captured */ - if (fh->buffers.buffer[num].state == BUZ_STATE_DONE || - fh->buffers.buffer[num].state == BUZ_STATE_USER) { - buf->sequence = fh->buffers.buffer[num].bs.seq; - buf->timestamp = ns_to_timeval(fh->buffers.buffer[num].bs.ts); - buf->bytesused = fh->buffers.buffer[num].bs.length; - buf->flags |= V4L2_BUF_FLAG_DONE; - } else { - buf->flags |= V4L2_BUF_FLAG_QUEUED; - } - - /* which fields are these? */ - if (fh->jpg_settings.TmpDcm != 1) - buf->field = fh->jpg_settings.odd_even ? - V4L2_FIELD_TOP : V4L2_FIELD_BOTTOM; - else - buf->field = fh->jpg_settings.odd_even ? - V4L2_FIELD_SEQ_TB : V4L2_FIELD_SEQ_BT; - - break; - - default: - - dprintk(5, - KERN_ERR - "%s: %s - invalid buffer type|map_mode (%d|%d)\n", - ZR_DEVNAME(zr), __func__, buf->type, fh->map_mode); - return -EINVAL; - } - - buf->memory = V4L2_MEMORY_MMAP; - buf->index = num; - buf->m.offset = buf->length * num; - - return 0; -} - -static int -zoran_set_norm (struct zoran *zr, - v4l2_std_id norm) -{ - int on; - - if (zr->v4l_buffers.active != ZORAN_FREE || - zr->jpg_buffers.active != ZORAN_FREE) { - dprintk(1, - KERN_WARNING - "%s: %s called while in playback/capture mode\n", - ZR_DEVNAME(zr), __func__); - return -EBUSY; - } - - if (!(norm & zr->card.norms)) { - dprintk(1, - KERN_ERR "%s: %s - unsupported norm %llx\n", - ZR_DEVNAME(zr), __func__, norm); - return -EINVAL; - } - - if (norm & V4L2_STD_SECAM) - zr->timing = zr->card.tvn[2]; - else if (norm & V4L2_STD_NTSC) - zr->timing = zr->card.tvn[1]; - else - zr->timing = zr->card.tvn[0]; - - /* We switch overlay off and on since a change in the - * norm needs different VFE settings */ - on = zr->overlay_active && !zr->v4l_memgrab_active; - if (on) - zr36057_overlay(zr, 0); - - decoder_call(zr, video, s_std, norm); - encoder_call(zr, video, s_std_output, norm); - - if (on) - zr36057_overlay(zr, 1); - - /* Make sure the changes come into effect */ - zr->norm = norm; - - return 0; -} - -static int -zoran_set_input (struct zoran *zr, - int input) -{ - if (input == zr->input) { - return 0; - } - - if (zr->v4l_buffers.active != ZORAN_FREE || - zr->jpg_buffers.active != ZORAN_FREE) { - dprintk(1, - KERN_WARNING - "%s: %s called while in playback/capture mode\n", - ZR_DEVNAME(zr), __func__); - return -EBUSY; - } - - if (input < 0 || input >= zr->card.inputs) { - dprintk(1, - KERN_ERR - "%s: %s - unsupported input %d\n", - ZR_DEVNAME(zr), __func__, input); - return -EINVAL; - } - - zr->input = input; - - decoder_call(zr, video, s_routing, - zr->card.input[input].muxsel, 0, 0); - - return 0; -} - -/* - * ioctl routine - */ - -static int zoran_querycap(struct file *file, void *__fh, struct v4l2_capability *cap) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - - strscpy(cap->card, ZR_DEVNAME(zr), sizeof(cap->card)); - strscpy(cap->driver, "zoran", sizeof(cap->driver)); - snprintf(cap->bus_info, sizeof(cap->bus_info), "PCI:%s", - pci_name(zr->pci_dev)); - cap->device_caps = V4L2_CAP_STREAMING | V4L2_CAP_VIDEO_CAPTURE | - V4L2_CAP_VIDEO_OUTPUT | V4L2_CAP_VIDEO_OVERLAY; - cap->capabilities = cap->device_caps | V4L2_CAP_DEVICE_CAPS; - return 0; -} - -static int zoran_enum_fmt(struct zoran *zr, struct v4l2_fmtdesc *fmt, int flag) -{ - unsigned int num, i; - - for (num = i = 0; i < NUM_FORMATS; i++) { - if (zoran_formats[i].flags & flag && num++ == fmt->index) { - strscpy(fmt->description, zoran_formats[i].name, - sizeof(fmt->description)); - /* fmt struct pre-zeroed, so adding '\0' not needed */ - fmt->pixelformat = zoran_formats[i].fourcc; - if (zoran_formats[i].flags & ZORAN_FORMAT_COMPRESSED) - fmt->flags |= V4L2_FMT_FLAG_COMPRESSED; - return 0; - } - } - return -EINVAL; -} - -static int zoran_enum_fmt_vid_cap(struct file *file, void *__fh, - struct v4l2_fmtdesc *f) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - - return zoran_enum_fmt(zr, f, ZORAN_FORMAT_CAPTURE); -} - -static int zoran_enum_fmt_vid_out(struct file *file, void *__fh, - struct v4l2_fmtdesc *f) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - - return zoran_enum_fmt(zr, f, ZORAN_FORMAT_PLAYBACK); -} - -static int zoran_enum_fmt_vid_overlay(struct file *file, void *__fh, - struct v4l2_fmtdesc *f) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - - return zoran_enum_fmt(zr, f, ZORAN_FORMAT_OVERLAY); -} - -static int zoran_g_fmt_vid_out(struct file *file, void *__fh, - struct v4l2_format *fmt) -{ - struct zoran_fh *fh = __fh; - - fmt->fmt.pix.width = fh->jpg_settings.img_width / fh->jpg_settings.HorDcm; - fmt->fmt.pix.height = fh->jpg_settings.img_height * 2 / - (fh->jpg_settings.VerDcm * fh->jpg_settings.TmpDcm); - fmt->fmt.pix.sizeimage = zoran_v4l2_calc_bufsize(&fh->jpg_settings); - fmt->fmt.pix.pixelformat = V4L2_PIX_FMT_MJPEG; - if (fh->jpg_settings.TmpDcm == 1) - fmt->fmt.pix.field = (fh->jpg_settings.odd_even ? - V4L2_FIELD_SEQ_TB : V4L2_FIELD_SEQ_BT); - else - fmt->fmt.pix.field = (fh->jpg_settings.odd_even ? - V4L2_FIELD_TOP : V4L2_FIELD_BOTTOM); - fmt->fmt.pix.bytesperline = 0; - fmt->fmt.pix.colorspace = V4L2_COLORSPACE_SMPTE170M; - - return 0; -} - -static int zoran_g_fmt_vid_cap(struct file *file, void *__fh, - struct v4l2_format *fmt) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - - if (fh->map_mode != ZORAN_MAP_MODE_RAW) - return zoran_g_fmt_vid_out(file, fh, fmt); - - fmt->fmt.pix.width = fh->v4l_settings.width; - fmt->fmt.pix.height = fh->v4l_settings.height; - fmt->fmt.pix.sizeimage = fh->v4l_settings.bytesperline * - fh->v4l_settings.height; - fmt->fmt.pix.pixelformat = fh->v4l_settings.format->fourcc; - fmt->fmt.pix.colorspace = fh->v4l_settings.format->colorspace; - fmt->fmt.pix.bytesperline = fh->v4l_settings.bytesperline; - if (BUZ_MAX_HEIGHT < (fh->v4l_settings.height * 2)) - fmt->fmt.pix.field = V4L2_FIELD_INTERLACED; - else - fmt->fmt.pix.field = V4L2_FIELD_TOP; - return 0; -} - -static int zoran_g_fmt_vid_overlay(struct file *file, void *__fh, - struct v4l2_format *fmt) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - - fmt->fmt.win.w.left = fh->overlay_settings.x; - fmt->fmt.win.w.top = fh->overlay_settings.y; - fmt->fmt.win.w.width = fh->overlay_settings.width; - fmt->fmt.win.w.height = fh->overlay_settings.height; - if (fh->overlay_settings.width * 2 > BUZ_MAX_HEIGHT) - fmt->fmt.win.field = V4L2_FIELD_INTERLACED; - else - fmt->fmt.win.field = V4L2_FIELD_TOP; - - return 0; -} - -static int zoran_try_fmt_vid_overlay(struct file *file, void *__fh, - struct v4l2_format *fmt) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - - if (fmt->fmt.win.w.width > BUZ_MAX_WIDTH) - fmt->fmt.win.w.width = BUZ_MAX_WIDTH; - if (fmt->fmt.win.w.width < BUZ_MIN_WIDTH) - fmt->fmt.win.w.width = BUZ_MIN_WIDTH; - if (fmt->fmt.win.w.height > BUZ_MAX_HEIGHT) - fmt->fmt.win.w.height = BUZ_MAX_HEIGHT; - if (fmt->fmt.win.w.height < BUZ_MIN_HEIGHT) - fmt->fmt.win.w.height = BUZ_MIN_HEIGHT; - - return 0; -} - -static int zoran_try_fmt_vid_out(struct file *file, void *__fh, - struct v4l2_format *fmt) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - struct zoran_jpg_settings settings; - int res = 0; - - if (fmt->fmt.pix.pixelformat != V4L2_PIX_FMT_MJPEG) - return -EINVAL; - - settings = fh->jpg_settings; - - /* we actually need to set 'real' parameters now */ - if ((fmt->fmt.pix.height * 2) > BUZ_MAX_HEIGHT) - settings.TmpDcm = 1; - else - settings.TmpDcm = 2; - settings.decimation = 0; - if (fmt->fmt.pix.height <= fh->jpg_settings.img_height / 2) - settings.VerDcm = 2; - else - settings.VerDcm = 1; - if (fmt->fmt.pix.width <= fh->jpg_settings.img_width / 4) - settings.HorDcm = 4; - else if (fmt->fmt.pix.width <= fh->jpg_settings.img_width / 2) - settings.HorDcm = 2; - else - settings.HorDcm = 1; - if (settings.TmpDcm == 1) - settings.field_per_buff = 2; - else - settings.field_per_buff = 1; - - if (settings.HorDcm > 1) { - settings.img_x = (BUZ_MAX_WIDTH == 720) ? 8 : 0; - settings.img_width = (BUZ_MAX_WIDTH == 720) ? 704 : BUZ_MAX_WIDTH; - } else { - settings.img_x = 0; - settings.img_width = BUZ_MAX_WIDTH; - } - - /* check */ - res = zoran_check_jpg_settings(zr, &settings, 1); - if (res) - return res; - - /* tell the user what we actually did */ - fmt->fmt.pix.width = settings.img_width / settings.HorDcm; - fmt->fmt.pix.height = settings.img_height * 2 / - (settings.TmpDcm * settings.VerDcm); - if (settings.TmpDcm == 1) - fmt->fmt.pix.field = (fh->jpg_settings.odd_even ? - V4L2_FIELD_SEQ_TB : V4L2_FIELD_SEQ_BT); - else - fmt->fmt.pix.field = (fh->jpg_settings.odd_even ? - V4L2_FIELD_TOP : V4L2_FIELD_BOTTOM); - - fmt->fmt.pix.sizeimage = zoran_v4l2_calc_bufsize(&settings); - fmt->fmt.pix.bytesperline = 0; - fmt->fmt.pix.colorspace = V4L2_COLORSPACE_SMPTE170M; - return res; -} - -static int zoran_try_fmt_vid_cap(struct file *file, void *__fh, - struct v4l2_format *fmt) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - int bpp; - int i; - - if (fmt->fmt.pix.pixelformat == V4L2_PIX_FMT_MJPEG) - return zoran_try_fmt_vid_out(file, fh, fmt); - - for (i = 0; i < NUM_FORMATS; i++) - if (zoran_formats[i].fourcc == fmt->fmt.pix.pixelformat) - break; - - if (i == NUM_FORMATS) - return -EINVAL; - - bpp = DIV_ROUND_UP(zoran_formats[i].depth, 8); - v4l_bound_align_image( - &fmt->fmt.pix.width, BUZ_MIN_WIDTH, BUZ_MAX_WIDTH, bpp == 2 ? 1 : 2, - &fmt->fmt.pix.height, BUZ_MIN_HEIGHT, BUZ_MAX_HEIGHT, 0, 0); - return 0; -} - -static int zoran_s_fmt_vid_overlay(struct file *file, void *__fh, - struct v4l2_format *fmt) -{ - struct zoran_fh *fh = __fh; - int res; - - dprintk(3, "x=%d, y=%d, w=%d, h=%d, cnt=%d, map=0x%p\n", - fmt->fmt.win.w.left, fmt->fmt.win.w.top, - fmt->fmt.win.w.width, - fmt->fmt.win.w.height, - fmt->fmt.win.clipcount, - fmt->fmt.win.bitmap); - res = setup_window(fh, fmt->fmt.win.w.left, fmt->fmt.win.w.top, - fmt->fmt.win.w.width, fmt->fmt.win.w.height, - (struct v4l2_clip __user *)fmt->fmt.win.clips, - fmt->fmt.win.clipcount, fmt->fmt.win.bitmap); - return res; -} - -static int zoran_s_fmt_vid_out(struct file *file, void *__fh, - struct v4l2_format *fmt) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - __le32 printformat = __cpu_to_le32(fmt->fmt.pix.pixelformat); - struct zoran_jpg_settings settings; - int res = 0; - - dprintk(3, "size=%dx%d, fmt=0x%x (%4.4s)\n", - fmt->fmt.pix.width, fmt->fmt.pix.height, - fmt->fmt.pix.pixelformat, - (char *) &printformat); - if (fmt->fmt.pix.pixelformat != V4L2_PIX_FMT_MJPEG) - return -EINVAL; - - if (fh->buffers.allocated) { - dprintk(1, KERN_ERR "%s: VIDIOC_S_FMT - cannot change capture mode\n", - ZR_DEVNAME(zr)); - res = -EBUSY; - return res; - } - - settings = fh->jpg_settings; - - /* we actually need to set 'real' parameters now */ - if (fmt->fmt.pix.height * 2 > BUZ_MAX_HEIGHT) - settings.TmpDcm = 1; - else - settings.TmpDcm = 2; - settings.decimation = 0; - if (fmt->fmt.pix.height <= fh->jpg_settings.img_height / 2) - settings.VerDcm = 2; - else - settings.VerDcm = 1; - if (fmt->fmt.pix.width <= fh->jpg_settings.img_width / 4) - settings.HorDcm = 4; - else if (fmt->fmt.pix.width <= fh->jpg_settings.img_width / 2) - settings.HorDcm = 2; - else - settings.HorDcm = 1; - if (settings.TmpDcm == 1) - settings.field_per_buff = 2; - else - settings.field_per_buff = 1; - - if (settings.HorDcm > 1) { - settings.img_x = (BUZ_MAX_WIDTH == 720) ? 8 : 0; - settings.img_width = (BUZ_MAX_WIDTH == 720) ? 704 : BUZ_MAX_WIDTH; - } else { - settings.img_x = 0; - settings.img_width = BUZ_MAX_WIDTH; - } - - /* check */ - res = zoran_check_jpg_settings(zr, &settings, 0); - if (res) - return res; - - /* it's ok, so set them */ - fh->jpg_settings = settings; - - map_mode_jpg(fh, fmt->type == V4L2_BUF_TYPE_VIDEO_OUTPUT); - fh->buffers.buffer_size = zoran_v4l2_calc_bufsize(&fh->jpg_settings); - - /* tell the user what we actually did */ - fmt->fmt.pix.width = settings.img_width / settings.HorDcm; - fmt->fmt.pix.height = settings.img_height * 2 / - (settings.TmpDcm * settings.VerDcm); - if (settings.TmpDcm == 1) - fmt->fmt.pix.field = (fh->jpg_settings.odd_even ? - V4L2_FIELD_SEQ_TB : V4L2_FIELD_SEQ_BT); - else - fmt->fmt.pix.field = (fh->jpg_settings.odd_even ? - V4L2_FIELD_TOP : V4L2_FIELD_BOTTOM); - fmt->fmt.pix.bytesperline = 0; - fmt->fmt.pix.sizeimage = fh->buffers.buffer_size; - fmt->fmt.pix.colorspace = V4L2_COLORSPACE_SMPTE170M; - return res; -} - -static int zoran_s_fmt_vid_cap(struct file *file, void *__fh, - struct v4l2_format *fmt) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - int i; - int res = 0; - - if (fmt->fmt.pix.pixelformat == V4L2_PIX_FMT_MJPEG) - return zoran_s_fmt_vid_out(file, fh, fmt); - - for (i = 0; i < NUM_FORMATS; i++) - if (fmt->fmt.pix.pixelformat == zoran_formats[i].fourcc) - break; - if (i == NUM_FORMATS) { - dprintk(1, KERN_ERR "%s: VIDIOC_S_FMT - unknown/unsupported format 0x%x\n", - ZR_DEVNAME(zr), fmt->fmt.pix.pixelformat); - return -EINVAL; - } - - if ((fh->map_mode != ZORAN_MAP_MODE_RAW && fh->buffers.allocated) || - fh->buffers.active != ZORAN_FREE) { - dprintk(1, KERN_ERR "%s: VIDIOC_S_FMT - cannot change capture mode\n", - ZR_DEVNAME(zr)); - res = -EBUSY; - return res; - } - if (fmt->fmt.pix.height > BUZ_MAX_HEIGHT) - fmt->fmt.pix.height = BUZ_MAX_HEIGHT; - if (fmt->fmt.pix.width > BUZ_MAX_WIDTH) - fmt->fmt.pix.width = BUZ_MAX_WIDTH; - - map_mode_raw(fh); - - res = zoran_v4l_set_format(fh, fmt->fmt.pix.width, fmt->fmt.pix.height, - &zoran_formats[i]); - if (res) - return res; - - /* tell the user the results/missing stuff */ - fmt->fmt.pix.bytesperline = fh->v4l_settings.bytesperline; - fmt->fmt.pix.sizeimage = fh->v4l_settings.height * fh->v4l_settings.bytesperline; - fmt->fmt.pix.colorspace = fh->v4l_settings.format->colorspace; - if (BUZ_MAX_HEIGHT < (fh->v4l_settings.height * 2)) - fmt->fmt.pix.field = V4L2_FIELD_INTERLACED; - else - fmt->fmt.pix.field = V4L2_FIELD_TOP; - return res; -} - -static int zoran_g_fbuf(struct file *file, void *__fh, - struct v4l2_framebuffer *fb) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - - memset(fb, 0, sizeof(*fb)); - fb->base = zr->vbuf_base; - fb->fmt.width = zr->vbuf_width; - fb->fmt.height = zr->vbuf_height; - if (zr->overlay_settings.format) - fb->fmt.pixelformat = fh->overlay_settings.format->fourcc; - fb->fmt.bytesperline = zr->vbuf_bytesperline; - fb->fmt.colorspace = V4L2_COLORSPACE_SRGB; - fb->fmt.field = V4L2_FIELD_INTERLACED; - fb->capability = V4L2_FBUF_CAP_LIST_CLIPPING; - - return 0; -} - -static int zoran_s_fbuf(struct file *file, void *__fh, - const struct v4l2_framebuffer *fb) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - int i, res = 0; - __le32 printformat = __cpu_to_le32(fb->fmt.pixelformat); - - for (i = 0; i < NUM_FORMATS; i++) - if (zoran_formats[i].fourcc == fb->fmt.pixelformat) - break; - if (i == NUM_FORMATS) { - dprintk(1, KERN_ERR "%s: VIDIOC_S_FBUF - format=0x%x (%4.4s) not allowed\n", - ZR_DEVNAME(zr), fb->fmt.pixelformat, - (char *)&printformat); - return -EINVAL; - } - - res = setup_fbuffer(fh, fb->base, &zoran_formats[i], fb->fmt.width, - fb->fmt.height, fb->fmt.bytesperline); - - return res; -} - -static int zoran_overlay(struct file *file, void *__fh, unsigned int on) -{ - struct zoran_fh *fh = __fh; - int res; - - res = setup_overlay(fh, on); - - return res; -} - -static int zoran_streamoff(struct file *file, void *__fh, enum v4l2_buf_type type); - -static int zoran_reqbufs(struct file *file, void *__fh, struct v4l2_requestbuffers *req) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - int res = 0; - - if (req->memory != V4L2_MEMORY_MMAP) { - dprintk(2, - KERN_ERR - "%s: only MEMORY_MMAP capture is supported, not %d\n", - ZR_DEVNAME(zr), req->memory); - return -EINVAL; - } - - if (req->count == 0) - return zoran_streamoff(file, fh, req->type); - - if (fh->buffers.allocated) { - dprintk(2, - KERN_ERR - "%s: VIDIOC_REQBUFS - buffers already allocated\n", - ZR_DEVNAME(zr)); - res = -EBUSY; - return res; - } - - if (fh->map_mode == ZORAN_MAP_MODE_RAW && - req->type == V4L2_BUF_TYPE_VIDEO_CAPTURE) { - /* control user input */ - if (req->count < 2) - req->count = 2; - if (req->count > v4l_nbufs) - req->count = v4l_nbufs; - - /* The next mmap will map the V4L buffers */ - map_mode_raw(fh); - fh->buffers.num_buffers = req->count; - - if (v4l_fbuffer_alloc(fh)) { - res = -ENOMEM; - return res; - } - } else if (fh->map_mode == ZORAN_MAP_MODE_JPG_REC || - fh->map_mode == ZORAN_MAP_MODE_JPG_PLAY) { - /* we need to calculate size ourselves now */ - if (req->count < 4) - req->count = 4; - if (req->count > jpg_nbufs) - req->count = jpg_nbufs; - - /* The next mmap will map the MJPEG buffers */ - map_mode_jpg(fh, req->type == V4L2_BUF_TYPE_VIDEO_OUTPUT); - fh->buffers.num_buffers = req->count; - fh->buffers.buffer_size = zoran_v4l2_calc_bufsize(&fh->jpg_settings); - - if (jpg_fbuffer_alloc(fh)) { - res = -ENOMEM; - return res; - } - } else { - dprintk(1, - KERN_ERR - "%s: VIDIOC_REQBUFS - unknown type %d\n", - ZR_DEVNAME(zr), req->type); - res = -EINVAL; - return res; - } - return res; -} - -static int zoran_querybuf(struct file *file, void *__fh, struct v4l2_buffer *buf) -{ - struct zoran_fh *fh = __fh; - int res; - - res = zoran_v4l2_buffer_status(fh, buf, buf->index); - - return res; -} - -static int zoran_qbuf(struct file *file, void *__fh, struct v4l2_buffer *buf) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - int res = 0, codec_mode, buf_type; - - switch (fh->map_mode) { - case ZORAN_MAP_MODE_RAW: - if (buf->type != V4L2_BUF_TYPE_VIDEO_CAPTURE) { - dprintk(1, KERN_ERR - "%s: VIDIOC_QBUF - invalid buf->type=%d for map_mode=%d\n", - ZR_DEVNAME(zr), buf->type, fh->map_mode); - res = -EINVAL; - return res; - } - - res = zoran_v4l_queue_frame(fh, buf->index); - if (res) - return res; - if (!zr->v4l_memgrab_active && fh->buffers.active == ZORAN_LOCKED) - zr36057_set_memgrab(zr, 1); - break; - - case ZORAN_MAP_MODE_JPG_REC: - case ZORAN_MAP_MODE_JPG_PLAY: - if (fh->map_mode == ZORAN_MAP_MODE_JPG_PLAY) { - buf_type = V4L2_BUF_TYPE_VIDEO_OUTPUT; - codec_mode = BUZ_MODE_MOTION_DECOMPRESS; - } else { - buf_type = V4L2_BUF_TYPE_VIDEO_CAPTURE; - codec_mode = BUZ_MODE_MOTION_COMPRESS; - } - - if (buf->type != buf_type) { - dprintk(1, KERN_ERR - "%s: VIDIOC_QBUF - invalid buf->type=%d for map_mode=%d\n", - ZR_DEVNAME(zr), buf->type, fh->map_mode); - res = -EINVAL; - return res; - } - - res = zoran_jpg_queue_frame(fh, buf->index, codec_mode); - if (res != 0) - return res; - if (zr->codec_mode == BUZ_MODE_IDLE && - fh->buffers.active == ZORAN_LOCKED) - zr36057_enable_jpg(zr, codec_mode); - - break; - - default: - dprintk(1, KERN_ERR - "%s: VIDIOC_QBUF - unsupported type %d\n", - ZR_DEVNAME(zr), buf->type); - res = -EINVAL; - break; - } - return res; -} - -static int zoran_dqbuf(struct file *file, void *__fh, struct v4l2_buffer *buf) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - int res = 0, buf_type, num = -1; /* compiler borks here (?) */ - - switch (fh->map_mode) { - case ZORAN_MAP_MODE_RAW: - if (buf->type != V4L2_BUF_TYPE_VIDEO_CAPTURE) { - dprintk(1, KERN_ERR - "%s: VIDIOC_QBUF - invalid buf->type=%d for map_mode=%d\n", - ZR_DEVNAME(zr), buf->type, fh->map_mode); - res = -EINVAL; - return res; - } - - num = zr->v4l_pend[zr->v4l_sync_tail & V4L_MASK_FRAME]; - if (file->f_flags & O_NONBLOCK && - zr->v4l_buffers.buffer[num].state != BUZ_STATE_DONE) { - res = -EAGAIN; - return res; - } - res = v4l_sync(fh, num); - if (res) - return res; - zr->v4l_sync_tail++; - res = zoran_v4l2_buffer_status(fh, buf, num); - break; - - case ZORAN_MAP_MODE_JPG_REC: - case ZORAN_MAP_MODE_JPG_PLAY: - { - struct zoran_sync bs; - - if (fh->map_mode == ZORAN_MAP_MODE_JPG_PLAY) - buf_type = V4L2_BUF_TYPE_VIDEO_OUTPUT; - else - buf_type = V4L2_BUF_TYPE_VIDEO_CAPTURE; - - if (buf->type != buf_type) { - dprintk(1, KERN_ERR - "%s: VIDIOC_QBUF - invalid buf->type=%d for map_mode=%d\n", - ZR_DEVNAME(zr), buf->type, fh->map_mode); - res = -EINVAL; - return res; - } - - num = zr->jpg_pend[zr->jpg_que_tail & BUZ_MASK_FRAME]; - - if (file->f_flags & O_NONBLOCK && - zr->jpg_buffers.buffer[num].state != BUZ_STATE_DONE) { - res = -EAGAIN; - return res; - } - bs.frame = 0; /* suppress compiler warning */ - res = jpg_sync(fh, &bs); - if (res) - return res; - res = zoran_v4l2_buffer_status(fh, buf, bs.frame); - break; - } - - default: - dprintk(1, KERN_ERR - "%s: VIDIOC_DQBUF - unsupported type %d\n", - ZR_DEVNAME(zr), buf->type); - res = -EINVAL; - break; - } - return res; -} - -static int zoran_streamon(struct file *file, void *__fh, enum v4l2_buf_type type) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - int res = 0; - - switch (fh->map_mode) { - case ZORAN_MAP_MODE_RAW: /* raw capture */ - if (zr->v4l_buffers.active != ZORAN_ACTIVE || - fh->buffers.active != ZORAN_ACTIVE) { - res = -EBUSY; - return res; - } - - zr->v4l_buffers.active = fh->buffers.active = ZORAN_LOCKED; - zr->v4l_settings = fh->v4l_settings; - - zr->v4l_sync_tail = zr->v4l_pend_tail; - if (!zr->v4l_memgrab_active && - zr->v4l_pend_head != zr->v4l_pend_tail) { - zr36057_set_memgrab(zr, 1); - } - break; - - case ZORAN_MAP_MODE_JPG_REC: - case ZORAN_MAP_MODE_JPG_PLAY: - /* what is the codec mode right now? */ - if (zr->jpg_buffers.active != ZORAN_ACTIVE || - fh->buffers.active != ZORAN_ACTIVE) { - res = -EBUSY; - return res; - } - - zr->jpg_buffers.active = fh->buffers.active = ZORAN_LOCKED; - - if (zr->jpg_que_head != zr->jpg_que_tail) { - /* Start the jpeg codec when the first frame is queued */ - jpeg_start(zr); - } - break; - - default: - dprintk(1, - KERN_ERR - "%s: VIDIOC_STREAMON - invalid map mode %d\n", - ZR_DEVNAME(zr), fh->map_mode); - res = -EINVAL; - break; - } - return res; -} - -static int zoran_streamoff(struct file *file, void *__fh, enum v4l2_buf_type type) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - int i, res = 0; - unsigned long flags; - - switch (fh->map_mode) { - case ZORAN_MAP_MODE_RAW: /* raw capture */ - if (fh->buffers.active == ZORAN_FREE && - zr->v4l_buffers.active != ZORAN_FREE) { - res = -EPERM; /* stay off other's settings! */ - return res; - } - if (zr->v4l_buffers.active == ZORAN_FREE) - return res; - - spin_lock_irqsave(&zr->spinlock, flags); - /* unload capture */ - if (zr->v4l_memgrab_active) { - - zr36057_set_memgrab(zr, 0); - } - - for (i = 0; i < fh->buffers.num_buffers; i++) - zr->v4l_buffers.buffer[i].state = BUZ_STATE_USER; - fh->buffers = zr->v4l_buffers; - - zr->v4l_buffers.active = fh->buffers.active = ZORAN_FREE; - - zr->v4l_grab_seq = 0; - zr->v4l_pend_head = zr->v4l_pend_tail = 0; - zr->v4l_sync_tail = 0; - - spin_unlock_irqrestore(&zr->spinlock, flags); - - break; - - case ZORAN_MAP_MODE_JPG_REC: - case ZORAN_MAP_MODE_JPG_PLAY: - if (fh->buffers.active == ZORAN_FREE && - zr->jpg_buffers.active != ZORAN_FREE) { - res = -EPERM; /* stay off other's settings! */ - return res; - } - if (zr->jpg_buffers.active == ZORAN_FREE) - return res; - - res = jpg_qbuf(fh, -1, - (fh->map_mode == ZORAN_MAP_MODE_JPG_REC) ? - BUZ_MODE_MOTION_COMPRESS : - BUZ_MODE_MOTION_DECOMPRESS); - if (res) - return res; - break; - default: - dprintk(1, KERN_ERR - "%s: VIDIOC_STREAMOFF - invalid map mode %d\n", - ZR_DEVNAME(zr), fh->map_mode); - res = -EINVAL; - break; - } - return res; -} -static int zoran_g_std(struct file *file, void *__fh, v4l2_std_id *std) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - - *std = zr->norm; - return 0; -} - -static int zoran_s_std(struct file *file, void *__fh, v4l2_std_id std) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - int res = 0; - - res = zoran_set_norm(zr, std); - if (res) - return res; - - res = wait_grab_pending(zr); - return res; -} - -static int zoran_enum_input(struct file *file, void *__fh, - struct v4l2_input *inp) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - - if (inp->index >= zr->card.inputs) - return -EINVAL; - - strscpy(inp->name, zr->card.input[inp->index].name, - sizeof(inp->name)); - inp->type = V4L2_INPUT_TYPE_CAMERA; - inp->std = V4L2_STD_ALL; - - /* Get status of video decoder */ - decoder_call(zr, video, g_input_status, &inp->status); - return 0; -} - -static int zoran_g_input(struct file *file, void *__fh, unsigned int *input) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - - *input = zr->input; - - return 0; -} - -static int zoran_s_input(struct file *file, void *__fh, unsigned int input) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - int res; - - res = zoran_set_input(zr, input); - if (res) - return res; - - /* Make sure the changes come into effect */ - res = wait_grab_pending(zr); - return res; -} - -static int zoran_enum_output(struct file *file, void *__fh, - struct v4l2_output *outp) -{ - if (outp->index != 0) - return -EINVAL; - - outp->index = 0; - outp->type = V4L2_OUTPUT_TYPE_ANALOGVGAOVERLAY; - strscpy(outp->name, "Autodetect", sizeof(outp->name)); - - return 0; -} - -static int zoran_g_output(struct file *file, void *__fh, unsigned int *output) -{ - *output = 0; - - return 0; -} - -static int zoran_s_output(struct file *file, void *__fh, unsigned int output) -{ - if (output != 0) - return -EINVAL; - - return 0; -} - -/* cropping (sub-frame capture) */ -static int zoran_g_selection(struct file *file, void *__fh, struct v4l2_selection *sel) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - - if (sel->type != V4L2_BUF_TYPE_VIDEO_OUTPUT && - sel->type != V4L2_BUF_TYPE_VIDEO_CAPTURE) - return -EINVAL; - - if (fh->map_mode == ZORAN_MAP_MODE_RAW) { - dprintk(1, KERN_ERR - "%s: VIDIOC_G_SELECTION - subcapture only supported for compressed capture\n", - ZR_DEVNAME(zr)); - return -EINVAL; - } - - switch (sel->target) { - case V4L2_SEL_TGT_CROP: - sel->r.top = fh->jpg_settings.img_y; - sel->r.left = fh->jpg_settings.img_x; - sel->r.width = fh->jpg_settings.img_width; - sel->r.height = fh->jpg_settings.img_height; - break; - case V4L2_SEL_TGT_CROP_DEFAULT: - sel->r.top = sel->r.left = 0; - sel->r.width = BUZ_MIN_WIDTH; - sel->r.height = BUZ_MIN_HEIGHT; - break; - case V4L2_SEL_TGT_CROP_BOUNDS: - sel->r.top = sel->r.left = 0; - sel->r.width = BUZ_MAX_WIDTH; - sel->r.height = BUZ_MAX_HEIGHT; - break; - default: - return -EINVAL; - } - return 0; -} - -static int zoran_s_selection(struct file *file, void *__fh, struct v4l2_selection *sel) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - struct zoran_jpg_settings settings; - int res; - - if (sel->type != V4L2_BUF_TYPE_VIDEO_OUTPUT && - sel->type != V4L2_BUF_TYPE_VIDEO_CAPTURE) - return -EINVAL; - - if (sel->target != V4L2_SEL_TGT_CROP) - return -EINVAL; - - if (fh->map_mode == ZORAN_MAP_MODE_RAW) { - dprintk(1, KERN_ERR - "%s: VIDIOC_S_SELECTION - subcapture only supported for compressed capture\n", - ZR_DEVNAME(zr)); - return -EINVAL; - } - - settings = fh->jpg_settings; - - if (fh->buffers.allocated) { - dprintk(1, KERN_ERR - "%s: VIDIOC_S_SELECTION - cannot change settings while active\n", - ZR_DEVNAME(zr)); - return -EBUSY; - } - - /* move into a form that we understand */ - settings.img_x = sel->r.left; - settings.img_y = sel->r.top; - settings.img_width = sel->r.width; - settings.img_height = sel->r.height; - - /* check validity */ - res = zoran_check_jpg_settings(zr, &settings, 0); - if (res) - return res; - - /* accept */ - fh->jpg_settings = settings; - return res; -} - -static int zoran_g_jpegcomp(struct file *file, void *__fh, - struct v4l2_jpegcompression *params) -{ - struct zoran_fh *fh = __fh; - memset(params, 0, sizeof(*params)); - - params->quality = fh->jpg_settings.jpg_comp.quality; - params->APPn = fh->jpg_settings.jpg_comp.APPn; - memcpy(params->APP_data, - fh->jpg_settings.jpg_comp.APP_data, - fh->jpg_settings.jpg_comp.APP_len); - params->APP_len = fh->jpg_settings.jpg_comp.APP_len; - memcpy(params->COM_data, - fh->jpg_settings.jpg_comp.COM_data, - fh->jpg_settings.jpg_comp.COM_len); - params->COM_len = fh->jpg_settings.jpg_comp.COM_len; - params->jpeg_markers = - fh->jpg_settings.jpg_comp.jpeg_markers; - - return 0; -} - -static int zoran_s_jpegcomp(struct file *file, void *__fh, - const struct v4l2_jpegcompression *params) -{ - struct zoran_fh *fh = __fh; - struct zoran *zr = fh->zr; - int res = 0; - struct zoran_jpg_settings settings; - - settings = fh->jpg_settings; - - settings.jpg_comp = *params; - - if (fh->buffers.active != ZORAN_FREE) { - dprintk(1, KERN_WARNING - "%s: VIDIOC_S_JPEGCOMP called while in playback/capture mode\n", - ZR_DEVNAME(zr)); - res = -EBUSY; - return res; - } - - res = zoran_check_jpg_settings(zr, &settings, 0); - if (res) - return res; - if (!fh->buffers.allocated) - fh->buffers.buffer_size = - zoran_v4l2_calc_bufsize(&fh->jpg_settings); - fh->jpg_settings.jpg_comp = settings.jpg_comp; - return res; -} - -static __poll_t -zoran_poll (struct file *file, - poll_table *wait) -{ - struct zoran_fh *fh = file->private_data; - struct zoran *zr = fh->zr; - __poll_t res = v4l2_ctrl_poll(file, wait); - int frame; - unsigned long flags; - - /* we should check whether buffers are ready to be synced on - * (w/o waits - O_NONBLOCK) here - * if ready for read (sync), return EPOLLIN|EPOLLRDNORM, - * if ready for write (sync), return EPOLLOUT|EPOLLWRNORM, - * if error, return EPOLLERR, - * if no buffers queued or so, return EPOLLNVAL - */ - - switch (fh->map_mode) { - case ZORAN_MAP_MODE_RAW: - poll_wait(file, &zr->v4l_capq, wait); - frame = zr->v4l_pend[zr->v4l_sync_tail & V4L_MASK_FRAME]; - - spin_lock_irqsave(&zr->spinlock, flags); - dprintk(3, - KERN_DEBUG - "%s: %s() raw - active=%c, sync_tail=%lu/%c, pend_tail=%lu, pend_head=%lu\n", - ZR_DEVNAME(zr), __func__, - "FAL"[fh->buffers.active], zr->v4l_sync_tail, - "UPMD"[zr->v4l_buffers.buffer[frame].state], - zr->v4l_pend_tail, zr->v4l_pend_head); - /* Process is the one capturing? */ - if (fh->buffers.active != ZORAN_FREE && - /* Buffer ready to DQBUF? */ - zr->v4l_buffers.buffer[frame].state == BUZ_STATE_DONE) - res |= EPOLLIN | EPOLLRDNORM; - spin_unlock_irqrestore(&zr->spinlock, flags); - - break; - - case ZORAN_MAP_MODE_JPG_REC: - case ZORAN_MAP_MODE_JPG_PLAY: - poll_wait(file, &zr->jpg_capq, wait); - frame = zr->jpg_pend[zr->jpg_que_tail & BUZ_MASK_FRAME]; - - spin_lock_irqsave(&zr->spinlock, flags); - dprintk(3, - KERN_DEBUG - "%s: %s() jpg - active=%c, que_tail=%lu/%c, que_head=%lu, dma=%lu/%lu\n", - ZR_DEVNAME(zr), __func__, - "FAL"[fh->buffers.active], zr->jpg_que_tail, - "UPMD"[zr->jpg_buffers.buffer[frame].state], - zr->jpg_que_head, zr->jpg_dma_tail, zr->jpg_dma_head); - if (fh->buffers.active != ZORAN_FREE && - zr->jpg_buffers.buffer[frame].state == BUZ_STATE_DONE) { - if (fh->map_mode == ZORAN_MAP_MODE_JPG_REC) - res |= EPOLLIN | EPOLLRDNORM; - else - res |= EPOLLOUT | EPOLLWRNORM; - } - spin_unlock_irqrestore(&zr->spinlock, flags); - - break; - - default: - dprintk(1, - KERN_ERR - "%s: %s - internal error, unknown map_mode=%d\n", - ZR_DEVNAME(zr), __func__, fh->map_mode); - res |= EPOLLERR; - } - - return res; -} - - -/* - * This maps the buffers to user space. - * - * Depending on the state of fh->map_mode - * the V4L or the MJPEG buffers are mapped - * per buffer or all together - * - * Note that we need to connect to some - * unmap signal event to unmap the de-allocate - * the buffer accordingly (zoran_vm_close()) - */ - -static void -zoran_vm_open (struct vm_area_struct *vma) -{ - struct zoran_mapping *map = vma->vm_private_data; - atomic_inc(&map->count); -} - -static void -zoran_vm_close (struct vm_area_struct *vma) -{ - struct zoran_mapping *map = vma->vm_private_data; - struct zoran_fh *fh = map->fh; - struct zoran *zr = fh->zr; - int i; - - dprintk(3, KERN_INFO "%s: %s - munmap(%s)\n", ZR_DEVNAME(zr), - __func__, mode_name(fh->map_mode)); - - for (i = 0; i < fh->buffers.num_buffers; i++) { - if (fh->buffers.buffer[i].map == map) - fh->buffers.buffer[i].map = NULL; - } - kfree(map); - - /* Any buffers still mapped? */ - for (i = 0; i < fh->buffers.num_buffers; i++) { - if (fh->buffers.buffer[i].map) { - return; - } - } - - dprintk(3, KERN_INFO "%s: %s - free %s buffers\n", ZR_DEVNAME(zr), - __func__, mode_name(fh->map_mode)); - - if (fh->map_mode == ZORAN_MAP_MODE_RAW) { - if (fh->buffers.active != ZORAN_FREE) { - unsigned long flags; - - spin_lock_irqsave(&zr->spinlock, flags); - zr36057_set_memgrab(zr, 0); - zr->v4l_buffers.allocated = 0; - zr->v4l_buffers.active = fh->buffers.active = ZORAN_FREE; - spin_unlock_irqrestore(&zr->spinlock, flags); - } - v4l_fbuffer_free(fh); - } else { - if (fh->buffers.active != ZORAN_FREE) { - jpg_qbuf(fh, -1, zr->codec_mode); - zr->jpg_buffers.allocated = 0; - zr->jpg_buffers.active = fh->buffers.active = ZORAN_FREE; - } - jpg_fbuffer_free(fh); - } -} - -static const struct vm_operations_struct zoran_vm_ops = { - .open = zoran_vm_open, - .close = zoran_vm_close, -}; - -static int -zoran_mmap (struct file *file, - struct vm_area_struct *vma) -{ - struct zoran_fh *fh = file->private_data; - struct zoran *zr = fh->zr; - unsigned long size = (vma->vm_end - vma->vm_start); - unsigned long offset = vma->vm_pgoff << PAGE_SHIFT; - int i, j; - unsigned long page, start = vma->vm_start, todo, pos, fraglen; - int first, last; - struct zoran_mapping *map; - int res = 0; - - dprintk(3, - KERN_INFO "%s: %s(%s) of 0x%08lx-0x%08lx (size=%lu)\n", - ZR_DEVNAME(zr), __func__, - mode_name(fh->map_mode), vma->vm_start, vma->vm_end, size); - - if (!(vma->vm_flags & VM_SHARED) || !(vma->vm_flags & VM_READ) || - !(vma->vm_flags & VM_WRITE)) { - dprintk(1, - KERN_ERR - "%s: %s - no MAP_SHARED/PROT_{READ,WRITE} given\n", - ZR_DEVNAME(zr), __func__); - return -EINVAL; - } - - if (!fh->buffers.allocated) { - dprintk(1, - KERN_ERR - "%s: %s(%s) - buffers not yet allocated\n", - ZR_DEVNAME(zr), __func__, mode_name(fh->map_mode)); - res = -ENOMEM; - return res; - } - - first = offset / fh->buffers.buffer_size; - last = first - 1 + size / fh->buffers.buffer_size; - if (offset % fh->buffers.buffer_size != 0 || - size % fh->buffers.buffer_size != 0 || first < 0 || - last < 0 || first >= fh->buffers.num_buffers || - last >= fh->buffers.buffer_size) { - dprintk(1, - KERN_ERR - "%s: %s(%s) - offset=%lu or size=%lu invalid for bufsize=%d and numbufs=%d\n", - ZR_DEVNAME(zr), __func__, mode_name(fh->map_mode), offset, size, - fh->buffers.buffer_size, - fh->buffers.num_buffers); - res = -EINVAL; - return res; - } - - /* Check if any buffers are already mapped */ - for (i = first; i <= last; i++) { - if (fh->buffers.buffer[i].map) { - dprintk(1, - KERN_ERR - "%s: %s(%s) - buffer %d already mapped\n", - ZR_DEVNAME(zr), __func__, mode_name(fh->map_mode), i); - res = -EBUSY; - return res; - } - } - - /* map these buffers */ - map = kmalloc(sizeof(struct zoran_mapping), GFP_KERNEL); - if (!map) { - res = -ENOMEM; - return res; - } - map->fh = fh; - atomic_set(&map->count, 1); - - vma->vm_ops = &zoran_vm_ops; - vma->vm_flags |= VM_DONTEXPAND; - vma->vm_private_data = map; - - if (fh->map_mode == ZORAN_MAP_MODE_RAW) { - for (i = first; i <= last; i++) { - todo = size; - if (todo > fh->buffers.buffer_size) - todo = fh->buffers.buffer_size; - page = fh->buffers.buffer[i].v4l.fbuffer_phys; - if (remap_pfn_range(vma, start, page >> PAGE_SHIFT, - todo, PAGE_SHARED)) { - dprintk(1, - KERN_ERR - "%s: %s(V4L) - remap_pfn_range failed\n", - ZR_DEVNAME(zr), __func__); - res = -EAGAIN; - return res; - } - size -= todo; - start += todo; - fh->buffers.buffer[i].map = map; - if (size == 0) - break; - } - } else { - for (i = first; i <= last; i++) { - for (j = 0; - j < fh->buffers.buffer_size / PAGE_SIZE; - j++) { - fraglen = - (le32_to_cpu(fh->buffers.buffer[i].jpg. - frag_tab[2 * j + 1]) & ~1) << 1; - todo = size; - if (todo > fraglen) - todo = fraglen; - pos = - le32_to_cpu(fh->buffers. - buffer[i].jpg.frag_tab[2 * j]); - /* should just be pos on i386 */ - page = virt_to_phys(bus_to_virt(pos)) - >> PAGE_SHIFT; - if (remap_pfn_range(vma, start, page, - todo, PAGE_SHARED)) { - dprintk(1, - KERN_ERR - "%s: %s(V4L) - remap_pfn_range failed\n", - ZR_DEVNAME(zr), __func__); - res = -EAGAIN; - return res; - } - size -= todo; - start += todo; - if (size == 0) - break; - if (le32_to_cpu(fh->buffers.buffer[i].jpg. - frag_tab[2 * j + 1]) & 1) - break; /* was last fragment */ - } - fh->buffers.buffer[i].map = map; - if (size == 0) - break; - - } - } - return res; -} - -static const struct v4l2_ioctl_ops zoran_ioctl_ops = { - .vidioc_querycap = zoran_querycap, - .vidioc_s_selection = zoran_s_selection, - .vidioc_g_selection = zoran_g_selection, - .vidioc_enum_input = zoran_enum_input, - .vidioc_g_input = zoran_g_input, - .vidioc_s_input = zoran_s_input, - .vidioc_enum_output = zoran_enum_output, - .vidioc_g_output = zoran_g_output, - .vidioc_s_output = zoran_s_output, - .vidioc_g_fbuf = zoran_g_fbuf, - .vidioc_s_fbuf = zoran_s_fbuf, - .vidioc_g_std = zoran_g_std, - .vidioc_s_std = zoran_s_std, - .vidioc_g_jpegcomp = zoran_g_jpegcomp, - .vidioc_s_jpegcomp = zoran_s_jpegcomp, - .vidioc_overlay = zoran_overlay, - .vidioc_reqbufs = zoran_reqbufs, - .vidioc_querybuf = zoran_querybuf, - .vidioc_qbuf = zoran_qbuf, - .vidioc_dqbuf = zoran_dqbuf, - .vidioc_streamon = zoran_streamon, - .vidioc_streamoff = zoran_streamoff, - .vidioc_enum_fmt_vid_cap = zoran_enum_fmt_vid_cap, - .vidioc_enum_fmt_vid_out = zoran_enum_fmt_vid_out, - .vidioc_enum_fmt_vid_overlay = zoran_enum_fmt_vid_overlay, - .vidioc_g_fmt_vid_cap = zoran_g_fmt_vid_cap, - .vidioc_g_fmt_vid_out = zoran_g_fmt_vid_out, - .vidioc_g_fmt_vid_overlay = zoran_g_fmt_vid_overlay, - .vidioc_s_fmt_vid_cap = zoran_s_fmt_vid_cap, - .vidioc_s_fmt_vid_out = zoran_s_fmt_vid_out, - .vidioc_s_fmt_vid_overlay = zoran_s_fmt_vid_overlay, - .vidioc_try_fmt_vid_cap = zoran_try_fmt_vid_cap, - .vidioc_try_fmt_vid_out = zoran_try_fmt_vid_out, - .vidioc_try_fmt_vid_overlay = zoran_try_fmt_vid_overlay, - .vidioc_subscribe_event = v4l2_ctrl_subscribe_event, - .vidioc_unsubscribe_event = v4l2_event_unsubscribe, -}; - -static const struct v4l2_file_operations zoran_fops = { - .owner = THIS_MODULE, - .open = zoran_open, - .release = zoran_close, - .unlocked_ioctl = video_ioctl2, - .mmap = zoran_mmap, - .poll = zoran_poll, -}; - -const struct video_device zoran_template = { - .name = ZORAN_NAME, - .fops = &zoran_fops, - .ioctl_ops = &zoran_ioctl_ops, - .release = &zoran_vdev_release, - .tvnorms = V4L2_STD_NTSC | V4L2_STD_PAL | V4L2_STD_SECAM, -}; - diff --git a/drivers/staging/media/zoran/zoran_procfs.c b/drivers/staging/media/zoran/zoran_procfs.c deleted file mode 100644 index 78ac8f853748..000000000000 --- a/drivers/staging/media/zoran/zoran_procfs.c +++ /dev/null @@ -1,221 +0,0 @@ -/* - * Zoran zr36057/zr36067 PCI controller driver, for the - * Pinnacle/Miro DC10/DC10+/DC30/DC30+, Iomega Buz, Linux - * Media Labs LML33/LML33R10. - * - * This part handles the procFS entries (/proc/ZORAN[%d]) - * - * Copyright (C) 2000 Serguei Miridonov - * - * Currently maintained by: - * Ronald Bultje - * Laurent Pinchart - * Mailinglist - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - */ - -#include -#include -#include -#include - -#include -#include -#include -#include -#include -#include -#include -#include - -#include -#include -#include - -#include "videocodec.h" -#include "zoran.h" -#include "zoran_procfs.h" -#include "zoran_card.h" - -#ifdef CONFIG_PROC_FS -struct procfs_params_zr36067 { - char *name; - short reg; - u32 mask; - short bit; -}; - -static const struct procfs_params_zr36067 zr67[] = { - {"HSPol", 0x000, 1, 30}, - {"HStart", 0x000, 0x3ff, 10}, - {"HEnd", 0x000, 0x3ff, 0}, - - {"VSPol", 0x004, 1, 30}, - {"VStart", 0x004, 0x3ff, 10}, - {"VEnd", 0x004, 0x3ff, 0}, - - {"ExtFl", 0x008, 1, 26}, - {"TopField", 0x008, 1, 25}, - {"VCLKPol", 0x008, 1, 24}, - {"DupFld", 0x008, 1, 20}, - {"LittleEndian", 0x008, 1, 0}, - - {"HsyncStart", 0x10c, 0xffff, 16}, - {"LineTot", 0x10c, 0xffff, 0}, - - {"NAX", 0x110, 0xffff, 16}, - {"PAX", 0x110, 0xffff, 0}, - - {"NAY", 0x114, 0xffff, 16}, - {"PAY", 0x114, 0xffff, 0}, - - /* {"",,,}, */ - - {NULL, 0, 0, 0}, -}; - -static void -setparam (struct zoran *zr, - char *name, - char *sval) -{ - int i = 0, reg0, reg, val; - - while (zr67[i].name != NULL) { - if (!strncmp(name, zr67[i].name, strlen(zr67[i].name))) { - reg = reg0 = btread(zr67[i].reg); - reg &= ~(zr67[i].mask << zr67[i].bit); - if (!isdigit(sval[0])) - break; - val = simple_strtoul(sval, NULL, 0); - if ((val & ~zr67[i].mask)) - break; - reg |= (val & zr67[i].mask) << zr67[i].bit; - dprintk(4, - KERN_INFO - "%s: setparam: setting ZR36067 register 0x%03x: 0x%08x=>0x%08x %s=%d\n", - ZR_DEVNAME(zr), zr67[i].reg, reg0, reg, - zr67[i].name, val); - btwrite(reg, zr67[i].reg); - break; - } - i++; - } -} - -static int zoran_show(struct seq_file *p, void *v) -{ - struct zoran *zr = p->private; - int i; - - seq_printf(p, "ZR36067 registers:\n"); - for (i = 0; i < 0x130; i += 16) - seq_printf(p, "%03X %08X %08X %08X %08X \n", i, - btread(i), btread(i+4), btread(i+8), btread(i+12)); - return 0; -} - -static int zoran_open(struct inode *inode, struct file *file) -{ - struct zoran *data = PDE_DATA(inode); - return single_open(file, zoran_show, data); -} - -static ssize_t zoran_write(struct file *file, const char __user *buffer, - size_t count, loff_t *ppos) -{ - struct zoran *zr = PDE_DATA(file_inode(file)); - char *string, *sp; - char *line, *ldelim, *varname, *svar, *tdelim; - - if (count > 32768) /* Stupidity filter */ - return -EINVAL; - - string = sp = vmalloc(count + 1); - if (!string) { - dprintk(1, - KERN_ERR - "%s: write_proc: can not allocate memory\n", - ZR_DEVNAME(zr)); - return -ENOMEM; - } - if (copy_from_user(string, buffer, count)) { - vfree (string); - return -EFAULT; - } - string[count] = 0; - dprintk(4, KERN_INFO "%s: write_proc: name=%pD count=%zu zr=%p\n", - ZR_DEVNAME(zr), file, count, zr); - ldelim = " \t\n"; - tdelim = "="; - line = strpbrk(sp, ldelim); - while (line) { - *line = 0; - svar = strpbrk(sp, tdelim); - if (svar) { - *svar = 0; - varname = sp; - svar++; - setparam(zr, varname, svar); - } - sp = line + 1; - line = strpbrk(sp, ldelim); - } - vfree(string); - - return count; -} - -static const struct file_operations zoran_operations = { - .owner = THIS_MODULE, - .open = zoran_open, - .read = seq_read, - .write = zoran_write, - .llseek = seq_lseek, - .release = single_release, -}; -#endif - -int -zoran_proc_init (struct zoran *zr) -{ -#ifdef CONFIG_PROC_FS - char name[8]; - - snprintf(name, 7, "zoran%d", zr->id); - zr->zoran_proc = proc_create_data(name, 0, NULL, &zoran_operations, zr); - if (zr->zoran_proc != NULL) { - dprintk(2, - KERN_INFO - "%s: procfs entry /proc/%s allocated. data=%p\n", - ZR_DEVNAME(zr), name, zr); - } else { - dprintk(1, KERN_ERR "%s: Unable to initialise /proc/%s\n", - ZR_DEVNAME(zr), name); - return 1; - } -#endif - return 0; -} - -void -zoran_proc_cleanup (struct zoran *zr) -{ -#ifdef CONFIG_PROC_FS - char name[8]; - - snprintf(name, 7, "zoran%d", zr->id); - if (zr->zoran_proc) - remove_proc_entry(name, NULL); - zr->zoran_proc = NULL; -#endif -} diff --git a/drivers/staging/media/zoran/zoran_procfs.h b/drivers/staging/media/zoran/zoran_procfs.h deleted file mode 100644 index 0ac7cb0011f2..000000000000 --- a/drivers/staging/media/zoran/zoran_procfs.h +++ /dev/null @@ -1,32 +0,0 @@ -/* - * Zoran zr36057/zr36067 PCI controller driver, for the - * Pinnacle/Miro DC10/DC10+/DC30/DC30+, Iomega Buz, Linux - * Media Labs LML33/LML33R10. - * - * This part handles card-specific data and detection - * - * Copyright (C) 2000 Serguei Miridonov - * - * Currently maintained by: - * Ronald Bultje - * Laurent Pinchart - * Mailinglist - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - */ - -#ifndef __ZORAN_PROCFS_H__ -#define __ZORAN_PROCFS_H__ - -extern int zoran_proc_init(struct zoran *zr); -extern void zoran_proc_cleanup(struct zoran *zr); - -#endif /* __ZORAN_PROCFS_H__ */ diff --git a/drivers/staging/media/zoran/zr36016.c b/drivers/staging/media/zoran/zr36016.c deleted file mode 100644 index 8736b9d8d97e..000000000000 --- a/drivers/staging/media/zoran/zr36016.c +++ /dev/null @@ -1,516 +0,0 @@ -/* - * Zoran ZR36016 basic configuration functions - * - * Copyright (C) 2001 Wolfgang Scherr - * - * $Id: zr36016.c,v 1.1.2.14 2003/08/20 19:46:55 rbultje Exp $ - * - * ------------------------------------------------------------------------ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * ------------------------------------------------------------------------ - */ - -#define ZR016_VERSION "v0.7" - -#include -#include -#include -#include - -#include -#include - -/* I/O commands, error codes */ -#include - -/* v4l API */ - -/* headerfile of this module */ -#include "zr36016.h" - -/* codec io API */ -#include "videocodec.h" - -/* it doesn't make sense to have more than 20 or so, - just to prevent some unwanted loops */ -#define MAX_CODECS 20 - -/* amount of chips attached via this driver */ -static int zr36016_codecs; - -/* debugging is available via module parameter */ -static int debug; -module_param(debug, int, 0); -MODULE_PARM_DESC(debug, "Debug level (0-4)"); - -#define dprintk(num, format, args...) \ - do { \ - if (debug >= num) \ - printk(format, ##args); \ - } while (0) - -/* ========================================================================= - Local hardware I/O functions: - - read/write via codec layer (registers are located in the master device) - ========================================================================= */ - -/* read and write functions */ -static u8 -zr36016_read (struct zr36016 *ptr, - u16 reg) -{ - u8 value = 0; - - // just in case something is wrong... - if (ptr->codec->master_data->readreg) - value = - (ptr->codec->master_data-> - readreg(ptr->codec, reg)) & 0xFF; - else - dprintk(1, - KERN_ERR "%s: invalid I/O setup, nothing read!\n", - ptr->name); - - dprintk(4, "%s: reading from 0x%04x: %02x\n", ptr->name, reg, - value); - - return value; -} - -static void -zr36016_write (struct zr36016 *ptr, - u16 reg, - u8 value) -{ - dprintk(4, "%s: writing 0x%02x to 0x%04x\n", ptr->name, value, - reg); - - // just in case something is wrong... - if (ptr->codec->master_data->writereg) { - ptr->codec->master_data->writereg(ptr->codec, reg, value); - } else - dprintk(1, - KERN_ERR - "%s: invalid I/O setup, nothing written!\n", - ptr->name); -} - -/* indirect read and write functions */ -/* the 016 supports auto-addr-increment, but - * writing it all time cost not much and is safer... */ -static u8 -zr36016_readi (struct zr36016 *ptr, - u16 reg) -{ - u8 value = 0; - - // just in case something is wrong... - if ((ptr->codec->master_data->writereg) && - (ptr->codec->master_data->readreg)) { - ptr->codec->master_data->writereg(ptr->codec, ZR016_IADDR, reg & 0x0F); // ADDR - value = (ptr->codec->master_data->readreg(ptr->codec, ZR016_IDATA)) & 0xFF; // DATA - } else - dprintk(1, - KERN_ERR - "%s: invalid I/O setup, nothing read (i)!\n", - ptr->name); - - dprintk(4, "%s: reading indirect from 0x%04x: %02x\n", ptr->name, - reg, value); - return value; -} - -static void -zr36016_writei (struct zr36016 *ptr, - u16 reg, - u8 value) -{ - dprintk(4, "%s: writing indirect 0x%02x to 0x%04x\n", ptr->name, - value, reg); - - // just in case something is wrong... - if (ptr->codec->master_data->writereg) { - ptr->codec->master_data->writereg(ptr->codec, ZR016_IADDR, reg & 0x0F); // ADDR - ptr->codec->master_data->writereg(ptr->codec, ZR016_IDATA, value & 0x0FF); // DATA - } else - dprintk(1, - KERN_ERR - "%s: invalid I/O setup, nothing written (i)!\n", - ptr->name); -} - -/* ========================================================================= - Local helper function: - - version read - ========================================================================= */ - -/* version kept in datastructure */ -static u8 -zr36016_read_version (struct zr36016 *ptr) -{ - ptr->version = zr36016_read(ptr, 0) >> 4; - return ptr->version; -} - -/* ========================================================================= - Local helper function: - - basic test of "connectivity", writes/reads to/from PAX-Lo register - ========================================================================= */ - -static int -zr36016_basic_test (struct zr36016 *ptr) -{ - if (debug) { - int i; - zr36016_writei(ptr, ZR016I_PAX_LO, 0x55); - dprintk(1, KERN_INFO "%s: registers: ", ptr->name); - for (i = 0; i <= 0x0b; i++) - dprintk(1, "%02x ", zr36016_readi(ptr, i)); - dprintk(1, "\n"); - } - // for testing just write 0, then the default value to a register and read - // it back in both cases - zr36016_writei(ptr, ZR016I_PAX_LO, 0x00); - if (zr36016_readi(ptr, ZR016I_PAX_LO) != 0x0) { - dprintk(1, - KERN_ERR - "%s: attach failed, can't connect to vfe processor!\n", - ptr->name); - return -ENXIO; - } - zr36016_writei(ptr, ZR016I_PAX_LO, 0x0d0); - if (zr36016_readi(ptr, ZR016I_PAX_LO) != 0x0d0) { - dprintk(1, - KERN_ERR - "%s: attach failed, can't connect to vfe processor!\n", - ptr->name); - return -ENXIO; - } - // we allow version numbers from 0-3, should be enough, though - zr36016_read_version(ptr); - if (ptr->version & 0x0c) { - dprintk(1, - KERN_ERR - "%s: attach failed, suspicious version %d found...\n", - ptr->name, ptr->version); - return -ENXIO; - } - - return 0; /* looks good! */ -} - -/* ========================================================================= - Local helper function: - - simple loop for pushing the init datasets - NO USE -- - ========================================================================= */ - -#if 0 -static int zr36016_pushit (struct zr36016 *ptr, - u16 startreg, - u16 len, - const char *data) -{ - int i=0; - - dprintk(4, "%s: write data block to 0x%04x (len=%d)\n", - ptr->name, startreg,len); - while (imode == CODEC_DO_COMPRESSION ? - ZR016_COMPRESSION : ZR016_EXPANSION)); - - // misc setup - zr36016_writei(ptr, ZR016I_SETUP1, - (ptr->xdec ? (ZR016_HRFL | ZR016_HORZ) : 0) | - (ptr->ydec ? ZR016_VERT : 0) | ZR016_CNTI); - zr36016_writei(ptr, ZR016I_SETUP2, ZR016_CCIR); - - // Window setup - // (no extra offset for now, norm defines offset, default width height) - zr36016_writei(ptr, ZR016I_PAX_HI, ptr->width >> 8); - zr36016_writei(ptr, ZR016I_PAX_LO, ptr->width & 0xFF); - zr36016_writei(ptr, ZR016I_PAY_HI, ptr->height >> 8); - zr36016_writei(ptr, ZR016I_PAY_LO, ptr->height & 0xFF); - zr36016_writei(ptr, ZR016I_NAX_HI, ptr->xoff >> 8); - zr36016_writei(ptr, ZR016I_NAX_LO, ptr->xoff & 0xFF); - zr36016_writei(ptr, ZR016I_NAY_HI, ptr->yoff >> 8); - zr36016_writei(ptr, ZR016I_NAY_LO, ptr->yoff & 0xFF); - - /* shall we continue now, please? */ - zr36016_write(ptr, ZR016_GOSTOP, 1); -} - -/* ========================================================================= - CODEC API FUNCTIONS - - this functions are accessed by the master via the API structure - ========================================================================= */ - -/* set compression/expansion mode and launches codec - - this should be the last call from the master before starting processing */ -static int -zr36016_set_mode (struct videocodec *codec, - int mode) -{ - struct zr36016 *ptr = (struct zr36016 *) codec->data; - - dprintk(2, "%s: set_mode %d call\n", ptr->name, mode); - - if ((mode != CODEC_DO_EXPANSION) && (mode != CODEC_DO_COMPRESSION)) - return -EINVAL; - - ptr->mode = mode; - zr36016_init(ptr); - - return 0; -} - -/* set picture size */ -static int -zr36016_set_video (struct videocodec *codec, - struct tvnorm *norm, - struct vfe_settings *cap, - struct vfe_polarity *pol) -{ - struct zr36016 *ptr = (struct zr36016 *) codec->data; - - dprintk(2, "%s: set_video %d.%d, %d/%d-%dx%d (0x%x) call\n", - ptr->name, norm->HStart, norm->VStart, - cap->x, cap->y, cap->width, cap->height, - cap->decimation); - - /* if () return -EINVAL; - * trust the master driver that it knows what it does - so - * we allow invalid startx/y for now ... */ - ptr->width = cap->width; - ptr->height = cap->height; - /* (Ronald) This is ugly. zoran_device.c, line 387 - * already mentions what happens if HStart is even - * (blue faces, etc., cr/cb inversed). There's probably - * some good reason why HStart is 0 instead of 1, so I'm - * leaving it to this for now, but really... This can be - * done a lot simpler */ - ptr->xoff = (norm->HStart ? norm->HStart : 1) + cap->x; - /* Something to note here (I don't understand it), setting - * VStart too high will cause the codec to 'not work'. I - * really don't get it. values of 16 (VStart) already break - * it here. Just '0' seems to work. More testing needed! */ - ptr->yoff = norm->VStart + cap->y; - /* (Ronald) dzjeeh, can't this thing do hor_decimation = 4? */ - ptr->xdec = ((cap->decimation & 0xff) == 1) ? 0 : 1; - ptr->ydec = (((cap->decimation >> 8) & 0xff) == 1) ? 0 : 1; - - return 0; -} - -/* additional control functions */ -static int -zr36016_control (struct videocodec *codec, - int type, - int size, - void *data) -{ - struct zr36016 *ptr = (struct zr36016 *) codec->data; - int *ival = (int *) data; - - dprintk(2, "%s: control %d call with %d byte\n", ptr->name, type, - size); - - switch (type) { - case CODEC_G_STATUS: /* get last status - we don't know it ... */ - if (size != sizeof(int)) - return -EFAULT; - *ival = 0; - break; - - case CODEC_G_CODEC_MODE: - if (size != sizeof(int)) - return -EFAULT; - *ival = 0; - break; - - case CODEC_S_CODEC_MODE: - if (size != sizeof(int)) - return -EFAULT; - if (*ival != 0) - return -EINVAL; - /* not needed, do nothing */ - return 0; - - case CODEC_G_VFE: - case CODEC_S_VFE: - return 0; - - case CODEC_S_MMAP: - /* not available, give an error */ - return -ENXIO; - - default: - return -EINVAL; - } - - return size; -} - -/* ========================================================================= - Exit and unregister function: - - Deinitializes Zoran's JPEG processor - ========================================================================= */ - -static int -zr36016_unset (struct videocodec *codec) -{ - struct zr36016 *ptr = codec->data; - - if (ptr) { - /* do wee need some codec deinit here, too ???? */ - - dprintk(1, "%s: finished codec #%d\n", ptr->name, - ptr->num); - kfree(ptr); - codec->data = NULL; - - zr36016_codecs--; - return 0; - } - - return -EFAULT; -} - -/* ========================================================================= - Setup and registry function: - - Initializes Zoran's JPEG processor - - Also sets pixel size, average code size, mode (compr./decompr.) - (the given size is determined by the processor with the video interface) - ========================================================================= */ - -static int -zr36016_setup (struct videocodec *codec) -{ - struct zr36016 *ptr; - int res; - - dprintk(2, "zr36016: initializing VFE subsystem #%d.\n", - zr36016_codecs); - - if (zr36016_codecs == MAX_CODECS) { - dprintk(1, - KERN_ERR "zr36016: Can't attach more codecs!\n"); - return -ENOSPC; - } - //mem structure init - codec->data = ptr = kzalloc(sizeof(struct zr36016), GFP_KERNEL); - if (NULL == ptr) { - dprintk(1, KERN_ERR "zr36016: Can't get enough memory!\n"); - return -ENOMEM; - } - - snprintf(ptr->name, sizeof(ptr->name), "zr36016[%d]", - zr36016_codecs); - ptr->num = zr36016_codecs++; - ptr->codec = codec; - - //testing - res = zr36016_basic_test(ptr); - if (res < 0) { - zr36016_unset(codec); - return res; - } - //final setup - ptr->mode = CODEC_DO_COMPRESSION; - ptr->width = 768; - ptr->height = 288; - ptr->xdec = 1; - ptr->ydec = 0; - zr36016_init(ptr); - - dprintk(1, KERN_INFO "%s: codec v%d attached and running\n", - ptr->name, ptr->version); - - return 0; -} - -static const struct videocodec zr36016_codec = { - .owner = THIS_MODULE, - .name = "zr36016", - .magic = 0L, // magic not used - .flags = - CODEC_FLAG_HARDWARE | CODEC_FLAG_VFE | CODEC_FLAG_ENCODER | - CODEC_FLAG_DECODER, - .type = CODEC_TYPE_ZR36016, - .setup = zr36016_setup, // functionality - .unset = zr36016_unset, - .set_mode = zr36016_set_mode, - .set_video = zr36016_set_video, - .control = zr36016_control, - // others are not used -}; - -/* ========================================================================= - HOOK IN DRIVER AS KERNEL MODULE - ========================================================================= */ - -static int __init -zr36016_init_module (void) -{ - //dprintk(1, "ZR36016 driver %s\n",ZR016_VERSION); - zr36016_codecs = 0; - return videocodec_register(&zr36016_codec); -} - -static void __exit -zr36016_cleanup_module (void) -{ - if (zr36016_codecs) { - dprintk(1, - "zr36016: something's wrong - %d codecs left somehow.\n", - zr36016_codecs); - } - videocodec_unregister(&zr36016_codec); -} - -module_init(zr36016_init_module); -module_exit(zr36016_cleanup_module); - -MODULE_AUTHOR("Wolfgang Scherr "); -MODULE_DESCRIPTION("Driver module for ZR36016 video frontends " - ZR016_VERSION); -MODULE_LICENSE("GPL"); diff --git a/drivers/staging/media/zoran/zr36016.h b/drivers/staging/media/zoran/zr36016.h deleted file mode 100644 index 784bcf5727b8..000000000000 --- a/drivers/staging/media/zoran/zr36016.h +++ /dev/null @@ -1,107 +0,0 @@ -/* - * Zoran ZR36016 basic configuration functions - header file - * - * Copyright (C) 2001 Wolfgang Scherr - * - * $Id: zr36016.h,v 1.1.2.3 2003/01/14 21:18:07 rbultje Exp $ - * - * ------------------------------------------------------------------------ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * ------------------------------------------------------------------------ - */ - -#ifndef ZR36016_H -#define ZR36016_H - -/* data stored for each zoran jpeg codec chip */ -struct zr36016 { - char name[32]; - int num; - /* io datastructure */ - struct videocodec *codec; - // coder status - __u8 version; - // actual coder setup - int mode; - - __u16 xoff; - __u16 yoff; - __u16 width; - __u16 height; - __u16 xdec; - __u16 ydec; -}; - -/* direct register addresses */ -#define ZR016_GOSTOP 0x00 -#define ZR016_MODE 0x01 -#define ZR016_IADDR 0x02 -#define ZR016_IDATA 0x03 - -/* indirect register addresses */ -#define ZR016I_SETUP1 0x00 -#define ZR016I_SETUP2 0x01 -#define ZR016I_NAX_LO 0x02 -#define ZR016I_NAX_HI 0x03 -#define ZR016I_PAX_LO 0x04 -#define ZR016I_PAX_HI 0x05 -#define ZR016I_NAY_LO 0x06 -#define ZR016I_NAY_HI 0x07 -#define ZR016I_PAY_LO 0x08 -#define ZR016I_PAY_HI 0x09 -#define ZR016I_NOL_LO 0x0a -#define ZR016I_NOL_HI 0x0b - -/* possible values for mode register */ -#define ZR016_RGB444_YUV444 0x00 -#define ZR016_RGB444_YUV422 0x01 -#define ZR016_RGB444_YUV411 0x02 -#define ZR016_RGB444_Y400 0x03 -#define ZR016_RGB444_RGB444 0x04 -#define ZR016_YUV444_YUV444 0x08 -#define ZR016_YUV444_YUV422 0x09 -#define ZR016_YUV444_YUV411 0x0a -#define ZR016_YUV444_Y400 0x0b -#define ZR016_YUV444_RGB444 0x0c -#define ZR016_YUV422_YUV422 0x11 -#define ZR016_YUV422_YUV411 0x12 -#define ZR016_YUV422_Y400 0x13 -#define ZR016_YUV411_YUV411 0x16 -#define ZR016_YUV411_Y400 0x17 -#define ZR016_4444_4444 0x19 -#define ZR016_100_100 0x1b - -#define ZR016_RGB444 0x00 -#define ZR016_YUV444 0x20 -#define ZR016_YUV422 0x40 - -#define ZR016_COMPRESSION 0x80 -#define ZR016_EXPANSION 0x80 - -/* possible values for setup 1 register */ -#define ZR016_CKRT 0x80 -#define ZR016_VERT 0x40 -#define ZR016_HORZ 0x20 -#define ZR016_HRFL 0x10 -#define ZR016_DSFL 0x08 -#define ZR016_SBFL 0x04 -#define ZR016_RSTR 0x02 -#define ZR016_CNTI 0x01 - -/* possible values for setup 2 register */ -#define ZR016_SYEN 0x40 -#define ZR016_CCIR 0x04 -#define ZR016_SIGN 0x02 -#define ZR016_YMCS 0x01 - -#endif /*fndef ZR36016_H */ diff --git a/drivers/staging/media/zoran/zr36050.c b/drivers/staging/media/zoran/zr36050.c deleted file mode 100644 index 5ebfc16672f3..000000000000 --- a/drivers/staging/media/zoran/zr36050.c +++ /dev/null @@ -1,896 +0,0 @@ -/* - * Zoran ZR36050 basic configuration functions - * - * Copyright (C) 2001 Wolfgang Scherr - * - * $Id: zr36050.c,v 1.1.2.11 2003/08/03 14:54:53 rbultje Exp $ - * - * ------------------------------------------------------------------------ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * ------------------------------------------------------------------------ - */ - -#define ZR050_VERSION "v0.7.1" - -#include -#include -#include -#include - -#include -#include - -/* I/O commands, error codes */ -#include - -/* headerfile of this module */ -#include "zr36050.h" - -/* codec io API */ -#include "videocodec.h" - -/* it doesn't make sense to have more than 20 or so, - just to prevent some unwanted loops */ -#define MAX_CODECS 20 - -/* amount of chips attached via this driver */ -static int zr36050_codecs; - -/* debugging is available via module parameter */ -static int debug; -module_param(debug, int, 0); -MODULE_PARM_DESC(debug, "Debug level (0-4)"); - -#define dprintk(num, format, args...) \ - do { \ - if (debug >= num) \ - printk(format, ##args); \ - } while (0) - -/* ========================================================================= - Local hardware I/O functions: - - read/write via codec layer (registers are located in the master device) - ========================================================================= */ - -/* read and write functions */ -static u8 -zr36050_read (struct zr36050 *ptr, - u16 reg) -{ - u8 value = 0; - - // just in case something is wrong... - if (ptr->codec->master_data->readreg) - value = (ptr->codec->master_data->readreg(ptr->codec, - reg)) & 0xFF; - else - dprintk(1, - KERN_ERR "%s: invalid I/O setup, nothing read!\n", - ptr->name); - - dprintk(4, "%s: reading from 0x%04x: %02x\n", ptr->name, reg, - value); - - return value; -} - -static void -zr36050_write (struct zr36050 *ptr, - u16 reg, - u8 value) -{ - dprintk(4, "%s: writing 0x%02x to 0x%04x\n", ptr->name, value, - reg); - - // just in case something is wrong... - if (ptr->codec->master_data->writereg) - ptr->codec->master_data->writereg(ptr->codec, reg, value); - else - dprintk(1, - KERN_ERR - "%s: invalid I/O setup, nothing written!\n", - ptr->name); -} - -/* ========================================================================= - Local helper function: - - status read - ========================================================================= */ - -/* status is kept in datastructure */ -static u8 -zr36050_read_status1 (struct zr36050 *ptr) -{ - ptr->status1 = zr36050_read(ptr, ZR050_STATUS_1); - - zr36050_read(ptr, 0); - return ptr->status1; -} - -/* ========================================================================= - Local helper function: - - scale factor read - ========================================================================= */ - -/* scale factor is kept in datastructure */ -static u16 -zr36050_read_scalefactor (struct zr36050 *ptr) -{ - ptr->scalefact = (zr36050_read(ptr, ZR050_SF_HI) << 8) | - (zr36050_read(ptr, ZR050_SF_LO) & 0xFF); - - /* leave 0 selected for an eventually GO from master */ - zr36050_read(ptr, 0); - return ptr->scalefact; -} - -/* ========================================================================= - Local helper function: - - wait if codec is ready to proceed (end of processing) or time is over - ========================================================================= */ - -static void -zr36050_wait_end (struct zr36050 *ptr) -{ - int i = 0; - - while (!(zr36050_read_status1(ptr) & 0x4)) { - udelay(1); - if (i++ > 200000) { // 200ms, there is for sure something wrong!!! - dprintk(1, - "%s: timeout at wait_end (last status: 0x%02x)\n", - ptr->name, ptr->status1); - break; - } - } -} - -/* ========================================================================= - Local helper function: - - basic test of "connectivity", writes/reads to/from memory the SOF marker - ========================================================================= */ - -static int -zr36050_basic_test (struct zr36050 *ptr) -{ - zr36050_write(ptr, ZR050_SOF_IDX, 0x00); - zr36050_write(ptr, ZR050_SOF_IDX + 1, 0x00); - if ((zr36050_read(ptr, ZR050_SOF_IDX) | - zr36050_read(ptr, ZR050_SOF_IDX + 1)) != 0x0000) { - dprintk(1, - KERN_ERR - "%s: attach failed, can't connect to jpeg processor!\n", - ptr->name); - return -ENXIO; - } - zr36050_write(ptr, ZR050_SOF_IDX, 0xff); - zr36050_write(ptr, ZR050_SOF_IDX + 1, 0xc0); - if (((zr36050_read(ptr, ZR050_SOF_IDX) << 8) | - zr36050_read(ptr, ZR050_SOF_IDX + 1)) != 0xffc0) { - dprintk(1, - KERN_ERR - "%s: attach failed, can't connect to jpeg processor!\n", - ptr->name); - return -ENXIO; - } - - zr36050_wait_end(ptr); - if ((ptr->status1 & 0x4) == 0) { - dprintk(1, - KERN_ERR - "%s: attach failed, jpeg processor failed (end flag)!\n", - ptr->name); - return -EBUSY; - } - - return 0; /* looks good! */ -} - -/* ========================================================================= - Local helper function: - - simple loop for pushing the init datasets - ========================================================================= */ - -static int -zr36050_pushit (struct zr36050 *ptr, - u16 startreg, - u16 len, - const char *data) -{ - int i = 0; - - dprintk(4, "%s: write data block to 0x%04x (len=%d)\n", ptr->name, - startreg, len); - while (i < len) { - zr36050_write(ptr, startreg++, data[i++]); - } - - return i; -} - -/* ========================================================================= - Basic datasets: - - jpeg baseline setup data (you find it on lots places in internet, or just - extract it from any regular .jpg image...) - - Could be variable, but until it's not needed it they are just fixed to save - memory. Otherwise expand zr36050 structure with arrays, push the values to - it and initialize from there, as e.g. the linux zr36057/60 driver does it. - ========================================================================= */ - -static const char zr36050_dqt[0x86] = { - 0xff, 0xdb, //Marker: DQT - 0x00, 0x84, //Length: 2*65+2 - 0x00, //Pq,Tq first table - 0x10, 0x0b, 0x0c, 0x0e, 0x0c, 0x0a, 0x10, 0x0e, - 0x0d, 0x0e, 0x12, 0x11, 0x10, 0x13, 0x18, 0x28, - 0x1a, 0x18, 0x16, 0x16, 0x18, 0x31, 0x23, 0x25, - 0x1d, 0x28, 0x3a, 0x33, 0x3d, 0x3c, 0x39, 0x33, - 0x38, 0x37, 0x40, 0x48, 0x5c, 0x4e, 0x40, 0x44, - 0x57, 0x45, 0x37, 0x38, 0x50, 0x6d, 0x51, 0x57, - 0x5f, 0x62, 0x67, 0x68, 0x67, 0x3e, 0x4d, 0x71, - 0x79, 0x70, 0x64, 0x78, 0x5c, 0x65, 0x67, 0x63, - 0x01, //Pq,Tq second table - 0x11, 0x12, 0x12, 0x18, 0x15, 0x18, 0x2f, 0x1a, - 0x1a, 0x2f, 0x63, 0x42, 0x38, 0x42, 0x63, 0x63, - 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, - 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, - 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, - 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, - 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, - 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63 -}; - -static const char zr36050_dht[0x1a4] = { - 0xff, 0xc4, //Marker: DHT - 0x01, 0xa2, //Length: 2*AC, 2*DC - 0x00, //DC first table - 0x00, 0x01, 0x05, 0x01, 0x01, 0x01, 0x01, 0x01, - 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, - 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A, 0x0B, - 0x01, //DC second table - 0x00, 0x03, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, - 0x01, 0x01, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, - 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A, 0x0B, - 0x10, //AC first table - 0x00, 0x02, 0x01, 0x03, 0x03, 0x02, 0x04, 0x03, - 0x05, 0x05, 0x04, 0x04, 0x00, 0x00, - 0x01, 0x7D, 0x01, 0x02, 0x03, 0x00, 0x04, 0x11, - 0x05, 0x12, 0x21, 0x31, 0x41, 0x06, 0x13, 0x51, 0x61, - 0x07, 0x22, 0x71, 0x14, 0x32, 0x81, 0x91, 0xA1, - 0x08, 0x23, 0x42, 0xB1, 0xC1, 0x15, 0x52, 0xD1, 0xF0, 0x24, - 0x33, 0x62, 0x72, 0x82, 0x09, 0x0A, 0x16, 0x17, - 0x18, 0x19, 0x1A, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2A, 0x34, - 0x35, 0x36, 0x37, 0x38, 0x39, 0x3A, 0x43, 0x44, - 0x45, 0x46, 0x47, 0x48, 0x49, 0x4A, 0x53, 0x54, 0x55, 0x56, - 0x57, 0x58, 0x59, 0x5A, 0x63, 0x64, 0x65, 0x66, - 0x67, 0x68, 0x69, 0x6A, 0x73, 0x74, 0x75, 0x76, 0x77, 0x78, - 0x79, 0x7A, 0x83, 0x84, 0x85, 0x86, 0x87, 0x88, - 0x89, 0x8A, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97, 0x98, 0x99, - 0x9A, 0xA2, 0xA3, 0xA4, 0xA5, 0xA6, 0xA7, 0xA8, - 0xA9, 0xAA, 0xB2, 0xB3, 0xB4, 0xB5, 0xB6, 0xB7, 0xB8, 0xB9, - 0xBA, 0xC2, 0xC3, 0xC4, 0xC5, 0xC6, 0xC7, 0xC8, - 0xC9, 0xCA, 0xD2, 0xD3, 0xD4, 0xD5, 0xD6, 0xD7, 0xD8, 0xD9, - 0xDA, 0xE1, 0xE2, 0xE3, 0xE4, 0xE5, 0xE6, 0xE7, - 0xE8, 0xE9, 0xEA, 0xF1, 0xF2, 0xF3, 0xF4, 0xF5, 0xF6, 0xF7, - 0xF8, 0xF9, 0xFA, - 0x11, //AC second table - 0x00, 0x02, 0x01, 0x02, 0x04, 0x04, 0x03, 0x04, - 0x07, 0x05, 0x04, 0x04, 0x00, 0x01, - 0x02, 0x77, 0x00, 0x01, 0x02, 0x03, 0x11, 0x04, - 0x05, 0x21, 0x31, 0x06, 0x12, 0x41, 0x51, 0x07, 0x61, 0x71, - 0x13, 0x22, 0x32, 0x81, 0x08, 0x14, 0x42, 0x91, - 0xA1, 0xB1, 0xC1, 0x09, 0x23, 0x33, 0x52, 0xF0, 0x15, 0x62, - 0x72, 0xD1, 0x0A, 0x16, 0x24, 0x34, 0xE1, 0x25, - 0xF1, 0x17, 0x18, 0x19, 0x1A, 0x26, 0x27, 0x28, 0x29, 0x2A, - 0x35, 0x36, 0x37, 0x38, 0x39, 0x3A, 0x43, 0x44, - 0x45, 0x46, 0x47, 0x48, 0x49, 0x4A, 0x53, 0x54, 0x55, 0x56, - 0x57, 0x58, 0x59, 0x5A, 0x63, 0x64, 0x65, 0x66, - 0x67, 0x68, 0x69, 0x6A, 0x73, 0x74, 0x75, 0x76, 0x77, 0x78, - 0x79, 0x7A, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87, - 0x88, 0x89, 0x8A, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97, 0x98, - 0x99, 0x9A, 0xA2, 0xA3, 0xA4, 0xA5, 0xA6, 0xA7, - 0xA8, 0xA9, 0xAA, 0xB2, 0xB3, 0xB4, 0xB5, 0xB6, 0xB7, 0xB8, - 0xB9, 0xBA, 0xC2, 0xC3, 0xC4, 0xC5, 0xC6, 0xC7, - 0xC8, 0xC9, 0xCA, 0xD2, 0xD3, 0xD4, 0xD5, 0xD6, 0xD7, 0xD8, - 0xD9, 0xDA, 0xE2, 0xE3, 0xE4, 0xE5, 0xE6, 0xE7, - 0xE8, 0xE9, 0xEA, 0xF2, 0xF3, 0xF4, 0xF5, 0xF6, 0xF7, 0xF8, - 0xF9, 0xFA -}; - -/* jpeg baseline setup, this is just fixed in this driver (YUV pictures) */ -#define NO_OF_COMPONENTS 0x3 //Y,U,V -#define BASELINE_PRECISION 0x8 //MCU size (?) -static const char zr36050_tq[8] = { 0, 1, 1, 0, 0, 0, 0, 0 }; //table idx's QT -static const char zr36050_td[8] = { 0, 1, 1, 0, 0, 0, 0, 0 }; //table idx's DC -static const char zr36050_ta[8] = { 0, 1, 1, 0, 0, 0, 0, 0 }; //table idx's AC - -/* horizontal 422 decimation setup (maybe we support 411 or so later, too) */ -static const char zr36050_decimation_h[8] = { 2, 1, 1, 0, 0, 0, 0, 0 }; -static const char zr36050_decimation_v[8] = { 1, 1, 1, 0, 0, 0, 0, 0 }; - -/* ========================================================================= - Local helper functions: - - calculation and setup of parameter-dependent JPEG baseline segments - (needed for compression only) - ========================================================================= */ - -/* ------------------------------------------------------------------------- */ - -/* SOF (start of frame) segment depends on width, height and sampling ratio - of each color component */ - -static int -zr36050_set_sof (struct zr36050 *ptr) -{ - char sof_data[34]; // max. size of register set - int i; - - dprintk(3, "%s: write SOF (%dx%d, %d components)\n", ptr->name, - ptr->width, ptr->height, NO_OF_COMPONENTS); - sof_data[0] = 0xff; - sof_data[1] = 0xc0; - sof_data[2] = 0x00; - sof_data[3] = (3 * NO_OF_COMPONENTS) + 8; - sof_data[4] = BASELINE_PRECISION; // only '8' possible with zr36050 - sof_data[5] = (ptr->height) >> 8; - sof_data[6] = (ptr->height) & 0xff; - sof_data[7] = (ptr->width) >> 8; - sof_data[8] = (ptr->width) & 0xff; - sof_data[9] = NO_OF_COMPONENTS; - for (i = 0; i < NO_OF_COMPONENTS; i++) { - sof_data[10 + (i * 3)] = i; // index identifier - sof_data[11 + (i * 3)] = (ptr->h_samp_ratio[i] << 4) | (ptr->v_samp_ratio[i]); // sampling ratios - sof_data[12 + (i * 3)] = zr36050_tq[i]; // Q table selection - } - return zr36050_pushit(ptr, ZR050_SOF_IDX, - (3 * NO_OF_COMPONENTS) + 10, sof_data); -} - -/* ------------------------------------------------------------------------- */ - -/* SOS (start of scan) segment depends on the used scan components - of each color component */ - -static int -zr36050_set_sos (struct zr36050 *ptr) -{ - char sos_data[16]; // max. size of register set - int i; - - dprintk(3, "%s: write SOS\n", ptr->name); - sos_data[0] = 0xff; - sos_data[1] = 0xda; - sos_data[2] = 0x00; - sos_data[3] = 2 + 1 + (2 * NO_OF_COMPONENTS) + 3; - sos_data[4] = NO_OF_COMPONENTS; - for (i = 0; i < NO_OF_COMPONENTS; i++) { - sos_data[5 + (i * 2)] = i; // index - sos_data[6 + (i * 2)] = (zr36050_td[i] << 4) | zr36050_ta[i]; // AC/DC tbl.sel. - } - sos_data[2 + 1 + (2 * NO_OF_COMPONENTS) + 2] = 00; // scan start - sos_data[2 + 1 + (2 * NO_OF_COMPONENTS) + 3] = 0x3F; - sos_data[2 + 1 + (2 * NO_OF_COMPONENTS) + 4] = 00; - return zr36050_pushit(ptr, ZR050_SOS1_IDX, - 4 + 1 + (2 * NO_OF_COMPONENTS) + 3, - sos_data); -} - -/* ------------------------------------------------------------------------- */ - -/* DRI (define restart interval) */ - -static int -zr36050_set_dri (struct zr36050 *ptr) -{ - char dri_data[6]; // max. size of register set - - dprintk(3, "%s: write DRI\n", ptr->name); - dri_data[0] = 0xff; - dri_data[1] = 0xdd; - dri_data[2] = 0x00; - dri_data[3] = 0x04; - dri_data[4] = ptr->dri >> 8; - dri_data[5] = ptr->dri & 0xff; - return zr36050_pushit(ptr, ZR050_DRI_IDX, 6, dri_data); -} - -/* ========================================================================= - Setup function: - - Setup compression/decompression of Zoran's JPEG processor - ( see also zoran 36050 manual ) - - ... sorry for the spaghetti code ... - ========================================================================= */ -static void -zr36050_init (struct zr36050 *ptr) -{ - int sum = 0; - long bitcnt, tmp; - - if (ptr->mode == CODEC_DO_COMPRESSION) { - dprintk(2, "%s: COMPRESSION SETUP\n", ptr->name); - - /* 050 communicates with 057 in master mode */ - zr36050_write(ptr, ZR050_HARDWARE, ZR050_HW_MSTR); - - /* encoding table preload for compression */ - zr36050_write(ptr, ZR050_MODE, - ZR050_MO_COMP | ZR050_MO_TLM); - zr36050_write(ptr, ZR050_OPTIONS, 0); - - /* disable all IRQs */ - zr36050_write(ptr, ZR050_INT_REQ_0, 0); - zr36050_write(ptr, ZR050_INT_REQ_1, 3); // low 2 bits always 1 - - /* volume control settings */ - /*zr36050_write(ptr, ZR050_MBCV, ptr->max_block_vol);*/ - zr36050_write(ptr, ZR050_SF_HI, ptr->scalefact >> 8); - zr36050_write(ptr, ZR050_SF_LO, ptr->scalefact & 0xff); - - zr36050_write(ptr, ZR050_AF_HI, 0xff); - zr36050_write(ptr, ZR050_AF_M, 0xff); - zr36050_write(ptr, ZR050_AF_LO, 0xff); - - /* setup the variable jpeg tables */ - sum += zr36050_set_sof(ptr); - sum += zr36050_set_sos(ptr); - sum += zr36050_set_dri(ptr); - - /* setup the fixed jpeg tables - maybe variable, though - - * (see table init section above) */ - dprintk(3, "%s: write DQT, DHT, APP\n", ptr->name); - sum += zr36050_pushit(ptr, ZR050_DQT_IDX, - sizeof(zr36050_dqt), zr36050_dqt); - sum += zr36050_pushit(ptr, ZR050_DHT_IDX, - sizeof(zr36050_dht), zr36050_dht); - zr36050_write(ptr, ZR050_APP_IDX, 0xff); - zr36050_write(ptr, ZR050_APP_IDX + 1, 0xe0 + ptr->app.appn); - zr36050_write(ptr, ZR050_APP_IDX + 2, 0x00); - zr36050_write(ptr, ZR050_APP_IDX + 3, ptr->app.len + 2); - sum += zr36050_pushit(ptr, ZR050_APP_IDX + 4, 60, - ptr->app.data) + 4; - zr36050_write(ptr, ZR050_COM_IDX, 0xff); - zr36050_write(ptr, ZR050_COM_IDX + 1, 0xfe); - zr36050_write(ptr, ZR050_COM_IDX + 2, 0x00); - zr36050_write(ptr, ZR050_COM_IDX + 3, ptr->com.len + 2); - sum += zr36050_pushit(ptr, ZR050_COM_IDX + 4, 60, - ptr->com.data) + 4; - - /* do the internal huffman table preload */ - zr36050_write(ptr, ZR050_MARKERS_EN, ZR050_ME_DHTI); - - zr36050_write(ptr, ZR050_GO, 1); // launch codec - zr36050_wait_end(ptr); - dprintk(2, "%s: Status after table preload: 0x%02x\n", - ptr->name, ptr->status1); - - if ((ptr->status1 & 0x4) == 0) { - dprintk(1, KERN_ERR "%s: init aborted!\n", - ptr->name); - return; // something is wrong, its timed out!!!! - } - - /* setup misc. data for compression (target code sizes) */ - - /* size of compressed code to reach without header data */ - sum = ptr->real_code_vol - sum; - bitcnt = sum << 3; /* need the size in bits */ - - tmp = bitcnt >> 16; - dprintk(3, - "%s: code: csize=%d, tot=%d, bit=%ld, highbits=%ld\n", - ptr->name, sum, ptr->real_code_vol, bitcnt, tmp); - zr36050_write(ptr, ZR050_TCV_NET_HI, tmp >> 8); - zr36050_write(ptr, ZR050_TCV_NET_MH, tmp & 0xff); - tmp = bitcnt & 0xffff; - zr36050_write(ptr, ZR050_TCV_NET_ML, tmp >> 8); - zr36050_write(ptr, ZR050_TCV_NET_LO, tmp & 0xff); - - bitcnt -= bitcnt >> 7; // bits without stuffing - bitcnt -= ((bitcnt * 5) >> 6); // bits without eob - - tmp = bitcnt >> 16; - dprintk(3, "%s: code: nettobit=%ld, highnettobits=%ld\n", - ptr->name, bitcnt, tmp); - zr36050_write(ptr, ZR050_TCV_DATA_HI, tmp >> 8); - zr36050_write(ptr, ZR050_TCV_DATA_MH, tmp & 0xff); - tmp = bitcnt & 0xffff; - zr36050_write(ptr, ZR050_TCV_DATA_ML, tmp >> 8); - zr36050_write(ptr, ZR050_TCV_DATA_LO, tmp & 0xff); - - /* compression setup with or without bitrate control */ - zr36050_write(ptr, ZR050_MODE, - ZR050_MO_COMP | ZR050_MO_PASS2 | - (ptr->bitrate_ctrl ? ZR050_MO_BRC : 0)); - - /* this headers seem to deliver "valid AVI" jpeg frames */ - zr36050_write(ptr, ZR050_MARKERS_EN, - ZR050_ME_DQT | ZR050_ME_DHT | - ((ptr->app.len > 0) ? ZR050_ME_APP : 0) | - ((ptr->com.len > 0) ? ZR050_ME_COM : 0)); - } else { - dprintk(2, "%s: EXPANSION SETUP\n", ptr->name); - - /* 050 communicates with 055 in master mode */ - zr36050_write(ptr, ZR050_HARDWARE, - ZR050_HW_MSTR | ZR050_HW_CFIS_2_CLK); - - /* encoding table preload */ - zr36050_write(ptr, ZR050_MODE, ZR050_MO_TLM); - - /* disable all IRQs */ - zr36050_write(ptr, ZR050_INT_REQ_0, 0); - zr36050_write(ptr, ZR050_INT_REQ_1, 3); // low 2 bits always 1 - - dprintk(3, "%s: write DHT\n", ptr->name); - zr36050_pushit(ptr, ZR050_DHT_IDX, sizeof(zr36050_dht), - zr36050_dht); - - /* do the internal huffman table preload */ - zr36050_write(ptr, ZR050_MARKERS_EN, ZR050_ME_DHTI); - - zr36050_write(ptr, ZR050_GO, 1); // launch codec - zr36050_wait_end(ptr); - dprintk(2, "%s: Status after table preload: 0x%02x\n", - ptr->name, ptr->status1); - - if ((ptr->status1 & 0x4) == 0) { - dprintk(1, KERN_ERR "%s: init aborted!\n", - ptr->name); - return; // something is wrong, its timed out!!!! - } - - /* setup misc. data for expansion */ - zr36050_write(ptr, ZR050_MODE, 0); - zr36050_write(ptr, ZR050_MARKERS_EN, 0); - } - - /* adr on selected, to allow GO from master */ - zr36050_read(ptr, 0); -} - -/* ========================================================================= - CODEC API FUNCTIONS - - this functions are accessed by the master via the API structure - ========================================================================= */ - -/* set compression/expansion mode and launches codec - - this should be the last call from the master before starting processing */ -static int -zr36050_set_mode (struct videocodec *codec, - int mode) -{ - struct zr36050 *ptr = (struct zr36050 *) codec->data; - - dprintk(2, "%s: set_mode %d call\n", ptr->name, mode); - - if ((mode != CODEC_DO_EXPANSION) && (mode != CODEC_DO_COMPRESSION)) - return -EINVAL; - - ptr->mode = mode; - zr36050_init(ptr); - - return 0; -} - -/* set picture size (norm is ignored as the codec doesn't know about it) */ -static int -zr36050_set_video (struct videocodec *codec, - struct tvnorm *norm, - struct vfe_settings *cap, - struct vfe_polarity *pol) -{ - struct zr36050 *ptr = (struct zr36050 *) codec->data; - int size; - - dprintk(2, "%s: set_video %d.%d, %d/%d-%dx%d (0x%x) q%d call\n", - ptr->name, norm->HStart, norm->VStart, - cap->x, cap->y, cap->width, cap->height, - cap->decimation, cap->quality); - /* if () return -EINVAL; - * trust the master driver that it knows what it does - so - * we allow invalid startx/y and norm for now ... */ - ptr->width = cap->width / (cap->decimation & 0xff); - ptr->height = cap->height / ((cap->decimation >> 8) & 0xff); - - /* (KM) JPEG quality */ - size = ptr->width * ptr->height; - size *= 16; /* size in bits */ - /* apply quality setting */ - size = size * cap->quality / 200; - - /* Minimum: 1kb */ - if (size < 8192) - size = 8192; - /* Maximum: 7/8 of code buffer */ - if (size > ptr->total_code_vol * 7) - size = ptr->total_code_vol * 7; - - ptr->real_code_vol = size >> 3; /* in bytes */ - - /* Set max_block_vol here (previously in zr36050_init, moved - * here for consistency with zr36060 code */ - zr36050_write(ptr, ZR050_MBCV, ptr->max_block_vol); - - return 0; -} - -/* additional control functions */ -static int -zr36050_control (struct videocodec *codec, - int type, - int size, - void *data) -{ - struct zr36050 *ptr = (struct zr36050 *) codec->data; - int *ival = (int *) data; - - dprintk(2, "%s: control %d call with %d byte\n", ptr->name, type, - size); - - switch (type) { - case CODEC_G_STATUS: /* get last status */ - if (size != sizeof(int)) - return -EFAULT; - zr36050_read_status1(ptr); - *ival = ptr->status1; - break; - - case CODEC_G_CODEC_MODE: - if (size != sizeof(int)) - return -EFAULT; - *ival = CODEC_MODE_BJPG; - break; - - case CODEC_S_CODEC_MODE: - if (size != sizeof(int)) - return -EFAULT; - if (*ival != CODEC_MODE_BJPG) - return -EINVAL; - /* not needed, do nothing */ - return 0; - - case CODEC_G_VFE: - case CODEC_S_VFE: - /* not needed, do nothing */ - return 0; - - case CODEC_S_MMAP: - /* not available, give an error */ - return -ENXIO; - - case CODEC_G_JPEG_TDS_BYTE: /* get target volume in byte */ - if (size != sizeof(int)) - return -EFAULT; - *ival = ptr->total_code_vol; - break; - - case CODEC_S_JPEG_TDS_BYTE: /* get target volume in byte */ - if (size != sizeof(int)) - return -EFAULT; - ptr->total_code_vol = *ival; - /* (Kieran Morrissey) - * code copied from zr36060.c to ensure proper bitrate */ - ptr->real_code_vol = (ptr->total_code_vol * 6) >> 3; - break; - - case CODEC_G_JPEG_SCALE: /* get scaling factor */ - if (size != sizeof(int)) - return -EFAULT; - *ival = zr36050_read_scalefactor(ptr); - break; - - case CODEC_S_JPEG_SCALE: /* set scaling factor */ - if (size != sizeof(int)) - return -EFAULT; - ptr->scalefact = *ival; - break; - - case CODEC_G_JPEG_APP_DATA: { /* get appn marker data */ - struct jpeg_app_marker *app = data; - - if (size != sizeof(struct jpeg_app_marker)) - return -EFAULT; - - *app = ptr->app; - break; - } - - case CODEC_S_JPEG_APP_DATA: { /* set appn marker data */ - struct jpeg_app_marker *app = data; - - if (size != sizeof(struct jpeg_app_marker)) - return -EFAULT; - - ptr->app = *app; - break; - } - - case CODEC_G_JPEG_COM_DATA: { /* get comment marker data */ - struct jpeg_com_marker *com = data; - - if (size != sizeof(struct jpeg_com_marker)) - return -EFAULT; - - *com = ptr->com; - break; - } - - case CODEC_S_JPEG_COM_DATA: { /* set comment marker data */ - struct jpeg_com_marker *com = data; - - if (size != sizeof(struct jpeg_com_marker)) - return -EFAULT; - - ptr->com = *com; - break; - } - - default: - return -EINVAL; - } - - return size; -} - -/* ========================================================================= - Exit and unregister function: - - Deinitializes Zoran's JPEG processor - ========================================================================= */ - -static int -zr36050_unset (struct videocodec *codec) -{ - struct zr36050 *ptr = codec->data; - - if (ptr) { - /* do wee need some codec deinit here, too ???? */ - - dprintk(1, "%s: finished codec #%d\n", ptr->name, - ptr->num); - kfree(ptr); - codec->data = NULL; - - zr36050_codecs--; - return 0; - } - - return -EFAULT; -} - -/* ========================================================================= - Setup and registry function: - - Initializes Zoran's JPEG processor - - Also sets pixel size, average code size, mode (compr./decompr.) - (the given size is determined by the processor with the video interface) - ========================================================================= */ - -static int -zr36050_setup (struct videocodec *codec) -{ - struct zr36050 *ptr; - int res; - - dprintk(2, "zr36050: initializing MJPEG subsystem #%d.\n", - zr36050_codecs); - - if (zr36050_codecs == MAX_CODECS) { - dprintk(1, - KERN_ERR "zr36050: Can't attach more codecs!\n"); - return -ENOSPC; - } - //mem structure init - codec->data = ptr = kzalloc(sizeof(struct zr36050), GFP_KERNEL); - if (NULL == ptr) { - dprintk(1, KERN_ERR "zr36050: Can't get enough memory!\n"); - return -ENOMEM; - } - - snprintf(ptr->name, sizeof(ptr->name), "zr36050[%d]", - zr36050_codecs); - ptr->num = zr36050_codecs++; - ptr->codec = codec; - - //testing - res = zr36050_basic_test(ptr); - if (res < 0) { - zr36050_unset(codec); - return res; - } - //final setup - memcpy(ptr->h_samp_ratio, zr36050_decimation_h, 8); - memcpy(ptr->v_samp_ratio, zr36050_decimation_v, 8); - - ptr->bitrate_ctrl = 0; /* 0 or 1 - fixed file size flag - * (what is the difference?) */ - ptr->mode = CODEC_DO_COMPRESSION; - ptr->width = 384; - ptr->height = 288; - ptr->total_code_vol = 16000; - ptr->max_block_vol = 240; - ptr->scalefact = 0x100; - ptr->dri = 1; - - /* no app/com marker by default */ - ptr->app.appn = 0; - ptr->app.len = 0; - ptr->com.len = 0; - - zr36050_init(ptr); - - dprintk(1, KERN_INFO "%s: codec attached and running\n", - ptr->name); - - return 0; -} - -static const struct videocodec zr36050_codec = { - .owner = THIS_MODULE, - .name = "zr36050", - .magic = 0L, // magic not used - .flags = - CODEC_FLAG_JPEG | CODEC_FLAG_HARDWARE | CODEC_FLAG_ENCODER | - CODEC_FLAG_DECODER, - .type = CODEC_TYPE_ZR36050, - .setup = zr36050_setup, // functionality - .unset = zr36050_unset, - .set_mode = zr36050_set_mode, - .set_video = zr36050_set_video, - .control = zr36050_control, - // others are not used -}; - -/* ========================================================================= - HOOK IN DRIVER AS KERNEL MODULE - ========================================================================= */ - -static int __init -zr36050_init_module (void) -{ - //dprintk(1, "ZR36050 driver %s\n",ZR050_VERSION); - zr36050_codecs = 0; - return videocodec_register(&zr36050_codec); -} - -static void __exit -zr36050_cleanup_module (void) -{ - if (zr36050_codecs) { - dprintk(1, - "zr36050: something's wrong - %d codecs left somehow.\n", - zr36050_codecs); - } - videocodec_unregister(&zr36050_codec); -} - -module_init(zr36050_init_module); -module_exit(zr36050_cleanup_module); - -MODULE_AUTHOR("Wolfgang Scherr "); -MODULE_DESCRIPTION("Driver module for ZR36050 jpeg processors " - ZR050_VERSION); -MODULE_LICENSE("GPL"); diff --git a/drivers/staging/media/zoran/zr36050.h b/drivers/staging/media/zoran/zr36050.h deleted file mode 100644 index 9236486d3c2b..000000000000 --- a/drivers/staging/media/zoran/zr36050.h +++ /dev/null @@ -1,179 +0,0 @@ -/* - * Zoran ZR36050 basic configuration functions - header file - * - * Copyright (C) 2001 Wolfgang Scherr - * - * $Id: zr36050.h,v 1.1.2.2 2003/01/14 21:18:22 rbultje Exp $ - * - * ------------------------------------------------------------------------ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * ------------------------------------------------------------------------ - */ - -#ifndef ZR36050_H -#define ZR36050_H - -#include "videocodec.h" - -/* data stored for each zoran jpeg codec chip */ -struct zr36050 { - char name[32]; - int num; - /* io datastructure */ - struct videocodec *codec; - // last coder status - __u8 status1; - // actual coder setup - int mode; - - __u16 width; - __u16 height; - - __u16 bitrate_ctrl; - - __u32 total_code_vol; - __u32 real_code_vol; - __u16 max_block_vol; - - __u8 h_samp_ratio[8]; - __u8 v_samp_ratio[8]; - __u16 scalefact; - __u16 dri; - - /* com/app marker */ - struct jpeg_com_marker com; - struct jpeg_app_marker app; -}; - -/* zr36050 register addresses */ -#define ZR050_GO 0x000 -#define ZR050_HARDWARE 0x002 -#define ZR050_MODE 0x003 -#define ZR050_OPTIONS 0x004 -#define ZR050_MBCV 0x005 -#define ZR050_MARKERS_EN 0x006 -#define ZR050_INT_REQ_0 0x007 -#define ZR050_INT_REQ_1 0x008 -#define ZR050_TCV_NET_HI 0x009 -#define ZR050_TCV_NET_MH 0x00a -#define ZR050_TCV_NET_ML 0x00b -#define ZR050_TCV_NET_LO 0x00c -#define ZR050_TCV_DATA_HI 0x00d -#define ZR050_TCV_DATA_MH 0x00e -#define ZR050_TCV_DATA_ML 0x00f -#define ZR050_TCV_DATA_LO 0x010 -#define ZR050_SF_HI 0x011 -#define ZR050_SF_LO 0x012 -#define ZR050_AF_HI 0x013 -#define ZR050_AF_M 0x014 -#define ZR050_AF_LO 0x015 -#define ZR050_ACV_HI 0x016 -#define ZR050_ACV_MH 0x017 -#define ZR050_ACV_ML 0x018 -#define ZR050_ACV_LO 0x019 -#define ZR050_ACT_HI 0x01a -#define ZR050_ACT_MH 0x01b -#define ZR050_ACT_ML 0x01c -#define ZR050_ACT_LO 0x01d -#define ZR050_ACV_TRUN_HI 0x01e -#define ZR050_ACV_TRUN_MH 0x01f -#define ZR050_ACV_TRUN_ML 0x020 -#define ZR050_ACV_TRUN_LO 0x021 -#define ZR050_STATUS_0 0x02e -#define ZR050_STATUS_1 0x02f - -#define ZR050_SOF_IDX 0x040 -#define ZR050_SOS1_IDX 0x07a -#define ZR050_SOS2_IDX 0x08a -#define ZR050_SOS3_IDX 0x09a -#define ZR050_SOS4_IDX 0x0aa -#define ZR050_DRI_IDX 0x0c0 -#define ZR050_DNL_IDX 0x0c6 -#define ZR050_DQT_IDX 0x0cc -#define ZR050_DHT_IDX 0x1d4 -#define ZR050_APP_IDX 0x380 -#define ZR050_COM_IDX 0x3c0 - -/* zr36050 hardware register bits */ - -#define ZR050_HW_BSWD 0x80 -#define ZR050_HW_MSTR 0x40 -#define ZR050_HW_DMA 0x20 -#define ZR050_HW_CFIS_1_CLK 0x00 -#define ZR050_HW_CFIS_2_CLK 0x04 -#define ZR050_HW_CFIS_3_CLK 0x08 -#define ZR050_HW_CFIS_4_CLK 0x0C -#define ZR050_HW_CFIS_5_CLK 0x10 -#define ZR050_HW_CFIS_6_CLK 0x14 -#define ZR050_HW_CFIS_7_CLK 0x18 -#define ZR050_HW_CFIS_8_CLK 0x1C -#define ZR050_HW_BELE 0x01 - -/* zr36050 mode register bits */ - -#define ZR050_MO_COMP 0x80 -#define ZR050_MO_ATP 0x40 -#define ZR050_MO_PASS2 0x20 -#define ZR050_MO_TLM 0x10 -#define ZR050_MO_DCONLY 0x08 -#define ZR050_MO_BRC 0x04 - -#define ZR050_MO_ATP 0x40 -#define ZR050_MO_PASS2 0x20 -#define ZR050_MO_TLM 0x10 -#define ZR050_MO_DCONLY 0x08 - -/* zr36050 option register bits */ - -#define ZR050_OP_NSCN_1 0x00 -#define ZR050_OP_NSCN_2 0x20 -#define ZR050_OP_NSCN_3 0x40 -#define ZR050_OP_NSCN_4 0x60 -#define ZR050_OP_NSCN_5 0x80 -#define ZR050_OP_NSCN_6 0xA0 -#define ZR050_OP_NSCN_7 0xC0 -#define ZR050_OP_NSCN_8 0xE0 -#define ZR050_OP_OVF 0x10 - - -/* zr36050 markers-enable register bits */ - -#define ZR050_ME_APP 0x80 -#define ZR050_ME_COM 0x40 -#define ZR050_ME_DRI 0x20 -#define ZR050_ME_DQT 0x10 -#define ZR050_ME_DHT 0x08 -#define ZR050_ME_DNL 0x04 -#define ZR050_ME_DQTI 0x02 -#define ZR050_ME_DHTI 0x01 - -/* zr36050 status0/1 register bit masks */ - -#define ZR050_ST_RST_MASK 0x20 -#define ZR050_ST_SOF_MASK 0x02 -#define ZR050_ST_SOS_MASK 0x02 -#define ZR050_ST_DATRDY_MASK 0x80 -#define ZR050_ST_MRKDET_MASK 0x40 -#define ZR050_ST_RFM_MASK 0x10 -#define ZR050_ST_RFD_MASK 0x08 -#define ZR050_ST_END_MASK 0x04 -#define ZR050_ST_TCVOVF_MASK 0x02 -#define ZR050_ST_DATOVF_MASK 0x01 - -/* pixel component idx */ - -#define ZR050_Y_COMPONENT 0 -#define ZR050_U_COMPONENT 1 -#define ZR050_V_COMPONENT 2 - -#endif /*fndef ZR36050_H */ diff --git a/drivers/staging/media/zoran/zr36057.h b/drivers/staging/media/zoran/zr36057.h deleted file mode 100644 index c8acb21dcb5c..000000000000 --- a/drivers/staging/media/zoran/zr36057.h +++ /dev/null @@ -1,164 +0,0 @@ -/* - * zr36057.h - zr36057 register offsets - * - * Copyright (C) 1998 Dave Perks - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - */ - -#ifndef _ZR36057_H_ -#define _ZR36057_H_ - - -/* Zoran ZR36057 registers */ - -#define ZR36057_VFEHCR 0x000 /* Video Front End, Horizontal Configuration Register */ -#define ZR36057_VFEHCR_HSPol (1<<30) -#define ZR36057_VFEHCR_HStart 10 -#define ZR36057_VFEHCR_HEnd 0 -#define ZR36057_VFEHCR_Hmask 0x3ff - -#define ZR36057_VFEVCR 0x004 /* Video Front End, Vertical Configuration Register */ -#define ZR36057_VFEVCR_VSPol (1<<30) -#define ZR36057_VFEVCR_VStart 10 -#define ZR36057_VFEVCR_VEnd 0 -#define ZR36057_VFEVCR_Vmask 0x3ff - -#define ZR36057_VFESPFR 0x008 /* Video Front End, Scaler and Pixel Format Register */ -#define ZR36057_VFESPFR_ExtFl (1<<26) -#define ZR36057_VFESPFR_TopField (1<<25) -#define ZR36057_VFESPFR_VCLKPol (1<<24) -#define ZR36057_VFESPFR_HFilter 21 -#define ZR36057_VFESPFR_HorDcm 14 -#define ZR36057_VFESPFR_VerDcm 8 -#define ZR36057_VFESPFR_DispMode 6 -#define ZR36057_VFESPFR_YUV422 (0<<3) -#define ZR36057_VFESPFR_RGB888 (1<<3) -#define ZR36057_VFESPFR_RGB565 (2<<3) -#define ZR36057_VFESPFR_RGB555 (3<<3) -#define ZR36057_VFESPFR_ErrDif (1<<2) -#define ZR36057_VFESPFR_Pack24 (1<<1) -#define ZR36057_VFESPFR_LittleEndian (1<<0) - -#define ZR36057_VDTR 0x00c /* Video Display "Top" Register */ - -#define ZR36057_VDBR 0x010 /* Video Display "Bottom" Register */ - -#define ZR36057_VSSFGR 0x014 /* Video Stride, Status, and Frame Grab Register */ -#define ZR36057_VSSFGR_DispStride 16 -#define ZR36057_VSSFGR_VidOvf (1<<8) -#define ZR36057_VSSFGR_SnapShot (1<<1) -#define ZR36057_VSSFGR_FrameGrab (1<<0) - -#define ZR36057_VDCR 0x018 /* Video Display Configuration Register */ -#define ZR36057_VDCR_VidEn (1<<31) -#define ZR36057_VDCR_MinPix 24 -#define ZR36057_VDCR_Triton (1<<24) -#define ZR36057_VDCR_VidWinHt 12 -#define ZR36057_VDCR_VidWinWid 0 - -#define ZR36057_MMTR 0x01c /* Masking Map "Top" Register */ - -#define ZR36057_MMBR 0x020 /* Masking Map "Bottom" Register */ - -#define ZR36057_OCR 0x024 /* Overlay Control Register */ -#define ZR36057_OCR_OvlEnable (1 << 15) -#define ZR36057_OCR_MaskStride 0 - -#define ZR36057_SPGPPCR 0x028 /* System, PCI, and General Purpose Pins Control Register */ -#define ZR36057_SPGPPCR_SoftReset (1<<24) - -#define ZR36057_GPPGCR1 0x02c /* General Purpose Pins and GuestBus Control Register (1) */ - -#define ZR36057_MCSAR 0x030 /* MPEG Code Source Address Register */ - -#define ZR36057_MCTCR 0x034 /* MPEG Code Transfer Control Register */ -#define ZR36057_MCTCR_CodTime (1 << 30) -#define ZR36057_MCTCR_CEmpty (1 << 29) -#define ZR36057_MCTCR_CFlush (1 << 28) -#define ZR36057_MCTCR_CodGuestID 20 -#define ZR36057_MCTCR_CodGuestReg 16 - -#define ZR36057_MCMPR 0x038 /* MPEG Code Memory Pointer Register */ - -#define ZR36057_ISR 0x03c /* Interrupt Status Register */ -#define ZR36057_ISR_GIRQ1 (1<<30) -#define ZR36057_ISR_GIRQ0 (1<<29) -#define ZR36057_ISR_CodRepIRQ (1<<28) -#define ZR36057_ISR_JPEGRepIRQ (1<<27) - -#define ZR36057_ICR 0x040 /* Interrupt Control Register */ -#define ZR36057_ICR_GIRQ1 (1<<30) -#define ZR36057_ICR_GIRQ0 (1<<29) -#define ZR36057_ICR_CodRepIRQ (1<<28) -#define ZR36057_ICR_JPEGRepIRQ (1<<27) -#define ZR36057_ICR_IntPinEn (1<<24) - -#define ZR36057_I2CBR 0x044 /* I2C Bus Register */ -#define ZR36057_I2CBR_SDA (1<<1) -#define ZR36057_I2CBR_SCL (1<<0) - -#define ZR36057_JMC 0x100 /* JPEG Mode and Control */ -#define ZR36057_JMC_JPG (1 << 31) -#define ZR36057_JMC_JPGExpMode (0 << 29) -#define ZR36057_JMC_JPGCmpMode (1 << 29) -#define ZR36057_JMC_MJPGExpMode (2 << 29) -#define ZR36057_JMC_MJPGCmpMode (3 << 29) -#define ZR36057_JMC_RTBUSY_FB (1 << 6) -#define ZR36057_JMC_Go_en (1 << 5) -#define ZR36057_JMC_SyncMstr (1 << 4) -#define ZR36057_JMC_Fld_per_buff (1 << 3) -#define ZR36057_JMC_VFIFO_FB (1 << 2) -#define ZR36057_JMC_CFIFO_FB (1 << 1) -#define ZR36057_JMC_Stll_LitEndian (1 << 0) - -#define ZR36057_JPC 0x104 /* JPEG Process Control */ -#define ZR36057_JPC_P_Reset (1 << 7) -#define ZR36057_JPC_CodTrnsEn (1 << 5) -#define ZR36057_JPC_Active (1 << 0) - -#define ZR36057_VSP 0x108 /* Vertical Sync Parameters */ -#define ZR36057_VSP_VsyncSize 16 -#define ZR36057_VSP_FrmTot 0 - -#define ZR36057_HSP 0x10c /* Horizontal Sync Parameters */ -#define ZR36057_HSP_HsyncStart 16 -#define ZR36057_HSP_LineTot 0 - -#define ZR36057_FHAP 0x110 /* Field Horizontal Active Portion */ -#define ZR36057_FHAP_NAX 16 -#define ZR36057_FHAP_PAX 0 - -#define ZR36057_FVAP 0x114 /* Field Vertical Active Portion */ -#define ZR36057_FVAP_NAY 16 -#define ZR36057_FVAP_PAY 0 - -#define ZR36057_FPP 0x118 /* Field Process Parameters */ -#define ZR36057_FPP_Odd_Even (1 << 0) - -#define ZR36057_JCBA 0x11c /* JPEG Code Base Address */ - -#define ZR36057_JCFT 0x120 /* JPEG Code FIFO Threshold */ - -#define ZR36057_JCGI 0x124 /* JPEG Codec Guest ID */ -#define ZR36057_JCGI_JPEGuestID 4 -#define ZR36057_JCGI_JPEGuestReg 0 - -#define ZR36057_GCR2 0x12c /* GuestBus Control Register (2) */ - -#define ZR36057_POR 0x200 /* Post Office Register */ -#define ZR36057_POR_POPen (1<<25) -#define ZR36057_POR_POTime (1<<24) -#define ZR36057_POR_PODir (1<<23) - -#define ZR36057_STR 0x300 /* "Still" Transfer Register */ - -#endif diff --git a/drivers/staging/media/zoran/zr36060.c b/drivers/staging/media/zoran/zr36060.c deleted file mode 100644 index 2c2e8130fc96..000000000000 --- a/drivers/staging/media/zoran/zr36060.c +++ /dev/null @@ -1,1006 +0,0 @@ -/* - * Zoran ZR36060 basic configuration functions - * - * Copyright (C) 2002 Laurent Pinchart - * - * $Id: zr36060.c,v 1.1.2.22 2003/05/06 09:35:36 rbultje Exp $ - * - * ------------------------------------------------------------------------ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * ------------------------------------------------------------------------ - */ - -#define ZR060_VERSION "v0.7" - -#include -#include -#include -#include - -#include -#include - -/* I/O commands, error codes */ -#include - -/* headerfile of this module */ -#include "zr36060.h" - -/* codec io API */ -#include "videocodec.h" - -/* it doesn't make sense to have more than 20 or so, - just to prevent some unwanted loops */ -#define MAX_CODECS 20 - -/* amount of chips attached via this driver */ -static int zr36060_codecs; - -static bool low_bitrate; -module_param(low_bitrate, bool, 0); -MODULE_PARM_DESC(low_bitrate, "Buz compatibility option, halves bitrate"); - -/* debugging is available via module parameter */ -static int debug; -module_param(debug, int, 0); -MODULE_PARM_DESC(debug, "Debug level (0-4)"); - -#define dprintk(num, format, args...) \ - do { \ - if (debug >= num) \ - printk(format, ##args); \ - } while (0) - -/* ========================================================================= - Local hardware I/O functions: - - read/write via codec layer (registers are located in the master device) - ========================================================================= */ - -/* read and write functions */ -static u8 -zr36060_read (struct zr36060 *ptr, - u16 reg) -{ - u8 value = 0; - - // just in case something is wrong... - if (ptr->codec->master_data->readreg) - value = (ptr->codec->master_data->readreg(ptr->codec, - reg)) & 0xff; - else - dprintk(1, - KERN_ERR "%s: invalid I/O setup, nothing read!\n", - ptr->name); - - //dprintk(4, "%s: reading from 0x%04x: %02x\n",ptr->name,reg,value); - - return value; -} - -static void -zr36060_write(struct zr36060 *ptr, - u16 reg, - u8 value) -{ - //dprintk(4, "%s: writing 0x%02x to 0x%04x\n",ptr->name,value,reg); - dprintk(4, "0x%02x @0x%04x\n", value, reg); - - // just in case something is wrong... - if (ptr->codec->master_data->writereg) - ptr->codec->master_data->writereg(ptr->codec, reg, value); - else - dprintk(1, - KERN_ERR - "%s: invalid I/O setup, nothing written!\n", - ptr->name); -} - -/* ========================================================================= - Local helper function: - - status read - ========================================================================= */ - -/* status is kept in datastructure */ -static u8 -zr36060_read_status (struct zr36060 *ptr) -{ - ptr->status = zr36060_read(ptr, ZR060_CFSR); - - zr36060_read(ptr, 0); - return ptr->status; -} - -/* ========================================================================= - Local helper function: - - scale factor read - ========================================================================= */ - -/* scale factor is kept in datastructure */ -static u16 -zr36060_read_scalefactor (struct zr36060 *ptr) -{ - ptr->scalefact = (zr36060_read(ptr, ZR060_SF_HI) << 8) | - (zr36060_read(ptr, ZR060_SF_LO) & 0xFF); - - /* leave 0 selected for an eventually GO from master */ - zr36060_read(ptr, 0); - return ptr->scalefact; -} - -/* ========================================================================= - Local helper function: - - wait if codec is ready to proceed (end of processing) or time is over - ========================================================================= */ - -static void -zr36060_wait_end (struct zr36060 *ptr) -{ - int i = 0; - - while (zr36060_read_status(ptr) & ZR060_CFSR_Busy) { - udelay(1); - if (i++ > 200000) { // 200ms, there is for sure something wrong!!! - dprintk(1, - "%s: timeout at wait_end (last status: 0x%02x)\n", - ptr->name, ptr->status); - break; - } - } -} - -/* ========================================================================= - Local helper function: - - basic test of "connectivity", writes/reads to/from memory the SOF marker - ========================================================================= */ - -static int -zr36060_basic_test (struct zr36060 *ptr) -{ - if ((zr36060_read(ptr, ZR060_IDR_DEV) != 0x33) && - (zr36060_read(ptr, ZR060_IDR_REV) != 0x01)) { - dprintk(1, - KERN_ERR - "%s: attach failed, can't connect to jpeg processor!\n", - ptr->name); - return -ENXIO; - } - - zr36060_wait_end(ptr); - if (ptr->status & ZR060_CFSR_Busy) { - dprintk(1, - KERN_ERR - "%s: attach failed, jpeg processor failed (end flag)!\n", - ptr->name); - return -EBUSY; - } - - return 0; /* looks good! */ -} - -/* ========================================================================= - Local helper function: - - simple loop for pushing the init datasets - ========================================================================= */ - -static int -zr36060_pushit (struct zr36060 *ptr, - u16 startreg, - u16 len, - const char *data) -{ - int i = 0; - - dprintk(4, "%s: write data block to 0x%04x (len=%d)\n", ptr->name, - startreg, len); - while (i < len) { - zr36060_write(ptr, startreg++, data[i++]); - } - - return i; -} - -/* ========================================================================= - Basic datasets: - - jpeg baseline setup data (you find it on lots places in internet, or just - extract it from any regular .jpg image...) - - Could be variable, but until it's not needed it they are just fixed to save - memory. Otherwise expand zr36060 structure with arrays, push the values to - it and initialize from there, as e.g. the linux zr36057/60 driver does it. - ========================================================================= */ - -static const char zr36060_dqt[0x86] = { - 0xff, 0xdb, //Marker: DQT - 0x00, 0x84, //Length: 2*65+2 - 0x00, //Pq,Tq first table - 0x10, 0x0b, 0x0c, 0x0e, 0x0c, 0x0a, 0x10, 0x0e, - 0x0d, 0x0e, 0x12, 0x11, 0x10, 0x13, 0x18, 0x28, - 0x1a, 0x18, 0x16, 0x16, 0x18, 0x31, 0x23, 0x25, - 0x1d, 0x28, 0x3a, 0x33, 0x3d, 0x3c, 0x39, 0x33, - 0x38, 0x37, 0x40, 0x48, 0x5c, 0x4e, 0x40, 0x44, - 0x57, 0x45, 0x37, 0x38, 0x50, 0x6d, 0x51, 0x57, - 0x5f, 0x62, 0x67, 0x68, 0x67, 0x3e, 0x4d, 0x71, - 0x79, 0x70, 0x64, 0x78, 0x5c, 0x65, 0x67, 0x63, - 0x01, //Pq,Tq second table - 0x11, 0x12, 0x12, 0x18, 0x15, 0x18, 0x2f, 0x1a, - 0x1a, 0x2f, 0x63, 0x42, 0x38, 0x42, 0x63, 0x63, - 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, - 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, - 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, - 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, - 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, - 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63, 0x63 -}; - -static const char zr36060_dht[0x1a4] = { - 0xff, 0xc4, //Marker: DHT - 0x01, 0xa2, //Length: 2*AC, 2*DC - 0x00, //DC first table - 0x00, 0x01, 0x05, 0x01, 0x01, 0x01, 0x01, 0x01, - 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, - 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A, 0x0B, - 0x01, //DC second table - 0x00, 0x03, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, - 0x01, 0x01, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, - 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A, 0x0B, - 0x10, //AC first table - 0x00, 0x02, 0x01, 0x03, 0x03, 0x02, 0x04, 0x03, - 0x05, 0x05, 0x04, 0x04, 0x00, 0x00, - 0x01, 0x7D, 0x01, 0x02, 0x03, 0x00, 0x04, 0x11, - 0x05, 0x12, 0x21, 0x31, 0x41, 0x06, 0x13, 0x51, 0x61, - 0x07, 0x22, 0x71, 0x14, 0x32, 0x81, 0x91, 0xA1, - 0x08, 0x23, 0x42, 0xB1, 0xC1, 0x15, 0x52, 0xD1, 0xF0, 0x24, - 0x33, 0x62, 0x72, 0x82, 0x09, 0x0A, 0x16, 0x17, - 0x18, 0x19, 0x1A, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2A, 0x34, - 0x35, 0x36, 0x37, 0x38, 0x39, 0x3A, 0x43, 0x44, - 0x45, 0x46, 0x47, 0x48, 0x49, 0x4A, 0x53, 0x54, 0x55, 0x56, - 0x57, 0x58, 0x59, 0x5A, 0x63, 0x64, 0x65, 0x66, - 0x67, 0x68, 0x69, 0x6A, 0x73, 0x74, 0x75, 0x76, 0x77, 0x78, - 0x79, 0x7A, 0x83, 0x84, 0x85, 0x86, 0x87, 0x88, - 0x89, 0x8A, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97, 0x98, 0x99, - 0x9A, 0xA2, 0xA3, 0xA4, 0xA5, 0xA6, 0xA7, 0xA8, - 0xA9, 0xAA, 0xB2, 0xB3, 0xB4, 0xB5, 0xB6, 0xB7, 0xB8, 0xB9, - 0xBA, 0xC2, 0xC3, 0xC4, 0xC5, 0xC6, 0xC7, 0xC8, - 0xC9, 0xCA, 0xD2, 0xD3, 0xD4, 0xD5, 0xD6, 0xD7, 0xD8, 0xD9, - 0xDA, 0xE1, 0xE2, 0xE3, 0xE4, 0xE5, 0xE6, 0xE7, - 0xE8, 0xE9, 0xEA, 0xF1, 0xF2, 0xF3, 0xF4, 0xF5, 0xF6, 0xF7, - 0xF8, 0xF9, 0xFA, - 0x11, //AC second table - 0x00, 0x02, 0x01, 0x02, 0x04, 0x04, 0x03, 0x04, - 0x07, 0x05, 0x04, 0x04, 0x00, 0x01, - 0x02, 0x77, 0x00, 0x01, 0x02, 0x03, 0x11, 0x04, - 0x05, 0x21, 0x31, 0x06, 0x12, 0x41, 0x51, 0x07, 0x61, 0x71, - 0x13, 0x22, 0x32, 0x81, 0x08, 0x14, 0x42, 0x91, - 0xA1, 0xB1, 0xC1, 0x09, 0x23, 0x33, 0x52, 0xF0, 0x15, 0x62, - 0x72, 0xD1, 0x0A, 0x16, 0x24, 0x34, 0xE1, 0x25, - 0xF1, 0x17, 0x18, 0x19, 0x1A, 0x26, 0x27, 0x28, 0x29, 0x2A, - 0x35, 0x36, 0x37, 0x38, 0x39, 0x3A, 0x43, 0x44, - 0x45, 0x46, 0x47, 0x48, 0x49, 0x4A, 0x53, 0x54, 0x55, 0x56, - 0x57, 0x58, 0x59, 0x5A, 0x63, 0x64, 0x65, 0x66, - 0x67, 0x68, 0x69, 0x6A, 0x73, 0x74, 0x75, 0x76, 0x77, 0x78, - 0x79, 0x7A, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87, - 0x88, 0x89, 0x8A, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97, 0x98, - 0x99, 0x9A, 0xA2, 0xA3, 0xA4, 0xA5, 0xA6, 0xA7, - 0xA8, 0xA9, 0xAA, 0xB2, 0xB3, 0xB4, 0xB5, 0xB6, 0xB7, 0xB8, - 0xB9, 0xBA, 0xC2, 0xC3, 0xC4, 0xC5, 0xC6, 0xC7, - 0xC8, 0xC9, 0xCA, 0xD2, 0xD3, 0xD4, 0xD5, 0xD6, 0xD7, 0xD8, - 0xD9, 0xDA, 0xE2, 0xE3, 0xE4, 0xE5, 0xE6, 0xE7, - 0xE8, 0xE9, 0xEA, 0xF2, 0xF3, 0xF4, 0xF5, 0xF6, 0xF7, 0xF8, - 0xF9, 0xFA -}; - -/* jpeg baseline setup, this is just fixed in this driver (YUV pictures) */ -#define NO_OF_COMPONENTS 0x3 //Y,U,V -#define BASELINE_PRECISION 0x8 //MCU size (?) -static const char zr36060_tq[8] = { 0, 1, 1, 0, 0, 0, 0, 0 }; //table idx's QT -static const char zr36060_td[8] = { 0, 1, 1, 0, 0, 0, 0, 0 }; //table idx's DC -static const char zr36060_ta[8] = { 0, 1, 1, 0, 0, 0, 0, 0 }; //table idx's AC - -/* horizontal 422 decimation setup (maybe we support 411 or so later, too) */ -static const char zr36060_decimation_h[8] = { 2, 1, 1, 0, 0, 0, 0, 0 }; -static const char zr36060_decimation_v[8] = { 1, 1, 1, 0, 0, 0, 0, 0 }; - -/* ========================================================================= - Local helper functions: - - calculation and setup of parameter-dependent JPEG baseline segments - (needed for compression only) - ========================================================================= */ - -/* ------------------------------------------------------------------------- */ - -/* SOF (start of frame) segment depends on width, height and sampling ratio - of each color component */ - -static int -zr36060_set_sof (struct zr36060 *ptr) -{ - char sof_data[34]; // max. size of register set - int i; - - dprintk(3, "%s: write SOF (%dx%d, %d components)\n", ptr->name, - ptr->width, ptr->height, NO_OF_COMPONENTS); - sof_data[0] = 0xff; - sof_data[1] = 0xc0; - sof_data[2] = 0x00; - sof_data[3] = (3 * NO_OF_COMPONENTS) + 8; - sof_data[4] = BASELINE_PRECISION; // only '8' possible with zr36060 - sof_data[5] = (ptr->height) >> 8; - sof_data[6] = (ptr->height) & 0xff; - sof_data[7] = (ptr->width) >> 8; - sof_data[8] = (ptr->width) & 0xff; - sof_data[9] = NO_OF_COMPONENTS; - for (i = 0; i < NO_OF_COMPONENTS; i++) { - sof_data[10 + (i * 3)] = i; // index identifier - sof_data[11 + (i * 3)] = (ptr->h_samp_ratio[i] << 4) | - (ptr->v_samp_ratio[i]); // sampling ratios - sof_data[12 + (i * 3)] = zr36060_tq[i]; // Q table selection - } - return zr36060_pushit(ptr, ZR060_SOF_IDX, - (3 * NO_OF_COMPONENTS) + 10, sof_data); -} - -/* ------------------------------------------------------------------------- */ - -/* SOS (start of scan) segment depends on the used scan components - of each color component */ - -static int -zr36060_set_sos (struct zr36060 *ptr) -{ - char sos_data[16]; // max. size of register set - int i; - - dprintk(3, "%s: write SOS\n", ptr->name); - sos_data[0] = 0xff; - sos_data[1] = 0xda; - sos_data[2] = 0x00; - sos_data[3] = 2 + 1 + (2 * NO_OF_COMPONENTS) + 3; - sos_data[4] = NO_OF_COMPONENTS; - for (i = 0; i < NO_OF_COMPONENTS; i++) { - sos_data[5 + (i * 2)] = i; // index - sos_data[6 + (i * 2)] = (zr36060_td[i] << 4) | - zr36060_ta[i]; // AC/DC tbl.sel. - } - sos_data[2 + 1 + (2 * NO_OF_COMPONENTS) + 2] = 00; // scan start - sos_data[2 + 1 + (2 * NO_OF_COMPONENTS) + 3] = 0x3f; - sos_data[2 + 1 + (2 * NO_OF_COMPONENTS) + 4] = 00; - return zr36060_pushit(ptr, ZR060_SOS_IDX, - 4 + 1 + (2 * NO_OF_COMPONENTS) + 3, - sos_data); -} - -/* ------------------------------------------------------------------------- */ - -/* DRI (define restart interval) */ - -static int -zr36060_set_dri (struct zr36060 *ptr) -{ - char dri_data[6]; // max. size of register set - - dprintk(3, "%s: write DRI\n", ptr->name); - dri_data[0] = 0xff; - dri_data[1] = 0xdd; - dri_data[2] = 0x00; - dri_data[3] = 0x04; - dri_data[4] = (ptr->dri) >> 8; - dri_data[5] = (ptr->dri) & 0xff; - return zr36060_pushit(ptr, ZR060_DRI_IDX, 6, dri_data); -} - -/* ========================================================================= - Setup function: - - Setup compression/decompression of Zoran's JPEG processor - ( see also zoran 36060 manual ) - - ... sorry for the spaghetti code ... - ========================================================================= */ -static void -zr36060_init (struct zr36060 *ptr) -{ - int sum = 0; - long bitcnt, tmp; - - if (ptr->mode == CODEC_DO_COMPRESSION) { - dprintk(2, "%s: COMPRESSION SETUP\n", ptr->name); - - zr36060_write(ptr, ZR060_LOAD, ZR060_LOAD_SyncRst); - - /* 060 communicates with 067 in master mode */ - zr36060_write(ptr, ZR060_CIR, ZR060_CIR_CodeMstr); - - /* Compression with or without variable scale factor */ - /*FIXME: What about ptr->bitrate_ctrl? */ - zr36060_write(ptr, ZR060_CMR, - ZR060_CMR_Comp | ZR060_CMR_Pass2 | - ZR060_CMR_BRB); - - /* Must be zero */ - zr36060_write(ptr, ZR060_MBZ, 0x00); - zr36060_write(ptr, ZR060_TCR_HI, 0x00); - zr36060_write(ptr, ZR060_TCR_LO, 0x00); - - /* Disable all IRQs - no DataErr means autoreset */ - zr36060_write(ptr, ZR060_IMR, 0); - - /* volume control settings */ - zr36060_write(ptr, ZR060_SF_HI, ptr->scalefact >> 8); - zr36060_write(ptr, ZR060_SF_LO, ptr->scalefact & 0xff); - - zr36060_write(ptr, ZR060_AF_HI, 0xff); - zr36060_write(ptr, ZR060_AF_M, 0xff); - zr36060_write(ptr, ZR060_AF_LO, 0xff); - - /* setup the variable jpeg tables */ - sum += zr36060_set_sof(ptr); - sum += zr36060_set_sos(ptr); - sum += zr36060_set_dri(ptr); - - /* setup the fixed jpeg tables - maybe variable, though - - * (see table init section above) */ - sum += - zr36060_pushit(ptr, ZR060_DQT_IDX, sizeof(zr36060_dqt), - zr36060_dqt); - sum += - zr36060_pushit(ptr, ZR060_DHT_IDX, sizeof(zr36060_dht), - zr36060_dht); - zr36060_write(ptr, ZR060_APP_IDX, 0xff); - zr36060_write(ptr, ZR060_APP_IDX + 1, 0xe0 + ptr->app.appn); - zr36060_write(ptr, ZR060_APP_IDX + 2, 0x00); - zr36060_write(ptr, ZR060_APP_IDX + 3, ptr->app.len + 2); - sum += zr36060_pushit(ptr, ZR060_APP_IDX + 4, 60, - ptr->app.data) + 4; - zr36060_write(ptr, ZR060_COM_IDX, 0xff); - zr36060_write(ptr, ZR060_COM_IDX + 1, 0xfe); - zr36060_write(ptr, ZR060_COM_IDX + 2, 0x00); - zr36060_write(ptr, ZR060_COM_IDX + 3, ptr->com.len + 2); - sum += zr36060_pushit(ptr, ZR060_COM_IDX + 4, 60, - ptr->com.data) + 4; - - /* setup misc. data for compression (target code sizes) */ - - /* size of compressed code to reach without header data */ - sum = ptr->real_code_vol - sum; - bitcnt = sum << 3; /* need the size in bits */ - - tmp = bitcnt >> 16; - dprintk(3, - "%s: code: csize=%d, tot=%d, bit=%ld, highbits=%ld\n", - ptr->name, sum, ptr->real_code_vol, bitcnt, tmp); - zr36060_write(ptr, ZR060_TCV_NET_HI, tmp >> 8); - zr36060_write(ptr, ZR060_TCV_NET_MH, tmp & 0xff); - tmp = bitcnt & 0xffff; - zr36060_write(ptr, ZR060_TCV_NET_ML, tmp >> 8); - zr36060_write(ptr, ZR060_TCV_NET_LO, tmp & 0xff); - - bitcnt -= bitcnt >> 7; // bits without stuffing - bitcnt -= ((bitcnt * 5) >> 6); // bits without eob - - tmp = bitcnt >> 16; - dprintk(3, "%s: code: nettobit=%ld, highnettobits=%ld\n", - ptr->name, bitcnt, tmp); - zr36060_write(ptr, ZR060_TCV_DATA_HI, tmp >> 8); - zr36060_write(ptr, ZR060_TCV_DATA_MH, tmp & 0xff); - tmp = bitcnt & 0xffff; - zr36060_write(ptr, ZR060_TCV_DATA_ML, tmp >> 8); - zr36060_write(ptr, ZR060_TCV_DATA_LO, tmp & 0xff); - - /* JPEG markers to be included in the compressed stream */ - zr36060_write(ptr, ZR060_MER, - ZR060_MER_DQT | ZR060_MER_DHT | - ((ptr->com.len > 0) ? ZR060_MER_Com : 0) | - ((ptr->app.len > 0) ? ZR060_MER_App : 0)); - - /* Setup the Video Frontend */ - /* Limit pixel range to 16..235 as per CCIR-601 */ - zr36060_write(ptr, ZR060_VCR, ZR060_VCR_Range); - - } else { - dprintk(2, "%s: EXPANSION SETUP\n", ptr->name); - - zr36060_write(ptr, ZR060_LOAD, ZR060_LOAD_SyncRst); - - /* 060 communicates with 067 in master mode */ - zr36060_write(ptr, ZR060_CIR, ZR060_CIR_CodeMstr); - - /* Decompression */ - zr36060_write(ptr, ZR060_CMR, 0); - - /* Must be zero */ - zr36060_write(ptr, ZR060_MBZ, 0x00); - zr36060_write(ptr, ZR060_TCR_HI, 0x00); - zr36060_write(ptr, ZR060_TCR_LO, 0x00); - - /* Disable all IRQs - no DataErr means autoreset */ - zr36060_write(ptr, ZR060_IMR, 0); - - /* setup misc. data for expansion */ - zr36060_write(ptr, ZR060_MER, 0); - - /* setup the fixed jpeg tables - maybe variable, though - - * (see table init section above) */ - zr36060_pushit(ptr, ZR060_DHT_IDX, sizeof(zr36060_dht), - zr36060_dht); - - /* Setup the Video Frontend */ - //zr36060_write(ptr, ZR060_VCR, ZR060_VCR_FIExt); - //this doesn't seem right and doesn't work... - zr36060_write(ptr, ZR060_VCR, ZR060_VCR_Range); - } - - /* Load the tables */ - zr36060_write(ptr, ZR060_LOAD, - ZR060_LOAD_SyncRst | ZR060_LOAD_Load); - zr36060_wait_end(ptr); - dprintk(2, "%s: Status after table preload: 0x%02x\n", ptr->name, - ptr->status); - - if (ptr->status & ZR060_CFSR_Busy) { - dprintk(1, KERN_ERR "%s: init aborted!\n", ptr->name); - return; // something is wrong, its timed out!!!! - } -} - -/* ========================================================================= - CODEC API FUNCTIONS - - this functions are accessed by the master via the API structure - ========================================================================= */ - -/* set compression/expansion mode and launches codec - - this should be the last call from the master before starting processing */ -static int -zr36060_set_mode (struct videocodec *codec, - int mode) -{ - struct zr36060 *ptr = (struct zr36060 *) codec->data; - - dprintk(2, "%s: set_mode %d call\n", ptr->name, mode); - - if ((mode != CODEC_DO_EXPANSION) && (mode != CODEC_DO_COMPRESSION)) - return -EINVAL; - - ptr->mode = mode; - zr36060_init(ptr); - - return 0; -} - -/* set picture size (norm is ignored as the codec doesn't know about it) */ -static int -zr36060_set_video (struct videocodec *codec, - struct tvnorm *norm, - struct vfe_settings *cap, - struct vfe_polarity *pol) -{ - struct zr36060 *ptr = (struct zr36060 *) codec->data; - u32 reg; - int size; - - dprintk(2, "%s: set_video %d/%d-%dx%d (%%%d) call\n", ptr->name, - cap->x, cap->y, cap->width, cap->height, cap->decimation); - - /* if () return -EINVAL; - * trust the master driver that it knows what it does - so - * we allow invalid startx/y and norm for now ... */ - ptr->width = cap->width / (cap->decimation & 0xff); - ptr->height = cap->height / (cap->decimation >> 8); - - zr36060_write(ptr, ZR060_LOAD, ZR060_LOAD_SyncRst); - - /* Note that VSPol/HSPol bits in zr36060 have the opposite - * meaning of their zr360x7 counterparts with the same names - * N.b. for VSPol this is only true if FIVEdge = 0 (default, - * left unchanged here - in accordance with datasheet). - */ - reg = (!pol->vsync_pol ? ZR060_VPR_VSPol : 0) - | (!pol->hsync_pol ? ZR060_VPR_HSPol : 0) - | (pol->field_pol ? ZR060_VPR_FIPol : 0) - | (pol->blank_pol ? ZR060_VPR_BLPol : 0) - | (pol->subimg_pol ? ZR060_VPR_SImgPol : 0) - | (pol->poe_pol ? ZR060_VPR_PoePol : 0) - | (pol->pvalid_pol ? ZR060_VPR_PValPol : 0) - | (pol->vclk_pol ? ZR060_VPR_VCLKPol : 0); - zr36060_write(ptr, ZR060_VPR, reg); - - reg = 0; - switch (cap->decimation & 0xff) { - default: - case 1: - break; - - case 2: - reg |= ZR060_SR_HScale2; - break; - - case 4: - reg |= ZR060_SR_HScale4; - break; - } - - switch (cap->decimation >> 8) { - default: - case 1: - break; - - case 2: - reg |= ZR060_SR_VScale; - break; - } - zr36060_write(ptr, ZR060_SR, reg); - - zr36060_write(ptr, ZR060_BCR_Y, 0x00); - zr36060_write(ptr, ZR060_BCR_U, 0x80); - zr36060_write(ptr, ZR060_BCR_V, 0x80); - - /* sync generator */ - - reg = norm->Ht - 1; /* Vtotal */ - zr36060_write(ptr, ZR060_SGR_VTOTAL_HI, (reg >> 8) & 0xff); - zr36060_write(ptr, ZR060_SGR_VTOTAL_LO, (reg >> 0) & 0xff); - - reg = norm->Wt - 1; /* Htotal */ - zr36060_write(ptr, ZR060_SGR_HTOTAL_HI, (reg >> 8) & 0xff); - zr36060_write(ptr, ZR060_SGR_HTOTAL_LO, (reg >> 0) & 0xff); - - reg = 6 - 1; /* VsyncSize */ - zr36060_write(ptr, ZR060_SGR_VSYNC, reg); - - //reg = 30 - 1; /* HsyncSize */ -///*CP*/ reg = (zr->params.norm == 1 ? 57 : 68); - reg = 68; - zr36060_write(ptr, ZR060_SGR_HSYNC, reg); - - reg = norm->VStart - 1; /* BVstart */ - zr36060_write(ptr, ZR060_SGR_BVSTART, reg); - - reg += norm->Ha / 2; /* BVend */ - zr36060_write(ptr, ZR060_SGR_BVEND_HI, (reg >> 8) & 0xff); - zr36060_write(ptr, ZR060_SGR_BVEND_LO, (reg >> 0) & 0xff); - - reg = norm->HStart - 1; /* BHstart */ - zr36060_write(ptr, ZR060_SGR_BHSTART, reg); - - reg += norm->Wa; /* BHend */ - zr36060_write(ptr, ZR060_SGR_BHEND_HI, (reg >> 8) & 0xff); - zr36060_write(ptr, ZR060_SGR_BHEND_LO, (reg >> 0) & 0xff); - - /* active area */ - reg = cap->y + norm->VStart; /* Vstart */ - zr36060_write(ptr, ZR060_AAR_VSTART_HI, (reg >> 8) & 0xff); - zr36060_write(ptr, ZR060_AAR_VSTART_LO, (reg >> 0) & 0xff); - - reg += cap->height; /* Vend */ - zr36060_write(ptr, ZR060_AAR_VEND_HI, (reg >> 8) & 0xff); - zr36060_write(ptr, ZR060_AAR_VEND_LO, (reg >> 0) & 0xff); - - reg = cap->x + norm->HStart; /* Hstart */ - zr36060_write(ptr, ZR060_AAR_HSTART_HI, (reg >> 8) & 0xff); - zr36060_write(ptr, ZR060_AAR_HSTART_LO, (reg >> 0) & 0xff); - - reg += cap->width; /* Hend */ - zr36060_write(ptr, ZR060_AAR_HEND_HI, (reg >> 8) & 0xff); - zr36060_write(ptr, ZR060_AAR_HEND_LO, (reg >> 0) & 0xff); - - /* subimage area */ - reg = norm->VStart - 4; /* SVstart */ - zr36060_write(ptr, ZR060_SWR_VSTART_HI, (reg >> 8) & 0xff); - zr36060_write(ptr, ZR060_SWR_VSTART_LO, (reg >> 0) & 0xff); - - reg += norm->Ha / 2 + 8; /* SVend */ - zr36060_write(ptr, ZR060_SWR_VEND_HI, (reg >> 8) & 0xff); - zr36060_write(ptr, ZR060_SWR_VEND_LO, (reg >> 0) & 0xff); - - reg = norm->HStart /*+ 64 */ - 4; /* SHstart */ - zr36060_write(ptr, ZR060_SWR_HSTART_HI, (reg >> 8) & 0xff); - zr36060_write(ptr, ZR060_SWR_HSTART_LO, (reg >> 0) & 0xff); - - reg += norm->Wa + 8; /* SHend */ - zr36060_write(ptr, ZR060_SWR_HEND_HI, (reg >> 8) & 0xff); - zr36060_write(ptr, ZR060_SWR_HEND_LO, (reg >> 0) & 0xff); - - size = ptr->width * ptr->height; - /* Target compressed field size in bits: */ - size = size * 16; /* uncompressed size in bits */ - /* (Ronald) by default, quality = 100 is a compression - * ratio 1:2. Setting low_bitrate (insmod option) sets - * it to 1:4 (instead of 1:2, zr36060 max) as limit because the - * buz can't handle more at decimation=1... Use low_bitrate if - * you have a Buz, unless you know what you're doing */ - size = size * cap->quality / (low_bitrate ? 400 : 200); - /* Lower limit (arbitrary, 1 KB) */ - if (size < 8192) - size = 8192; - /* Upper limit: 7/8 of the code buffers */ - if (size > ptr->total_code_vol * 7) - size = ptr->total_code_vol * 7; - - ptr->real_code_vol = size >> 3; /* in bytes */ - - /* the MBCVR is the *maximum* block volume, according to the - * JPEG ISO specs, this shouldn't be used, since that allows - * for the best encoding quality. So set it to it's max value */ - reg = ptr->max_block_vol; - zr36060_write(ptr, ZR060_MBCVR, reg); - - return 0; -} - -/* additional control functions */ -static int -zr36060_control (struct videocodec *codec, - int type, - int size, - void *data) -{ - struct zr36060 *ptr = (struct zr36060 *) codec->data; - int *ival = (int *) data; - - dprintk(2, "%s: control %d call with %d byte\n", ptr->name, type, - size); - - switch (type) { - case CODEC_G_STATUS: /* get last status */ - if (size != sizeof(int)) - return -EFAULT; - zr36060_read_status(ptr); - *ival = ptr->status; - break; - - case CODEC_G_CODEC_MODE: - if (size != sizeof(int)) - return -EFAULT; - *ival = CODEC_MODE_BJPG; - break; - - case CODEC_S_CODEC_MODE: - if (size != sizeof(int)) - return -EFAULT; - if (*ival != CODEC_MODE_BJPG) - return -EINVAL; - /* not needed, do nothing */ - return 0; - - case CODEC_G_VFE: - case CODEC_S_VFE: - /* not needed, do nothing */ - return 0; - - case CODEC_S_MMAP: - /* not available, give an error */ - return -ENXIO; - - case CODEC_G_JPEG_TDS_BYTE: /* get target volume in byte */ - if (size != sizeof(int)) - return -EFAULT; - *ival = ptr->total_code_vol; - break; - - case CODEC_S_JPEG_TDS_BYTE: /* get target volume in byte */ - if (size != sizeof(int)) - return -EFAULT; - ptr->total_code_vol = *ival; - ptr->real_code_vol = (ptr->total_code_vol * 6) >> 3; - break; - - case CODEC_G_JPEG_SCALE: /* get scaling factor */ - if (size != sizeof(int)) - return -EFAULT; - *ival = zr36060_read_scalefactor(ptr); - break; - - case CODEC_S_JPEG_SCALE: /* set scaling factor */ - if (size != sizeof(int)) - return -EFAULT; - ptr->scalefact = *ival; - break; - - case CODEC_G_JPEG_APP_DATA: { /* get appn marker data */ - struct jpeg_app_marker *app = data; - - if (size != sizeof(struct jpeg_app_marker)) - return -EFAULT; - - *app = ptr->app; - break; - } - - case CODEC_S_JPEG_APP_DATA: { /* set appn marker data */ - struct jpeg_app_marker *app = data; - - if (size != sizeof(struct jpeg_app_marker)) - return -EFAULT; - - ptr->app = *app; - break; - } - - case CODEC_G_JPEG_COM_DATA: { /* get comment marker data */ - struct jpeg_com_marker *com = data; - - if (size != sizeof(struct jpeg_com_marker)) - return -EFAULT; - - *com = ptr->com; - break; - } - - case CODEC_S_JPEG_COM_DATA: { /* set comment marker data */ - struct jpeg_com_marker *com = data; - - if (size != sizeof(struct jpeg_com_marker)) - return -EFAULT; - - ptr->com = *com; - break; - } - - default: - return -EINVAL; - } - - return size; -} - -/* ========================================================================= - Exit and unregister function: - - Deinitializes Zoran's JPEG processor - ========================================================================= */ - -static int -zr36060_unset (struct videocodec *codec) -{ - struct zr36060 *ptr = codec->data; - - if (ptr) { - /* do wee need some codec deinit here, too ???? */ - - dprintk(1, "%s: finished codec #%d\n", ptr->name, - ptr->num); - kfree(ptr); - codec->data = NULL; - - zr36060_codecs--; - return 0; - } - - return -EFAULT; -} - -/* ========================================================================= - Setup and registry function: - - Initializes Zoran's JPEG processor - - Also sets pixel size, average code size, mode (compr./decompr.) - (the given size is determined by the processor with the video interface) - ========================================================================= */ - -static int -zr36060_setup (struct videocodec *codec) -{ - struct zr36060 *ptr; - int res; - - dprintk(2, "zr36060: initializing MJPEG subsystem #%d.\n", - zr36060_codecs); - - if (zr36060_codecs == MAX_CODECS) { - dprintk(1, - KERN_ERR "zr36060: Can't attach more codecs!\n"); - return -ENOSPC; - } - //mem structure init - codec->data = ptr = kzalloc(sizeof(struct zr36060), GFP_KERNEL); - if (NULL == ptr) { - dprintk(1, KERN_ERR "zr36060: Can't get enough memory!\n"); - return -ENOMEM; - } - - snprintf(ptr->name, sizeof(ptr->name), "zr36060[%d]", - zr36060_codecs); - ptr->num = zr36060_codecs++; - ptr->codec = codec; - - //testing - res = zr36060_basic_test(ptr); - if (res < 0) { - zr36060_unset(codec); - return res; - } - //final setup - memcpy(ptr->h_samp_ratio, zr36060_decimation_h, 8); - memcpy(ptr->v_samp_ratio, zr36060_decimation_v, 8); - - ptr->bitrate_ctrl = 0; /* 0 or 1 - fixed file size flag - * (what is the difference?) */ - ptr->mode = CODEC_DO_COMPRESSION; - ptr->width = 384; - ptr->height = 288; - ptr->total_code_vol = 16000; /* CHECKME */ - ptr->real_code_vol = (ptr->total_code_vol * 6) >> 3; - ptr->max_block_vol = 240; /* CHECKME, was 120 is 240 */ - ptr->scalefact = 0x100; - ptr->dri = 1; /* CHECKME, was 8 is 1 */ - - /* by default, no COM or APP markers - app should set those */ - ptr->com.len = 0; - ptr->app.appn = 0; - ptr->app.len = 0; - - zr36060_init(ptr); - - dprintk(1, KERN_INFO "%s: codec attached and running\n", - ptr->name); - - return 0; -} - -static const struct videocodec zr36060_codec = { - .owner = THIS_MODULE, - .name = "zr36060", - .magic = 0L, // magic not used - .flags = - CODEC_FLAG_JPEG | CODEC_FLAG_HARDWARE | CODEC_FLAG_ENCODER | - CODEC_FLAG_DECODER | CODEC_FLAG_VFE, - .type = CODEC_TYPE_ZR36060, - .setup = zr36060_setup, // functionality - .unset = zr36060_unset, - .set_mode = zr36060_set_mode, - .set_video = zr36060_set_video, - .control = zr36060_control, - // others are not used -}; - -/* ========================================================================= - HOOK IN DRIVER AS KERNEL MODULE - ========================================================================= */ - -static int __init -zr36060_init_module (void) -{ - //dprintk(1, "zr36060 driver %s\n",ZR060_VERSION); - zr36060_codecs = 0; - return videocodec_register(&zr36060_codec); -} - -static void __exit -zr36060_cleanup_module (void) -{ - if (zr36060_codecs) { - dprintk(1, - "zr36060: something's wrong - %d codecs left somehow.\n", - zr36060_codecs); - } - - /* however, we can't just stay alive */ - videocodec_unregister(&zr36060_codec); -} - -module_init(zr36060_init_module); -module_exit(zr36060_cleanup_module); - -MODULE_AUTHOR("Laurent Pinchart "); -MODULE_DESCRIPTION("Driver module for ZR36060 jpeg processors " - ZR060_VERSION); -MODULE_LICENSE("GPL"); diff --git a/drivers/staging/media/zoran/zr36060.h b/drivers/staging/media/zoran/zr36060.h deleted file mode 100644 index 82911757ba78..000000000000 --- a/drivers/staging/media/zoran/zr36060.h +++ /dev/null @@ -1,216 +0,0 @@ -/* - * Zoran ZR36060 basic configuration functions - header file - * - * Copyright (C) 2002 Laurent Pinchart - * - * $Id: zr36060.h,v 1.1.1.1.2.3 2003/01/14 21:18:47 rbultje Exp $ - * - * ------------------------------------------------------------------------ - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * ------------------------------------------------------------------------ - */ - -#ifndef ZR36060_H -#define ZR36060_H - -#include "videocodec.h" - -/* data stored for each zoran jpeg codec chip */ -struct zr36060 { - char name[32]; - int num; - /* io datastructure */ - struct videocodec *codec; - // last coder status - __u8 status; - // actual coder setup - int mode; - - __u16 width; - __u16 height; - - __u16 bitrate_ctrl; - - __u32 total_code_vol; - __u32 real_code_vol; - __u16 max_block_vol; - - __u8 h_samp_ratio[8]; - __u8 v_samp_ratio[8]; - __u16 scalefact; - __u16 dri; - - /* app/com marker data */ - struct jpeg_app_marker app; - struct jpeg_com_marker com; -}; - -/* ZR36060 register addresses */ -#define ZR060_LOAD 0x000 -#define ZR060_CFSR 0x001 -#define ZR060_CIR 0x002 -#define ZR060_CMR 0x003 -#define ZR060_MBZ 0x004 -#define ZR060_MBCVR 0x005 -#define ZR060_MER 0x006 -#define ZR060_IMR 0x007 -#define ZR060_ISR 0x008 -#define ZR060_TCV_NET_HI 0x009 -#define ZR060_TCV_NET_MH 0x00a -#define ZR060_TCV_NET_ML 0x00b -#define ZR060_TCV_NET_LO 0x00c -#define ZR060_TCV_DATA_HI 0x00d -#define ZR060_TCV_DATA_MH 0x00e -#define ZR060_TCV_DATA_ML 0x00f -#define ZR060_TCV_DATA_LO 0x010 -#define ZR060_SF_HI 0x011 -#define ZR060_SF_LO 0x012 -#define ZR060_AF_HI 0x013 -#define ZR060_AF_M 0x014 -#define ZR060_AF_LO 0x015 -#define ZR060_ACV_HI 0x016 -#define ZR060_ACV_MH 0x017 -#define ZR060_ACV_ML 0x018 -#define ZR060_ACV_LO 0x019 -#define ZR060_ACT_HI 0x01a -#define ZR060_ACT_MH 0x01b -#define ZR060_ACT_ML 0x01c -#define ZR060_ACT_LO 0x01d -#define ZR060_ACV_TRUN_HI 0x01e -#define ZR060_ACV_TRUN_MH 0x01f -#define ZR060_ACV_TRUN_ML 0x020 -#define ZR060_ACV_TRUN_LO 0x021 -#define ZR060_IDR_DEV 0x022 -#define ZR060_IDR_REV 0x023 -#define ZR060_TCR_HI 0x024 -#define ZR060_TCR_LO 0x025 -#define ZR060_VCR 0x030 -#define ZR060_VPR 0x031 -#define ZR060_SR 0x032 -#define ZR060_BCR_Y 0x033 -#define ZR060_BCR_U 0x034 -#define ZR060_BCR_V 0x035 -#define ZR060_SGR_VTOTAL_HI 0x036 -#define ZR060_SGR_VTOTAL_LO 0x037 -#define ZR060_SGR_HTOTAL_HI 0x038 -#define ZR060_SGR_HTOTAL_LO 0x039 -#define ZR060_SGR_VSYNC 0x03a -#define ZR060_SGR_HSYNC 0x03b -#define ZR060_SGR_BVSTART 0x03c -#define ZR060_SGR_BHSTART 0x03d -#define ZR060_SGR_BVEND_HI 0x03e -#define ZR060_SGR_BVEND_LO 0x03f -#define ZR060_SGR_BHEND_HI 0x040 -#define ZR060_SGR_BHEND_LO 0x041 -#define ZR060_AAR_VSTART_HI 0x042 -#define ZR060_AAR_VSTART_LO 0x043 -#define ZR060_AAR_VEND_HI 0x044 -#define ZR060_AAR_VEND_LO 0x045 -#define ZR060_AAR_HSTART_HI 0x046 -#define ZR060_AAR_HSTART_LO 0x047 -#define ZR060_AAR_HEND_HI 0x048 -#define ZR060_AAR_HEND_LO 0x049 -#define ZR060_SWR_VSTART_HI 0x04a -#define ZR060_SWR_VSTART_LO 0x04b -#define ZR060_SWR_VEND_HI 0x04c -#define ZR060_SWR_VEND_LO 0x04d -#define ZR060_SWR_HSTART_HI 0x04e -#define ZR060_SWR_HSTART_LO 0x04f -#define ZR060_SWR_HEND_HI 0x050 -#define ZR060_SWR_HEND_LO 0x051 - -#define ZR060_SOF_IDX 0x060 -#define ZR060_SOS_IDX 0x07a -#define ZR060_DRI_IDX 0x0c0 -#define ZR060_DQT_IDX 0x0cc -#define ZR060_DHT_IDX 0x1d4 -#define ZR060_APP_IDX 0x380 -#define ZR060_COM_IDX 0x3c0 - -/* ZR36060 LOAD register bits */ - -#define ZR060_LOAD_Load (1 << 7) -#define ZR060_LOAD_SyncRst (1 << 0) - -/* ZR36060 Code FIFO Status register bits */ - -#define ZR060_CFSR_Busy (1 << 7) -#define ZR060_CFSR_CBusy (1 << 2) -#define ZR060_CFSR_CFIFO (3 << 0) - -/* ZR36060 Code Interface register */ - -#define ZR060_CIR_Code16 (1 << 7) -#define ZR060_CIR_Endian (1 << 6) -#define ZR060_CIR_CFIS (1 << 2) -#define ZR060_CIR_CodeMstr (1 << 0) - -/* ZR36060 Codec Mode register */ - -#define ZR060_CMR_Comp (1 << 7) -#define ZR060_CMR_ATP (1 << 6) -#define ZR060_CMR_Pass2 (1 << 5) -#define ZR060_CMR_TLM (1 << 4) -#define ZR060_CMR_BRB (1 << 2) -#define ZR060_CMR_FSF (1 << 1) - -/* ZR36060 Markers Enable register */ - -#define ZR060_MER_App (1 << 7) -#define ZR060_MER_Com (1 << 6) -#define ZR060_MER_DRI (1 << 5) -#define ZR060_MER_DQT (1 << 4) -#define ZR060_MER_DHT (1 << 3) - -/* ZR36060 Interrupt Mask register */ - -#define ZR060_IMR_EOAV (1 << 3) -#define ZR060_IMR_EOI (1 << 2) -#define ZR060_IMR_End (1 << 1) -#define ZR060_IMR_DataErr (1 << 0) - -/* ZR36060 Interrupt Status register */ - -#define ZR060_ISR_ProCnt (3 << 6) -#define ZR060_ISR_EOAV (1 << 3) -#define ZR060_ISR_EOI (1 << 2) -#define ZR060_ISR_End (1 << 1) -#define ZR060_ISR_DataErr (1 << 0) - -/* ZR36060 Video Control register */ - -#define ZR060_VCR_Video8 (1 << 7) -#define ZR060_VCR_Range (1 << 6) -#define ZR060_VCR_FIDet (1 << 3) -#define ZR060_VCR_FIVedge (1 << 2) -#define ZR060_VCR_FIExt (1 << 1) -#define ZR060_VCR_SyncMstr (1 << 0) - -/* ZR36060 Video Polarity register */ - -#define ZR060_VPR_VCLKPol (1 << 7) -#define ZR060_VPR_PValPol (1 << 6) -#define ZR060_VPR_PoePol (1 << 5) -#define ZR060_VPR_SImgPol (1 << 4) -#define ZR060_VPR_BLPol (1 << 3) -#define ZR060_VPR_FIPol (1 << 2) -#define ZR060_VPR_HSPol (1 << 1) -#define ZR060_VPR_VSPol (1 << 0) - -/* ZR36060 Scaling register */ - -#define ZR060_SR_VScale (1 << 2) -#define ZR060_SR_HScale2 (1 << 0) -#define ZR060_SR_HScale4 (2 << 0) - -#endif /*fndef ZR36060_H */ -- cgit v1.2.3 From e57695e772e87e270ee451483b76ba1ccc1f1cfc Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Mon, 22 Apr 2019 14:39:37 -0300 Subject: docs: hwmon: convert three docs to ReST format Those three new drivers were missed on the initial conversion to ReST format. So: - Rename them to .rst; - Add them to the hwmon index.rst index; - add some blank lines at the "Supported systems:" part, in order to allow Sphinx to properly identify new lines, suppressing warnings and avoid it to output some random lines in bold; - When multiple authors are involved, change the authors part to a list, in order to avoid adding blank lines. - adjust the table cells (one of the tables seemed to be assuming that tab is 4 positions instead of 8) and add the table markup. - be sure that the section markups have the same number of characters as the section title. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Guenter Roeck --- Documentation/hwmon/index.rst | 3 ++ Documentation/hwmon/ir38064 | 61 ---------------------------- Documentation/hwmon/ir38064.rst | 66 +++++++++++++++++++++++++++++++ Documentation/hwmon/isl68137 | 72 --------------------------------- Documentation/hwmon/isl68137.rst | 80 +++++++++++++++++++++++++++++++++++++ Documentation/hwmon/lochnagar | 80 ------------------------------------- Documentation/hwmon/lochnagar.rst | 83 +++++++++++++++++++++++++++++++++++++++ 7 files changed, 232 insertions(+), 213 deletions(-) delete mode 100644 Documentation/hwmon/ir38064 create mode 100644 Documentation/hwmon/ir38064.rst delete mode 100644 Documentation/hwmon/isl68137 create mode 100644 Documentation/hwmon/isl68137.rst delete mode 100644 Documentation/hwmon/lochnagar create mode 100644 Documentation/hwmon/lochnagar.rst (limited to 'Documentation') diff --git a/Documentation/hwmon/index.rst b/Documentation/hwmon/index.rst index 893804414510..3fa14fe7b49c 100644 --- a/Documentation/hwmon/index.rst +++ b/Documentation/hwmon/index.rst @@ -65,6 +65,8 @@ Hardware Monitoring Kernel Drivers ina2xx.rst ina3221.rst ir35221.rst + ir38064.rst + isl68137.rst it87.rst jc42.rst k10temp.rst @@ -86,6 +88,7 @@ Hardware Monitoring Kernel Drivers lm93.rst lm95234.rst lm95245.rst + lochnagar.rst ltc2945.rst ltc2978.rst ltc2990.rst diff --git a/Documentation/hwmon/ir38064 b/Documentation/hwmon/ir38064 deleted file mode 100644 index 9f218c39bfe6..000000000000 --- a/Documentation/hwmon/ir38064 +++ /dev/null @@ -1,61 +0,0 @@ -Kernel driver ir38064 -===================== - -Supported chips: - * Infineon IR38064 - Prefix: 'ir38064' - Addresses scanned: - - Datasheet: Publicly available at the Infineon webiste - https://www.infineon.com/dgdl/Infineon-IR38064MTRPBF-DS-v03_07-EN.pdf?fileId=5546d462584d1d4a0158db0d9efb67ca - -Authors: - Maxim Sloyko - Patrick Venture - -Description ------------ - -IR38064 is a Single-input Voltage, Synchronous Buck Regulator, DC-DC Converter. - -Usage Notes ------------ - -This driver does not probe for PMBus devices. You will have to instantiate -devices explicitly. - -Sysfs attributes ----------------- - -curr1_label "iout1" -curr1_input Measured output current -curr1_crit Critical maximum current -curr1_crit_alarm Current critical high alarm -curr1_max Maximum current -curr1_max_alarm Current high alarm - -in1_label "vin" -in1_input Measured input voltage -in1_crit Critical maximum input voltage -in1_crit_alarm Input voltage critical high alarm -in1_min Minimum input voltage -in1_min_alarm Input voltage low alarm - -in2_label "vout1" -in2_input Measured output voltage -in2_lcrit Critical minimum output voltage -in2_lcrit_alarm Output voltage critical low alarm -in2_crit Critical maximum output voltage -in2_crit_alarm Output voltage critical high alarm -in2_max Maximum output voltage -in2_max_alarm Output voltage high alarm -in2_min Minimum output voltage -in2_min_alarm Output voltage low alarm - -power1_label "pout1" -power1_input Measured output power - -temp1_input Measured temperature -temp1_crit Critical high temperature -temp1_crit_alarm Chip temperature critical high alarm -temp1_max Maximum temperature -temp1_max_alarm Chip temperature high alarm diff --git a/Documentation/hwmon/ir38064.rst b/Documentation/hwmon/ir38064.rst new file mode 100644 index 000000000000..c455d755a267 --- /dev/null +++ b/Documentation/hwmon/ir38064.rst @@ -0,0 +1,66 @@ +Kernel driver ir38064 +===================== + +Supported chips: + + * Infineon IR38064 + + Prefix: 'ir38064' + Addresses scanned: - + + Datasheet: Publicly available at the Infineon webiste + https://www.infineon.com/dgdl/Infineon-IR38064MTRPBF-DS-v03_07-EN.pdf?fileId=5546d462584d1d4a0158db0d9efb67ca + +Authors: + - Maxim Sloyko + - Patrick Venture + +Description +----------- + +IR38064 is a Single-input Voltage, Synchronous Buck Regulator, DC-DC Converter. + +Usage Notes +----------- + +This driver does not probe for PMBus devices. You will have to instantiate +devices explicitly. + +Sysfs attributes +---------------- + +======================= =========================== +curr1_label "iout1" +curr1_input Measured output current +curr1_crit Critical maximum current +curr1_crit_alarm Current critical high alarm +curr1_max Maximum current +curr1_max_alarm Current high alarm + +in1_label "vin" +in1_input Measured input voltage +in1_crit Critical maximum input voltage +in1_crit_alarm Input voltage critical high alarm +in1_min Minimum input voltage +in1_min_alarm Input voltage low alarm + +in2_label "vout1" +in2_input Measured output voltage +in2_lcrit Critical minimum output voltage +in2_lcrit_alarm Output voltage critical low alarm +in2_crit Critical maximum output voltage +in2_crit_alarm Output voltage critical high alarm +in2_max Maximum output voltage +in2_max_alarm Output voltage high alarm +in2_min Minimum output voltage +in2_min_alarm Output voltage low alarm + +power1_label "pout1" +power1_input Measured output power + +temp1_input Measured temperature +temp1_crit Critical high temperature +temp1_crit_alarm Chip temperature critical high alarm +temp1_max Maximum temperature +temp1_max_alarm Chip temperature high alarm +======================= =========================== diff --git a/Documentation/hwmon/isl68137 b/Documentation/hwmon/isl68137 deleted file mode 100644 index 92e5c5fc5b77..000000000000 --- a/Documentation/hwmon/isl68137 +++ /dev/null @@ -1,72 +0,0 @@ -Kernel driver isl68137 -====================== - -Supported chips: - * Intersil ISL68137 - Prefix: 'isl68137' - Addresses scanned: - - Datasheet: Publicly available at the Intersil website - https://www.intersil.com/content/dam/Intersil/documents/isl6/isl68137.pdf - -Authors: - Maxim Sloyko - Robert Lippert - Patrick Venture - -Description ------------ - -Intersil ISL68137 is a digital output 7-phase configurable PWM -controller with an AVSBus interface. - -Usage Notes ------------ - -This driver does not probe for PMBus devices. You will have to instantiate -devices explicitly. - -The ISL68137 AVS operation mode must be enabled/disabled at runtime. - -Beyond the normal sysfs pmbus attributes, the driver exposes a control attribute. - -Additional Sysfs attributes ---------------------------- - -avs(0|1)_enable Controls the AVS state of each rail. - -curr1_label "iin" -curr1_input Measured input current -curr1_crit Critical maximum current -curr1_crit_alarm Current critical high alarm - -curr[2-3]_label "iout[1-2]" -curr[2-3]_input Measured output current -curr[2-3]_crit Critical maximum current -curr[2-3]_crit_alarm Current critical high alarm - -in1_label "vin" -in1_input Measured input voltage -in1_lcrit Critical minimum input voltage -in1_lcrit_alarm Input voltage critical low alarm -in1_crit Critical maximum input voltage -in1_crit_alarm Input voltage critical high alarm - -in[2-3]_label "vout[1-2]" -in[2-3]_input Measured output voltage -in[2-3]_lcrit Critical minimum output voltage -in[2-3]_lcrit_alarm Output voltage critical low alarm -in[2-3]_crit Critical maximum output voltage -in[2-3]_crit_alarm Output voltage critical high alarm - -power1_label "pin" -power1_input Measured input power -power1_alarm Input power high alarm - -power[2-3]_label "pout[1-2]" -power[2-3]_input Measured output power - -temp[1-3]_input Measured temperature -temp[1-3]_crit Critical high temperature -temp[1-3]_crit_alarm Chip temperature critical high alarm -temp[1-3]_max Maximum temperature -temp[1-3]_max_alarm Chip temperature high alarm diff --git a/Documentation/hwmon/isl68137.rst b/Documentation/hwmon/isl68137.rst new file mode 100644 index 000000000000..a5a7c8545c9e --- /dev/null +++ b/Documentation/hwmon/isl68137.rst @@ -0,0 +1,80 @@ +Kernel driver isl68137 +====================== + +Supported chips: + + * Intersil ISL68137 + + Prefix: 'isl68137' + + Addresses scanned: - + + Datasheet: + + Publicly available at the Intersil website + https://www.intersil.com/content/dam/Intersil/documents/isl6/isl68137.pdf + +Authors: + - Maxim Sloyko + - Robert Lippert + - Patrick Venture + +Description +----------- + +Intersil ISL68137 is a digital output 7-phase configurable PWM +controller with an AVSBus interface. + +Usage Notes +----------- + +This driver does not probe for PMBus devices. You will have to instantiate +devices explicitly. + +The ISL68137 AVS operation mode must be enabled/disabled at runtime. + +Beyond the normal sysfs pmbus attributes, the driver exposes a control attribute. + +Additional Sysfs attributes +--------------------------- + +======================= ==================================== +avs(0|1)_enable Controls the AVS state of each rail. + +curr1_label "iin" +curr1_input Measured input current +curr1_crit Critical maximum current +curr1_crit_alarm Current critical high alarm + +curr[2-3]_label "iout[1-2]" +curr[2-3]_input Measured output current +curr[2-3]_crit Critical maximum current +curr[2-3]_crit_alarm Current critical high alarm + +in1_label "vin" +in1_input Measured input voltage +in1_lcrit Critical minimum input voltage +in1_lcrit_alarm Input voltage critical low alarm +in1_crit Critical maximum input voltage +in1_crit_alarm Input voltage critical high alarm + +in[2-3]_label "vout[1-2]" +in[2-3]_input Measured output voltage +in[2-3]_lcrit Critical minimum output voltage +in[2-3]_lcrit_alarm Output voltage critical low alarm +in[2-3]_crit Critical maximum output voltage +in[2-3]_crit_alarm Output voltage critical high alarm + +power1_label "pin" +power1_input Measured input power +power1_alarm Input power high alarm + +power[2-3]_label "pout[1-2]" +power[2-3]_input Measured output power + +temp[1-3]_input Measured temperature +temp[1-3]_crit Critical high temperature +temp[1-3]_crit_alarm Chip temperature critical high alarm +temp[1-3]_max Maximum temperature +temp[1-3]_max_alarm Chip temperature high alarm +======================= ==================================== diff --git a/Documentation/hwmon/lochnagar b/Documentation/hwmon/lochnagar deleted file mode 100644 index e9686fb3eb40..000000000000 --- a/Documentation/hwmon/lochnagar +++ /dev/null @@ -1,80 +0,0 @@ -Kernel Driver Lochnagar -======================== - -Supported systems: - * Cirrus Logic : Lochnagar 2 - -Author: Lucas A. Tanure Alves - -Description ------------ - -Lochnagar 2 features built-in Current Monitor circuitry that allows for the -measurement of both voltage and current on up to eight of the supply voltage -rails provided to the minicards. The Current Monitor does not require any -hardware modifications or external circuitry to operate. - -The current and voltage measurements are obtained through the standard register -map interface to the Lochnagar board controller, and can therefore be monitored -by software. - -Sysfs attributes ----------------- - -temp1_input The Lochnagar board temperature (milliCelsius) -in0_input Measured voltage for DBVDD1 (milliVolts) -in0_label "DBVDD1" -curr1_input Measured current for DBVDD1 (milliAmps) -curr1_label "DBVDD1" -power1_average Measured average power for DBVDD1 (microWatts) -power1_average_interval Power averaging time input valid from 1 to 1708mS -power1_label "DBVDD1" -in1_input Measured voltage for 1V8 DSP (milliVolts) -in1_label "1V8 DSP" -curr2_input Measured current for 1V8 DSP (milliAmps) -curr2_label "1V8 DSP" -power2_average Measured average power for 1V8 DSP (microWatts) -power2_average_interval Power averaging time input valid from 1 to 1708mS -power2_label "1V8 DSP" -in2_input Measured voltage for 1V8 CDC (milliVolts) -in2_label "1V8 CDC" -curr3_input Measured current for 1V8 CDC (milliAmps) -curr3_label "1V8 CDC" -power3_average Measured average power for 1V8 CDC (microWatts) -power3_average_interval Power averaging time input valid from 1 to 1708mS -power3_label "1V8 CDC" -in3_input Measured voltage for VDDCORE DSP (milliVolts) -in3_label "VDDCORE DSP" -curr4_input Measured current for VDDCORE DSP (milliAmps) -curr4_label "VDDCORE DSP" -power4_average Measured average power for VDDCORE DSP (microWatts) -power4_average_interval Power averaging time input valid from 1 to 1708mS -power4_label "VDDCORE DSP" -in4_input Measured voltage for AVDD 1V8 (milliVolts) -in4_label "AVDD 1V8" -curr5_input Measured current for AVDD 1V8 (milliAmps) -curr5_label "AVDD 1V8" -power5_average Measured average power for AVDD 1V8 (microWatts) -power5_average_interval Power averaging time input valid from 1 to 1708mS -power5_label "AVDD 1V8" -curr6_input Measured current for SYSVDD (milliAmps) -curr6_label "SYSVDD" -power6_average Measured average power for SYSVDD (microWatts) -power6_average_interval Power averaging time input valid from 1 to 1708mS -power6_label "SYSVDD" -in6_input Measured voltage for VDDCORE CDC (milliVolts) -in6_label "VDDCORE CDC" -curr7_input Measured current for VDDCORE CDC (milliAmps) -curr7_label "VDDCORE CDC" -power7_average Measured average power for VDDCORE CDC (microWatts) -power7_average_interval Power averaging time input valid from 1 to 1708mS -power7_label "VDDCORE CDC" -in7_input Measured voltage for MICVDD (milliVolts) -in7_label "MICVDD" -curr8_input Measured current for MICVDD (milliAmps) -curr8_label "MICVDD" -power8_average Measured average power for MICVDD (microWatts) -power8_average_interval Power averaging time input valid from 1 to 1708mS -power8_label "MICVDD" - -Note: It is not possible to measure voltage on the SYSVDD rail. diff --git a/Documentation/hwmon/lochnagar.rst b/Documentation/hwmon/lochnagar.rst new file mode 100644 index 000000000000..1d609c4d18c3 --- /dev/null +++ b/Documentation/hwmon/lochnagar.rst @@ -0,0 +1,83 @@ +Kernel Driver Lochnagar +======================= + +Supported systems: + * Cirrus Logic : Lochnagar 2 + +Author: Lucas A. Tanure Alves + +Description +----------- + +Lochnagar 2 features built-in Current Monitor circuitry that allows for the +measurement of both voltage and current on up to eight of the supply voltage +rails provided to the minicards. The Current Monitor does not require any +hardware modifications or external circuitry to operate. + +The current and voltage measurements are obtained through the standard register +map interface to the Lochnagar board controller, and can therefore be monitored +by software. + +Sysfs attributes +---------------- + +======================= ======================================================= +temp1_input The Lochnagar board temperature (milliCelsius) +in0_input Measured voltage for DBVDD1 (milliVolts) +in0_label "DBVDD1" +curr1_input Measured current for DBVDD1 (milliAmps) +curr1_label "DBVDD1" +power1_average Measured average power for DBVDD1 (microWatts) +power1_average_interval Power averaging time input valid from 1 to 1708mS +power1_label "DBVDD1" +in1_input Measured voltage for 1V8 DSP (milliVolts) +in1_label "1V8 DSP" +curr2_input Measured current for 1V8 DSP (milliAmps) +curr2_label "1V8 DSP" +power2_average Measured average power for 1V8 DSP (microWatts) +power2_average_interval Power averaging time input valid from 1 to 1708mS +power2_label "1V8 DSP" +in2_input Measured voltage for 1V8 CDC (milliVolts) +in2_label "1V8 CDC" +curr3_input Measured current for 1V8 CDC (milliAmps) +curr3_label "1V8 CDC" +power3_average Measured average power for 1V8 CDC (microWatts) +power3_average_interval Power averaging time input valid from 1 to 1708mS +power3_label "1V8 CDC" +in3_input Measured voltage for VDDCORE DSP (milliVolts) +in3_label "VDDCORE DSP" +curr4_input Measured current for VDDCORE DSP (milliAmps) +curr4_label "VDDCORE DSP" +power4_average Measured average power for VDDCORE DSP (microWatts) +power4_average_interval Power averaging time input valid from 1 to 1708mS +power4_label "VDDCORE DSP" +in4_input Measured voltage for AVDD 1V8 (milliVolts) +in4_label "AVDD 1V8" +curr5_input Measured current for AVDD 1V8 (milliAmps) +curr5_label "AVDD 1V8" +power5_average Measured average power for AVDD 1V8 (microWatts) +power5_average_interval Power averaging time input valid from 1 to 1708mS +power5_label "AVDD 1V8" +curr6_input Measured current for SYSVDD (milliAmps) +curr6_label "SYSVDD" +power6_average Measured average power for SYSVDD (microWatts) +power6_average_interval Power averaging time input valid from 1 to 1708mS +power6_label "SYSVDD" +in6_input Measured voltage for VDDCORE CDC (milliVolts) +in6_label "VDDCORE CDC" +curr7_input Measured current for VDDCORE CDC (milliAmps) +curr7_label "VDDCORE CDC" +power7_average Measured average power for VDDCORE CDC (microWatts) +power7_average_interval Power averaging time input valid from 1 to 1708mS +power7_label "VDDCORE CDC" +in7_input Measured voltage for MICVDD (milliVolts) +in7_label "MICVDD" +curr8_input Measured current for MICVDD (milliAmps) +curr8_label "MICVDD" +power8_average Measured average power for MICVDD (microWatts) +power8_average_interval Power averaging time input valid from 1 to 1708mS +power8_label "MICVDD" +======================= ======================================================= + +Note: + It is not possible to measure voltage on the SYSVDD rail. -- cgit v1.2.3 From f786dbbe6f2683d6ed0823f3ee53203afeea1ec7 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Mon, 22 Apr 2019 08:14:55 -0300 Subject: docs: hwmon: remove the extension from .rst files On almost all places, we're including ReST files without the extension. Let's remove the extension here as well, in order to use just one standard. Suggested-by: Jani Nikula Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Guenter Roeck --- Documentation/hwmon/index.rst | 322 +++++++++++++++++++++--------------------- 1 file changed, 161 insertions(+), 161 deletions(-) (limited to 'Documentation') diff --git a/Documentation/hwmon/index.rst b/Documentation/hwmon/index.rst index 3fa14fe7b49c..ee090e51653a 100644 --- a/Documentation/hwmon/index.rst +++ b/Documentation/hwmon/index.rst @@ -5,11 +5,11 @@ Linux Hardware Monitoring .. toctree:: :maxdepth: 1 - hwmon-kernel-api.rst - pmbus-core.rst - submitting-patches.rst - sysfs-interface.rst - userspace-tools.rst + hwmon-kernel-api + pmbus-core + submitting-patches + sysfs-interface + userspace-tools Hardware Monitoring Kernel Drivers ================================== @@ -17,162 +17,162 @@ Hardware Monitoring Kernel Drivers .. toctree:: :maxdepth: 1 - ab8500.rst - abituguru.rst - abituguru3.rst - abx500.rst - acpi_power_meter.rst - ad7314.rst - adc128d818.rst - adm1021.rst - adm1025.rst - adm1026.rst - adm1031.rst - adm1275.rst - adm9240.rst - ads1015.rst - ads7828.rst - adt7410.rst - adt7411.rst - adt7462.rst - adt7470.rst - adt7475.rst - amc6821.rst - asb100.rst - asc7621.rst - aspeed-pwm-tacho.rst - coretemp.rst - da9052.rst - da9055.rst - dme1737.rst - ds1621.rst - ds620.rst - emc1403.rst - emc2103.rst - emc6w201.rst - f71805f.rst - f71882fg.rst - fam15h_power.rst - ftsteutates.rst - g760a.rst - g762.rst - gl518sm.rst - hih6130.rst - ibmaem.rst - ibm-cffps.rst - ibmpowernv.rst - ina209.rst - ina2xx.rst - ina3221.rst - ir35221.rst - ir38064.rst - isl68137.rst - it87.rst - jc42.rst - k10temp.rst - k8temp.rst - lineage-pem.rst - lm25066.rst - lm63.rst - lm70.rst - lm73.rst - lm75.rst - lm77.rst - lm78.rst - lm80.rst - lm83.rst - lm85.rst - lm87.rst - lm90.rst - lm92.rst - lm93.rst - lm95234.rst - lm95245.rst - lochnagar.rst - ltc2945.rst - ltc2978.rst - ltc2990.rst - ltc3815.rst - ltc4151.rst - ltc4215.rst - ltc4245.rst - ltc4260.rst - ltc4261.rst - max16064.rst - max16065.rst - max1619.rst - max1668.rst - max197.rst - max20751.rst - max31722.rst - max31785.rst - max31790.rst - max34440.rst - max6639.rst - max6642.rst - max6650.rst - max6697.rst - max8688.rst - mc13783-adc.rst - mcp3021.rst - menf21bmc.rst - mlxreg-fan.rst - nct6683.rst - nct6775.rst - nct7802.rst - nct7904.rst - npcm750-pwm-fan.rst - nsa320.rst - ntc_thermistor.rst - occ.rst - pc87360.rst - pc87427.rst - pcf8591.rst - pmbus.rst - powr1220.rst - pwm-fan.rst - raspberrypi-hwmon.rst - sch5627.rst - sch5636.rst - scpi-hwmon.rst - sht15.rst - sht21.rst - sht3x.rst - shtc1.rst - sis5595.rst - smm665.rst - smsc47b397.rst - smsc47m192.rst - smsc47m1.rst - tc654.rst - tc74.rst - thmc50.rst - tmp102.rst - tmp103.rst - tmp108.rst - tmp401.rst - tmp421.rst - tps40422.rst - twl4030-madc-hwmon.rst - ucd9000.rst - ucd9200.rst - vexpress.rst - via686a.rst - vt1211.rst - w83627ehf.rst - w83627hf.rst - w83773g.rst - w83781d.rst - w83791d.rst - w83792d.rst - w83793.rst - w83795.rst - w83l785ts.rst - w83l786ng.rst - wm831x.rst - wm8350.rst - xgene-hwmon.rst - zl6100.rst + ab8500 + abituguru + abituguru3 + abx500 + acpi_power_meter + ad7314 + adc128d818 + adm1021 + adm1025 + adm1026 + adm1031 + adm1275 + adm9240 + ads1015 + ads7828 + adt7410 + adt7411 + adt7462 + adt7470 + adt7475 + amc6821 + asb100 + asc7621 + aspeed-pwm-tacho + coretemp + da9052 + da9055 + dme1737 + ds1621 + ds620 + emc1403 + emc2103 + emc6w201 + f71805f + f71882fg + fam15h_power + ftsteutates + g760a + g762 + gl518sm + hih6130 + ibmaem + ibm-cffps + ibmpowernv + ina209 + ina2xx + ina3221 + ir35221 + ir38064 + isl68137 + it87 + jc42 + k10temp + k8temp + lineage-pem + lm25066 + lm63 + lm70 + lm73 + lm75 + lm77 + lm78 + lm80 + lm83 + lm85 + lm87 + lm90 + lm92 + lm93 + lm95234 + lm95245 + lochnagar + ltc2945 + ltc2978 + ltc2990 + ltc3815 + ltc4151 + ltc4215 + ltc4245 + ltc4260 + ltc4261 + max16064 + max16065 + max1619 + max1668 + max197 + max20751 + max31722 + max31785 + max31790 + max34440 + max6639 + max6642 + max6650 + max6697 + max8688 + mc13783-adc + mcp3021 + menf21bmc + mlxreg-fan + nct6683 + nct6775 + nct7802 + nct7904 + npcm750-pwm-fan + nsa320 + ntc_thermistor + occ + pc87360 + pc87427 + pcf8591 + pmbus + powr1220 + pwm-fan + raspberrypi-hwmon + sch5627 + sch5636 + scpi-hwmon + sht15 + sht21 + sht3x + shtc1 + sis5595 + smm665 + smsc47b397 + smsc47m192 + smsc47m1 + tc654 + tc74 + thmc50 + tmp102 + tmp103 + tmp108 + tmp401 + tmp421 + tps40422 + twl4030-madc-hwmon + ucd9000 + ucd9200 + vexpress + via686a + vt1211 + w83627ehf + w83627hf + w83773g + w83781d + w83791d + w83792d + w83793 + w83795 + w83l785ts + w83l786ng + wm831x + wm8350 + xgene-hwmon + zl6100 .. only:: subproject and html -- cgit v1.2.3 From 3b8802446d27522cd6d32178ba975cc492611f31 Mon Sep 17 00:00:00 2001 From: Alexei Starovoitov Date: Wed, 17 Apr 2019 18:27:01 -0700 Subject: bpf: document the verifier limits Document the verifier limits. Signed-off-by: Alexei Starovoitov Acked-by: Yonghong Song Signed-off-by: Daniel Borkmann --- Documentation/bpf/bpf_design_QA.rst | 29 +++++++++++++++++++++++++++-- 1 file changed, 27 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/bpf/bpf_design_QA.rst b/Documentation/bpf/bpf_design_QA.rst index 10453c627135..cb402c59eca5 100644 --- a/Documentation/bpf/bpf_design_QA.rst +++ b/Documentation/bpf/bpf_design_QA.rst @@ -85,8 +85,33 @@ Q: Can loops be supported in a safe way? A: It's not clear yet. BPF developers are trying to find a way to -support bounded loops where the verifier can guarantee that -the program terminates in less than 4096 instructions. +support bounded loops. + +Q: What are the verifier limits? +-------------------------------- +A: The only limit known to the user space is BPF_MAXINSNS (4096). +It's the maximum number of instructions that the unprivileged bpf +program can have. The verifier has various internal limits. +Like the maximum number of instructions that can be explored during +program analysis. Currently, that limit is set to 1 million. +Which essentially means that the largest program can consist +of 1 million NOP instructions. There is a limit to the maximum number +of subsequent branches, a limit to the number of nested bpf-to-bpf +calls, a limit to the number of the verifier states per instruction, +a limit to the number of maps used by the program. +All these limits can be hit with a sufficiently complex program. +There are also non-numerical limits that can cause the program +to be rejected. The verifier used to recognize only pointer + constant +expressions. Now it can recognize pointer + bounded_register. +bpf_lookup_map_elem(key) had a requirement that 'key' must be +a pointer to the stack. Now, 'key' can be a pointer to map value. +The verifier is steadily getting 'smarter'. The limits are +being removed. The only way to know that the program is going to +be accepted by the verifier is to try to load it. +The bpf development process guarantees that the future kernel +versions will accept all bpf programs that were accepted by +the earlier versions. + Instruction level questions --------------------------- -- cgit v1.2.3 From e2c7f52bcdaf6ee24447cd7bc6100702c0b0f777 Mon Sep 17 00:00:00 2001 From: Andrey Smirnov Date: Sun, 14 Apr 2019 11:34:00 -0700 Subject: dt-bindings: iio: imx7d-adc: Add #io-channel-cells to required Add #io-channel-cells to list of required properties. Needed to be able to reference that node by phandle. Signed-off-by: Andrey Smirnov Cc: Shawn Guo Cc: Chris Healy Cc: Andrew Lunn Cc: Fabio Estevam Cc: Rob Herring Cc: linux-kernel@vger.kernel.org Cc: devicetree@vger.kernel.org Signed-off-by: Shawn Guo --- Documentation/devicetree/bindings/iio/adc/imx7d-adc.txt | 2 ++ 1 file changed, 2 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/iio/adc/imx7d-adc.txt b/Documentation/devicetree/bindings/iio/adc/imx7d-adc.txt index 5c184b940669..f1f3a552459b 100644 --- a/Documentation/devicetree/bindings/iio/adc/imx7d-adc.txt +++ b/Documentation/devicetree/bindings/iio/adc/imx7d-adc.txt @@ -10,6 +10,7 @@ Required properties: - clocks: The root clock of the ADC controller - clock-names: Must contain "adc", matching entry in the clocks property - vref-supply: The regulator supply ADC reference voltage +- #io-channel-cells: Must be 1 as per ../iio-bindings.txt Example: adc1: adc@30610000 { @@ -19,4 +20,5 @@ adc1: adc@30610000 { clocks = <&clks IMX7D_ADC_ROOT_CLK>; clock-names = "adc"; vref-supply = <®_vcc_3v3_mcu>; + #io-channel-cells = <1>; }; -- cgit v1.2.3 From 966d9b928f626a54a0c27c0fdae1e3dfe9bab416 Mon Sep 17 00:00:00 2001 From: Alexandre Torgue Date: Wed, 10 Apr 2019 13:30:20 +0200 Subject: dt-bindings: pinctrl: stm32: add new entry for package information Add "st,package" entry. Possibles values are: -STM32MP_PKG_AA for LFBGA448 (18*18) package -STM32MP_PKG_AB for LFBGA354 (16*16) package -STM32MP_PKG_AC for TFBGA361 (12*12) package -STM32MP_PKG_AD for TFBGA257 (10*10) package Signed-off-by: Alexandre Torgue Signed-off-by: Linus Walleij --- Documentation/devicetree/bindings/pinctrl/st,stm32-pinctrl.txt | 2 ++ include/dt-bindings/pinctrl/stm32-pinfunc.h | 6 ++++++ 2 files changed, 8 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/pinctrl/st,stm32-pinctrl.txt b/Documentation/devicetree/bindings/pinctrl/st,stm32-pinctrl.txt index 48df30a36b01..00169255e48c 100644 --- a/Documentation/devicetree/bindings/pinctrl/st,stm32-pinctrl.txt +++ b/Documentation/devicetree/bindings/pinctrl/st,stm32-pinctrl.txt @@ -57,6 +57,8 @@ Optional properties: - st,bank-ioport: should correspond to the EXTI IOport selection (EXTI line used to select GPIOs as interrupts). - hwlocks: reference to a phandle of a hardware spinlock provider node. + - st,package: Indicates the SOC package used. + More details in include/dt-bindings/pinctrl/stm32-pinfunc.h Example 1: #include diff --git a/include/dt-bindings/pinctrl/stm32-pinfunc.h b/include/dt-bindings/pinctrl/stm32-pinfunc.h index b5a2174a6386..e6fb8ada3f4d 100644 --- a/include/dt-bindings/pinctrl/stm32-pinfunc.h +++ b/include/dt-bindings/pinctrl/stm32-pinfunc.h @@ -32,5 +32,11 @@ #define STM32_PINMUX(port, line, mode) (((PIN_NO(port, line)) << 8) | (mode)) +/* package information */ +#define STM32MP_PKG_AA 0x1 +#define STM32MP_PKG_AB 0x2 +#define STM32MP_PKG_AC 0x4 +#define STM32MP_PKG_AD 0x8 + #endif /* _DT_BINDINGS_STM32_PINFUNC_H */ -- cgit v1.2.3 From 9726840d9cf0d42377e1591263d7c1d9ae0988ac Mon Sep 17 00:00:00 2001 From: Will Deacon Date: Fri, 12 Apr 2019 13:42:18 +0100 Subject: docs/memory-barriers.txt: Update I/O section to be clearer about CPU vs thread The revised I/O ordering section of memory-barriers.txt introduced in 4614bbdee357 ("docs/memory-barriers.txt: Rewrite "KERNEL I/O BARRIER EFFECTS" section") loosely refers to "the CPU", whereas the ordering guarantees generally apply within a thread of execution that can migrate between cores, with the scheduler providing the relevant barrier semantics. Reword the section to refer to "CPU thread" and call out ordering of MMIO writes separately from ordering of writes to memory. Ben also spotted that the string accessors are native-endian, so fix that up too. Link: https://lkml.kernel.org/r/080d1ec73e3e29d6ffeeeb50b39b613da28afb37.camel@kernel.crashing.org Fixes: 4614bbdee357 ("docs/memory-barriers.txt: Rewrite "KERNEL I/O BARRIER EFFECTS" section") Reported-by: Benjamin Herrenschmidt Signed-off-by: Will Deacon --- Documentation/memory-barriers.txt | 67 +++++++++++++++++++++++---------------- 1 file changed, 40 insertions(+), 27 deletions(-) (limited to 'Documentation') diff --git a/Documentation/memory-barriers.txt b/Documentation/memory-barriers.txt index 1660dde75e14..f70ebcdfe592 100644 --- a/Documentation/memory-barriers.txt +++ b/Documentation/memory-barriers.txt @@ -2523,27 +2523,37 @@ guarantees: ioremap()), the ordering guarantees are as follows: 1. All readX() and writeX() accesses to the same peripheral are ordered - with respect to each other. This ensures that MMIO register writes by - the CPU to a particular device will arrive in program order. - - 2. A writeX() by the CPU to the peripheral will first wait for the - completion of all prior CPU writes to memory. This ensures that - writes by the CPU to an outbound DMA buffer allocated by - dma_alloc_coherent() will be visible to a DMA engine when the CPU - writes to its MMIO control register to trigger the transfer. - - 3. A readX() by the CPU from the peripheral will complete before any - subsequent CPU reads from memory can begin. This ensures that reads - by the CPU from an incoming DMA buffer allocated by - dma_alloc_coherent() will not see stale data after reading from the - DMA engine's MMIO status register to establish that the DMA transfer - has completed. - - 4. A readX() by the CPU from the peripheral will complete before any - subsequent delay() loop can begin execution. This ensures that two - MMIO register writes by the CPU to a peripheral will arrive at least - 1us apart if the first write is immediately read back with readX() - and udelay(1) is called prior to the second writeX(): + with respect to each other. This ensures that MMIO register accesses + by the same CPU thread to a particular device will arrive in program + order. + + 2. A writeX() issued by a CPU thread holding a spinlock is ordered + before a writeX() to the same peripheral from another CPU thread + issued after a later acquisition of the same spinlock. This ensures + that MMIO register writes to a particular device issued while holding + a spinlock will arrive in an order consistent with acquisitions of + the lock. + + 3. A writeX() by a CPU thread to the peripheral will first wait for the + completion of all prior writes to memory either issued by, or + propagated to, the same thread. This ensures that writes by the CPU + to an outbound DMA buffer allocated by dma_alloc_coherent() will be + visible to a DMA engine when the CPU writes to its MMIO control + register to trigger the transfer. + + 4. A readX() by a CPU thread from the peripheral will complete before + any subsequent reads from memory by the same thread can begin. This + ensures that reads by the CPU from an incoming DMA buffer allocated + by dma_alloc_coherent() will not see stale data after reading from + the DMA engine's MMIO status register to establish that the DMA + transfer has completed. + + 5. A readX() by a CPU thread from the peripheral will complete before + any subsequent delay() loop can begin execution on the same thread. + This ensures that two MMIO register writes by the CPU to a peripheral + will arrive at least 1us apart if the first write is immediately read + back with readX() and udelay(1) is called prior to the second + writeX(): writel(42, DEVICE_REGISTER_0); // Arrives at the device... readl(DEVICE_REGISTER_0); @@ -2559,10 +2569,11 @@ guarantees: These are similar to readX() and writeX(), but provide weaker memory ordering guarantees. Specifically, they do not guarantee ordering with - respect to normal memory accesses or delay() loops (i.e. bullets 2-4 - above) but they are still guaranteed to be ordered with respect to other - accesses to the same peripheral when operating on __iomem pointers - mapped with the default I/O attributes. + respect to locking, normal memory accesses or delay() loops (i.e. + bullets 2-5 above) but they are still guaranteed to be ordered with + respect to other accesses from the same CPU thread to the same + peripheral when operating on __iomem pointers mapped with the default + I/O attributes. (*) readsX(), writesX(): @@ -2600,8 +2611,10 @@ guarantees: These will perform appropriately for the type of access they're actually doing, be it inX()/outX() or readX()/writeX(). -All of these accessors assume that the underlying peripheral is little-endian, -and will therefore perform byte-swapping operations on big-endian architectures. +With the exception of the string accessors (insX(), outsX(), readsX() and +writesX()), all of the above assume that the underlying peripheral is +little-endian and will therefore perform byte-swapping operations on big-endian +architectures. ======================================== -- cgit v1.2.3 From 167c6b5ecee1c91867b4a92fcd472e3ddeaeffdc Mon Sep 17 00:00:00 2001 From: Linus Walleij Date: Fri, 1 Feb 2019 17:09:46 +0100 Subject: irqchip: ixp4xx: Add DT bindings This adds device tree bindings for the IXP4xx interrupt controller. It's a standard 2-cell controller. Cc: Marc Zyngier Cc: Jason Cooper Cc: Thomas Gleixner Cc: devicetree@vger.kernel.org Reviewed-by: Rob Herring Signed-off-by: Linus Walleij --- .../intel,ixp4xx-interrupt.yaml | 54 ++++++++++++++++++++++ MAINTAINERS | 1 + 2 files changed, 55 insertions(+) create mode 100644 Documentation/devicetree/bindings/interrupt-controller/intel,ixp4xx-interrupt.yaml (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/interrupt-controller/intel,ixp4xx-interrupt.yaml b/Documentation/devicetree/bindings/interrupt-controller/intel,ixp4xx-interrupt.yaml new file mode 100644 index 000000000000..bae10e261fa9 --- /dev/null +++ b/Documentation/devicetree/bindings/interrupt-controller/intel,ixp4xx-interrupt.yaml @@ -0,0 +1,54 @@ +# SPDX-License-Identifier: (GPL-2.0 OR BSD-2-Clause) +# Copyright 2018 Linaro Ltd. +%YAML 1.2 +--- +$id: "http://devicetree.org/schemas/interrupt/intel-ixp4xx-interrupt.yaml#" +$schema: "http://devicetree.org/meta-schemas/core.yaml#" + +title: Intel IXP4xx XScale Networking Processors Interrupt Controller + +maintainers: + - Linus Walleij + +description: | + This interrupt controller is found in the Intel IXP4xx processors. + Some processors have 32 interrupts, some have up to 64 interrupts. + The exact number of interrupts is determined from the compatible + string. + + The distinct IXP4xx families with different interrupt controller + variations are IXP42x, IXP43x, IXP45x and IXP46x. Those four + families were the only ones to reach the developer and consumer + market. + +properties: + compatible: + items: + - enum: + - intel,ixp42x-interrupt + - intel,ixp43x-interrupt + - intel,ixp45x-interrupt + - intel,ixp46x-interrupt + + reg: + maxItems: 1 + + interrupt-controller: true + + '#interrupt-cells': + const: 2 + +required: + - compatible + - reg + - interrupt-controller + - '#interrupt-cells' + +examples: + - | + intcon: interrupt-controller@c8003000 { + compatible = "intel,ixp43x-interrupt"; + reg = <0xc8003000 0x100>; + interrupt-controller; + #interrupt-cells = <2>; + }; diff --git a/MAINTAINERS b/MAINTAINERS index bc918f318797..ad05704fbd68 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -1690,6 +1690,7 @@ M: Imre Kaloz M: Krzysztof Halasa L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained +F: Documentation/devicetree/bindings/interrupt-controller/intel,ixp4xx-interrupt.yaml F: arch/arm/mach-ixp4xx/ F: drivers/clocksource/timer-ixp4xx.c F: drivers/gpio/gpio-ixp4xx.c -- cgit v1.2.3 From 7c23b0e1d4d32f1d1a96730ff1abb8b6cc681cfc Mon Sep 17 00:00:00 2001 From: Linus Walleij Date: Fri, 1 Feb 2019 19:12:58 +0100 Subject: clocksource/drivers/ixp4xx: Add DT bindings This adds device tree bindings for the Intel IXP4xx timers. Cc: Daniel Lezcano Cc: Thomas Gleixner Cc: devicetree@vger.kernel.org Reviewed-by: Rob Herring Signed-off-by: Linus Walleij --- .../bindings/timer/intel,ixp4xx-timer.yaml | 42 ++++++++++++++++++++++ MAINTAINERS | 1 + 2 files changed, 43 insertions(+) create mode 100644 Documentation/devicetree/bindings/timer/intel,ixp4xx-timer.yaml (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/timer/intel,ixp4xx-timer.yaml b/Documentation/devicetree/bindings/timer/intel,ixp4xx-timer.yaml new file mode 100644 index 000000000000..a36a0746c056 --- /dev/null +++ b/Documentation/devicetree/bindings/timer/intel,ixp4xx-timer.yaml @@ -0,0 +1,42 @@ +# SPDX-License-Identifier: (GPL-2.0 OR BSD-2-Clause) +# Copyright 2018 Linaro Ltd. +%YAML 1.2 +--- +$id: "http://devicetree.org/schemas/timer/intel-ixp4xx-timer.yaml#" +$schema: "http://devicetree.org/meta-schemas/core.yaml#" + +title: Intel IXP4xx XScale Networking Processors Timers + +maintainers: + - Linus Walleij + +description: This timer is found in the Intel IXP4xx processors. + +properties: + compatible: + items: + - const: intel,ixp4xx-timer + + reg: + description: Should contain registers location and length + + interrupts: + minItems: 1 + maxItems: 2 + items: + - description: Timer 1 interrupt + - description: Timer 2 interrupt + +required: + - compatible + - reg + - interrupts + +examples: + - | + #include + timer@c8005000 { + compatible = "intel,ixp4xx-timer"; + reg = <0xc8005000 0x100>; + interrupts = <5 IRQ_TYPE_LEVEL_HIGH>; + }; diff --git a/MAINTAINERS b/MAINTAINERS index ad05704fbd68..78f50505a313 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -1691,6 +1691,7 @@ M: Krzysztof Halasa L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained F: Documentation/devicetree/bindings/interrupt-controller/intel,ixp4xx-interrupt.yaml +F: Documentation/devicetree/bindings/timer/intel,ixp4xx-timer.yaml F: arch/arm/mach-ixp4xx/ F: drivers/clocksource/timer-ixp4xx.c F: drivers/gpio/gpio-ixp4xx.c -- cgit v1.2.3 From 50d2c8d29106a6309b97d7ca75b48f2c42850d1f Mon Sep 17 00:00:00 2001 From: Linus Walleij Date: Sun, 3 Feb 2019 14:51:12 +0100 Subject: ARM: ixp4xx: Add DT bindings This adds initial device tree bindings for the IXP4xx machines. This time I tried something wild and crazy and try to make proper JSON-style YAML bindings for the top level. Cc: devicetree@vger.kernel.org Reviewed-by: Rob Herring Signed-off-by: Linus Walleij --- .../devicetree/bindings/arm/intel-ixp4xx.yaml | 22 ++++++++++++++++++++++ MAINTAINERS | 1 + 2 files changed, 23 insertions(+) create mode 100644 Documentation/devicetree/bindings/arm/intel-ixp4xx.yaml (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/intel-ixp4xx.yaml b/Documentation/devicetree/bindings/arm/intel-ixp4xx.yaml new file mode 100644 index 000000000000..f4f7451e5e8a --- /dev/null +++ b/Documentation/devicetree/bindings/arm/intel-ixp4xx.yaml @@ -0,0 +1,22 @@ +# SPDX-License-Identifier: GPL-2.0 +%YAML 1.2 +--- +$id: http://devicetree.org/schemas/arm/intel-ixp4xx.yaml# +$schema: http://devicetree.org/meta-schemas/core.yaml# + +title: Intel IXP4xx Device Tree Bindings + +maintainers: + - Linus Walleij + +properties: + compatible: + oneOf: + - items: + - enum: + - linksys,nslu2 + - const: intel,ixp42x + - items: + - enum: + - gateworks,gw2358 + - const: intel,ixp43x diff --git a/MAINTAINERS b/MAINTAINERS index 0a8999c09764..49052de0567b 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -1690,6 +1690,7 @@ M: Imre Kaloz M: Krzysztof Halasa L: linux-arm-kernel@lists.infradead.org (moderated for non-subscribers) S: Maintained +F: Documentation/devicetree/bindings/arm/intel-ixp4xx.yaml F: Documentation/devicetree/bindings/gpio/intel,ixp4xx-gpio.txt F: Documentation/devicetree/bindings/interrupt-controller/intel,ixp4xx-interrupt.yaml F: Documentation/devicetree/bindings/timer/intel,ixp4xx-timer.yaml -- cgit v1.2.3 From 3107fbf7059bcad924a241271f667dc2f74910a5 Mon Sep 17 00:00:00 2001 From: Linus Walleij Date: Sun, 10 Feb 2019 22:40:48 +0100 Subject: soc: ixp4xx: Add DT bindings for IXP4xx NPE This adds DT bindings for the Intel IXP4xx Network Processing Engine (NPE). These are three firmware-executing units found in the IXP4xx SoC. These bindings use YAML. Cc: devicetree@vger.kernel.org Reviewed-by: Rob Herring Signed-off-by: Linus Walleij --- .../intel,ixp4xx-network-processing-engine.yaml | 44 ++++++++++++++++++++++ 1 file changed, 44 insertions(+) create mode 100644 Documentation/devicetree/bindings/firmware/intel,ixp4xx-network-processing-engine.yaml (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/firmware/intel,ixp4xx-network-processing-engine.yaml b/Documentation/devicetree/bindings/firmware/intel,ixp4xx-network-processing-engine.yaml new file mode 100644 index 000000000000..8cb136c376fb --- /dev/null +++ b/Documentation/devicetree/bindings/firmware/intel,ixp4xx-network-processing-engine.yaml @@ -0,0 +1,44 @@ +# SPDX-License-Identifier: (GPL-2.0 OR BSD-2-Clause) +# Copyright 2019 Linaro Ltd. +%YAML 1.2 +--- +$id: "http://devicetree.org/schemas/firmware/intel-ixp4xx-network-processing-engine.yaml#" +$schema: "http://devicetree.org/meta-schemas/core.yaml#" + +title: Intel IXP4xx Network Processing Engine + +maintainers: + - Linus Walleij + +description: | + On the IXP4xx SoCs, the Network Processing Engine (NPE) is a small + processor that can load a firmware to perform offloading of networking + and crypto tasks. It also manages the MDIO bus to the ethernet PHYs + on the IXP4xx platform. All IXP4xx platforms have three NPEs at + consecutive memory locations. They are all included in the same + device node since they are not independent of each other. + +properties: + compatible: + oneOf: + - items: + - const: intel,ixp4xx-network-processing-engine + + reg: + minItems: 3 + maxItems: 3 + items: + - description: NPE0 register range + - description: NPE1 register range + - description: NPE2 register range + +required: + - compatible + - reg + +examples: + - | + npe@c8006000 { + compatible = "intel,ixp4xx-network-processing-engine"; + reg = <0xc8006000 0x1000>, <0xc8007000 0x1000>, <0xc8008000 0x1000>; + }; -- cgit v1.2.3 From 6e2b0f8c9bc8897f6260981cff231632c20d3048 Mon Sep 17 00:00:00 2001 From: Linus Walleij Date: Sun, 10 Feb 2019 23:40:28 +0100 Subject: soc: ixp4xx: qmgr: Add DT bindings for IXP4xx qmgr This adds device tree bindings for the Intel IXP4xx AHB Queue Manager. Cc: devicetree@vger.kernel.org Reviewed-by: Rob Herring Signed-off-by: Linus Walleij --- .../bindings/misc/intel,ixp4xx-queue-manager.yaml | 49 ++++++++++++++++++++++ 1 file changed, 49 insertions(+) create mode 100644 Documentation/devicetree/bindings/misc/intel,ixp4xx-queue-manager.yaml (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/misc/intel,ixp4xx-queue-manager.yaml b/Documentation/devicetree/bindings/misc/intel,ixp4xx-queue-manager.yaml new file mode 100644 index 000000000000..d2313b1d9405 --- /dev/null +++ b/Documentation/devicetree/bindings/misc/intel,ixp4xx-queue-manager.yaml @@ -0,0 +1,49 @@ +# SPDX-License-Identifier: (GPL-2.0 OR BSD-2-Clause) +# Copyright 2019 Linaro Ltd. +%YAML 1.2 +--- +$id: "http://devicetree.org/schemas/misc/intel-ixp4xx-ahb-queue-manager.yaml#" +$schema: "http://devicetree.org/meta-schemas/core.yaml#" + +title: Intel IXP4xx AHB Queue Manager + +maintainers: + - Linus Walleij + +description: | + The IXP4xx AHB Queue Manager maintains queues as circular buffers in + an 8KB embedded SRAM along with hardware pointers. It is used by both + the XScale processor and the NPEs (Network Processing Units) in the + IXP4xx for accelerating queues, especially for networking. Clients pick + queues from the queue manager with foo-queue = <&qmgr N> where the + &qmgr is a phandle to the queue manager and N is the queue resource + number. The queue resources available and their specific purpose + on a certain IXP4xx system will vary. + +properties: + compatible: + items: + - const: intel,ixp4xx-ahb-queue-manager + + reg: + maxItems: 1 + + interrupts: + items: + - description: Interrupt for queues 0-31 + - description: Interrupt for queues 32-63 + +required: + - compatible + - reg + - interrupts + +examples: + - | + #include + + qmgr: queue-manager@60000000 { + compatible = "intel,ixp4xx-ahb-queue-manager"; + reg = <0x60000000 0x4000>; + interrupts = <3 IRQ_TYPE_LEVEL_HIGH>, <4 IRQ_TYPE_LEVEL_HIGH>; + }; -- cgit v1.2.3 From 2ec16bc0fc7ab544f2d405fd4fdd0d717c5ec0c5 Mon Sep 17 00:00:00 2001 From: Ryan Thibodeaux Date: Fri, 22 Mar 2019 14:29:57 -0400 Subject: x86/xen: Add "xen_timer_slop" command line option Add a new command-line option "xen_timer_slop=" that sets the minimum delta of virtual Xen timers. This commit does not change the default timer slop value for virtual Xen timers. Lowering the timer slop value should improve the accuracy of virtual timers (e.g., better process dispatch latency), but it will likely increase the number of virtual timer interrupts (relative to the original slop setting). The original timer slop value has not changed since the introduction of the Xen-aware Linux kernel code. This commit provides users an opportunity to tune timer performance given the refinements to hardware and the Xen event channel processing. It also mirrors a feature in the Xen hypervisor - the "timer_slop" Xen command line option. [boris: updated comment describing TIMER_SLOP] Signed-off-by: Ryan Thibodeaux Reviewed-by: Boris Ostrovsky Signed-off-by: Boris Ostrovsky --- Documentation/admin-guide/kernel-parameters.txt | 7 +++++++ arch/x86/xen/time.c | 20 +++++++++++++++++--- 2 files changed, 24 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt index 2b8ee90bb644..2623749ae7a3 100644 --- a/Documentation/admin-guide/kernel-parameters.txt +++ b/Documentation/admin-guide/kernel-parameters.txt @@ -5173,6 +5173,13 @@ with /sys/devices/system/xen_memory/xen_memory0/scrub_pages. Default value controlled with CONFIG_XEN_SCRUB_PAGES_DEFAULT. + xen_timer_slop= [X86-64,XEN] + Set the timer slop (in nanoseconds) for the virtual Xen + timers (default is 100000). This adjusts the minimum + delta of virtualized Xen timers, where lower values + improve timer resolution at the expense of processing + more timer interrupts. + xirc2ps_cs= [NET,PCMCIA] Format: ,,,,,[,[,[,]]] diff --git a/arch/x86/xen/time.c b/arch/x86/xen/time.c index 6e29794573b7..befbdd8b17f0 100644 --- a/arch/x86/xen/time.c +++ b/arch/x86/xen/time.c @@ -28,7 +28,7 @@ #include "xen-ops.h" -/* Xen may fire a timer up to this many ns early */ +/* Minimum amount of time until next clock event fires */ #define TIMER_SLOP 100000 static u64 xen_sched_clock_offset __read_mostly; @@ -212,7 +212,7 @@ static int xen_timerop_set_next_event(unsigned long delta, return 0; } -static const struct clock_event_device xen_timerop_clockevent = { +static struct clock_event_device xen_timerop_clockevent __ro_after_init = { .name = "xen", .features = CLOCK_EVT_FEAT_ONESHOT, @@ -273,7 +273,7 @@ static int xen_vcpuop_set_next_event(unsigned long delta, return ret; } -static const struct clock_event_device xen_vcpuop_clockevent = { +static struct clock_event_device xen_vcpuop_clockevent __ro_after_init = { .name = "xen", .features = CLOCK_EVT_FEAT_ONESHOT, @@ -570,3 +570,17 @@ void __init xen_hvm_init_time_ops(void) x86_platform.set_wallclock = xen_set_wallclock; } #endif + +/* Kernel parameter to specify Xen timer slop */ +static int __init parse_xen_timer_slop(char *ptr) +{ + unsigned long slop = memparse(ptr, NULL); + + xen_timerop_clockevent.min_delta_ns = slop; + xen_timerop_clockevent.min_delta_ticks = slop; + xen_vcpuop_clockevent.min_delta_ns = slop; + xen_vcpuop_clockevent.min_delta_ticks = slop; + + return 0; +} +early_param("xen_timer_slop", parse_xen_timer_slop); -- cgit v1.2.3 From 06a916feca2b262ab0c1a2aeb68882f4b1108a07 Mon Sep 17 00:00:00 2001 From: Dave Martin Date: Thu, 18 Apr 2019 18:41:38 +0100 Subject: arm64: Expose SVE2 features for userspace This patch provides support for reporting the presence of SVE2 and its optional features to userspace. This will also enable visibility of SVE2 for guests, when KVM support for SVE-enabled guests is available. Signed-off-by: Dave Martin Signed-off-by: Will Deacon --- Documentation/arm64/cpu-feature-registers.txt | 16 ++++++++++++++++ Documentation/arm64/elf_hwcaps.txt | 24 ++++++++++++++++++++++++ Documentation/arm64/sve.txt | 17 +++++++++++++++++ arch/arm64/Kconfig | 3 +++ arch/arm64/include/asm/hwcap.h | 6 ++++++ arch/arm64/include/asm/sysreg.h | 14 ++++++++++++++ arch/arm64/include/uapi/asm/hwcap.h | 6 ++++++ arch/arm64/kernel/cpufeature.c | 17 ++++++++++++++++- arch/arm64/kernel/cpuinfo.c | 6 ++++++ 9 files changed, 108 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/arm64/cpu-feature-registers.txt b/Documentation/arm64/cpu-feature-registers.txt index d4b4dd1fe786..684a0da39378 100644 --- a/Documentation/arm64/cpu-feature-registers.txt +++ b/Documentation/arm64/cpu-feature-registers.txt @@ -209,6 +209,22 @@ infrastructure: | AT | [35-32] | y | x--------------------------------------------------x + 6) ID_AA64ZFR0_EL1 - SVE feature ID register 0 + + x--------------------------------------------------x + | Name | bits | visible | + |--------------------------------------------------| + | SM4 | [43-40] | y | + |--------------------------------------------------| + | SHA3 | [35-32] | y | + |--------------------------------------------------| + | BitPerm | [19-16] | y | + |--------------------------------------------------| + | AES | [7-4] | y | + |--------------------------------------------------| + | SVEVer | [3-0] | y | + x--------------------------------------------------x + Appendix I: Example --------------------------- diff --git a/Documentation/arm64/elf_hwcaps.txt b/Documentation/arm64/elf_hwcaps.txt index 55431fd2a67a..b73a2519ecf2 100644 --- a/Documentation/arm64/elf_hwcaps.txt +++ b/Documentation/arm64/elf_hwcaps.txt @@ -163,6 +163,30 @@ HWCAP_SVE Functionality implied by ID_AA64PFR0_EL1.SVE == 0b0001. +HWCAP2_SVE2 + + Functionality implied by ID_AA64ZFR0_EL1.SVEVer == 0b0001. + +HWCAP2_SVEAES + + Functionality implied by ID_AA64ZFR0_EL1.AES == 0b0001. + +HWCAP2_SVEPMULL + + Functionality implied by ID_AA64ZFR0_EL1.AES == 0b0010. + +HWCAP2_SVEBITPERM + + Functionality implied by ID_AA64ZFR0_EL1.BitPerm == 0b0001. + +HWCAP2_SVESHA3 + + Functionality implied by ID_AA64ZFR0_EL1.SHA3 == 0b0001. + +HWCAP2_SVESM4 + + Functionality implied by ID_AA64ZFR0_EL1.SM4 == 0b0001. + HWCAP_ASIMDFHM Functionality implied by ID_AA64ISAR0_EL1.FHM == 0b0001. diff --git a/Documentation/arm64/sve.txt b/Documentation/arm64/sve.txt index 7169a0ec41d8..9940e924a47e 100644 --- a/Documentation/arm64/sve.txt +++ b/Documentation/arm64/sve.txt @@ -34,6 +34,23 @@ model features for SVE is included in Appendix A. following sections: software that needs to verify that those interfaces are present must check for HWCAP_SVE instead. +* On hardware that supports the SVE2 extensions, HWCAP2_SVE2 will also + be reported in the AT_HWCAP2 aux vector entry. In addition to this, + optional extensions to SVE2 may be reported by the presence of: + + HWCAP2_SVE2 + HWCAP2_SVEAES + HWCAP2_SVEPMULL + HWCAP2_SVEBITPERM + HWCAP2_SVESHA3 + HWCAP2_SVESM4 + + This list may be extended over time as the SVE architecture evolves. + + These extensions are also reported via the CPU ID register ID_AA64ZFR0_EL1, + which userspace can read using an MRS instruction. See elf_hwcaps.txt and + cpu-feature-registers.txt for details. + * Debuggers should restrict themselves to interacting with the target via the NT_ARM_SVE regset. The recommended way of detecting support for this regset is to connect to a target process first and then attempt a diff --git a/arch/arm64/Kconfig b/arch/arm64/Kconfig index 75c1a07abc72..4791d4857124 100644 --- a/arch/arm64/Kconfig +++ b/arch/arm64/Kconfig @@ -1372,6 +1372,9 @@ config ARM64_SVE To enable use of this extension on CPUs that implement it, say Y. + On CPUs that support the SVE2 extensions, this option will enable + those too. + Note that for architectural reasons, firmware _must_ implement SVE support when running on SVE capable hardware. The required support is present in: diff --git a/arch/arm64/include/asm/hwcap.h b/arch/arm64/include/asm/hwcap.h index f78c86c64e68..b4bfb6672168 100644 --- a/arch/arm64/include/asm/hwcap.h +++ b/arch/arm64/include/asm/hwcap.h @@ -89,6 +89,12 @@ #define __khwcap2_feature(x) (const_ilog2(HWCAP2_ ## x) + 32) #define KERNEL_HWCAP_DCPODP __khwcap2_feature(DCPODP) +#define KERNEL_HWCAP_SVE2 __khwcap2_feature(SVE2) +#define KERNEL_HWCAP_SVEAES __khwcap2_feature(SVEAES) +#define KERNEL_HWCAP_SVEPMULL __khwcap2_feature(SVEPMULL) +#define KERNEL_HWCAP_SVEBITPERM __khwcap2_feature(SVEBITPERM) +#define KERNEL_HWCAP_SVESHA3 __khwcap2_feature(SVESHA3) +#define KERNEL_HWCAP_SVESM4 __khwcap2_feature(SVESM4) /* * This yields a mask that user programs can use to figure out what diff --git a/arch/arm64/include/asm/sysreg.h b/arch/arm64/include/asm/sysreg.h index 5b267dec6194..29c655969320 100644 --- a/arch/arm64/include/asm/sysreg.h +++ b/arch/arm64/include/asm/sysreg.h @@ -606,6 +606,20 @@ #define ID_AA64PFR1_SSBS_PSTATE_ONLY 1 #define ID_AA64PFR1_SSBS_PSTATE_INSNS 2 +/* id_aa64zfr0 */ +#define ID_AA64ZFR0_SM4_SHIFT 40 +#define ID_AA64ZFR0_SHA3_SHIFT 32 +#define ID_AA64ZFR0_BITPERM_SHIFT 16 +#define ID_AA64ZFR0_AES_SHIFT 4 +#define ID_AA64ZFR0_SVEVER_SHIFT 0 + +#define ID_AA64ZFR0_SM4 0x1 +#define ID_AA64ZFR0_SHA3 0x1 +#define ID_AA64ZFR0_BITPERM 0x1 +#define ID_AA64ZFR0_AES 0x1 +#define ID_AA64ZFR0_AES_PMULL 0x2 +#define ID_AA64ZFR0_SVEVER_SVE2 0x1 + /* id_aa64mmfr0 */ #define ID_AA64MMFR0_TGRAN4_SHIFT 28 #define ID_AA64MMFR0_TGRAN64_SHIFT 24 diff --git a/arch/arm64/include/uapi/asm/hwcap.h b/arch/arm64/include/uapi/asm/hwcap.h index d64af3913a9e..1a772b162191 100644 --- a/arch/arm64/include/uapi/asm/hwcap.h +++ b/arch/arm64/include/uapi/asm/hwcap.h @@ -57,5 +57,11 @@ * HWCAP2 flags - for AT_HWCAP2 */ #define HWCAP2_DCPODP (1 << 0) +#define HWCAP2_SVE2 (1 << 1) +#define HWCAP2_SVEAES (1 << 2) +#define HWCAP2_SVEPMULL (1 << 3) +#define HWCAP2_SVEBITPERM (1 << 4) +#define HWCAP2_SVESHA3 (1 << 5) +#define HWCAP2_SVESM4 (1 << 6) #endif /* _UAPI__ASM_HWCAP_H */ diff --git a/arch/arm64/kernel/cpufeature.c b/arch/arm64/kernel/cpufeature.c index 9d18e45311fd..d856c55445a2 100644 --- a/arch/arm64/kernel/cpufeature.c +++ b/arch/arm64/kernel/cpufeature.c @@ -184,6 +184,15 @@ static const struct arm64_ftr_bits ftr_id_aa64pfr1[] = { ARM64_FTR_END, }; +static const struct arm64_ftr_bits ftr_id_aa64zfr0[] = { + ARM64_FTR_BITS(FTR_VISIBLE, FTR_STRICT, FTR_LOWER_SAFE, ID_AA64ZFR0_SM4_SHIFT, 4, 0), + ARM64_FTR_BITS(FTR_VISIBLE, FTR_STRICT, FTR_LOWER_SAFE, ID_AA64ZFR0_SHA3_SHIFT, 4, 0), + ARM64_FTR_BITS(FTR_VISIBLE, FTR_STRICT, FTR_LOWER_SAFE, ID_AA64ZFR0_BITPERM_SHIFT, 4, 0), + ARM64_FTR_BITS(FTR_VISIBLE, FTR_STRICT, FTR_LOWER_SAFE, ID_AA64ZFR0_AES_SHIFT, 4, 0), + ARM64_FTR_BITS(FTR_VISIBLE, FTR_STRICT, FTR_LOWER_SAFE, ID_AA64ZFR0_SVEVER_SHIFT, 4, 0), + ARM64_FTR_END, +}; + static const struct arm64_ftr_bits ftr_id_aa64mmfr0[] = { S_ARM64_FTR_BITS(FTR_HIDDEN, FTR_STRICT, FTR_LOWER_SAFE, ID_AA64MMFR0_TGRAN4_SHIFT, 4, ID_AA64MMFR0_TGRAN4_NI), S_ARM64_FTR_BITS(FTR_HIDDEN, FTR_STRICT, FTR_LOWER_SAFE, ID_AA64MMFR0_TGRAN64_SHIFT, 4, ID_AA64MMFR0_TGRAN64_NI), @@ -392,7 +401,7 @@ static const struct __ftr_reg_entry { /* Op1 = 0, CRn = 0, CRm = 4 */ ARM64_FTR_REG(SYS_ID_AA64PFR0_EL1, ftr_id_aa64pfr0), ARM64_FTR_REG(SYS_ID_AA64PFR1_EL1, ftr_id_aa64pfr1), - ARM64_FTR_REG(SYS_ID_AA64ZFR0_EL1, ftr_raz), + ARM64_FTR_REG(SYS_ID_AA64ZFR0_EL1, ftr_id_aa64zfr0), /* Op1 = 0, CRn = 0, CRm = 5 */ ARM64_FTR_REG(SYS_ID_AA64DFR0_EL1, ftr_id_aa64dfr0), @@ -1610,6 +1619,12 @@ static const struct arm64_cpu_capabilities arm64_elf_hwcaps[] = { HWCAP_CAP(SYS_ID_AA64MMFR2_EL1, ID_AA64MMFR2_AT_SHIFT, FTR_UNSIGNED, 1, CAP_HWCAP, KERNEL_HWCAP_USCAT), #ifdef CONFIG_ARM64_SVE HWCAP_CAP(SYS_ID_AA64PFR0_EL1, ID_AA64PFR0_SVE_SHIFT, FTR_UNSIGNED, ID_AA64PFR0_SVE, CAP_HWCAP, KERNEL_HWCAP_SVE), + HWCAP_CAP(SYS_ID_AA64ZFR0_EL1, ID_AA64ZFR0_SVEVER_SHIFT, FTR_UNSIGNED, ID_AA64ZFR0_SVEVER_SVE2, CAP_HWCAP, KERNEL_HWCAP_SVE2), + HWCAP_CAP(SYS_ID_AA64ZFR0_EL1, ID_AA64ZFR0_AES_SHIFT, FTR_UNSIGNED, ID_AA64ZFR0_AES, CAP_HWCAP, KERNEL_HWCAP_SVEAES), + HWCAP_CAP(SYS_ID_AA64ZFR0_EL1, ID_AA64ZFR0_AES_SHIFT, FTR_UNSIGNED, ID_AA64ZFR0_AES_PMULL, CAP_HWCAP, KERNEL_HWCAP_SVEPMULL), + HWCAP_CAP(SYS_ID_AA64ZFR0_EL1, ID_AA64ZFR0_BITPERM_SHIFT, FTR_UNSIGNED, ID_AA64ZFR0_BITPERM, CAP_HWCAP, KERNEL_HWCAP_SVEBITPERM), + HWCAP_CAP(SYS_ID_AA64ZFR0_EL1, ID_AA64ZFR0_SHA3_SHIFT, FTR_UNSIGNED, ID_AA64ZFR0_SHA3, CAP_HWCAP, KERNEL_HWCAP_SVESHA3), + HWCAP_CAP(SYS_ID_AA64ZFR0_EL1, ID_AA64ZFR0_SM4_SHIFT, FTR_UNSIGNED, ID_AA64ZFR0_SM4, CAP_HWCAP, KERNEL_HWCAP_SVESM4), #endif HWCAP_CAP(SYS_ID_AA64PFR1_EL1, ID_AA64PFR1_SSBS_SHIFT, FTR_UNSIGNED, ID_AA64PFR1_SSBS_PSTATE_INSNS, CAP_HWCAP, KERNEL_HWCAP_SSBS), #ifdef CONFIG_ARM64_PTR_AUTH diff --git a/arch/arm64/kernel/cpuinfo.c b/arch/arm64/kernel/cpuinfo.c index 093ca53ce1d1..f6f7936be6e7 100644 --- a/arch/arm64/kernel/cpuinfo.c +++ b/arch/arm64/kernel/cpuinfo.c @@ -86,6 +86,12 @@ static const char *const hwcap_str[] = { "paca", "pacg", "dcpodp", + "sve2", + "sveaes", + "svepmull", + "svebitperm", + "svesha3", + "svesm4", NULL }; -- cgit v1.2.3 From 7358a821f0b571e824fa531c4f764000eeee320a Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Mon, 22 Apr 2019 10:27:04 -0300 Subject: docs: gpio: convert docs to ReST and rename to *.rst The API described at sysfs.txt is deprecated. Still, as it is still part of the Kernel (and will likely be there for some time, as we don't simply remove APIs). So, it makes sense to keep it there. The conversion of this file is trivial: - add blank lines and identation in order to identify paragraphs; - mark a literal block as such. At its new index.rst, let's add a :orphan: while this is not linked to the main index.rst file, in order to avoid build warnings. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Linus Walleij --- Documentation/gpio/index.rst | 17 +++++ Documentation/gpio/sysfs.rst | 167 +++++++++++++++++++++++++++++++++++++++++++ Documentation/gpio/sysfs.txt | 156 ---------------------------------------- 3 files changed, 184 insertions(+), 156 deletions(-) create mode 100644 Documentation/gpio/index.rst create mode 100644 Documentation/gpio/sysfs.rst delete mode 100644 Documentation/gpio/sysfs.txt (limited to 'Documentation') diff --git a/Documentation/gpio/index.rst b/Documentation/gpio/index.rst new file mode 100644 index 000000000000..09a4a553f434 --- /dev/null +++ b/Documentation/gpio/index.rst @@ -0,0 +1,17 @@ +:orphan: + +==== +gpio +==== + +.. toctree:: + :maxdepth: 1 + + sysfs + +.. only:: subproject and html + + Indices + ======= + + * :ref:`genindex` diff --git a/Documentation/gpio/sysfs.rst b/Documentation/gpio/sysfs.rst new file mode 100644 index 000000000000..ec09ffd983e7 --- /dev/null +++ b/Documentation/gpio/sysfs.rst @@ -0,0 +1,167 @@ +GPIO Sysfs Interface for Userspace +================================== + +.. warning:: + + THIS ABI IS DEPRECATED, THE ABI DOCUMENTATION HAS BEEN MOVED TO + Documentation/ABI/obsolete/sysfs-gpio AND NEW USERSPACE CONSUMERS + ARE SUPPOSED TO USE THE CHARACTER DEVICE ABI. THIS OLD SYSFS ABI WILL + NOT BE DEVELOPED (NO NEW FEATURES), IT WILL JUST BE MAINTAINED. + +Refer to the examples in tools/gpio/* for an introduction to the new +character device ABI. Also see the userspace header in +include/uapi/linux/gpio.h + +The deprecated sysfs ABI +------------------------ +Platforms which use the "gpiolib" implementors framework may choose to +configure a sysfs user interface to GPIOs. This is different from the +debugfs interface, since it provides control over GPIO direction and +value instead of just showing a gpio state summary. Plus, it could be +present on production systems without debugging support. + +Given appropriate hardware documentation for the system, userspace could +know for example that GPIO #23 controls the write protect line used to +protect boot loader segments in flash memory. System upgrade procedures +may need to temporarily remove that protection, first importing a GPIO, +then changing its output state, then updating the code before re-enabling +the write protection. In normal use, GPIO #23 would never be touched, +and the kernel would have no need to know about it. + +Again depending on appropriate hardware documentation, on some systems +userspace GPIO can be used to determine system configuration data that +standard kernels won't know about. And for some tasks, simple userspace +GPIO drivers could be all that the system really needs. + +DO NOT ABUSE SYSFS TO CONTROL HARDWARE THAT HAS PROPER KERNEL DRIVERS. +PLEASE READ THE DOCUMENT AT Documentation/driver-api/gpio/drivers-on-gpio.rst +TO AVOID REINVENTING KERNEL WHEELS IN USERSPACE. I MEAN IT. REALLY. + +Paths in Sysfs +-------------- +There are three kinds of entries in /sys/class/gpio: + + - Control interfaces used to get userspace control over GPIOs; + + - GPIOs themselves; and + + - GPIO controllers ("gpio_chip" instances). + +That's in addition to standard files including the "device" symlink. + +The control interfaces are write-only: + + /sys/class/gpio/ + + "export" ... + Userspace may ask the kernel to export control of + a GPIO to userspace by writing its number to this file. + + Example: "echo 19 > export" will create a "gpio19" node + for GPIO #19, if that's not requested by kernel code. + + "unexport" ... + Reverses the effect of exporting to userspace. + + Example: "echo 19 > unexport" will remove a "gpio19" + node exported using the "export" file. + +GPIO signals have paths like /sys/class/gpio/gpio42/ (for GPIO #42) +and have the following read/write attributes: + + /sys/class/gpio/gpioN/ + + "direction" ... + reads as either "in" or "out". This value may + normally be written. Writing as "out" defaults to + initializing the value as low. To ensure glitch free + operation, values "low" and "high" may be written to + configure the GPIO as an output with that initial value. + + Note that this attribute *will not exist* if the kernel + doesn't support changing the direction of a GPIO, or + it was exported by kernel code that didn't explicitly + allow userspace to reconfigure this GPIO's direction. + + "value" ... + reads as either 0 (low) or 1 (high). If the GPIO + is configured as an output, this value may be written; + any nonzero value is treated as high. + + If the pin can be configured as interrupt-generating interrupt + and if it has been configured to generate interrupts (see the + description of "edge"), you can poll(2) on that file and + poll(2) will return whenever the interrupt was triggered. If + you use poll(2), set the events POLLPRI and POLLERR. If you + use select(2), set the file descriptor in exceptfds. After + poll(2) returns, either lseek(2) to the beginning of the sysfs + file and read the new value or close the file and re-open it + to read the value. + + "edge" ... + reads as either "none", "rising", "falling", or + "both". Write these strings to select the signal edge(s) + that will make poll(2) on the "value" file return. + + This file exists only if the pin can be configured as an + interrupt generating input pin. + + "active_low" ... + reads as either 0 (false) or 1 (true). Write + any nonzero value to invert the value attribute both + for reading and writing. Existing and subsequent + poll(2) support configuration via the edge attribute + for "rising" and "falling" edges will follow this + setting. + +GPIO controllers have paths like /sys/class/gpio/gpiochip42/ (for the +controller implementing GPIOs starting at #42) and have the following +read-only attributes: + + /sys/class/gpio/gpiochipN/ + + "base" ... + same as N, the first GPIO managed by this chip + + "label" ... + provided for diagnostics (not always unique) + + "ngpio" ... + how many GPIOs this manages (N to N + ngpio - 1) + +Board documentation should in most cases cover what GPIOs are used for +what purposes. However, those numbers are not always stable; GPIOs on +a daughtercard might be different depending on the base board being used, +or other cards in the stack. In such cases, you may need to use the +gpiochip nodes (possibly in conjunction with schematics) to determine +the correct GPIO number to use for a given signal. + + +Exporting from Kernel code +-------------------------- +Kernel code can explicitly manage exports of GPIOs which have already been +requested using gpio_request():: + + /* export the GPIO to userspace */ + int gpiod_export(struct gpio_desc *desc, bool direction_may_change); + + /* reverse gpio_export() */ + void gpiod_unexport(struct gpio_desc *desc); + + /* create a sysfs link to an exported GPIO node */ + int gpiod_export_link(struct device *dev, const char *name, + struct gpio_desc *desc); + +After a kernel driver requests a GPIO, it may only be made available in +the sysfs interface by gpiod_export(). The driver can control whether the +signal direction may change. This helps drivers prevent userspace code +from accidentally clobbering important system state. + +This explicit exporting can help with debugging (by making some kinds +of experiments easier), or can provide an always-there interface that's +suitable for documenting as part of a board support package. + +After the GPIO has been exported, gpiod_export_link() allows creating +symlinks from elsewhere in sysfs to the GPIO sysfs node. Drivers can +use this to provide the interface under their own device in sysfs with +a descriptive name. diff --git a/Documentation/gpio/sysfs.txt b/Documentation/gpio/sysfs.txt deleted file mode 100644 index 58eeab81f349..000000000000 --- a/Documentation/gpio/sysfs.txt +++ /dev/null @@ -1,156 +0,0 @@ -GPIO Sysfs Interface for Userspace -================================== - -THIS ABI IS DEPRECATED, THE ABI DOCUMENTATION HAS BEEN MOVED TO -Documentation/ABI/obsolete/sysfs-gpio AND NEW USERSPACE CONSUMERS -ARE SUPPOSED TO USE THE CHARACTER DEVICE ABI. THIS OLD SYSFS ABI WILL -NOT BE DEVELOPED (NO NEW FEATURES), IT WILL JUST BE MAINTAINED. - -Refer to the examples in tools/gpio/* for an introduction to the new -character device ABI. Also see the userspace header in -include/uapi/linux/gpio.h - -The deprecated sysfs ABI ------------------------- -Platforms which use the "gpiolib" implementors framework may choose to -configure a sysfs user interface to GPIOs. This is different from the -debugfs interface, since it provides control over GPIO direction and -value instead of just showing a gpio state summary. Plus, it could be -present on production systems without debugging support. - -Given appropriate hardware documentation for the system, userspace could -know for example that GPIO #23 controls the write protect line used to -protect boot loader segments in flash memory. System upgrade procedures -may need to temporarily remove that protection, first importing a GPIO, -then changing its output state, then updating the code before re-enabling -the write protection. In normal use, GPIO #23 would never be touched, -and the kernel would have no need to know about it. - -Again depending on appropriate hardware documentation, on some systems -userspace GPIO can be used to determine system configuration data that -standard kernels won't know about. And for some tasks, simple userspace -GPIO drivers could be all that the system really needs. - -DO NOT ABUSE SYSFS TO CONTROL HARDWARE THAT HAS PROPER KERNEL DRIVERS. -PLEASE READ THE DOCUMENT AT Documentation/driver-api/gpio/drivers-on-gpio.rst -TO AVOID REINVENTING KERNEL WHEELS IN USERSPACE. I MEAN IT. REALLY. - -Paths in Sysfs --------------- -There are three kinds of entries in /sys/class/gpio: - - - Control interfaces used to get userspace control over GPIOs; - - - GPIOs themselves; and - - - GPIO controllers ("gpio_chip" instances). - -That's in addition to standard files including the "device" symlink. - -The control interfaces are write-only: - - /sys/class/gpio/ - - "export" ... Userspace may ask the kernel to export control of - a GPIO to userspace by writing its number to this file. - - Example: "echo 19 > export" will create a "gpio19" node - for GPIO #19, if that's not requested by kernel code. - - "unexport" ... Reverses the effect of exporting to userspace. - - Example: "echo 19 > unexport" will remove a "gpio19" - node exported using the "export" file. - -GPIO signals have paths like /sys/class/gpio/gpio42/ (for GPIO #42) -and have the following read/write attributes: - - /sys/class/gpio/gpioN/ - - "direction" ... reads as either "in" or "out". This value may - normally be written. Writing as "out" defaults to - initializing the value as low. To ensure glitch free - operation, values "low" and "high" may be written to - configure the GPIO as an output with that initial value. - - Note that this attribute *will not exist* if the kernel - doesn't support changing the direction of a GPIO, or - it was exported by kernel code that didn't explicitly - allow userspace to reconfigure this GPIO's direction. - - "value" ... reads as either 0 (low) or 1 (high). If the GPIO - is configured as an output, this value may be written; - any nonzero value is treated as high. - - If the pin can be configured as interrupt-generating interrupt - and if it has been configured to generate interrupts (see the - description of "edge"), you can poll(2) on that file and - poll(2) will return whenever the interrupt was triggered. If - you use poll(2), set the events POLLPRI and POLLERR. If you - use select(2), set the file descriptor in exceptfds. After - poll(2) returns, either lseek(2) to the beginning of the sysfs - file and read the new value or close the file and re-open it - to read the value. - - "edge" ... reads as either "none", "rising", "falling", or - "both". Write these strings to select the signal edge(s) - that will make poll(2) on the "value" file return. - - This file exists only if the pin can be configured as an - interrupt generating input pin. - - "active_low" ... reads as either 0 (false) or 1 (true). Write - any nonzero value to invert the value attribute both - for reading and writing. Existing and subsequent - poll(2) support configuration via the edge attribute - for "rising" and "falling" edges will follow this - setting. - -GPIO controllers have paths like /sys/class/gpio/gpiochip42/ (for the -controller implementing GPIOs starting at #42) and have the following -read-only attributes: - - /sys/class/gpio/gpiochipN/ - - "base" ... same as N, the first GPIO managed by this chip - - "label" ... provided for diagnostics (not always unique) - - "ngpio" ... how many GPIOs this manages (N to N + ngpio - 1) - -Board documentation should in most cases cover what GPIOs are used for -what purposes. However, those numbers are not always stable; GPIOs on -a daughtercard might be different depending on the base board being used, -or other cards in the stack. In such cases, you may need to use the -gpiochip nodes (possibly in conjunction with schematics) to determine -the correct GPIO number to use for a given signal. - - -Exporting from Kernel code --------------------------- -Kernel code can explicitly manage exports of GPIOs which have already been -requested using gpio_request(): - - /* export the GPIO to userspace */ - int gpiod_export(struct gpio_desc *desc, bool direction_may_change); - - /* reverse gpio_export() */ - void gpiod_unexport(struct gpio_desc *desc); - - /* create a sysfs link to an exported GPIO node */ - int gpiod_export_link(struct device *dev, const char *name, - struct gpio_desc *desc); - -After a kernel driver requests a GPIO, it may only be made available in -the sysfs interface by gpiod_export(). The driver can control whether the -signal direction may change. This helps drivers prevent userspace code -from accidentally clobbering important system state. - -This explicit exporting can help with debugging (by making some kinds -of experiments easier), or can provide an always-there interface that's -suitable for documenting as part of a board support package. - -After the GPIO has been exported, gpiod_export_link() allows creating -symlinks from elsewhere in sysfs to the GPIO sysfs node. Drivers can -use this to provide the interface under their own device in sysfs with -a descriptive name. -- cgit v1.2.3 From 3a02cd6854432e0141bcbc80265587b30278fbdd Mon Sep 17 00:00:00 2001 From: Charles Keepax Date: Tue, 19 Mar 2019 13:36:59 +0000 Subject: clk: lochnagar: Add initial binding documentation Lochnagar is an evaluation and development board for Cirrus Logic Smart CODEC and Amp devices. It allows the connection of most Cirrus Logic devices on mini-cards, as well as allowing connection of various application processor systems to provide a full evaluation platform. This driver supports the board controller chip on the Lochnagar board. Signed-off-by: Charles Keepax Reviewed-by: Rob Herring Signed-off-by: Stephen Boyd --- .../devicetree/bindings/clock/cirrus,lochnagar.txt | 93 ++++++++++++++++++++++ 1 file changed, 93 insertions(+) create mode 100644 Documentation/devicetree/bindings/clock/cirrus,lochnagar.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/clock/cirrus,lochnagar.txt b/Documentation/devicetree/bindings/clock/cirrus,lochnagar.txt new file mode 100644 index 000000000000..b8d8ef3bdc5f --- /dev/null +++ b/Documentation/devicetree/bindings/clock/cirrus,lochnagar.txt @@ -0,0 +1,93 @@ +Cirrus Logic Lochnagar Audio Development Board + +Lochnagar is an evaluation and development board for Cirrus Logic +Smart CODEC and Amp devices. It allows the connection of most Cirrus +Logic devices on mini-cards, as well as allowing connection of +various application processor systems to provide a full evaluation +platform. Audio system topology, clocking and power can all be +controlled through the Lochnagar, allowing the device under test +to be used in a variety of possible use cases. + +This binding document describes the binding for the clock portion of +the driver. + +Also see these documents for generic binding information: + [1] Clock : ../clock/clock-bindings.txt + +And these for relevant defines: + [2] include/dt-bindings/clock/lochnagar.h + +This binding must be part of the Lochnagar MFD binding: + [3] ../mfd/cirrus,lochnagar.txt + +Required properties: + + - compatible : One of the following strings: + "cirrus,lochnagar1-clk" + "cirrus,lochnagar2-clk" + + - #clock-cells : Must be 1. The first cell indicates the clock + number, see [2] for available clocks and [1]. + +Optional properties: + + - clocks : Must contain an entry for each clock in clock-names. + - clock-names : May contain entries for each of the following + clocks: + - ln-cdc-clkout : Output clock from CODEC card. + - ln-dsp-clkout : Output clock from DSP card. + - ln-gf-mclk1,ln-gf-mclk2,ln-gf-mclk3,ln-gf-mclk4 : Optional + input audio clocks from host system. + - ln-psia1-mclk, ln-psia2-mclk : Optional input audio clocks from + external connector. + - ln-spdif-clkout : Optional input audio clock from SPDIF. + - ln-adat-mclk : Optional input audio clock from ADAT. + - ln-pmic-32k : On board fixed clock. + - ln-clk-12m : On board fixed clock. + - ln-clk-11m : On board fixed clock. + - ln-clk-24m : On board fixed clock. + - ln-clk-22m : On board fixed clock. + - ln-clk-8m : On board fixed clock. + - ln-usb-clk-24m : On board fixed clock. + - ln-usb-clk-12m : On board fixed clock. + + - assigned-clocks : A list of Lochnagar clocks to be reparented, see + [2] for available clocks. + - assigned-clock-parents : Parents to be assigned to the clocks + listed in "assigned-clocks". + +Optional nodes: + + - fixed-clock nodes may be registered for the following on board clocks: + - ln-pmic-32k : 32768 Hz + - ln-clk-12m : 12288000 Hz + - ln-clk-11m : 11298600 Hz + - ln-clk-24m : 24576000 Hz + - ln-clk-22m : 22579200 Hz + - ln-clk-8m : 8192000 Hz + - ln-usb-clk-24m : 24576000 Hz + - ln-usb-clk-12m : 12288000 Hz + +Example: + +lochnagar { + lochnagar-clk { + compatible = "cirrus,lochnagar2-clk"; + + #clock-cells = <1>; + + clocks = <&clk-audio>, <&clk_pmic>; + clock-names = "ln-gf-mclk2", "ln-pmic-32k"; + + assigned-clocks = <&lochnagar-clk LOCHNAGAR_CDC_MCLK1>, + <&lochnagar-clk LOCHNAGAR_CDC_MCLK2>; + assigned-clock-parents = <&clk-audio>, + <&clk-pmic>; + }; + + clk-pmic: clk-pmic { + compatible = "fixed-clock"; + clock-cells = <0>; + clock-frequency = <32768>; + }; +}; -- cgit v1.2.3 From 56009f0d2f54e4ce4305d65ce589eee6c22ac25f Mon Sep 17 00:00:00 2001 From: Lars-Peter Clausen Date: Tue, 26 Mar 2019 15:06:28 +0200 Subject: dmaengine: axi-dmac: Infer synthesis configuration parameters hardware Some synthesis time configuration parameters of the DMA controller can be inferred from the hardware itself. Use this information as it is more reliably than the information specified in the devicetree which might be outdated if the HDL project got changed. Deprecate the devicetree properties that can be inferred from the hardware itself. Signed-off-by: Lars-Peter Clausen Signed-off-by: Alexandru Ardelean Signed-off-by: Vinod Koul --- .../devicetree/bindings/dma/adi,axi-dmac.txt | 4 +-- drivers/dma/dma-axi-dmac.c | 32 ++++++++++++++-------- 2 files changed, 22 insertions(+), 14 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/dma/adi,axi-dmac.txt b/Documentation/devicetree/bindings/dma/adi,axi-dmac.txt index 47cb1d14b690..b38ee732efa9 100644 --- a/Documentation/devicetree/bindings/dma/adi,axi-dmac.txt +++ b/Documentation/devicetree/bindings/dma/adi,axi-dmac.txt @@ -18,7 +18,6 @@ Required properties for adi,channels sub-node: Required channel sub-node properties: - reg: Which channel this node refers to. - - adi,length-width: Width of the DMA transfer length register. - adi,source-bus-width, adi,destination-bus-width: Width of the source or destination bus in bits. - adi,source-bus-type, @@ -28,7 +27,8 @@ Required channel sub-node properties: 1 (AXI_DMAC_TYPE_AXI_STREAM): Streaming AXI interface 2 (AXI_DMAC_TYPE_AXI_FIFO): FIFO interface -Optional channel properties: +Deprecated optional channel properties: + - adi,length-width: Width of the DMA transfer length register. - adi,cyclic: Must be set if the channel supports hardware cyclic DMA transfers. - adi,2d: Must be set if the channel supports hardware 2D DMA transfers. diff --git a/drivers/dma/dma-axi-dmac.c b/drivers/dma/dma-axi-dmac.c index 0fe3a931d8d5..eecb367b4f3e 100644 --- a/drivers/dma/dma-axi-dmac.c +++ b/drivers/dma/dma-axi-dmac.c @@ -618,15 +618,6 @@ static int axi_dmac_parse_chan_dt(struct device_node *of_chan, return ret; chan->dest_width = val / 8; - ret = of_property_read_u32(of_chan, "adi,length-width", &val); - if (ret) - return ret; - - if (val >= 32) - chan->max_length = UINT_MAX; - else - chan->max_length = (1ULL << val) - 1; - chan->align_mask = max(chan->dest_width, chan->src_width) - 1; if (axi_dmac_dest_is_mem(chan) && axi_dmac_src_is_mem(chan)) @@ -638,12 +629,27 @@ static int axi_dmac_parse_chan_dt(struct device_node *of_chan, else chan->direction = DMA_DEV_TO_DEV; - chan->hw_cyclic = of_property_read_bool(of_chan, "adi,cyclic"); - chan->hw_2d = of_property_read_bool(of_chan, "adi,2d"); - return 0; } +static void axi_dmac_detect_caps(struct axi_dmac *dmac) +{ + struct axi_dmac_chan *chan = &dmac->chan; + + axi_dmac_write(dmac, AXI_DMAC_REG_FLAGS, AXI_DMAC_FLAG_CYCLIC); + if (axi_dmac_read(dmac, AXI_DMAC_REG_FLAGS) == AXI_DMAC_FLAG_CYCLIC) + chan->hw_cyclic = true; + + axi_dmac_write(dmac, AXI_DMAC_REG_Y_LENGTH, 1); + if (axi_dmac_read(dmac, AXI_DMAC_REG_Y_LENGTH) == 1) + chan->hw_2d = true; + + axi_dmac_write(dmac, AXI_DMAC_REG_X_LENGTH, 0xffffffff); + chan->max_length = axi_dmac_read(dmac, AXI_DMAC_REG_X_LENGTH); + if (chan->max_length != UINT_MAX) + chan->max_length++; +} + static int axi_dmac_probe(struct platform_device *pdev) { struct device_node *of_channels, *of_chan; @@ -716,6 +722,8 @@ static int axi_dmac_probe(struct platform_device *pdev) if (ret < 0) return ret; + axi_dmac_detect_caps(dmac); + axi_dmac_write(dmac, AXI_DMAC_REG_IRQ_MASK, 0x00); ret = dma_async_device_register(dma_dev); -- cgit v1.2.3 From a22fa321d13b0264976cbbc1d22f4c27c41d3642 Mon Sep 17 00:00:00 2001 From: Amit Daniel Kachhap Date: Tue, 23 Apr 2019 10:12:36 +0530 Subject: KVM: arm64: Add userspace flag to enable pointer authentication Now that the building blocks of pointer authentication are present, lets add userspace flags KVM_ARM_VCPU_PTRAUTH_ADDRESS and KVM_ARM_VCPU_PTRAUTH_GENERIC. These flags will enable pointer authentication for the KVM guest on a per-vcpu basis through the ioctl KVM_ARM_VCPU_INIT. This features will allow the KVM guest to allow the handling of pointer authentication instructions or to treat them as undefined if not set. Necessary documentations are added to reflect the changes done. Reviewed-by: Dave Martin Signed-off-by: Amit Daniel Kachhap Cc: Mark Rutland Cc: Marc Zyngier Cc: Christoffer Dall Cc: kvmarm@lists.cs.columbia.edu Signed-off-by: Marc Zyngier --- Documentation/arm64/pointer-authentication.txt | 22 +++++++++++++++++---- Documentation/virtual/kvm/api.txt | 10 ++++++++++ arch/arm64/include/asm/kvm_host.h | 2 +- arch/arm64/include/uapi/asm/kvm.h | 2 ++ arch/arm64/kvm/reset.c | 27 ++++++++++++++++++++++++++ 5 files changed, 58 insertions(+), 5 deletions(-) (limited to 'Documentation') diff --git a/Documentation/arm64/pointer-authentication.txt b/Documentation/arm64/pointer-authentication.txt index 5baca42ba146..fc71b33de87e 100644 --- a/Documentation/arm64/pointer-authentication.txt +++ b/Documentation/arm64/pointer-authentication.txt @@ -87,7 +87,21 @@ used to get and set the keys for a thread. Virtualization -------------- -Pointer authentication is not currently supported in KVM guests. KVM -will mask the feature bits from ID_AA64ISAR1_EL1, and attempted use of -the feature will result in an UNDEFINED exception being injected into -the guest. +Pointer authentication is enabled in KVM guest when each virtual cpu is +initialised by passing flags KVM_ARM_VCPU_PTRAUTH_[ADDRESS/GENERIC] and +requesting these two separate cpu features to be enabled. The current KVM +guest implementation works by enabling both features together, so both +these userspace flags are checked before enabling pointer authentication. +The separate userspace flag will allow to have no userspace ABI changes +if support is added in the future to allow these two features to be +enabled independently of one another. + +As Arm Architecture specifies that Pointer Authentication feature is +implemented along with the VHE feature so KVM arm64 ptrauth code relies +on VHE mode to be present. + +Additionally, when these vcpu feature flags are not set then KVM will +filter out the Pointer Authentication system key registers from +KVM_GET/SET_REG_* ioctls and mask those features from cpufeature ID +register. Any attempt to use the Pointer Authentication instructions will +result in an UNDEFINED exception being injected into the guest. diff --git a/Documentation/virtual/kvm/api.txt b/Documentation/virtual/kvm/api.txt index e410a9f0f0d4..32afe7f5c35a 100644 --- a/Documentation/virtual/kvm/api.txt +++ b/Documentation/virtual/kvm/api.txt @@ -2761,6 +2761,16 @@ Possible features: - KVM_ARM_VCPU_PMU_V3: Emulate PMUv3 for the CPU. Depends on KVM_CAP_ARM_PMU_V3. + - KVM_ARM_VCPU_PTRAUTH_ADDRESS: Enables Address Pointer authentication + for arm64 only. + Both KVM_ARM_VCPU_PTRAUTH_ADDRESS and KVM_ARM_VCPU_PTRAUTH_GENERIC + must be requested or neither must be requested. + + - KVM_ARM_VCPU_PTRAUTH_GENERIC: Enables Generic Pointer authentication + for arm64 only. + Both KVM_ARM_VCPU_PTRAUTH_ADDRESS and KVM_ARM_VCPU_PTRAUTH_GENERIC + must be requested or neither must be requested. + - KVM_ARM_VCPU_SVE: Enables SVE for the CPU (arm64 only). Depends on KVM_CAP_ARM_SVE. Requires KVM_ARM_VCPU_FINALIZE(KVM_ARM_VCPU_SVE): diff --git a/arch/arm64/include/asm/kvm_host.h b/arch/arm64/include/asm/kvm_host.h index 7eebea7059c6..f772ac2fb3e9 100644 --- a/arch/arm64/include/asm/kvm_host.h +++ b/arch/arm64/include/asm/kvm_host.h @@ -49,7 +49,7 @@ #define KVM_MAX_VCPUS VGIC_V3_MAX_CPUS -#define KVM_VCPU_MAX_FEATURES 5 +#define KVM_VCPU_MAX_FEATURES 7 #define KVM_REQ_SLEEP \ KVM_ARCH_REQ_FLAGS(0, KVM_REQUEST_WAIT | KVM_REQUEST_NO_WAKEUP) diff --git a/arch/arm64/include/uapi/asm/kvm.h b/arch/arm64/include/uapi/asm/kvm.h index edd2db8e5160..7b7ac0f6cec9 100644 --- a/arch/arm64/include/uapi/asm/kvm.h +++ b/arch/arm64/include/uapi/asm/kvm.h @@ -104,6 +104,8 @@ struct kvm_regs { #define KVM_ARM_VCPU_PSCI_0_2 2 /* CPU uses PSCI v0.2 */ #define KVM_ARM_VCPU_PMU_V3 3 /* Support guest PMUv3 */ #define KVM_ARM_VCPU_SVE 4 /* enable SVE for this CPU */ +#define KVM_ARM_VCPU_PTRAUTH_ADDRESS 5 /* VCPU uses address authentication */ +#define KVM_ARM_VCPU_PTRAUTH_GENERIC 6 /* VCPU uses generic authentication */ struct kvm_vcpu_init { __u32 target; diff --git a/arch/arm64/kvm/reset.c b/arch/arm64/kvm/reset.c index 3402543fdcd3..028d0c604652 100644 --- a/arch/arm64/kvm/reset.c +++ b/arch/arm64/kvm/reset.c @@ -221,6 +221,27 @@ static void kvm_vcpu_reset_sve(struct kvm_vcpu *vcpu) memset(vcpu->arch.sve_state, 0, vcpu_sve_state_size(vcpu)); } +static int kvm_vcpu_enable_ptrauth(struct kvm_vcpu *vcpu) +{ + /* Support ptrauth only if the system supports these capabilities. */ + if (!has_vhe()) + return -EINVAL; + + if (!system_supports_address_auth() || + !system_supports_generic_auth()) + return -EINVAL; + /* + * For now make sure that both address/generic pointer authentication + * features are requested by the userspace together. + */ + if (!test_bit(KVM_ARM_VCPU_PTRAUTH_ADDRESS, vcpu->arch.features) || + !test_bit(KVM_ARM_VCPU_PTRAUTH_GENERIC, vcpu->arch.features)) + return -EINVAL; + + vcpu->arch.flags |= KVM_ARM64_GUEST_HAS_PTRAUTH; + return 0; +} + /** * kvm_reset_vcpu - sets core registers and sys_regs to reset value * @vcpu: The VCPU pointer @@ -261,6 +282,12 @@ int kvm_reset_vcpu(struct kvm_vcpu *vcpu) kvm_vcpu_reset_sve(vcpu); } + if (test_bit(KVM_ARM_VCPU_PTRAUTH_ADDRESS, vcpu->arch.features) || + test_bit(KVM_ARM_VCPU_PTRAUTH_GENERIC, vcpu->arch.features)) { + if (kvm_vcpu_enable_ptrauth(vcpu)) + goto out; + } + switch (vcpu->arch.target) { default: if (test_bit(KVM_ARM_VCPU_EL1_32BIT, vcpu->arch.features)) { -- cgit v1.2.3 From a243c16d18be130b17cf1064e9115de73bfdff5a Mon Sep 17 00:00:00 2001 From: Amit Daniel Kachhap Date: Tue, 23 Apr 2019 10:12:37 +0530 Subject: KVM: arm64: Add capability to advertise ptrauth for guest This patch advertises the capability of two cpu feature called address pointer authentication and generic pointer authentication. These capabilities depend upon system support for pointer authentication and VHE mode. The current arm64 KVM partially implements pointer authentication and support of address/generic authentication are tied together. However, separate ABI requirements for both of them is added so that any future isolated implementation will not require any ABI changes. Signed-off-by: Amit Daniel Kachhap Cc: Mark Rutland Cc: Marc Zyngier Cc: Christoffer Dall Cc: kvmarm@lists.cs.columbia.edu Signed-off-by: Marc Zyngier --- Documentation/virtual/kvm/api.txt | 14 ++++++++++---- arch/arm64/kvm/reset.c | 5 +++++ include/uapi/linux/kvm.h | 2 ++ 3 files changed, 17 insertions(+), 4 deletions(-) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/api.txt b/Documentation/virtual/kvm/api.txt index 32afe7f5c35a..fac1887f25b5 100644 --- a/Documentation/virtual/kvm/api.txt +++ b/Documentation/virtual/kvm/api.txt @@ -2763,13 +2763,19 @@ Possible features: - KVM_ARM_VCPU_PTRAUTH_ADDRESS: Enables Address Pointer authentication for arm64 only. - Both KVM_ARM_VCPU_PTRAUTH_ADDRESS and KVM_ARM_VCPU_PTRAUTH_GENERIC - must be requested or neither must be requested. + Depends on KVM_CAP_ARM_PTRAUTH_ADDRESS. + If KVM_CAP_ARM_PTRAUTH_ADDRESS and KVM_CAP_ARM_PTRAUTH_GENERIC are + both present, then both KVM_ARM_VCPU_PTRAUTH_ADDRESS and + KVM_ARM_VCPU_PTRAUTH_GENERIC must be requested or neither must be + requested. - KVM_ARM_VCPU_PTRAUTH_GENERIC: Enables Generic Pointer authentication for arm64 only. - Both KVM_ARM_VCPU_PTRAUTH_ADDRESS and KVM_ARM_VCPU_PTRAUTH_GENERIC - must be requested or neither must be requested. + Depends on KVM_CAP_ARM_PTRAUTH_GENERIC. + If KVM_CAP_ARM_PTRAUTH_ADDRESS and KVM_CAP_ARM_PTRAUTH_GENERIC are + both present, then both KVM_ARM_VCPU_PTRAUTH_ADDRESS and + KVM_ARM_VCPU_PTRAUTH_GENERIC must be requested or neither must be + requested. - KVM_ARM_VCPU_SVE: Enables SVE for the CPU (arm64 only). Depends on KVM_CAP_ARM_SVE. diff --git a/arch/arm64/kvm/reset.c b/arch/arm64/kvm/reset.c index 028d0c604652..f0faf54f5857 100644 --- a/arch/arm64/kvm/reset.c +++ b/arch/arm64/kvm/reset.c @@ -101,6 +101,11 @@ int kvm_arch_vm_ioctl_check_extension(struct kvm *kvm, long ext) case KVM_CAP_ARM_SVE: r = system_supports_sve(); break; + case KVM_CAP_ARM_PTRAUTH_ADDRESS: + case KVM_CAP_ARM_PTRAUTH_GENERIC: + r = has_vhe() && system_supports_address_auth() && + system_supports_generic_auth(); + break; default: r = 0; } diff --git a/include/uapi/linux/kvm.h b/include/uapi/linux/kvm.h index 1d564445b515..4dc34f8e29f6 100644 --- a/include/uapi/linux/kvm.h +++ b/include/uapi/linux/kvm.h @@ -989,6 +989,8 @@ struct kvm_ppc_resize_hpt { #define KVM_CAP_MANUAL_DIRTY_LOG_PROTECT 166 #define KVM_CAP_HYPERV_CPUID 167 #define KVM_CAP_ARM_SVE 168 +#define KVM_CAP_ARM_PTRAUTH_ADDRESS 169 +#define KVM_CAP_ARM_PTRAUTH_GENERIC 170 #ifdef KVM_CAP_IRQ_ROUTING -- cgit v1.2.3 From a9bf3130ebfe0378df449a1b13997c47a58e661a Mon Sep 17 00:00:00 2001 From: Andrew Murray Date: Tue, 9 Apr 2019 20:22:17 +0100 Subject: arm64: docs: Document perf event attributes The interaction between the exclude_{host,guest} flags, exclude_{user,kernel,hv} flags and presence of VHE can result in different exception levels being filtered by the ARMv8 PMU. As this can be confusing let's document how they work on arm64. Signed-off-by: Andrew Murray Reviewed-by: Suzuki K Poulose Acked-by: Will Deacon Signed-off-by: Marc Zyngier --- Documentation/arm64/perf.txt | 85 ++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 85 insertions(+) create mode 100644 Documentation/arm64/perf.txt (limited to 'Documentation') diff --git a/Documentation/arm64/perf.txt b/Documentation/arm64/perf.txt new file mode 100644 index 000000000000..0d6a7d87d49e --- /dev/null +++ b/Documentation/arm64/perf.txt @@ -0,0 +1,85 @@ +Perf Event Attributes +===================== + +Author: Andrew Murray +Date: 2019-03-06 + +exclude_user +------------ + +This attribute excludes userspace. + +Userspace always runs at EL0 and thus this attribute will exclude EL0. + + +exclude_kernel +-------------- + +This attribute excludes the kernel. + +The kernel runs at EL2 with VHE and EL1 without. Guest kernels always run +at EL1. + +For the host this attribute will exclude EL1 and additionally EL2 on a VHE +system. + +For the guest this attribute will exclude EL1. Please note that EL2 is +never counted within a guest. + + +exclude_hv +---------- + +This attribute excludes the hypervisor. + +For a VHE host this attribute is ignored as we consider the host kernel to +be the hypervisor. + +For a non-VHE host this attribute will exclude EL2 as we consider the +hypervisor to be any code that runs at EL2 which is predominantly used for +guest/host transitions. + +For the guest this attribute has no effect. Please note that EL2 is +never counted within a guest. + + +exclude_host / exclude_guest +---------------------------- + +These attributes exclude the KVM host and guest, respectively. + +The KVM host may run at EL0 (userspace), EL1 (non-VHE kernel) and EL2 (VHE +kernel or non-VHE hypervisor). + +The KVM guest may run at EL0 (userspace) and EL1 (kernel). + +Due to the overlapping exception levels between host and guests we cannot +exclusively rely on the PMU's hardware exception filtering - therefore we +must enable/disable counting on the entry and exit to the guest. This is +performed differently on VHE and non-VHE systems. + +For non-VHE systems we exclude EL2 for exclude_host - upon entering and +exiting the guest we disable/enable the event as appropriate based on the +exclude_host and exclude_guest attributes. + +For VHE systems we exclude EL1 for exclude_guest and exclude both EL0,EL2 +for exclude_host. Upon entering and exiting the guest we modify the event +to include/exclude EL0 as appropriate based on the exclude_host and +exclude_guest attributes. + +The statements above also apply when these attributes are used within a +non-VHE guest however please note that EL2 is never counted within a guest. + + +Accuracy +-------- + +On non-VHE hosts we enable/disable counters on the entry/exit of host/guest +transition at EL2 - however there is a period of time between +enabling/disabling the counters and entering/exiting the guest. We are +able to eliminate counters counting host events on the boundaries of guest +entry/exit when counting guest events by filtering out EL2 for +exclude_host. However when using !exclude_hv there is a small blackout +window at the guest entry/exit where host events are not captured. + +On VHE systems there are no blackout windows. -- cgit v1.2.3 From 877b5691f27a1aec0d9b53095a323e45c30069e2 Mon Sep 17 00:00:00 2001 From: Eric Biggers Date: Sun, 14 Apr 2019 17:37:09 -0700 Subject: crypto: shash - remove shash_desc::flags The flags field in 'struct shash_desc' never actually does anything. The only ostensibly supported flag is CRYPTO_TFM_REQ_MAY_SLEEP. However, no shash algorithm ever sleeps, making this flag a no-op. With this being the case, inevitably some users who can't sleep wrongly pass MAY_SLEEP. These would all need to be fixed if any shash algorithm actually started sleeping. For example, the shash_ahash_*() functions, which wrap a shash algorithm with the ahash API, pass through MAY_SLEEP from the ahash API to the shash API. However, the shash functions are called under kmap_atomic(), so actually they're assumed to never sleep. Even if it turns out that some users do need preemption points while hashing large buffers, we could easily provide a helper function crypto_shash_update_large() which divides the data into smaller chunks and calls crypto_shash_update() and cond_resched() for each chunk. It's not necessary to have a flag in 'struct shash_desc', nor is it necessary to make individual shash algorithms aware of this at all. Therefore, remove shash_desc::flags, and document that the crypto_shash_*() functions can be called from any context. Signed-off-by: Eric Biggers Signed-off-by: Herbert Xu --- Documentation/crypto/api-samples.rst | 1 - arch/arm/crypto/ghash-ce-glue.c | 3 --- arch/x86/crypto/ghash-clmulni-intel_glue.c | 2 -- arch/x86/power/hibernate.c | 1 - crypto/adiantum.c | 1 - crypto/asymmetric_keys/pkcs7_verify.c | 1 - crypto/asymmetric_keys/verify_pefile.c | 1 - crypto/asymmetric_keys/x509_public_key.c | 1 - crypto/cryptd.c | 3 --- crypto/drbg.c | 1 - crypto/hmac.c | 11 ----------- crypto/shash.c | 4 ---- crypto/testmgr.c | 2 -- drivers/block/drbd/drbd_receiver.c | 1 - drivers/block/drbd/drbd_worker.c | 2 -- drivers/crypto/axis/artpec6_crypto.c | 2 -- drivers/crypto/bcm/cipher.c | 1 - drivers/crypto/bcm/util.c | 1 - drivers/crypto/ccp/ccp-crypto-sha.c | 2 -- drivers/crypto/chelsio/chcr_algo.c | 2 -- drivers/crypto/mediatek/mtk-sha.c | 3 --- drivers/crypto/n2_core.c | 2 -- drivers/crypto/omap-sham.c | 2 -- drivers/crypto/padlock-sha.c | 5 ----- drivers/crypto/qat/qat_common/qat_algs.c | 1 - drivers/crypto/s5p-sss.c | 1 - drivers/crypto/vmx/ghash.c | 1 - drivers/infiniband/sw/rxe/rxe.h | 1 - drivers/md/dm-crypt.c | 3 --- drivers/md/dm-integrity.c | 2 -- drivers/net/ppp/ppp_mppe.c | 1 - drivers/net/wireless/intersil/orinoco/mic.c | 1 - drivers/nfc/s3fwrn5/firmware.c | 1 - drivers/staging/ks7010/ks_hostif.c | 1 - drivers/staging/rtl8192e/rtllib_crypt_tkip.c | 1 - drivers/staging/rtl8192u/ieee80211/ieee80211_crypt_tkip.c | 1 - drivers/target/iscsi/iscsi_target_auth.c | 1 - drivers/thunderbolt/domain.c | 1 - fs/cifs/misc.c | 1 - fs/crypto/keyinfo.c | 1 - fs/ecryptfs/crypto.c | 1 - fs/ecryptfs/keystore.c | 1 - fs/ext4/ext4.h | 1 - fs/f2fs/f2fs.h | 1 - fs/nfsd/nfs4recover.c | 1 - fs/ubifs/auth.c | 6 ------ fs/ubifs/replay.c | 2 -- include/crypto/hash.h | 10 ++++++++-- include/linux/jbd2.h | 1 - kernel/kexec_file.c | 1 - lib/crc-t10dif.c | 1 - lib/digsig.c | 1 - lib/libcrc32c.c | 1 - net/bluetooth/amp.c | 1 - net/bluetooth/smp.c | 1 - net/sctp/auth.c | 1 - net/sctp/sm_make_chunk.c | 2 -- net/sunrpc/auth_gss/gss_krb5_crypto.c | 2 -- net/sunrpc/auth_gss/gss_krb5_mech.c | 1 - net/wireless/lib80211_crypt_tkip.c | 1 - security/apparmor/crypto.c | 2 -- security/integrity/evm/evm_crypto.c | 1 - security/integrity/ima/ima_crypto.c | 4 ---- security/keys/dh.c | 1 - security/keys/encrypted-keys/encrypted.c | 1 - security/keys/trusted.c | 1 - 66 files changed, 8 insertions(+), 113 deletions(-) (limited to 'Documentation') diff --git a/Documentation/crypto/api-samples.rst b/Documentation/crypto/api-samples.rst index 0f6ca8b7261e..f14afaaf2f32 100644 --- a/Documentation/crypto/api-samples.rst +++ b/Documentation/crypto/api-samples.rst @@ -133,7 +133,6 @@ Code Example For Use of Operational State Memory With SHASH if (!sdesc) return ERR_PTR(-ENOMEM); sdesc->shash.tfm = alg; - sdesc->shash.flags = 0x0; return sdesc; } diff --git a/arch/arm/crypto/ghash-ce-glue.c b/arch/arm/crypto/ghash-ce-glue.c index 60123e9ea9d8..39d1ccec1aab 100644 --- a/arch/arm/crypto/ghash-ce-glue.c +++ b/arch/arm/crypto/ghash-ce-glue.c @@ -186,7 +186,6 @@ static int ghash_async_init(struct ahash_request *req) struct crypto_shash *child = cryptd_ahash_child(cryptd_tfm); desc->tfm = child; - desc->flags = req->base.flags; return crypto_shash_init(desc); } @@ -243,7 +242,6 @@ static int ghash_async_digest(struct ahash_request *req) struct crypto_shash *child = cryptd_ahash_child(cryptd_tfm); desc->tfm = child; - desc->flags = req->base.flags; return shash_ahash_digest(req, desc); } } @@ -256,7 +254,6 @@ static int ghash_async_import(struct ahash_request *req, const void *in) struct shash_desc *desc = cryptd_shash_desc(cryptd_req); desc->tfm = cryptd_ahash_child(ctx->cryptd_tfm); - desc->flags = req->base.flags; return crypto_shash_import(desc, in); } diff --git a/arch/x86/crypto/ghash-clmulni-intel_glue.c b/arch/x86/crypto/ghash-clmulni-intel_glue.c index 4099a0ae17dd..e3f3e6fd9d65 100644 --- a/arch/x86/crypto/ghash-clmulni-intel_glue.c +++ b/arch/x86/crypto/ghash-clmulni-intel_glue.c @@ -172,7 +172,6 @@ static int ghash_async_init(struct ahash_request *req) struct crypto_shash *child = cryptd_ahash_child(cryptd_tfm); desc->tfm = child; - desc->flags = req->base.flags; return crypto_shash_init(desc); } @@ -252,7 +251,6 @@ static int ghash_async_digest(struct ahash_request *req) struct crypto_shash *child = cryptd_ahash_child(cryptd_tfm); desc->tfm = child; - desc->flags = req->base.flags; return shash_ahash_digest(req, desc); } } diff --git a/arch/x86/power/hibernate.c b/arch/x86/power/hibernate.c index bcddf09b5aa3..4845b8c7be7f 100644 --- a/arch/x86/power/hibernate.c +++ b/arch/x86/power/hibernate.c @@ -90,7 +90,6 @@ static int get_e820_md5(struct e820_table *table, void *buf) } desc->tfm = tfm; - desc->flags = 0; size = offsetof(struct e820_table, entries) + sizeof(struct e820_entry) * table->nr_entries; diff --git a/crypto/adiantum.c b/crypto/adiantum.c index e6de50f669aa..395a3ddd3707 100644 --- a/crypto/adiantum.c +++ b/crypto/adiantum.c @@ -265,7 +265,6 @@ static int adiantum_hash_message(struct skcipher_request *req, int err; hash_desc->tfm = tctx->hash; - hash_desc->flags = 0; err = crypto_shash_init(hash_desc); if (err) diff --git a/crypto/asymmetric_keys/pkcs7_verify.c b/crypto/asymmetric_keys/pkcs7_verify.c index 97c77f66b20d..f7b0980bf02d 100644 --- a/crypto/asymmetric_keys/pkcs7_verify.c +++ b/crypto/asymmetric_keys/pkcs7_verify.c @@ -56,7 +56,6 @@ static int pkcs7_digest(struct pkcs7_message *pkcs7, goto error_no_desc; desc->tfm = tfm; - desc->flags = CRYPTO_TFM_REQ_MAY_SLEEP; /* Digest the message [RFC2315 9.3] */ ret = crypto_shash_digest(desc, pkcs7->data, pkcs7->data_len, diff --git a/crypto/asymmetric_keys/verify_pefile.c b/crypto/asymmetric_keys/verify_pefile.c index d178650fd524..f8e4a932bcfb 100644 --- a/crypto/asymmetric_keys/verify_pefile.c +++ b/crypto/asymmetric_keys/verify_pefile.c @@ -354,7 +354,6 @@ static int pefile_digest_pe(const void *pebuf, unsigned int pelen, goto error_no_desc; desc->tfm = tfm; - desc->flags = CRYPTO_TFM_REQ_MAY_SLEEP; ret = crypto_shash_init(desc); if (ret < 0) goto error; diff --git a/crypto/asymmetric_keys/x509_public_key.c b/crypto/asymmetric_keys/x509_public_key.c index 9338b4558cdc..bd96683d8cde 100644 --- a/crypto/asymmetric_keys/x509_public_key.c +++ b/crypto/asymmetric_keys/x509_public_key.c @@ -77,7 +77,6 @@ int x509_get_sig_params(struct x509_certificate *cert) goto error; desc->tfm = tfm; - desc->flags = CRYPTO_TFM_REQ_MAY_SLEEP; ret = crypto_shash_digest(desc, cert->tbs, cert->tbs_size, sig->digest); if (ret < 0) diff --git a/crypto/cryptd.c b/crypto/cryptd.c index 42533cf80acc..b3bb99390ae7 100644 --- a/crypto/cryptd.c +++ b/crypto/cryptd.c @@ -545,7 +545,6 @@ static void cryptd_hash_init(struct crypto_async_request *req_async, int err) goto out; desc->tfm = child; - desc->flags = CRYPTO_TFM_REQ_MAY_SLEEP; err = crypto_shash_init(desc); @@ -637,7 +636,6 @@ static void cryptd_hash_digest(struct crypto_async_request *req_async, int err) goto out; desc->tfm = child; - desc->flags = CRYPTO_TFM_REQ_MAY_SLEEP; err = shash_ahash_digest(req, desc); @@ -666,7 +664,6 @@ static int cryptd_hash_import(struct ahash_request *req, const void *in) struct shash_desc *desc = cryptd_shash_desc(req); desc->tfm = ctx->child; - desc->flags = req->base.flags; return crypto_shash_import(desc, in); } diff --git a/crypto/drbg.c b/crypto/drbg.c index 710b3046a4df..2a5b16bb000c 100644 --- a/crypto/drbg.c +++ b/crypto/drbg.c @@ -1587,7 +1587,6 @@ static int drbg_init_hash_kernel(struct drbg_state *drbg) } sdesc->shash.tfm = tfm; - sdesc->shash.flags = 0; drbg->priv_data = sdesc; return crypto_shash_alignmask(tfm); diff --git a/crypto/hmac.c b/crypto/hmac.c index 4ceb3f1f0eb8..a68c1266121f 100644 --- a/crypto/hmac.c +++ b/crypto/hmac.c @@ -57,8 +57,6 @@ static int hmac_setkey(struct crypto_shash *parent, unsigned int i; shash->tfm = hash; - shash->flags = crypto_shash_get_flags(parent) - & CRYPTO_TFM_REQ_MAY_SLEEP; if (keylen > bs) { int err; @@ -91,8 +89,6 @@ static int hmac_export(struct shash_desc *pdesc, void *out) { struct shash_desc *desc = shash_desc_ctx(pdesc); - desc->flags = pdesc->flags & CRYPTO_TFM_REQ_MAY_SLEEP; - return crypto_shash_export(desc, out); } @@ -102,7 +98,6 @@ static int hmac_import(struct shash_desc *pdesc, const void *in) struct hmac_ctx *ctx = hmac_ctx(pdesc->tfm); desc->tfm = ctx->hash; - desc->flags = pdesc->flags & CRYPTO_TFM_REQ_MAY_SLEEP; return crypto_shash_import(desc, in); } @@ -117,8 +112,6 @@ static int hmac_update(struct shash_desc *pdesc, { struct shash_desc *desc = shash_desc_ctx(pdesc); - desc->flags = pdesc->flags & CRYPTO_TFM_REQ_MAY_SLEEP; - return crypto_shash_update(desc, data, nbytes); } @@ -130,8 +123,6 @@ static int hmac_final(struct shash_desc *pdesc, u8 *out) char *opad = crypto_shash_ctx_aligned(parent) + ss; struct shash_desc *desc = shash_desc_ctx(pdesc); - desc->flags = pdesc->flags & CRYPTO_TFM_REQ_MAY_SLEEP; - return crypto_shash_final(desc, out) ?: crypto_shash_import(desc, opad) ?: crypto_shash_finup(desc, out, ds, out); @@ -147,8 +138,6 @@ static int hmac_finup(struct shash_desc *pdesc, const u8 *data, char *opad = crypto_shash_ctx_aligned(parent) + ss; struct shash_desc *desc = shash_desc_ctx(pdesc); - desc->flags = pdesc->flags & CRYPTO_TFM_REQ_MAY_SLEEP; - return crypto_shash_finup(desc, data, nbytes, out) ?: crypto_shash_import(desc, opad) ?: crypto_shash_finup(desc, out, ds, out); diff --git a/crypto/shash.c b/crypto/shash.c index 599468478f7b..e55c1f558bc3 100644 --- a/crypto/shash.c +++ b/crypto/shash.c @@ -238,7 +238,6 @@ static int shash_async_init(struct ahash_request *req) struct shash_desc *desc = ahash_request_ctx(req); desc->tfm = *ctx; - desc->flags = req->base.flags; return crypto_shash_init(desc); } @@ -293,7 +292,6 @@ static int shash_async_finup(struct ahash_request *req) struct shash_desc *desc = ahash_request_ctx(req); desc->tfm = *ctx; - desc->flags = req->base.flags; return shash_ahash_finup(req, desc); } @@ -328,7 +326,6 @@ static int shash_async_digest(struct ahash_request *req) struct shash_desc *desc = ahash_request_ctx(req); desc->tfm = *ctx; - desc->flags = req->base.flags; return shash_ahash_digest(req, desc); } @@ -344,7 +341,6 @@ static int shash_async_import(struct ahash_request *req, const void *in) struct shash_desc *desc = ahash_request_ctx(req); desc->tfm = *ctx; - desc->flags = req->base.flags; return crypto_shash_import(desc, in); } diff --git a/crypto/testmgr.c b/crypto/testmgr.c index 87abfd1ce232..2bd89a65e9e7 100644 --- a/crypto/testmgr.c +++ b/crypto/testmgr.c @@ -1328,7 +1328,6 @@ static void generate_random_hash_testvec(struct crypto_shash *tfm, /* Digest */ desc->tfm = tfm; - desc->flags = 0; vec->digest_error = crypto_shash_digest(desc, vec->plaintext, vec->psize, (u8 *)vec->digest); done: @@ -3027,7 +3026,6 @@ static int alg_test_crc32c(const struct alg_test_desc *desc, u32 *ctx = (u32 *)shash_desc_ctx(shash); shash->tfm = tfm; - shash->flags = 0; *ctx = 420553207; err = crypto_shash_final(shash, (u8 *)&val); diff --git a/drivers/block/drbd/drbd_receiver.c b/drivers/block/drbd/drbd_receiver.c index c7ad88d91a09..843a9b9b3d74 100644 --- a/drivers/block/drbd/drbd_receiver.c +++ b/drivers/block/drbd/drbd_receiver.c @@ -5443,7 +5443,6 @@ static int drbd_do_auth(struct drbd_connection *connection) rcu_read_unlock(); desc->tfm = connection->cram_hmac_tfm; - desc->flags = 0; rv = crypto_shash_setkey(connection->cram_hmac_tfm, (u8 *)secret, key_len); if (rv) { diff --git a/drivers/block/drbd/drbd_worker.c b/drivers/block/drbd/drbd_worker.c index 268ef0c5d4ab..6781bcf3ec26 100644 --- a/drivers/block/drbd/drbd_worker.c +++ b/drivers/block/drbd/drbd_worker.c @@ -304,7 +304,6 @@ void drbd_csum_ee(struct crypto_shash *tfm, struct drbd_peer_request *peer_req, void *src; desc->tfm = tfm; - desc->flags = 0; crypto_shash_init(desc); @@ -332,7 +331,6 @@ void drbd_csum_bio(struct crypto_shash *tfm, struct bio *bio, void *digest) struct bvec_iter iter; desc->tfm = tfm; - desc->flags = 0; crypto_shash_init(desc); diff --git a/drivers/crypto/axis/artpec6_crypto.c b/drivers/crypto/axis/artpec6_crypto.c index 57e5dca3253f..d2fb72811442 100644 --- a/drivers/crypto/axis/artpec6_crypto.c +++ b/drivers/crypto/axis/artpec6_crypto.c @@ -2247,8 +2247,6 @@ artpec6_crypto_hash_set_key(struct crypto_ahash *tfm, SHASH_DESC_ON_STACK(hdesc, tfm_ctx->child_hash); hdesc->tfm = tfm_ctx->child_hash; - hdesc->flags = crypto_ahash_get_flags(tfm) & - CRYPTO_TFM_REQ_MAY_SLEEP; tfm_ctx->hmac_key_length = blocksize; ret = crypto_shash_digest(hdesc, key, keylen, diff --git a/drivers/crypto/bcm/cipher.c b/drivers/crypto/bcm/cipher.c index 8862200d4a0b..25f8d3913ceb 100644 --- a/drivers/crypto/bcm/cipher.c +++ b/drivers/crypto/bcm/cipher.c @@ -2140,7 +2140,6 @@ static int ahash_init(struct ahash_request *req) goto err_hash; } ctx->shash->tfm = hash; - ctx->shash->flags = 0; /* Set the key using data we already have from setkey */ if (ctx->authkeylen > 0) { diff --git a/drivers/crypto/bcm/util.c b/drivers/crypto/bcm/util.c index d8cda5fb75ad..91ec56399d84 100644 --- a/drivers/crypto/bcm/util.c +++ b/drivers/crypto/bcm/util.c @@ -242,7 +242,6 @@ int do_shash(unsigned char *name, unsigned char *result, goto do_shash_err; } sdesc->shash.tfm = hash; - sdesc->shash.flags = 0x0; if (key_len > 0) { rc = crypto_shash_setkey(hash, key, key_len); diff --git a/drivers/crypto/ccp/ccp-crypto-sha.c b/drivers/crypto/ccp/ccp-crypto-sha.c index 10a61cd54fce..3e10573f589e 100644 --- a/drivers/crypto/ccp/ccp-crypto-sha.c +++ b/drivers/crypto/ccp/ccp-crypto-sha.c @@ -293,8 +293,6 @@ static int ccp_sha_setkey(struct crypto_ahash *tfm, const u8 *key, if (key_len > block_size) { /* Must hash the input key */ sdesc->tfm = shash; - sdesc->flags = crypto_ahash_get_flags(tfm) & - CRYPTO_TFM_REQ_MAY_SLEEP; ret = crypto_shash_digest(sdesc, key, key_len, ctx->u.sha.key); diff --git a/drivers/crypto/chelsio/chcr_algo.c b/drivers/crypto/chelsio/chcr_algo.c index 8d8cf80b9294..8a76fce22943 100644 --- a/drivers/crypto/chelsio/chcr_algo.c +++ b/drivers/crypto/chelsio/chcr_algo.c @@ -2130,7 +2130,6 @@ static int chcr_ahash_setkey(struct crypto_ahash *tfm, const u8 *key, * ipad in hmacctx->ipad and opad in hmacctx->opad location */ shash->tfm = hmacctx->base_hash; - shash->flags = crypto_shash_get_flags(hmacctx->base_hash); if (keylen > bs) { err = crypto_shash_digest(shash, key, keylen, hmacctx->ipad); @@ -3517,7 +3516,6 @@ static int chcr_authenc_setkey(struct crypto_aead *authenc, const u8 *key, SHASH_DESC_ON_STACK(shash, base_hash); shash->tfm = base_hash; - shash->flags = crypto_shash_get_flags(base_hash); bs = crypto_shash_blocksize(base_hash); align = KEYCTX_ALIGN_PAD(max_authsize); o_ptr = actx->h_iopad + param.result_size + align; diff --git a/drivers/crypto/mediatek/mtk-sha.c b/drivers/crypto/mediatek/mtk-sha.c index 5f4f845adbb8..a0806ba40c68 100644 --- a/drivers/crypto/mediatek/mtk-sha.c +++ b/drivers/crypto/mediatek/mtk-sha.c @@ -365,7 +365,6 @@ static int mtk_sha_finish_hmac(struct ahash_request *req) SHASH_DESC_ON_STACK(shash, bctx->shash); shash->tfm = bctx->shash; - shash->flags = 0; /* not CRYPTO_TFM_REQ_MAY_SLEEP */ return crypto_shash_init(shash) ?: crypto_shash_update(shash, bctx->opad, ctx->bs) ?: @@ -810,8 +809,6 @@ static int mtk_sha_setkey(struct crypto_ahash *tfm, const u8 *key, SHASH_DESC_ON_STACK(shash, bctx->shash); shash->tfm = bctx->shash; - shash->flags = crypto_shash_get_flags(bctx->shash) & - CRYPTO_TFM_REQ_MAY_SLEEP; if (keylen > bs) { err = crypto_shash_digest(shash, key, keylen, bctx->ipad); diff --git a/drivers/crypto/n2_core.c b/drivers/crypto/n2_core.c index df675aea58f6..0d5d3d8eb680 100644 --- a/drivers/crypto/n2_core.c +++ b/drivers/crypto/n2_core.c @@ -469,8 +469,6 @@ static int n2_hmac_async_setkey(struct crypto_ahash *tfm, const u8 *key, return err; shash->tfm = child_shash; - shash->flags = crypto_ahash_get_flags(tfm) & - CRYPTO_TFM_REQ_MAY_SLEEP; bs = crypto_shash_blocksize(child_shash); ds = crypto_shash_digestsize(child_shash); diff --git a/drivers/crypto/omap-sham.c b/drivers/crypto/omap-sham.c index 0641185bd82f..51b20abac464 100644 --- a/drivers/crypto/omap-sham.c +++ b/drivers/crypto/omap-sham.c @@ -1055,7 +1055,6 @@ static int omap_sham_finish_hmac(struct ahash_request *req) SHASH_DESC_ON_STACK(shash, bctx->shash); shash->tfm = bctx->shash; - shash->flags = 0; /* not CRYPTO_TFM_REQ_MAY_SLEEP */ return crypto_shash_init(shash) ?: crypto_shash_update(shash, bctx->opad, bs) ?: @@ -1226,7 +1225,6 @@ static int omap_sham_shash_digest(struct crypto_shash *tfm, u32 flags, SHASH_DESC_ON_STACK(shash, tfm); shash->tfm = tfm; - shash->flags = flags & CRYPTO_TFM_REQ_MAY_SLEEP; return crypto_shash_digest(shash, data, len, out); } diff --git a/drivers/crypto/padlock-sha.c b/drivers/crypto/padlock-sha.c index 21e5cae0a1e0..e641481a3cd9 100644 --- a/drivers/crypto/padlock-sha.c +++ b/drivers/crypto/padlock-sha.c @@ -39,7 +39,6 @@ static int padlock_sha_init(struct shash_desc *desc) struct padlock_sha_ctx *ctx = crypto_shash_ctx(desc->tfm); dctx->fallback.tfm = ctx->fallback; - dctx->fallback.flags = desc->flags & CRYPTO_TFM_REQ_MAY_SLEEP; return crypto_shash_init(&dctx->fallback); } @@ -48,7 +47,6 @@ static int padlock_sha_update(struct shash_desc *desc, { struct padlock_sha_desc *dctx = shash_desc_ctx(desc); - dctx->fallback.flags = desc->flags & CRYPTO_TFM_REQ_MAY_SLEEP; return crypto_shash_update(&dctx->fallback, data, length); } @@ -65,7 +63,6 @@ static int padlock_sha_import(struct shash_desc *desc, const void *in) struct padlock_sha_ctx *ctx = crypto_shash_ctx(desc->tfm); dctx->fallback.tfm = ctx->fallback; - dctx->fallback.flags = desc->flags & CRYPTO_TFM_REQ_MAY_SLEEP; return crypto_shash_import(&dctx->fallback, in); } @@ -91,7 +88,6 @@ static int padlock_sha1_finup(struct shash_desc *desc, const u8 *in, unsigned int leftover; int err; - dctx->fallback.flags = desc->flags & CRYPTO_TFM_REQ_MAY_SLEEP; err = crypto_shash_export(&dctx->fallback, &state); if (err) goto out; @@ -153,7 +149,6 @@ static int padlock_sha256_finup(struct shash_desc *desc, const u8 *in, unsigned int leftover; int err; - dctx->fallback.flags = desc->flags & CRYPTO_TFM_REQ_MAY_SLEEP; err = crypto_shash_export(&dctx->fallback, &state); if (err) goto out; diff --git a/drivers/crypto/qat/qat_common/qat_algs.c b/drivers/crypto/qat/qat_common/qat_algs.c index 975c75198f56..c8d401646902 100644 --- a/drivers/crypto/qat/qat_common/qat_algs.c +++ b/drivers/crypto/qat/qat_common/qat_algs.c @@ -164,7 +164,6 @@ static int qat_alg_do_precomputes(struct icp_qat_hw_auth_algo_blk *hash, memset(ctx->ipad, 0, block_size); memset(ctx->opad, 0, block_size); shash->tfm = ctx->hash_tfm; - shash->flags = 0x0; if (auth_keylen > block_size) { int ret = crypto_shash_digest(shash, auth_key, diff --git a/drivers/crypto/s5p-sss.c b/drivers/crypto/s5p-sss.c index 1afdcb81d8ed..9ef25230c199 100644 --- a/drivers/crypto/s5p-sss.c +++ b/drivers/crypto/s5p-sss.c @@ -1534,7 +1534,6 @@ static int s5p_hash_shash_digest(struct crypto_shash *tfm, u32 flags, SHASH_DESC_ON_STACK(shash, tfm); shash->tfm = tfm; - shash->flags = flags & ~CRYPTO_TFM_REQ_MAY_SLEEP; return crypto_shash_digest(shash, data, len, out); } diff --git a/drivers/crypto/vmx/ghash.c b/drivers/crypto/vmx/ghash.c index 611ff591410e..b5a6883bb09e 100644 --- a/drivers/crypto/vmx/ghash.c +++ b/drivers/crypto/vmx/ghash.c @@ -101,7 +101,6 @@ static int p8_ghash_init(struct shash_desc *desc) dctx->bytes = 0; memset(dctx->shash, 0, GHASH_DIGEST_SIZE); dctx->fallback_desc.tfm = ctx->fallback; - dctx->fallback_desc.flags = desc->flags; return crypto_shash_init(&dctx->fallback_desc); } diff --git a/drivers/infiniband/sw/rxe/rxe.h b/drivers/infiniband/sw/rxe/rxe.h index 2e2dff478833..ecf6e659c0da 100644 --- a/drivers/infiniband/sw/rxe/rxe.h +++ b/drivers/infiniband/sw/rxe/rxe.h @@ -80,7 +80,6 @@ static inline u32 rxe_crc32(struct rxe_dev *rxe, SHASH_DESC_ON_STACK(shash, rxe->tfm); shash->tfm = rxe->tfm; - shash->flags = 0; *(u32 *)shash_desc_ctx(shash) = crc; err = crypto_shash_update(shash, next, len); if (unlikely(err)) { diff --git a/drivers/md/dm-crypt.c b/drivers/md/dm-crypt.c index dd6565798778..9faed1c92b52 100644 --- a/drivers/md/dm-crypt.c +++ b/drivers/md/dm-crypt.c @@ -332,7 +332,6 @@ static int crypt_iv_essiv_init(struct crypt_config *cc) int err; desc->tfm = essiv->hash_tfm; - desc->flags = 0; err = crypto_shash_digest(desc, cc->key, cc->key_size, essiv->salt); shash_desc_zero(desc); @@ -606,7 +605,6 @@ static int crypt_iv_lmk_one(struct crypt_config *cc, u8 *iv, int i, r; desc->tfm = lmk->hash_tfm; - desc->flags = 0; r = crypto_shash_init(desc); if (r) @@ -768,7 +766,6 @@ static int crypt_iv_tcw_whitening(struct crypt_config *cc, /* calculate crc32 for every 32bit part and xor it */ desc->tfm = tcw->crc32_tfm; - desc->flags = 0; for (i = 0; i < 4; i++) { r = crypto_shash_init(desc); if (r) diff --git a/drivers/md/dm-integrity.c b/drivers/md/dm-integrity.c index d57d997a52c8..1366d886907c 100644 --- a/drivers/md/dm-integrity.c +++ b/drivers/md/dm-integrity.c @@ -532,7 +532,6 @@ static void section_mac(struct dm_integrity_c *ic, unsigned section, __u8 result unsigned j, size; desc->tfm = ic->journal_mac; - desc->flags = 0; r = crypto_shash_init(desc); if (unlikely(r)) { @@ -1278,7 +1277,6 @@ static void integrity_sector_checksum(struct dm_integrity_c *ic, sector_t sector unsigned digest_size; req->tfm = ic->internal_hash; - req->flags = 0; r = crypto_shash_init(req); if (unlikely(r < 0)) { diff --git a/drivers/net/ppp/ppp_mppe.c b/drivers/net/ppp/ppp_mppe.c index 7ccdc62c6052..ff61dd8748de 100644 --- a/drivers/net/ppp/ppp_mppe.c +++ b/drivers/net/ppp/ppp_mppe.c @@ -222,7 +222,6 @@ static void *mppe_alloc(unsigned char *options, int optlen) goto out_free; } state->sha1->tfm = shash; - state->sha1->flags = 0; digestsize = crypto_shash_digestsize(shash); if (digestsize < MPPE_MAX_KEY_LEN) diff --git a/drivers/net/wireless/intersil/orinoco/mic.c b/drivers/net/wireless/intersil/orinoco/mic.c index 67b0c05afbdb..a324bc4b7938 100644 --- a/drivers/net/wireless/intersil/orinoco/mic.c +++ b/drivers/net/wireless/intersil/orinoco/mic.c @@ -65,7 +65,6 @@ int orinoco_mic(struct crypto_shash *tfm_michael, u8 *key, hdr[ETH_ALEN * 2 + 3] = 0; desc->tfm = tfm_michael; - desc->flags = 0; err = crypto_shash_setkey(tfm_michael, key, MIC_KEYLEN); if (err) diff --git a/drivers/nfc/s3fwrn5/firmware.c b/drivers/nfc/s3fwrn5/firmware.c index b7828fb252f2..b681073ae8ba 100644 --- a/drivers/nfc/s3fwrn5/firmware.c +++ b/drivers/nfc/s3fwrn5/firmware.c @@ -449,7 +449,6 @@ int s3fwrn5_fw_download(struct s3fwrn5_fw_info *fw_info) SHASH_DESC_ON_STACK(desc, tfm); desc->tfm = tfm; - desc->flags = CRYPTO_TFM_REQ_MAY_SLEEP; ret = crypto_shash_digest(desc, fw->image, image_size, hash_data); diff --git a/drivers/staging/ks7010/ks_hostif.c b/drivers/staging/ks7010/ks_hostif.c index 06ebea0be118..122d4c0af363 100644 --- a/drivers/staging/ks7010/ks_hostif.c +++ b/drivers/staging/ks7010/ks_hostif.c @@ -219,7 +219,6 @@ michael_mic(u8 *key, u8 *data, unsigned int len, u8 priority, u8 *result) } desc->tfm = tfm; - desc->flags = 0; ret = crypto_shash_init(desc); if (ret < 0) diff --git a/drivers/staging/rtl8192e/rtllib_crypt_tkip.c b/drivers/staging/rtl8192e/rtllib_crypt_tkip.c index 55da8c9dfe50..a084e1501f9d 100644 --- a/drivers/staging/rtl8192e/rtllib_crypt_tkip.c +++ b/drivers/staging/rtl8192e/rtllib_crypt_tkip.c @@ -507,7 +507,6 @@ static int michael_mic(struct crypto_shash *tfm_michael, u8 *key, u8 *hdr, int err; desc->tfm = tfm_michael; - desc->flags = 0; if (crypto_shash_setkey(tfm_michael, key, 8)) return -1; diff --git a/drivers/staging/rtl8192u/ieee80211/ieee80211_crypt_tkip.c b/drivers/staging/rtl8192u/ieee80211/ieee80211_crypt_tkip.c index 829fa4bd253c..d67bb57994c4 100644 --- a/drivers/staging/rtl8192u/ieee80211/ieee80211_crypt_tkip.c +++ b/drivers/staging/rtl8192u/ieee80211/ieee80211_crypt_tkip.c @@ -503,7 +503,6 @@ static int michael_mic(struct crypto_shash *tfm_michael, u8 *key, u8 *hdr, int err; desc->tfm = tfm_michael; - desc->flags = 0; if (crypto_shash_setkey(tfm_michael, key, 8)) return -1; diff --git a/drivers/target/iscsi/iscsi_target_auth.c b/drivers/target/iscsi/iscsi_target_auth.c index 4e680d753941..ca7d7e8aecc0 100644 --- a/drivers/target/iscsi/iscsi_target_auth.c +++ b/drivers/target/iscsi/iscsi_target_auth.c @@ -252,7 +252,6 @@ static int chap_server_compute_md5( } desc->tfm = tfm; - desc->flags = 0; ret = crypto_shash_init(desc); if (ret < 0) { diff --git a/drivers/thunderbolt/domain.c b/drivers/thunderbolt/domain.c index 7416bdbd8576..b7980c856898 100644 --- a/drivers/thunderbolt/domain.c +++ b/drivers/thunderbolt/domain.c @@ -678,7 +678,6 @@ int tb_domain_challenge_switch_key(struct tb *tb, struct tb_switch *sw) } shash->tfm = tfm; - shash->flags = CRYPTO_TFM_REQ_MAY_SLEEP; memset(hmac, 0, sizeof(hmac)); ret = crypto_shash_digest(shash, challenge, sizeof(hmac), hmac); diff --git a/fs/cifs/misc.c b/fs/cifs/misc.c index bee203055b30..1a6040998227 100644 --- a/fs/cifs/misc.c +++ b/fs/cifs/misc.c @@ -917,7 +917,6 @@ cifs_alloc_hash(const char *name, } (*sdesc)->shash.tfm = *shash; - (*sdesc)->shash.flags = 0x0; return 0; } diff --git a/fs/crypto/keyinfo.c b/fs/crypto/keyinfo.c index 322ce9686bdb..2cb4956f8511 100644 --- a/fs/crypto/keyinfo.c +++ b/fs/crypto/keyinfo.c @@ -402,7 +402,6 @@ static int derive_essiv_salt(const u8 *key, int keysize, u8 *salt) { SHASH_DESC_ON_STACK(desc, tfm); desc->tfm = tfm; - desc->flags = 0; return crypto_shash_digest(desc, key, keysize, salt); } diff --git a/fs/ecryptfs/crypto.c b/fs/ecryptfs/crypto.c index f664da55234e..491cf5baa8c2 100644 --- a/fs/ecryptfs/crypto.c +++ b/fs/ecryptfs/crypto.c @@ -68,7 +68,6 @@ static int ecryptfs_hash_digest(struct crypto_shash *tfm, int err; desc->tfm = tfm; - desc->flags = CRYPTO_TFM_REQ_MAY_SLEEP; err = crypto_shash_digest(desc, src, len, dst); shash_desc_zero(desc); return err; diff --git a/fs/ecryptfs/keystore.c b/fs/ecryptfs/keystore.c index e74fe84d0886..90fbac5d485b 100644 --- a/fs/ecryptfs/keystore.c +++ b/fs/ecryptfs/keystore.c @@ -769,7 +769,6 @@ ecryptfs_write_tag_70_packet(char *dest, size_t *remaining_bytes, } s->hash_desc->tfm = s->hash_tfm; - s->hash_desc->flags = CRYPTO_TFM_REQ_MAY_SLEEP; rc = crypto_shash_digest(s->hash_desc, (u8 *)s->auth_tok->token.password.session_key_encryption_key, diff --git a/fs/ext4/ext4.h b/fs/ext4/ext4.h index 82ffdacdc7fa..0833b5fc0668 100644 --- a/fs/ext4/ext4.h +++ b/fs/ext4/ext4.h @@ -2024,7 +2024,6 @@ static inline u32 ext4_chksum(struct ext4_sb_info *sbi, u32 crc, BUG_ON(crypto_shash_descsize(sbi->s_chksum_driver)!=sizeof(desc.ctx)); desc.shash.tfm = sbi->s_chksum_driver; - desc.shash.flags = 0; *(u32 *)desc.ctx = crc; BUG_ON(crypto_shash_update(&desc.shash, address, length)); diff --git a/fs/f2fs/f2fs.h b/fs/f2fs/f2fs.h index 87f75ebd2fd6..21b0ab6bd15a 100644 --- a/fs/f2fs/f2fs.h +++ b/fs/f2fs/f2fs.h @@ -1422,7 +1422,6 @@ static inline u32 __f2fs_crc32(struct f2fs_sb_info *sbi, u32 crc, BUG_ON(crypto_shash_descsize(sbi->s_chksum_driver) != sizeof(desc.ctx)); desc.shash.tfm = sbi->s_chksum_driver; - desc.shash.flags = 0; *(u32 *)desc.ctx = crc; err = crypto_shash_update(&desc.shash, address, length); diff --git a/fs/nfsd/nfs4recover.c b/fs/nfsd/nfs4recover.c index 5188f9f70c78..8c8563441208 100644 --- a/fs/nfsd/nfs4recover.c +++ b/fs/nfsd/nfs4recover.c @@ -126,7 +126,6 @@ nfs4_make_rec_clidname(char *dname, const struct xdr_netobj *clname) SHASH_DESC_ON_STACK(desc, tfm); desc->tfm = tfm; - desc->flags = CRYPTO_TFM_REQ_MAY_SLEEP; status = crypto_shash_digest(desc, clname->data, clname->len, cksum.data); diff --git a/fs/ubifs/auth.c b/fs/ubifs/auth.c index 5bf5fd08879e..b758004085c4 100644 --- a/fs/ubifs/auth.c +++ b/fs/ubifs/auth.c @@ -33,7 +33,6 @@ int __ubifs_node_calc_hash(const struct ubifs_info *c, const void *node, int err; shash->tfm = c->hash_tfm; - shash->flags = CRYPTO_TFM_REQ_MAY_SLEEP; err = crypto_shash_digest(shash, node, le32_to_cpu(ch->len), hash); if (err < 0) @@ -56,7 +55,6 @@ static int ubifs_hash_calc_hmac(const struct ubifs_info *c, const u8 *hash, int err; shash->tfm = c->hmac_tfm; - shash->flags = CRYPTO_TFM_REQ_MAY_SLEEP; err = crypto_shash_digest(shash, hash, c->hash_len, hmac); if (err < 0) @@ -88,7 +86,6 @@ int ubifs_prepare_auth_node(struct ubifs_info *c, void *node, return -ENOMEM; hash_desc->tfm = c->hash_tfm; - hash_desc->flags = CRYPTO_TFM_REQ_MAY_SLEEP; ubifs_shash_copy_state(c, inhash, hash_desc); err = crypto_shash_final(hash_desc, hash); @@ -123,7 +120,6 @@ static struct shash_desc *ubifs_get_desc(const struct ubifs_info *c, return ERR_PTR(-ENOMEM); desc->tfm = tfm; - desc->flags = CRYPTO_TFM_REQ_MAY_SLEEP; err = crypto_shash_init(desc); if (err) { @@ -364,7 +360,6 @@ static int ubifs_node_calc_hmac(const struct ubifs_info *c, const void *node, ubifs_assert(c, ofs_hmac + hmac_len < len); shash->tfm = c->hmac_tfm; - shash->flags = CRYPTO_TFM_REQ_MAY_SLEEP; err = crypto_shash_init(shash); if (err) @@ -483,7 +478,6 @@ int ubifs_hmac_wkm(struct ubifs_info *c, u8 *hmac) return 0; shash->tfm = c->hmac_tfm; - shash->flags = CRYPTO_TFM_REQ_MAY_SLEEP; err = crypto_shash_init(shash); if (err) diff --git a/fs/ubifs/replay.c b/fs/ubifs/replay.c index 0a0e65c07c6d..5c8a81a019a4 100644 --- a/fs/ubifs/replay.c +++ b/fs/ubifs/replay.c @@ -576,7 +576,6 @@ static int authenticate_sleb_hash(struct ubifs_info *c, struct shash_desc *log_h SHASH_DESC_ON_STACK(hash_desc, c->hash_tfm); hash_desc->tfm = c->hash_tfm; - hash_desc->flags = CRYPTO_TFM_REQ_MAY_SLEEP; ubifs_shash_copy_state(c, log_hash, hash_desc); return crypto_shash_final(hash_desc, hash); @@ -587,7 +586,6 @@ static int authenticate_sleb_hmac(struct ubifs_info *c, u8 *hash, u8 *hmac) SHASH_DESC_ON_STACK(hmac_desc, c->hmac_tfm); hmac_desc->tfm = c->hmac_tfm; - hmac_desc->flags = CRYPTO_TFM_REQ_MAY_SLEEP; return crypto_shash_digest(hmac_desc, hash, c->hash_len, hmac); } diff --git a/include/crypto/hash.h b/include/crypto/hash.h index 3b31c1b349ae..d21bea2c4382 100644 --- a/include/crypto/hash.h +++ b/include/crypto/hash.h @@ -146,8 +146,6 @@ struct ahash_alg { struct shash_desc { struct crypto_shash *tfm; - u32 flags; - void *__ctx[] CRYPTO_MINALIGN_ATTR; }; @@ -819,6 +817,7 @@ static inline void *shash_desc_ctx(struct shash_desc *desc) * cipher handle must point to a keyed message digest cipher in order for this * function to succeed. * + * Context: Any context. * Return: 0 if the setting of the key was successful; < 0 if an error occurred */ int crypto_shash_setkey(struct crypto_shash *tfm, const u8 *key, @@ -835,6 +834,7 @@ int crypto_shash_setkey(struct crypto_shash *tfm, const u8 *key, * crypto_shash_update and crypto_shash_final. The parameters have the same * meaning as discussed for those separate three functions. * + * Context: Any context. * Return: 0 if the message digest creation was successful; < 0 if an error * occurred */ @@ -850,6 +850,7 @@ int crypto_shash_digest(struct shash_desc *desc, const u8 *data, * caller-allocated output buffer out which must have sufficient size (e.g. by * calling crypto_shash_descsize). * + * Context: Any context. * Return: 0 if the export creation was successful; < 0 if an error occurred */ static inline int crypto_shash_export(struct shash_desc *desc, void *out) @@ -866,6 +867,7 @@ static inline int crypto_shash_export(struct shash_desc *desc, void *out) * the input buffer. That buffer should have been generated with the * crypto_ahash_export function. * + * Context: Any context. * Return: 0 if the import was successful; < 0 if an error occurred */ static inline int crypto_shash_import(struct shash_desc *desc, const void *in) @@ -886,6 +888,7 @@ static inline int crypto_shash_import(struct shash_desc *desc, const void *in) * operational state handle. Any potentially existing state created by * previous operations is discarded. * + * Context: Any context. * Return: 0 if the message digest initialization was successful; < 0 if an * error occurred */ @@ -907,6 +910,7 @@ static inline int crypto_shash_init(struct shash_desc *desc) * * Updates the message digest state of the operational state handle. * + * Context: Any context. * Return: 0 if the message digest update was successful; < 0 if an error * occurred */ @@ -923,6 +927,7 @@ int crypto_shash_update(struct shash_desc *desc, const u8 *data, * into the output buffer. The caller must ensure that the output buffer is * large enough by using crypto_shash_digestsize. * + * Context: Any context. * Return: 0 if the message digest creation was successful; < 0 if an error * occurred */ @@ -939,6 +944,7 @@ int crypto_shash_final(struct shash_desc *desc, u8 *out); * crypto_shash_update and crypto_shash_final. The parameters have the same * meaning as discussed for those separate functions. * + * Context: Any context. * Return: 0 if the message digest creation was successful; < 0 if an error * occurred */ diff --git a/include/linux/jbd2.h b/include/linux/jbd2.h index 0f919d5fe84f..c2ffff5f9ae2 100644 --- a/include/linux/jbd2.h +++ b/include/linux/jbd2.h @@ -1606,7 +1606,6 @@ static inline u32 jbd2_chksum(journal_t *journal, u32 crc, JBD_MAX_CHECKSUM_SIZE); desc.shash.tfm = journal->j_chksum_driver; - desc.shash.flags = 0; *(u32 *)desc.ctx = crc; err = crypto_shash_update(&desc.shash, address, length); diff --git a/kernel/kexec_file.c b/kernel/kexec_file.c index f1d0e00a3971..f7fb8f6a688f 100644 --- a/kernel/kexec_file.c +++ b/kernel/kexec_file.c @@ -688,7 +688,6 @@ static int kexec_calculate_store_digests(struct kimage *image) goto out_free_desc; desc->tfm = tfm; - desc->flags = 0; ret = crypto_shash_init(desc); if (ret < 0) diff --git a/lib/crc-t10dif.c b/lib/crc-t10dif.c index 4d0d47c1ffbd..e89ebfdbb0fc 100644 --- a/lib/crc-t10dif.c +++ b/lib/crc-t10dif.c @@ -69,7 +69,6 @@ __u16 crc_t10dif_update(__u16 crc, const unsigned char *buffer, size_t len) rcu_read_lock(); desc.shash.tfm = rcu_dereference(crct10dif_tfm); - desc.shash.flags = 0; *(__u16 *)desc.ctx = crc; err = crypto_shash_update(&desc.shash, buffer, len); diff --git a/lib/digsig.c b/lib/digsig.c index 6ba6fcd92dd1..3b0a579bdcdf 100644 --- a/lib/digsig.c +++ b/lib/digsig.c @@ -240,7 +240,6 @@ int digsig_verify(struct key *keyring, const char *sig, int siglen, goto err; desc->tfm = shash; - desc->flags = CRYPTO_TFM_REQ_MAY_SLEEP; crypto_shash_init(desc); crypto_shash_update(desc, data, datalen); diff --git a/lib/libcrc32c.c b/lib/libcrc32c.c index f0a2934605bf..4e9829c4d64c 100644 --- a/lib/libcrc32c.c +++ b/lib/libcrc32c.c @@ -47,7 +47,6 @@ u32 crc32c(u32 crc, const void *address, unsigned int length) int err; shash->tfm = tfm; - shash->flags = 0; *ctx = crc; err = crypto_shash_update(shash, address, length); diff --git a/net/bluetooth/amp.c b/net/bluetooth/amp.c index 78bec8df8525..aaa39409eeb7 100644 --- a/net/bluetooth/amp.c +++ b/net/bluetooth/amp.c @@ -161,7 +161,6 @@ static int hmac_sha256(u8 *key, u8 ksize, char *plaintext, u8 psize, u8 *output) } shash->tfm = tfm; - shash->flags = CRYPTO_TFM_REQ_MAY_SLEEP; ret = crypto_shash_digest(shash, plaintext, psize, output); diff --git a/net/bluetooth/smp.c b/net/bluetooth/smp.c index 621146d04c03..e68c715f8d37 100644 --- a/net/bluetooth/smp.c +++ b/net/bluetooth/smp.c @@ -183,7 +183,6 @@ static int aes_cmac(struct crypto_shash *tfm, const u8 k[16], const u8 *m, } desc->tfm = tfm; - desc->flags = 0; /* Swap key and message from LSB to MSB */ swap_buf(k, tmp, 16); diff --git a/net/sctp/auth.c b/net/sctp/auth.c index 39d72e58b8e5..31569f4809f6 100644 --- a/net/sctp/auth.c +++ b/net/sctp/auth.c @@ -760,7 +760,6 @@ void sctp_auth_calculate_hmac(const struct sctp_association *asoc, SHASH_DESC_ON_STACK(desc, tfm); desc->tfm = tfm; - desc->flags = 0; crypto_shash_digest(desc, (u8 *)auth, end - (unsigned char *)auth, digest); shash_desc_zero(desc); diff --git a/net/sctp/sm_make_chunk.c b/net/sctp/sm_make_chunk.c index d05c57664e36..72e74503f9fc 100644 --- a/net/sctp/sm_make_chunk.c +++ b/net/sctp/sm_make_chunk.c @@ -1684,7 +1684,6 @@ static struct sctp_cookie_param *sctp_pack_cookie( /* Sign the message. */ desc->tfm = sctp_sk(ep->base.sk)->hmac; - desc->flags = 0; err = crypto_shash_setkey(desc->tfm, ep->secret_key, sizeof(ep->secret_key)) ?: @@ -1755,7 +1754,6 @@ struct sctp_association *sctp_unpack_cookie( int err; desc->tfm = sctp_sk(ep->base.sk)->hmac; - desc->flags = 0; err = crypto_shash_setkey(desc->tfm, ep->secret_key, sizeof(ep->secret_key)) ?: diff --git a/net/sunrpc/auth_gss/gss_krb5_crypto.c b/net/sunrpc/auth_gss/gss_krb5_crypto.c index 4f43383971ba..6f2d30d7b766 100644 --- a/net/sunrpc/auth_gss/gss_krb5_crypto.c +++ b/net/sunrpc/auth_gss/gss_krb5_crypto.c @@ -977,7 +977,6 @@ krb5_rc4_setup_seq_key(struct krb5_ctx *kctx, } desc->tfm = hmac; - desc->flags = 0; /* Compute intermediate Kseq from session key */ err = crypto_shash_setkey(hmac, kctx->Ksess, kctx->gk5e->keylength); @@ -1045,7 +1044,6 @@ krb5_rc4_setup_enc_key(struct krb5_ctx *kctx, } desc->tfm = hmac; - desc->flags = 0; /* Compute intermediate Kcrypt from session key */ for (i = 0; i < kctx->gk5e->keylength; i++) diff --git a/net/sunrpc/auth_gss/gss_krb5_mech.c b/net/sunrpc/auth_gss/gss_krb5_mech.c index 56cc85c5bc06..6e5d6d240215 100644 --- a/net/sunrpc/auth_gss/gss_krb5_mech.c +++ b/net/sunrpc/auth_gss/gss_krb5_mech.c @@ -438,7 +438,6 @@ context_derive_keys_rc4(struct krb5_ctx *ctx) } desc->tfm = hmac; - desc->flags = 0; err = crypto_shash_digest(desc, sigkeyconstant, slen, ctx->cksum); kzfree(desc); diff --git a/net/wireless/lib80211_crypt_tkip.c b/net/wireless/lib80211_crypt_tkip.c index 35f06563207d..11eaa5956f00 100644 --- a/net/wireless/lib80211_crypt_tkip.c +++ b/net/wireless/lib80211_crypt_tkip.c @@ -501,7 +501,6 @@ static int michael_mic(struct crypto_shash *tfm_michael, u8 *key, u8 *hdr, } desc->tfm = tfm_michael; - desc->flags = 0; if (crypto_shash_setkey(tfm_michael, key, 8)) return -1; diff --git a/security/apparmor/crypto.c b/security/apparmor/crypto.c index af03d98c7552..baba63bc66b1 100644 --- a/security/apparmor/crypto.c +++ b/security/apparmor/crypto.c @@ -43,7 +43,6 @@ char *aa_calc_hash(void *data, size_t len) goto fail; desc->tfm = apparmor_tfm; - desc->flags = 0; error = crypto_shash_init(desc); if (error) @@ -81,7 +80,6 @@ int aa_calc_profile_hash(struct aa_profile *profile, u32 version, void *start, goto fail; desc->tfm = apparmor_tfm; - desc->flags = 0; error = crypto_shash_init(desc); if (error) diff --git a/security/integrity/evm/evm_crypto.c b/security/integrity/evm/evm_crypto.c index c37d08118af5..e11564eb645b 100644 --- a/security/integrity/evm/evm_crypto.c +++ b/security/integrity/evm/evm_crypto.c @@ -124,7 +124,6 @@ out: return ERR_PTR(-ENOMEM); desc->tfm = *tfm; - desc->flags = CRYPTO_TFM_REQ_MAY_SLEEP; rc = crypto_shash_init(desc); if (rc) { diff --git a/security/integrity/ima/ima_crypto.c b/security/integrity/ima/ima_crypto.c index 16a4f45863b1..a32878e10ebc 100644 --- a/security/integrity/ima/ima_crypto.c +++ b/security/integrity/ima/ima_crypto.c @@ -333,7 +333,6 @@ static int ima_calc_file_hash_tfm(struct file *file, SHASH_DESC_ON_STACK(shash, tfm); shash->tfm = tfm; - shash->flags = 0; hash->length = crypto_shash_digestsize(tfm); @@ -469,7 +468,6 @@ static int ima_calc_field_array_hash_tfm(struct ima_field_data *field_data, int rc, i; shash->tfm = tfm; - shash->flags = 0; hash->length = crypto_shash_digestsize(tfm); @@ -591,7 +589,6 @@ static int calc_buffer_shash_tfm(const void *buf, loff_t size, int rc; shash->tfm = tfm; - shash->flags = 0; hash->length = crypto_shash_digestsize(tfm); @@ -664,7 +661,6 @@ static int __init ima_calc_boot_aggregate_tfm(char *digest, SHASH_DESC_ON_STACK(shash, tfm); shash->tfm = tfm; - shash->flags = 0; rc = crypto_shash_init(shash); if (rc != 0) diff --git a/security/keys/dh.c b/security/keys/dh.c index 711e89d8c415..23f95dec771b 100644 --- a/security/keys/dh.c +++ b/security/keys/dh.c @@ -112,7 +112,6 @@ static int kdf_alloc(struct kdf_sdesc **sdesc_ret, char *hashname) if (!sdesc) goto out_free_tfm; sdesc->shash.tfm = tfm; - sdesc->shash.flags = 0x0; *sdesc_ret = sdesc; diff --git a/security/keys/encrypted-keys/encrypted.c b/security/keys/encrypted-keys/encrypted.c index 347108f660a1..1b1456b21a93 100644 --- a/security/keys/encrypted-keys/encrypted.c +++ b/security/keys/encrypted-keys/encrypted.c @@ -333,7 +333,6 @@ static int calc_hash(struct crypto_shash *tfm, u8 *digest, int err; desc->tfm = tfm; - desc->flags = 0; err = crypto_shash_digest(desc, buf, buflen, digest); shash_desc_zero(desc); diff --git a/security/keys/trusted.c b/security/keys/trusted.c index bcc9c6ead7fd..45ffd9e53937 100644 --- a/security/keys/trusted.c +++ b/security/keys/trusted.c @@ -55,7 +55,6 @@ static struct sdesc *init_sdesc(struct crypto_shash *alg) if (!sdesc) return ERR_PTR(-ENOMEM); sdesc->shash.tfm = alg; - sdesc->shash.flags = 0x0; return sdesc; } -- cgit v1.2.3 From 5c9ae5a87573d38cfc4c740aafda2fa6ce06e401 Mon Sep 17 00:00:00 2001 From: Ajay Gupta Date: Tue, 23 Apr 2019 17:21:47 +0300 Subject: usb: typec: ucsi: ccg: add firmware flashing support CCGx has two copies of the firmware in addition to the bootloader. If the device is running FW1, FW2 can be updated with the new version. Dual firmware mode allows the CCG device to stay in a PD contract and support USB PD and Type-C functionality while a firmware update is in progress. First we read the currently flashed firmware version of both primary and secondary firmware and then compare it with version of firmware file to determine if flashing is required. Command framework is added to support sending commands to CCGx controller. We wait for response after sending the command and then read the response from RAB_RESPONSE register. Below commands are supported, - ENTER_FLASHING - RESET - PDPORT_ENABLE - JUMP_TO_BOOT - FLASH_ROW_RW - VALIDATE_FW Command specific mutex lock is also added to sync between driver and user threads. PD port number information is added which is required while sending PD_PORT_ENABLE command Signed-off-by: Ajay Gupta [ heikki: Added ABI documentation. ] Signed-off-by: Heikki Krogerus Signed-off-by: Greg Kroah-Hartman --- Documentation/ABI/testing/sysfs-driver-ucsi-ccg | 6 + drivers/usb/typec/ucsi/ucsi_ccg.c | 827 +++++++++++++++++++++++- 2 files changed, 820 insertions(+), 13 deletions(-) create mode 100644 Documentation/ABI/testing/sysfs-driver-ucsi-ccg (limited to 'Documentation') diff --git a/Documentation/ABI/testing/sysfs-driver-ucsi-ccg b/Documentation/ABI/testing/sysfs-driver-ucsi-ccg new file mode 100644 index 000000000000..45cf62ad89e9 --- /dev/null +++ b/Documentation/ABI/testing/sysfs-driver-ucsi-ccg @@ -0,0 +1,6 @@ +What: /sys/bus/i2c/drivers/ucsi_ccg/.../do_flash +Date: May 2019 +Contact: Ajay Gupta +Description: + Tell the driver for Cypress CCGx Type-C controller to attempt + firmware upgrade by writing [Yy1] to the file. diff --git a/drivers/usb/typec/ucsi/ucsi_ccg.c b/drivers/usb/typec/ucsi/ucsi_ccg.c index 3884fb41c72e..4632b91a04a6 100644 --- a/drivers/usb/typec/ucsi/ucsi_ccg.c +++ b/drivers/usb/typec/ucsi/ucsi_ccg.c @@ -9,6 +9,7 @@ */ #include #include +#include #include #include #include @@ -24,6 +25,73 @@ enum enum_fw_mode { FW_INVALID, }; +#define CCGX_RAB_DEVICE_MODE 0x0000 +#define CCGX_RAB_INTR_REG 0x0006 +#define DEV_INT BIT(0) +#define PORT0_INT BIT(1) +#define PORT1_INT BIT(2) +#define UCSI_READ_INT BIT(7) +#define CCGX_RAB_JUMP_TO_BOOT 0x0007 +#define TO_BOOT 'J' +#define TO_ALT_FW 'A' +#define CCGX_RAB_RESET_REQ 0x0008 +#define RESET_SIG 'R' +#define CMD_RESET_I2C 0x0 +#define CMD_RESET_DEV 0x1 +#define CCGX_RAB_ENTER_FLASHING 0x000A +#define FLASH_ENTER_SIG 'P' +#define CCGX_RAB_VALIDATE_FW 0x000B +#define CCGX_RAB_FLASH_ROW_RW 0x000C +#define FLASH_SIG 'F' +#define FLASH_RD_CMD 0x0 +#define FLASH_WR_CMD 0x1 +#define FLASH_FWCT1_WR_CMD 0x2 +#define FLASH_FWCT2_WR_CMD 0x3 +#define FLASH_FWCT_SIG_WR_CMD 0x4 +#define CCGX_RAB_READ_ALL_VER 0x0010 +#define CCGX_RAB_READ_FW2_VER 0x0020 +#define CCGX_RAB_UCSI_CONTROL 0x0039 +#define CCGX_RAB_UCSI_CONTROL_START BIT(0) +#define CCGX_RAB_UCSI_CONTROL_STOP BIT(1) +#define CCGX_RAB_UCSI_DATA_BLOCK(offset) (0xf000 | ((offset) & 0xff)) +#define REG_FLASH_RW_MEM 0x0200 +#define DEV_REG_IDX CCGX_RAB_DEVICE_MODE +#define CCGX_RAB_PDPORT_ENABLE 0x002C +#define PDPORT_1 BIT(0) +#define PDPORT_2 BIT(1) +#define CCGX_RAB_RESPONSE 0x007E +#define ASYNC_EVENT BIT(7) + +/* CCGx events & async msg codes */ +#define RESET_COMPLETE 0x80 +#define EVENT_INDEX RESET_COMPLETE +#define PORT_CONNECT_DET 0x84 +#define PORT_DISCONNECT_DET 0x85 +#define ROLE_SWAP_COMPELETE 0x87 + +/* ccg firmware */ +#define CYACD_LINE_SIZE 527 +#define CCG4_ROW_SIZE 256 +#define FW1_METADATA_ROW 0x1FF +#define FW2_METADATA_ROW 0x1FE +#define FW_CFG_TABLE_SIG_SIZE 256 + +static int secondary_fw_min_ver = 41; + +enum enum_flash_mode { + SECONDARY_BL, /* update secondary using bootloader */ + PRIMARY, /* update primary using secondary */ + SECONDARY, /* update secondary using primary */ + FLASH_NOT_NEEDED, /* update not required */ + FLASH_INVALID, +}; + +static const char * const ccg_fw_names[] = { + "ccg_boot.cyacd", + "ccg_primary.cyacd", + "ccg_secondary.cyacd" +}; + struct ccg_dev_info { #define CCG_DEVINFO_FWMODE_SHIFT (0) #define CCG_DEVINFO_FWMODE_MASK (0x3 << CCG_DEVINFO_FWMODE_SHIFT) @@ -50,6 +118,50 @@ struct version_info { struct version_format app; }; +struct fw_config_table { + u32 identity; + u16 table_size; + u8 fwct_version; + u8 is_key_change; + u8 guid[16]; + struct version_format base; + struct version_format app; + u8 primary_fw_digest[32]; + u32 key_exp_length; + u8 key_modulus[256]; + u8 key_exp[4]; +}; + +/* CCGx response codes */ +enum ccg_resp_code { + CMD_NO_RESP = 0x00, + CMD_SUCCESS = 0x02, + FLASH_DATA_AVAILABLE = 0x03, + CMD_INVALID = 0x05, + FLASH_UPDATE_FAIL = 0x07, + INVALID_FW = 0x08, + INVALID_ARG = 0x09, + CMD_NOT_SUPPORT = 0x0A, + TRANSACTION_FAIL = 0x0C, + PD_CMD_FAIL = 0x0D, + UNDEF_ERROR = 0x0F, + INVALID_RESP = 0x10, +}; + +#define CCG_EVENT_MAX (EVENT_INDEX + 43) + +struct ccg_cmd { + u16 reg; + u32 data; + int len; + u32 delay; /* ms delay for cmd timeout */ +}; + +struct ccg_resp { + u8 code; + u8 length; +}; + struct ucsi_ccg { struct device *dev; struct ucsi *ucsi; @@ -58,16 +170,20 @@ struct ucsi_ccg { struct ccg_dev_info info; /* version info for boot, primary and secondary */ struct version_info version[FW2 + 1]; -}; + /* CCG HPI communication flags */ + unsigned long flags; +#define RESET_PENDING 0 +#define DEV_CMD_PENDING 1 + struct ccg_resp dev_resp; + u8 cmd_resp; + int port_num; + int irq; + struct work_struct work; + struct mutex lock; /* to sync between user and driver thread */ -#define CCGX_RAB_DEVICE_MODE 0x0000 -#define CCGX_RAB_INTR_REG 0x0006 -#define CCGX_RAB_READ_ALL_VER 0x0010 -#define CCGX_RAB_READ_FW2_VER 0x0020 -#define CCGX_RAB_UCSI_CONTROL 0x0039 -#define CCGX_RAB_UCSI_CONTROL_START BIT(0) -#define CCGX_RAB_UCSI_CONTROL_STOP BIT(1) -#define CCGX_RAB_UCSI_DATA_BLOCK(offset) (0xf000 | ((offset) & 0xff)) + /* fw build with vendor information */ + u16 fw_build; +}; static int ccg_read(struct ucsi_ccg *uc, u16 rab, u8 *data, u32 len) { @@ -276,6 +392,669 @@ static int get_fw_info(struct ucsi_ccg *uc) return 0; } +static inline bool invalid_async_evt(int code) +{ + return (code >= CCG_EVENT_MAX) || (code < EVENT_INDEX); +} + +static void ccg_process_response(struct ucsi_ccg *uc) +{ + struct device *dev = uc->dev; + + if (uc->dev_resp.code & ASYNC_EVENT) { + if (uc->dev_resp.code == RESET_COMPLETE) { + if (test_bit(RESET_PENDING, &uc->flags)) + uc->cmd_resp = uc->dev_resp.code; + get_fw_info(uc); + } + if (invalid_async_evt(uc->dev_resp.code)) + dev_err(dev, "invalid async evt %d\n", + uc->dev_resp.code); + } else { + if (test_bit(DEV_CMD_PENDING, &uc->flags)) { + uc->cmd_resp = uc->dev_resp.code; + clear_bit(DEV_CMD_PENDING, &uc->flags); + } else { + dev_err(dev, "dev resp 0x%04x but no cmd pending\n", + uc->dev_resp.code); + } + } +} + +static int ccg_read_response(struct ucsi_ccg *uc) +{ + unsigned long target = jiffies + msecs_to_jiffies(1000); + struct device *dev = uc->dev; + u8 intval; + int status; + + /* wait for interrupt status to get updated */ + do { + status = ccg_read(uc, CCGX_RAB_INTR_REG, &intval, + sizeof(intval)); + if (status < 0) + return status; + + if (intval & DEV_INT) + break; + usleep_range(500, 600); + } while (time_is_after_jiffies(target)); + + if (time_is_before_jiffies(target)) { + dev_err(dev, "response timeout error\n"); + return -ETIME; + } + + status = ccg_read(uc, CCGX_RAB_RESPONSE, (u8 *)&uc->dev_resp, + sizeof(uc->dev_resp)); + if (status < 0) + return status; + + status = ccg_write(uc, CCGX_RAB_INTR_REG, &intval, sizeof(intval)); + if (status < 0) + return status; + + return 0; +} + +/* Caller must hold uc->lock */ +static int ccg_send_command(struct ucsi_ccg *uc, struct ccg_cmd *cmd) +{ + struct device *dev = uc->dev; + int ret; + + switch (cmd->reg & 0xF000) { + case DEV_REG_IDX: + set_bit(DEV_CMD_PENDING, &uc->flags); + break; + default: + dev_err(dev, "invalid cmd register\n"); + break; + } + + ret = ccg_write(uc, cmd->reg, (u8 *)&cmd->data, cmd->len); + if (ret < 0) + return ret; + + msleep(cmd->delay); + + ret = ccg_read_response(uc); + if (ret < 0) { + dev_err(dev, "response read error\n"); + switch (cmd->reg & 0xF000) { + case DEV_REG_IDX: + clear_bit(DEV_CMD_PENDING, &uc->flags); + break; + default: + dev_err(dev, "invalid cmd register\n"); + break; + } + return -EIO; + } + ccg_process_response(uc); + + return uc->cmd_resp; +} + +static int ccg_cmd_enter_flashing(struct ucsi_ccg *uc) +{ + struct ccg_cmd cmd; + int ret; + + cmd.reg = CCGX_RAB_ENTER_FLASHING; + cmd.data = FLASH_ENTER_SIG; + cmd.len = 1; + cmd.delay = 50; + + mutex_lock(&uc->lock); + + ret = ccg_send_command(uc, &cmd); + + mutex_unlock(&uc->lock); + + if (ret != CMD_SUCCESS) { + dev_err(uc->dev, "enter flashing failed ret=%d\n", ret); + return ret; + } + + return 0; +} + +static int ccg_cmd_reset(struct ucsi_ccg *uc) +{ + struct ccg_cmd cmd; + u8 *p; + int ret; + + p = (u8 *)&cmd.data; + cmd.reg = CCGX_RAB_RESET_REQ; + p[0] = RESET_SIG; + p[1] = CMD_RESET_DEV; + cmd.len = 2; + cmd.delay = 5000; + + mutex_lock(&uc->lock); + + set_bit(RESET_PENDING, &uc->flags); + + ret = ccg_send_command(uc, &cmd); + if (ret != RESET_COMPLETE) + goto err_clear_flag; + + ret = 0; + +err_clear_flag: + clear_bit(RESET_PENDING, &uc->flags); + + mutex_unlock(&uc->lock); + + return ret; +} + +static int ccg_cmd_port_control(struct ucsi_ccg *uc, bool enable) +{ + struct ccg_cmd cmd; + int ret; + + cmd.reg = CCGX_RAB_PDPORT_ENABLE; + if (enable) + cmd.data = (uc->port_num == 1) ? + PDPORT_1 : (PDPORT_1 | PDPORT_2); + else + cmd.data = 0x0; + cmd.len = 1; + cmd.delay = 10; + + mutex_lock(&uc->lock); + + ret = ccg_send_command(uc, &cmd); + + mutex_unlock(&uc->lock); + + if (ret != CMD_SUCCESS) { + dev_err(uc->dev, "port control failed ret=%d\n", ret); + return ret; + } + return 0; +} + +static int ccg_cmd_jump_boot_mode(struct ucsi_ccg *uc, int bl_mode) +{ + struct ccg_cmd cmd; + int ret; + + cmd.reg = CCGX_RAB_JUMP_TO_BOOT; + + if (bl_mode) + cmd.data = TO_BOOT; + else + cmd.data = TO_ALT_FW; + + cmd.len = 1; + cmd.delay = 100; + + mutex_lock(&uc->lock); + + set_bit(RESET_PENDING, &uc->flags); + + ret = ccg_send_command(uc, &cmd); + if (ret != RESET_COMPLETE) + goto err_clear_flag; + + ret = 0; + +err_clear_flag: + clear_bit(RESET_PENDING, &uc->flags); + + mutex_unlock(&uc->lock); + + return ret; +} + +static int +ccg_cmd_write_flash_row(struct ucsi_ccg *uc, u16 row, + const void *data, u8 fcmd) +{ + struct i2c_client *client = uc->client; + struct ccg_cmd cmd; + u8 buf[CCG4_ROW_SIZE + 2]; + u8 *p; + int ret; + + /* Copy the data into the flash read/write memory. */ + put_unaligned_le16(REG_FLASH_RW_MEM, buf); + + memcpy(buf + 2, data, CCG4_ROW_SIZE); + + mutex_lock(&uc->lock); + + ret = i2c_master_send(client, buf, CCG4_ROW_SIZE + 2); + if (ret != CCG4_ROW_SIZE + 2) { + dev_err(uc->dev, "REG_FLASH_RW_MEM write fail %d\n", ret); + return ret < 0 ? ret : -EIO; + } + + /* Use the FLASH_ROW_READ_WRITE register to trigger */ + /* writing of data to the desired flash row */ + p = (u8 *)&cmd.data; + cmd.reg = CCGX_RAB_FLASH_ROW_RW; + p[0] = FLASH_SIG; + p[1] = fcmd; + put_unaligned_le16(row, &p[2]); + cmd.len = 4; + cmd.delay = 50; + if (fcmd == FLASH_FWCT_SIG_WR_CMD) + cmd.delay += 400; + if (row == 510) + cmd.delay += 220; + ret = ccg_send_command(uc, &cmd); + + mutex_unlock(&uc->lock); + + if (ret != CMD_SUCCESS) { + dev_err(uc->dev, "write flash row failed ret=%d\n", ret); + return ret; + } + + return 0; +} + +static int ccg_cmd_validate_fw(struct ucsi_ccg *uc, unsigned int fwid) +{ + struct ccg_cmd cmd; + int ret; + + cmd.reg = CCGX_RAB_VALIDATE_FW; + cmd.data = fwid; + cmd.len = 1; + cmd.delay = 500; + + mutex_lock(&uc->lock); + + ret = ccg_send_command(uc, &cmd); + + mutex_unlock(&uc->lock); + + if (ret != CMD_SUCCESS) + return ret; + + return 0; +} + +static bool ccg_check_vendor_version(struct ucsi_ccg *uc, + struct version_format *app, + struct fw_config_table *fw_cfg) +{ + struct device *dev = uc->dev; + + /* Check if the fw build is for supported vendors */ + if (le16_to_cpu(app->build) != uc->fw_build) { + dev_info(dev, "current fw is not from supported vendor\n"); + return false; + } + + /* Check if the new fw build is for supported vendors */ + if (le16_to_cpu(fw_cfg->app.build) != uc->fw_build) { + dev_info(dev, "new fw is not from supported vendor\n"); + return false; + } + return true; +} + +static bool ccg_check_fw_version(struct ucsi_ccg *uc, const char *fw_name, + struct version_format *app) +{ + const struct firmware *fw = NULL; + struct device *dev = uc->dev; + struct fw_config_table fw_cfg; + u32 cur_version, new_version; + bool is_later = false; + + if (request_firmware(&fw, fw_name, dev) != 0) { + dev_err(dev, "error: Failed to open cyacd file %s\n", fw_name); + return false; + } + + /* + * check if signed fw + * last part of fw image is fw cfg table and signature + */ + if (fw->size < sizeof(fw_cfg) + FW_CFG_TABLE_SIG_SIZE) + goto out_release_firmware; + + memcpy((uint8_t *)&fw_cfg, fw->data + fw->size - + sizeof(fw_cfg) - FW_CFG_TABLE_SIG_SIZE, sizeof(fw_cfg)); + + if (fw_cfg.identity != ('F' | 'W' << 8 | 'C' << 16 | 'T' << 24)) { + dev_info(dev, "not a signed image\n"); + goto out_release_firmware; + } + + /* compare input version with FWCT version */ + cur_version = le16_to_cpu(app->build) | app->patch << 16 | + app->ver << 24; + + new_version = le16_to_cpu(fw_cfg.app.build) | fw_cfg.app.patch << 16 | + fw_cfg.app.ver << 24; + + if (!ccg_check_vendor_version(uc, app, &fw_cfg)) + goto out_release_firmware; + + if (new_version > cur_version) + is_later = true; + +out_release_firmware: + release_firmware(fw); + return is_later; +} + +static int ccg_fw_update_needed(struct ucsi_ccg *uc, + enum enum_flash_mode *mode) +{ + struct device *dev = uc->dev; + int err; + struct version_info version[3]; + + err = ccg_read(uc, CCGX_RAB_DEVICE_MODE, (u8 *)(&uc->info), + sizeof(uc->info)); + if (err) { + dev_err(dev, "read device mode failed\n"); + return err; + } + + err = ccg_read(uc, CCGX_RAB_READ_ALL_VER, (u8 *)version, + sizeof(version)); + if (err) { + dev_err(dev, "read device mode failed\n"); + return err; + } + + if (memcmp(&version[FW1], "\0\0\0\0\0\0\0\0", + sizeof(struct version_info)) == 0) { + dev_info(dev, "secondary fw is not flashed\n"); + *mode = SECONDARY_BL; + } else if (le16_to_cpu(version[FW1].base.build) < + secondary_fw_min_ver) { + dev_info(dev, "secondary fw version is too low (< %d)\n", + secondary_fw_min_ver); + *mode = SECONDARY; + } else if (memcmp(&version[FW2], "\0\0\0\0\0\0\0\0", + sizeof(struct version_info)) == 0) { + dev_info(dev, "primary fw is not flashed\n"); + *mode = PRIMARY; + } else if (ccg_check_fw_version(uc, ccg_fw_names[PRIMARY], + &version[FW2].app)) { + dev_info(dev, "found primary fw with later version\n"); + *mode = PRIMARY; + } else { + dev_info(dev, "secondary and primary fw are the latest\n"); + *mode = FLASH_NOT_NEEDED; + } + return 0; +} + +static int do_flash(struct ucsi_ccg *uc, enum enum_flash_mode mode) +{ + struct device *dev = uc->dev; + const struct firmware *fw = NULL; + const char *p, *s; + const char *eof; + int err, row, len, line_sz, line_cnt = 0; + unsigned long start_time = jiffies; + struct fw_config_table fw_cfg; + u8 fw_cfg_sig[FW_CFG_TABLE_SIG_SIZE]; + u8 *wr_buf; + + err = request_firmware(&fw, ccg_fw_names[mode], dev); + if (err) { + dev_err(dev, "request %s failed err=%d\n", + ccg_fw_names[mode], err); + return err; + } + + if (((uc->info.mode & CCG_DEVINFO_FWMODE_MASK) >> + CCG_DEVINFO_FWMODE_SHIFT) == FW2) { + err = ccg_cmd_port_control(uc, false); + if (err < 0) + goto release_fw; + err = ccg_cmd_jump_boot_mode(uc, 0); + if (err < 0) + goto release_fw; + } + + eof = fw->data + fw->size; + + /* + * check if signed fw + * last part of fw image is fw cfg table and signature + */ + if (fw->size < sizeof(fw_cfg) + sizeof(fw_cfg_sig)) + goto not_signed_fw; + + memcpy((uint8_t *)&fw_cfg, fw->data + fw->size - + sizeof(fw_cfg) - sizeof(fw_cfg_sig), sizeof(fw_cfg)); + + if (fw_cfg.identity != ('F' | ('W' << 8) | ('C' << 16) | ('T' << 24))) { + dev_info(dev, "not a signed image\n"); + goto not_signed_fw; + } + eof = fw->data + fw->size - sizeof(fw_cfg) - sizeof(fw_cfg_sig); + + memcpy((uint8_t *)&fw_cfg_sig, + fw->data + fw->size - sizeof(fw_cfg_sig), sizeof(fw_cfg_sig)); + + /* flash fw config table and signature first */ + err = ccg_cmd_write_flash_row(uc, 0, (u8 *)&fw_cfg, + FLASH_FWCT1_WR_CMD); + if (err) + goto release_fw; + + err = ccg_cmd_write_flash_row(uc, 0, (u8 *)&fw_cfg + CCG4_ROW_SIZE, + FLASH_FWCT2_WR_CMD); + if (err) + goto release_fw; + + err = ccg_cmd_write_flash_row(uc, 0, &fw_cfg_sig, + FLASH_FWCT_SIG_WR_CMD); + if (err) + goto release_fw; + +not_signed_fw: + wr_buf = kzalloc(CCG4_ROW_SIZE + 4, GFP_KERNEL); + if (!wr_buf) + return -ENOMEM; + + err = ccg_cmd_enter_flashing(uc); + if (err) + goto release_mem; + + /***************************************************************** + * CCG firmware image (.cyacd) file line format + * + * :00rrrrllll[dd....]cc/r/n + * + * :00 header + * rrrr is row number to flash (4 char) + * llll is data len to flash (4 char) + * dd is a data field represents one byte of data (512 char) + * cc is checksum (2 char) + * \r\n newline + * + * Total length: 3 + 4 + 4 + 512 + 2 + 2 = 527 + * + *****************************************************************/ + + p = strnchr(fw->data, fw->size, ':'); + while (p < eof) { + s = strnchr(p + 1, eof - p - 1, ':'); + + if (!s) + s = eof; + + line_sz = s - p; + + if (line_sz != CYACD_LINE_SIZE) { + dev_err(dev, "Bad FW format line_sz=%d\n", line_sz); + err = -EINVAL; + goto release_mem; + } + + if (hex2bin(wr_buf, p + 3, CCG4_ROW_SIZE + 4)) { + err = -EINVAL; + goto release_mem; + } + + row = get_unaligned_be16(wr_buf); + len = get_unaligned_be16(&wr_buf[2]); + + if (len != CCG4_ROW_SIZE) { + err = -EINVAL; + goto release_mem; + } + + err = ccg_cmd_write_flash_row(uc, row, wr_buf + 4, + FLASH_WR_CMD); + if (err) + goto release_mem; + + line_cnt++; + p = s; + } + + dev_info(dev, "total %d row flashed. time: %dms\n", + line_cnt, jiffies_to_msecs(jiffies - start_time)); + + err = ccg_cmd_validate_fw(uc, (mode == PRIMARY) ? FW2 : FW1); + if (err) + dev_err(dev, "%s validation failed err=%d\n", + (mode == PRIMARY) ? "FW2" : "FW1", err); + else + dev_info(dev, "%s validated\n", + (mode == PRIMARY) ? "FW2" : "FW1"); + + err = ccg_cmd_port_control(uc, false); + if (err < 0) + goto release_mem; + + err = ccg_cmd_reset(uc); + if (err < 0) + goto release_mem; + + err = ccg_cmd_port_control(uc, true); + if (err < 0) + goto release_mem; + +release_mem: + kfree(wr_buf); + +release_fw: + release_firmware(fw); + return err; +} + +/******************************************************************************* + * CCG4 has two copies of the firmware in addition to the bootloader. + * If the device is running FW1, FW2 can be updated with the new version. + * Dual firmware mode allows the CCG device to stay in a PD contract and support + * USB PD and Type-C functionality while a firmware update is in progress. + ******************************************************************************/ +static int ccg_fw_update(struct ucsi_ccg *uc, enum enum_flash_mode flash_mode) +{ + int err; + + while (flash_mode != FLASH_NOT_NEEDED) { + err = do_flash(uc, flash_mode); + if (err < 0) + return err; + err = ccg_fw_update_needed(uc, &flash_mode); + if (err < 0) + return err; + } + dev_info(uc->dev, "CCG FW update successful\n"); + + return err; +} + +static int ccg_restart(struct ucsi_ccg *uc) +{ + struct device *dev = uc->dev; + int status; + + status = ucsi_ccg_init(uc); + if (status < 0) { + dev_err(dev, "ucsi_ccg_start fail, err=%d\n", status); + return status; + } + + status = request_threaded_irq(uc->irq, NULL, ccg_irq_handler, + IRQF_ONESHOT | IRQF_TRIGGER_HIGH, + dev_name(dev), uc); + if (status < 0) { + dev_err(dev, "request_threaded_irq failed - %d\n", status); + return status; + } + + uc->ucsi = ucsi_register_ppm(dev, &uc->ppm); + if (IS_ERR(uc->ucsi)) { + dev_err(uc->dev, "ucsi_register_ppm failed\n"); + return PTR_ERR(uc->ucsi); + } + + return 0; +} + +static void ccg_update_firmware(struct work_struct *work) +{ + struct ucsi_ccg *uc = container_of(work, struct ucsi_ccg, work); + enum enum_flash_mode flash_mode; + int status; + + status = ccg_fw_update_needed(uc, &flash_mode); + if (status < 0) + return; + + if (flash_mode != FLASH_NOT_NEEDED) { + ucsi_unregister_ppm(uc->ucsi); + free_irq(uc->irq, uc); + + ccg_fw_update(uc, flash_mode); + ccg_restart(uc); + } +} + +static ssize_t do_flash_store(struct device *dev, + struct device_attribute *attr, + const char *buf, size_t n) +{ + struct ucsi_ccg *uc = i2c_get_clientdata(to_i2c_client(dev)); + bool flash; + + if (kstrtobool(buf, &flash)) + return -EINVAL; + + if (!flash) + return n; + + if (uc->fw_build == 0x0) { + dev_err(dev, "fail to flash FW due to missing FW build info\n"); + return -EINVAL; + } + + schedule_work(&uc->work); + return n; +} + +static DEVICE_ATTR_WO(do_flash); + +static struct attribute *ucsi_ccg_sysfs_attrs[] = { + &dev_attr_do_flash.attr, + NULL, +}; + +static struct attribute_group ucsi_ccg_attr_group = { + .attrs = ucsi_ccg_sysfs_attrs, +}; + static int ucsi_ccg_probe(struct i2c_client *client, const struct i2c_device_id *id) { @@ -296,6 +1075,14 @@ static int ucsi_ccg_probe(struct i2c_client *client, uc->ppm.sync = ucsi_ccg_sync; uc->dev = dev; uc->client = client; + mutex_init(&uc->lock); + INIT_WORK(&uc->work, ccg_update_firmware); + + /* Only fail FW flashing when FW build information is not provided */ + status = device_property_read_u16(dev, "ccgx,firmware-build", + &uc->fw_build); + if (status) + dev_err(uc->dev, "failed to get FW build information\n"); /* reset ccg device and initialize ucsi */ status = ucsi_ccg_init(uc); @@ -310,15 +1097,21 @@ static int ucsi_ccg_probe(struct i2c_client *client, return status; } - status = devm_request_threaded_irq(dev, client->irq, NULL, - ccg_irq_handler, - IRQF_ONESHOT | IRQF_TRIGGER_HIGH, - dev_name(dev), uc); + uc->port_num = 1; + + if (uc->info.mode & CCG_DEVINFO_PDPORTS_MASK) + uc->port_num++; + + status = request_threaded_irq(client->irq, NULL, ccg_irq_handler, + IRQF_ONESHOT | IRQF_TRIGGER_HIGH, + dev_name(dev), uc); if (status < 0) { dev_err(uc->dev, "request_threaded_irq failed - %d\n", status); return status; } + uc->irq = client->irq; + uc->ucsi = ucsi_register_ppm(dev, &uc->ppm); if (IS_ERR(uc->ucsi)) { dev_err(uc->dev, "ucsi_register_ppm failed\n"); @@ -335,6 +1128,11 @@ static int ucsi_ccg_probe(struct i2c_client *client, } i2c_set_clientdata(client, uc); + + status = sysfs_create_group(&uc->dev->kobj, &ucsi_ccg_attr_group); + if (status) + dev_err(uc->dev, "cannot create sysfs group: %d\n", status); + return 0; } @@ -342,7 +1140,10 @@ static int ucsi_ccg_remove(struct i2c_client *client) { struct ucsi_ccg *uc = i2c_get_clientdata(client); + cancel_work_sync(&uc->work); ucsi_unregister_ppm(uc->ucsi); + free_irq(uc->irq, uc); + sysfs_remove_group(&uc->dev->kobj, &ucsi_ccg_attr_group); return 0; } -- cgit v1.2.3 From a4d6a2989dc3f2f2bcd25ca53dd187a1de68ffac Mon Sep 17 00:00:00 2001 From: Raul E Rangel Date: Fri, 19 Apr 2019 09:30:22 -0600 Subject: usb/hcd: Send a uevent signaling that the host controller had died This change will send an OFFLINE event to udev with the ERROR=DEAD environment variable set when the HC dies. By notifying user space the appropriate policies can be applied. i.e., * Collect error logs. * Notify the user that USB is no longer functional. * Perform a graceful reboot. Reported-by: kbuild test robot Signed-off-by: Raul E Rangel Signed-off-by: Greg Kroah-Hartman --- Documentation/ABI/testing/usb-uevent | 27 +++++++++++++++++++++++++++ drivers/usb/core/hcd.c | 24 ++++++++++++++++++++++++ include/linux/usb/hcd.h | 1 + 3 files changed, 52 insertions(+) create mode 100644 Documentation/ABI/testing/usb-uevent (limited to 'Documentation') diff --git a/Documentation/ABI/testing/usb-uevent b/Documentation/ABI/testing/usb-uevent new file mode 100644 index 000000000000..d35c3cad892c --- /dev/null +++ b/Documentation/ABI/testing/usb-uevent @@ -0,0 +1,27 @@ +What: Raise a uevent when a USB Host Controller has died +Date: 2019-04-17 +KernelVersion: 5.2 +Contact: linux-usb@vger.kernel.org +Description: When the USB Host Controller has entered a state where it is no + longer functional a uevent will be raised. The uevent will + contain ACTION=offline and ERROR=DEAD. + + Here is an example taken using udevadm monitor -p: + + KERNEL[130.428945] offline /devices/pci0000:00/0000:00:10.0/usb2 (usb) + ACTION=offline + BUSNUM=002 + DEVNAME=/dev/bus/usb/002/001 + DEVNUM=001 + DEVPATH=/devices/pci0000:00/0000:00:10.0/usb2 + DEVTYPE=usb_device + DRIVER=usb + ERROR=DEAD + MAJOR=189 + MINOR=128 + PRODUCT=1d6b/2/414 + SEQNUM=2168 + SUBSYSTEM=usb + TYPE=9/0/1 + +Users: chromium-os-dev@chromium.org diff --git a/drivers/usb/core/hcd.c b/drivers/usb/core/hcd.c index 00655424baf5..94d22551fc1b 100644 --- a/drivers/usb/core/hcd.c +++ b/drivers/usb/core/hcd.c @@ -2435,6 +2435,19 @@ EXPORT_SYMBOL_GPL(usb_hcd_irq); /*-------------------------------------------------------------------------*/ +/* Workqueue routine for when the root-hub has died. */ +static void hcd_died_work(struct work_struct *work) +{ + struct usb_hcd *hcd = container_of(work, struct usb_hcd, died_work); + static char *env[] = { + "ERROR=DEAD", + NULL + }; + + /* Notify user space that the host controller has died */ + kobject_uevent_env(&hcd->self.root_hub->dev.kobj, KOBJ_OFFLINE, env); +} + /** * usb_hc_died - report abnormal shutdown of a host controller (bus glue) * @hcd: pointer to the HCD representing the controller @@ -2475,6 +2488,13 @@ void usb_hc_died (struct usb_hcd *hcd) usb_kick_hub_wq(hcd->self.root_hub); } } + + /* Handle the case where this function gets called with a shared HCD */ + if (usb_hcd_is_primary_hcd(hcd)) + schedule_work(&hcd->died_work); + else + schedule_work(&hcd->primary_hcd->died_work); + spin_unlock_irqrestore (&hcd_root_hub_lock, flags); /* Make sure that the other roothub is also deallocated. */ } @@ -2542,6 +2562,8 @@ struct usb_hcd *__usb_create_hcd(const struct hc_driver *driver, INIT_WORK(&hcd->wakeup_work, hcd_resume_work); #endif + INIT_WORK(&hcd->died_work, hcd_died_work); + hcd->driver = driver; hcd->speed = driver->flags & HCD_MASK; hcd->product_desc = (driver->product_desc) ? driver->product_desc : @@ -2895,6 +2917,7 @@ error_create_attr_group: #ifdef CONFIG_PM cancel_work_sync(&hcd->wakeup_work); #endif + cancel_work_sync(&hcd->died_work); mutex_lock(&usb_bus_idr_lock); usb_disconnect(&rhdev); /* Sets rhdev to NULL */ mutex_unlock(&usb_bus_idr_lock); @@ -2955,6 +2978,7 @@ void usb_remove_hcd(struct usb_hcd *hcd) #ifdef CONFIG_PM cancel_work_sync(&hcd->wakeup_work); #endif + cancel_work_sync(&hcd->died_work); mutex_lock(&usb_bus_idr_lock); usb_disconnect(&rhdev); /* Sets rhdev to NULL */ diff --git a/include/linux/usb/hcd.h b/include/linux/usb/hcd.h index 695931b03684..66a24b13e2ab 100644 --- a/include/linux/usb/hcd.h +++ b/include/linux/usb/hcd.h @@ -98,6 +98,7 @@ struct usb_hcd { #ifdef CONFIG_PM struct work_struct wakeup_work; /* for remote wakeup */ #endif + struct work_struct died_work; /* for when the device dies */ /* * hardware info/state -- cgit v1.2.3 From f137401780278c5a257945330936607701fbd2fd Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Mon, 22 Apr 2019 10:27:22 -0300 Subject: docs: serial: convert docs to ReST and rename to *.rst The converted files are focused at the Kernel internal API, so, this is a good candidate for the kernel API set of books. The conversion is actually: - add blank lines and identation in order to identify paragraphs; - fix tables markups; - add some lists markups; - mark literal blocks; - adjust title markups. At its new index.rst, let's add a :orphan: while this is not linked to the main index.rst file, in order to avoid build warnings. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Greg Kroah-Hartman --- Documentation/serial/README.cycladesZ | 8 - Documentation/serial/cyclades_z.rst | 11 + Documentation/serial/driver | 486 ------------------------- Documentation/serial/driver.rst | 549 ++++++++++++++++++++++++++++ Documentation/serial/index.rst | 32 ++ Documentation/serial/moxa-smartio | 523 --------------------------- Documentation/serial/moxa-smartio.rst | 615 ++++++++++++++++++++++++++++++++ Documentation/serial/n_gsm.rst | 103 ++++++ Documentation/serial/n_gsm.txt | 96 ----- Documentation/serial/rocket.rst | 185 ++++++++++ Documentation/serial/rocket.txt | 189 ---------- Documentation/serial/serial-iso7816.rst | 90 +++++ Documentation/serial/serial-iso7816.txt | 83 ----- Documentation/serial/serial-rs485.rst | 103 ++++++ Documentation/serial/serial-rs485.txt | 95 ----- Documentation/serial/tty.rst | 328 +++++++++++++++++ Documentation/serial/tty.txt | 313 ---------------- MAINTAINERS | 4 +- drivers/tty/Kconfig | 4 +- drivers/tty/serial/ucc_uart.c | 2 +- include/linux/serial_core.h | 2 +- 21 files changed, 2022 insertions(+), 1799 deletions(-) delete mode 100644 Documentation/serial/README.cycladesZ create mode 100644 Documentation/serial/cyclades_z.rst delete mode 100644 Documentation/serial/driver create mode 100644 Documentation/serial/driver.rst create mode 100644 Documentation/serial/index.rst delete mode 100644 Documentation/serial/moxa-smartio create mode 100644 Documentation/serial/moxa-smartio.rst create mode 100644 Documentation/serial/n_gsm.rst delete mode 100644 Documentation/serial/n_gsm.txt create mode 100644 Documentation/serial/rocket.rst delete mode 100644 Documentation/serial/rocket.txt create mode 100644 Documentation/serial/serial-iso7816.rst delete mode 100644 Documentation/serial/serial-iso7816.txt create mode 100644 Documentation/serial/serial-rs485.rst delete mode 100644 Documentation/serial/serial-rs485.txt create mode 100644 Documentation/serial/tty.rst delete mode 100644 Documentation/serial/tty.txt (limited to 'Documentation') diff --git a/Documentation/serial/README.cycladesZ b/Documentation/serial/README.cycladesZ deleted file mode 100644 index 024a69443cc2..000000000000 --- a/Documentation/serial/README.cycladesZ +++ /dev/null @@ -1,8 +0,0 @@ - -The Cyclades-Z must have firmware loaded onto the card before it will -operate. This operation should be performed during system startup, - -The firmware, loader program and the latest device driver code are -available from Cyclades at - ftp://ftp.cyclades.com/pub/cyclades/cyclades-z/linux/ - diff --git a/Documentation/serial/cyclades_z.rst b/Documentation/serial/cyclades_z.rst new file mode 100644 index 000000000000..532ff67e2f1c --- /dev/null +++ b/Documentation/serial/cyclades_z.rst @@ -0,0 +1,11 @@ +================ +Cyclades-Z notes +================ + +The Cyclades-Z must have firmware loaded onto the card before it will +operate. This operation should be performed during system startup, + +The firmware, loader program and the latest device driver code are +available from Cyclades at + + ftp://ftp.cyclades.com/pub/cyclades/cyclades-z/linux/ diff --git a/Documentation/serial/driver b/Documentation/serial/driver deleted file mode 100644 index 86e47c19a924..000000000000 --- a/Documentation/serial/driver +++ /dev/null @@ -1,486 +0,0 @@ - - Low Level Serial API - -------------------- - - -This document is meant as a brief overview of some aspects of the new serial -driver. It is not complete, any questions you have should be directed to - - -The reference implementation is contained within amba-pl011.c. - - - -Low Level Serial Hardware Driver --------------------------------- - -The low level serial hardware driver is responsible for supplying port -information (defined by uart_port) and a set of control methods (defined -by uart_ops) to the core serial driver. The low level driver is also -responsible for handling interrupts for the port, and providing any -console support. - - -Console Support ---------------- - -The serial core provides a few helper functions. This includes identifing -the correct port structure (via uart_get_console) and decoding command line -arguments (uart_parse_options). - -There is also a helper function (uart_console_write) which performs a -character by character write, translating newlines to CRLF sequences. -Driver writers are recommended to use this function rather than implementing -their own version. - - -Locking -------- - -It is the responsibility of the low level hardware driver to perform the -necessary locking using port->lock. There are some exceptions (which -are described in the uart_ops listing below.) - -There are two locks. A per-port spinlock, and an overall semaphore. - -From the core driver perspective, the port->lock locks the following -data: - - port->mctrl - port->icount - port->state->xmit.head (circ_buf->head) - port->state->xmit.tail (circ_buf->tail) - -The low level driver is free to use this lock to provide any additional -locking. - -The port_sem semaphore is used to protect against ports being added/ -removed or reconfigured at inappropriate times. Since v2.6.27, this -semaphore has been the 'mutex' member of the tty_port struct, and -commonly referred to as the port mutex. - - -uart_ops --------- - -The uart_ops structure is the main interface between serial_core and the -hardware specific driver. It contains all the methods to control the -hardware. - - tx_empty(port) - This function tests whether the transmitter fifo and shifter - for the port described by 'port' is empty. If it is empty, - this function should return TIOCSER_TEMT, otherwise return 0. - If the port does not support this operation, then it should - return TIOCSER_TEMT. - - Locking: none. - Interrupts: caller dependent. - This call must not sleep - - set_mctrl(port, mctrl) - This function sets the modem control lines for port described - by 'port' to the state described by mctrl. The relevant bits - of mctrl are: - - TIOCM_RTS RTS signal. - - TIOCM_DTR DTR signal. - - TIOCM_OUT1 OUT1 signal. - - TIOCM_OUT2 OUT2 signal. - - TIOCM_LOOP Set the port into loopback mode. - If the appropriate bit is set, the signal should be driven - active. If the bit is clear, the signal should be driven - inactive. - - Locking: port->lock taken. - Interrupts: locally disabled. - This call must not sleep - - get_mctrl(port) - Returns the current state of modem control inputs. The state - of the outputs should not be returned, since the core keeps - track of their state. The state information should include: - - TIOCM_CAR state of DCD signal - - TIOCM_CTS state of CTS signal - - TIOCM_DSR state of DSR signal - - TIOCM_RI state of RI signal - The bit is set if the signal is currently driven active. If - the port does not support CTS, DCD or DSR, the driver should - indicate that the signal is permanently active. If RI is - not available, the signal should not be indicated as active. - - Locking: port->lock taken. - Interrupts: locally disabled. - This call must not sleep - - stop_tx(port) - Stop transmitting characters. This might be due to the CTS - line becoming inactive or the tty layer indicating we want - to stop transmission due to an XOFF character. - - The driver should stop transmitting characters as soon as - possible. - - Locking: port->lock taken. - Interrupts: locally disabled. - This call must not sleep - - start_tx(port) - Start transmitting characters. - - Locking: port->lock taken. - Interrupts: locally disabled. - This call must not sleep - - throttle(port) - Notify the serial driver that input buffers for the line discipline are - close to full, and it should somehow signal that no more characters - should be sent to the serial port. - This will be called only if hardware assisted flow control is enabled. - - Locking: serialized with .unthrottle() and termios modification by the - tty layer. - - unthrottle(port) - Notify the serial driver that characters can now be sent to the serial - port without fear of overrunning the input buffers of the line - disciplines. - This will be called only if hardware assisted flow control is enabled. - - Locking: serialized with .throttle() and termios modification by the - tty layer. - - send_xchar(port,ch) - Transmit a high priority character, even if the port is stopped. - This is used to implement XON/XOFF flow control and tcflow(). If - the serial driver does not implement this function, the tty core - will append the character to the circular buffer and then call - start_tx() / stop_tx() to flush the data out. - - Do not transmit if ch == '\0' (__DISABLED_CHAR). - - Locking: none. - Interrupts: caller dependent. - - stop_rx(port) - Stop receiving characters; the port is in the process of - being closed. - - Locking: port->lock taken. - Interrupts: locally disabled. - This call must not sleep - - enable_ms(port) - Enable the modem status interrupts. - - This method may be called multiple times. Modem status - interrupts should be disabled when the shutdown method is - called. - - Locking: port->lock taken. - Interrupts: locally disabled. - This call must not sleep - - break_ctl(port,ctl) - Control the transmission of a break signal. If ctl is - nonzero, the break signal should be transmitted. The signal - should be terminated when another call is made with a zero - ctl. - - Locking: caller holds tty_port->mutex - - startup(port) - Grab any interrupt resources and initialise any low level driver - state. Enable the port for reception. It should not activate - RTS nor DTR; this will be done via a separate call to set_mctrl. - - This method will only be called when the port is initially opened. - - Locking: port_sem taken. - Interrupts: globally disabled. - - shutdown(port) - Disable the port, disable any break condition that may be in - effect, and free any interrupt resources. It should not disable - RTS nor DTR; this will have already been done via a separate - call to set_mctrl. - - Drivers must not access port->state once this call has completed. - - This method will only be called when there are no more users of - this port. - - Locking: port_sem taken. - Interrupts: caller dependent. - - flush_buffer(port) - Flush any write buffers, reset any DMA state and stop any - ongoing DMA transfers. - - This will be called whenever the port->state->xmit circular - buffer is cleared. - - Locking: port->lock taken. - Interrupts: locally disabled. - This call must not sleep - - set_termios(port,termios,oldtermios) - Change the port parameters, including word length, parity, stop - bits. Update read_status_mask and ignore_status_mask to indicate - the types of events we are interested in receiving. Relevant - termios->c_cflag bits are: - CSIZE - word size - CSTOPB - 2 stop bits - PARENB - parity enable - PARODD - odd parity (when PARENB is in force) - CREAD - enable reception of characters (if not set, - still receive characters from the port, but - throw them away. - CRTSCTS - if set, enable CTS status change reporting - CLOCAL - if not set, enable modem status change - reporting. - Relevant termios->c_iflag bits are: - INPCK - enable frame and parity error events to be - passed to the TTY layer. - BRKINT - PARMRK - both of these enable break events to be - passed to the TTY layer. - - IGNPAR - ignore parity and framing errors - IGNBRK - ignore break errors, If IGNPAR is also - set, ignore overrun errors as well. - The interaction of the iflag bits is as follows (parity error - given as an example): - Parity error INPCK IGNPAR - n/a 0 n/a character received, marked as - TTY_NORMAL - None 1 n/a character received, marked as - TTY_NORMAL - Yes 1 0 character received, marked as - TTY_PARITY - Yes 1 1 character discarded - - Other flags may be used (eg, xon/xoff characters) if your - hardware supports hardware "soft" flow control. - - Locking: caller holds tty_port->mutex - Interrupts: caller dependent. - This call must not sleep - - set_ldisc(port,termios) - Notifier for discipline change. See Documentation/serial/tty.txt. - - Locking: caller holds tty_port->mutex - - pm(port,state,oldstate) - Perform any power management related activities on the specified - port. State indicates the new state (defined by - enum uart_pm_state), oldstate indicates the previous state. - - This function should not be used to grab any resources. - - This will be called when the port is initially opened and finally - closed, except when the port is also the system console. This - will occur even if CONFIG_PM is not set. - - Locking: none. - Interrupts: caller dependent. - - type(port) - Return a pointer to a string constant describing the specified - port, or return NULL, in which case the string 'unknown' is - substituted. - - Locking: none. - Interrupts: caller dependent. - - release_port(port) - Release any memory and IO region resources currently in use by - the port. - - Locking: none. - Interrupts: caller dependent. - - request_port(port) - Request any memory and IO region resources required by the port. - If any fail, no resources should be registered when this function - returns, and it should return -EBUSY on failure. - - Locking: none. - Interrupts: caller dependent. - - config_port(port,type) - Perform any autoconfiguration steps required for the port. `type` - contains a bit mask of the required configuration. UART_CONFIG_TYPE - indicates that the port requires detection and identification. - port->type should be set to the type found, or PORT_UNKNOWN if - no port was detected. - - UART_CONFIG_IRQ indicates autoconfiguration of the interrupt signal, - which should be probed using standard kernel autoprobing techniques. - This is not necessary on platforms where ports have interrupts - internally hard wired (eg, system on a chip implementations). - - Locking: none. - Interrupts: caller dependent. - - verify_port(port,serinfo) - Verify the new serial port information contained within serinfo is - suitable for this port type. - - Locking: none. - Interrupts: caller dependent. - - ioctl(port,cmd,arg) - Perform any port specific IOCTLs. IOCTL commands must be defined - using the standard numbering system found in - - Locking: none. - Interrupts: caller dependent. - - poll_init(port) - Called by kgdb to perform the minimal hardware initialization needed - to support poll_put_char() and poll_get_char(). Unlike ->startup() - this should not request interrupts. - - Locking: tty_mutex and tty_port->mutex taken. - Interrupts: n/a. - - poll_put_char(port,ch) - Called by kgdb to write a single character directly to the serial - port. It can and should block until there is space in the TX FIFO. - - Locking: none. - Interrupts: caller dependent. - This call must not sleep - - poll_get_char(port) - Called by kgdb to read a single character directly from the serial - port. If data is available, it should be returned; otherwise - the function should return NO_POLL_CHAR immediately. - - Locking: none. - Interrupts: caller dependent. - This call must not sleep - -Other functions ---------------- - -uart_update_timeout(port,cflag,baud) - Update the FIFO drain timeout, port->timeout, according to the - number of bits, parity, stop bits and baud rate. - - Locking: caller is expected to take port->lock - Interrupts: n/a - -uart_get_baud_rate(port,termios,old,min,max) - Return the numeric baud rate for the specified termios, taking - account of the special 38400 baud "kludge". The B0 baud rate - is mapped to 9600 baud. - - If the baud rate is not within min..max, then if old is non-NULL, - the original baud rate will be tried. If that exceeds the - min..max constraint, 9600 baud will be returned. termios will - be updated to the baud rate in use. - - Note: min..max must always allow 9600 baud to be selected. - - Locking: caller dependent. - Interrupts: n/a - -uart_get_divisor(port,baud) - Return the divisor (baud_base / baud) for the specified baud - rate, appropriately rounded. - - If 38400 baud and custom divisor is selected, return the - custom divisor instead. - - Locking: caller dependent. - Interrupts: n/a - -uart_match_port(port1,port2) - This utility function can be used to determine whether two - uart_port structures describe the same port. - - Locking: n/a - Interrupts: n/a - -uart_write_wakeup(port) - A driver is expected to call this function when the number of - characters in the transmit buffer have dropped below a threshold. - - Locking: port->lock should be held. - Interrupts: n/a - -uart_register_driver(drv) - Register a uart driver with the core driver. We in turn register - with the tty layer, and initialise the core driver per-port state. - - drv->port should be NULL, and the per-port structures should be - registered using uart_add_one_port after this call has succeeded. - - Locking: none - Interrupts: enabled - -uart_unregister_driver() - Remove all references to a driver from the core driver. The low - level driver must have removed all its ports via the - uart_remove_one_port() if it registered them with uart_add_one_port(). - - Locking: none - Interrupts: enabled - -uart_suspend_port() - -uart_resume_port() - -uart_add_one_port() - -uart_remove_one_port() - -Other notes ------------ - -It is intended some day to drop the 'unused' entries from uart_port, and -allow low level drivers to register their own individual uart_port's with -the core. This will allow drivers to use uart_port as a pointer to a -structure containing both the uart_port entry with their own extensions, -thus: - - struct my_port { - struct uart_port port; - int my_stuff; - }; - -Modem control lines via GPIO ----------------------------- - -Some helpers are provided in order to set/get modem control lines via GPIO. - -mctrl_gpio_init(port, idx): - This will get the {cts,rts,...}-gpios from device tree if they are - present and request them, set direction etc, and return an - allocated structure. devm_* functions are used, so there's no need - to call mctrl_gpio_free(). - As this sets up the irq handling make sure to not handle changes to the - gpio input lines in your driver, too. - -mctrl_gpio_free(dev, gpios): - This will free the requested gpios in mctrl_gpio_init(). - As devm_* functions are used, there's generally no need to call - this function. - -mctrl_gpio_to_gpiod(gpios, gidx) - This returns the gpio_desc structure associated to the modem line - index. - -mctrl_gpio_set(gpios, mctrl): - This will sets the gpios according to the mctrl state. - -mctrl_gpio_get(gpios, mctrl): - This will update mctrl with the gpios values. - -mctrl_gpio_enable_ms(gpios): - Enables irqs and handling of changes to the ms lines. - -mctrl_gpio_disable_ms(gpios): - Disables irqs and handling of changes to the ms lines. diff --git a/Documentation/serial/driver.rst b/Documentation/serial/driver.rst new file mode 100644 index 000000000000..4537119bf624 --- /dev/null +++ b/Documentation/serial/driver.rst @@ -0,0 +1,549 @@ +==================== +Low Level Serial API +==================== + + +This document is meant as a brief overview of some aspects of the new serial +driver. It is not complete, any questions you have should be directed to + + +The reference implementation is contained within amba-pl011.c. + + + +Low Level Serial Hardware Driver +-------------------------------- + +The low level serial hardware driver is responsible for supplying port +information (defined by uart_port) and a set of control methods (defined +by uart_ops) to the core serial driver. The low level driver is also +responsible for handling interrupts for the port, and providing any +console support. + + +Console Support +--------------- + +The serial core provides a few helper functions. This includes identifing +the correct port structure (via uart_get_console) and decoding command line +arguments (uart_parse_options). + +There is also a helper function (uart_console_write) which performs a +character by character write, translating newlines to CRLF sequences. +Driver writers are recommended to use this function rather than implementing +their own version. + + +Locking +------- + +It is the responsibility of the low level hardware driver to perform the +necessary locking using port->lock. There are some exceptions (which +are described in the uart_ops listing below.) + +There are two locks. A per-port spinlock, and an overall semaphore. + +From the core driver perspective, the port->lock locks the following +data:: + + port->mctrl + port->icount + port->state->xmit.head (circ_buf->head) + port->state->xmit.tail (circ_buf->tail) + +The low level driver is free to use this lock to provide any additional +locking. + +The port_sem semaphore is used to protect against ports being added/ +removed or reconfigured at inappropriate times. Since v2.6.27, this +semaphore has been the 'mutex' member of the tty_port struct, and +commonly referred to as the port mutex. + + +uart_ops +-------- + +The uart_ops structure is the main interface between serial_core and the +hardware specific driver. It contains all the methods to control the +hardware. + + tx_empty(port) + This function tests whether the transmitter fifo and shifter + for the port described by 'port' is empty. If it is empty, + this function should return TIOCSER_TEMT, otherwise return 0. + If the port does not support this operation, then it should + return TIOCSER_TEMT. + + Locking: none. + + Interrupts: caller dependent. + + This call must not sleep + + set_mctrl(port, mctrl) + This function sets the modem control lines for port described + by 'port' to the state described by mctrl. The relevant bits + of mctrl are: + + - TIOCM_RTS RTS signal. + - TIOCM_DTR DTR signal. + - TIOCM_OUT1 OUT1 signal. + - TIOCM_OUT2 OUT2 signal. + - TIOCM_LOOP Set the port into loopback mode. + + If the appropriate bit is set, the signal should be driven + active. If the bit is clear, the signal should be driven + inactive. + + Locking: port->lock taken. + + Interrupts: locally disabled. + + This call must not sleep + + get_mctrl(port) + Returns the current state of modem control inputs. The state + of the outputs should not be returned, since the core keeps + track of their state. The state information should include: + + - TIOCM_CAR state of DCD signal + - TIOCM_CTS state of CTS signal + - TIOCM_DSR state of DSR signal + - TIOCM_RI state of RI signal + + The bit is set if the signal is currently driven active. If + the port does not support CTS, DCD or DSR, the driver should + indicate that the signal is permanently active. If RI is + not available, the signal should not be indicated as active. + + Locking: port->lock taken. + + Interrupts: locally disabled. + + This call must not sleep + + stop_tx(port) + Stop transmitting characters. This might be due to the CTS + line becoming inactive or the tty layer indicating we want + to stop transmission due to an XOFF character. + + The driver should stop transmitting characters as soon as + possible. + + Locking: port->lock taken. + + Interrupts: locally disabled. + + This call must not sleep + + start_tx(port) + Start transmitting characters. + + Locking: port->lock taken. + + Interrupts: locally disabled. + + This call must not sleep + + throttle(port) + Notify the serial driver that input buffers for the line discipline are + close to full, and it should somehow signal that no more characters + should be sent to the serial port. + This will be called only if hardware assisted flow control is enabled. + + Locking: serialized with .unthrottle() and termios modification by the + tty layer. + + unthrottle(port) + Notify the serial driver that characters can now be sent to the serial + port without fear of overrunning the input buffers of the line + disciplines. + + This will be called only if hardware assisted flow control is enabled. + + Locking: serialized with .throttle() and termios modification by the + tty layer. + + send_xchar(port,ch) + Transmit a high priority character, even if the port is stopped. + This is used to implement XON/XOFF flow control and tcflow(). If + the serial driver does not implement this function, the tty core + will append the character to the circular buffer and then call + start_tx() / stop_tx() to flush the data out. + + Do not transmit if ch == '\0' (__DISABLED_CHAR). + + Locking: none. + + Interrupts: caller dependent. + + stop_rx(port) + Stop receiving characters; the port is in the process of + being closed. + + Locking: port->lock taken. + + Interrupts: locally disabled. + + This call must not sleep + + enable_ms(port) + Enable the modem status interrupts. + + This method may be called multiple times. Modem status + interrupts should be disabled when the shutdown method is + called. + + Locking: port->lock taken. + + Interrupts: locally disabled. + + This call must not sleep + + break_ctl(port,ctl) + Control the transmission of a break signal. If ctl is + nonzero, the break signal should be transmitted. The signal + should be terminated when another call is made with a zero + ctl. + + Locking: caller holds tty_port->mutex + + startup(port) + Grab any interrupt resources and initialise any low level driver + state. Enable the port for reception. It should not activate + RTS nor DTR; this will be done via a separate call to set_mctrl. + + This method will only be called when the port is initially opened. + + Locking: port_sem taken. + + Interrupts: globally disabled. + + shutdown(port) + Disable the port, disable any break condition that may be in + effect, and free any interrupt resources. It should not disable + RTS nor DTR; this will have already been done via a separate + call to set_mctrl. + + Drivers must not access port->state once this call has completed. + + This method will only be called when there are no more users of + this port. + + Locking: port_sem taken. + + Interrupts: caller dependent. + + flush_buffer(port) + Flush any write buffers, reset any DMA state and stop any + ongoing DMA transfers. + + This will be called whenever the port->state->xmit circular + buffer is cleared. + + Locking: port->lock taken. + + Interrupts: locally disabled. + + This call must not sleep + + set_termios(port,termios,oldtermios) + Change the port parameters, including word length, parity, stop + bits. Update read_status_mask and ignore_status_mask to indicate + the types of events we are interested in receiving. Relevant + termios->c_cflag bits are: + + CSIZE + - word size + CSTOPB + - 2 stop bits + PARENB + - parity enable + PARODD + - odd parity (when PARENB is in force) + CREAD + - enable reception of characters (if not set, + still receive characters from the port, but + throw them away. + CRTSCTS + - if set, enable CTS status change reporting + CLOCAL + - if not set, enable modem status change + reporting. + + Relevant termios->c_iflag bits are: + + INPCK + - enable frame and parity error events to be + passed to the TTY layer. + BRKINT / PARMRK + - both of these enable break events to be + passed to the TTY layer. + + IGNPAR + - ignore parity and framing errors + IGNBRK + - ignore break errors, If IGNPAR is also + set, ignore overrun errors as well. + + The interaction of the iflag bits is as follows (parity error + given as an example): + + =============== ======= ====== ============================= + Parity error INPCK IGNPAR + =============== ======= ====== ============================= + n/a 0 n/a character received, marked as + TTY_NORMAL + None 1 n/a character received, marked as + TTY_NORMAL + Yes 1 0 character received, marked as + TTY_PARITY + Yes 1 1 character discarded + =============== ======= ====== ============================= + + Other flags may be used (eg, xon/xoff characters) if your + hardware supports hardware "soft" flow control. + + Locking: caller holds tty_port->mutex + + Interrupts: caller dependent. + + This call must not sleep + + set_ldisc(port,termios) + Notifier for discipline change. See Documentation/serial/tty.rst. + + Locking: caller holds tty_port->mutex + + pm(port,state,oldstate) + Perform any power management related activities on the specified + port. State indicates the new state (defined by + enum uart_pm_state), oldstate indicates the previous state. + + This function should not be used to grab any resources. + + This will be called when the port is initially opened and finally + closed, except when the port is also the system console. This + will occur even if CONFIG_PM is not set. + + Locking: none. + + Interrupts: caller dependent. + + type(port) + Return a pointer to a string constant describing the specified + port, or return NULL, in which case the string 'unknown' is + substituted. + + Locking: none. + + Interrupts: caller dependent. + + release_port(port) + Release any memory and IO region resources currently in use by + the port. + + Locking: none. + + Interrupts: caller dependent. + + request_port(port) + Request any memory and IO region resources required by the port. + If any fail, no resources should be registered when this function + returns, and it should return -EBUSY on failure. + + Locking: none. + + Interrupts: caller dependent. + + config_port(port,type) + Perform any autoconfiguration steps required for the port. `type` + contains a bit mask of the required configuration. UART_CONFIG_TYPE + indicates that the port requires detection and identification. + port->type should be set to the type found, or PORT_UNKNOWN if + no port was detected. + + UART_CONFIG_IRQ indicates autoconfiguration of the interrupt signal, + which should be probed using standard kernel autoprobing techniques. + This is not necessary on platforms where ports have interrupts + internally hard wired (eg, system on a chip implementations). + + Locking: none. + + Interrupts: caller dependent. + + verify_port(port,serinfo) + Verify the new serial port information contained within serinfo is + suitable for this port type. + + Locking: none. + + Interrupts: caller dependent. + + ioctl(port,cmd,arg) + Perform any port specific IOCTLs. IOCTL commands must be defined + using the standard numbering system found in + + Locking: none. + + Interrupts: caller dependent. + + poll_init(port) + Called by kgdb to perform the minimal hardware initialization needed + to support poll_put_char() and poll_get_char(). Unlike ->startup() + this should not request interrupts. + + Locking: tty_mutex and tty_port->mutex taken. + + Interrupts: n/a. + + poll_put_char(port,ch) + Called by kgdb to write a single character directly to the serial + port. It can and should block until there is space in the TX FIFO. + + Locking: none. + + Interrupts: caller dependent. + + This call must not sleep + + poll_get_char(port) + Called by kgdb to read a single character directly from the serial + port. If data is available, it should be returned; otherwise + the function should return NO_POLL_CHAR immediately. + + Locking: none. + + Interrupts: caller dependent. + + This call must not sleep + +Other functions +--------------- + +uart_update_timeout(port,cflag,baud) + Update the FIFO drain timeout, port->timeout, according to the + number of bits, parity, stop bits and baud rate. + + Locking: caller is expected to take port->lock + + Interrupts: n/a + +uart_get_baud_rate(port,termios,old,min,max) + Return the numeric baud rate for the specified termios, taking + account of the special 38400 baud "kludge". The B0 baud rate + is mapped to 9600 baud. + + If the baud rate is not within min..max, then if old is non-NULL, + the original baud rate will be tried. If that exceeds the + min..max constraint, 9600 baud will be returned. termios will + be updated to the baud rate in use. + + Note: min..max must always allow 9600 baud to be selected. + + Locking: caller dependent. + + Interrupts: n/a + +uart_get_divisor(port,baud) + Return the divisor (baud_base / baud) for the specified baud + rate, appropriately rounded. + + If 38400 baud and custom divisor is selected, return the + custom divisor instead. + + Locking: caller dependent. + + Interrupts: n/a + +uart_match_port(port1,port2) + This utility function can be used to determine whether two + uart_port structures describe the same port. + + Locking: n/a + + Interrupts: n/a + +uart_write_wakeup(port) + A driver is expected to call this function when the number of + characters in the transmit buffer have dropped below a threshold. + + Locking: port->lock should be held. + + Interrupts: n/a + +uart_register_driver(drv) + Register a uart driver with the core driver. We in turn register + with the tty layer, and initialise the core driver per-port state. + + drv->port should be NULL, and the per-port structures should be + registered using uart_add_one_port after this call has succeeded. + + Locking: none + + Interrupts: enabled + +uart_unregister_driver() + Remove all references to a driver from the core driver. The low + level driver must have removed all its ports via the + uart_remove_one_port() if it registered them with uart_add_one_port(). + + Locking: none + + Interrupts: enabled + +**uart_suspend_port()** + +**uart_resume_port()** + +**uart_add_one_port()** + +**uart_remove_one_port()** + +Other notes +----------- + +It is intended some day to drop the 'unused' entries from uart_port, and +allow low level drivers to register their own individual uart_port's with +the core. This will allow drivers to use uart_port as a pointer to a +structure containing both the uart_port entry with their own extensions, +thus:: + + struct my_port { + struct uart_port port; + int my_stuff; + }; + +Modem control lines via GPIO +---------------------------- + +Some helpers are provided in order to set/get modem control lines via GPIO. + +mctrl_gpio_init(port, idx): + This will get the {cts,rts,...}-gpios from device tree if they are + present and request them, set direction etc, and return an + allocated structure. `devm_*` functions are used, so there's no need + to call mctrl_gpio_free(). + As this sets up the irq handling make sure to not handle changes to the + gpio input lines in your driver, too. + +mctrl_gpio_free(dev, gpios): + This will free the requested gpios in mctrl_gpio_init(). + As `devm_*` functions are used, there's generally no need to call + this function. + +mctrl_gpio_to_gpiod(gpios, gidx) + This returns the gpio_desc structure associated to the modem line + index. + +mctrl_gpio_set(gpios, mctrl): + This will sets the gpios according to the mctrl state. + +mctrl_gpio_get(gpios, mctrl): + This will update mctrl with the gpios values. + +mctrl_gpio_enable_ms(gpios): + Enables irqs and handling of changes to the ms lines. + +mctrl_gpio_disable_ms(gpios): + Disables irqs and handling of changes to the ms lines. diff --git a/Documentation/serial/index.rst b/Documentation/serial/index.rst new file mode 100644 index 000000000000..d0ba22ea23bf --- /dev/null +++ b/Documentation/serial/index.rst @@ -0,0 +1,32 @@ +:orphan: + +========================== +Support for Serial devices +========================== + +.. toctree:: + :maxdepth: 1 + + + driver + tty + +Serial drivers +============== + +.. toctree:: + :maxdepth: 1 + + cyclades_z + moxa-smartio + n_gsm + rocket + serial-iso7816 + serial-rs485 + +.. only:: subproject and html + + Indices + ======= + + * :ref:`genindex` diff --git a/Documentation/serial/moxa-smartio b/Documentation/serial/moxa-smartio deleted file mode 100644 index 5d2a33be0bd8..000000000000 --- a/Documentation/serial/moxa-smartio +++ /dev/null @@ -1,523 +0,0 @@ -============================================================================= - MOXA Smartio/Industio Family Device Driver Installation Guide - for Linux Kernel 2.4.x, 2.6.x - Copyright (C) 2008, Moxa Inc. -============================================================================= -Date: 01/21/2008 - -Content - -1. Introduction -2. System Requirement -3. Installation - 3.1 Hardware installation - 3.2 Driver files - 3.3 Device naming convention - 3.4 Module driver configuration - 3.5 Static driver configuration for Linux kernel 2.4.x and 2.6.x. - 3.6 Custom configuration - 3.7 Verify driver installation -4. Utilities -5. Setserial -6. Troubleshooting - ------------------------------------------------------------------------------ -1. Introduction - - The Smartio/Industio/UPCI family Linux driver supports following multiport - boards. - - - 2 ports multiport board - CP-102U, CP-102UL, CP-102UF - CP-132U-I, CP-132UL, - CP-132, CP-132I, CP132S, CP-132IS, - CI-132, CI-132I, CI-132IS, - (C102H, C102HI, C102HIS, C102P, CP-102, CP-102S) - - - 4 ports multiport board - CP-104EL, - CP-104UL, CP-104JU, - CP-134U, CP-134U-I, - C104H/PCI, C104HS/PCI, - CP-114, CP-114I, CP-114S, CP-114IS, CP-114UL, - C104H, C104HS, - CI-104J, CI-104JS, - CI-134, CI-134I, CI-134IS, - (C114HI, CT-114I, C104P) - POS-104UL, - CB-114, - CB-134I - - - 8 ports multiport board - CP-118EL, CP-168EL, - CP-118U, CP-168U, - C168H/PCI, - C168H, C168HS, - (C168P), - CB-108 - - This driver and installation procedure have been developed upon Linux Kernel - 2.4.x and 2.6.x. This driver supports Intel x86 hardware platform. In order - to maintain compatibility, this version has also been properly tested with - RedHat, Mandrake, Fedora and S.u.S.E Linux. However, if compatibility problem - occurs, please contact Moxa at support@moxa.com.tw. - - In addition to device driver, useful utilities are also provided in this - version. They are - - msdiag Diagnostic program for displaying installed Moxa - Smartio/Industio boards. - - msmon Monitor program to observe data count and line status signals. - - msterm A simple terminal program which is useful in testing serial - ports. - - io-irq.exe Configuration program to setup ISA boards. Please note that - this program can only be executed under DOS. - - All the drivers and utilities are published in form of source code under - GNU General Public License in this version. Please refer to GNU General - Public License announcement in each source code file for more detail. - - In Moxa's Web sites, you may always find latest driver at http://www.moxa.com/. - - This version of driver can be installed as Loadable Module (Module driver) - or built-in into kernel (Static driver). You may refer to following - installation procedure for suitable one. Before you install the driver, - please refer to hardware installation procedure in the User's Manual. - - We assume the user should be familiar with following documents. - - Serial-HOWTO - - Kernel-HOWTO - ------------------------------------------------------------------------------ -2. System Requirement - - Hardware platform: Intel x86 machine - - Kernel version: 2.4.x or 2.6.x - - gcc version 2.72 or later - - Maximum 4 boards can be installed in combination - ------------------------------------------------------------------------------ -3. Installation - - 3.1 Hardware installation - 3.2 Driver files - 3.3 Device naming convention - 3.4 Module driver configuration - 3.5 Static driver configuration for Linux kernel 2.4.x, 2.6.x. - 3.6 Custom configuration - 3.7 Verify driver installation - - - 3.1 Hardware installation - - There are two types of buses, ISA and PCI, for Smartio/Industio - family multiport board. - - ISA board - --------- - You'll have to configure CAP address, I/O address, Interrupt Vector - as well as IRQ before installing this driver. Please refer to hardware - installation procedure in User's Manual before proceed any further. - Please make sure the JP1 is open after the ISA board is set properly. - - PCI/UPCI board - -------------- - You may need to adjust IRQ usage in BIOS to avoid from IRQ conflict - with other ISA devices. Please refer to hardware installation - procedure in User's Manual in advance. - - PCI IRQ Sharing - ----------- - Each port within the same multiport board shares the same IRQ. Up to - 4 Moxa Smartio/Industio PCI Family multiport boards can be installed - together on one system and they can share the same IRQ. - - - 3.2 Driver files - - The driver file may be obtained from ftp, CD-ROM or floppy disk. The - first step, anyway, is to copy driver file "mxser.tgz" into specified - directory. e.g. /moxa. The execute commands as below. - - # cd / - # mkdir moxa - # cd /moxa - # tar xvf /dev/fd0 - - or - - # cd / - # mkdir moxa - # cd /moxa - # cp /mnt/cdrom//mxser.tgz . - # tar xvfz mxser.tgz - - - 3.3 Device naming convention - - You may find all the driver and utilities files in /moxa/mxser. - Following installation procedure depends on the model you'd like to - run the driver. If you prefer module driver, please refer to 3.4. - If static driver is required, please refer to 3.5. - - Dialin and callout port - ----------------------- - This driver remains traditional serial device properties. There are - two special file name for each serial port. One is dial-in port - which is named "ttyMxx". For callout port, the naming convention - is "cumxx". - - Device naming when more than 2 boards installed - ----------------------------------------------- - Naming convention for each Smartio/Industio multiport board is - pre-defined as below. - - Board Num. Dial-in Port Callout port - 1st board ttyM0 - ttyM7 cum0 - cum7 - 2nd board ttyM8 - ttyM15 cum8 - cum15 - 3rd board ttyM16 - ttyM23 cum16 - cum23 - 4th board ttyM24 - ttym31 cum24 - cum31 - - - !!!!!!!!!!!!!!!!!!!! NOTE !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! - Under Kernel 2.6 the cum Device is Obsolete. So use ttyM* - device instead. - !!!!!!!!!!!!!!!!!!!! NOTE !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! - - Board sequence - -------------- - This driver will activate ISA boards according to the parameter set - in the driver. After all specified ISA board activated, PCI board - will be installed in the system automatically driven. - Therefore the board number is sorted by the CAP address of ISA boards. - For PCI boards, their sequence will be after ISA boards and C168H/PCI - has higher priority than C104H/PCI boards. - - 3.4 Module driver configuration - Module driver is easiest way to install. If you prefer static driver - installation, please skip this paragraph. - - - ------------- Prepare to use the MOXA driver-------------------- - 3.4.1 Create tty device with correct major number - Before using MOXA driver, your system must have the tty devices - which are created with driver's major number. We offer one shell - script "msmknod" to simplify the procedure. - This step is only needed to be executed once. But you still - need to do this procedure when: - a. You change the driver's major number. Please refer the "3.7" - section. - b. Your total installed MOXA boards number is changed. Maybe you - add/delete one MOXA board. - c. You want to change the tty name. This needs to modify the - shell script "msmknod" - - The procedure is: - # cd /moxa/mxser/driver - # ./msmknod - - This shell script will require the major number for dial-in - device and callout device to create tty device. You also need - to specify the total installed MOXA board number. Default major - numbers for dial-in device and callout device are 30, 35. If - you need to change to other number, please refer section "3.7" - for more detailed procedure. - Msmknod will delete any special files occupying the same device - naming. - - 3.4.2 Build the MOXA driver and utilities - Before using the MOXA driver and utilities, you need compile the - all the source code. This step is only need to be executed once. - But you still re-compile the source code if you modify the source - code. For example, if you change the driver's major number (see - "3.7" section), then you need to do this step again. - - Find "Makefile" in /moxa/mxser, then run - - # make clean; make install - - !!!!!!!!!! NOTE !!!!!!!!!!!!!!!!! - For Red Hat 9, Red Hat Enterprise Linux AS3/ES3/WS3 & Fedora Core1: - # make clean; make installsp1 - - For Red Hat Enterprise Linux AS4/ES4/WS4: - # make clean; make installsp2 - !!!!!!!!!! NOTE !!!!!!!!!!!!!!!!! - - The driver files "mxser.o" and utilities will be properly compiled - and copied to system directories respectively. - - ------------- Load MOXA driver-------------------- - 3.4.3 Load the MOXA driver - - # modprobe mxser - - will activate the module driver. You may run "lsmod" to check - if "mxser" is activated. If the MOXA board is ISA board, the - is needed. Please refer to section "3.4.5" for more - information. - - - ------------- Load MOXA driver on boot -------------------- - 3.4.4 For the above description, you may manually execute - "modprobe mxser" to activate this driver and run - "rmmod mxser" to remove it. - However, it's better to have a boot time configuration to - eliminate manual operation. Boot time configuration can be - achieved by rc file. We offer one "rc.mxser" file to simplify - the procedure under "moxa/mxser/driver". - - But if you use ISA board, please modify the "modprobe ..." command - to add the argument (see "3.4.5" section). After modifying the - rc.mxser, please try to execute "/moxa/mxser/driver/rc.mxser" - manually to make sure the modification is ok. If any error - encountered, please try to modify again. If the modification is - completed, follow the below step. - - Run following command for setting rc files. - - # cd /moxa/mxser/driver - # cp ./rc.mxser /etc/rc.d - # cd /etc/rc.d - - Check "rc.serial" is existed or not. If "rc.serial" doesn't exist, - create it by vi, run "chmod 755 rc.serial" to change the permission. - Add "/etc/rc.d/rc.mxser" in last line, - - Reboot and check if moxa.o activated by "lsmod" command. - - 3.4.5. If you'd like to drive Smartio/Industio ISA boards in the system, - you'll have to add parameter to specify CAP address of given - board while activating "mxser.o". The format for parameters are - as follows. - - modprobe mxser ioaddr=0x???,0x???,0x???,0x??? - | | | | - | | | +- 4th ISA board - | | +------ 3rd ISA board - | +------------ 2nd ISA board - +------------------- 1st ISA board - - 3.5 Static driver configuration for Linux kernel 2.4.x and 2.6.x - - Note: To use static driver, you must install the linux kernel - source package. - - 3.5.1 Backup the built-in driver in the kernel. - # cd /usr/src/linux/drivers/char - # mv mxser.c mxser.c.old - - For Red Hat 7.x user, you need to create link: - # cd /usr/src - # ln -s linux-2.4 linux - - 3.5.2 Create link - # cd /usr/src/linux/drivers/char - # ln -s /moxa/mxser/driver/mxser.c mxser.c - - 3.5.3 Add CAP address list for ISA boards. For PCI boards user, - please skip this step. - - In module mode, the CAP address for ISA board is given by - parameter. In static driver configuration, you'll have to - assign it within driver's source code. If you will not - install any ISA boards, you may skip to next portion. - The instructions to modify driver source code are as - below. - a. # cd /moxa/mxser/driver - # vi mxser.c - b. Find the array mxserBoardCAP[] as below. - - static int mxserBoardCAP[] - = {0x00, 0x00, 0x00, 0x00}; - - c. Change the address within this array using vi. For - example, to driver 2 ISA boards with CAP address - 0x280 and 0x180 as 1st and 2nd board. Just to change - the source code as follows. - - static int mxserBoardCAP[] - = {0x280, 0x180, 0x00, 0x00}; - - 3.5.4 Setup kernel configuration - - Configure the kernel: - - # cd /usr/src/linux - # make menuconfig - - You will go into a menu-driven system. Please select [Character - devices][Non-standard serial port support], enable the [Moxa - SmartIO support] driver with "[*]" for built-in (not "[M]"), then - select [Exit] to exit this program. - - 3.5.5 Rebuild kernel - The following are for Linux kernel rebuilding, for your - reference only. - For appropriate details, please refer to the Linux document. - - a. cd /usr/src/linux - b. make clean /* take a few minutes */ - c. make dep /* take a few minutes */ - d. make bzImage /* take probably 10-20 minutes */ - e. make install /* copy boot image to correct position */ - f. Please make sure the boot kernel (vmlinuz) is in the - correct position. - g. If you use 'lilo' utility, you should check /etc/lilo.conf - 'image' item specified the path which is the 'vmlinuz' path, - or you will load wrong (or old) boot kernel image (vmlinuz). - After checking /etc/lilo.conf, please run "lilo". - - Note that if the result of "make bzImage" is ERROR, then you have to - go back to Linux configuration Setup. Type "make menuconfig" in - directory /usr/src/linux. - - - 3.5.6 Make tty device and special file - # cd /moxa/mxser/driver - # ./msmknod - - 3.5.7 Make utility - # cd /moxa/mxser/utility - # make clean; make install - - 3.5.8 Reboot - - - - 3.6 Custom configuration - Although this driver already provides you default configuration, you - still can change the device name and major number. The instruction to - change these parameters are shown as below. - - Change Device name - ------------------ - If you'd like to use other device names instead of default naming - convention, all you have to do is to modify the internal code - within the shell script "msmknod". First, you have to open "msmknod" - by vi. Locate each line contains "ttyM" and "cum" and change them - to the device name you desired. "msmknod" creates the device names - you need next time executed. - - Change Major number - ------------------- - If major number 30 and 35 had been occupied, you may have to select - 2 free major numbers for this driver. There are 3 steps to change - major numbers. - - 3.6.1 Find free major numbers - In /proc/devices, you may find all the major numbers occupied - in the system. Please select 2 major numbers that are available. - e.g. 40, 45. - 3.6.2 Create special files - Run /moxa/mxser/driver/msmknod to create special files with - specified major numbers. - 3.6.3 Modify driver with new major number - Run vi to open /moxa/mxser/driver/mxser.c. Locate the line - contains "MXSERMAJOR". Change the content as below. - #define MXSERMAJOR 40 - #define MXSERCUMAJOR 45 - 3.6.4 Run "make clean; make install" in /moxa/mxser/driver. - - 3.7 Verify driver installation - You may refer to /var/log/messages to check the latest status - log reported by this driver whenever it's activated. - ------------------------------------------------------------------------------ -4. Utilities - There are 3 utilities contained in this driver. They are msdiag, msmon and - msterm. These 3 utilities are released in form of source code. They should - be compiled into executable file and copied into /usr/bin. - - Before using these utilities, please load driver (refer 3.4 & 3.5) and - make sure you had run the "msmknod" utility. - - msdiag - Diagnostic - -------------------- - This utility provides the function to display what Moxa Smartio/Industio - board found by driver in the system. - - msmon - Port Monitoring - ----------------------- - This utility gives the user a quick view about all the MOXA ports' - activities. One can easily learn each port's total received/transmitted - (Rx/Tx) character count since the time when the monitoring is started. - Rx/Tx throughputs per second are also reported in interval basis (e.g. - the last 5 seconds) and in average basis (since the time the monitoring - is started). You can reset all ports' count by key. <+> <-> - (plus/minus) keys to change the displaying time interval. Press - on the port, that cursor stay, to view the port's communication - parameters, signal status, and input/output queue. - - msterm - Terminal Emulation - --------------------------- - This utility provides data sending and receiving ability of all tty ports, - especially for MOXA ports. It is quite useful for testing simple - application, for example, sending AT command to a modem connected to the - port or used as a terminal for login purpose. Note that this is only a - dumb terminal emulation without handling full screen operation. - ------------------------------------------------------------------------------ -5. Setserial - - Supported Setserial parameters are listed as below. - - uart set UART type(16450-->disable FIFO, 16550A-->enable FIFO) - close_delay set the amount of time(in 1/100 of a second) that DTR - should be kept low while being closed. - closing_wait set the amount of time(in 1/100 of a second) that the - serial port should wait for data to be drained while - being closed, before the receiver is disable. - spd_hi Use 57.6kb when the application requests 38.4kb. - spd_vhi Use 115.2kb when the application requests 38.4kb. - spd_shi Use 230.4kb when the application requests 38.4kb. - spd_warp Use 460.8kb when the application requests 38.4kb. - spd_normal Use 38.4kb when the application requests 38.4kb. - spd_cust Use the custom divisor to set the speed when the - application requests 38.4kb. - divisor This option set the custom division. - baud_base This option set the base baud rate. - ------------------------------------------------------------------------------ -6. Troubleshooting - - The boot time error messages and solutions are stated as clearly as - possible. If all the possible solutions fail, please contact our technical - support team to get more help. - - - Error msg: More than 4 Moxa Smartio/Industio family boards found. Fifth board - and after are ignored. - Solution: - To avoid this problem, please unplug fifth and after board, because Moxa - driver supports up to 4 boards. - - Error msg: Request_irq fail, IRQ(?) may be conflict with another device. - Solution: - Other PCI or ISA devices occupy the assigned IRQ. If you are not sure - which device causes the situation, please check /proc/interrupts to find - free IRQ and simply change another free IRQ for Moxa board. - - Error msg: Board #: C1xx Series(CAP=xxx) interrupt number invalid. - Solution: - Each port within the same multiport board shares the same IRQ. Please set - one IRQ (IRQ doesn't equal to zero) for one Moxa board. - - Error msg: No interrupt vector be set for Moxa ISA board(CAP=xxx). - Solution: - Moxa ISA board needs an interrupt vector.Please refer to user's manual - "Hardware Installation" chapter to set interrupt vector. - - Error msg: Couldn't install MOXA Smartio/Industio family driver! - Solution: - Load Moxa driver fail, the major number may conflict with other devices. - Please refer to previous section 3.7 to change a free major number for - Moxa driver. - - Error msg: Couldn't install MOXA Smartio/Industio family callout driver! - Solution: - Load Moxa callout driver fail, the callout device major number may - conflict with other devices. Please refer to previous section 3.7 to - change a free callout device major number for Moxa driver. - - ------------------------------------------------------------------------------ - diff --git a/Documentation/serial/moxa-smartio.rst b/Documentation/serial/moxa-smartio.rst new file mode 100644 index 000000000000..156100f17c3f --- /dev/null +++ b/Documentation/serial/moxa-smartio.rst @@ -0,0 +1,615 @@ +============================================================= +MOXA Smartio/Industio Family Device Driver Installation Guide +============================================================= + +.. note:: + + This file is outdated. It needs some care in order to make it + updated to Kernel 5.0 and upper + +Copyright (C) 2008, Moxa Inc. + +Date: 01/21/2008 + +.. Content + + 1. Introduction + 2. System Requirement + 3. Installation + 3.1 Hardware installation + 3.2 Driver files + 3.3 Device naming convention + 3.4 Module driver configuration + 3.5 Static driver configuration for Linux kernel 2.4.x and 2.6.x. + 3.6 Custom configuration + 3.7 Verify driver installation + 4. Utilities + 5. Setserial + 6. Troubleshooting + +1. Introduction +^^^^^^^^^^^^^^^ + + The Smartio/Industio/UPCI family Linux driver supports following multiport + boards. + + - 2 ports multiport board + CP-102U, CP-102UL, CP-102UF + CP-132U-I, CP-132UL, + CP-132, CP-132I, CP132S, CP-132IS, + CI-132, CI-132I, CI-132IS, + (C102H, C102HI, C102HIS, C102P, CP-102, CP-102S) + + - 4 ports multiport board + CP-104EL, + CP-104UL, CP-104JU, + CP-134U, CP-134U-I, + C104H/PCI, C104HS/PCI, + CP-114, CP-114I, CP-114S, CP-114IS, CP-114UL, + C104H, C104HS, + CI-104J, CI-104JS, + CI-134, CI-134I, CI-134IS, + (C114HI, CT-114I, C104P), + POS-104UL, + CB-114, + CB-134I + + - 8 ports multiport board + CP-118EL, CP-168EL, + CP-118U, CP-168U, + C168H/PCI, + C168H, C168HS, + (C168P), + CB-108 + + This driver and installation procedure have been developed upon Linux Kernel + 2.4.x and 2.6.x. This driver supports Intel x86 hardware platform. In order + to maintain compatibility, this version has also been properly tested with + RedHat, Mandrake, Fedora and S.u.S.E Linux. However, if compatibility problem + occurs, please contact Moxa at support@moxa.com.tw. + + In addition to device driver, useful utilities are also provided in this + version. They are: + + - msdiag + Diagnostic program for displaying installed Moxa + Smartio/Industio boards. + - msmon + Monitor program to observe data count and line status signals. + - msterm A simple terminal program which is useful in testing serial + ports. + - io-irq.exe + Configuration program to setup ISA boards. Please note that + this program can only be executed under DOS. + + All the drivers and utilities are published in form of source code under + GNU General Public License in this version. Please refer to GNU General + Public License announcement in each source code file for more detail. + + In Moxa's Web sites, you may always find latest driver at http://www.moxa.com/. + + This version of driver can be installed as Loadable Module (Module driver) + or built-in into kernel (Static driver). You may refer to following + installation procedure for suitable one. Before you install the driver, + please refer to hardware installation procedure in the User's Manual. + + We assume the user should be familiar with following documents. + + - Serial-HOWTO + - Kernel-HOWTO + +2. System Requirement +^^^^^^^^^^^^^^^^^^^^^ + + - Hardware platform: Intel x86 machine + - Kernel version: 2.4.x or 2.6.x + - gcc version 2.72 or later + - Maximum 4 boards can be installed in combination + +3. Installation +^^^^^^^^^^^^^^^ + +3.1 Hardware installation +========================= + + There are two types of buses, ISA and PCI, for Smartio/Industio + family multiport board. + +ISA board +--------- + + You'll have to configure CAP address, I/O address, Interrupt Vector + as well as IRQ before installing this driver. Please refer to hardware + installation procedure in User's Manual before proceed any further. + Please make sure the JP1 is open after the ISA board is set properly. + +PCI/UPCI board +-------------- + + You may need to adjust IRQ usage in BIOS to avoid from IRQ conflict + with other ISA devices. Please refer to hardware installation + procedure in User's Manual in advance. + +PCI IRQ Sharing +--------------- + + Each port within the same multiport board shares the same IRQ. Up to + 4 Moxa Smartio/Industio PCI Family multiport boards can be installed + together on one system and they can share the same IRQ. + + +3.2 Driver files +================ + + The driver file may be obtained from ftp, CD-ROM or floppy disk. The + first step, anyway, is to copy driver file "mxser.tgz" into specified + directory. e.g. /moxa. The execute commands as below:: + + # cd / + # mkdir moxa + # cd /moxa + # tar xvf /dev/fd0 + +or:: + + # cd / + # mkdir moxa + # cd /moxa + # cp /mnt/cdrom//mxser.tgz . + # tar xvfz mxser.tgz + + +3.3 Device naming convention +============================ + + You may find all the driver and utilities files in /moxa/mxser. + Following installation procedure depends on the model you'd like to + run the driver. If you prefer module driver, please refer to 3.4. + If static driver is required, please refer to 3.5. + +Dialin and callout port +----------------------- + + This driver remains traditional serial device properties. There are + two special file name for each serial port. One is dial-in port + which is named "ttyMxx". For callout port, the naming convention + is "cumxx". + +Device naming when more than 2 boards installed +----------------------------------------------- + + Naming convention for each Smartio/Industio multiport board is + pre-defined as below. + + ============ =============== ============== + Board Num. Dial-in Port Callout port + 1st board ttyM0 - ttyM7 cum0 - cum7 + 2nd board ttyM8 - ttyM15 cum8 - cum15 + 3rd board ttyM16 - ttyM23 cum16 - cum23 + 4th board ttyM24 - ttym31 cum24 - cum31 + ============ =============== ============== + +.. note:: + + Under Kernel 2.6 and upper, the cum Device is Obsolete. So use ttyM* + device instead. + +Board sequence +-------------- + + This driver will activate ISA boards according to the parameter set + in the driver. After all specified ISA board activated, PCI board + will be installed in the system automatically driven. + Therefore the board number is sorted by the CAP address of ISA boards. + For PCI boards, their sequence will be after ISA boards and C168H/PCI + has higher priority than C104H/PCI boards. + +3.4 Module driver configuration +=============================== + + Module driver is easiest way to install. If you prefer static driver + installation, please skip this paragraph. + + + ------------- Prepare to use the MOXA driver -------------------- + +3.4.1 Create tty device with correct major number +------------------------------------------------- + + Before using MOXA driver, your system must have the tty devices + which are created with driver's major number. We offer one shell + script "msmknod" to simplify the procedure. + This step is only needed to be executed once. But you still + need to do this procedure when: + + a. You change the driver's major number. Please refer the "3.7" + section. + b. Your total installed MOXA boards number is changed. Maybe you + add/delete one MOXA board. + c. You want to change the tty name. This needs to modify the + shell script "msmknod" + + The procedure is:: + + # cd /moxa/mxser/driver + # ./msmknod + + This shell script will require the major number for dial-in + device and callout device to create tty device. You also need + to specify the total installed MOXA board number. Default major + numbers for dial-in device and callout device are 30, 35. If + you need to change to other number, please refer section "3.7" + for more detailed procedure. + Msmknod will delete any special files occupying the same device + naming. + +3.4.2 Build the MOXA driver and utilities +----------------------------------------- + + Before using the MOXA driver and utilities, you need compile the + all the source code. This step is only need to be executed once. + But you still re-compile the source code if you modify the source + code. For example, if you change the driver's major number (see + "3.7" section), then you need to do this step again. + + Find "Makefile" in /moxa/mxser, then run + + # make clean; make install + + ..note:: + + For Red Hat 9, Red Hat Enterprise Linux AS3/ES3/WS3 & Fedora Core1: + # make clean; make installsp1 + + For Red Hat Enterprise Linux AS4/ES4/WS4: + # make clean; make installsp2 + + The driver files "mxser.o" and utilities will be properly compiled + and copied to system directories respectively. + +------------- Load MOXA driver-------------------- + +3.4.3 Load the MOXA driver +-------------------------- + + :: + + # modprobe mxser + + will activate the module driver. You may run "lsmod" to check + if "mxser" is activated. If the MOXA board is ISA board, the + is needed. Please refer to section "3.4.5" for more + information. + +------------- Load MOXA driver on boot -------------------- + +3.4.4 Load the mxser driver +--------------------------- + + + For the above description, you may manually execute + "modprobe mxser" to activate this driver and run + "rmmod mxser" to remove it. + + However, it's better to have a boot time configuration to + eliminate manual operation. Boot time configuration can be + achieved by rc file. We offer one "rc.mxser" file to simplify + the procedure under "moxa/mxser/driver". + + But if you use ISA board, please modify the "modprobe ..." command + to add the argument (see "3.4.5" section). After modifying the + rc.mxser, please try to execute "/moxa/mxser/driver/rc.mxser" + manually to make sure the modification is ok. If any error + encountered, please try to modify again. If the modification is + completed, follow the below step. + + Run following command for setting rc files:: + + # cd /moxa/mxser/driver + # cp ./rc.mxser /etc/rc.d + # cd /etc/rc.d + + Check "rc.serial" is existed or not. If "rc.serial" doesn't exist, + create it by vi, run "chmod 755 rc.serial" to change the permission. + + Add "/etc/rc.d/rc.mxser" in last line. + + Reboot and check if moxa.o activated by "lsmod" command. + +3.4.5. specify CAP address +-------------------------- + + If you'd like to drive Smartio/Industio ISA boards in the system, + you'll have to add parameter to specify CAP address of given + board while activating "mxser.o". The format for parameters are + as follows.:: + + modprobe mxser ioaddr=0x???,0x???,0x???,0x??? + | | | | + | | | +- 4th ISA board + | | +------ 3rd ISA board + | +------------ 2nd ISA board + +-------------------1st ISA board + +3.5 Static driver configuration for Linux kernel 2.4.x and 2.6.x +================================================================ + + Note: + To use static driver, you must install the linux kernel + source package. + +3.5.1 Backup the built-in driver in the kernel +---------------------------------------------- + + :: + + # cd /usr/src/linux/drivers/char + # mv mxser.c mxser.c.old + + For Red Hat 7.x user, you need to create link: + # cd /usr/src + # ln -s linux-2.4 linux + +3.5.2 Create link +----------------- + :: + + # cd /usr/src/linux/drivers/char + # ln -s /moxa/mxser/driver/mxser.c mxser.c + +3.5.3 Add CAP address list for ISA boards. +------------------------------------------ + + For PCI boards user, please skip this step. + + In module mode, the CAP address for ISA board is given by + parameter. In static driver configuration, you'll have to + assign it within driver's source code. If you will not + install any ISA boards, you may skip to next portion. + The instructions to modify driver source code are as + below. + + a. run:: + + # cd /moxa/mxser/driver + # vi mxser.c + + b. Find the array mxserBoardCAP[] as below:: + + static int mxserBoardCAP[] = {0x00, 0x00, 0x00, 0x00}; + + c. Change the address within this array using vi. For + example, to driver 2 ISA boards with CAP address + 0x280 and 0x180 as 1st and 2nd board. Just to change + the source code as follows:: + + static int mxserBoardCAP[] = {0x280, 0x180, 0x00, 0x00}; + +3.5.4 Setup kernel configuration +-------------------------------- + + Configure the kernel:: + + # cd /usr/src/linux + # make menuconfig + + You will go into a menu-driven system. Please select [Character + devices][Non-standard serial port support], enable the [Moxa + SmartIO support] driver with "[*]" for built-in (not "[M]"), then + select [Exit] to exit this program. + +3.5.5 Rebuild kernel +-------------------- + + The following are for Linux kernel rebuilding, for your + reference only. + + For appropriate details, please refer to the Linux document: + + a. Run the following commands:: + + cd /usr/src/linux + make clean # take a few minutes + make dep # take a few minutes + make bzImage # take probably 10-20 minutes + make install # copy boot image to correct position + + f. Please make sure the boot kernel (vmlinuz) is in the + correct position. + g. If you use 'lilo' utility, you should check /etc/lilo.conf + 'image' item specified the path which is the 'vmlinuz' path, + or you will load wrong (or old) boot kernel image (vmlinuz). + After checking /etc/lilo.conf, please run "lilo". + + Note that if the result of "make bzImage" is ERROR, then you have to + go back to Linux configuration Setup. Type "make menuconfig" in + directory /usr/src/linux. + + +3.5.6 Make tty device and special file +-------------------------------------- + + :: + # cd /moxa/mxser/driver + # ./msmknod + +3.5.7 Make utility +------------------ + + :: + + # cd /moxa/mxser/utility + # make clean; make install + +3.5.8 Reboot +------------ + + + +3.6 Custom configuration +======================== + + Although this driver already provides you default configuration, you + still can change the device name and major number. The instruction to + change these parameters are shown as below. + +a. Change Device name + + If you'd like to use other device names instead of default naming + convention, all you have to do is to modify the internal code + within the shell script "msmknod". First, you have to open "msmknod" + by vi. Locate each line contains "ttyM" and "cum" and change them + to the device name you desired. "msmknod" creates the device names + you need next time executed. + +b. Change Major number + + If major number 30 and 35 had been occupied, you may have to select + 2 free major numbers for this driver. There are 3 steps to change + major numbers. + +3.6.1 Find free major numbers +----------------------------- + + In /proc/devices, you may find all the major numbers occupied + in the system. Please select 2 major numbers that are available. + e.g. 40, 45. + +3.6.2 Create special files +-------------------------- + + Run /moxa/mxser/driver/msmknod to create special files with + specified major numbers. + +3.6.3 Modify driver with new major number +----------------------------------------- + + Run vi to open /moxa/mxser/driver/mxser.c. Locate the line + contains "MXSERMAJOR". Change the content as below:: + + #define MXSERMAJOR 40 + #define MXSERCUMAJOR 45 + + 3.6.4 Run "make clean; make install" in /moxa/mxser/driver. + +3.7 Verify driver installation +============================== + + You may refer to /var/log/messages to check the latest status + log reported by this driver whenever it's activated. + +4. Utilities +^^^^^^^^^^^^ + + There are 3 utilities contained in this driver. They are msdiag, msmon and + msterm. These 3 utilities are released in form of source code. They should + be compiled into executable file and copied into /usr/bin. + + Before using these utilities, please load driver (refer 3.4 & 3.5) and + make sure you had run the "msmknod" utility. + +msdiag - Diagnostic +=================== + + This utility provides the function to display what Moxa Smartio/Industio + board found by driver in the system. + +msmon - Port Monitoring +======================= + + This utility gives the user a quick view about all the MOXA ports' + activities. One can easily learn each port's total received/transmitted + (Rx/Tx) character count since the time when the monitoring is started. + + Rx/Tx throughputs per second are also reported in interval basis (e.g. + the last 5 seconds) and in average basis (since the time the monitoring + is started). You can reset all ports' count by key. <+> <-> + (plus/minus) keys to change the displaying time interval. Press + on the port, that cursor stay, to view the port's communication + parameters, signal status, and input/output queue. + +msterm - Terminal Emulation +=========================== + + This utility provides data sending and receiving ability of all tty ports, + especially for MOXA ports. It is quite useful for testing simple + application, for example, sending AT command to a modem connected to the + port or used as a terminal for login purpose. Note that this is only a + dumb terminal emulation without handling full screen operation. + +5. Setserial +^^^^^^^^^^^^ + + Supported Setserial parameters are listed as below. + + ============== ========================================================= + uart set UART type(16450-->disable FIFO, 16550A-->enable FIFO) + close_delay set the amount of time(in 1/100 of a second) that DTR + should be kept low while being closed. + closing_wait set the amount of time(in 1/100 of a second) that the + serial port should wait for data to be drained while + being closed, before the receiver is disable. + spd_hi Use 57.6kb when the application requests 38.4kb. + spd_vhi Use 115.2kb when the application requests 38.4kb. + spd_shi Use 230.4kb when the application requests 38.4kb. + spd_warp Use 460.8kb when the application requests 38.4kb. + spd_normal Use 38.4kb when the application requests 38.4kb. + spd_cust Use the custom divisor to set the speed when the + application requests 38.4kb. + divisor This option set the custom division. + baud_base This option set the base baud rate. + ============== ========================================================= + +6. Troubleshooting +^^^^^^^^^^^^^^^^^^ + + The boot time error messages and solutions are stated as clearly as + possible. If all the possible solutions fail, please contact our technical + support team to get more help. + + + Error msg: + More than 4 Moxa Smartio/Industio family boards found. Fifth board + and after are ignored. + + Solution: + To avoid this problem, please unplug fifth and after board, because Moxa + driver supports up to 4 boards. + + Error msg: + Request_irq fail, IRQ(?) may be conflict with another device. + + Solution: + Other PCI or ISA devices occupy the assigned IRQ. If you are not sure + which device causes the situation, please check /proc/interrupts to find + free IRQ and simply change another free IRQ for Moxa board. + + Error msg: + Board #: C1xx Series(CAP=xxx) interrupt number invalid. + + Solution: + Each port within the same multiport board shares the same IRQ. Please set + one IRQ (IRQ doesn't equal to zero) for one Moxa board. + + Error msg: + No interrupt vector be set for Moxa ISA board(CAP=xxx). + + Solution: + Moxa ISA board needs an interrupt vector.Please refer to user's manual + "Hardware Installation" chapter to set interrupt vector. + + Error msg: + Couldn't install MOXA Smartio/Industio family driver! + + Solution: + Load Moxa driver fail, the major number may conflict with other devices. + Please refer to previous section 3.7 to change a free major number for + Moxa driver. + + Error msg: + Couldn't install MOXA Smartio/Industio family callout driver! + + Solution: + Load Moxa callout driver fail, the callout device major number may + conflict with other devices. Please refer to previous section 3.7 to + change a free callout device major number for Moxa driver. diff --git a/Documentation/serial/n_gsm.rst b/Documentation/serial/n_gsm.rst new file mode 100644 index 000000000000..f3ad9fd26408 --- /dev/null +++ b/Documentation/serial/n_gsm.rst @@ -0,0 +1,103 @@ +============================== +GSM 0710 tty multiplexor HOWTO +============================== + +This line discipline implements the GSM 07.10 multiplexing protocol +detailed in the following 3GPP document: + + http://www.3gpp.org/ftp/Specs/archive/07_series/07.10/0710-720.zip + +This document give some hints on how to use this driver with GPRS and 3G +modems connected to a physical serial port. + +How to use it +------------- +1. initialize the modem in 0710 mux mode (usually AT+CMUX= command) through + its serial port. Depending on the modem used, you can pass more or less + parameters to this command, +2. switch the serial line to using the n_gsm line discipline by using + TIOCSETD ioctl, +3. configure the mux using GSMIOC_GETCONF / GSMIOC_SETCONF ioctl, + +Major parts of the initialization program : +(a good starting point is util-linux-ng/sys-utils/ldattach.c):: + + #include + #define N_GSM0710 21 /* GSM 0710 Mux */ + #define DEFAULT_SPEED B115200 + #define SERIAL_PORT /dev/ttyS0 + + int ldisc = N_GSM0710; + struct gsm_config c; + struct termios configuration; + + /* open the serial port connected to the modem */ + fd = open(SERIAL_PORT, O_RDWR | O_NOCTTY | O_NDELAY); + + /* configure the serial port : speed, flow control ... */ + + /* send the AT commands to switch the modem to CMUX mode + and check that it's successful (should return OK) */ + write(fd, "AT+CMUX=0\r", 10); + + /* experience showed that some modems need some time before + being able to answer to the first MUX packet so a delay + may be needed here in some case */ + sleep(3); + + /* use n_gsm line discipline */ + ioctl(fd, TIOCSETD, &ldisc); + + /* get n_gsm configuration */ + ioctl(fd, GSMIOC_GETCONF, &c); + /* we are initiator and need encoding 0 (basic) */ + c.initiator = 1; + c.encapsulation = 0; + /* our modem defaults to a maximum size of 127 bytes */ + c.mru = 127; + c.mtu = 127; + /* set the new configuration */ + ioctl(fd, GSMIOC_SETCONF, &c); + + /* and wait for ever to keep the line discipline enabled */ + daemon(0,0); + pause(); + +4. create the devices corresponding to the "virtual" serial ports (take care, + each modem has its configuration and some DLC have dedicated functions, + for example GPS), starting with minor 1 (DLC0 is reserved for the management + of the mux):: + + MAJOR=`cat /proc/devices |grep gsmtty | awk '{print $1}` + for i in `seq 1 4`; do + mknod /dev/ttygsm$i c $MAJOR $i + done + +5. use these devices as plain serial ports. + + for example, it's possible: + + - and to use gnokii to send / receive SMS on ttygsm1 + - to use ppp to establish a datalink on ttygsm2 + +6. first close all virtual ports before closing the physical port. + + Note that after closing the physical port the modem is still in multiplexing + mode. This may prevent a successful re-opening of the port later. To avoid + this situation either reset the modem if your hardware allows that or send + a disconnect command frame manually before initializing the multiplexing mode + for the second time. The byte sequence for the disconnect command frame is:: + + 0xf9, 0x03, 0xef, 0x03, 0xc3, 0x16, 0xf9. + +Additional Documentation +------------------------ +More practical details on the protocol and how it's supported by industrial +modems can be found in the following documents : + +- http://www.telit.com/module/infopool/download.php?id=616 +- http://www.u-blox.com/images/downloads/Product_Docs/LEON-G100-G200-MuxImplementation_ApplicationNote_%28GSM%20G1-CS-10002%29.pdf +- http://www.sierrawireless.com/Support/Downloads/AirPrime/WMP_Series/~/media/Support_Downloads/AirPrime/Application_notes/CMUX_Feature_Application_Note-Rev004.ashx +- http://wm.sim.com/sim/News/photo/2010721161442.pdf + +11-03-08 - Eric Bénard - diff --git a/Documentation/serial/n_gsm.txt b/Documentation/serial/n_gsm.txt deleted file mode 100644 index 875361bb7cb4..000000000000 --- a/Documentation/serial/n_gsm.txt +++ /dev/null @@ -1,96 +0,0 @@ -n_gsm.c GSM 0710 tty multiplexor HOWTO -=================================================== - -This line discipline implements the GSM 07.10 multiplexing protocol -detailed in the following 3GPP document : -http://www.3gpp.org/ftp/Specs/archive/07_series/07.10/0710-720.zip - -This document give some hints on how to use this driver with GPRS and 3G -modems connected to a physical serial port. - -How to use it -------------- -1- initialize the modem in 0710 mux mode (usually AT+CMUX= command) through -its serial port. Depending on the modem used, you can pass more or less -parameters to this command, -2- switch the serial line to using the n_gsm line discipline by using -TIOCSETD ioctl, -3- configure the mux using GSMIOC_GETCONF / GSMIOC_SETCONF ioctl, - -Major parts of the initialization program : -(a good starting point is util-linux-ng/sys-utils/ldattach.c) -#include -#define N_GSM0710 21 /* GSM 0710 Mux */ -#define DEFAULT_SPEED B115200 -#define SERIAL_PORT /dev/ttyS0 - - int ldisc = N_GSM0710; - struct gsm_config c; - struct termios configuration; - - /* open the serial port connected to the modem */ - fd = open(SERIAL_PORT, O_RDWR | O_NOCTTY | O_NDELAY); - - /* configure the serial port : speed, flow control ... */ - - /* send the AT commands to switch the modem to CMUX mode - and check that it's successful (should return OK) */ - write(fd, "AT+CMUX=0\r", 10); - - /* experience showed that some modems need some time before - being able to answer to the first MUX packet so a delay - may be needed here in some case */ - sleep(3); - - /* use n_gsm line discipline */ - ioctl(fd, TIOCSETD, &ldisc); - - /* get n_gsm configuration */ - ioctl(fd, GSMIOC_GETCONF, &c); - /* we are initiator and need encoding 0 (basic) */ - c.initiator = 1; - c.encapsulation = 0; - /* our modem defaults to a maximum size of 127 bytes */ - c.mru = 127; - c.mtu = 127; - /* set the new configuration */ - ioctl(fd, GSMIOC_SETCONF, &c); - - /* and wait for ever to keep the line discipline enabled */ - daemon(0,0); - pause(); - -4- create the devices corresponding to the "virtual" serial ports (take care, -each modem has its configuration and some DLC have dedicated functions, -for example GPS), starting with minor 1 (DLC0 is reserved for the management -of the mux) - -MAJOR=`cat /proc/devices |grep gsmtty | awk '{print $1}` -for i in `seq 1 4`; do - mknod /dev/ttygsm$i c $MAJOR $i -done - -5- use these devices as plain serial ports. -for example, it's possible : -- and to use gnokii to send / receive SMS on ttygsm1 -- to use ppp to establish a datalink on ttygsm2 - -6- first close all virtual ports before closing the physical port. - -Note that after closing the physical port the modem is still in multiplexing -mode. This may prevent a successful re-opening of the port later. To avoid -this situation either reset the modem if your hardware allows that or send -a disconnect command frame manually before initializing the multiplexing mode -for the second time. The byte sequence for the disconnect command frame is: -0xf9, 0x03, 0xef, 0x03, 0xc3, 0x16, 0xf9. - -Additional Documentation ------------------------- -More practical details on the protocol and how it's supported by industrial -modems can be found in the following documents : -http://www.telit.com/module/infopool/download.php?id=616 -http://www.u-blox.com/images/downloads/Product_Docs/LEON-G100-G200-MuxImplementation_ApplicationNote_%28GSM%20G1-CS-10002%29.pdf -http://www.sierrawireless.com/Support/Downloads/AirPrime/WMP_Series/~/media/Support_Downloads/AirPrime/Application_notes/CMUX_Feature_Application_Note-Rev004.ashx -http://wm.sim.com/sim/News/photo/2010721161442.pdf - -11-03-08 - Eric Bénard - diff --git a/Documentation/serial/rocket.rst b/Documentation/serial/rocket.rst new file mode 100644 index 000000000000..23761eae4282 --- /dev/null +++ b/Documentation/serial/rocket.rst @@ -0,0 +1,185 @@ +================================================ +Comtrol(tm) RocketPort(R)/RocketModem(TM) Series +================================================ + +Device Driver for the Linux Operating System +============================================ + +Product overview +---------------- + +This driver provides a loadable kernel driver for the Comtrol RocketPort +and RocketModem PCI boards. These boards provide, 2, 4, 8, 16, or 32 +high-speed serial ports or modems. This driver supports up to a combination +of four RocketPort or RocketModems boards in one machine simultaneously. +This file assumes that you are using the RocketPort driver which is +integrated into the kernel sources. + +The driver can also be installed as an external module using the usual +"make;make install" routine. This external module driver, obtainable +from the Comtrol website listed below, is useful for updating the driver +or installing it into kernels which do not have the driver configured +into them. Installations instructions for the external module +are in the included README and HW_INSTALL files. + +RocketPort ISA and RocketModem II PCI boards currently are only supported by +this driver in module form. + +The RocketPort ISA board requires I/O ports to be configured by the DIP +switches on the board. See the section "ISA Rocketport Boards" below for +information on how to set the DIP switches. + +You pass the I/O port to the driver using the following module parameters: + +board1: + I/O port for the first ISA board +board2: + I/O port for the second ISA board +board3: + I/O port for the third ISA board +board4: + I/O port for the fourth ISA board + +There is a set of utilities and scripts provided with the external driver +(downloadable from http://www.comtrol.com) that ease the configuration and +setup of the ISA cards. + +The RocketModem II PCI boards require firmware to be loaded into the card +before it will function. The driver has only been tested as a module for this +board. + +Installation Procedures +----------------------- + +RocketPort/RocketModem PCI cards require no driver configuration, they are +automatically detected and configured. + +The RocketPort driver can be installed as a module (recommended) or built +into the kernel. This is selected, as for other drivers, through the `make config` +command from the root of the Linux source tree during the kernel build process. + +The RocketPort/RocketModem serial ports installed by this driver are assigned +device major number 46, and will be named /dev/ttyRx, where x is the port number +starting at zero (ex. /dev/ttyR0, /devttyR1, ...). If you have multiple cards +installed in the system, the mapping of port names to serial ports is displayed +in the system log at /var/log/messages. + +If installed as a module, the module must be loaded. This can be done +manually by entering "modprobe rocket". To have the module loaded automatically +upon system boot, edit a `/etc/modprobe.d/*.conf` file and add the line +"alias char-major-46 rocket". + +In order to use the ports, their device names (nodes) must be created with mknod. +This is only required once, the system will retain the names once created. To +create the RocketPort/RocketModem device names, use the command +"mknod /dev/ttyRx c 46 x" where x is the port number starting at zero. + +For example:: + + > mknod /dev/ttyR0 c 46 0 + > mknod /dev/ttyR1 c 46 1 + > mknod /dev/ttyR2 c 46 2 + +The Linux script MAKEDEV will create the first 16 ttyRx device names (nodes) +for you:: + + >/dev/MAKEDEV ttyR + +ISA Rocketport Boards +--------------------- + +You must assign and configure the I/O addresses used by the ISA Rocketport +card before installing and using it. This is done by setting a set of DIP +switches on the Rocketport board. + + +Setting the I/O address +----------------------- + +Before installing RocketPort(R) or RocketPort RA boards, you must find +a range of I/O addresses for it to use. The first RocketPort card +requires a 68-byte contiguous block of I/O addresses, starting at one +of the following: 0x100h, 0x140h, 0x180h, 0x200h, 0x240h, 0x280h, +0x300h, 0x340h, 0x380h. This I/O address must be reflected in the DIP +switches of *all* of the Rocketport cards. + +The second, third, and fourth RocketPort cards require a 64-byte +contiguous block of I/O addresses, starting at one of the following +I/O addresses: 0x100h, 0x140h, 0x180h, 0x1C0h, 0x200h, 0x240h, 0x280h, +0x2C0h, 0x300h, 0x340h, 0x380h, 0x3C0h. The I/O address used by the +second, third, and fourth Rocketport cards (if present) are set via +software control. The DIP switch settings for the I/O address must be +set to the value of the first Rocketport cards. + +In order to distinguish each of the card from the others, each card +must have a unique board ID set on the dip switches. The first +Rocketport board must be set with the DIP switches corresponding to +the first board, the second board must be set with the DIP switches +corresponding to the second board, etc. IMPORTANT: The board ID is +the only place where the DIP switch settings should differ between the +various Rocketport boards in a system. + +The I/O address range used by any of the RocketPort cards must not +conflict with any other cards in the system, including other +RocketPort cards. Below, you will find a list of commonly used I/O +address ranges which may be in use by other devices in your system. +On a Linux system, "cat /proc/ioports" will also be helpful in +identifying what I/O addresses are being used by devices on your +system. + +Remember, the FIRST RocketPort uses 68 I/O addresses. So, if you set it +for 0x100, it will occupy 0x100 to 0x143. This would mean that you +CAN NOT set the second, third or fourth board for address 0x140 since +the first 4 bytes of that range are used by the first board. You would +need to set the second, third, or fourth board to one of the next available +blocks such as 0x180. + +RocketPort and RocketPort RA SW1 Settings:: + + +-------------------------------+ + | 8 | 7 | 6 | 5 | 4 | 3 | 2 | 1 | + +-------+-------+---------------+ + | Unused| Card | I/O Port Block| + +-------------------------------+ + + DIP Switches DIP Switches + 7 8 6 5 + =================== =================== + On On UNUSED, MUST BE ON. On On First Card <==== Default + On Off Second Card + Off On Third Card + Off Off Fourth Card + + DIP Switches I/O Address Range + 4 3 2 1 Used by the First Card + ===================================== + On Off On Off 100-143 + On Off Off On 140-183 + On Off Off Off 180-1C3 <==== Default + Off On On Off 200-243 + Off On Off On 240-283 + Off On Off Off 280-2C3 + Off Off On Off 300-343 + Off Off Off On 340-383 + Off Off Off Off 380-3C3 + +Reporting Bugs +-------------- + +For technical support, please provide the following +information: Driver version, kernel release, distribution of +kernel, and type of board you are using. Error messages and log +printouts port configuration details are especially helpful. + +USA: + :Phone: (612) 494-4100 + :FAX: (612) 494-4199 + :email: support@comtrol.com + +Comtrol Europe: + :Phone: +44 (0) 1 869 323-220 + :FAX: +44 (0) 1 869 323-211 + :email: support@comtrol.co.uk + +Web: http://www.comtrol.com +FTP: ftp.comtrol.com diff --git a/Documentation/serial/rocket.txt b/Documentation/serial/rocket.txt deleted file mode 100644 index 60b039891057..000000000000 --- a/Documentation/serial/rocket.txt +++ /dev/null @@ -1,189 +0,0 @@ -Comtrol(tm) RocketPort(R)/RocketModem(TM) Series -Device Driver for the Linux Operating System - -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=- - -PRODUCT OVERVIEW ----------------- - -This driver provides a loadable kernel driver for the Comtrol RocketPort -and RocketModem PCI boards. These boards provide, 2, 4, 8, 16, or 32 -high-speed serial ports or modems. This driver supports up to a combination -of four RocketPort or RocketModems boards in one machine simultaneously. -This file assumes that you are using the RocketPort driver which is -integrated into the kernel sources. - -The driver can also be installed as an external module using the usual -"make;make install" routine. This external module driver, obtainable -from the Comtrol website listed below, is useful for updating the driver -or installing it into kernels which do not have the driver configured -into them. Installations instructions for the external module -are in the included README and HW_INSTALL files. - -RocketPort ISA and RocketModem II PCI boards currently are only supported by -this driver in module form. - -The RocketPort ISA board requires I/O ports to be configured by the DIP -switches on the board. See the section "ISA Rocketport Boards" below for -information on how to set the DIP switches. - -You pass the I/O port to the driver using the following module parameters: - -board1 : I/O port for the first ISA board -board2 : I/O port for the second ISA board -board3 : I/O port for the third ISA board -board4 : I/O port for the fourth ISA board - -There is a set of utilities and scripts provided with the external driver -( downloadable from http://www.comtrol.com ) that ease the configuration and -setup of the ISA cards. - -The RocketModem II PCI boards require firmware to be loaded into the card -before it will function. The driver has only been tested as a module for this -board. - -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=- - -INSTALLATION PROCEDURES ------------------------ - -RocketPort/RocketModem PCI cards require no driver configuration, they are -automatically detected and configured. - -The RocketPort driver can be installed as a module (recommended) or built -into the kernel. This is selected, as for other drivers, through the `make config` -command from the root of the Linux source tree during the kernel build process. - -The RocketPort/RocketModem serial ports installed by this driver are assigned -device major number 46, and will be named /dev/ttyRx, where x is the port number -starting at zero (ex. /dev/ttyR0, /devttyR1, ...). If you have multiple cards -installed in the system, the mapping of port names to serial ports is displayed -in the system log at /var/log/messages. - -If installed as a module, the module must be loaded. This can be done -manually by entering "modprobe rocket". To have the module loaded automatically -upon system boot, edit a /etc/modprobe.d/*.conf file and add the line -"alias char-major-46 rocket". - -In order to use the ports, their device names (nodes) must be created with mknod. -This is only required once, the system will retain the names once created. To -create the RocketPort/RocketModem device names, use the command -"mknod /dev/ttyRx c 46 x" where x is the port number starting at zero. For example: - ->mknod /dev/ttyR0 c 46 0 ->mknod /dev/ttyR1 c 46 1 ->mknod /dev/ttyR2 c 46 2 - -The Linux script MAKEDEV will create the first 16 ttyRx device names (nodes) -for you: - ->/dev/MAKEDEV ttyR - -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=- - -ISA Rocketport Boards ---------------------- - -You must assign and configure the I/O addresses used by the ISA Rocketport -card before installing and using it. This is done by setting a set of DIP -switches on the Rocketport board. - - -SETTING THE I/O ADDRESS ------------------------ - -Before installing RocketPort(R) or RocketPort RA boards, you must find -a range of I/O addresses for it to use. The first RocketPort card -requires a 68-byte contiguous block of I/O addresses, starting at one -of the following: 0x100h, 0x140h, 0x180h, 0x200h, 0x240h, 0x280h, -0x300h, 0x340h, 0x380h. This I/O address must be reflected in the DIP -switches of *all* of the Rocketport cards. - -The second, third, and fourth RocketPort cards require a 64-byte -contiguous block of I/O addresses, starting at one of the following -I/O addresses: 0x100h, 0x140h, 0x180h, 0x1C0h, 0x200h, 0x240h, 0x280h, -0x2C0h, 0x300h, 0x340h, 0x380h, 0x3C0h. The I/O address used by the -second, third, and fourth Rocketport cards (if present) are set via -software control. The DIP switch settings for the I/O address must be -set to the value of the first Rocketport cards. - -In order to distinguish each of the card from the others, each card -must have a unique board ID set on the dip switches. The first -Rocketport board must be set with the DIP switches corresponding to -the first board, the second board must be set with the DIP switches -corresponding to the second board, etc. IMPORTANT: The board ID is -the only place where the DIP switch settings should differ between the -various Rocketport boards in a system. - -The I/O address range used by any of the RocketPort cards must not -conflict with any other cards in the system, including other -RocketPort cards. Below, you will find a list of commonly used I/O -address ranges which may be in use by other devices in your system. -On a Linux system, "cat /proc/ioports" will also be helpful in -identifying what I/O addresses are being used by devices on your -system. - -Remember, the FIRST RocketPort uses 68 I/O addresses. So, if you set it -for 0x100, it will occupy 0x100 to 0x143. This would mean that you -CAN NOT set the second, third or fourth board for address 0x140 since -the first 4 bytes of that range are used by the first board. You would -need to set the second, third, or fourth board to one of the next available -blocks such as 0x180. - -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=- - -RocketPort and RocketPort RA SW1 Settings: - - +-------------------------------+ - | 8 | 7 | 6 | 5 | 4 | 3 | 2 | 1 | - +-------+-------+---------------+ - | Unused| Card | I/O Port Block| - +-------------------------------+ - -DIP Switches DIP Switches -7 8 6 5 -=================== =================== -On On UNUSED, MUST BE ON. On On First Card <==== Default - On Off Second Card - Off On Third Card - Off Off Fourth Card - -DIP Switches I/O Address Range -4 3 2 1 Used by the First Card -===================================== -On Off On Off 100-143 -On Off Off On 140-183 -On Off Off Off 180-1C3 <==== Default -Off On On Off 200-243 -Off On Off On 240-283 -Off On Off Off 280-2C3 -Off Off On Off 300-343 -Off Off Off On 340-383 -Off Off Off Off 380-3C3 - -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=- - -REPORTING BUGS --------------- - -For technical support, please provide the following -information: Driver version, kernel release, distribution of -kernel, and type of board you are using. Error messages and log -printouts port configuration details are especially helpful. - -USA - Phone: (612) 494-4100 - FAX: (612) 494-4199 - email: support@comtrol.com - -Comtrol Europe - Phone: +44 (0) 1 869 323-220 - FAX: +44 (0) 1 869 323-211 - email: support@comtrol.co.uk - -Web: http://www.comtrol.com -FTP: ftp.comtrol.com - -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=- - - diff --git a/Documentation/serial/serial-iso7816.rst b/Documentation/serial/serial-iso7816.rst new file mode 100644 index 000000000000..d990143de0c6 --- /dev/null +++ b/Documentation/serial/serial-iso7816.rst @@ -0,0 +1,90 @@ +============================= +ISO7816 Serial Communications +============================= + +1. Introduction +=============== + + ISO/IEC7816 is a series of standards specifying integrated circuit cards (ICC) + also known as smart cards. + +2. Hardware-related considerations +================================== + + Some CPUs/UARTs (e.g., Microchip AT91) contain a built-in mode capable of + handling communication with a smart card. + + For these microcontrollers, the Linux driver should be made capable of + working in both modes, and proper ioctls (see later) should be made + available at user-level to allow switching from one mode to the other, and + vice versa. + +3. Data Structures Already Available in the Kernel +================================================== + + The Linux kernel provides the serial_iso7816 structure (see [1]) to handle + ISO7816 communications. This data structure is used to set and configure + ISO7816 parameters in ioctls. + + Any driver for devices capable of working both as RS232 and ISO7816 should + implement the iso7816_config callback in the uart_port structure. The + serial_core calls iso7816_config to do the device specific part in response + to TIOCGISO7816 and TIOCSISO7816 ioctls (see below). The iso7816_config + callback receives a pointer to struct serial_iso7816. + +4. Usage from user-level +======================== + + From user-level, ISO7816 configuration can be get/set using the previous + ioctls. For instance, to set ISO7816 you can use the following code:: + + #include + + /* Include definition for ISO7816 ioctls: TIOCSISO7816 and TIOCGISO7816 */ + #include + + /* Open your specific device (e.g., /dev/mydevice): */ + int fd = open ("/dev/mydevice", O_RDWR); + if (fd < 0) { + /* Error handling. See errno. */ + } + + struct serial_iso7816 iso7816conf; + + /* Reserved fields as to be zeroed */ + memset(&iso7816conf, 0, sizeof(iso7816conf)); + + /* Enable ISO7816 mode: */ + iso7816conf.flags |= SER_ISO7816_ENABLED; + + /* Select the protocol: */ + /* T=0 */ + iso7816conf.flags |= SER_ISO7816_T(0); + /* or T=1 */ + iso7816conf.flags |= SER_ISO7816_T(1); + + /* Set the guard time: */ + iso7816conf.tg = 2; + + /* Set the clock frequency*/ + iso7816conf.clk = 3571200; + + /* Set transmission factors: */ + iso7816conf.sc_fi = 372; + iso7816conf.sc_di = 1; + + if (ioctl(fd_usart, TIOCSISO7816, &iso7816conf) < 0) { + /* Error handling. See errno. */ + } + + /* Use read() and write() syscalls here... */ + + /* Close the device when finished: */ + if (close (fd) < 0) { + /* Error handling. See errno. */ + } + +5. References +============= + + [1] include/uapi/linux/serial.h diff --git a/Documentation/serial/serial-iso7816.txt b/Documentation/serial/serial-iso7816.txt deleted file mode 100644 index 3193d24a2b0f..000000000000 --- a/Documentation/serial/serial-iso7816.txt +++ /dev/null @@ -1,83 +0,0 @@ - ISO7816 SERIAL COMMUNICATIONS - -1. INTRODUCTION - - ISO/IEC7816 is a series of standards specifying integrated circuit cards (ICC) - also known as smart cards. - -2. HARDWARE-RELATED CONSIDERATIONS - - Some CPUs/UARTs (e.g., Microchip AT91) contain a built-in mode capable of - handling communication with a smart card. - - For these microcontrollers, the Linux driver should be made capable of - working in both modes, and proper ioctls (see later) should be made - available at user-level to allow switching from one mode to the other, and - vice versa. - -3. DATA STRUCTURES ALREADY AVAILABLE IN THE KERNEL - - The Linux kernel provides the serial_iso7816 structure (see [1]) to handle - ISO7816 communications. This data structure is used to set and configure - ISO7816 parameters in ioctls. - - Any driver for devices capable of working both as RS232 and ISO7816 should - implement the iso7816_config callback in the uart_port structure. The - serial_core calls iso7816_config to do the device specific part in response - to TIOCGISO7816 and TIOCSISO7816 ioctls (see below). The iso7816_config - callback receives a pointer to struct serial_iso7816. - -4. USAGE FROM USER-LEVEL - - From user-level, ISO7816 configuration can be get/set using the previous - ioctls. For instance, to set ISO7816 you can use the following code: - - #include - - /* Include definition for ISO7816 ioctls: TIOCSISO7816 and TIOCGISO7816 */ - #include - - /* Open your specific device (e.g., /dev/mydevice): */ - int fd = open ("/dev/mydevice", O_RDWR); - if (fd < 0) { - /* Error handling. See errno. */ - } - - struct serial_iso7816 iso7816conf; - - /* Reserved fields as to be zeroed */ - memset(&iso7816conf, 0, sizeof(iso7816conf)); - - /* Enable ISO7816 mode: */ - iso7816conf.flags |= SER_ISO7816_ENABLED; - - /* Select the protocol: */ - /* T=0 */ - iso7816conf.flags |= SER_ISO7816_T(0); - /* or T=1 */ - iso7816conf.flags |= SER_ISO7816_T(1); - - /* Set the guard time: */ - iso7816conf.tg = 2; - - /* Set the clock frequency*/ - iso7816conf.clk = 3571200; - - /* Set transmission factors: */ - iso7816conf.sc_fi = 372; - iso7816conf.sc_di = 1; - - if (ioctl(fd_usart, TIOCSISO7816, &iso7816conf) < 0) { - /* Error handling. See errno. */ - } - - /* Use read() and write() syscalls here... */ - - /* Close the device when finished: */ - if (close (fd) < 0) { - /* Error handling. See errno. */ - } - -5. REFERENCES - - [1] include/uapi/linux/serial.h diff --git a/Documentation/serial/serial-rs485.rst b/Documentation/serial/serial-rs485.rst new file mode 100644 index 000000000000..6bc824f948f9 --- /dev/null +++ b/Documentation/serial/serial-rs485.rst @@ -0,0 +1,103 @@ +=========================== +RS485 Serial Communications +=========================== + +1. Introduction +=============== + + EIA-485, also known as TIA/EIA-485 or RS-485, is a standard defining the + electrical characteristics of drivers and receivers for use in balanced + digital multipoint systems. + This standard is widely used for communications in industrial automation + because it can be used effectively over long distances and in electrically + noisy environments. + +2. Hardware-related Considerations +================================== + + Some CPUs/UARTs (e.g., Atmel AT91 or 16C950 UART) contain a built-in + half-duplex mode capable of automatically controlling line direction by + toggling RTS or DTR signals. That can be used to control external + half-duplex hardware like an RS485 transceiver or any RS232-connected + half-duplex devices like some modems. + + For these microcontrollers, the Linux driver should be made capable of + working in both modes, and proper ioctls (see later) should be made + available at user-level to allow switching from one mode to the other, and + vice versa. + +3. Data Structures Already Available in the Kernel +================================================== + + The Linux kernel provides the serial_rs485 structure (see [1]) to handle + RS485 communications. This data structure is used to set and configure RS485 + parameters in the platform data and in ioctls. + + The device tree can also provide RS485 boot time parameters (see [2] + for bindings). The driver is in charge of filling this data structure from + the values given by the device tree. + + Any driver for devices capable of working both as RS232 and RS485 should + implement the rs485_config callback in the uart_port structure. The + serial_core calls rs485_config to do the device specific part in response + to TIOCSRS485 and TIOCGRS485 ioctls (see below). The rs485_config callback + receives a pointer to struct serial_rs485. + +4. Usage from user-level +======================== + + From user-level, RS485 configuration can be get/set using the previous + ioctls. For instance, to set RS485 you can use the following code:: + + #include + + /* Include definition for RS485 ioctls: TIOCGRS485 and TIOCSRS485 */ + #include + + /* Open your specific device (e.g., /dev/mydevice): */ + int fd = open ("/dev/mydevice", O_RDWR); + if (fd < 0) { + /* Error handling. See errno. */ + } + + struct serial_rs485 rs485conf; + + /* Enable RS485 mode: */ + rs485conf.flags |= SER_RS485_ENABLED; + + /* Set logical level for RTS pin equal to 1 when sending: */ + rs485conf.flags |= SER_RS485_RTS_ON_SEND; + /* or, set logical level for RTS pin equal to 0 when sending: */ + rs485conf.flags &= ~(SER_RS485_RTS_ON_SEND); + + /* Set logical level for RTS pin equal to 1 after sending: */ + rs485conf.flags |= SER_RS485_RTS_AFTER_SEND; + /* or, set logical level for RTS pin equal to 0 after sending: */ + rs485conf.flags &= ~(SER_RS485_RTS_AFTER_SEND); + + /* Set rts delay before send, if needed: */ + rs485conf.delay_rts_before_send = ...; + + /* Set rts delay after send, if needed: */ + rs485conf.delay_rts_after_send = ...; + + /* Set this flag if you want to receive data even while sending data */ + rs485conf.flags |= SER_RS485_RX_DURING_TX; + + if (ioctl (fd, TIOCSRS485, &rs485conf) < 0) { + /* Error handling. See errno. */ + } + + /* Use read() and write() syscalls here... */ + + /* Close the device when finished: */ + if (close (fd) < 0) { + /* Error handling. See errno. */ + } + +5. References +============= + + [1] include/uapi/linux/serial.h + + [2] Documentation/devicetree/bindings/serial/rs485.txt diff --git a/Documentation/serial/serial-rs485.txt b/Documentation/serial/serial-rs485.txt deleted file mode 100644 index ce0c1a9b8aab..000000000000 --- a/Documentation/serial/serial-rs485.txt +++ /dev/null @@ -1,95 +0,0 @@ - RS485 SERIAL COMMUNICATIONS - -1. INTRODUCTION - - EIA-485, also known as TIA/EIA-485 or RS-485, is a standard defining the - electrical characteristics of drivers and receivers for use in balanced - digital multipoint systems. - This standard is widely used for communications in industrial automation - because it can be used effectively over long distances and in electrically - noisy environments. - -2. HARDWARE-RELATED CONSIDERATIONS - - Some CPUs/UARTs (e.g., Atmel AT91 or 16C950 UART) contain a built-in - half-duplex mode capable of automatically controlling line direction by - toggling RTS or DTR signals. That can be used to control external - half-duplex hardware like an RS485 transceiver or any RS232-connected - half-duplex devices like some modems. - - For these microcontrollers, the Linux driver should be made capable of - working in both modes, and proper ioctls (see later) should be made - available at user-level to allow switching from one mode to the other, and - vice versa. - -3. DATA STRUCTURES ALREADY AVAILABLE IN THE KERNEL - - The Linux kernel provides the serial_rs485 structure (see [1]) to handle - RS485 communications. This data structure is used to set and configure RS485 - parameters in the platform data and in ioctls. - - The device tree can also provide RS485 boot time parameters (see [2] - for bindings). The driver is in charge of filling this data structure from - the values given by the device tree. - - Any driver for devices capable of working both as RS232 and RS485 should - implement the rs485_config callback in the uart_port structure. The - serial_core calls rs485_config to do the device specific part in response - to TIOCSRS485 and TIOCGRS485 ioctls (see below). The rs485_config callback - receives a pointer to struct serial_rs485. - -4. USAGE FROM USER-LEVEL - - From user-level, RS485 configuration can be get/set using the previous - ioctls. For instance, to set RS485 you can use the following code: - - #include - - /* Include definition for RS485 ioctls: TIOCGRS485 and TIOCSRS485 */ - #include - - /* Open your specific device (e.g., /dev/mydevice): */ - int fd = open ("/dev/mydevice", O_RDWR); - if (fd < 0) { - /* Error handling. See errno. */ - } - - struct serial_rs485 rs485conf; - - /* Enable RS485 mode: */ - rs485conf.flags |= SER_RS485_ENABLED; - - /* Set logical level for RTS pin equal to 1 when sending: */ - rs485conf.flags |= SER_RS485_RTS_ON_SEND; - /* or, set logical level for RTS pin equal to 0 when sending: */ - rs485conf.flags &= ~(SER_RS485_RTS_ON_SEND); - - /* Set logical level for RTS pin equal to 1 after sending: */ - rs485conf.flags |= SER_RS485_RTS_AFTER_SEND; - /* or, set logical level for RTS pin equal to 0 after sending: */ - rs485conf.flags &= ~(SER_RS485_RTS_AFTER_SEND); - - /* Set rts delay before send, if needed: */ - rs485conf.delay_rts_before_send = ...; - - /* Set rts delay after send, if needed: */ - rs485conf.delay_rts_after_send = ...; - - /* Set this flag if you want to receive data even while sending data */ - rs485conf.flags |= SER_RS485_RX_DURING_TX; - - if (ioctl (fd, TIOCSRS485, &rs485conf) < 0) { - /* Error handling. See errno. */ - } - - /* Use read() and write() syscalls here... */ - - /* Close the device when finished: */ - if (close (fd) < 0) { - /* Error handling. See errno. */ - } - -5. REFERENCES - - [1] include/uapi/linux/serial.h - [2] Documentation/devicetree/bindings/serial/rs485.txt diff --git a/Documentation/serial/tty.rst b/Documentation/serial/tty.rst new file mode 100644 index 000000000000..dd972caacf3e --- /dev/null +++ b/Documentation/serial/tty.rst @@ -0,0 +1,328 @@ +================= +The Lockronomicon +================= + +Your guide to the ancient and twisted locking policies of the tty layer and +the warped logic behind them. Beware all ye who read on. + + +Line Discipline +--------------- + +Line disciplines are registered with tty_register_ldisc() passing the +discipline number and the ldisc structure. At the point of registration the +discipline must be ready to use and it is possible it will get used before +the call returns success. If the call returns an error then it won't get +called. Do not re-use ldisc numbers as they are part of the userspace ABI +and writing over an existing ldisc will cause demons to eat your computer. +After the return the ldisc data has been copied so you may free your own +copy of the structure. You must not re-register over the top of the line +discipline even with the same data or your computer again will be eaten by +demons. + +In order to remove a line discipline call tty_unregister_ldisc(). +In ancient times this always worked. In modern times the function will +return -EBUSY if the ldisc is currently in use. Since the ldisc referencing +code manages the module counts this should not usually be a concern. + +Heed this warning: the reference count field of the registered copies of the +tty_ldisc structure in the ldisc table counts the number of lines using this +discipline. The reference count of the tty_ldisc structure within a tty +counts the number of active users of the ldisc at this instant. In effect it +counts the number of threads of execution within an ldisc method (plus those +about to enter and exit although this detail matters not). + +Line Discipline Methods +----------------------- + +TTY side interfaces +^^^^^^^^^^^^^^^^^^^ + +======================= ======================================================= +open() Called when the line discipline is attached to + the terminal. No other call into the line + discipline for this tty will occur until it + completes successfully. Should initialize any + state needed by the ldisc, and set receive_room + in the tty_struct to the maximum amount of data + the line discipline is willing to accept from the + driver with a single call to receive_buf(). + Returning an error will prevent the ldisc from + being attached. Can sleep. + +close() This is called on a terminal when the line + discipline is being unplugged. At the point of + execution no further users will enter the + ldisc code for this tty. Can sleep. + +hangup() Called when the tty line is hung up. + The line discipline should cease I/O to the tty. + No further calls into the ldisc code will occur. + The return value is ignored. Can sleep. + +read() (optional) A process requests reading data from + the line. Multiple read calls may occur in parallel + and the ldisc must deal with serialization issues. + If not defined, the process will receive an EIO + error. May sleep. + +write() (optional) A process requests writing data to the + line. Multiple write calls are serialized by the + tty layer for the ldisc. If not defined, the + process will receive an EIO error. May sleep. + +flush_buffer() (optional) May be called at any point between + open and close, and instructs the line discipline + to empty its input buffer. + +set_termios() (optional) Called on termios structure changes. + The caller passes the old termios data and the + current data is in the tty. Called under the + termios semaphore so allowed to sleep. Serialized + against itself only. + +poll() (optional) Check the status for the poll/select + calls. Multiple poll calls may occur in parallel. + May sleep. + +ioctl() (optional) Called when an ioctl is handed to the + tty layer that might be for the ldisc. Multiple + ioctl calls may occur in parallel. May sleep. + +compat_ioctl() (optional) Called when a 32 bit ioctl is handed + to the tty layer that might be for the ldisc. + Multiple ioctl calls may occur in parallel. + May sleep. +======================= ======================================================= + +Driver Side Interfaces +^^^^^^^^^^^^^^^^^^^^^^ + +======================= ======================================================= +receive_buf() (optional) Called by the low-level driver to hand + a buffer of received bytes to the ldisc for + processing. The number of bytes is guaranteed not + to exceed the current value of tty->receive_room. + All bytes must be processed. + +receive_buf2() (optional) Called by the low-level driver to hand + a buffer of received bytes to the ldisc for + processing. Returns the number of bytes processed. + + If both receive_buf() and receive_buf2() are + defined, receive_buf2() should be preferred. + +write_wakeup() May be called at any point between open and close. + The TTY_DO_WRITE_WAKEUP flag indicates if a call + is needed but always races versus calls. Thus the + ldisc must be careful about setting order and to + handle unexpected calls. Must not sleep. + + The driver is forbidden from calling this directly + from the ->write call from the ldisc as the ldisc + is permitted to call the driver write method from + this function. In such a situation defer it. + +dcd_change() Report to the tty line the current DCD pin status + changes and the relative timestamp. The timestamp + cannot be NULL. +======================= ======================================================= + + +Driver Access +^^^^^^^^^^^^^ + +Line discipline methods can call the following methods of the underlying +hardware driver through the function pointers within the tty->driver +structure: + +======================= ======================================================= +write() Write a block of characters to the tty device. + Returns the number of characters accepted. The + character buffer passed to this method is already + in kernel space. + +put_char() Queues a character for writing to the tty device. + If there is no room in the queue, the character is + ignored. + +flush_chars() (Optional) If defined, must be called after + queueing characters with put_char() in order to + start transmission. + +write_room() Returns the numbers of characters the tty driver + will accept for queueing to be written. + +ioctl() Invoke device specific ioctl. + Expects data pointers to refer to userspace. + Returns ENOIOCTLCMD for unrecognized ioctl numbers. + +set_termios() Notify the tty driver that the device's termios + settings have changed. New settings are in + tty->termios. Previous settings should be passed in + the "old" argument. + + The API is defined such that the driver should return + the actual modes selected. This means that the + driver function is responsible for modifying any + bits in the request it cannot fulfill to indicate + the actual modes being used. A device with no + hardware capability for change (e.g. a USB dongle or + virtual port) can provide NULL for this method. + +throttle() Notify the tty driver that input buffers for the + line discipline are close to full, and it should + somehow signal that no more characters should be + sent to the tty. + +unthrottle() Notify the tty driver that characters can now be + sent to the tty without fear of overrunning the + input buffers of the line disciplines. + +stop() Ask the tty driver to stop outputting characters + to the tty device. + +start() Ask the tty driver to resume sending characters + to the tty device. + +hangup() Ask the tty driver to hang up the tty device. + +break_ctl() (Optional) Ask the tty driver to turn on or off + BREAK status on the RS-232 port. If state is -1, + then the BREAK status should be turned on; if + state is 0, then BREAK should be turned off. + If this routine is not implemented, use ioctls + TIOCSBRK / TIOCCBRK instead. + +wait_until_sent() Waits until the device has written out all of the + characters in its transmitter FIFO. + +send_xchar() Send a high-priority XON/XOFF character to the device. +======================= ======================================================= + + +Flags +^^^^^ + +Line discipline methods have access to tty->flags field containing the +following interesting flags: + +======================= ======================================================= +TTY_THROTTLED Driver input is throttled. The ldisc should call + tty->driver->unthrottle() in order to resume + reception when it is ready to process more data. + +TTY_DO_WRITE_WAKEUP If set, causes the driver to call the ldisc's + write_wakeup() method in order to resume + transmission when it can accept more data + to transmit. + +TTY_IO_ERROR If set, causes all subsequent userspace read/write + calls on the tty to fail, returning -EIO. + +TTY_OTHER_CLOSED Device is a pty and the other side has closed. + +TTY_NO_WRITE_SPLIT Prevent driver from splitting up writes into + smaller chunks. +======================= ======================================================= + + +Locking +^^^^^^^ + +Callers to the line discipline functions from the tty layer are required to +take line discipline locks. The same is true of calls from the driver side +but not yet enforced. + +Three calls are now provided:: + + ldisc = tty_ldisc_ref(tty); + +takes a handle to the line discipline in the tty and returns it. If no ldisc +is currently attached or the ldisc is being closed and re-opened at this +point then NULL is returned. While this handle is held the ldisc will not +change or go away:: + + tty_ldisc_deref(ldisc) + +Returns the ldisc reference and allows the ldisc to be closed. Returning the +reference takes away your right to call the ldisc functions until you take +a new reference:: + + ldisc = tty_ldisc_ref_wait(tty); + +Performs the same function as tty_ldisc_ref except that it will wait for an +ldisc change to complete and then return a reference to the new ldisc. + +While these functions are slightly slower than the old code they should have +minimal impact as most receive logic uses the flip buffers and they only +need to take a reference when they push bits up through the driver. + +A caution: The ldisc->open(), ldisc->close() and driver->set_ldisc +functions are called with the ldisc unavailable. Thus tty_ldisc_ref will +fail in this situation if used within these functions. Ldisc and driver +code calling its own functions must be careful in this case. + + +Driver Interface +---------------- + +======================= ======================================================= +open() Called when a device is opened. May sleep + +close() Called when a device is closed. At the point of + return from this call the driver must make no + further ldisc calls of any kind. May sleep + +write() Called to write bytes to the device. May not + sleep. May occur in parallel in special cases. + Because this includes panic paths drivers generally + shouldn't try and do clever locking here. + +put_char() Stuff a single character onto the queue. The + driver is guaranteed following up calls to + flush_chars. + +flush_chars() Ask the kernel to write put_char queue + +write_room() Return the number of characters that can be stuffed + into the port buffers without overflow (or less). + The ldisc is responsible for being intelligent + about multi-threading of write_room/write calls + +ioctl() Called when an ioctl may be for the driver + +set_termios() Called on termios change, serialized against + itself by a semaphore. May sleep. + +set_ldisc() Notifier for discipline change. At the point this + is done the discipline is not yet usable. Can now + sleep (I think) + +throttle() Called by the ldisc to ask the driver to do flow + control. Serialization including with unthrottle + is the job of the ldisc layer. + +unthrottle() Called by the ldisc to ask the driver to stop flow + control. + +stop() Ldisc notifier to the driver to stop output. As with + throttle the serializations with start() are down + to the ldisc layer. + +start() Ldisc notifier to the driver to start output. + +hangup() Ask the tty driver to cause a hangup initiated + from the host side. [Can sleep ??] + +break_ctl() Send RS232 break. Can sleep. Can get called in + parallel, driver must serialize (for now), and + with write calls. + +wait_until_sent() Wait for characters to exit the hardware queue + of the driver. Can sleep + +send_xchar() Send XON/XOFF and if possible jump the queue with + it in order to get fast flow control responses. + Cannot sleep ?? +======================= ======================================================= diff --git a/Documentation/serial/tty.txt b/Documentation/serial/tty.txt deleted file mode 100644 index b48780977a68..000000000000 --- a/Documentation/serial/tty.txt +++ /dev/null @@ -1,313 +0,0 @@ - - The Lockronomicon - -Your guide to the ancient and twisted locking policies of the tty layer and -the warped logic behind them. Beware all ye who read on. - - -Line Discipline ---------------- - -Line disciplines are registered with tty_register_ldisc() passing the -discipline number and the ldisc structure. At the point of registration the -discipline must be ready to use and it is possible it will get used before -the call returns success. If the call returns an error then it won't get -called. Do not re-use ldisc numbers as they are part of the userspace ABI -and writing over an existing ldisc will cause demons to eat your computer. -After the return the ldisc data has been copied so you may free your own -copy of the structure. You must not re-register over the top of the line -discipline even with the same data or your computer again will be eaten by -demons. - -In order to remove a line discipline call tty_unregister_ldisc(). -In ancient times this always worked. In modern times the function will -return -EBUSY if the ldisc is currently in use. Since the ldisc referencing -code manages the module counts this should not usually be a concern. - -Heed this warning: the reference count field of the registered copies of the -tty_ldisc structure in the ldisc table counts the number of lines using this -discipline. The reference count of the tty_ldisc structure within a tty -counts the number of active users of the ldisc at this instant. In effect it -counts the number of threads of execution within an ldisc method (plus those -about to enter and exit although this detail matters not). - -Line Discipline Methods ------------------------ - -TTY side interfaces: - -open() - Called when the line discipline is attached to - the terminal. No other call into the line - discipline for this tty will occur until it - completes successfully. Should initialize any - state needed by the ldisc, and set receive_room - in the tty_struct to the maximum amount of data - the line discipline is willing to accept from the - driver with a single call to receive_buf(). - Returning an error will prevent the ldisc from - being attached. Can sleep. - -close() - This is called on a terminal when the line - discipline is being unplugged. At the point of - execution no further users will enter the - ldisc code for this tty. Can sleep. - -hangup() - Called when the tty line is hung up. - The line discipline should cease I/O to the tty. - No further calls into the ldisc code will occur. - The return value is ignored. Can sleep. - -read() - (optional) A process requests reading data from - the line. Multiple read calls may occur in parallel - and the ldisc must deal with serialization issues. - If not defined, the process will receive an EIO - error. May sleep. - -write() - (optional) A process requests writing data to the - line. Multiple write calls are serialized by the - tty layer for the ldisc. If not defined, the - process will receive an EIO error. May sleep. - -flush_buffer() - (optional) May be called at any point between - open and close, and instructs the line discipline - to empty its input buffer. - -set_termios() - (optional) Called on termios structure changes. - The caller passes the old termios data and the - current data is in the tty. Called under the - termios semaphore so allowed to sleep. Serialized - against itself only. - -poll() - (optional) Check the status for the poll/select - calls. Multiple poll calls may occur in parallel. - May sleep. - -ioctl() - (optional) Called when an ioctl is handed to the - tty layer that might be for the ldisc. Multiple - ioctl calls may occur in parallel. May sleep. - -compat_ioctl() - (optional) Called when a 32 bit ioctl is handed - to the tty layer that might be for the ldisc. - Multiple ioctl calls may occur in parallel. - May sleep. - -Driver Side Interfaces: - -receive_buf() - (optional) Called by the low-level driver to hand - a buffer of received bytes to the ldisc for - processing. The number of bytes is guaranteed not - to exceed the current value of tty->receive_room. - All bytes must be processed. - -receive_buf2() - (optional) Called by the low-level driver to hand - a buffer of received bytes to the ldisc for - processing. Returns the number of bytes processed. - - If both receive_buf() and receive_buf2() are - defined, receive_buf2() should be preferred. - -write_wakeup() - May be called at any point between open and close. - The TTY_DO_WRITE_WAKEUP flag indicates if a call - is needed but always races versus calls. Thus the - ldisc must be careful about setting order and to - handle unexpected calls. Must not sleep. - - The driver is forbidden from calling this directly - from the ->write call from the ldisc as the ldisc - is permitted to call the driver write method from - this function. In such a situation defer it. - -dcd_change() - Report to the tty line the current DCD pin status - changes and the relative timestamp. The timestamp - cannot be NULL. - - -Driver Access - -Line discipline methods can call the following methods of the underlying -hardware driver through the function pointers within the tty->driver -structure: - -write() Write a block of characters to the tty device. - Returns the number of characters accepted. The - character buffer passed to this method is already - in kernel space. - -put_char() Queues a character for writing to the tty device. - If there is no room in the queue, the character is - ignored. - -flush_chars() (Optional) If defined, must be called after - queueing characters with put_char() in order to - start transmission. - -write_room() Returns the numbers of characters the tty driver - will accept for queueing to be written. - -ioctl() Invoke device specific ioctl. - Expects data pointers to refer to userspace. - Returns ENOIOCTLCMD for unrecognized ioctl numbers. - -set_termios() Notify the tty driver that the device's termios - settings have changed. New settings are in - tty->termios. Previous settings should be passed in - the "old" argument. - - The API is defined such that the driver should return - the actual modes selected. This means that the - driver function is responsible for modifying any - bits in the request it cannot fulfill to indicate - the actual modes being used. A device with no - hardware capability for change (e.g. a USB dongle or - virtual port) can provide NULL for this method. - -throttle() Notify the tty driver that input buffers for the - line discipline are close to full, and it should - somehow signal that no more characters should be - sent to the tty. - -unthrottle() Notify the tty driver that characters can now be - sent to the tty without fear of overrunning the - input buffers of the line disciplines. - -stop() Ask the tty driver to stop outputting characters - to the tty device. - -start() Ask the tty driver to resume sending characters - to the tty device. - -hangup() Ask the tty driver to hang up the tty device. - -break_ctl() (Optional) Ask the tty driver to turn on or off - BREAK status on the RS-232 port. If state is -1, - then the BREAK status should be turned on; if - state is 0, then BREAK should be turned off. - If this routine is not implemented, use ioctls - TIOCSBRK / TIOCCBRK instead. - -wait_until_sent() Waits until the device has written out all of the - characters in its transmitter FIFO. - -send_xchar() Send a high-priority XON/XOFF character to the device. - - -Flags - -Line discipline methods have access to tty->flags field containing the -following interesting flags: - -TTY_THROTTLED Driver input is throttled. The ldisc should call - tty->driver->unthrottle() in order to resume - reception when it is ready to process more data. - -TTY_DO_WRITE_WAKEUP If set, causes the driver to call the ldisc's - write_wakeup() method in order to resume - transmission when it can accept more data - to transmit. - -TTY_IO_ERROR If set, causes all subsequent userspace read/write - calls on the tty to fail, returning -EIO. - -TTY_OTHER_CLOSED Device is a pty and the other side has closed. - -TTY_NO_WRITE_SPLIT Prevent driver from splitting up writes into - smaller chunks. - - -Locking - -Callers to the line discipline functions from the tty layer are required to -take line discipline locks. The same is true of calls from the driver side -but not yet enforced. - -Three calls are now provided - - ldisc = tty_ldisc_ref(tty); - -takes a handle to the line discipline in the tty and returns it. If no ldisc -is currently attached or the ldisc is being closed and re-opened at this -point then NULL is returned. While this handle is held the ldisc will not -change or go away. - - tty_ldisc_deref(ldisc) - -Returns the ldisc reference and allows the ldisc to be closed. Returning the -reference takes away your right to call the ldisc functions until you take -a new reference. - - ldisc = tty_ldisc_ref_wait(tty); - -Performs the same function as tty_ldisc_ref except that it will wait for an -ldisc change to complete and then return a reference to the new ldisc. - -While these functions are slightly slower than the old code they should have -minimal impact as most receive logic uses the flip buffers and they only -need to take a reference when they push bits up through the driver. - -A caution: The ldisc->open(), ldisc->close() and driver->set_ldisc -functions are called with the ldisc unavailable. Thus tty_ldisc_ref will -fail in this situation if used within these functions. Ldisc and driver -code calling its own functions must be careful in this case. - - -Driver Interface ----------------- - -open() - Called when a device is opened. May sleep - -close() - Called when a device is closed. At the point of - return from this call the driver must make no - further ldisc calls of any kind. May sleep - -write() - Called to write bytes to the device. May not - sleep. May occur in parallel in special cases. - Because this includes panic paths drivers generally - shouldn't try and do clever locking here. - -put_char() - Stuff a single character onto the queue. The - driver is guaranteed following up calls to - flush_chars. - -flush_chars() - Ask the kernel to write put_char queue - -write_room() - Return the number of characters that can be stuffed - into the port buffers without overflow (or less). - The ldisc is responsible for being intelligent - about multi-threading of write_room/write calls - -ioctl() - Called when an ioctl may be for the driver - -set_termios() - Called on termios change, serialized against - itself by a semaphore. May sleep. - -set_ldisc() - Notifier for discipline change. At the point this - is done the discipline is not yet usable. Can now - sleep (I think) - -throttle() - Called by the ldisc to ask the driver to do flow - control. Serialization including with unthrottle - is the job of the ldisc layer. - -unthrottle() - Called by the ldisc to ask the driver to stop flow - control. - -stop() - Ldisc notifier to the driver to stop output. As with - throttle the serializations with start() are down - to the ldisc layer. - -start() - Ldisc notifier to the driver to start output. - -hangup() - Ask the tty driver to cause a hangup initiated - from the host side. [Can sleep ??] - -break_ctl() - Send RS232 break. Can sleep. Can get called in - parallel, driver must serialize (for now), and - with write calls. - -wait_until_sent() - Wait for characters to exit the hardware queue - of the driver. Can sleep - -send_xchar() - Send XON/XOFF and if possible jump the queue with - it in order to get fast flow control responses. - Cannot sleep ?? - diff --git a/MAINTAINERS b/MAINTAINERS index 09f43f1bdd15..be2a1176410e 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -10433,7 +10433,7 @@ F: include/uapi/linux/meye.h MOXA SMARTIO/INDUSTIO/INTELLIO SERIAL CARD M: Jiri Slaby S: Maintained -F: Documentation/serial/moxa-smartio +F: Documentation/serial/moxa-smartio.rst F: drivers/tty/mxser.* MR800 AVERMEDIA USB FM RADIO DRIVER @@ -13317,7 +13317,7 @@ ROCKETPORT DRIVER P: Comtrol Corp. W: http://www.comtrol.com S: Maintained -F: Documentation/serial/rocket.txt +F: Documentation/serial/rocket.rst F: drivers/tty/rocket* ROCKETPORT EXPRESS/INFINITY DRIVER diff --git a/drivers/tty/Kconfig b/drivers/tty/Kconfig index 80f65767aacf..3b1d312bb175 100644 --- a/drivers/tty/Kconfig +++ b/drivers/tty/Kconfig @@ -175,7 +175,7 @@ config ROCKETPORT This driver supports Comtrol RocketPort and RocketModem PCI boards. These boards provide 2, 4, 8, 16, or 32 high-speed serial ports or modems. For information about the RocketPort/RocketModem boards - and this driver read . + and this driver read . To compile this driver as a module, choose M here: the module will be called rocket. @@ -193,7 +193,7 @@ config CYCLADES your Linux box, for instance in order to become a dial-in server. For information about the Cyclades-Z card, read - . + . To compile this driver as a module, choose M here: the module will be called cyclades. diff --git a/drivers/tty/serial/ucc_uart.c b/drivers/tty/serial/ucc_uart.c index 2b6376e6e5ad..6e3c66ab0e62 100644 --- a/drivers/tty/serial/ucc_uart.c +++ b/drivers/tty/serial/ucc_uart.c @@ -1081,7 +1081,7 @@ static int qe_uart_verify_port(struct uart_port *port, } /* UART operations * - * Details on these functions can be found in Documentation/serial/driver + * Details on these functions can be found in Documentation/serial/driver.rst */ static const struct uart_ops qe_uart_pops = { .tx_empty = qe_uart_tx_empty, diff --git a/include/linux/serial_core.h b/include/linux/serial_core.h index 5fe2b037e833..fea2216a893f 100644 --- a/include/linux/serial_core.h +++ b/include/linux/serial_core.h @@ -45,7 +45,7 @@ struct device; /* * This structure describes all the operations that can be done on the - * physical hardware. See Documentation/serial/driver for details. + * physical hardware. See Documentation/serial/driver.rst for details. */ struct uart_ops { unsigned int (*tx_empty)(struct uart_port *); -- cgit v1.2.3 From 9abb24990a2bfa3d9dd35a6b3b93ff54d9cc7908 Mon Sep 17 00:00:00 2001 From: Ronald Tschalär Date: Mon, 15 Apr 2019 01:25:05 -0700 Subject: debugfs: update documented return values of debugfs helpers MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Since commit ff9fb72bc077 ("debugfs: return error values, not NULL") these helper functions do not return NULL anymore (with the exception of debugfs_create_u32_array()). Fixes: ff9fb72bc077 ("debugfs: return error values, not NULL") Signed-off-by: Ronald Tschalär Signed-off-by: Greg Kroah-Hartman --- Documentation/filesystems/debugfs.txt | 16 ++++---- fs/debugfs/file.c | 77 ++++++++++++++++------------------- 2 files changed, 44 insertions(+), 49 deletions(-) (limited to 'Documentation') diff --git a/Documentation/filesystems/debugfs.txt b/Documentation/filesystems/debugfs.txt index 4f45f71149cb..4a0a9c3f4af6 100644 --- a/Documentation/filesystems/debugfs.txt +++ b/Documentation/filesystems/debugfs.txt @@ -31,10 +31,10 @@ This call, if successful, will make a directory called name underneath the indicated parent directory. If parent is NULL, the directory will be created in the debugfs root. On success, the return value is a struct dentry pointer which can be used to create files in the directory (and to -clean it up at the end). A NULL return value indicates that something went -wrong. If ERR_PTR(-ENODEV) is returned, that is an indication that the -kernel has been built without debugfs support and none of the functions -described below will work. +clean it up at the end). An ERR_PTR(-ERROR) return value indicates that +something went wrong. If ERR_PTR(-ENODEV) is returned, that is an +indication that the kernel has been built without debugfs support and none +of the functions described below will work. The most general way to create a file within a debugfs directory is with: @@ -48,8 +48,9 @@ should hold the file, data will be stored in the i_private field of the resulting inode structure, and fops is a set of file operations which implement the file's behavior. At a minimum, the read() and/or write() operations should be provided; others can be included as needed. Again, -the return value will be a dentry pointer to the created file, NULL for -error, or ERR_PTR(-ENODEV) if debugfs support is missing. +the return value will be a dentry pointer to the created file, +ERR_PTR(-ERROR) on error, or ERR_PTR(-ENODEV) if debugfs support is +missing. Create a file with an initial size, the following function can be used instead: @@ -214,7 +215,8 @@ can be removed with: void debugfs_remove(struct dentry *dentry); -The dentry value can be NULL, in which case nothing will be removed. +The dentry value can be NULL or an error value, in which case nothing will +be removed. Once upon a time, debugfs users were required to remember the dentry pointer for every debugfs file they created so that all files could be diff --git a/fs/debugfs/file.c b/fs/debugfs/file.c index 4fce1da7db23..ddd708b09fa1 100644 --- a/fs/debugfs/file.c +++ b/fs/debugfs/file.c @@ -394,12 +394,11 @@ DEFINE_DEBUGFS_ATTRIBUTE(fops_u8_wo, NULL, debugfs_u8_set, "%llu\n"); * This function will return a pointer to a dentry if it succeeds. This * pointer must be passed to the debugfs_remove() function when the file is * to be removed (no automatic cleanup happens if your module is unloaded, - * you are responsible here.) If an error occurs, %NULL will be returned. + * you are responsible here.) If an error occurs, %ERR_PTR(-ERROR) will be + * returned. * - * If debugfs is not enabled in the kernel, the value -%ENODEV will be - * returned. It is not wise to check for this value, but rather, check for - * %NULL or !%NULL instead as to eliminate the need for #ifdef in the calling - * code. + * If debugfs is not enabled in the kernel, the value %ERR_PTR(-ENODEV) will + * be returned. */ struct dentry *debugfs_create_u8(const char *name, umode_t mode, struct dentry *parent, u8 *value) @@ -440,12 +439,11 @@ DEFINE_DEBUGFS_ATTRIBUTE(fops_u16_wo, NULL, debugfs_u16_set, "%llu\n"); * This function will return a pointer to a dentry if it succeeds. This * pointer must be passed to the debugfs_remove() function when the file is * to be removed (no automatic cleanup happens if your module is unloaded, - * you are responsible here.) If an error occurs, %NULL will be returned. + * you are responsible here.) If an error occurs, %ERR_PTR(-ERROR) will be + * returned. * - * If debugfs is not enabled in the kernel, the value -%ENODEV will be - * returned. It is not wise to check for this value, but rather, check for - * %NULL or !%NULL instead as to eliminate the need for #ifdef in the calling - * code. + * If debugfs is not enabled in the kernel, the value %ERR_PTR(-ENODEV) will + * be returned. */ struct dentry *debugfs_create_u16(const char *name, umode_t mode, struct dentry *parent, u16 *value) @@ -486,12 +484,11 @@ DEFINE_DEBUGFS_ATTRIBUTE(fops_u32_wo, NULL, debugfs_u32_set, "%llu\n"); * This function will return a pointer to a dentry if it succeeds. This * pointer must be passed to the debugfs_remove() function when the file is * to be removed (no automatic cleanup happens if your module is unloaded, - * you are responsible here.) If an error occurs, %NULL will be returned. + * you are responsible here.) If an error occurs, %ERR_PTR(-ERROR) will be + * returned. * - * If debugfs is not enabled in the kernel, the value -%ENODEV will be - * returned. It is not wise to check for this value, but rather, check for - * %NULL or !%NULL instead as to eliminate the need for #ifdef in the calling - * code. + * If debugfs is not enabled in the kernel, the value %ERR_PTR(-ENODEV) will + * be returned. */ struct dentry *debugfs_create_u32(const char *name, umode_t mode, struct dentry *parent, u32 *value) @@ -533,12 +530,11 @@ DEFINE_DEBUGFS_ATTRIBUTE(fops_u64_wo, NULL, debugfs_u64_set, "%llu\n"); * This function will return a pointer to a dentry if it succeeds. This * pointer must be passed to the debugfs_remove() function when the file is * to be removed (no automatic cleanup happens if your module is unloaded, - * you are responsible here.) If an error occurs, %NULL will be returned. + * you are responsible here.) If an error occurs, %ERR_PTR(-ERROR) will be + * returned. * - * If debugfs is not enabled in the kernel, the value -%ENODEV will be - * returned. It is not wise to check for this value, but rather, check for - * %NULL or !%NULL instead as to eliminate the need for #ifdef in the calling - * code. + * If debugfs is not enabled in the kernel, the value %ERR_PTR(-ENODEV) will + * be returned. */ struct dentry *debugfs_create_u64(const char *name, umode_t mode, struct dentry *parent, u64 *value) @@ -582,12 +578,11 @@ DEFINE_DEBUGFS_ATTRIBUTE(fops_ulong_wo, NULL, debugfs_ulong_set, "%llu\n"); * This function will return a pointer to a dentry if it succeeds. This * pointer must be passed to the debugfs_remove() function when the file is * to be removed (no automatic cleanup happens if your module is unloaded, - * you are responsible here.) If an error occurs, %NULL will be returned. + * you are responsible here.) If an error occurs, %ERR_PTR(-ERROR) will be + * returned. * - * If debugfs is not enabled in the kernel, the value -%ENODEV will be - * returned. It is not wise to check for this value, but rather, check for - * %NULL or !%NULL instead as to eliminate the need for #ifdef in the calling - * code. + * If debugfs is not enabled in the kernel, the value %ERR_PTR(-ENODEV) will + * be returned. */ struct dentry *debugfs_create_ulong(const char *name, umode_t mode, struct dentry *parent, unsigned long *value) @@ -850,12 +845,11 @@ static const struct file_operations fops_bool_wo = { * This function will return a pointer to a dentry if it succeeds. This * pointer must be passed to the debugfs_remove() function when the file is * to be removed (no automatic cleanup happens if your module is unloaded, - * you are responsible here.) If an error occurs, %NULL will be returned. + * you are responsible here.) If an error occurs, %ERR_PTR(-ERROR) will be + * returned. * - * If debugfs is not enabled in the kernel, the value -%ENODEV will be - * returned. It is not wise to check for this value, but rather, check for - * %NULL or !%NULL instead as to eliminate the need for #ifdef in the calling - * code. + * If debugfs is not enabled in the kernel, the value %ERR_PTR(-ENODEV) will + * be returned. */ struct dentry *debugfs_create_bool(const char *name, umode_t mode, struct dentry *parent, bool *value) @@ -904,12 +898,11 @@ static const struct file_operations fops_blob = { * This function will return a pointer to a dentry if it succeeds. This * pointer must be passed to the debugfs_remove() function when the file is * to be removed (no automatic cleanup happens if your module is unloaded, - * you are responsible here.) If an error occurs, %NULL will be returned. + * you are responsible here.) If an error occurs, %ERR_PTR(-ERROR) will be + * returned. * - * If debugfs is not enabled in the kernel, the value -%ENODEV will be - * returned. It is not wise to check for this value, but rather, check for - * %NULL or !%NULL instead as to eliminate the need for #ifdef in the calling - * code. + * If debugfs is not enabled in the kernel, the value %ERR_PTR(-ENODEV) will + * be returned. */ struct dentry *debugfs_create_blob(const char *name, umode_t mode, struct dentry *parent, @@ -1005,8 +998,9 @@ static const struct file_operations u32_array_fops = { * Writing is not supported. Seek within the file is also not supported. * Once array is created its size can not be changed. * - * The function returns a pointer to dentry on success. If debugfs is not - * enabled in the kernel, the value -%ENODEV will be returned. + * The function returns a pointer to dentry on success. If an error occurs, + * %ERR_PTR(-ERROR) or NULL will be returned. If debugfs is not enabled in + * the kernel, the value %ERR_PTR(-ENODEV) will be returned. */ struct dentry *debugfs_create_u32_array(const char *name, umode_t mode, struct dentry *parent, @@ -1102,12 +1096,11 @@ static const struct file_operations fops_regset32 = { * This function will return a pointer to a dentry if it succeeds. This * pointer must be passed to the debugfs_remove() function when the file is * to be removed (no automatic cleanup happens if your module is unloaded, - * you are responsible here.) If an error occurs, %NULL will be returned. + * you are responsible here.) If an error occurs, %ERR_PTR(-ERROR) will be + * returned. * - * If debugfs is not enabled in the kernel, the value -%ENODEV will be - * returned. It is not wise to check for this value, but rather, check for - * %NULL or !%NULL instead as to eliminate the need for #ifdef in the calling - * code. + * If debugfs is not enabled in the kernel, the value %ERR_PTR(-ENODEV) will + * be returned. */ struct dentry *debugfs_create_regset32(const char *name, umode_t mode, struct dentry *parent, -- cgit v1.2.3 From e25ec9141114c7124eeba09385e272dd76fbe617 Mon Sep 17 00:00:00 2001 From: Laurent Pinchart Date: Thu, 28 Mar 2019 01:23:54 -0400 Subject: media: v4l: Add definitions for missing 32-bit RGB formats The V4L2 API is missing the 32-bit RGB formats for the ABGR, XBGR, RGBA and RGBX component orders. Add them, using the same 4CCs as DRM. Signed-off-by: Laurent Pinchart Reviewed-by: Jacopo Mondi Acked-by: Sakari Ailus Signed-off-by: Mauro Carvalho Chehab --- Documentation/media/uapi/v4l/pixfmt-packed-rgb.rst | 160 +++++++++++++++++++++ include/uapi/linux/videodev2.h | 4 + 2 files changed, 164 insertions(+) (limited to 'Documentation') diff --git a/Documentation/media/uapi/v4l/pixfmt-packed-rgb.rst b/Documentation/media/uapi/v4l/pixfmt-packed-rgb.rst index 4766a6f47222..ed0b541afe59 100644 --- a/Documentation/media/uapi/v4l/pixfmt-packed-rgb.rst +++ b/Documentation/media/uapi/v4l/pixfmt-packed-rgb.rst @@ -453,6 +453,166 @@ next to each other in memory. - r\ :sub:`1` - r\ :sub:`0` + - + - + - + - + - + - + - + - + * .. _V4L2-PIX-FMT-BGRA32: + + - ``V4L2_PIX_FMT_BGRA32`` + - 'RA24' + + - a\ :sub:`7` + - a\ :sub:`6` + - a\ :sub:`5` + - a\ :sub:`4` + - a\ :sub:`3` + - a\ :sub:`2` + - a\ :sub:`1` + - a\ :sub:`0` + + - b\ :sub:`7` + - b\ :sub:`6` + - b\ :sub:`5` + - b\ :sub:`4` + - b\ :sub:`3` + - b\ :sub:`2` + - b\ :sub:`1` + - b\ :sub:`0` + + - g\ :sub:`7` + - g\ :sub:`6` + - g\ :sub:`5` + - g\ :sub:`4` + - g\ :sub:`3` + - g\ :sub:`2` + - g\ :sub:`1` + - g\ :sub:`0` + + - r\ :sub:`7` + - r\ :sub:`6` + - r\ :sub:`5` + - r\ :sub:`4` + - r\ :sub:`3` + - r\ :sub:`2` + - r\ :sub:`1` + - r\ :sub:`0` + * .. _V4L2-PIX-FMT-BGRX32: + + - ``V4L2_PIX_FMT_BGRX32`` + - 'RX24' + + - + - + - + - + - + - + - + - + + - b\ :sub:`7` + - b\ :sub:`6` + - b\ :sub:`5` + - b\ :sub:`4` + - b\ :sub:`3` + - b\ :sub:`2` + - b\ :sub:`1` + - b\ :sub:`0` + + - g\ :sub:`7` + - g\ :sub:`6` + - g\ :sub:`5` + - g\ :sub:`4` + - g\ :sub:`3` + - g\ :sub:`2` + - g\ :sub:`1` + - g\ :sub:`0` + + - r\ :sub:`7` + - r\ :sub:`6` + - r\ :sub:`5` + - r\ :sub:`4` + - r\ :sub:`3` + - r\ :sub:`2` + - r\ :sub:`1` + - r\ :sub:`0` + * .. _V4L2-PIX-FMT-RGBA32: + + - ``V4L2_PIX_FMT_RGBA32`` + - 'AB24' + + - r\ :sub:`7` + - r\ :sub:`6` + - r\ :sub:`5` + - r\ :sub:`4` + - r\ :sub:`3` + - r\ :sub:`2` + - r\ :sub:`1` + - r\ :sub:`0` + + - g\ :sub:`7` + - g\ :sub:`6` + - g\ :sub:`5` + - g\ :sub:`4` + - g\ :sub:`3` + - g\ :sub:`2` + - g\ :sub:`1` + - g\ :sub:`0` + + - b\ :sub:`7` + - b\ :sub:`6` + - b\ :sub:`5` + - b\ :sub:`4` + - b\ :sub:`3` + - b\ :sub:`2` + - b\ :sub:`1` + - b\ :sub:`0` + + - a\ :sub:`7` + - a\ :sub:`6` + - a\ :sub:`5` + - a\ :sub:`4` + - a\ :sub:`3` + - a\ :sub:`2` + - a\ :sub:`1` + - a\ :sub:`0` + * .. _V4L2-PIX-FMT-RGBX32: + + - ``V4L2_PIX_FMT_RGBX32`` + - 'XB24' + + - r\ :sub:`7` + - r\ :sub:`6` + - r\ :sub:`5` + - r\ :sub:`4` + - r\ :sub:`3` + - r\ :sub:`2` + - r\ :sub:`1` + - r\ :sub:`0` + + - g\ :sub:`7` + - g\ :sub:`6` + - g\ :sub:`5` + - g\ :sub:`4` + - g\ :sub:`3` + - g\ :sub:`2` + - g\ :sub:`1` + - g\ :sub:`0` + + - b\ :sub:`7` + - b\ :sub:`6` + - b\ :sub:`5` + - b\ :sub:`4` + - b\ :sub:`3` + - b\ :sub:`2` + - b\ :sub:`1` + - b\ :sub:`0` + - - - diff --git a/include/uapi/linux/videodev2.h b/include/uapi/linux/videodev2.h index 496e6453450c..00525503267d 100644 --- a/include/uapi/linux/videodev2.h +++ b/include/uapi/linux/videodev2.h @@ -528,7 +528,11 @@ struct v4l2_pix_format { #define V4L2_PIX_FMT_BGR32 v4l2_fourcc('B', 'G', 'R', '4') /* 32 BGR-8-8-8-8 */ #define V4L2_PIX_FMT_ABGR32 v4l2_fourcc('A', 'R', '2', '4') /* 32 BGRA-8-8-8-8 */ #define V4L2_PIX_FMT_XBGR32 v4l2_fourcc('X', 'R', '2', '4') /* 32 BGRX-8-8-8-8 */ +#define V4L2_PIX_FMT_BGRA32 v4l2_fourcc('R', 'A', '2', '4') /* 32 ABGR-8-8-8-8 */ +#define V4L2_PIX_FMT_BGRX32 v4l2_fourcc('R', 'X', '2', '4') /* 32 XBGR-8-8-8-8 */ #define V4L2_PIX_FMT_RGB32 v4l2_fourcc('R', 'G', 'B', '4') /* 32 RGB-8-8-8-8 */ +#define V4L2_PIX_FMT_RGBA32 v4l2_fourcc('A', 'B', '2', '4') /* 32 RGBA-8-8-8-8 */ +#define V4L2_PIX_FMT_RGBX32 v4l2_fourcc('X', 'B', '2', '4') /* 32 RGBX-8-8-8-8 */ #define V4L2_PIX_FMT_ARGB32 v4l2_fourcc('B', 'A', '2', '4') /* 32 ARGB-8-8-8-8 */ #define V4L2_PIX_FMT_XRGB32 v4l2_fourcc('B', 'X', '2', '4') /* 32 XRGB-8-8-8-8 */ -- cgit v1.2.3 From 6c84f9b1d2900c80eea74e682637976fd25eb471 Mon Sep 17 00:00:00 2001 From: Laurent Pinchart Date: Thu, 28 Mar 2019 01:23:54 -0400 Subject: media: v4l: Add definitions for missing 16-bit RGB4444 formats The V4L2 API is missing the 16-bit RGB4444 formats for the RGBA, RGBX, ABGR, XBGR, BGRA and BGRX component orders. Add them, using the same 4CCs as DRM. Signed-off-by: Laurent Pinchart Reviewed-by: Jacopo Mondi Acked-by: Sakari Ailus Signed-off-by: Mauro Carvalho Chehab --- Documentation/media/uapi/v4l/pixfmt-packed-rgb.rst | 138 +++++++++++++++++++++ include/uapi/linux/videodev2.h | 6 + 2 files changed, 144 insertions(+) (limited to 'Documentation') diff --git a/Documentation/media/uapi/v4l/pixfmt-packed-rgb.rst b/Documentation/media/uapi/v4l/pixfmt-packed-rgb.rst index ed0b541afe59..ab2416787c5a 100644 --- a/Documentation/media/uapi/v4l/pixfmt-packed-rgb.rst +++ b/Documentation/media/uapi/v4l/pixfmt-packed-rgb.rst @@ -139,6 +139,144 @@ next to each other in memory. - r\ :sub:`1` - r\ :sub:`0` - + * .. _V4L2-PIX-FMT-RGBA444: + + - ``V4L2_PIX_FMT_RGBA444`` + - 'RA12' + + - b\ :sub:`3` + - b\ :sub:`2` + - b\ :sub:`1` + - b\ :sub:`0` + - a\ :sub:`3` + - a\ :sub:`2` + - a\ :sub:`1` + - a\ :sub:`0` + + - r\ :sub:`3` + - r\ :sub:`2` + - r\ :sub:`1` + - r\ :sub:`0` + - g\ :sub:`3` + - g\ :sub:`2` + - g\ :sub:`1` + - g\ :sub:`0` + - + * .. _V4L2-PIX-FMT-RGBX444: + + - ``V4L2_PIX_FMT_RGBX444`` + - 'RX12' + + - b\ :sub:`3` + - b\ :sub:`2` + - b\ :sub:`1` + - b\ :sub:`0` + - + - + - + - + + - r\ :sub:`3` + - r\ :sub:`2` + - r\ :sub:`1` + - r\ :sub:`0` + - g\ :sub:`3` + - g\ :sub:`2` + - g\ :sub:`1` + - g\ :sub:`0` + - + * .. _V4L2-PIX-FMT-ABGR444: + + - ``V4L2_PIX_FMT_ABGR444`` + - 'AB12' + + - g\ :sub:`3` + - g\ :sub:`2` + - g\ :sub:`1` + - g\ :sub:`0` + - r\ :sub:`3` + - r\ :sub:`2` + - r\ :sub:`1` + - r\ :sub:`0` + + - a\ :sub:`3` + - a\ :sub:`2` + - a\ :sub:`1` + - a\ :sub:`0` + - b\ :sub:`3` + - b\ :sub:`2` + - b\ :sub:`1` + - b\ :sub:`0` + - + * .. _V4L2-PIX-FMT-XBGR444: + + - ``V4L2_PIX_FMT_XBGR444`` + - 'XB12' + + - g\ :sub:`3` + - g\ :sub:`2` + - g\ :sub:`1` + - g\ :sub:`0` + - r\ :sub:`3` + - r\ :sub:`2` + - r\ :sub:`1` + - r\ :sub:`0` + + - + - + - + - + - b\ :sub:`3` + - b\ :sub:`2` + - b\ :sub:`1` + - b\ :sub:`0` + - + * .. _V4L2-PIX-FMT-BGRA444: + + - ``V4L2_PIX_FMT_BGRA444`` + - 'BA12' + + - r\ :sub:`3` + - r\ :sub:`2` + - r\ :sub:`1` + - r\ :sub:`0` + - a\ :sub:`3` + - a\ :sub:`2` + - a\ :sub:`1` + - a\ :sub:`0` + + - b\ :sub:`3` + - b\ :sub:`2` + - b\ :sub:`1` + - b\ :sub:`0` + - g\ :sub:`3` + - g\ :sub:`2` + - g\ :sub:`1` + - g\ :sub:`0` + - + * .. _V4L2-PIX-FMT-BGRX444: + + - ``V4L2_PIX_FMT_BGRX444`` + - 'BX12' + + - r\ :sub:`3` + - r\ :sub:`2` + - r\ :sub:`1` + - r\ :sub:`0` + - + - + - + - + + - b\ :sub:`3` + - b\ :sub:`2` + - b\ :sub:`1` + - b\ :sub:`0` + - g\ :sub:`3` + - g\ :sub:`2` + - g\ :sub:`1` + - g\ :sub:`0` + - * .. _V4L2-PIX-FMT-ARGB555: - ``V4L2_PIX_FMT_ARGB555`` diff --git a/include/uapi/linux/videodev2.h b/include/uapi/linux/videodev2.h index 00525503267d..561eabdd027a 100644 --- a/include/uapi/linux/videodev2.h +++ b/include/uapi/linux/videodev2.h @@ -514,6 +514,12 @@ struct v4l2_pix_format { #define V4L2_PIX_FMT_RGB444 v4l2_fourcc('R', '4', '4', '4') /* 16 xxxxrrrr ggggbbbb */ #define V4L2_PIX_FMT_ARGB444 v4l2_fourcc('A', 'R', '1', '2') /* 16 aaaarrrr ggggbbbb */ #define V4L2_PIX_FMT_XRGB444 v4l2_fourcc('X', 'R', '1', '2') /* 16 xxxxrrrr ggggbbbb */ +#define V4L2_PIX_FMT_RGBA444 v4l2_fourcc('R', 'A', '1', '2') /* 16 rrrrgggg bbbbaaaa */ +#define V4L2_PIX_FMT_RGBX444 v4l2_fourcc('R', 'X', '1', '2') /* 16 rrrrgggg bbbbxxxx */ +#define V4L2_PIX_FMT_ABGR444 v4l2_fourcc('A', 'B', '1', '2') /* 16 aaaabbbb ggggrrrr */ +#define V4L2_PIX_FMT_XBGR444 v4l2_fourcc('X', 'B', '1', '2') /* 16 xxxxbbbb ggggrrrr */ +#define V4L2_PIX_FMT_BGRA444 v4l2_fourcc('B', 'A', '1', '2') /* 16 bbbbgggg rrrraaaa */ +#define V4L2_PIX_FMT_BGRX444 v4l2_fourcc('B', 'X', '1', '2') /* 16 bbbbgggg rrrrxxxx */ #define V4L2_PIX_FMT_RGB555 v4l2_fourcc('R', 'G', 'B', 'O') /* 16 RGB-5-5-5 */ #define V4L2_PIX_FMT_ARGB555 v4l2_fourcc('A', 'R', '1', '5') /* 16 ARGB-1-5-5-5 */ #define V4L2_PIX_FMT_XRGB555 v4l2_fourcc('X', 'R', '1', '5') /* 16 XRGB-1-5-5-5 */ -- cgit v1.2.3 From 8b65db13bf59ce0d3aeff4b3558f904e3d98b53a Mon Sep 17 00:00:00 2001 From: Laurent Pinchart Date: Thu, 28 Mar 2019 01:23:54 -0400 Subject: media: v4l: Add definitions for missing 16-bit RGB555 formats The V4L2 API is missing the 16-bit RGB555 formats for the RGBA, RGBX, ABGR, XBGR, BGRA and BGRX component orders. Add them, using the same 4CCs as DRM. Signed-off-by: Laurent Pinchart Acked-by: Sakari Ailus Reviewed-by: Jacopo Mondi Signed-off-by: Mauro Carvalho Chehab --- Documentation/media/uapi/v4l/pixfmt-packed-rgb.rst | 138 +++++++++++++++++++++ include/uapi/linux/videodev2.h | 6 + 2 files changed, 144 insertions(+) (limited to 'Documentation') diff --git a/Documentation/media/uapi/v4l/pixfmt-packed-rgb.rst b/Documentation/media/uapi/v4l/pixfmt-packed-rgb.rst index ab2416787c5a..738bb14c0ee2 100644 --- a/Documentation/media/uapi/v4l/pixfmt-packed-rgb.rst +++ b/Documentation/media/uapi/v4l/pixfmt-packed-rgb.rst @@ -323,6 +323,144 @@ next to each other in memory. - g\ :sub:`4` - g\ :sub:`3` - + * .. _V4L2-PIX-FMT-RGBA555: + + - ``V4L2_PIX_FMT_RGBA555`` + - 'RA15' + + - g\ :sub:`1` + - g\ :sub:`0` + - b\ :sub:`4` + - b\ :sub:`3` + - b\ :sub:`2` + - b\ :sub:`1` + - b\ :sub:`0` + - a + + - r\ :sub:`4` + - r\ :sub:`3` + - r\ :sub:`2` + - r\ :sub:`1` + - r\ :sub:`0` + - g\ :sub:`4` + - g\ :sub:`3` + - g\ :sub:`2` + - + * .. _V4L2-PIX-FMT-RGBX555: + + - ``V4L2_PIX_FMT_RGBX555`` + - 'RX15' + + - g\ :sub:`1` + - g\ :sub:`0` + - b\ :sub:`4` + - b\ :sub:`3` + - b\ :sub:`2` + - b\ :sub:`1` + - b\ :sub:`0` + - + + - r\ :sub:`4` + - r\ :sub:`3` + - r\ :sub:`2` + - r\ :sub:`1` + - r\ :sub:`0` + - g\ :sub:`4` + - g\ :sub:`3` + - g\ :sub:`2` + - + * .. _V4L2-PIX-FMT-ABGR555: + + - ``V4L2_PIX_FMT_ABGR555`` + - 'AB15' + + - g\ :sub:`2` + - g\ :sub:`1` + - g\ :sub:`0` + - r\ :sub:`4` + - r\ :sub:`3` + - r\ :sub:`2` + - r\ :sub:`1` + - r\ :sub:`0` + + - a + - b\ :sub:`4` + - b\ :sub:`3` + - b\ :sub:`2` + - b\ :sub:`1` + - b\ :sub:`0` + - g\ :sub:`4` + - g\ :sub:`3` + - + * .. _V4L2-PIX-FMT-XBGR555: + + - ``V4L2_PIX_FMT_XBGR555`` + - 'XB15' + + - g\ :sub:`2` + - g\ :sub:`1` + - g\ :sub:`0` + - r\ :sub:`4` + - r\ :sub:`3` + - r\ :sub:`2` + - r\ :sub:`1` + - r\ :sub:`0` + + - + - b\ :sub:`4` + - b\ :sub:`3` + - b\ :sub:`2` + - b\ :sub:`1` + - b\ :sub:`0` + - g\ :sub:`4` + - g\ :sub:`3` + - + * .. _V4L2-PIX-FMT-BGRA555: + + - ``V4L2_PIX_FMT_BGRA555`` + - 'BA15' + + - g\ :sub:`1` + - g\ :sub:`0` + - r\ :sub:`4` + - r\ :sub:`3` + - r\ :sub:`2` + - r\ :sub:`1` + - r\ :sub:`0` + - a + + - b\ :sub:`4` + - b\ :sub:`3` + - b\ :sub:`2` + - b\ :sub:`1` + - b\ :sub:`0` + - g\ :sub:`4` + - g\ :sub:`3` + - g\ :sub:`2` + - + * .. _V4L2-PIX-FMT-BGRX555: + + - ``V4L2_PIX_FMT_BGRX555`` + - 'BX15' + + - g\ :sub:`1` + - g\ :sub:`0` + - r\ :sub:`4` + - r\ :sub:`3` + - r\ :sub:`2` + - r\ :sub:`1` + - r\ :sub:`0` + - + + - b\ :sub:`4` + - b\ :sub:`3` + - b\ :sub:`2` + - b\ :sub:`1` + - b\ :sub:`0` + - g\ :sub:`4` + - g\ :sub:`3` + - g\ :sub:`2` + - * .. _V4L2-PIX-FMT-RGB565: - ``V4L2_PIX_FMT_RGB565`` diff --git a/include/uapi/linux/videodev2.h b/include/uapi/linux/videodev2.h index 561eabdd027a..1050a75fb7ef 100644 --- a/include/uapi/linux/videodev2.h +++ b/include/uapi/linux/videodev2.h @@ -523,6 +523,12 @@ struct v4l2_pix_format { #define V4L2_PIX_FMT_RGB555 v4l2_fourcc('R', 'G', 'B', 'O') /* 16 RGB-5-5-5 */ #define V4L2_PIX_FMT_ARGB555 v4l2_fourcc('A', 'R', '1', '5') /* 16 ARGB-1-5-5-5 */ #define V4L2_PIX_FMT_XRGB555 v4l2_fourcc('X', 'R', '1', '5') /* 16 XRGB-1-5-5-5 */ +#define V4L2_PIX_FMT_RGBA555 v4l2_fourcc('R', 'A', '1', '5') /* 16 RGBA-5-5-5-1 */ +#define V4L2_PIX_FMT_RGBX555 v4l2_fourcc('R', 'X', '1', '5') /* 16 RGBX-5-5-5-1 */ +#define V4L2_PIX_FMT_ABGR555 v4l2_fourcc('A', 'B', '1', '5') /* 16 ABGR-1-5-5-5 */ +#define V4L2_PIX_FMT_XBGR555 v4l2_fourcc('X', 'B', '1', '5') /* 16 XBGR-1-5-5-5 */ +#define V4L2_PIX_FMT_BGRA555 v4l2_fourcc('B', 'A', '1', '5') /* 16 BGRA-5-5-5-1 */ +#define V4L2_PIX_FMT_BGRX555 v4l2_fourcc('B', 'X', '1', '5') /* 16 BGRX-5-5-5-1 */ #define V4L2_PIX_FMT_RGB565 v4l2_fourcc('R', 'G', 'B', 'P') /* 16 RGB-5-6-5 */ #define V4L2_PIX_FMT_RGB555X v4l2_fourcc('R', 'G', 'B', 'Q') /* 16 RGB-5-5-5 BE */ #define V4L2_PIX_FMT_ARGB555X v4l2_fourcc_be('A', 'R', '1', '5') /* 16 ARGB-5-5-5 BE */ -- cgit v1.2.3 From 28703c6ef6228635f7c8b248c1d846511a2b60a3 Mon Sep 17 00:00:00 2001 From: Patrick Venture Date: Mon, 8 Apr 2019 07:42:16 -0700 Subject: dt-bindings: misc: aspeed-p2a-ctrl: add support Document the ast2400, ast2500 PCI-to-AHB bridge control driver bindings. Signed-off-by: Patrick Venture Reviewed-by: Rob Herring Reviewed-by: Andrew Jeffery Signed-off-by: Greg Kroah-Hartman --- .../devicetree/bindings/misc/aspeed-p2a-ctrl.txt | 47 ++++++++++++++++++++++ 1 file changed, 47 insertions(+) create mode 100644 Documentation/devicetree/bindings/misc/aspeed-p2a-ctrl.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/misc/aspeed-p2a-ctrl.txt b/Documentation/devicetree/bindings/misc/aspeed-p2a-ctrl.txt new file mode 100644 index 000000000000..854bd67ffec6 --- /dev/null +++ b/Documentation/devicetree/bindings/misc/aspeed-p2a-ctrl.txt @@ -0,0 +1,47 @@ +====================================================================== +Device tree bindings for Aspeed AST2400/AST2500 PCI-to-AHB Bridge Control Driver +====================================================================== + +The bridge is available on platforms with the VGA enabled on the Aspeed device. +In this case, the host has access to a 64KiB window into all of the BMC's +memory. The BMC can disable this bridge. If the bridge is enabled, the host +has read access to all the regions of memory, however the host only has read +and write access depending on a register controlled by the BMC. + +Required properties: +=================== + + - compatible: must be one of: + - "aspeed,ast2400-p2a-ctrl" + - "aspeed,ast2500-p2a-ctrl" + +Optional properties: +=================== + +- memory-region: A phandle to a reserved_memory region to be used for the PCI + to AHB mapping + +The p2a-control node should be the child of a syscon node with the required +property: + +- compatible : Should be one of the following: + "aspeed,ast2400-scu", "syscon", "simple-mfd" + "aspeed,g4-scu", "syscon", "simple-mfd" + "aspeed,ast2500-scu", "syscon", "simple-mfd" + "aspeed,g5-scu", "syscon", "simple-mfd" + +Example +=================== + +g4 Example +---------- + +syscon: scu@1e6e2000 { + compatible = "aspeed,ast2400-scu", "syscon", "simple-mfd"; + reg = <0x1e6e2000 0x1a8>; + + p2a: p2a-control { + compatible = "aspeed,ast2400-p2a-ctrl"; + memory-region = <&reserved_memory>; + }; +}; -- cgit v1.2.3 From 43b8a7ed4739a86c1e8543489bf5524780f66284 Mon Sep 17 00:00:00 2001 From: Alexander Usyskin Date: Mon, 22 Apr 2019 09:51:07 +0300 Subject: mei: expose device state in sysfs Expose mei device state to user-space through sysfs. This gives indication to applications that driver is in transition, usefully mostly to detect link reset state. Signed-off-by: Alexander Usyskin Signed-off-by: Tomas Winkler Signed-off-by: Greg Kroah-Hartman --- Documentation/ABI/testing/sysfs-class-mei | 15 +++++++ drivers/misc/mei/client.c | 2 +- drivers/misc/mei/init.c | 20 +++++----- drivers/misc/mei/main.c | 65 ++++++++++++++++++++++++++++--- drivers/misc/mei/mei_dev.h | 3 +- 5 files changed, 87 insertions(+), 18 deletions(-) (limited to 'Documentation') diff --git a/Documentation/ABI/testing/sysfs-class-mei b/Documentation/ABI/testing/sysfs-class-mei index 17d7444a2397..a92d844f806e 100644 --- a/Documentation/ABI/testing/sysfs-class-mei +++ b/Documentation/ABI/testing/sysfs-class-mei @@ -65,3 +65,18 @@ Description: Display the ME firmware version. :.... There can be up to three such blocks for different FW components. + +What: /sys/class/mei/meiN/dev_state +Date: Mar 2019 +KernelVersion: 5.1 +Contact: Tomas Winkler +Description: Display the ME device state. + + The device state can have following values: + INITIALIZING + INIT_CLIENTS + ENABLED + RESETTING + DISABLED + POWER_DOWN + POWER_UP diff --git a/drivers/misc/mei/client.c b/drivers/misc/mei/client.c index 88b83c4bc5b7..1e3edbbacb1e 100644 --- a/drivers/misc/mei/client.c +++ b/drivers/misc/mei/client.c @@ -669,7 +669,7 @@ int mei_cl_unlink(struct mei_cl *cl) void mei_host_client_init(struct mei_device *dev) { - dev->dev_state = MEI_DEV_ENABLED; + mei_set_devstate(dev, MEI_DEV_ENABLED); dev->reset_count = 0; schedule_work(&dev->bus_rescan_work); diff --git a/drivers/misc/mei/init.c b/drivers/misc/mei/init.c index cc359ae968ce..b9fef773e71b 100644 --- a/drivers/misc/mei/init.c +++ b/drivers/misc/mei/init.c @@ -123,12 +123,12 @@ int mei_reset(struct mei_device *dev) /* enter reset flow */ interrupts_enabled = state != MEI_DEV_POWER_DOWN; - dev->dev_state = MEI_DEV_RESETTING; + mei_set_devstate(dev, MEI_DEV_RESETTING); dev->reset_count++; if (dev->reset_count > MEI_MAX_CONSEC_RESET) { dev_err(dev->dev, "reset: reached maximal consecutive resets: disabling the device\n"); - dev->dev_state = MEI_DEV_DISABLED; + mei_set_devstate(dev, MEI_DEV_DISABLED); return -ENODEV; } @@ -150,7 +150,7 @@ int mei_reset(struct mei_device *dev) if (state == MEI_DEV_POWER_DOWN) { dev_dbg(dev->dev, "powering down: end of reset\n"); - dev->dev_state = MEI_DEV_DISABLED; + mei_set_devstate(dev, MEI_DEV_DISABLED); return 0; } @@ -162,11 +162,11 @@ int mei_reset(struct mei_device *dev) dev_dbg(dev->dev, "link is established start sending messages.\n"); - dev->dev_state = MEI_DEV_INIT_CLIENTS; + mei_set_devstate(dev, MEI_DEV_INIT_CLIENTS); ret = mei_hbm_start_req(dev); if (ret) { dev_err(dev->dev, "hbm_start failed ret = %d\n", ret); - dev->dev_state = MEI_DEV_RESETTING; + mei_set_devstate(dev, MEI_DEV_RESETTING); return ret; } @@ -196,7 +196,7 @@ int mei_start(struct mei_device *dev) dev->reset_count = 0; do { - dev->dev_state = MEI_DEV_INITIALIZING; + mei_set_devstate(dev, MEI_DEV_INITIALIZING); ret = mei_reset(dev); if (ret == -ENODEV || dev->dev_state == MEI_DEV_DISABLED) { @@ -231,7 +231,7 @@ int mei_start(struct mei_device *dev) return 0; err: dev_err(dev->dev, "link layer initialization failed.\n"); - dev->dev_state = MEI_DEV_DISABLED; + mei_set_devstate(dev, MEI_DEV_DISABLED); mutex_unlock(&dev->device_lock); return -ENODEV; } @@ -250,7 +250,7 @@ int mei_restart(struct mei_device *dev) mutex_lock(&dev->device_lock); - dev->dev_state = MEI_DEV_POWER_UP; + mei_set_devstate(dev, MEI_DEV_POWER_UP); dev->reset_count = 0; err = mei_reset(dev); @@ -301,7 +301,7 @@ void mei_stop(struct mei_device *dev) dev_dbg(dev->dev, "stopping the device.\n"); mutex_lock(&dev->device_lock); - dev->dev_state = MEI_DEV_POWER_DOWN; + mei_set_devstate(dev, MEI_DEV_POWER_DOWN); mutex_unlock(&dev->device_lock); mei_cl_bus_remove_devices(dev); @@ -314,7 +314,7 @@ void mei_stop(struct mei_device *dev) mei_reset(dev); /* move device to disabled state unconditionally */ - dev->dev_state = MEI_DEV_DISABLED; + mei_set_devstate(dev, MEI_DEV_DISABLED); mutex_unlock(&dev->device_lock); } diff --git a/drivers/misc/mei/main.c b/drivers/misc/mei/main.c index b454df214dde..ad02097d7fee 100644 --- a/drivers/misc/mei/main.c +++ b/drivers/misc/mei/main.c @@ -28,6 +28,12 @@ #include "mei_dev.h" #include "client.h" +static struct class *mei_class; +static dev_t mei_devt; +#define MEI_MAX_DEVS MINORMASK +static DEFINE_MUTEX(mei_minor_lock); +static DEFINE_IDR(mei_idr); + /** * mei_open - the open function * @@ -829,12 +835,65 @@ static ssize_t fw_ver_show(struct device *device, } static DEVICE_ATTR_RO(fw_ver); +/** + * dev_state_show - display device state + * + * @device: device pointer + * @attr: attribute pointer + * @buf: char out buffer + * + * Return: number of the bytes printed into buf or error + */ +static ssize_t dev_state_show(struct device *device, + struct device_attribute *attr, char *buf) +{ + struct mei_device *dev = dev_get_drvdata(device); + enum mei_dev_state dev_state; + + mutex_lock(&dev->device_lock); + dev_state = dev->dev_state; + mutex_unlock(&dev->device_lock); + + return sprintf(buf, "%s", mei_dev_state_str(dev_state)); +} +static DEVICE_ATTR_RO(dev_state); + +static int match_devt(struct device *dev, const void *data) +{ + const dev_t *devt = data; + + return dev->devt == *devt; +} + +/** + * dev_set_devstate: set to new device state and notify sysfs file. + * + * @dev: mei_device + * @state: new device state + */ +void mei_set_devstate(struct mei_device *dev, enum mei_dev_state state) +{ + struct device *clsdev; + + if (dev->dev_state == state) + return; + + dev->dev_state = state; + + clsdev = class_find_device(mei_class, NULL, &dev->cdev.dev, match_devt); + if (clsdev) { + sysfs_notify(&clsdev->kobj, NULL, "dev_state"); + put_device(clsdev); + } +} + static struct attribute *mei_attrs[] = { &dev_attr_fw_status.attr, &dev_attr_hbm_ver.attr, &dev_attr_hbm_ver_drv.attr, &dev_attr_tx_queue_limit.attr, &dev_attr_fw_ver.attr, + &dev_attr_dev_state.attr, NULL }; ATTRIBUTE_GROUPS(mei); @@ -858,12 +917,6 @@ static const struct file_operations mei_fops = { .llseek = no_llseek }; -static struct class *mei_class; -static dev_t mei_devt; -#define MEI_MAX_DEVS MINORMASK -static DEFINE_MUTEX(mei_minor_lock); -static DEFINE_IDR(mei_idr); - /** * mei_minor_get - obtain next free device minor number * diff --git a/drivers/misc/mei/mei_dev.h b/drivers/misc/mei/mei_dev.h index 3146df37ffb0..fca832fcac57 100644 --- a/drivers/misc/mei/mei_dev.h +++ b/drivers/misc/mei/mei_dev.h @@ -525,7 +525,6 @@ struct mei_device { struct dentry *dbgfs_dir; #endif /* CONFIG_DEBUG_FS */ - const struct mei_hw_ops *ops; char hw[0] __aligned(sizeof(void *)); }; @@ -584,6 +583,8 @@ int mei_restart(struct mei_device *dev); void mei_stop(struct mei_device *dev); void mei_cancel_work(struct mei_device *dev); +void mei_set_devstate(struct mei_device *dev, enum mei_dev_state state); + int mei_dmam_ring_alloc(struct mei_device *dev); void mei_dmam_ring_free(struct mei_device *dev); bool mei_dma_ring_is_allocated(struct mei_device *dev); -- cgit v1.2.3 From 4f4cb173d811ba37aab3048b70583b6c73803d42 Mon Sep 17 00:00:00 2001 From: Fabrice Gasnier Date: Sat, 13 Apr 2019 11:32:54 +0100 Subject: dt-bindings: nvmem: Add STM32 factory-programmed romem Add documentation for STMicroelectronics STM32 Factory-programmed read only memory area. Signed-off-by: Fabrice Gasnier Reviewed-by: Rob Herring Signed-off-by: Srinivas Kandagatla Signed-off-by: Greg Kroah-Hartman --- .../devicetree/bindings/nvmem/st,stm32-romem.txt | 31 ++++++++++++++++++++++ 1 file changed, 31 insertions(+) create mode 100644 Documentation/devicetree/bindings/nvmem/st,stm32-romem.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/nvmem/st,stm32-romem.txt b/Documentation/devicetree/bindings/nvmem/st,stm32-romem.txt new file mode 100644 index 000000000000..142a51d5a9be --- /dev/null +++ b/Documentation/devicetree/bindings/nvmem/st,stm32-romem.txt @@ -0,0 +1,31 @@ +STMicroelectronics STM32 Factory-programmed data device tree bindings + +This represents STM32 Factory-programmed read only non-volatile area: locked +flash, OTP, read-only HW regs... This contains various information such as: +analog calibration data for temperature sensor (e.g. TS_CAL1, TS_CAL2), +internal vref (VREFIN_CAL), unique device ID... + +Required properties: +- compatible: Should be one of: + "st,stm32f4-otp" + "st,stm32mp15-bsec" +- reg: Offset and length of factory-programmed area. +- #address-cells: Should be '<1>'. +- #size-cells: Should be '<1>'. + +Optional Data cells: +- Must be child nodes as described in nvmem.txt. + +Example on stm32f4: + romem: nvmem@1fff7800 { + compatible = "st,stm32f4-otp"; + reg = <0x1fff7800 0x400>; + #address-cells = <1>; + #size-cells = <1>; + + /* Data cells: ts_cal1 at 0x1fff7a2c */ + ts_cal1: calib@22c { + reg = <0x22c 0x2>; + }; + ... + }; -- cgit v1.2.3 From b8371fc104d3acb87b04dbc70e75eda4714931e6 Mon Sep 17 00:00:00 2001 From: Yangtao Li Date: Sat, 13 Apr 2019 11:33:02 +0100 Subject: nvmem: sunxi-sid: fix wrong description in kernel doc qfprom->sunxi-sid Acked-by: Maxime Ripard Reviewed-by: Rob Herring Signed-off-by: Yangtao Li Signed-off-by: Srinivas Kandagatla Signed-off-by: Greg Kroah-Hartman --- Documentation/devicetree/bindings/nvmem/allwinner,sunxi-sid.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/nvmem/allwinner,sunxi-sid.txt b/Documentation/devicetree/bindings/nvmem/allwinner,sunxi-sid.txt index 99c4ba6a3f61..d37017e343b1 100644 --- a/Documentation/devicetree/bindings/nvmem/allwinner,sunxi-sid.txt +++ b/Documentation/devicetree/bindings/nvmem/allwinner,sunxi-sid.txt @@ -12,7 +12,7 @@ Required properties: - reg: Should contain registers location and length = Data cells = -Are child nodes of qfprom, bindings of which as described in +Are child nodes of sunxi-sid, bindings of which as described in bindings/nvmem/nvmem.txt Example for sun4i: -- cgit v1.2.3 From f6edbb38ea8369bf366475924ba02178e4c25183 Mon Sep 17 00:00:00 2001 From: Yangtao Li Date: Sat, 13 Apr 2019 11:33:03 +0100 Subject: nvmem: sunxi-sid: add binding for H6's SID controller Add a binding for H6's SID controller. Acked-by: Maxime Ripard Reviewed-by: Rob Herring Signed-off-by: Yangtao Li Signed-off-by: Srinivas Kandagatla Signed-off-by: Greg Kroah-Hartman --- Documentation/devicetree/bindings/nvmem/allwinner,sunxi-sid.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/nvmem/allwinner,sunxi-sid.txt b/Documentation/devicetree/bindings/nvmem/allwinner,sunxi-sid.txt index d37017e343b1..cfb18b4ef8f7 100644 --- a/Documentation/devicetree/bindings/nvmem/allwinner,sunxi-sid.txt +++ b/Documentation/devicetree/bindings/nvmem/allwinner,sunxi-sid.txt @@ -8,6 +8,7 @@ Required properties: "allwinner,sun8i-h3-sid" "allwinner,sun50i-a64-sid" "allwinner,sun50i-h5-sid" + "allwinner,sun50i-h6-sid" - reg: Should contain registers location and length -- cgit v1.2.3 From ae0c2d725512f32a0d1a25f0cf2f07616d33a72e Mon Sep 17 00:00:00 2001 From: Srinivas Kandagatla Date: Tue, 16 Apr 2019 10:59:24 +0100 Subject: nvmem: core: add NVMEM_SYSFS Kconfig Many nvmem providers are not very keen on having default sysfs nvmem entry, as most of the usecases for them are inside kernel itself. And in some cases read/writes to some areas in nvmem are restricted and trapped at secure monitor level, so accessing them from userspace would result in board reboots. This patch adds new NVMEM_SYSFS Kconfig to make binary sysfs entry an optional one. This provision will give more flexibility to users. This patch also moves existing sysfs code to a new file so that its not compiled in when its not really required. Signed-off-by: Srinivas Kandagatla Reviewed-by: Mika Westerberg Reviewed-by: Gaurav Kohli Tested-by: Gaurav Kohli Signed-off-by: Greg Kroah-Hartman --- Documentation/ABI/stable/sysfs-bus-nvmem | 2 + drivers/nvmem/Kconfig | 10 ++ drivers/nvmem/Makefile | 3 + drivers/nvmem/core.c | 264 +------------------------------ drivers/nvmem/nvmem-sysfs.c | 256 ++++++++++++++++++++++++++++++ drivers/nvmem/nvmem.h | 62 ++++++++ 6 files changed, 337 insertions(+), 260 deletions(-) create mode 100644 drivers/nvmem/nvmem-sysfs.c create mode 100644 drivers/nvmem/nvmem.h (limited to 'Documentation') diff --git a/Documentation/ABI/stable/sysfs-bus-nvmem b/Documentation/ABI/stable/sysfs-bus-nvmem index 5923ab4620c5..9ffba8576f7b 100644 --- a/Documentation/ABI/stable/sysfs-bus-nvmem +++ b/Documentation/ABI/stable/sysfs-bus-nvmem @@ -6,6 +6,8 @@ Description: This file allows user to read/write the raw NVMEM contents. Permissions for write to this file depends on the nvmem provider configuration. + Note: This file is only present if CONFIG_NVMEM_SYSFS + is enabled ex: hexdump /sys/bus/nvmem/devices/qfprom0/nvmem diff --git a/drivers/nvmem/Kconfig b/drivers/nvmem/Kconfig index a90e9a1ebe55..6b2c4254c2fb 100644 --- a/drivers/nvmem/Kconfig +++ b/drivers/nvmem/Kconfig @@ -13,6 +13,16 @@ menuconfig NVMEM if NVMEM +config NVMEM_SYSFS + bool "/sys/bus/nvmem/devices/*/nvmem (sysfs interface)" + depends on SYSFS + default y + help + Say Y here to add a sysfs interface for NVMEM. + + This interface is mostly used by userspace applications to + read/write directly into nvmem. + config NVMEM_IMX_IIM tristate "i.MX IC Identification Module support" depends on ARCH_MXC || COMPILE_TEST diff --git a/drivers/nvmem/Makefile b/drivers/nvmem/Makefile index 4c7ba12a7005..c1fe4768dfef 100644 --- a/drivers/nvmem/Makefile +++ b/drivers/nvmem/Makefile @@ -6,6 +6,9 @@ obj-$(CONFIG_NVMEM) += nvmem_core.o nvmem_core-y := core.o +obj-$(CONFIG_NVMEM_SYSFS) += nvmem_sysfs.o +nvmem_sysfs-y := nvmem-sysfs.o + # Devices obj-$(CONFIG_NVMEM_BCM_OCOTP) += nvmem-bcm-ocotp.o nvmem-bcm-ocotp-y := bcm-ocotp.o diff --git a/drivers/nvmem/core.c b/drivers/nvmem/core.c index 5abebf2128b8..c7892c3da91f 100644 --- a/drivers/nvmem/core.c +++ b/drivers/nvmem/core.c @@ -17,27 +17,7 @@ #include #include #include - -struct nvmem_device { - struct module *owner; - struct device dev; - int stride; - int word_size; - int id; - struct kref refcnt; - size_t size; - bool read_only; - int flags; - enum nvmem_type type; - struct bin_attribute eeprom; - struct device *base_dev; - struct list_head cells; - nvmem_reg_read_t reg_read; - nvmem_reg_write_t reg_write; - void *priv; -}; - -#define FLAG_COMPAT BIT(0) +#include "nvmem.h" struct nvmem_cell { const char *name; @@ -61,18 +41,7 @@ static LIST_HEAD(nvmem_lookup_list); static BLOCKING_NOTIFIER_HEAD(nvmem_notifier); -static const char * const nvmem_type_str[] = { - [NVMEM_TYPE_UNKNOWN] = "Unknown", - [NVMEM_TYPE_EEPROM] = "EEPROM", - [NVMEM_TYPE_OTP] = "OTP", - [NVMEM_TYPE_BATTERY_BACKED] = "Battery backed", -}; - -#ifdef CONFIG_DEBUG_LOCK_ALLOC -static struct lock_class_key eeprom_lock_key; -#endif -#define to_nvmem_device(d) container_of(d, struct nvmem_device, dev) static int nvmem_reg_read(struct nvmem_device *nvmem, unsigned int offset, void *val, size_t bytes) { @@ -91,187 +60,6 @@ static int nvmem_reg_write(struct nvmem_device *nvmem, unsigned int offset, return -EINVAL; } -static ssize_t type_show(struct device *dev, - struct device_attribute *attr, char *buf) -{ - struct nvmem_device *nvmem = to_nvmem_device(dev); - - return sprintf(buf, "%s\n", nvmem_type_str[nvmem->type]); -} - -static DEVICE_ATTR_RO(type); - -static struct attribute *nvmem_attrs[] = { - &dev_attr_type.attr, - NULL, -}; - -static ssize_t bin_attr_nvmem_read(struct file *filp, struct kobject *kobj, - struct bin_attribute *attr, - char *buf, loff_t pos, size_t count) -{ - struct device *dev; - struct nvmem_device *nvmem; - int rc; - - if (attr->private) - dev = attr->private; - else - dev = container_of(kobj, struct device, kobj); - nvmem = to_nvmem_device(dev); - - /* Stop the user from reading */ - if (pos >= nvmem->size) - return 0; - - if (count < nvmem->word_size) - return -EINVAL; - - if (pos + count > nvmem->size) - count = nvmem->size - pos; - - count = round_down(count, nvmem->word_size); - - rc = nvmem_reg_read(nvmem, pos, buf, count); - - if (rc) - return rc; - - return count; -} - -static ssize_t bin_attr_nvmem_write(struct file *filp, struct kobject *kobj, - struct bin_attribute *attr, - char *buf, loff_t pos, size_t count) -{ - struct device *dev; - struct nvmem_device *nvmem; - int rc; - - if (attr->private) - dev = attr->private; - else - dev = container_of(kobj, struct device, kobj); - nvmem = to_nvmem_device(dev); - - /* Stop the user from writing */ - if (pos >= nvmem->size) - return -EFBIG; - - if (count < nvmem->word_size) - return -EINVAL; - - if (pos + count > nvmem->size) - count = nvmem->size - pos; - - count = round_down(count, nvmem->word_size); - - rc = nvmem_reg_write(nvmem, pos, buf, count); - - if (rc) - return rc; - - return count; -} - -/* default read/write permissions */ -static struct bin_attribute bin_attr_rw_nvmem = { - .attr = { - .name = "nvmem", - .mode = 0644, - }, - .read = bin_attr_nvmem_read, - .write = bin_attr_nvmem_write, -}; - -static struct bin_attribute *nvmem_bin_rw_attributes[] = { - &bin_attr_rw_nvmem, - NULL, -}; - -static const struct attribute_group nvmem_bin_rw_group = { - .bin_attrs = nvmem_bin_rw_attributes, - .attrs = nvmem_attrs, -}; - -static const struct attribute_group *nvmem_rw_dev_groups[] = { - &nvmem_bin_rw_group, - NULL, -}; - -/* read only permission */ -static struct bin_attribute bin_attr_ro_nvmem = { - .attr = { - .name = "nvmem", - .mode = 0444, - }, - .read = bin_attr_nvmem_read, -}; - -static struct bin_attribute *nvmem_bin_ro_attributes[] = { - &bin_attr_ro_nvmem, - NULL, -}; - -static const struct attribute_group nvmem_bin_ro_group = { - .bin_attrs = nvmem_bin_ro_attributes, - .attrs = nvmem_attrs, -}; - -static const struct attribute_group *nvmem_ro_dev_groups[] = { - &nvmem_bin_ro_group, - NULL, -}; - -/* default read/write permissions, root only */ -static struct bin_attribute bin_attr_rw_root_nvmem = { - .attr = { - .name = "nvmem", - .mode = 0600, - }, - .read = bin_attr_nvmem_read, - .write = bin_attr_nvmem_write, -}; - -static struct bin_attribute *nvmem_bin_rw_root_attributes[] = { - &bin_attr_rw_root_nvmem, - NULL, -}; - -static const struct attribute_group nvmem_bin_rw_root_group = { - .bin_attrs = nvmem_bin_rw_root_attributes, - .attrs = nvmem_attrs, -}; - -static const struct attribute_group *nvmem_rw_root_dev_groups[] = { - &nvmem_bin_rw_root_group, - NULL, -}; - -/* read only permission, root only */ -static struct bin_attribute bin_attr_ro_root_nvmem = { - .attr = { - .name = "nvmem", - .mode = 0400, - }, - .read = bin_attr_nvmem_read, -}; - -static struct bin_attribute *nvmem_bin_ro_root_attributes[] = { - &bin_attr_ro_root_nvmem, - NULL, -}; - -static const struct attribute_group nvmem_bin_ro_root_group = { - .bin_attrs = nvmem_bin_ro_root_attributes, - .attrs = nvmem_attrs, -}; - -static const struct attribute_group *nvmem_ro_root_dev_groups[] = { - &nvmem_bin_ro_root_group, - NULL, -}; - static void nvmem_release(struct device *dev) { struct nvmem_device *nvmem = to_nvmem_device(dev); @@ -422,43 +210,6 @@ err: return rval; } -/* - * nvmem_setup_compat() - Create an additional binary entry in - * drivers sys directory, to be backwards compatible with the older - * drivers/misc/eeprom drivers. - */ -static int nvmem_setup_compat(struct nvmem_device *nvmem, - const struct nvmem_config *config) -{ - int rval; - - if (!config->base_dev) - return -EINVAL; - - if (nvmem->read_only) - nvmem->eeprom = bin_attr_ro_root_nvmem; - else - nvmem->eeprom = bin_attr_rw_root_nvmem; - nvmem->eeprom.attr.name = "eeprom"; - nvmem->eeprom.size = nvmem->size; -#ifdef CONFIG_DEBUG_LOCK_ALLOC - nvmem->eeprom.attr.key = &eeprom_lock_key; -#endif - nvmem->eeprom.private = &nvmem->dev; - nvmem->base_dev = config->base_dev; - - rval = device_create_bin_file(nvmem->base_dev, &nvmem->eeprom); - if (rval) { - dev_err(&nvmem->dev, - "Failed to create eeprom binary file %d\n", rval); - return rval; - } - - nvmem->flags |= FLAG_COMPAT; - - return 0; -} - /** * nvmem_register_notifier() - Register a notifier block for nvmem events. * @@ -651,14 +402,7 @@ struct nvmem_device *nvmem_register(const struct nvmem_config *config) nvmem->read_only = device_property_present(config->dev, "read-only") || config->read_only || !nvmem->reg_write; - if (config->root_only) - nvmem->dev.groups = nvmem->read_only ? - nvmem_ro_root_dev_groups : - nvmem_rw_root_dev_groups; - else - nvmem->dev.groups = nvmem->read_only ? - nvmem_ro_dev_groups : - nvmem_rw_dev_groups; + nvmem->dev.groups = nvmem_sysfs_get_groups(nvmem, config); device_initialize(&nvmem->dev); @@ -669,7 +413,7 @@ struct nvmem_device *nvmem_register(const struct nvmem_config *config) goto err_put_device; if (config->compat) { - rval = nvmem_setup_compat(nvmem, config); + rval = nvmem_sysfs_setup_compat(nvmem, config); if (rval) goto err_device_del; } @@ -696,7 +440,7 @@ err_remove_cells: nvmem_device_remove_all_cells(nvmem); err_teardown_compat: if (config->compat) - device_remove_bin_file(nvmem->base_dev, &nvmem->eeprom); + nvmem_sysfs_remove_compat(nvmem, config); err_device_del: device_del(&nvmem->dev); err_put_device: diff --git a/drivers/nvmem/nvmem-sysfs.c b/drivers/nvmem/nvmem-sysfs.c new file mode 100644 index 000000000000..6f303b91f6e7 --- /dev/null +++ b/drivers/nvmem/nvmem-sysfs.c @@ -0,0 +1,256 @@ +// SPDX-License-Identifier: GPL-2.0 +/* + * Copyright (c) 2019, Linaro Limited + */ +#include "nvmem.h" + +static const char * const nvmem_type_str[] = { + [NVMEM_TYPE_UNKNOWN] = "Unknown", + [NVMEM_TYPE_EEPROM] = "EEPROM", + [NVMEM_TYPE_OTP] = "OTP", + [NVMEM_TYPE_BATTERY_BACKED] = "Battery backed", +}; + +#ifdef CONFIG_DEBUG_LOCK_ALLOC +static struct lock_class_key eeprom_lock_key; +#endif + +static ssize_t type_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + struct nvmem_device *nvmem = to_nvmem_device(dev); + + return sprintf(buf, "%s\n", nvmem_type_str[nvmem->type]); +} + +static DEVICE_ATTR_RO(type); + +static struct attribute *nvmem_attrs[] = { + &dev_attr_type.attr, + NULL, +}; + +static ssize_t bin_attr_nvmem_read(struct file *filp, struct kobject *kobj, + struct bin_attribute *attr, + char *buf, loff_t pos, size_t count) +{ + struct device *dev; + struct nvmem_device *nvmem; + int rc; + + if (attr->private) + dev = attr->private; + else + dev = container_of(kobj, struct device, kobj); + nvmem = to_nvmem_device(dev); + + /* Stop the user from reading */ + if (pos >= nvmem->size) + return 0; + + if (count < nvmem->word_size) + return -EINVAL; + + if (pos + count > nvmem->size) + count = nvmem->size - pos; + + count = round_down(count, nvmem->word_size); + + rc = nvmem->reg_read(nvmem->priv, pos, buf, count); + + if (rc) + return rc; + + return count; +} + +static ssize_t bin_attr_nvmem_write(struct file *filp, struct kobject *kobj, + struct bin_attribute *attr, + char *buf, loff_t pos, size_t count) +{ + struct device *dev; + struct nvmem_device *nvmem; + int rc; + + if (attr->private) + dev = attr->private; + else + dev = container_of(kobj, struct device, kobj); + nvmem = to_nvmem_device(dev); + + /* Stop the user from writing */ + if (pos >= nvmem->size) + return -EFBIG; + + if (count < nvmem->word_size) + return -EINVAL; + + if (pos + count > nvmem->size) + count = nvmem->size - pos; + + count = round_down(count, nvmem->word_size); + + rc = nvmem->reg_write(nvmem->priv, pos, buf, count); + + if (rc) + return rc; + + return count; +} + +/* default read/write permissions */ +static struct bin_attribute bin_attr_rw_nvmem = { + .attr = { + .name = "nvmem", + .mode = 0644, + }, + .read = bin_attr_nvmem_read, + .write = bin_attr_nvmem_write, +}; + +static struct bin_attribute *nvmem_bin_rw_attributes[] = { + &bin_attr_rw_nvmem, + NULL, +}; + +static const struct attribute_group nvmem_bin_rw_group = { + .bin_attrs = nvmem_bin_rw_attributes, + .attrs = nvmem_attrs, +}; + +static const struct attribute_group *nvmem_rw_dev_groups[] = { + &nvmem_bin_rw_group, + NULL, +}; + +/* read only permission */ +static struct bin_attribute bin_attr_ro_nvmem = { + .attr = { + .name = "nvmem", + .mode = 0444, + }, + .read = bin_attr_nvmem_read, +}; + +static struct bin_attribute *nvmem_bin_ro_attributes[] = { + &bin_attr_ro_nvmem, + NULL, +}; + +static const struct attribute_group nvmem_bin_ro_group = { + .bin_attrs = nvmem_bin_ro_attributes, + .attrs = nvmem_attrs, +}; + +static const struct attribute_group *nvmem_ro_dev_groups[] = { + &nvmem_bin_ro_group, + NULL, +}; + +/* default read/write permissions, root only */ +static struct bin_attribute bin_attr_rw_root_nvmem = { + .attr = { + .name = "nvmem", + .mode = 0600, + }, + .read = bin_attr_nvmem_read, + .write = bin_attr_nvmem_write, +}; + +static struct bin_attribute *nvmem_bin_rw_root_attributes[] = { + &bin_attr_rw_root_nvmem, + NULL, +}; + +static const struct attribute_group nvmem_bin_rw_root_group = { + .bin_attrs = nvmem_bin_rw_root_attributes, + .attrs = nvmem_attrs, +}; + +static const struct attribute_group *nvmem_rw_root_dev_groups[] = { + &nvmem_bin_rw_root_group, + NULL, +}; + +/* read only permission, root only */ +static struct bin_attribute bin_attr_ro_root_nvmem = { + .attr = { + .name = "nvmem", + .mode = 0400, + }, + .read = bin_attr_nvmem_read, +}; + +static struct bin_attribute *nvmem_bin_ro_root_attributes[] = { + &bin_attr_ro_root_nvmem, + NULL, +}; + +static const struct attribute_group nvmem_bin_ro_root_group = { + .bin_attrs = nvmem_bin_ro_root_attributes, + .attrs = nvmem_attrs, +}; + +static const struct attribute_group *nvmem_ro_root_dev_groups[] = { + &nvmem_bin_ro_root_group, + NULL, +}; + +const struct attribute_group **nvmem_sysfs_get_groups( + struct nvmem_device *nvmem, + const struct nvmem_config *config) +{ + if (config->root_only) + return nvmem->read_only ? + nvmem_ro_root_dev_groups : + nvmem_rw_root_dev_groups; + + return nvmem->read_only ? nvmem_ro_dev_groups : nvmem_rw_dev_groups; +} + +/* + * nvmem_setup_compat() - Create an additional binary entry in + * drivers sys directory, to be backwards compatible with the older + * drivers/misc/eeprom drivers. + */ +int nvmem_sysfs_setup_compat(struct nvmem_device *nvmem, + const struct nvmem_config *config) +{ + int rval; + + if (!config->compat) + return 0; + + if (!config->base_dev) + return -EINVAL; + + if (nvmem->read_only) + nvmem->eeprom = bin_attr_ro_root_nvmem; + else + nvmem->eeprom = bin_attr_rw_root_nvmem; + nvmem->eeprom.attr.name = "eeprom"; + nvmem->eeprom.size = nvmem->size; +#ifdef CONFIG_DEBUG_LOCK_ALLOC + nvmem->eeprom.attr.key = &eeprom_lock_key; +#endif + nvmem->eeprom.private = &nvmem->dev; + nvmem->base_dev = config->base_dev; + + rval = device_create_bin_file(nvmem->base_dev, &nvmem->eeprom); + if (rval) { + dev_err(&nvmem->dev, + "Failed to create eeprom binary file %d\n", rval); + return rval; + } + + nvmem->flags |= FLAG_COMPAT; + + return 0; +} + +void nvmem_sysfs_remove_compat(struct nvmem_device *nvmem, + const struct nvmem_config *config) +{ + if (config->compat) + device_remove_bin_file(nvmem->base_dev, &nvmem->eeprom); +} diff --git a/drivers/nvmem/nvmem.h b/drivers/nvmem/nvmem.h new file mode 100644 index 000000000000..eb8ed7121fa3 --- /dev/null +++ b/drivers/nvmem/nvmem.h @@ -0,0 +1,62 @@ +/* SPDX-License-Identifier: GPL-2.0 */ + +#ifndef _DRIVERS_NVMEM_H +#define _DRIVERS_NVMEM_H + +#include +#include +#include +#include +#include +#include + +struct nvmem_device { + struct module *owner; + struct device dev; + int stride; + int word_size; + int id; + struct kref refcnt; + size_t size; + bool read_only; + int flags; + enum nvmem_type type; + struct bin_attribute eeprom; + struct device *base_dev; + struct list_head cells; + nvmem_reg_read_t reg_read; + nvmem_reg_write_t reg_write; + void *priv; +}; + +#define to_nvmem_device(d) container_of(d, struct nvmem_device, dev) +#define FLAG_COMPAT BIT(0) + +#ifdef CONFIG_NVMEM_SYSFS +const struct attribute_group **nvmem_sysfs_get_groups( + struct nvmem_device *nvmem, + const struct nvmem_config *config); +int nvmem_sysfs_setup_compat(struct nvmem_device *nvmem, + const struct nvmem_config *config); +void nvmem_sysfs_remove_compat(struct nvmem_device *nvmem, + const struct nvmem_config *config); +#else +static inline const struct attribute_group **nvmem_sysfs_get_groups( + struct nvmem_device *nvmem, + const struct nvmem_config *config) +{ + return NULL; +} + +static inline int nvmem_sysfs_setup_compat(struct nvmem_device *nvmem, + const struct nvmem_config *config) +{ + return -ENOSYS; +} +static inline void nvmem_sysfs_remove_compat(struct nvmem_device *nvmem, + const struct nvmem_config *config) +{ +} +#endif /* CONFIG_NVMEM_SYSFS */ + +#endif /* _DRIVERS_NVMEM_H */ -- cgit v1.2.3 From 0a790fe4389d88253563c5e22bea47e6d357b525 Mon Sep 17 00:00:00 2001 From: Gabriel Krisman Bertazi Date: Thu, 25 Apr 2019 14:13:27 -0400 Subject: docs: ext4.rst: document case-insensitive directories Introduces the case-insensitive features on ext4 for system administrators. Explain the minimum of design decisions that are important for sysadmins wanting to enable this feature. Signed-off-by: Gabriel Krisman Bertazi Signed-off-by: Theodore Ts'o --- Documentation/admin-guide/ext4.rst | 38 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 38 insertions(+) (limited to 'Documentation') diff --git a/Documentation/admin-guide/ext4.rst b/Documentation/admin-guide/ext4.rst index e506d3dae510..059ddcbe769d 100644 --- a/Documentation/admin-guide/ext4.rst +++ b/Documentation/admin-guide/ext4.rst @@ -91,10 +91,48 @@ Currently Available * large block (up to pagesize) support * efficient new ordered mode in JBD2 and ext4 (avoid using buffer head to force the ordering) +* Case-insensitive file name lookups [1] Filesystems with a block size of 1k may see a limit imposed by the directory hash tree having a maximum depth of two. +case-insensitive file name lookups +====================================================== + +The case-insensitive file name lookup feature is supported on a +per-directory basis, allowing the user to mix case-insensitive and +case-sensitive directories in the same filesystem. It is enabled by +flipping the +F inode attribute of an empty directory. The +case-insensitive string match operation is only defined when we know how +text in encoded in a byte sequence. For that reason, in order to enable +case-insensitive directories, the filesystem must have the +casefold feature, which stores the filesystem-wide encoding +model used. By default, the charset adopted is the latest version of +Unicode (12.1.0, by the time of this writing), encoded in the UTF-8 +form. The comparison algorithm is implemented by normalizing the +strings to the Canonical decomposition form, as defined by Unicode, +followed by a byte per byte comparison. + +The case-awareness is name-preserving on the disk, meaning that the file +name provided by userspace is a byte-per-byte match to what is actually +written in the disk. The Unicode normalization format used by the +kernel is thus an internal representation, and not exposed to the +userspace nor to the disk, with the important exception of disk hashes, +used on large case-insensitive directories with DX feature. On DX +directories, the hash must be calculated using the casefolded version of +the filename, meaning that the normalization format used actually has an +impact on where the directory entry is stored. + +When we change from viewing filenames as opaque byte sequences to seeing +them as encoded strings we need to address what happens when a program +tries to create a file with an invalid name. The Unicode subsystem +within the kernel leaves the decision of what to do in this case to the +filesystem, which select its preferred behavior by enabling/disabling +the strict mode. When Ext4 encounters one of those strings and the +filesystem did not require strict mode, it falls back to considering the +entire string as an opaque byte sequence, which still allows the user to +operate on that file, but the case-insensitive lookups won't work. + Options ======= -- cgit v1.2.3 From f34b2c26fc7d120b26cb181b8d4115675ec58244 Mon Sep 17 00:00:00 2001 From: Yuantian Tang Date: Mon, 22 Apr 2019 17:15:08 +0800 Subject: dt-bindings: qoriq-clock: add more PLL divider clocks support More PLL divider clocks are needed by clock consumer IP. So update the PLL divider description to make it more general. Signed-off-by: Yuantian Tang Signed-off-by: Stephen Boyd --- Documentation/devicetree/bindings/clock/qoriq-clock.txt | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/clock/qoriq-clock.txt b/Documentation/devicetree/bindings/clock/qoriq-clock.txt index c655f28d5918..27aeed056872 100644 --- a/Documentation/devicetree/bindings/clock/qoriq-clock.txt +++ b/Documentation/devicetree/bindings/clock/qoriq-clock.txt @@ -83,8 +83,8 @@ second cell is the clock index for the specified type. 1 cmux index (n in CLKCnCSR) 2 hwaccel index (n in CLKCGnHWACSR) 3 fman 0 for fm1, 1 for fm2 - 4 platform pll 0=pll, 1=pll/2, 2=pll/3, 3=pll/4 - 4=pll/5, 5=pll/6, 6=pll/7, 7=pll/8 + 4 platform pll n=pll/(n+1). For example, when n=1, + that means output_freq=PLL_freq/2. 5 coreclk must be 0 3. Example -- cgit v1.2.3 From 008aa5fd119f00c76162de78a0bcd414af7c9fd4 Mon Sep 17 00:00:00 2001 From: Yuantian Tang Date: Wed, 24 Apr 2019 10:28:47 +0800 Subject: dt-bindings: qoriq-clock: Add ls1028a chip compatible string Add ls1028a chip compatible string in binding document. Signed-off-by: Yuantian Tang Signed-off-by: Stephen Boyd --- Documentation/devicetree/bindings/clock/qoriq-clock.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/clock/qoriq-clock.txt b/Documentation/devicetree/bindings/clock/qoriq-clock.txt index 27aeed056872..f7d48f23da44 100644 --- a/Documentation/devicetree/bindings/clock/qoriq-clock.txt +++ b/Documentation/devicetree/bindings/clock/qoriq-clock.txt @@ -39,6 +39,7 @@ Required properties: * "fsl,b4860-clockgen" * "fsl,ls1012a-clockgen" * "fsl,ls1021a-clockgen" + * "fsl,ls1028a-clockgen" * "fsl,ls1043a-clockgen" * "fsl,ls1046a-clockgen" * "fsl,ls1088a-clockgen" -- cgit v1.2.3 From cc40f6404d28d1de4a09064aeff185a391c51c35 Mon Sep 17 00:00:00 2001 From: Alexandre Belloni Date: Tue, 19 Feb 2019 18:01:54 +0100 Subject: dt-bindings: clock: at91: new sckc bindings Remove the need for child nodes in the sckc binding to be able to remove dtc warnings and have a more modern binding. Also document optional properties. Cc: Rob Herring Reviewed-by: Rob Herring Signed-off-by: Alexandre Belloni Signed-off-by: Stephen Boyd --- .../devicetree/bindings/clock/at91-clock.txt | 30 +++++++++------------- 1 file changed, 12 insertions(+), 18 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/clock/at91-clock.txt b/Documentation/devicetree/bindings/clock/at91-clock.txt index e9f70fcdfe80..cb838c1c4bdd 100644 --- a/Documentation/devicetree/bindings/clock/at91-clock.txt +++ b/Documentation/devicetree/bindings/clock/at91-clock.txt @@ -8,29 +8,23 @@ Slow Clock controller: Required properties: - compatible : shall be one of the following: - "atmel,at91sam9x5-sckc" or + "atmel,at91sam9x5-sckc", + "atmel,sama5d3-sckc" or "atmel,sama5d4-sckc": at91 SCKC (Slow Clock Controller) - This node contains the slow clock definitions. - - "atmel,at91sam9x5-clk-slow-osc": - at91 slow oscillator - - "atmel,at91sam9x5-clk-slow-rc-osc": - at91 internal slow RC oscillator -- reg : defines the IO memory reserved for the SCKC. -- #size-cells : shall be 0 (reg is used to encode clk id). -- #address-cells : shall be 1 (reg is used to encode clk id). +- #clock-cells : shall be 0. +- clocks : shall be the input parent clock phandle for the clock. +Optional properties: +- atmel,osc-bypass : boolean property. Set this when a clock signal is directly + provided on XIN. For example: - sckc: sckc@fffffe50 { - compatible = "atmel,sama5d3-pmc"; - reg = <0xfffffe50 0x4> - #size-cells = <0>; - #address-cells = <1>; - - /* put at91 slow clocks here */ + sckc@fffffe50 { + compatible = "atmel,at91sam9x5-sckc"; + reg = <0xfffffe50 0x4>; + clocks = <&slow_xtal>; + #clock-cells = <0>; }; Power Management Controller (PMC): -- cgit v1.2.3 From c634d3ffc6b2c3b15ea79ffe0a761ce08b4da71a Mon Sep 17 00:00:00 2001 From: Baolin Wang Date: Tue, 23 Apr 2019 10:26:21 +0800 Subject: dt-bindings: ASoC: Add Spreadtrum multi-channel data transfer support On Spreadtrum platform, the audio subsystem will use the multi-channel data transfer controller to transfer sound stream between audio subsystem and other AP/CP subsystem. It can support 10 DAC channel and 10 ADC channel, and each channel has 512 bytes depth data fifo. Moreover each channel can be used DMA mode or interrupt mode to transfer data. Signed-off-by: Baolin Wang Signed-off-by: Mark Brown --- Documentation/devicetree/bindings/sound/sprd-mcdt.txt | 19 +++++++++++++++++++ 1 file changed, 19 insertions(+) create mode 100644 Documentation/devicetree/bindings/sound/sprd-mcdt.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/sound/sprd-mcdt.txt b/Documentation/devicetree/bindings/sound/sprd-mcdt.txt new file mode 100644 index 000000000000..274ba0acbfd6 --- /dev/null +++ b/Documentation/devicetree/bindings/sound/sprd-mcdt.txt @@ -0,0 +1,19 @@ +Spreadtrum Multi-Channel Data Transfer Binding + +The Multi-channel data transfer controller is used for sound stream +transmission between audio subsystem and other AP/CP subsystem. It +supports 10 DAC channel and 10 ADC channel, and each channel can be +configured with DMA mode or interrupt mode. + +Required properties: +- compatible: Should be "sprd,sc9860-mcdt". +- reg: Should contain registers address and length. +- interrupts: Should contain one interrupt shared by all channel. + +Example: + +mcdt@41490000 { + compatible = "sprd,sc9860-mcdt"; + reg = <0 0x41490000 0 0x170>; + interrupts = ; +}; -- cgit v1.2.3 From 936289f0476bed97df55846f8fc671c837e4e58c Mon Sep 17 00:00:00 2001 From: Gabriel Fernandez Date: Fri, 5 Apr 2019 09:53:31 +0200 Subject: clk: stm32: Introduce clocks of STM32F769 board STM32F769 clocks are derived from STM32746 clocks. main differences are: - new source clock for SAI1 and SAI2 (HSI or HSE) - Add DFSDM & DSI clocks Signed-off-by: Gabriel Fernandez Signed-off-by: Stephen Boyd --- .../devicetree/bindings/clock/st,stm32-rcc.txt | 6 + drivers/clk/clk-stm32f4.c | 307 ++++++++++++++++++++- include/dt-bindings/clock/stm32fx-clock.h | 7 +- 3 files changed, 310 insertions(+), 10 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/clock/st,stm32-rcc.txt b/Documentation/devicetree/bindings/clock/st,stm32-rcc.txt index b240121d2ac9..cfa04b614d8a 100644 --- a/Documentation/devicetree/bindings/clock/st,stm32-rcc.txt +++ b/Documentation/devicetree/bindings/clock/st,stm32-rcc.txt @@ -11,6 +11,8 @@ Required properties: "st,stm32f42xx-rcc" "st,stm32f469-rcc" "st,stm32f746-rcc" + "st,stm32f769-rcc" + - reg: should be register base and length as documented in the datasheet - #reset-cells: 1, see below @@ -102,6 +104,10 @@ The secondary index is bound with the following magic numbers: 28 CLK_I2C3 29 CLK_I2C4 30 CLK_LPTIMER (LPTimer1 clock) + 31 CLK_PLL_SRC + 32 CLK_DFSDM1 + 33 CLK_ADFSDM1 + 34 CLK_F769_DSI ) Example: diff --git a/drivers/clk/clk-stm32f4.c b/drivers/clk/clk-stm32f4.c index cdaa567c8042..fdac33a9be2f 100644 --- a/drivers/clk/clk-stm32f4.c +++ b/drivers/clk/clk-stm32f4.c @@ -300,6 +300,85 @@ static const struct stm32f4_gate_data stm32f746_gates[] __initconst = { { STM32F4_RCC_APB2ENR, 26, "ltdc", "apb2_div" }, }; +static const struct stm32f4_gate_data stm32f769_gates[] __initconst = { + { STM32F4_RCC_AHB1ENR, 0, "gpioa", "ahb_div" }, + { STM32F4_RCC_AHB1ENR, 1, "gpiob", "ahb_div" }, + { STM32F4_RCC_AHB1ENR, 2, "gpioc", "ahb_div" }, + { STM32F4_RCC_AHB1ENR, 3, "gpiod", "ahb_div" }, + { STM32F4_RCC_AHB1ENR, 4, "gpioe", "ahb_div" }, + { STM32F4_RCC_AHB1ENR, 5, "gpiof", "ahb_div" }, + { STM32F4_RCC_AHB1ENR, 6, "gpiog", "ahb_div" }, + { STM32F4_RCC_AHB1ENR, 7, "gpioh", "ahb_div" }, + { STM32F4_RCC_AHB1ENR, 8, "gpioi", "ahb_div" }, + { STM32F4_RCC_AHB1ENR, 9, "gpioj", "ahb_div" }, + { STM32F4_RCC_AHB1ENR, 10, "gpiok", "ahb_div" }, + { STM32F4_RCC_AHB1ENR, 12, "crc", "ahb_div" }, + { STM32F4_RCC_AHB1ENR, 18, "bkpsra", "ahb_div" }, + { STM32F4_RCC_AHB1ENR, 20, "dtcmram", "ahb_div" }, + { STM32F4_RCC_AHB1ENR, 21, "dma1", "ahb_div" }, + { STM32F4_RCC_AHB1ENR, 22, "dma2", "ahb_div" }, + { STM32F4_RCC_AHB1ENR, 23, "dma2d", "ahb_div" }, + { STM32F4_RCC_AHB1ENR, 25, "ethmac", "ahb_div" }, + { STM32F4_RCC_AHB1ENR, 26, "ethmactx", "ahb_div" }, + { STM32F4_RCC_AHB1ENR, 27, "ethmacrx", "ahb_div" }, + { STM32F4_RCC_AHB1ENR, 28, "ethmacptp", "ahb_div" }, + { STM32F4_RCC_AHB1ENR, 29, "otghs", "ahb_div" }, + { STM32F4_RCC_AHB1ENR, 30, "otghsulpi", "ahb_div" }, + + { STM32F4_RCC_AHB2ENR, 0, "dcmi", "ahb_div" }, + { STM32F4_RCC_AHB2ENR, 1, "jpeg", "ahb_div" }, + { STM32F4_RCC_AHB2ENR, 4, "cryp", "ahb_div" }, + { STM32F4_RCC_AHB2ENR, 5, "hash", "ahb_div" }, + { STM32F4_RCC_AHB2ENR, 6, "rng", "pll48" }, + { STM32F4_RCC_AHB2ENR, 7, "otgfs", "pll48" }, + + { STM32F4_RCC_AHB3ENR, 0, "fmc", "ahb_div", + CLK_IGNORE_UNUSED }, + { STM32F4_RCC_AHB3ENR, 1, "qspi", "ahb_div", + CLK_IGNORE_UNUSED }, + + { STM32F4_RCC_APB1ENR, 0, "tim2", "apb1_mul" }, + { STM32F4_RCC_APB1ENR, 1, "tim3", "apb1_mul" }, + { STM32F4_RCC_APB1ENR, 2, "tim4", "apb1_mul" }, + { STM32F4_RCC_APB1ENR, 3, "tim5", "apb1_mul" }, + { STM32F4_RCC_APB1ENR, 4, "tim6", "apb1_mul" }, + { STM32F4_RCC_APB1ENR, 5, "tim7", "apb1_mul" }, + { STM32F4_RCC_APB1ENR, 6, "tim12", "apb1_mul" }, + { STM32F4_RCC_APB1ENR, 7, "tim13", "apb1_mul" }, + { STM32F4_RCC_APB1ENR, 8, "tim14", "apb1_mul" }, + { STM32F4_RCC_APB1ENR, 10, "rtcapb", "apb1_mul" }, + { STM32F4_RCC_APB1ENR, 11, "wwdg", "apb1_div" }, + { STM32F4_RCC_APB1ENR, 13, "can3", "apb1_div" }, + { STM32F4_RCC_APB1ENR, 14, "spi2", "apb1_div" }, + { STM32F4_RCC_APB1ENR, 15, "spi3", "apb1_div" }, + { STM32F4_RCC_APB1ENR, 16, "spdifrx", "apb1_div" }, + { STM32F4_RCC_APB1ENR, 25, "can1", "apb1_div" }, + { STM32F4_RCC_APB1ENR, 26, "can2", "apb1_div" }, + { STM32F4_RCC_APB1ENR, 27, "cec", "apb1_div" }, + { STM32F4_RCC_APB1ENR, 28, "pwr", "apb1_div" }, + { STM32F4_RCC_APB1ENR, 29, "dac", "apb1_div" }, + + { STM32F4_RCC_APB2ENR, 0, "tim1", "apb2_mul" }, + { STM32F4_RCC_APB2ENR, 1, "tim8", "apb2_mul" }, + { STM32F4_RCC_APB2ENR, 7, "sdmmc2", "sdmux2" }, + { STM32F4_RCC_APB2ENR, 8, "adc1", "apb2_div" }, + { STM32F4_RCC_APB2ENR, 9, "adc2", "apb2_div" }, + { STM32F4_RCC_APB2ENR, 10, "adc3", "apb2_div" }, + { STM32F4_RCC_APB2ENR, 11, "sdmmc1", "sdmux1" }, + { STM32F4_RCC_APB2ENR, 12, "spi1", "apb2_div" }, + { STM32F4_RCC_APB2ENR, 13, "spi4", "apb2_div" }, + { STM32F4_RCC_APB2ENR, 14, "syscfg", "apb2_div" }, + { STM32F4_RCC_APB2ENR, 16, "tim9", "apb2_mul" }, + { STM32F4_RCC_APB2ENR, 17, "tim10", "apb2_mul" }, + { STM32F4_RCC_APB2ENR, 18, "tim11", "apb2_mul" }, + { STM32F4_RCC_APB2ENR, 20, "spi5", "apb2_div" }, + { STM32F4_RCC_APB2ENR, 21, "spi6", "apb2_div" }, + { STM32F4_RCC_APB2ENR, 22, "sai1", "apb2_div" }, + { STM32F4_RCC_APB2ENR, 23, "sai2", "apb2_div" }, + { STM32F4_RCC_APB2ENR, 26, "ltdc", "apb2_div" }, + { STM32F4_RCC_APB2ENR, 30, "mdio", "apb2_div" }, +}; + /* * This bitmask tells us which bit offsets (0..192) on STM32F4[23]xxx * have gate bits associated with them. Its combined hweight is 71. @@ -318,6 +397,10 @@ static const u64 stm32f746_gate_map[MAX_GATE_MAP] = { 0x000000f17ef417ffull, 0x0000000000000003ull, 0x04f77f833e01c9ffull }; +static const u64 stm32f769_gate_map[MAX_GATE_MAP] = { 0x000000f37ef417ffull, + 0x0000000000000003ull, + 0x44F77F833E01EDFFull }; + static const u64 *stm32f4_gate_map; static struct clk_hw **clks; @@ -1048,6 +1131,10 @@ static const char *rtc_parents[4] = { "no-clock", "lse", "lsi", "hse-rtc" }; +static const char *pll_src = "pll-src"; + +static const char *pllsrc_parent[2] = { "hsi", NULL }; + static const char *dsi_parent[2] = { NULL, "pll-r" }; static const char *lcd_parent[1] = { "pllsai-r-div" }; @@ -1072,6 +1159,9 @@ static const char *uart_parents2[4] = { "apb1_div", "sys", "hsi", "lse" }; static const char *i2c_parents[4] = { "apb1_div", "sys", "hsi", "no-clock" }; +static const char * const dfsdm1_src[] = { "apb2_div", "sys" }; +static const char * const adsfdm1_parent[] = { "sai1_clk", "sai2_clk" }; + struct stm32_aux_clk { int idx; const char *name; @@ -1313,6 +1403,177 @@ static const struct stm32_aux_clk stm32f746_aux_clk[] = { }, }; +static const struct stm32_aux_clk stm32f769_aux_clk[] = { + { + CLK_LCD, "lcd-tft", lcd_parent, ARRAY_SIZE(lcd_parent), + NO_MUX, 0, 0, + STM32F4_RCC_APB2ENR, 26, + CLK_SET_RATE_PARENT + }, + { + CLK_I2S, "i2s", i2s_parents, ARRAY_SIZE(i2s_parents), + STM32F4_RCC_CFGR, 23, 1, + NO_GATE, 0, + CLK_SET_RATE_PARENT + }, + { + CLK_SAI1, "sai1_clk", sai_parents, ARRAY_SIZE(sai_parents), + STM32F4_RCC_DCKCFGR, 20, 3, + STM32F4_RCC_APB2ENR, 22, + CLK_SET_RATE_PARENT + }, + { + CLK_SAI2, "sai2_clk", sai_parents, ARRAY_SIZE(sai_parents), + STM32F4_RCC_DCKCFGR, 22, 3, + STM32F4_RCC_APB2ENR, 23, + CLK_SET_RATE_PARENT + }, + { + NO_IDX, "pll48", pll48_parents, ARRAY_SIZE(pll48_parents), + STM32F7_RCC_DCKCFGR2, 27, 1, + NO_GATE, 0, + 0 + }, + { + NO_IDX, "sdmux1", sdmux_parents, ARRAY_SIZE(sdmux_parents), + STM32F7_RCC_DCKCFGR2, 28, 1, + NO_GATE, 0, + 0 + }, + { + NO_IDX, "sdmux2", sdmux_parents, ARRAY_SIZE(sdmux_parents), + STM32F7_RCC_DCKCFGR2, 29, 1, + NO_GATE, 0, + 0 + }, + { + CLK_HDMI_CEC, "hdmi-cec", + hdmi_parents, ARRAY_SIZE(hdmi_parents), + STM32F7_RCC_DCKCFGR2, 26, 1, + NO_GATE, 0, + 0 + }, + { + CLK_SPDIF, "spdif-rx", + spdif_parent, ARRAY_SIZE(spdif_parent), + STM32F7_RCC_DCKCFGR2, 22, 3, + STM32F4_RCC_APB2ENR, 23, + CLK_SET_RATE_PARENT + }, + { + CLK_USART1, "usart1", + uart_parents1, ARRAY_SIZE(uart_parents1), + STM32F7_RCC_DCKCFGR2, 0, 3, + STM32F4_RCC_APB2ENR, 4, + CLK_SET_RATE_PARENT, + }, + { + CLK_USART2, "usart2", + uart_parents2, ARRAY_SIZE(uart_parents1), + STM32F7_RCC_DCKCFGR2, 2, 3, + STM32F4_RCC_APB1ENR, 17, + CLK_SET_RATE_PARENT, + }, + { + CLK_USART3, "usart3", + uart_parents2, ARRAY_SIZE(uart_parents1), + STM32F7_RCC_DCKCFGR2, 4, 3, + STM32F4_RCC_APB1ENR, 18, + CLK_SET_RATE_PARENT, + }, + { + CLK_UART4, "uart4", + uart_parents2, ARRAY_SIZE(uart_parents1), + STM32F7_RCC_DCKCFGR2, 6, 3, + STM32F4_RCC_APB1ENR, 19, + CLK_SET_RATE_PARENT, + }, + { + CLK_UART5, "uart5", + uart_parents2, ARRAY_SIZE(uart_parents1), + STM32F7_RCC_DCKCFGR2, 8, 3, + STM32F4_RCC_APB1ENR, 20, + CLK_SET_RATE_PARENT, + }, + { + CLK_USART6, "usart6", + uart_parents1, ARRAY_SIZE(uart_parents1), + STM32F7_RCC_DCKCFGR2, 10, 3, + STM32F4_RCC_APB2ENR, 5, + CLK_SET_RATE_PARENT, + }, + { + CLK_UART7, "uart7", + uart_parents2, ARRAY_SIZE(uart_parents1), + STM32F7_RCC_DCKCFGR2, 12, 3, + STM32F4_RCC_APB1ENR, 30, + CLK_SET_RATE_PARENT, + }, + { + CLK_UART8, "uart8", + uart_parents2, ARRAY_SIZE(uart_parents1), + STM32F7_RCC_DCKCFGR2, 14, 3, + STM32F4_RCC_APB1ENR, 31, + CLK_SET_RATE_PARENT, + }, + { + CLK_I2C1, "i2c1", + i2c_parents, ARRAY_SIZE(i2c_parents), + STM32F7_RCC_DCKCFGR2, 16, 3, + STM32F4_RCC_APB1ENR, 21, + CLK_SET_RATE_PARENT, + }, + { + CLK_I2C2, "i2c2", + i2c_parents, ARRAY_SIZE(i2c_parents), + STM32F7_RCC_DCKCFGR2, 18, 3, + STM32F4_RCC_APB1ENR, 22, + CLK_SET_RATE_PARENT, + }, + { + CLK_I2C3, "i2c3", + i2c_parents, ARRAY_SIZE(i2c_parents), + STM32F7_RCC_DCKCFGR2, 20, 3, + STM32F4_RCC_APB1ENR, 23, + CLK_SET_RATE_PARENT, + }, + { + CLK_I2C4, "i2c4", + i2c_parents, ARRAY_SIZE(i2c_parents), + STM32F7_RCC_DCKCFGR2, 22, 3, + STM32F4_RCC_APB1ENR, 24, + CLK_SET_RATE_PARENT, + }, + { + CLK_LPTIMER, "lptim1", + lptim_parent, ARRAY_SIZE(lptim_parent), + STM32F7_RCC_DCKCFGR2, 24, 3, + STM32F4_RCC_APB1ENR, 9, + CLK_SET_RATE_PARENT + }, + { + CLK_F769_DSI, "dsi", + dsi_parent, ARRAY_SIZE(dsi_parent), + STM32F7_RCC_DCKCFGR2, 0, 1, + STM32F4_RCC_APB2ENR, 27, + CLK_SET_RATE_PARENT + }, + { + CLK_DFSDM1, "dfsdm1", + dfsdm1_src, ARRAY_SIZE(dfsdm1_src), + STM32F4_RCC_DCKCFGR, 25, 1, + STM32F4_RCC_APB2ENR, 29, + CLK_SET_RATE_PARENT + }, + { + CLK_ADFSDM1, "adfsdm1", + adsfdm1_parent, ARRAY_SIZE(adsfdm1_parent), + STM32F4_RCC_DCKCFGR, 26, 1, + STM32F4_RCC_APB2ENR, 29, + CLK_SET_RATE_PARENT + }, +}; + static const struct stm32f4_clk_data stm32f429_clk_data = { .end_primary = END_PRIMARY_CLK, .gates_data = stm32f429_gates, @@ -1343,6 +1604,16 @@ static const struct stm32f4_clk_data stm32f746_clk_data = { .aux_clk_num = ARRAY_SIZE(stm32f746_aux_clk), }; +static const struct stm32f4_clk_data stm32f769_clk_data = { + .end_primary = END_PRIMARY_CLK_F7, + .gates_data = stm32f769_gates, + .gates_map = stm32f769_gate_map, + .gates_num = ARRAY_SIZE(stm32f769_gates), + .pll_data = stm32f469_pll, + .aux_clk = stm32f769_aux_clk, + .aux_clk_num = ARRAY_SIZE(stm32f769_aux_clk), +}; + static const struct of_device_id stm32f4_of_match[] = { { .compatible = "st,stm32f42xx-rcc", @@ -1356,6 +1627,10 @@ static const struct of_device_id stm32f4_of_match[] = { .compatible = "st,stm32f746-rcc", .data = &stm32f746_clk_data }, + { + .compatible = "st,stm32f769-rcc", + .data = &stm32f769_clk_data + }, {} }; @@ -1427,9 +1702,8 @@ static void __init stm32f4_rcc_init(struct device_node *np) int n; const struct of_device_id *match; const struct stm32f4_clk_data *data; - unsigned long pllcfgr; - const char *pllsrc; unsigned long pllm; + struct clk_hw *pll_src_hw; base = of_iomap(np, 0); if (!base) { @@ -1460,21 +1734,33 @@ static void __init stm32f4_rcc_init(struct device_node *np) hse_clk = of_clk_get_parent_name(np, 0); dsi_parent[0] = hse_clk; + pllsrc_parent[1] = hse_clk; i2s_in_clk = of_clk_get_parent_name(np, 1); i2s_parents[1] = i2s_in_clk; sai_parents[2] = i2s_in_clk; + if (of_device_is_compatible(np, "st,stm32f769-rcc")) { + clk_hw_register_gate(NULL, "dfsdm1_apb", "apb2_div", 0, + base + STM32F4_RCC_APB2ENR, 29, + CLK_IGNORE_UNUSED, &stm32f4_clk_lock); + dsi_parent[0] = pll_src; + sai_parents[3] = pll_src; + } + clks[CLK_HSI] = clk_hw_register_fixed_rate_with_accuracy(NULL, "hsi", NULL, 0, 16000000, 160000); - pllcfgr = readl(base + STM32F4_RCC_PLLCFGR); - pllsrc = pllcfgr & BIT(22) ? hse_clk : "hsi"; - pllm = pllcfgr & 0x3f; + pll_src_hw = clk_hw_register_mux(NULL, pll_src, pllsrc_parent, + ARRAY_SIZE(pllsrc_parent), 0, + base + STM32F4_RCC_PLLCFGR, 22, 1, 0, + &stm32f4_clk_lock); + + pllm = readl(base + STM32F4_RCC_PLLCFGR) & 0x3f; - clk_hw_register_fixed_factor(NULL, "vco_in", pllsrc, - 0, 1, pllm); + clk_hw_register_fixed_factor(NULL, "vco_in", pll_src, + 0, 1, pllm); stm32f4_rcc_register_pll("vco_in", &data->pll_data[0], &stm32f4_clk_lock); @@ -1612,12 +1898,16 @@ static void __init stm32f4_rcc_init(struct device_node *np) clks[aux_clk->idx] = hw; } - if (of_device_is_compatible(np, "st,stm32f746-rcc")) + if (of_device_is_compatible(np, "st,stm32f746-rcc")) { clk_hw_register_fixed_factor(NULL, "hsi_div488", "hsi", 0, 1, 488); + clks[CLK_PLL_SRC] = pll_src_hw; + } + of_clk_add_hw_provider(np, stm32f4_rcc_lookup_clk, NULL); + return; fail: kfree(clks); @@ -1626,3 +1916,4 @@ fail: CLK_OF_DECLARE_DRIVER(stm32f42xx_rcc, "st,stm32f42xx-rcc", stm32f4_rcc_init); CLK_OF_DECLARE_DRIVER(stm32f46xx_rcc, "st,stm32f469-rcc", stm32f4_rcc_init); CLK_OF_DECLARE_DRIVER(stm32f746_rcc, "st,stm32f746-rcc", stm32f4_rcc_init); +CLK_OF_DECLARE_DRIVER(stm32f769_rcc, "st,stm32f769-rcc", stm32f4_rcc_init); diff --git a/include/dt-bindings/clock/stm32fx-clock.h b/include/dt-bindings/clock/stm32fx-clock.h index 58d8b515be55..7d34e297049c 100644 --- a/include/dt-bindings/clock/stm32fx-clock.h +++ b/include/dt-bindings/clock/stm32fx-clock.h @@ -54,7 +54,10 @@ #define CLK_I2C3 28 #define CLK_I2C4 29 #define CLK_LPTIMER 30 - -#define END_PRIMARY_CLK_F7 31 +#define CLK_PLL_SRC 31 +#define CLK_DFSDM1 32 +#define CLK_ADFSDM1 33 +#define CLK_F769_DSI 34 +#define END_PRIMARY_CLK_F7 35 #endif -- cgit v1.2.3 From 6b903f9bdd98093a2c1ea79df07e86decfda3b04 Mon Sep 17 00:00:00 2001 From: Paul Cercueil Date: Sat, 20 Apr 2019 12:45:51 +0200 Subject: ASoC: doc: simple-card: Add pin-switches property The simple-audio-card,pin-switches property can contain the list of widget names for which pin switches must be created. Signed-off-by: Paul Cercueil Signed-off-by: Mark Brown --- Documentation/devicetree/bindings/sound/simple-card.txt | 2 ++ 1 file changed, 2 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/sound/simple-card.txt b/Documentation/devicetree/bindings/sound/simple-card.txt index 4629c8f8a6b6..79954cd6e37b 100644 --- a/Documentation/devicetree/bindings/sound/simple-card.txt +++ b/Documentation/devicetree/bindings/sound/simple-card.txt @@ -24,6 +24,8 @@ Optional properties: a microphone is attached. - simple-audio-card,aux-devs : List of phandles pointing to auxiliary devices, such as amplifiers, to be added to the sound card. +- simple-audio-card,pin-switches : List of strings containing the widget names for + which pin switches must be created. Optional subnodes: -- cgit v1.2.3 From ea2b23b89579d9765dc9b45d7bdbe7e4da37fa0f Mon Sep 17 00:00:00 2001 From: William Breathitt Gray Date: Tue, 2 Apr 2019 15:30:37 +0900 Subject: counter: Documentation: Add Generic Counter sysfs documentation This patch adds standard documentation for the userspace sysfs attributes of the Generic Counter interface. Reviewed-by: Jonathan Cameron Signed-off-by: William Breathitt Gray Signed-off-by: Greg Kroah-Hartman --- Documentation/ABI/testing/sysfs-bus-counter | 230 ++++++++++++++++++++++++++++ MAINTAINERS | 1 + 2 files changed, 231 insertions(+) create mode 100644 Documentation/ABI/testing/sysfs-bus-counter (limited to 'Documentation') diff --git a/Documentation/ABI/testing/sysfs-bus-counter b/Documentation/ABI/testing/sysfs-bus-counter new file mode 100644 index 000000000000..566bd99fe0a5 --- /dev/null +++ b/Documentation/ABI/testing/sysfs-bus-counter @@ -0,0 +1,230 @@ +What: /sys/bus/counter/devices/counterX/countY/count +KernelVersion: 5.2 +Contact: linux-iio@vger.kernel.org +Description: + Count data of Count Y represented as a string. + +What: /sys/bus/counter/devices/counterX/countY/ceiling +KernelVersion: 5.2 +Contact: linux-iio@vger.kernel.org +Description: + Count value ceiling for Count Y. This is the upper limit for the + respective counter. + +What: /sys/bus/counter/devices/counterX/countY/floor +KernelVersion: 5.2 +Contact: linux-iio@vger.kernel.org +Description: + Count value floor for Count Y. This is the lower limit for the + respective counter. + +What: /sys/bus/counter/devices/counterX/countY/count_mode +KernelVersion: 5.2 +Contact: linux-iio@vger.kernel.org +Description: + Count mode for channel Y. The ceiling and floor values for + Count Y are used by the count mode where required. The following + count modes are available: + + normal: + Counting is continuous in either direction. + + range limit: + An upper or lower limit is set, mimicking limit switches + in the mechanical counterpart. The upper limit is set to + the Count Y ceiling value, while the lower limit is set + to the Count Y floor value. The counter freezes at + count = ceiling when counting up, and at count = floor + when counting down. At either of these limits, the + counting is resumed only when the count direction is + reversed. + + non-recycle: + The counter is disabled whenever a counter overflow or + underflow takes place. The counter is re-enabled when a + new count value is loaded to the counter via a preset + operation or direct write. + + modulo-n: + A count value boundary is set between the Count Y floor + value and the Count Y ceiling value. The counter is + reset to the Count Y floor value at count = ceiling when + counting up, while the counter is set to the Count Y + ceiling value at count = floor when counting down; the + counter does not freeze at the boundary points, but + counts continuously throughout. + +What: /sys/bus/counter/devices/counterX/countY/count_mode_available +What: /sys/bus/counter/devices/counterX/countY/error_noise_available +What: /sys/bus/counter/devices/counterX/countY/function_available +What: /sys/bus/counter/devices/counterX/countY/signalZ_action_available +KernelVersion: 5.2 +Contact: linux-iio@vger.kernel.org +Description: + Discrete set of available values for the respective Count Y + configuration are listed in this file. Values are delimited by + newline characters. + +What: /sys/bus/counter/devices/counterX/countY/direction +KernelVersion: 5.2 +Contact: linux-iio@vger.kernel.org +Description: + Read-only attribute that indicates the count direction of Count + Y. Two count directions are available: forward and backward. + + Some counter devices are able to determine the direction of + their counting. For example, quadrature encoding counters can + determine the direction of movement by evaluating the leading + phase of the respective A and B quadrature encoding signals. + This attribute exposes such count directions. + +What: /sys/bus/counter/devices/counterX/countY/enable +KernelVersion: 5.2 +Contact: linux-iio@vger.kernel.org +Description: + Whether channel Y counter is enabled. Valid attribute values are + boolean. + + This attribute is intended to serve as a pause/unpause mechanism + for Count Y. Suppose a counter device is used to count the total + movement of a conveyor belt: this attribute allows an operator + to temporarily pause the counter, service the conveyor belt, + and then finally unpause the counter to continue where it had + left off. + +What: /sys/bus/counter/devices/counterX/countY/error_noise +KernelVersion: 5.2 +Contact: linux-iio@vger.kernel.org +Description: + Read-only attribute that indicates whether excessive noise is + present at the channel Y counter inputs. + +What: /sys/bus/counter/devices/counterX/countY/function +KernelVersion: 5.2 +Contact: linux-iio@vger.kernel.org +Description: + Count function mode of Count Y; count function evaluation is + triggered by conditions specified by the Count Y signalZ_action + attributes. The following count functions are available: + + increase: + Accumulated count is incremented. + + decrease: + Accumulated count is decremented. + + pulse-direction: + Rising edges on signal A updates the respective count. + The input level of signal B determines direction. + + quadrature x1 a: + If direction is forward, rising edges on quadrature pair + signal A updates the respective count; if the direction + is backward, falling edges on quadrature pair signal A + updates the respective count. Quadrature encoding + determines the direction. + + quadrature x1 b: + If direction is forward, rising edges on quadrature pair + signal B updates the respective count; if the direction + is backward, falling edges on quadrature pair signal B + updates the respective count. Quadrature encoding + determines the direction. + + quadrature x2 a: + Any state transition on quadrature pair signal A updates + the respective count. Quadrature encoding determines the + direction. + + quadrature x2 b: + Any state transition on quadrature pair signal B updates + the respective count. Quadrature encoding determines the + direction. + + quadrature x4: + Any state transition on either quadrature pair signals + updates the respective count. Quadrature encoding + determines the direction. + +What: /sys/bus/counter/devices/counterX/countY/name +KernelVersion: 5.2 +Contact: linux-iio@vger.kernel.org +Description: + Read-only attribute that indicates the device-specific name of + Count Y. If possible, this should match the name of the + respective channel as it appears in the device datasheet. + +What: /sys/bus/counter/devices/counterX/countY/preset +KernelVersion: 5.2 +Contact: linux-iio@vger.kernel.org +Description: + If the counter device supports preset registers -- registers + used to load counter channels to a set count upon device-defined + preset operation trigger events -- the preset count for channel + Y is provided by this attribute. + +What: /sys/bus/counter/devices/counterX/countY/preset_enable +KernelVersion: 5.2 +Contact: linux-iio@vger.kernel.org +Description: + Whether channel Y counter preset operation is enabled. Valid + attribute values are boolean. + +What: /sys/bus/counter/devices/counterX/countY/signalZ_action +KernelVersion: 5.2 +Contact: linux-iio@vger.kernel.org +Description: + Action mode of Count Y for Signal Z. This attribute indicates + the condition of Signal Z that triggers the count function + evaluation for Count Y. The following action modes are + available: + + none: + Signal does not trigger the count function. In + Pulse-Direction count function mode, this Signal is + evaluated as Direction. + + rising edge: + Low state transitions to high state. + + falling edge: + High state transitions to low state. + + both edges: + Any state transition. + +What: /sys/bus/counter/devices/counterX/name +KernelVersion: 5.2 +Contact: linux-iio@vger.kernel.org +Description: + Read-only attribute that indicates the device-specific name of + the Counter. This should match the name of the device as it + appears in its respective datasheet. + +What: /sys/bus/counter/devices/counterX/num_counts +KernelVersion: 5.2 +Contact: linux-iio@vger.kernel.org +Description: + Read-only attribute that indicates the total number of Counts + belonging to the Counter. + +What: /sys/bus/counter/devices/counterX/num_signals +KernelVersion: 5.2 +Contact: linux-iio@vger.kernel.org +Description: + Read-only attribute that indicates the total number of Signals + belonging to the Counter. + +What: /sys/bus/counter/devices/counterX/signalY/signal +KernelVersion: 5.2 +Contact: linux-iio@vger.kernel.org +Description: + Signal data of Signal Y represented as a string. + +What: /sys/bus/counter/devices/counterX/signalY/name +KernelVersion: 5.2 +Contact: linux-iio@vger.kernel.org +Description: + Read-only attribute that indicates the device-specific name of + Signal Y. If possible, this should match the name of the + respective signal as it appears in the device datasheet. diff --git a/MAINTAINERS b/MAINTAINERS index 5038b36867e9..b6028ebaf1b4 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -4058,6 +4058,7 @@ COUNTER SUBSYSTEM M: William Breathitt Gray L: linux-iio@vger.kernel.org S: Maintained +F: Documentation/ABI/testing/sysfs-bus-counter* F: drivers/counter/ F: include/linux/counter.h F: include/linux/counter_enum.h -- cgit v1.2.3 From 09e7d4ed89912bb97ff339ca2ee78b6f3e0c2154 Mon Sep 17 00:00:00 2001 From: William Breathitt Gray Date: Tue, 2 Apr 2019 15:30:38 +0900 Subject: docs: Add Generic Counter interface documentation This patch adds high-level documentation about the Generic Counter interface. Reviewed-by: Jonathan Cameron Signed-off-by: William Breathitt Gray Signed-off-by: Greg Kroah-Hartman --- Documentation/driver-api/generic-counter.rst | 342 +++++++++++++++++++++++++++ Documentation/driver-api/index.rst | 1 + MAINTAINERS | 1 + 3 files changed, 344 insertions(+) create mode 100644 Documentation/driver-api/generic-counter.rst (limited to 'Documentation') diff --git a/Documentation/driver-api/generic-counter.rst b/Documentation/driver-api/generic-counter.rst new file mode 100644 index 000000000000..f51db893f595 --- /dev/null +++ b/Documentation/driver-api/generic-counter.rst @@ -0,0 +1,342 @@ +.. SPDX-License-Identifier: GPL-2.0 + +========================= +Generic Counter Interface +========================= + +Introduction +============ + +Counter devices are prevalent within a diverse spectrum of industries. +The ubiquitous presence of these devices necessitates a common interface +and standard of interaction and exposure. This driver API attempts to +resolve the issue of duplicate code found among existing counter device +drivers by introducing a generic counter interface for consumption. The +Generic Counter interface enables drivers to support and expose a common +set of components and functionality present in counter devices. + +Theory +====== + +Counter devices can vary greatly in design, but regardless of whether +some devices are quadrature encoder counters or tally counters, all +counter devices consist of a core set of components. This core set of +components, shared by all counter devices, is what forms the essence of +the Generic Counter interface. + +There are three core components to a counter: + +* Count: + Count data for a set of Signals. + +* Signal: + Input data that is evaluated by the counter to determine the count + data. + +* Synapse: + The association of a Signal with a respective Count. + +COUNT +----- +A Count represents the count data for a set of Signals. The Generic +Counter interface provides the following available count data types: + +* COUNT_POSITION: + Unsigned integer value representing position. + +A Count has a count function mode which represents the update behavior +for the count data. The Generic Counter interface provides the following +available count function modes: + +* Increase: + Accumulated count is incremented. + +* Decrease: + Accumulated count is decremented. + +* Pulse-Direction: + Rising edges on signal A updates the respective count. The input level + of signal B determines direction. + +* Quadrature: + A pair of quadrature encoding signals are evaluated to determine + position and direction. The following Quadrature modes are available: + + - x1 A: + If direction is forward, rising edges on quadrature pair signal A + updates the respective count; if the direction is backward, falling + edges on quadrature pair signal A updates the respective count. + Quadrature encoding determines the direction. + + - x1 B: + If direction is forward, rising edges on quadrature pair signal B + updates the respective count; if the direction is backward, falling + edges on quadrature pair signal B updates the respective count. + Quadrature encoding determines the direction. + + - x2 A: + Any state transition on quadrature pair signal A updates the + respective count. Quadrature encoding determines the direction. + + - x2 B: + Any state transition on quadrature pair signal B updates the + respective count. Quadrature encoding determines the direction. + + - x4: + Any state transition on either quadrature pair signals updates the + respective count. Quadrature encoding determines the direction. + +A Count has a set of one or more associated Signals. + +SIGNAL +------ +A Signal represents a counter input data; this is the input data that is +evaluated by the counter to determine the count data; e.g. a quadrature +signal output line of a rotary encoder. Not all counter devices provide +user access to the Signal data. + +The Generic Counter interface provides the following available signal +data types for when the Signal data is available for user access: + +* SIGNAL_LEVEL: + Signal line state level. The following states are possible: + + - SIGNAL_LEVEL_LOW: + Signal line is in a low state. + + - SIGNAL_LEVEL_HIGH: + Signal line is in a high state. + +A Signal may be associated with one or more Counts. + +SYNAPSE +------- +A Synapse represents the association of a Signal with a respective +Count. Signal data affects respective Count data, and the Synapse +represents this relationship. + +The Synapse action mode specifies the Signal data condition which +triggers the respective Count's count function evaluation to update the +count data. The Generic Counter interface provides the following +available action modes: + +* None: + Signal does not trigger the count function. In Pulse-Direction count + function mode, this Signal is evaluated as Direction. + +* Rising Edge: + Low state transitions to high state. + +* Falling Edge: + High state transitions to low state. + +* Both Edges: + Any state transition. + +A counter is defined as a set of input signals associated with count +data that are generated by the evaluation of the state of the associated +input signals as defined by the respective count functions. Within the +context of the Generic Counter interface, a counter consists of Counts +each associated with a set of Signals, whose respective Synapse +instances represent the count function update conditions for the +associated Counts. + +Paradigm +======== + +The most basic counter device may be expressed as a single Count +associated with a single Signal via a single Synapse. Take for example +a counter device which simply accumulates a count of rising edges on a +source input line:: + + Count Synapse Signal + ----- ------- ------ + +---------------------+ + | Data: Count | Rising Edge ________ + | Function: Increase | <------------- / Source \ + | | ____________ + +---------------------+ + +In this example, the Signal is a source input line with a pulsing +voltage, while the Count is a persistent count value which is repeatedly +incremented. The Signal is associated with the respective Count via a +Synapse. The increase function is triggered by the Signal data condition +specified by the Synapse -- in this case a rising edge condition on the +voltage input line. In summary, the counter device existence and +behavior is aptly represented by respective Count, Signal, and Synapse +components: a rising edge condition triggers an increase function on an +accumulating count datum. + +A counter device is not limited to a single Signal; in fact, in theory +many Signals may be associated with even a single Count. For example, a +quadrature encoder counter device can keep track of position based on +the states of two input lines:: + + Count Synapse Signal + ----- ------- ------ + +-------------------------+ + | Data: Position | Both Edges ___ + | Function: Quadrature x4 | <------------ / A \ + | | _______ + | | + | | Both Edges ___ + | | <------------ / B \ + | | _______ + +-------------------------+ + +In this example, two Signals (quadrature encoder lines A and B) are +associated with a single Count: a rising or falling edge on either A or +B triggers the "Quadrature x4" function which determines the direction +of movement and updates the respective position data. The "Quadrature +x4" function is likely implemented in the hardware of the quadrature +encoder counter device; the Count, Signals, and Synapses simply +represent this hardware behavior and functionality. + +Signals associated with the same Count can have differing Synapse action +mode conditions. For example, a quadrature encoder counter device +operating in a non-quadrature Pulse-Direction mode could have one input +line dedicated for movement and a second input line dedicated for +direction:: + + Count Synapse Signal + ----- ------- ------ + +---------------------------+ + | Data: Position | Rising Edge ___ + | Function: Pulse-Direction | <------------- / A \ (Movement) + | | _______ + | | + | | None ___ + | | <------------- / B \ (Direction) + | | _______ + +---------------------------+ + +Only Signal A triggers the "Pulse-Direction" update function, but the +instantaneous state of Signal B is still required in order to know the +direction so that the position data may be properly updated. Ultimately, +both Signals are associated with the same Count via two respective +Synapses, but only one Synapse has an active action mode condition which +triggers the respective count function while the other is left with a +"None" condition action mode to indicate its respective Signal's +availability for state evaluation despite its non-triggering mode. + +Keep in mind that the Signal, Synapse, and Count are abstract +representations which do not need to be closely married to their +respective physical sources. This allows the user of a counter to +divorce themselves from the nuances of physical components (such as +whether an input line is differential or single-ended) and instead focus +on the core idea of what the data and process represent (e.g. position +as interpreted from quadrature encoding data). + +Userspace Interface +=================== + +Several sysfs attributes are generated by the Generic Counter interface, +and reside under the /sys/bus/counter/devices/counterX directory, where +counterX refers to the respective counter device. Please see +Documentation/ABI/testing/sys-bus-counter-generic-sysfs for detailed +information on each Generic Counter interface sysfs attribute. + +Through these sysfs attributes, programs and scripts may interact with +the Generic Counter paradigm Counts, Signals, and Synapses of respective +counter devices. + +Driver API +========== + +Driver authors may utilize the Generic Counter interface in their code +by including the include/linux/counter.h header file. This header file +provides several core data structures, function prototypes, and macros +for defining a counter device. + +.. kernel-doc:: include/linux/counter.h + :internal: + +.. kernel-doc:: drivers/counter/generic-counter.c + :export: + +Implementation +============== + +To support a counter device, a driver must first allocate the available +Counter Signals via counter_signal structures. These Signals should +be stored as an array and set to the signals array member of an +allocated counter_device structure before the Counter is registered to +the system. + +Counter Counts may be allocated via counter_count structures, and +respective Counter Signal associations (Synapses) made via +counter_synapse structures. Associated counter_synapse structures are +stored as an array and set to the the synapses array member of the +respective counter_count structure. These counter_count structures are +set to the counts array member of an allocated counter_device structure +before the Counter is registered to the system. + +Driver callbacks should be provided to the counter_device structure via +a constant counter_ops structure in order to communicate with the +device: to read and write various Signals and Counts, and to set and get +the "action mode" and "function mode" for various Synapses and Counts +respectively. + +A defined counter_device structure may be registered to the system by +passing it to the counter_register function, and unregistered by passing +it to the counter_unregister function. Similarly, the +devm_counter_register and devm_counter_unregister functions may be used +if device memory-managed registration is desired. + +Extension sysfs attributes can be created for auxiliary functionality +and data by passing in defined counter_device_ext, counter_count_ext, +and counter_signal_ext structures. In these cases, the +counter_device_ext structure is used for global configuration of the +respective Counter device, while the counter_count_ext and +counter_signal_ext structures allow for auxiliary exposure and +configuration of a specific Count or Signal respectively. + +Architecture +============ + +When the Generic Counter interface counter module is loaded, the +counter_init function is called which registers a bus_type named +"counter" to the system. Subsequently, when the module is unloaded, the +counter_exit function is called which unregisters the bus_type named +"counter" from the system. + +Counter devices are registered to the system via the counter_register +function, and later removed via the counter_unregister function. The +counter_register function establishes a unique ID for the Counter +device and creates a respective sysfs directory, where X is the +mentioned unique ID: + + /sys/bus/counter/devices/counterX + +Sysfs attributes are created within the counterX directory to expose +functionality, configurations, and data relating to the Counts, Signals, +and Synapses of the Counter device, as well as options and information +for the Counter device itself. + +Each Signal has a directory created to house its relevant sysfs +attributes, where Y is the unique ID of the respective Signal: + + /sys/bus/counter/devices/counterX/signalY + +Similarly, each Count has a directory created to house its relevant +sysfs attributes, where Y is the unique ID of the respective Count: + + /sys/bus/counter/devices/counterX/countY + +For a more detailed breakdown of the available Generic Counter interface +sysfs attributes, please refer to the +Documentation/ABI/testing/sys-bus-counter file. + +The Signals and Counts associated with the Counter device are registered +to the system as well by the counter_register function. The +signal_read/signal_write driver callbacks are associated with their +respective Signal attributes, while the count_read/count_write and +function_get/function_set driver callbacks are associated with their +respective Count attributes; similarly, the same is true for the +action_get/action_set driver callbacks and their respective Synapse +attributes. If a driver callback is left undefined, then the respective +read/write permission is left disabled for the relevant attributes. + +Similarly, extension sysfs attributes are created for the defined +counter_device_ext, counter_count_ext, and counter_signal_ext +structures that are passed in. diff --git a/Documentation/driver-api/index.rst b/Documentation/driver-api/index.rst index c0b600ed9961..201247b7c1e8 100644 --- a/Documentation/driver-api/index.rst +++ b/Documentation/driver-api/index.rst @@ -56,6 +56,7 @@ available subsections can be seen below. slimbus soundwire/index fpga/index + generic-counter .. only:: subproject and html diff --git a/MAINTAINERS b/MAINTAINERS index b6028ebaf1b4..24fb5ba6a335 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -4059,6 +4059,7 @@ M: William Breathitt Gray L: linux-iio@vger.kernel.org S: Maintained F: Documentation/ABI/testing/sysfs-bus-counter* +F: Documentation/driver-api/generic-counter.rst F: drivers/counter/ F: include/linux/counter.h F: include/linux/counter_enum.h -- cgit v1.2.3 From 7e798ef90c5f7bf934b8a720eeafd0226c5394e7 Mon Sep 17 00:00:00 2001 From: William Breathitt Gray Date: Tue, 2 Apr 2019 15:30:41 +0900 Subject: counter: 104-quad-8: Documentation: Add Generic Counter sysfs documentation This patch adds standard documentation for the Generic Counter interface userspace sysfs attributes of the 104-QUAD-8 driver. Acked-by: Jonathan Cameron Signed-off-by: William Breathitt Gray Signed-off-by: Greg Kroah-Hartman --- .../ABI/testing/sysfs-bus-counter-104-quad-8 | 36 ++++++++++++++++++++++ MAINTAINERS | 1 + 2 files changed, 37 insertions(+) create mode 100644 Documentation/ABI/testing/sysfs-bus-counter-104-quad-8 (limited to 'Documentation') diff --git a/Documentation/ABI/testing/sysfs-bus-counter-104-quad-8 b/Documentation/ABI/testing/sysfs-bus-counter-104-quad-8 new file mode 100644 index 000000000000..46b1f33b2fce --- /dev/null +++ b/Documentation/ABI/testing/sysfs-bus-counter-104-quad-8 @@ -0,0 +1,36 @@ +What: /sys/bus/counter/devices/counterX/signalY/index_polarity +KernelVersion: 5.2 +Contact: linux-iio@vger.kernel.org +Description: + Active level of index input Signal Y; irrelevant in + non-synchronous load mode. + +What: /sys/bus/counter/devices/counterX/signalY/index_polarity_available +What: /sys/bus/counter/devices/counterX/signalY/synchronous_mode_available +KernelVersion: 5.2 +Contact: linux-iio@vger.kernel.org +Description: + Discrete set of available values for the respective Signal Y + configuration are listed in this file. + +What: /sys/bus/counter/devices/counterX/signalY/synchronous_mode +KernelVersion: 5.2 +Contact: linux-iio@vger.kernel.org +Description: + Configure the counter associated with Signal Y for + non-synchronous or synchronous load mode. Synchronous load mode + cannot be selected in non-quadrature (Pulse-Direction) clock + mode. + + non-synchronous: + A logic low level is the active level at this index + input. The index function (as enabled via preset_enable) + is performed directly on the active level of the index + input. + + synchronous: + Intended for interfacing with encoder Index output in + quadrature clock mode. The active level is configured + via index_polarity. The index function (as enabled via + preset_enable) is performed synchronously with the + quadrature clock on the active level of the index input. diff --git a/MAINTAINERS b/MAINTAINERS index 5b01a0ce0c6c..43a9cebb2c19 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -272,6 +272,7 @@ ACCES 104-QUAD-8 DRIVER M: William Breathitt Gray L: linux-iio@vger.kernel.org S: Maintained +F: Documentation/ABI/testing/sysfs-bus-counter-104-quad-8 F: Documentation/ABI/testing/sysfs-bus-iio-counter-104-quad-8 F: drivers/counter/104-quad-8.c -- cgit v1.2.3 From ec63e2a4897075e427c121d863bd89c44578094f Mon Sep 17 00:00:00 2001 From: Benjamin Gaignard Date: Tue, 2 Apr 2019 15:30:43 +0900 Subject: dt-bindings: counter: Document stm32 quadrature encoder Add bindings for STM32 Timer quadrature encoder. It is a sub-node of STM32 Timer which implement the quadratic encoder part of the hardware. Cc: Mark Rutland Signed-off-by: Benjamin Gaignard Acked-by: Rob Herring Signed-off-by: William Breathitt Gray Signed-off-by: Greg Kroah-Hartman --- .../bindings/counter/stm32-timer-cnt.txt | 31 ++++++++++++++++++++++ .../devicetree/bindings/mfd/stm32-timers.txt | 7 +++++ 2 files changed, 38 insertions(+) create mode 100644 Documentation/devicetree/bindings/counter/stm32-timer-cnt.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/counter/stm32-timer-cnt.txt b/Documentation/devicetree/bindings/counter/stm32-timer-cnt.txt new file mode 100644 index 000000000000..c52fcdd4bf6c --- /dev/null +++ b/Documentation/devicetree/bindings/counter/stm32-timer-cnt.txt @@ -0,0 +1,31 @@ +STMicroelectronics STM32 Timer quadrature encoder + +STM32 Timer provides quadrature encoder to detect +angular position and direction of rotary elements, +from IN1 and IN2 input signals. + +Must be a sub-node of an STM32 Timer device tree node. +See ../mfd/stm32-timers.txt for details about the parent node. + +Required properties: +- compatible: Must be "st,stm32-timer-counter". +- pinctrl-names: Set to "default". +- pinctrl-0: List of phandles pointing to pin configuration nodes, + to set CH1/CH2 pins in mode of operation for STM32 + Timer input on external pin. + +Example: + timers@40010000 { + #address-cells = <1>; + #size-cells = <0>; + compatible = "st,stm32-timers"; + reg = <0x40010000 0x400>; + clocks = <&rcc 0 160>; + clock-names = "int"; + + counter { + compatible = "st,stm32-timer-counter"; + pinctrl-names = "default"; + pinctrl-0 = <&tim1_in_pins>; + }; + }; diff --git a/Documentation/devicetree/bindings/mfd/stm32-timers.txt b/Documentation/devicetree/bindings/mfd/stm32-timers.txt index 0e900b52e895..15c3b87f51d9 100644 --- a/Documentation/devicetree/bindings/mfd/stm32-timers.txt +++ b/Documentation/devicetree/bindings/mfd/stm32-timers.txt @@ -28,6 +28,7 @@ Optional parameters: Optional subnodes: - pwm: See ../pwm/pwm-stm32.txt - timer: See ../iio/timer/stm32-timer-trigger.txt +- counter: See ../counter/stm32-timer-cnt.txt Example: timers@40010000 { @@ -48,6 +49,12 @@ Example: compatible = "st,stm32-timer-trigger"; reg = <0>; }; + + counter { + compatible = "st,stm32-timer-counter"; + pinctrl-names = "default"; + pinctrl-0 = <&tim1_in_pins>; + }; }; Example with all dmas: -- cgit v1.2.3 From 7657b2c123deec38ce3091cbda976b2bfb8ff45a Mon Sep 17 00:00:00 2001 From: Fabrice Gasnier Date: Tue, 2 Apr 2019 15:30:45 +0900 Subject: dt-bindings: counter: Adjust dt-bindings for STM32 lptimer move The STM32 LP Timer counter driver now resides under the Counter subsystem. This patch adjusts dt-bindings to account for the STM32 lptimer driver move. Cc: Mark Rutland Signed-off-by: Fabrice Gasnier Acked-by: Rob Herring Signed-off-by: William Breathitt Gray Signed-off-by: Greg Kroah-Hartman --- .../bindings/counter/stm32-lptimer-cnt.txt | 29 ++++++++++++++++++++++ .../bindings/iio/counter/stm32-lptimer-cnt.txt | 29 ---------------------- .../devicetree/bindings/mfd/stm32-lptimer.txt | 2 +- 3 files changed, 30 insertions(+), 30 deletions(-) create mode 100644 Documentation/devicetree/bindings/counter/stm32-lptimer-cnt.txt delete mode 100644 Documentation/devicetree/bindings/iio/counter/stm32-lptimer-cnt.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/counter/stm32-lptimer-cnt.txt b/Documentation/devicetree/bindings/counter/stm32-lptimer-cnt.txt new file mode 100644 index 000000000000..e90bc47f752a --- /dev/null +++ b/Documentation/devicetree/bindings/counter/stm32-lptimer-cnt.txt @@ -0,0 +1,29 @@ +STMicroelectronics STM32 Low-Power Timer quadrature encoder and counter + +STM32 Low-Power Timer provides several counter modes. It can be used as: +- quadrature encoder to detect angular position and direction of rotary + elements, from IN1 and IN2 input signals. +- simple counter from IN1 input signal. + +Must be a sub-node of an STM32 Low-Power Timer device tree node. +See ../mfd/stm32-lptimer.txt for details about the parent node. + +Required properties: +- compatible: Must be "st,stm32-lptimer-counter". +- pinctrl-names: Set to "default". An additional "sleep" state can be + defined to set pins in sleep state. +- pinctrl-n: List of phandles pointing to pin configuration nodes, + to set IN1/IN2 pins in mode of operation for Low-Power + Timer input on external pin. + +Example: + timer@40002400 { + compatible = "st,stm32-lptimer"; + ... + counter { + compatible = "st,stm32-lptimer-counter"; + pinctrl-names = "default", "sleep"; + pinctrl-0 = <&lptim1_in_pins>; + pinctrl-1 = <&lptim1_sleep_in_pins>; + }; + }; diff --git a/Documentation/devicetree/bindings/iio/counter/stm32-lptimer-cnt.txt b/Documentation/devicetree/bindings/iio/counter/stm32-lptimer-cnt.txt deleted file mode 100644 index e90bc47f752a..000000000000 --- a/Documentation/devicetree/bindings/iio/counter/stm32-lptimer-cnt.txt +++ /dev/null @@ -1,29 +0,0 @@ -STMicroelectronics STM32 Low-Power Timer quadrature encoder and counter - -STM32 Low-Power Timer provides several counter modes. It can be used as: -- quadrature encoder to detect angular position and direction of rotary - elements, from IN1 and IN2 input signals. -- simple counter from IN1 input signal. - -Must be a sub-node of an STM32 Low-Power Timer device tree node. -See ../mfd/stm32-lptimer.txt for details about the parent node. - -Required properties: -- compatible: Must be "st,stm32-lptimer-counter". -- pinctrl-names: Set to "default". An additional "sleep" state can be - defined to set pins in sleep state. -- pinctrl-n: List of phandles pointing to pin configuration nodes, - to set IN1/IN2 pins in mode of operation for Low-Power - Timer input on external pin. - -Example: - timer@40002400 { - compatible = "st,stm32-lptimer"; - ... - counter { - compatible = "st,stm32-lptimer-counter"; - pinctrl-names = "default", "sleep"; - pinctrl-0 = <&lptim1_in_pins>; - pinctrl-1 = <&lptim1_sleep_in_pins>; - }; - }; diff --git a/Documentation/devicetree/bindings/mfd/stm32-lptimer.txt b/Documentation/devicetree/bindings/mfd/stm32-lptimer.txt index 2a9ff29db9c9..fb54e4dad5b3 100644 --- a/Documentation/devicetree/bindings/mfd/stm32-lptimer.txt +++ b/Documentation/devicetree/bindings/mfd/stm32-lptimer.txt @@ -16,7 +16,7 @@ Required properties: Optional subnodes: - pwm: See ../pwm/pwm-stm32-lp.txt -- counter: See ../iio/timer/stm32-lptimer-cnt.txt +- counter: See ../counter/stm32-lptimer-cnt.txt - trigger: See ../iio/timer/stm32-lptimer-trigger.txt Example: -- cgit v1.2.3 From 4bb00e934daf6452f642e2913379f88fae2fb9f1 Mon Sep 17 00:00:00 2001 From: William Breathitt Gray Date: Tue, 2 Apr 2019 15:30:46 +0900 Subject: iio: counter: Add deprecation markings for IIO Counter attributes The IIO counter subdirectory is now superceded by the Counter subsystem. This patch adds deprecation warnings to the documentation of the relevant IIO Counter sysfs attributes. Acked-by: Jonathan Cameron Signed-off-by: William Breathitt Gray Signed-off-by: Greg Kroah-Hartman --- Documentation/ABI/testing/sysfs-bus-iio | 8 ++++++++ .../ABI/testing/sysfs-bus-iio-counter-104-quad-8 | 16 ++++++++++++++++ 2 files changed, 24 insertions(+) (limited to 'Documentation') diff --git a/Documentation/ABI/testing/sysfs-bus-iio b/Documentation/ABI/testing/sysfs-bus-iio index 864f8efd12e5..6aef7dbbde44 100644 --- a/Documentation/ABI/testing/sysfs-bus-iio +++ b/Documentation/ABI/testing/sysfs-bus-iio @@ -1656,6 +1656,8 @@ What: /sys/bus/iio/devices/iio:deviceX/in_countY_raw KernelVersion: 4.10 Contact: linux-iio@vger.kernel.org Description: + This interface is deprecated; please use the Counter subsystem. + Raw counter device counts from channel Y. For quadrature counters, multiplication by an available [Y]_scale results in the counts of a single quadrature signal phase from channel Y. @@ -1664,6 +1666,8 @@ What: /sys/bus/iio/devices/iio:deviceX/in_indexY_raw KernelVersion: 4.10 Contact: linux-iio@vger.kernel.org Description: + This interface is deprecated; please use the Counter subsystem. + Raw counter device index value from channel Y. This attribute provides an absolute positional reference (e.g. a pulse once per revolution) which may be used to home positional systems as @@ -1673,6 +1677,8 @@ What: /sys/bus/iio/devices/iio:deviceX/in_count_count_direction_available KernelVersion: 4.12 Contact: linux-iio@vger.kernel.org Description: + This interface is deprecated; please use the Counter subsystem. + A list of possible counting directions which are: - "up" : counter device is increasing. - "down": counter device is decreasing. @@ -1681,6 +1687,8 @@ What: /sys/bus/iio/devices/iio:deviceX/in_countY_count_direction KernelVersion: 4.12 Contact: linux-iio@vger.kernel.org Description: + This interface is deprecated; please use the Counter subsystem. + Raw counter device counters direction for channel Y. What: /sys/bus/iio/devices/iio:deviceX/in_phaseY_raw diff --git a/Documentation/ABI/testing/sysfs-bus-iio-counter-104-quad-8 b/Documentation/ABI/testing/sysfs-bus-iio-counter-104-quad-8 index 7fac2c268d9a..bac3d0d48b7b 100644 --- a/Documentation/ABI/testing/sysfs-bus-iio-counter-104-quad-8 +++ b/Documentation/ABI/testing/sysfs-bus-iio-counter-104-quad-8 @@ -6,6 +6,8 @@ What: /sys/bus/iio/devices/iio:deviceX/in_index_synchronous_mode_available KernelVersion: 4.10 Contact: linux-iio@vger.kernel.org Description: + This interface is deprecated; please use the Counter subsystem. + Discrete set of available values for the respective counter configuration are listed in this file. @@ -13,6 +15,8 @@ What: /sys/bus/iio/devices/iio:deviceX/in_countY_count_mode KernelVersion: 4.10 Contact: linux-iio@vger.kernel.org Description: + This interface is deprecated; please use the Counter subsystem. + Count mode for channel Y. Four count modes are available: normal, range limit, non-recycle, and modulo-n. The preset value for channel Y is used by the count mode where required. @@ -47,6 +51,8 @@ What: /sys/bus/iio/devices/iio:deviceX/in_countY_noise_error KernelVersion: 4.10 Contact: linux-iio@vger.kernel.org Description: + This interface is deprecated; please use the Counter subsystem. + Read-only attribute that indicates whether excessive noise is present at the channel Y count inputs in quadrature clock mode; irrelevant in non-quadrature clock mode. @@ -55,6 +61,8 @@ What: /sys/bus/iio/devices/iio:deviceX/in_countY_preset KernelVersion: 4.10 Contact: linux-iio@vger.kernel.org Description: + This interface is deprecated; please use the Counter subsystem. + If the counter device supports preset registers, the preset count for channel Y is provided by this attribute. @@ -62,6 +70,8 @@ What: /sys/bus/iio/devices/iio:deviceX/in_countY_quadrature_mode KernelVersion: 4.10 Contact: linux-iio@vger.kernel.org Description: + This interface is deprecated; please use the Counter subsystem. + Configure channel Y counter for non-quadrature or quadrature clock mode. Selecting non-quadrature clock mode will disable synchronous load mode. In quadrature clock mode, the channel Y @@ -83,6 +93,8 @@ What: /sys/bus/iio/devices/iio:deviceX/in_countY_set_to_preset_on_index KernelVersion: 4.10 Contact: linux-iio@vger.kernel.org Description: + This interface is deprecated; please use the Counter subsystem. + Whether to set channel Y counter with channel Y preset value when channel Y index input is active, or continuously count. Valid attribute values are boolean. @@ -91,6 +103,8 @@ What: /sys/bus/iio/devices/iio:deviceX/in_indexY_index_polarity KernelVersion: 4.10 Contact: linux-iio@vger.kernel.org Description: + This interface is deprecated; please use the Counter subsystem. + Active level of channel Y index input; irrelevant in non-synchronous load mode. @@ -98,6 +112,8 @@ What: /sys/bus/iio/devices/iio:deviceX/in_indexY_synchronous_mode KernelVersion: 4.10 Contact: linux-iio@vger.kernel.org Description: + This interface is deprecated; please use the Counter subsystem. + Configure channel Y counter for non-synchronous or synchronous load mode. Synchronous load mode cannot be selected in non-quadrature clock mode. -- cgit v1.2.3 From 7f2e3ea306fc12c2a0939793c5b4e35aef22ac4a Mon Sep 17 00:00:00 2001 From: Patrick Havelange Date: Tue, 2 Apr 2019 15:30:50 +0900 Subject: dt-bindings: counter: ftm-quaddec FlexTimer quadrature decoder driver. Reviewed-by: Esben Haabendal Signed-off-by: Patrick Havelange Signed-off-by: William Breathitt Gray Signed-off-by: Greg Kroah-Hartman --- .../devicetree/bindings/counter/ftm-quaddec.txt | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) create mode 100644 Documentation/devicetree/bindings/counter/ftm-quaddec.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/counter/ftm-quaddec.txt b/Documentation/devicetree/bindings/counter/ftm-quaddec.txt new file mode 100644 index 000000000000..4d18cd722074 --- /dev/null +++ b/Documentation/devicetree/bindings/counter/ftm-quaddec.txt @@ -0,0 +1,18 @@ +FlexTimer Quadrature decoder counter + +This driver exposes a simple counter for the quadrature decoder mode. + +Required properties: +- compatible: Must be "fsl,ftm-quaddec". +- reg: Must be set to the memory region of the flextimer. + +Optional property: +- big-endian: Access the device registers in big-endian mode. + +Example: + counter0: counter@29d0000 { + compatible = "fsl,ftm-quaddec"; + reg = <0x0 0x29d0000 0x0 0x10000>; + big-endian; + status = "disabled"; + }; -- cgit v1.2.3 From d8ea4ccfaea0b87831ac9a265bb902904e70a25d Mon Sep 17 00:00:00 2001 From: Patrick Havelange Date: Tue, 2 Apr 2019 15:30:52 +0900 Subject: counter: ftm-quaddec: Documentation: Add specific counter sysfs documentation This adds documentation for the specific prescaler entry. Signed-off-by: Patrick Havelange Signed-off-by: William Breathitt Gray Signed-off-by: Greg Kroah-Hartman --- Documentation/ABI/testing/sysfs-bus-counter-ftm-quaddec | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) create mode 100644 Documentation/ABI/testing/sysfs-bus-counter-ftm-quaddec (limited to 'Documentation') diff --git a/Documentation/ABI/testing/sysfs-bus-counter-ftm-quaddec b/Documentation/ABI/testing/sysfs-bus-counter-ftm-quaddec new file mode 100644 index 000000000000..7d2e7b363467 --- /dev/null +++ b/Documentation/ABI/testing/sysfs-bus-counter-ftm-quaddec @@ -0,0 +1,16 @@ +What: /sys/bus/counter/devices/counterX/countY/prescaler_available +KernelVersion: 5.2 +Contact: linux-iio@vger.kernel.org +Description: + Discrete set of available values for the respective Count Y + configuration are listed in this file. Values are delimited by + newline characters. + +What: /sys/bus/counter/devices/counterX/countY/prescaler +KernelVersion: 5.2 +Contact: linux-iio@vger.kernel.org +Description: + Configure the prescaler value associated with Count Y. + On the FlexTimer, the counter clock source passes through a + prescaler (i.e. a counter). This acts like a clock + divider. -- cgit v1.2.3 From b408038415d91b9cc320e01ea6952bb614367004 Mon Sep 17 00:00:00 2001 From: Alexandre Belloni Date: Tue, 2 Apr 2019 14:50:55 +0200 Subject: dt-bindings: clk: at91: add bindings for SAM9X60 pmc Add SAM9X60 PMC compatible string. Signed-off-by: Alexandre Belloni Signed-off-by: Stephen Boyd --- Documentation/devicetree/bindings/clock/at91-clock.txt | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/clock/at91-clock.txt b/Documentation/devicetree/bindings/clock/at91-clock.txt index cb838c1c4bdd..b520280e33ff 100644 --- a/Documentation/devicetree/bindings/clock/at91-clock.txt +++ b/Documentation/devicetree/bindings/clock/at91-clock.txt @@ -30,7 +30,8 @@ For example: Power Management Controller (PMC): Required properties: -- compatible : shall be "atmel,-pmc", "syscon": +- compatible : shall be "atmel,-pmc", "syscon" or + "microchip,sam9x60-pmc" can be: at91rm9200, at91sam9260, at91sam9261, at91sam9263, at91sam9g45, at91sam9n12, at91sam9rl, at91sam9g15, at91sam9g25, at91sam9g35, at91sam9x25, at91sam9x35, at91sam9x5, -- cgit v1.2.3 From 15235f1f495efc5ed435cf6fff95066ba85c5328 Mon Sep 17 00:00:00 2001 From: Lucas Stach Date: Sat, 13 Apr 2019 11:32:46 +0100 Subject: dt-bindings: imx-ocotp: Add i.MX8MQ compatible Add compatible for i.MX8MQ and add i.MX7D/S, i.MX7ULP and i.M8MQ to the description. Signed-off-by: Lucas Stach Reviewed-by: Rob Herring Reviewed-by: Abel Vesa Signed-off-by: Srinivas Kandagatla Signed-off-by: Greg Kroah-Hartman --- Documentation/devicetree/bindings/nvmem/imx-ocotp.txt | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/nvmem/imx-ocotp.txt b/Documentation/devicetree/bindings/nvmem/imx-ocotp.txt index 7a999a135e56..68f7d6fdd140 100644 --- a/Documentation/devicetree/bindings/nvmem/imx-ocotp.txt +++ b/Documentation/devicetree/bindings/nvmem/imx-ocotp.txt @@ -1,7 +1,8 @@ Freescale i.MX6 On-Chip OTP Controller (OCOTP) device tree bindings This binding represents the on-chip eFuse OTP controller found on -i.MX6Q/D, i.MX6DL/S, i.MX6SL, i.MX6SX, i.MX6UL, i.MX6ULL/ULZ and i.MX6SLL SoCs. +i.MX6Q/D, i.MX6DL/S, i.MX6SL, i.MX6SX, i.MX6UL, i.MX6ULL/ULZ, i.MX6SLL, +i.MX7D/S, i.MX7ULP and i.MX8MQ SoCs. Required properties: - compatible: should be one of @@ -13,6 +14,7 @@ Required properties: "fsl,imx7d-ocotp" (i.MX7D/S), "fsl,imx6sll-ocotp" (i.MX6SLL), "fsl,imx7ulp-ocotp" (i.MX7ULP), + "fsl,imx8mq-ocotp" (i.MX8MQ), followed by "syscon". - #address-cells : Should be 1 - #size-cells : Should be 1 -- cgit v1.2.3 From 680e6ffa15103ab610c0fc1241d2f98c801b13e2 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 23:30:54 +0800 Subject: Documentation: add Linux ACPI to Sphinx TOC tree Add below index.rst files for ACPI subsystem. More docs will be added later. o admin-guide/acpi/index.rst o driver-api/acpi/index.rst o firmware-guide/index.rst Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Rafael J. Wysocki --- Documentation/admin-guide/acpi/index.rst | 10 ++++++++++ Documentation/admin-guide/index.rst | 1 + Documentation/driver-api/acpi/index.rst | 7 +++++++ Documentation/driver-api/index.rst | 1 + Documentation/firmware-guide/acpi/index.rst | 9 +++++++++ Documentation/firmware-guide/index.rst | 13 +++++++++++++ Documentation/index.rst | 10 ++++++++++ 7 files changed, 51 insertions(+) create mode 100644 Documentation/admin-guide/acpi/index.rst create mode 100644 Documentation/driver-api/acpi/index.rst create mode 100644 Documentation/firmware-guide/acpi/index.rst create mode 100644 Documentation/firmware-guide/index.rst (limited to 'Documentation') diff --git a/Documentation/admin-guide/acpi/index.rst b/Documentation/admin-guide/acpi/index.rst new file mode 100644 index 000000000000..3e041206089d --- /dev/null +++ b/Documentation/admin-guide/acpi/index.rst @@ -0,0 +1,10 @@ +============ +ACPI Support +============ + +Here we document in detail how to interact with various mechanisms in +the Linux ACPI support. + +.. toctree:: + :maxdepth: 1 + diff --git a/Documentation/admin-guide/index.rst b/Documentation/admin-guide/index.rst index 0a491676685e..5b8286fdd91b 100644 --- a/Documentation/admin-guide/index.rst +++ b/Documentation/admin-guide/index.rst @@ -77,6 +77,7 @@ configure specific aspects of kernel behavior to your liking. LSM/index mm/index perf-security + acpi/index .. only:: subproject and html diff --git a/Documentation/driver-api/acpi/index.rst b/Documentation/driver-api/acpi/index.rst new file mode 100644 index 000000000000..898b0c60671a --- /dev/null +++ b/Documentation/driver-api/acpi/index.rst @@ -0,0 +1,7 @@ +============ +ACPI Support +============ + +.. toctree:: + :maxdepth: 2 + diff --git a/Documentation/driver-api/index.rst b/Documentation/driver-api/index.rst index c0b600ed9961..aa87075c7846 100644 --- a/Documentation/driver-api/index.rst +++ b/Documentation/driver-api/index.rst @@ -56,6 +56,7 @@ available subsections can be seen below. slimbus soundwire/index fpga/index + acpi/index .. only:: subproject and html diff --git a/Documentation/firmware-guide/acpi/index.rst b/Documentation/firmware-guide/acpi/index.rst new file mode 100644 index 000000000000..0ec7d072ba22 --- /dev/null +++ b/Documentation/firmware-guide/acpi/index.rst @@ -0,0 +1,9 @@ +.. SPDX-License-Identifier: GPL-2.0 + +============ +ACPI Support +============ + +.. toctree:: + :maxdepth: 1 + diff --git a/Documentation/firmware-guide/index.rst b/Documentation/firmware-guide/index.rst new file mode 100644 index 000000000000..5355784ca0a2 --- /dev/null +++ b/Documentation/firmware-guide/index.rst @@ -0,0 +1,13 @@ +.. SPDX-License-Identifier: GPL-2.0 + +=============================== +The Linux kernel firmware guide +=============================== + +This section describes the ACPI subsystem in Linux from firmware perspective. + +.. toctree:: + :maxdepth: 1 + + acpi/index + diff --git a/Documentation/index.rst b/Documentation/index.rst index 80a421cb935e..fdfa85c56a50 100644 --- a/Documentation/index.rst +++ b/Documentation/index.rst @@ -35,6 +35,16 @@ trying to get it to work optimally on a given system. admin-guide/index +Firmware-related documentation +------------------------------ +The following holds information on the kernel's expectations regarding the +platform firmwares. + +.. toctree:: + :maxdepth: 2 + + firmware-guide/index + Application-developer documentation ----------------------------------- -- cgit v1.2.3 From 8a2fe04b446f909ffffadb84b886199edbe408c2 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 01:52:44 +0800 Subject: Documentation: ACPI: move namespace.txt to firmware-guide/acpi and convert to reST This converts the plain text documentation to reStructuredText format and adds it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/namespace.txt | 388 ----------------------- Documentation/firmware-guide/acpi/index.rst | 1 + Documentation/firmware-guide/acpi/namespace.rst | 400 ++++++++++++++++++++++++ 3 files changed, 401 insertions(+), 388 deletions(-) delete mode 100644 Documentation/acpi/namespace.txt create mode 100644 Documentation/firmware-guide/acpi/namespace.rst (limited to 'Documentation') diff --git a/Documentation/acpi/namespace.txt b/Documentation/acpi/namespace.txt deleted file mode 100644 index 1860cb3865c6..000000000000 --- a/Documentation/acpi/namespace.txt +++ /dev/null @@ -1,388 +0,0 @@ -ACPI Device Tree - Representation of ACPI Namespace - -Copyright (C) 2013, Intel Corporation -Author: Lv Zheng - - -Abstract: - -The Linux ACPI subsystem converts ACPI namespace objects into a Linux -device tree under the /sys/devices/LNXSYSTEM:00 and updates it upon -receiving ACPI hotplug notification events. For each device object in this -hierarchy there is a corresponding symbolic link in the -/sys/bus/acpi/devices. -This document illustrates the structure of the ACPI device tree. - - -Credit: - -Thanks for the help from Zhang Rui and Rafael J. -Wysocki . - - -1. ACPI Definition Blocks - - The ACPI firmware sets up RSDP (Root System Description Pointer) in the - system memory address space pointing to the XSDT (Extended System - Description Table). The XSDT always points to the FADT (Fixed ACPI - Description Table) using its first entry, the data within the FADT - includes various fixed-length entries that describe fixed ACPI features - of the hardware. The FADT contains a pointer to the DSDT - (Differentiated System Descripition Table). The XSDT also contains - entries pointing to possibly multiple SSDTs (Secondary System - Description Table). - - The DSDT and SSDT data is organized in data structures called definition - blocks that contain definitions of various objects, including ACPI - control methods, encoded in AML (ACPI Machine Language). The data block - of the DSDT along with the contents of SSDTs represents a hierarchical - data structure called the ACPI namespace whose topology reflects the - structure of the underlying hardware platform. - - The relationships between ACPI System Definition Tables described above - are illustrated in the following diagram. - - +---------+ +-------+ +--------+ +------------------------+ - | RSDP | +->| XSDT | +->| FADT | | +-------------------+ | - +---------+ | +-------+ | +--------+ +-|->| DSDT | | - | Pointer | | | Entry |-+ | ...... | | | +-------------------+ | - +---------+ | +-------+ | X_DSDT |--+ | | Definition Blocks | | - | Pointer |-+ | ..... | | ...... | | +-------------------+ | - +---------+ +-------+ +--------+ | +-------------------+ | - | Entry |------------------|->| SSDT | | - +- - - -+ | +-------------------| | - | Entry | - - - - - - - -+ | | Definition Blocks | | - +- - - -+ | | +-------------------+ | - | | +- - - - - - - - - -+ | - +-|->| SSDT | | - | +-------------------+ | - | | Definition Blocks | | - | +- - - - - - - - - -+ | - +------------------------+ - | - OSPM Loading | - \|/ - +----------------+ - | ACPI Namespace | - +----------------+ - - Figure 1. ACPI Definition Blocks - - NOTE: RSDP can also contain a pointer to the RSDT (Root System - Description Table). Platforms provide RSDT to enable - compatibility with ACPI 1.0 operating systems. The OS is expected - to use XSDT, if present. - - -2. Example ACPI Namespace - - All definition blocks are loaded into a single namespace. The namespace - is a hierarchy of objects identified by names and paths. - The following naming conventions apply to object names in the ACPI - namespace: - 1. All names are 32 bits long. - 2. The first byte of a name must be one of 'A' - 'Z', '_'. - 3. Each of the remaining bytes of a name must be one of 'A' - 'Z', '0' - - '9', '_'. - 4. Names starting with '_' are reserved by the ACPI specification. - 5. The '\' symbol represents the root of the namespace (i.e. names - prepended with '\' are relative to the namespace root). - 6. The '^' symbol represents the parent of the current namespace node - (i.e. names prepended with '^' are relative to the parent of the - current namespace node). - - The figure below shows an example ACPI namespace. - - +------+ - | \ | Root - +------+ - | - | +------+ - +-| _PR | Scope(_PR): the processor namespace - | +------+ - | | - | | +------+ - | +-| CPU0 | Processor(CPU0): the first processor - | +------+ - | - | +------+ - +-| _SB | Scope(_SB): the system bus namespace - | +------+ - | | - | | +------+ - | +-| LID0 | Device(LID0); the lid device - | | +------+ - | | | - | | | +------+ - | | +-| _HID | Name(_HID, "PNP0C0D"): the hardware ID - | | | +------+ - | | | - | | | +------+ - | | +-| _STA | Method(_STA): the status control method - | | +------+ - | | - | | +------+ - | +-| PCI0 | Device(PCI0); the PCI root bridge - | +------+ - | | - | | +------+ - | +-| _HID | Name(_HID, "PNP0A08"): the hardware ID - | | +------+ - | | - | | +------+ - | +-| _CID | Name(_CID, "PNP0A03"): the compatible ID - | | +------+ - | | - | | +------+ - | +-| RP03 | Scope(RP03): the PCI0 power scope - | | +------+ - | | | - | | | +------+ - | | +-| PXP3 | PowerResource(PXP3): the PCI0 power resource - | | +------+ - | | - | | +------+ - | +-| GFX0 | Device(GFX0): the graphics adapter - | +------+ - | | - | | +------+ - | +-| _ADR | Name(_ADR, 0x00020000): the PCI bus address - | | +------+ - | | - | | +------+ - | +-| DD01 | Device(DD01): the LCD output device - | +------+ - | | - | | +------+ - | +-| _BCL | Method(_BCL): the backlight control method - | +------+ - | - | +------+ - +-| _TZ | Scope(_TZ): the thermal zone namespace - | +------+ - | | - | | +------+ - | +-| FN00 | PowerResource(FN00): the FAN0 power resource - | | +------+ - | | - | | +------+ - | +-| FAN0 | Device(FAN0): the FAN0 cooling device - | | +------+ - | | | - | | | +------+ - | | +-| _HID | Name(_HID, "PNP0A0B"): the hardware ID - | | +------+ - | | - | | +------+ - | +-| TZ00 | ThermalZone(TZ00); the FAN thermal zone - | +------+ - | - | +------+ - +-| _GPE | Scope(_GPE): the GPE namespace - +------+ - - Figure 2. Example ACPI Namespace - - -3. Linux ACPI Device Objects - - The Linux kernel's core ACPI subsystem creates struct acpi_device - objects for ACPI namespace objects representing devices, power resources - processors, thermal zones. Those objects are exported to user space via - sysfs as directories in the subtree under /sys/devices/LNXSYSTM:00. The - format of their names is , where 'bus_id' refers to the - ACPI namespace representation of the given object and 'instance' is used - for distinguishing different object of the same 'bus_id' (it is - two-digit decimal representation of an unsigned integer). - - The value of 'bus_id' depends on the type of the object whose name it is - part of as listed in the table below. - - +---+-----------------+-------+----------+ - | | Object/Feature | Table | bus_id | - +---+-----------------+-------+----------+ - | N | Root | xSDT | LNXSYSTM | - +---+-----------------+-------+----------+ - | N | Device | xSDT | _HID | - +---+-----------------+-------+----------+ - | N | Processor | xSDT | LNXCPU | - +---+-----------------+-------+----------+ - | N | ThermalZone | xSDT | LNXTHERM | - +---+-----------------+-------+----------+ - | N | PowerResource | xSDT | LNXPOWER | - +---+-----------------+-------+----------+ - | N | Other Devices | xSDT | device | - +---+-----------------+-------+----------+ - | F | PWR_BUTTON | FADT | LNXPWRBN | - +---+-----------------+-------+----------+ - | F | SLP_BUTTON | FADT | LNXSLPBN | - +---+-----------------+-------+----------+ - | M | Video Extension | xSDT | LNXVIDEO | - +---+-----------------+-------+----------+ - | M | ATA Controller | xSDT | LNXIOBAY | - +---+-----------------+-------+----------+ - | M | Docking Station | xSDT | LNXDOCK | - +---+-----------------+-------+----------+ - - Table 1. ACPI Namespace Objects Mapping - - The following rules apply when creating struct acpi_device objects on - the basis of the contents of ACPI System Description Tables (as - indicated by the letter in the first column and the notation in the - second column of the table above): - N: - The object's source is an ACPI namespace node (as indicated by the - named object's type in the second column). In that case the object's - directory in sysfs will contain the 'path' attribute whose value is - the full path to the node from the namespace root. - F: - The struct acpi_device object is created for a fixed hardware - feature (as indicated by the fixed feature flag's name in the second - column), so its sysfs directory will not contain the 'path' - attribute. - M: - The struct acpi_device object is created for an ACPI namespace node - with specific control methods (as indicated by the ACPI defined - device's type in the second column). The 'path' attribute containing - its namespace path will be present in its sysfs directory. For - example, if the _BCL method is present for an ACPI namespace node, a - struct acpi_device object with LNXVIDEO 'bus_id' will be created for - it. - - The third column of the above table indicates which ACPI System - Description Tables contain information used for the creation of the - struct acpi_device objects represented by the given row (xSDT means DSDT - or SSDT). - - The forth column of the above table indicates the 'bus_id' generation - rule of the struct acpi_device object: - _HID: - _HID in the last column of the table means that the object's bus_id - is derived from the _HID/_CID identification objects present under - the corresponding ACPI namespace node. The object's sysfs directory - will then contain the 'hid' and 'modalias' attributes that can be - used to retrieve the _HID and _CIDs of that object. - LNXxxxxx: - The 'modalias' attribute is also present for struct acpi_device - objects having bus_id of the "LNXxxxxx" form (pseudo devices), in - which cases it contains the bus_id string itself. - device: - 'device' in the last column of the table indicates that the object's - bus_id cannot be determined from _HID/_CID of the corresponding - ACPI namespace node, although that object represents a device (for - example, it may be a PCI device with _ADR defined and without _HID - or _CID). In that case the string 'device' will be used as the - object's bus_id. - - -4. Linux ACPI Physical Device Glue - - ACPI device (i.e. struct acpi_device) objects may be linked to other - objects in the Linux' device hierarchy that represent "physical" devices - (for example, devices on the PCI bus). If that happens, it means that - the ACPI device object is a "companion" of a device otherwise - represented in a different way and is used (1) to provide configuration - information on that device which cannot be obtained by other means and - (2) to do specific things to the device with the help of its ACPI - control methods. One ACPI device object may be linked this way to - multiple "physical" devices. - - If an ACPI device object is linked to a "physical" device, its sysfs - directory contains the "physical_node" symbolic link to the sysfs - directory of the target device object. In turn, the target device's - sysfs directory will then contain the "firmware_node" symbolic link to - the sysfs directory of the companion ACPI device object. - The linking mechanism relies on device identification provided by the - ACPI namespace. For example, if there's an ACPI namespace object - representing a PCI device (i.e. a device object under an ACPI namespace - object representing a PCI bridge) whose _ADR returns 0x00020000 and the - bus number of the parent PCI bridge is 0, the sysfs directory - representing the struct acpi_device object created for that ACPI - namespace object will contain the 'physical_node' symbolic link to the - /sys/devices/pci0000:00/0000:00:02:0/ sysfs directory of the - corresponding PCI device. - - The linking mechanism is generally bus-specific. The core of its - implementation is located in the drivers/acpi/glue.c file, but there are - complementary parts depending on the bus types in question located - elsewhere. For example, the PCI-specific part of it is located in - drivers/pci/pci-acpi.c. - - -5. Example Linux ACPI Device Tree - - The sysfs hierarchy of struct acpi_device objects corresponding to the - example ACPI namespace illustrated in Figure 2 with the addition of - fixed PWR_BUTTON/SLP_BUTTON devices is shown below. - - +--------------+---+-----------------+ - | LNXSYSTEM:00 | \ | acpi:LNXSYSTEM: | - +--------------+---+-----------------+ - | - | +-------------+-----+----------------+ - +-| LNXPWRBN:00 | N/A | acpi:LNXPWRBN: | - | +-------------+-----+----------------+ - | - | +-------------+-----+----------------+ - +-| LNXSLPBN:00 | N/A | acpi:LNXSLPBN: | - | +-------------+-----+----------------+ - | - | +-----------+------------+--------------+ - +-| LNXCPU:00 | \_PR_.CPU0 | acpi:LNXCPU: | - | +-----------+------------+--------------+ - | - | +-------------+-------+----------------+ - +-| LNXSYBUS:00 | \_SB_ | acpi:LNXSYBUS: | - | +-------------+-------+----------------+ - | | - | | +- - - - - - - +- - - - - - +- - - - - - - -+ - | +-| PNP0C0D:00 | \_SB_.LID0 | acpi:PNP0C0D: | - | | +- - - - - - - +- - - - - - +- - - - - - - -+ - | | - | | +------------+------------+-----------------------+ - | +-| PNP0A08:00 | \_SB_.PCI0 | acpi:PNP0A08:PNP0A03: | - | +------------+------------+-----------------------+ - | | - | | +-----------+-----------------+-----+ - | +-| device:00 | \_SB_.PCI0.RP03 | N/A | - | | +-----------+-----------------+-----+ - | | | - | | | +-------------+----------------------+----------------+ - | | +-| LNXPOWER:00 | \_SB_.PCI0.RP03.PXP3 | acpi:LNXPOWER: | - | | +-------------+----------------------+----------------+ - | | - | | +-------------+-----------------+----------------+ - | +-| LNXVIDEO:00 | \_SB_.PCI0.GFX0 | acpi:LNXVIDEO: | - | +-------------+-----------------+----------------+ - | | - | | +-----------+-----------------+-----+ - | +-| device:01 | \_SB_.PCI0.DD01 | N/A | - | +-----------+-----------------+-----+ - | - | +-------------+-------+----------------+ - +-| LNXSYBUS:01 | \_TZ_ | acpi:LNXSYBUS: | - +-------------+-------+----------------+ - | - | +-------------+------------+----------------+ - +-| LNXPOWER:0a | \_TZ_.FN00 | acpi:LNXPOWER: | - | +-------------+------------+----------------+ - | - | +------------+------------+---------------+ - +-| PNP0C0B:00 | \_TZ_.FAN0 | acpi:PNP0C0B: | - | +------------+------------+---------------+ - | - | +-------------+------------+----------------+ - +-| LNXTHERM:00 | \_TZ_.TZ00 | acpi:LNXTHERM: | - +-------------+------------+----------------+ - - Figure 3. Example Linux ACPI Device Tree - - NOTE: Each node is represented as "object/path/modalias", where: - 1. 'object' is the name of the object's directory in sysfs. - 2. 'path' is the ACPI namespace path of the corresponding - ACPI namespace object, as returned by the object's 'path' - sysfs attribute. - 3. 'modalias' is the value of the object's 'modalias' sysfs - attribute (as described earlier in this document). - NOTE: N/A indicates the device object does not have the 'path' or the - 'modalias' attribute. diff --git a/Documentation/firmware-guide/acpi/index.rst b/Documentation/firmware-guide/acpi/index.rst index 0ec7d072ba22..210ad8acd6df 100644 --- a/Documentation/firmware-guide/acpi/index.rst +++ b/Documentation/firmware-guide/acpi/index.rst @@ -7,3 +7,4 @@ ACPI Support .. toctree:: :maxdepth: 1 + namespace diff --git a/Documentation/firmware-guide/acpi/namespace.rst b/Documentation/firmware-guide/acpi/namespace.rst new file mode 100644 index 000000000000..835521baeb89 --- /dev/null +++ b/Documentation/firmware-guide/acpi/namespace.rst @@ -0,0 +1,400 @@ +.. SPDX-License-Identifier: GPL-2.0 +.. include:: + +=================================================== +ACPI Device Tree - Representation of ACPI Namespace +=================================================== + +:Copyright: |copy| 2013, Intel Corporation + +:Author: Lv Zheng + +:Credit: Thanks for the help from Zhang Rui and + Rafael J.Wysocki . + +Abstract +======== +The Linux ACPI subsystem converts ACPI namespace objects into a Linux +device tree under the /sys/devices/LNXSYSTEM:00 and updates it upon +receiving ACPI hotplug notification events. For each device object +in this hierarchy there is a corresponding symbolic link in the +/sys/bus/acpi/devices. + +This document illustrates the structure of the ACPI device tree. + +ACPI Definition Blocks +====================== + +The ACPI firmware sets up RSDP (Root System Description Pointer) in the +system memory address space pointing to the XSDT (Extended System +Description Table). The XSDT always points to the FADT (Fixed ACPI +Description Table) using its first entry, the data within the FADT +includes various fixed-length entries that describe fixed ACPI features +of the hardware. The FADT contains a pointer to the DSDT +(Differentiated System Descripition Table). The XSDT also contains +entries pointing to possibly multiple SSDTs (Secondary System +Description Table). + +The DSDT and SSDT data is organized in data structures called definition +blocks that contain definitions of various objects, including ACPI +control methods, encoded in AML (ACPI Machine Language). The data block +of the DSDT along with the contents of SSDTs represents a hierarchical +data structure called the ACPI namespace whose topology reflects the +structure of the underlying hardware platform. + +The relationships between ACPI System Definition Tables described above +are illustrated in the following diagram:: + + +---------+ +-------+ +--------+ +------------------------+ + | RSDP | +->| XSDT | +->| FADT | | +-------------------+ | + +---------+ | +-------+ | +--------+ +-|->| DSDT | | + | Pointer | | | Entry |-+ | ...... | | | +-------------------+ | + +---------+ | +-------+ | X_DSDT |--+ | | Definition Blocks | | + | Pointer |-+ | ..... | | ...... | | +-------------------+ | + +---------+ +-------+ +--------+ | +-------------------+ | + | Entry |------------------|->| SSDT | | + +- - - -+ | +-------------------| | + | Entry | - - - - - - - -+ | | Definition Blocks | | + +- - - -+ | | +-------------------+ | + | | +- - - - - - - - - -+ | + +-|->| SSDT | | + | +-------------------+ | + | | Definition Blocks | | + | +- - - - - - - - - -+ | + +------------------------+ + | + OSPM Loading | + \|/ + +----------------+ + | ACPI Namespace | + +----------------+ + + Figure 1. ACPI Definition Blocks + +.. note:: RSDP can also contain a pointer to the RSDT (Root System + Description Table). Platforms provide RSDT to enable + compatibility with ACPI 1.0 operating systems. The OS is expected + to use XSDT, if present. + + +Example ACPI Namespace +====================== + +All definition blocks are loaded into a single namespace. The namespace +is a hierarchy of objects identified by names and paths. +The following naming conventions apply to object names in the ACPI +namespace: + + 1. All names are 32 bits long. + 2. The first byte of a name must be one of 'A' - 'Z', '_'. + 3. Each of the remaining bytes of a name must be one of 'A' - 'Z', '0' + - '9', '_'. + 4. Names starting with '_' are reserved by the ACPI specification. + 5. The '\' symbol represents the root of the namespace (i.e. names + prepended with '\' are relative to the namespace root). + 6. The '^' symbol represents the parent of the current namespace node + (i.e. names prepended with '^' are relative to the parent of the + current namespace node). + +The figure below shows an example ACPI namespace:: + + +------+ + | \ | Root + +------+ + | + | +------+ + +-| _PR | Scope(_PR): the processor namespace + | +------+ + | | + | | +------+ + | +-| CPU0 | Processor(CPU0): the first processor + | +------+ + | + | +------+ + +-| _SB | Scope(_SB): the system bus namespace + | +------+ + | | + | | +------+ + | +-| LID0 | Device(LID0); the lid device + | | +------+ + | | | + | | | +------+ + | | +-| _HID | Name(_HID, "PNP0C0D"): the hardware ID + | | | +------+ + | | | + | | | +------+ + | | +-| _STA | Method(_STA): the status control method + | | +------+ + | | + | | +------+ + | +-| PCI0 | Device(PCI0); the PCI root bridge + | +------+ + | | + | | +------+ + | +-| _HID | Name(_HID, "PNP0A08"): the hardware ID + | | +------+ + | | + | | +------+ + | +-| _CID | Name(_CID, "PNP0A03"): the compatible ID + | | +------+ + | | + | | +------+ + | +-| RP03 | Scope(RP03): the PCI0 power scope + | | +------+ + | | | + | | | +------+ + | | +-| PXP3 | PowerResource(PXP3): the PCI0 power resource + | | +------+ + | | + | | +------+ + | +-| GFX0 | Device(GFX0): the graphics adapter + | +------+ + | | + | | +------+ + | +-| _ADR | Name(_ADR, 0x00020000): the PCI bus address + | | +------+ + | | + | | +------+ + | +-| DD01 | Device(DD01): the LCD output device + | +------+ + | | + | | +------+ + | +-| _BCL | Method(_BCL): the backlight control method + | +------+ + | + | +------+ + +-| _TZ | Scope(_TZ): the thermal zone namespace + | +------+ + | | + | | +------+ + | +-| FN00 | PowerResource(FN00): the FAN0 power resource + | | +------+ + | | + | | +------+ + | +-| FAN0 | Device(FAN0): the FAN0 cooling device + | | +------+ + | | | + | | | +------+ + | | +-| _HID | Name(_HID, "PNP0A0B"): the hardware ID + | | +------+ + | | + | | +------+ + | +-| TZ00 | ThermalZone(TZ00); the FAN thermal zone + | +------+ + | + | +------+ + +-| _GPE | Scope(_GPE): the GPE namespace + +------+ + + Figure 2. Example ACPI Namespace + + +Linux ACPI Device Objects +========================= + +The Linux kernel's core ACPI subsystem creates struct acpi_device +objects for ACPI namespace objects representing devices, power resources +processors, thermal zones. Those objects are exported to user space via +sysfs as directories in the subtree under /sys/devices/LNXSYSTM:00. The +format of their names is , where 'bus_id' refers to the +ACPI namespace representation of the given object and 'instance' is used +for distinguishing different object of the same 'bus_id' (it is +two-digit decimal representation of an unsigned integer). + +The value of 'bus_id' depends on the type of the object whose name it is +part of as listed in the table below:: + + +---+-----------------+-------+----------+ + | | Object/Feature | Table | bus_id | + +---+-----------------+-------+----------+ + | N | Root | xSDT | LNXSYSTM | + +---+-----------------+-------+----------+ + | N | Device | xSDT | _HID | + +---+-----------------+-------+----------+ + | N | Processor | xSDT | LNXCPU | + +---+-----------------+-------+----------+ + | N | ThermalZone | xSDT | LNXTHERM | + +---+-----------------+-------+----------+ + | N | PowerResource | xSDT | LNXPOWER | + +---+-----------------+-------+----------+ + | N | Other Devices | xSDT | device | + +---+-----------------+-------+----------+ + | F | PWR_BUTTON | FADT | LNXPWRBN | + +---+-----------------+-------+----------+ + | F | SLP_BUTTON | FADT | LNXSLPBN | + +---+-----------------+-------+----------+ + | M | Video Extension | xSDT | LNXVIDEO | + +---+-----------------+-------+----------+ + | M | ATA Controller | xSDT | LNXIOBAY | + +---+-----------------+-------+----------+ + | M | Docking Station | xSDT | LNXDOCK | + +---+-----------------+-------+----------+ + + Table 1. ACPI Namespace Objects Mapping + +The following rules apply when creating struct acpi_device objects on +the basis of the contents of ACPI System Description Tables (as +indicated by the letter in the first column and the notation in the +second column of the table above): + + N: + The object's source is an ACPI namespace node (as indicated by the + named object's type in the second column). In that case the object's + directory in sysfs will contain the 'path' attribute whose value is + the full path to the node from the namespace root. + F: + The struct acpi_device object is created for a fixed hardware + feature (as indicated by the fixed feature flag's name in the second + column), so its sysfs directory will not contain the 'path' + attribute. + M: + The struct acpi_device object is created for an ACPI namespace node + with specific control methods (as indicated by the ACPI defined + device's type in the second column). The 'path' attribute containing + its namespace path will be present in its sysfs directory. For + example, if the _BCL method is present for an ACPI namespace node, a + struct acpi_device object with LNXVIDEO 'bus_id' will be created for + it. + +The third column of the above table indicates which ACPI System +Description Tables contain information used for the creation of the +struct acpi_device objects represented by the given row (xSDT means DSDT +or SSDT). + +The forth column of the above table indicates the 'bus_id' generation +rule of the struct acpi_device object: + + _HID: + _HID in the last column of the table means that the object's bus_id + is derived from the _HID/_CID identification objects present under + the corresponding ACPI namespace node. The object's sysfs directory + will then contain the 'hid' and 'modalias' attributes that can be + used to retrieve the _HID and _CIDs of that object. + LNXxxxxx: + The 'modalias' attribute is also present for struct acpi_device + objects having bus_id of the "LNXxxxxx" form (pseudo devices), in + which cases it contains the bus_id string itself. + device: + 'device' in the last column of the table indicates that the object's + bus_id cannot be determined from _HID/_CID of the corresponding + ACPI namespace node, although that object represents a device (for + example, it may be a PCI device with _ADR defined and without _HID + or _CID). In that case the string 'device' will be used as the + object's bus_id. + + +Linux ACPI Physical Device Glue +=============================== + +ACPI device (i.e. struct acpi_device) objects may be linked to other +objects in the Linux' device hierarchy that represent "physical" devices +(for example, devices on the PCI bus). If that happens, it means that +the ACPI device object is a "companion" of a device otherwise +represented in a different way and is used (1) to provide configuration +information on that device which cannot be obtained by other means and +(2) to do specific things to the device with the help of its ACPI +control methods. One ACPI device object may be linked this way to +multiple "physical" devices. + +If an ACPI device object is linked to a "physical" device, its sysfs +directory contains the "physical_node" symbolic link to the sysfs +directory of the target device object. In turn, the target device's +sysfs directory will then contain the "firmware_node" symbolic link to +the sysfs directory of the companion ACPI device object. +The linking mechanism relies on device identification provided by the +ACPI namespace. For example, if there's an ACPI namespace object +representing a PCI device (i.e. a device object under an ACPI namespace +object representing a PCI bridge) whose _ADR returns 0x00020000 and the +bus number of the parent PCI bridge is 0, the sysfs directory +representing the struct acpi_device object created for that ACPI +namespace object will contain the 'physical_node' symbolic link to the +/sys/devices/pci0000:00/0000:00:02:0/ sysfs directory of the +corresponding PCI device. + +The linking mechanism is generally bus-specific. The core of its +implementation is located in the drivers/acpi/glue.c file, but there are +complementary parts depending on the bus types in question located +elsewhere. For example, the PCI-specific part of it is located in +drivers/pci/pci-acpi.c. + + +Example Linux ACPI Device Tree +================================= + +The sysfs hierarchy of struct acpi_device objects corresponding to the +example ACPI namespace illustrated in Figure 2 with the addition of +fixed PWR_BUTTON/SLP_BUTTON devices is shown below:: + + +--------------+---+-----------------+ + | LNXSYSTEM:00 | \ | acpi:LNXSYSTEM: | + +--------------+---+-----------------+ + | + | +-------------+-----+----------------+ + +-| LNXPWRBN:00 | N/A | acpi:LNXPWRBN: | + | +-------------+-----+----------------+ + | + | +-------------+-----+----------------+ + +-| LNXSLPBN:00 | N/A | acpi:LNXSLPBN: | + | +-------------+-----+----------------+ + | + | +-----------+------------+--------------+ + +-| LNXCPU:00 | \_PR_.CPU0 | acpi:LNXCPU: | + | +-----------+------------+--------------+ + | + | +-------------+-------+----------------+ + +-| LNXSYBUS:00 | \_SB_ | acpi:LNXSYBUS: | + | +-------------+-------+----------------+ + | | + | | +- - - - - - - +- - - - - - +- - - - - - - -+ + | +-| PNP0C0D:00 | \_SB_.LID0 | acpi:PNP0C0D: | + | | +- - - - - - - +- - - - - - +- - - - - - - -+ + | | + | | +------------+------------+-----------------------+ + | +-| PNP0A08:00 | \_SB_.PCI0 | acpi:PNP0A08:PNP0A03: | + | +------------+------------+-----------------------+ + | | + | | +-----------+-----------------+-----+ + | +-| device:00 | \_SB_.PCI0.RP03 | N/A | + | | +-----------+-----------------+-----+ + | | | + | | | +-------------+----------------------+----------------+ + | | +-| LNXPOWER:00 | \_SB_.PCI0.RP03.PXP3 | acpi:LNXPOWER: | + | | +-------------+----------------------+----------------+ + | | + | | +-------------+-----------------+----------------+ + | +-| LNXVIDEO:00 | \_SB_.PCI0.GFX0 | acpi:LNXVIDEO: | + | +-------------+-----------------+----------------+ + | | + | | +-----------+-----------------+-----+ + | +-| device:01 | \_SB_.PCI0.DD01 | N/A | + | +-----------+-----------------+-----+ + | + | +-------------+-------+----------------+ + +-| LNXSYBUS:01 | \_TZ_ | acpi:LNXSYBUS: | + +-------------+-------+----------------+ + | + | +-------------+------------+----------------+ + +-| LNXPOWER:0a | \_TZ_.FN00 | acpi:LNXPOWER: | + | +-------------+------------+----------------+ + | + | +------------+------------+---------------+ + +-| PNP0C0B:00 | \_TZ_.FAN0 | acpi:PNP0C0B: | + | +------------+------------+---------------+ + | + | +-------------+------------+----------------+ + +-| LNXTHERM:00 | \_TZ_.TZ00 | acpi:LNXTHERM: | + +-------------+------------+----------------+ + + Figure 3. Example Linux ACPI Device Tree + +.. note:: Each node is represented as "object/path/modalias", where: + + 1. 'object' is the name of the object's directory in sysfs. + 2. 'path' is the ACPI namespace path of the corresponding + ACPI namespace object, as returned by the object's 'path' + sysfs attribute. + 3. 'modalias' is the value of the object's 'modalias' sysfs + attribute (as described earlier in this document). + +.. note:: N/A indicates the device object does not have the 'path' or the + 'modalias' attribute. -- cgit v1.2.3 From c24bc66e8157ca4956b8be1ed62493d70dfdb547 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 01:52:45 +0800 Subject: Documentation: ACPI: move enumeration.txt to firmware-guide/acpi and convert to reST This converts the plain text documentation to reStructuredText format and adds it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/enumeration.txt | 452 --------------------- Documentation/firmware-guide/acpi/enumeration.rst | 463 ++++++++++++++++++++++ Documentation/firmware-guide/acpi/index.rst | 1 + 3 files changed, 464 insertions(+), 452 deletions(-) delete mode 100644 Documentation/acpi/enumeration.txt create mode 100644 Documentation/firmware-guide/acpi/enumeration.rst (limited to 'Documentation') diff --git a/Documentation/acpi/enumeration.txt b/Documentation/acpi/enumeration.txt deleted file mode 100644 index 1395b844649c..000000000000 --- a/Documentation/acpi/enumeration.txt +++ /dev/null @@ -1,452 +0,0 @@ -ACPI based device enumeration -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -ACPI 5 introduced a set of new resources (UartTSerialBus, I2cSerialBus, -SpiSerialBus, GpioIo and GpioInt) which can be used in enumerating slave -devices behind serial bus controllers. - -In addition we are starting to see peripherals integrated in the -SoC/Chipset to appear only in ACPI namespace. These are typically devices -that are accessed through memory-mapped registers. - -In order to support this and re-use the existing drivers as much as -possible we decided to do following: - - o Devices that have no bus connector resource are represented as - platform devices. - - o Devices behind real busses where there is a connector resource - are represented as struct spi_device or struct i2c_device - (standard UARTs are not busses so there is no struct uart_device). - -As both ACPI and Device Tree represent a tree of devices (and their -resources) this implementation follows the Device Tree way as much as -possible. - -The ACPI implementation enumerates devices behind busses (platform, SPI and -I2C), creates the physical devices and binds them to their ACPI handle in -the ACPI namespace. - -This means that when ACPI_HANDLE(dev) returns non-NULL the device was -enumerated from ACPI namespace. This handle can be used to extract other -device-specific configuration. There is an example of this below. - -Platform bus support -~~~~~~~~~~~~~~~~~~~~ -Since we are using platform devices to represent devices that are not -connected to any physical bus we only need to implement a platform driver -for the device and add supported ACPI IDs. If this same IP-block is used on -some other non-ACPI platform, the driver might work out of the box or needs -some minor changes. - -Adding ACPI support for an existing driver should be pretty -straightforward. Here is the simplest example: - - #ifdef CONFIG_ACPI - static const struct acpi_device_id mydrv_acpi_match[] = { - /* ACPI IDs here */ - { } - }; - MODULE_DEVICE_TABLE(acpi, mydrv_acpi_match); - #endif - - static struct platform_driver my_driver = { - ... - .driver = { - .acpi_match_table = ACPI_PTR(mydrv_acpi_match), - }, - }; - -If the driver needs to perform more complex initialization like getting and -configuring GPIOs it can get its ACPI handle and extract this information -from ACPI tables. - -DMA support -~~~~~~~~~~~ -DMA controllers enumerated via ACPI should be registered in the system to -provide generic access to their resources. For example, a driver that would -like to be accessible to slave devices via generic API call -dma_request_slave_channel() must register itself at the end of the probe -function like this: - - err = devm_acpi_dma_controller_register(dev, xlate_func, dw); - /* Handle the error if it's not a case of !CONFIG_ACPI */ - -and implement custom xlate function if needed (usually acpi_dma_simple_xlate() -is enough) which converts the FixedDMA resource provided by struct -acpi_dma_spec into the corresponding DMA channel. A piece of code for that case -could look like: - - #ifdef CONFIG_ACPI - struct filter_args { - /* Provide necessary information for the filter_func */ - ... - }; - - static bool filter_func(struct dma_chan *chan, void *param) - { - /* Choose the proper channel */ - ... - } - - static struct dma_chan *xlate_func(struct acpi_dma_spec *dma_spec, - struct acpi_dma *adma) - { - dma_cap_mask_t cap; - struct filter_args args; - - /* Prepare arguments for filter_func */ - ... - return dma_request_channel(cap, filter_func, &args); - } - #else - static struct dma_chan *xlate_func(struct acpi_dma_spec *dma_spec, - struct acpi_dma *adma) - { - return NULL; - } - #endif - -dma_request_slave_channel() will call xlate_func() for each registered DMA -controller. In the xlate function the proper channel must be chosen based on -information in struct acpi_dma_spec and the properties of the controller -provided by struct acpi_dma. - -Clients must call dma_request_slave_channel() with the string parameter that -corresponds to a specific FixedDMA resource. By default "tx" means the first -entry of the FixedDMA resource array, "rx" means the second entry. The table -below shows a layout: - - Device (I2C0) - { - ... - Method (_CRS, 0, NotSerialized) - { - Name (DBUF, ResourceTemplate () - { - FixedDMA (0x0018, 0x0004, Width32bit, _Y48) - FixedDMA (0x0019, 0x0005, Width32bit, ) - }) - ... - } - } - -So, the FixedDMA with request line 0x0018 is "tx" and next one is "rx" in -this example. - -In robust cases the client unfortunately needs to call -acpi_dma_request_slave_chan_by_index() directly and therefore choose the -specific FixedDMA resource by its index. - -SPI serial bus support -~~~~~~~~~~~~~~~~~~~~~~ -Slave devices behind SPI bus have SpiSerialBus resource attached to them. -This is extracted automatically by the SPI core and the slave devices are -enumerated once spi_register_master() is called by the bus driver. - -Here is what the ACPI namespace for a SPI slave might look like: - - Device (EEP0) - { - Name (_ADR, 1) - Name (_CID, Package() { - "ATML0025", - "AT25", - }) - ... - Method (_CRS, 0, NotSerialized) - { - SPISerialBus(1, PolarityLow, FourWireMode, 8, - ControllerInitiated, 1000000, ClockPolarityLow, - ClockPhaseFirst, "\\_SB.PCI0.SPI1",) - } - ... - -The SPI device drivers only need to add ACPI IDs in a similar way than with -the platform device drivers. Below is an example where we add ACPI support -to at25 SPI eeprom driver (this is meant for the above ACPI snippet): - - #ifdef CONFIG_ACPI - static const struct acpi_device_id at25_acpi_match[] = { - { "AT25", 0 }, - { }, - }; - MODULE_DEVICE_TABLE(acpi, at25_acpi_match); - #endif - - static struct spi_driver at25_driver = { - .driver = { - ... - .acpi_match_table = ACPI_PTR(at25_acpi_match), - }, - }; - -Note that this driver actually needs more information like page size of the -eeprom etc. but at the time writing this there is no standard way of -passing those. One idea is to return this in _DSM method like: - - Device (EEP0) - { - ... - Method (_DSM, 4, NotSerialized) - { - Store (Package (6) - { - "byte-len", 1024, - "addr-mode", 2, - "page-size, 32 - }, Local0) - - // Check UUIDs etc. - - Return (Local0) - } - -Then the at25 SPI driver can get this configuration by calling _DSM on its -ACPI handle like: - - struct acpi_buffer output = { ACPI_ALLOCATE_BUFFER, NULL }; - struct acpi_object_list input; - acpi_status status; - - /* Fill in the input buffer */ - - status = acpi_evaluate_object(ACPI_HANDLE(&spi->dev), "_DSM", - &input, &output); - if (ACPI_FAILURE(status)) - /* Handle the error */ - - /* Extract the data here */ - - kfree(output.pointer); - -I2C serial bus support -~~~~~~~~~~~~~~~~~~~~~~ -The slaves behind I2C bus controller only need to add the ACPI IDs like -with the platform and SPI drivers. The I2C core automatically enumerates -any slave devices behind the controller device once the adapter is -registered. - -Below is an example of how to add ACPI support to the existing mpu3050 -input driver: - - #ifdef CONFIG_ACPI - static const struct acpi_device_id mpu3050_acpi_match[] = { - { "MPU3050", 0 }, - { }, - }; - MODULE_DEVICE_TABLE(acpi, mpu3050_acpi_match); - #endif - - static struct i2c_driver mpu3050_i2c_driver = { - .driver = { - .name = "mpu3050", - .owner = THIS_MODULE, - .pm = &mpu3050_pm, - .of_match_table = mpu3050_of_match, - .acpi_match_table = ACPI_PTR(mpu3050_acpi_match), - }, - .probe = mpu3050_probe, - .remove = mpu3050_remove, - .id_table = mpu3050_ids, - }; - -GPIO support -~~~~~~~~~~~~ -ACPI 5 introduced two new resources to describe GPIO connections: GpioIo -and GpioInt. These resources can be used to pass GPIO numbers used by -the device to the driver. ACPI 5.1 extended this with _DSD (Device -Specific Data) which made it possible to name the GPIOs among other things. - -For example: - -Device (DEV) -{ - Method (_CRS, 0, NotSerialized) - { - Name (SBUF, ResourceTemplate() - { - ... - // Used to power on/off the device - GpioIo (Exclusive, PullDefault, 0x0000, 0x0000, - IoRestrictionOutputOnly, "\\_SB.PCI0.GPI0", - 0x00, ResourceConsumer,,) - { - // Pin List - 0x0055 - } - - // Interrupt for the device - GpioInt (Edge, ActiveHigh, ExclusiveAndWake, PullNone, - 0x0000, "\\_SB.PCI0.GPI0", 0x00, ResourceConsumer,,) - { - // Pin list - 0x0058 - } - - ... - - } - - Return (SBUF) - } - - // ACPI 5.1 _DSD used for naming the GPIOs - Name (_DSD, Package () - { - ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), - Package () - { - Package () {"power-gpios", Package() {^DEV, 0, 0, 0 }}, - Package () {"irq-gpios", Package() {^DEV, 1, 0, 0 }}, - } - }) - ... - -These GPIO numbers are controller relative and path "\\_SB.PCI0.GPI0" -specifies the path to the controller. In order to use these GPIOs in Linux -we need to translate them to the corresponding Linux GPIO descriptors. - -There is a standard GPIO API for that and is documented in -Documentation/gpio/. - -In the above example we can get the corresponding two GPIO descriptors with -a code like this: - - #include - ... - - struct gpio_desc *irq_desc, *power_desc; - - irq_desc = gpiod_get(dev, "irq"); - if (IS_ERR(irq_desc)) - /* handle error */ - - power_desc = gpiod_get(dev, "power"); - if (IS_ERR(power_desc)) - /* handle error */ - - /* Now we can use the GPIO descriptors */ - -There are also devm_* versions of these functions which release the -descriptors once the device is released. - -See Documentation/acpi/gpio-properties.txt for more information about the -_DSD binding related to GPIOs. - -MFD devices -~~~~~~~~~~~ -The MFD devices register their children as platform devices. For the child -devices there needs to be an ACPI handle that they can use to reference -parts of the ACPI namespace that relate to them. In the Linux MFD subsystem -we provide two ways: - - o The children share the parent ACPI handle. - o The MFD cell can specify the ACPI id of the device. - -For the first case, the MFD drivers do not need to do anything. The -resulting child platform device will have its ACPI_COMPANION() set to point -to the parent device. - -If the ACPI namespace has a device that we can match using an ACPI id or ACPI -adr, the cell should be set like: - - static struct mfd_cell_acpi_match my_subdevice_cell_acpi_match = { - .pnpid = "XYZ0001", - .adr = 0, - }; - - static struct mfd_cell my_subdevice_cell = { - .name = "my_subdevice", - /* set the resources relative to the parent */ - .acpi_match = &my_subdevice_cell_acpi_match, - }; - -The ACPI id "XYZ0001" is then used to lookup an ACPI device directly under -the MFD device and if found, that ACPI companion device is bound to the -resulting child platform device. - -Device Tree namespace link device ID -~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ -The Device Tree protocol uses device identification based on the "compatible" -property whose value is a string or an array of strings recognized as device -identifiers by drivers and the driver core. The set of all those strings may be -regarded as a device identification namespace analogous to the ACPI/PNP device -ID namespace. Consequently, in principle it should not be necessary to allocate -a new (and arguably redundant) ACPI/PNP device ID for a devices with an existing -identification string in the Device Tree (DT) namespace, especially if that ID -is only needed to indicate that a given device is compatible with another one, -presumably having a matching driver in the kernel already. - -In ACPI, the device identification object called _CID (Compatible ID) is used to -list the IDs of devices the given one is compatible with, but those IDs must -belong to one of the namespaces prescribed by the ACPI specification (see -Section 6.1.2 of ACPI 6.0 for details) and the DT namespace is not one of them. -Moreover, the specification mandates that either a _HID or an _ADR identification -object be present for all ACPI objects representing devices (Section 6.1 of ACPI -6.0). For non-enumerable bus types that object must be _HID and its value must -be a device ID from one of the namespaces prescribed by the specification too. - -The special DT namespace link device ID, PRP0001, provides a means to use the -existing DT-compatible device identification in ACPI and to satisfy the above -requirements following from the ACPI specification at the same time. Namely, -if PRP0001 is returned by _HID, the ACPI subsystem will look for the -"compatible" property in the device object's _DSD and will use the value of that -property to identify the corresponding device in analogy with the original DT -device identification algorithm. If the "compatible" property is not present -or its value is not valid, the device will not be enumerated by the ACPI -subsystem. Otherwise, it will be enumerated automatically as a platform device -(except when an I2C or SPI link from the device to its parent is present, in -which case the ACPI core will leave the device enumeration to the parent's -driver) and the identification strings from the "compatible" property value will -be used to find a driver for the device along with the device IDs listed by _CID -(if present). - -Analogously, if PRP0001 is present in the list of device IDs returned by _CID, -the identification strings listed by the "compatible" property value (if present -and valid) will be used to look for a driver matching the device, but in that -case their relative priority with respect to the other device IDs listed by -_HID and _CID depends on the position of PRP0001 in the _CID return package. -Specifically, the device IDs returned by _HID and preceding PRP0001 in the _CID -return package will be checked first. Also in that case the bus type the device -will be enumerated to depends on the device ID returned by _HID. - -For example, the following ACPI sample might be used to enumerate an lm75-type -I2C temperature sensor and match it to the driver using the Device Tree -namespace link: - - Device (TMP0) - { - Name (_HID, "PRP0001") - Name (_DSD, Package() { - ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), - Package () { - Package (2) { "compatible", "ti,tmp75" }, - } - }) - Method (_CRS, 0, Serialized) - { - Name (SBUF, ResourceTemplate () - { - I2cSerialBusV2 (0x48, ControllerInitiated, - 400000, AddressingMode7Bit, - "\\_SB.PCI0.I2C1", 0x00, - ResourceConsumer, , Exclusive,) - }) - Return (SBUF) - } - } - -It is valid to define device objects with a _HID returning PRP0001 and without -the "compatible" property in the _DSD or a _CID as long as one of their -ancestors provides a _DSD with a valid "compatible" property. Such device -objects are then simply regarded as additional "blocks" providing hierarchical -configuration information to the driver of the composite ancestor device. - -However, PRP0001 can only be returned from either _HID or _CID of a device -object if all of the properties returned by the _DSD associated with it (either -the _DSD of the device object itself or the _DSD of its ancestor in the -"composite device" case described above) can be used in the ACPI environment. -Otherwise, the _DSD itself is regarded as invalid and therefore the "compatible" -property returned by it is meaningless. - -Refer to DSD-properties-rules.txt for more information. diff --git a/Documentation/firmware-guide/acpi/enumeration.rst b/Documentation/firmware-guide/acpi/enumeration.rst new file mode 100644 index 000000000000..6b32b7be8c85 --- /dev/null +++ b/Documentation/firmware-guide/acpi/enumeration.rst @@ -0,0 +1,463 @@ +.. SPDX-License-Identifier: GPL-2.0 + +============================= +ACPI Based Device Enumeration +============================= + +ACPI 5 introduced a set of new resources (UartTSerialBus, I2cSerialBus, +SpiSerialBus, GpioIo and GpioInt) which can be used in enumerating slave +devices behind serial bus controllers. + +In addition we are starting to see peripherals integrated in the +SoC/Chipset to appear only in ACPI namespace. These are typically devices +that are accessed through memory-mapped registers. + +In order to support this and re-use the existing drivers as much as +possible we decided to do following: + + - Devices that have no bus connector resource are represented as + platform devices. + + - Devices behind real busses where there is a connector resource + are represented as struct spi_device or struct i2c_device + (standard UARTs are not busses so there is no struct uart_device). + +As both ACPI and Device Tree represent a tree of devices (and their +resources) this implementation follows the Device Tree way as much as +possible. + +The ACPI implementation enumerates devices behind busses (platform, SPI and +I2C), creates the physical devices and binds them to their ACPI handle in +the ACPI namespace. + +This means that when ACPI_HANDLE(dev) returns non-NULL the device was +enumerated from ACPI namespace. This handle can be used to extract other +device-specific configuration. There is an example of this below. + +Platform bus support +==================== + +Since we are using platform devices to represent devices that are not +connected to any physical bus we only need to implement a platform driver +for the device and add supported ACPI IDs. If this same IP-block is used on +some other non-ACPI platform, the driver might work out of the box or needs +some minor changes. + +Adding ACPI support for an existing driver should be pretty +straightforward. Here is the simplest example:: + + #ifdef CONFIG_ACPI + static const struct acpi_device_id mydrv_acpi_match[] = { + /* ACPI IDs here */ + { } + }; + MODULE_DEVICE_TABLE(acpi, mydrv_acpi_match); + #endif + + static struct platform_driver my_driver = { + ... + .driver = { + .acpi_match_table = ACPI_PTR(mydrv_acpi_match), + }, + }; + +If the driver needs to perform more complex initialization like getting and +configuring GPIOs it can get its ACPI handle and extract this information +from ACPI tables. + +DMA support +=========== + +DMA controllers enumerated via ACPI should be registered in the system to +provide generic access to their resources. For example, a driver that would +like to be accessible to slave devices via generic API call +dma_request_slave_channel() must register itself at the end of the probe +function like this:: + + err = devm_acpi_dma_controller_register(dev, xlate_func, dw); + /* Handle the error if it's not a case of !CONFIG_ACPI */ + +and implement custom xlate function if needed (usually acpi_dma_simple_xlate() +is enough) which converts the FixedDMA resource provided by struct +acpi_dma_spec into the corresponding DMA channel. A piece of code for that case +could look like:: + + #ifdef CONFIG_ACPI + struct filter_args { + /* Provide necessary information for the filter_func */ + ... + }; + + static bool filter_func(struct dma_chan *chan, void *param) + { + /* Choose the proper channel */ + ... + } + + static struct dma_chan *xlate_func(struct acpi_dma_spec *dma_spec, + struct acpi_dma *adma) + { + dma_cap_mask_t cap; + struct filter_args args; + + /* Prepare arguments for filter_func */ + ... + return dma_request_channel(cap, filter_func, &args); + } + #else + static struct dma_chan *xlate_func(struct acpi_dma_spec *dma_spec, + struct acpi_dma *adma) + { + return NULL; + } + #endif + +dma_request_slave_channel() will call xlate_func() for each registered DMA +controller. In the xlate function the proper channel must be chosen based on +information in struct acpi_dma_spec and the properties of the controller +provided by struct acpi_dma. + +Clients must call dma_request_slave_channel() with the string parameter that +corresponds to a specific FixedDMA resource. By default "tx" means the first +entry of the FixedDMA resource array, "rx" means the second entry. The table +below shows a layout:: + + Device (I2C0) + { + ... + Method (_CRS, 0, NotSerialized) + { + Name (DBUF, ResourceTemplate () + { + FixedDMA (0x0018, 0x0004, Width32bit, _Y48) + FixedDMA (0x0019, 0x0005, Width32bit, ) + }) + ... + } + } + +So, the FixedDMA with request line 0x0018 is "tx" and next one is "rx" in +this example. + +In robust cases the client unfortunately needs to call +acpi_dma_request_slave_chan_by_index() directly and therefore choose the +specific FixedDMA resource by its index. + +SPI serial bus support +====================== + +Slave devices behind SPI bus have SpiSerialBus resource attached to them. +This is extracted automatically by the SPI core and the slave devices are +enumerated once spi_register_master() is called by the bus driver. + +Here is what the ACPI namespace for a SPI slave might look like:: + + Device (EEP0) + { + Name (_ADR, 1) + Name (_CID, Package() { + "ATML0025", + "AT25", + }) + ... + Method (_CRS, 0, NotSerialized) + { + SPISerialBus(1, PolarityLow, FourWireMode, 8, + ControllerInitiated, 1000000, ClockPolarityLow, + ClockPhaseFirst, "\\_SB.PCI0.SPI1",) + } + ... + +The SPI device drivers only need to add ACPI IDs in a similar way than with +the platform device drivers. Below is an example where we add ACPI support +to at25 SPI eeprom driver (this is meant for the above ACPI snippet):: + + #ifdef CONFIG_ACPI + static const struct acpi_device_id at25_acpi_match[] = { + { "AT25", 0 }, + { }, + }; + MODULE_DEVICE_TABLE(acpi, at25_acpi_match); + #endif + + static struct spi_driver at25_driver = { + .driver = { + ... + .acpi_match_table = ACPI_PTR(at25_acpi_match), + }, + }; + +Note that this driver actually needs more information like page size of the +eeprom etc. but at the time writing this there is no standard way of +passing those. One idea is to return this in _DSM method like:: + + Device (EEP0) + { + ... + Method (_DSM, 4, NotSerialized) + { + Store (Package (6) + { + "byte-len", 1024, + "addr-mode", 2, + "page-size, 32 + }, Local0) + + // Check UUIDs etc. + + Return (Local0) + } + +Then the at25 SPI driver can get this configuration by calling _DSM on its +ACPI handle like:: + + struct acpi_buffer output = { ACPI_ALLOCATE_BUFFER, NULL }; + struct acpi_object_list input; + acpi_status status; + + /* Fill in the input buffer */ + + status = acpi_evaluate_object(ACPI_HANDLE(&spi->dev), "_DSM", + &input, &output); + if (ACPI_FAILURE(status)) + /* Handle the error */ + + /* Extract the data here */ + + kfree(output.pointer); + +I2C serial bus support +====================== + +The slaves behind I2C bus controller only need to add the ACPI IDs like +with the platform and SPI drivers. The I2C core automatically enumerates +any slave devices behind the controller device once the adapter is +registered. + +Below is an example of how to add ACPI support to the existing mpu3050 +input driver:: + + #ifdef CONFIG_ACPI + static const struct acpi_device_id mpu3050_acpi_match[] = { + { "MPU3050", 0 }, + { }, + }; + MODULE_DEVICE_TABLE(acpi, mpu3050_acpi_match); + #endif + + static struct i2c_driver mpu3050_i2c_driver = { + .driver = { + .name = "mpu3050", + .owner = THIS_MODULE, + .pm = &mpu3050_pm, + .of_match_table = mpu3050_of_match, + .acpi_match_table = ACPI_PTR(mpu3050_acpi_match), + }, + .probe = mpu3050_probe, + .remove = mpu3050_remove, + .id_table = mpu3050_ids, + }; + +GPIO support +============ + +ACPI 5 introduced two new resources to describe GPIO connections: GpioIo +and GpioInt. These resources can be used to pass GPIO numbers used by +the device to the driver. ACPI 5.1 extended this with _DSD (Device +Specific Data) which made it possible to name the GPIOs among other things. + +For example:: + + Device (DEV) + { + Method (_CRS, 0, NotSerialized) + { + Name (SBUF, ResourceTemplate() + { + ... + // Used to power on/off the device + GpioIo (Exclusive, PullDefault, 0x0000, 0x0000, + IoRestrictionOutputOnly, "\\_SB.PCI0.GPI0", + 0x00, ResourceConsumer,,) + { + // Pin List + 0x0055 + } + + // Interrupt for the device + GpioInt (Edge, ActiveHigh, ExclusiveAndWake, PullNone, + 0x0000, "\\_SB.PCI0.GPI0", 0x00, ResourceConsumer,,) + { + // Pin list + 0x0058 + } + + ... + + } + + Return (SBUF) + } + + // ACPI 5.1 _DSD used for naming the GPIOs + Name (_DSD, Package () + { + ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), + Package () + { + Package () {"power-gpios", Package() {^DEV, 0, 0, 0 }}, + Package () {"irq-gpios", Package() {^DEV, 1, 0, 0 }}, + } + }) + ... + +These GPIO numbers are controller relative and path "\\_SB.PCI0.GPI0" +specifies the path to the controller. In order to use these GPIOs in Linux +we need to translate them to the corresponding Linux GPIO descriptors. + +There is a standard GPIO API for that and is documented in +Documentation/gpio/. + +In the above example we can get the corresponding two GPIO descriptors with +a code like this:: + + #include + ... + + struct gpio_desc *irq_desc, *power_desc; + + irq_desc = gpiod_get(dev, "irq"); + if (IS_ERR(irq_desc)) + /* handle error */ + + power_desc = gpiod_get(dev, "power"); + if (IS_ERR(power_desc)) + /* handle error */ + + /* Now we can use the GPIO descriptors */ + +There are also devm_* versions of these functions which release the +descriptors once the device is released. + +See Documentation/acpi/gpio-properties.txt for more information about the +_DSD binding related to GPIOs. + +MFD devices +=========== + +The MFD devices register their children as platform devices. For the child +devices there needs to be an ACPI handle that they can use to reference +parts of the ACPI namespace that relate to them. In the Linux MFD subsystem +we provide two ways: + + - The children share the parent ACPI handle. + - The MFD cell can specify the ACPI id of the device. + +For the first case, the MFD drivers do not need to do anything. The +resulting child platform device will have its ACPI_COMPANION() set to point +to the parent device. + +If the ACPI namespace has a device that we can match using an ACPI id or ACPI +adr, the cell should be set like:: + + static struct mfd_cell_acpi_match my_subdevice_cell_acpi_match = { + .pnpid = "XYZ0001", + .adr = 0, + }; + + static struct mfd_cell my_subdevice_cell = { + .name = "my_subdevice", + /* set the resources relative to the parent */ + .acpi_match = &my_subdevice_cell_acpi_match, + }; + +The ACPI id "XYZ0001" is then used to lookup an ACPI device directly under +the MFD device and if found, that ACPI companion device is bound to the +resulting child platform device. + +Device Tree namespace link device ID +==================================== + +The Device Tree protocol uses device identification based on the "compatible" +property whose value is a string or an array of strings recognized as device +identifiers by drivers and the driver core. The set of all those strings may be +regarded as a device identification namespace analogous to the ACPI/PNP device +ID namespace. Consequently, in principle it should not be necessary to allocate +a new (and arguably redundant) ACPI/PNP device ID for a devices with an existing +identification string in the Device Tree (DT) namespace, especially if that ID +is only needed to indicate that a given device is compatible with another one, +presumably having a matching driver in the kernel already. + +In ACPI, the device identification object called _CID (Compatible ID) is used to +list the IDs of devices the given one is compatible with, but those IDs must +belong to one of the namespaces prescribed by the ACPI specification (see +Section 6.1.2 of ACPI 6.0 for details) and the DT namespace is not one of them. +Moreover, the specification mandates that either a _HID or an _ADR identification +object be present for all ACPI objects representing devices (Section 6.1 of ACPI +6.0). For non-enumerable bus types that object must be _HID and its value must +be a device ID from one of the namespaces prescribed by the specification too. + +The special DT namespace link device ID, PRP0001, provides a means to use the +existing DT-compatible device identification in ACPI and to satisfy the above +requirements following from the ACPI specification at the same time. Namely, +if PRP0001 is returned by _HID, the ACPI subsystem will look for the +"compatible" property in the device object's _DSD and will use the value of that +property to identify the corresponding device in analogy with the original DT +device identification algorithm. If the "compatible" property is not present +or its value is not valid, the device will not be enumerated by the ACPI +subsystem. Otherwise, it will be enumerated automatically as a platform device +(except when an I2C or SPI link from the device to its parent is present, in +which case the ACPI core will leave the device enumeration to the parent's +driver) and the identification strings from the "compatible" property value will +be used to find a driver for the device along with the device IDs listed by _CID +(if present). + +Analogously, if PRP0001 is present in the list of device IDs returned by _CID, +the identification strings listed by the "compatible" property value (if present +and valid) will be used to look for a driver matching the device, but in that +case their relative priority with respect to the other device IDs listed by +_HID and _CID depends on the position of PRP0001 in the _CID return package. +Specifically, the device IDs returned by _HID and preceding PRP0001 in the _CID +return package will be checked first. Also in that case the bus type the device +will be enumerated to depends on the device ID returned by _HID. + +For example, the following ACPI sample might be used to enumerate an lm75-type +I2C temperature sensor and match it to the driver using the Device Tree +namespace link: + + Device (TMP0) + { + Name (_HID, "PRP0001") + Name (_DSD, Package() { + ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), + Package () { + Package (2) { "compatible", "ti,tmp75" }, + } + }) + Method (_CRS, 0, Serialized) + { + Name (SBUF, ResourceTemplate () + { + I2cSerialBusV2 (0x48, ControllerInitiated, + 400000, AddressingMode7Bit, + "\\_SB.PCI0.I2C1", 0x00, + ResourceConsumer, , Exclusive,) + }) + Return (SBUF) + } + } + +It is valid to define device objects with a _HID returning PRP0001 and without +the "compatible" property in the _DSD or a _CID as long as one of their +ancestors provides a _DSD with a valid "compatible" property. Such device +objects are then simply regarded as additional "blocks" providing hierarchical +configuration information to the driver of the composite ancestor device. + +However, PRP0001 can only be returned from either _HID or _CID of a device +object if all of the properties returned by the _DSD associated with it (either +the _DSD of the device object itself or the _DSD of its ancestor in the +"composite device" case described above) can be used in the ACPI environment. +Otherwise, the _DSD itself is regarded as invalid and therefore the "compatible" +property returned by it is meaningless. + +Refer to :doc:`DSD-properties-rules` for more information. diff --git a/Documentation/firmware-guide/acpi/index.rst b/Documentation/firmware-guide/acpi/index.rst index 210ad8acd6df..99677c73f1fb 100644 --- a/Documentation/firmware-guide/acpi/index.rst +++ b/Documentation/firmware-guide/acpi/index.rst @@ -8,3 +8,4 @@ ACPI Support :maxdepth: 1 namespace + enumeration -- cgit v1.2.3 From 1cf70ae6f07b071affcd4e324803e928e3336a8d Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 01:52:46 +0800 Subject: Documentation: ACPI: move osi.txt to firmware-guide/acpi and convert to reST This converts the plain text documentation to reStructuredText format and adds it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/osi.txt | 187 --------------------------- Documentation/firmware-guide/acpi/index.rst | 1 + Documentation/firmware-guide/acpi/osi.rst | 190 ++++++++++++++++++++++++++++ 3 files changed, 191 insertions(+), 187 deletions(-) delete mode 100644 Documentation/acpi/osi.txt create mode 100644 Documentation/firmware-guide/acpi/osi.rst (limited to 'Documentation') diff --git a/Documentation/acpi/osi.txt b/Documentation/acpi/osi.txt deleted file mode 100644 index 50cde0ceb9b0..000000000000 --- a/Documentation/acpi/osi.txt +++ /dev/null @@ -1,187 +0,0 @@ -ACPI _OSI and _REV methods --------------------------- - -An ACPI BIOS can use the "Operating System Interfaces" method (_OSI) -to find out what the operating system supports. Eg. If BIOS -AML code includes _OSI("XYZ"), the kernel's AML interpreter -can evaluate that method, look to see if it supports 'XYZ' -and answer YES or NO to the BIOS. - -The ACPI _REV method returns the "Revision of the ACPI specification -that OSPM supports" - -This document explains how and why the BIOS and Linux should use these methods. -It also explains how and why they are widely misused. - -How to use _OSI ---------------- - -Linux runs on two groups of machines -- those that are tested by the OEM -to be compatible with Linux, and those that were never tested with Linux, -but where Linux was installed to replace the original OS (Windows or OSX). - -The larger group is the systems tested to run only Windows. Not only that, -but many were tested to run with just one specific version of Windows. -So even though the BIOS may use _OSI to query what version of Windows is running, -only a single path through the BIOS has actually been tested. -Experience shows that taking untested paths through the BIOS -exposes Linux to an entire category of BIOS bugs. -For this reason, Linux _OSI defaults must continue to claim compatibility -with all versions of Windows. - -But Linux isn't actually compatible with Windows, and the Linux community -has also been hurt with regressions when Linux adds the latest version of -Windows to its list of _OSI strings. So it is possible that additional strings -will be more thoroughly vetted before shipping upstream in the future. -But it is likely that they will all eventually be added. - -What should an OEM do if they want to support Linux and Windows -using the same BIOS image? Often they need to do something different -for Linux to deal with how Linux is different from Windows. -Here the BIOS should ask exactly what it wants to know: - -_OSI("Linux-OEM-my_interface_name") -where 'OEM' is needed if this is an OEM-specific hook, -and 'my_interface_name' describes the hook, which could be a -quirk, a bug, or a bug-fix. - -In addition, the OEM should send a patch to upstream Linux -via the linux-acpi@vger.kernel.org mailing list. When that patch -is checked into Linux, the OS will answer "YES" when the BIOS -on the OEM's system uses _OSI to ask if the interface is supported -by the OS. Linux distributors can back-port that patch for Linux -pre-installs, and it will be included by all distributions that -re-base to upstream. If the distribution can not update the kernel binary, -they can also add an acpi_osi=Linux-OEM-my_interface_name -cmdline parameter to the boot loader, as needed. - -If the string refers to a feature where the upstream kernel -eventually grows support, a patch should be sent to remove -the string when that support is added to the kernel. - -That was easy. Read on, to find out how to do it wrong. - -Before _OSI, there was _OS --------------------------- - -ACPI 1.0 specified "_OS" as an -"object that evaluates to a string that identifies the operating system." - -The ACPI BIOS flow would include an evaluation of _OS, and the AML -interpreter in the kernel would return to it a string identifying the OS: - -Windows 98, SE: "Microsoft Windows" -Windows ME: "Microsoft WindowsME:Millenium Edition" -Windows NT: "Microsoft Windows NT" - -The idea was on a platform tasked with running multiple OS's, -the BIOS could use _OS to enable devices that an OS -might support, or enable quirks or bug workarounds -necessary to make the platform compatible with that pre-existing OS. - -But _OS had fundamental problems. First, the BIOS needed to know the name -of every possible version of the OS that would run on it, and needed to know -all the quirks of those OS's. Certainly it would make more sense -for the BIOS to ask *specific* things of the OS, such -"do you support a specific interface", and thus in ACPI 3.0, -_OSI was born to replace _OS. - -_OS was abandoned, though even today, many BIOS look for -_OS "Microsoft Windows NT", though it seems somewhat far-fetched -that anybody would install those old operating systems -over what came with the machine. - -Linux answers "Microsoft Windows NT" to please that BIOS idiom. -That is the *only* viable strategy, as that is what modern Windows does, -and so doing otherwise could steer the BIOS down an untested path. - -_OSI is born, and immediately misused --------------------------------------- - -With _OSI, the *BIOS* provides the string describing an interface, -and asks the OS: "YES/NO, are you compatible with this interface?" - -eg. _OSI("3.0 Thermal Model") would return TRUE if the OS knows how -to deal with the thermal extensions made to the ACPI 3.0 specification. -An old OS that doesn't know about those extensions would answer FALSE, -and a new OS may be able to return TRUE. - -For an OS-specific interface, the ACPI spec said that the BIOS and the OS -were to agree on a string of the form such as "Windows-interface_name". - -But two bad things happened. First, the Windows ecosystem used _OSI -not as designed, but as a direct replacement for _OS -- identifying -the OS version, rather than an OS supported interface. Indeed, right -from the start, the ACPI 3.0 spec itself codified this misuse -in example code using _OSI("Windows 2001"). - -This misuse was adopted and continues today. - -Linux had no choice but to also return TRUE to _OSI("Windows 2001") -and its successors. To do otherwise would virtually guarantee breaking -a BIOS that has been tested only with that _OSI returning TRUE. - -This strategy is problematic, as Linux is never completely compatible with -the latest version of Windows, and sometimes it takes more than a year -to iron out incompatibilities. - -Not to be out-done, the Linux community made things worse by returning TRUE -to _OSI("Linux"). Doing so is even worse than the Windows misuse -of _OSI, as "Linux" does not even contain any version information. -_OSI("Linux") led to some BIOS' malfunctioning due to BIOS writer's -using it in untested BIOS flows. But some OEM's used _OSI("Linux") -in tested flows to support real Linux features. In 2009, Linux -removed _OSI("Linux"), and added a cmdline parameter to restore it -for legacy systems still needed it. Further a BIOS_BUG warning prints -for all BIOS's that invoke it. - -No BIOS should use _OSI("Linux"). - -The result is a strategy for Linux to maximize compatibility with -ACPI BIOS that are tested on Windows machines. There is a real risk -of over-stating that compatibility; but the alternative has often been -catastrophic failure resulting from the BIOS taking paths that -were never validated under *any* OS. - -Do not use _REV ---------------- - -Since _OSI("Linux") went away, some BIOS writers used _REV -to support Linux and Windows differences in the same BIOS. - -_REV was defined in ACPI 1.0 to return the version of ACPI -supported by the OS and the OS AML interpreter. - -Modern Windows returns _REV = 2. Linux used ACPI_CA_SUPPORT_LEVEL, -which would increment, based on the version of the spec supported. - -Unfortunately, _REV was also misused. eg. some BIOS would check -for _REV = 3, and do something for Linux, but when Linux returned -_REV = 4, that support broke. - -In response to this problem, Linux returns _REV = 2 always, -from mid-2015 onward. The ACPI specification will also be updated -to reflect that _REV is deprecated, and always returns 2. - -Apple Mac and _OSI("Darwin") ----------------------------- - -On Apple's Mac platforms, the ACPI BIOS invokes _OSI("Darwin") -to determine if the machine is running Apple OSX. - -Like Linux's _OSI("*Windows*") strategy, Linux defaults to -answering YES to _OSI("Darwin") to enable full access -to the hardware and validated BIOS paths seen by OSX. -Just like on Windows-tested platforms, this strategy has risks. - -Starting in Linux-3.18, the kernel answered YES to _OSI("Darwin") -for the purpose of enabling Mac Thunderbolt support. Further, -if the kernel noticed _OSI("Darwin") being invoked, it additionally -disabled all _OSI("*Windows*") to keep poorly written Mac BIOS -from going down untested combinations of paths. - -The Linux-3.18 change in default caused power regressions on Mac -laptops, and the 3.18 implementation did not allow changing -the default via cmdline "acpi_osi=!Darwin". Linux-4.7 fixed -the ability to use acpi_osi=!Darwin as a workaround, and -we hope to see Mac Thunderbolt power management support in Linux-4.11. diff --git a/Documentation/firmware-guide/acpi/index.rst b/Documentation/firmware-guide/acpi/index.rst index 99677c73f1fb..868bd25a3398 100644 --- a/Documentation/firmware-guide/acpi/index.rst +++ b/Documentation/firmware-guide/acpi/index.rst @@ -9,3 +9,4 @@ ACPI Support namespace enumeration + osi diff --git a/Documentation/firmware-guide/acpi/osi.rst b/Documentation/firmware-guide/acpi/osi.rst new file mode 100644 index 000000000000..29e9ef79ebc0 --- /dev/null +++ b/Documentation/firmware-guide/acpi/osi.rst @@ -0,0 +1,190 @@ +.. SPDX-License-Identifier: GPL-2.0 + +========================== +ACPI _OSI and _REV methods +========================== + +An ACPI BIOS can use the "Operating System Interfaces" method (_OSI) +to find out what the operating system supports. Eg. If BIOS +AML code includes _OSI("XYZ"), the kernel's AML interpreter +can evaluate that method, look to see if it supports 'XYZ' +and answer YES or NO to the BIOS. + +The ACPI _REV method returns the "Revision of the ACPI specification +that OSPM supports" + +This document explains how and why the BIOS and Linux should use these methods. +It also explains how and why they are widely misused. + +How to use _OSI +=============== + +Linux runs on two groups of machines -- those that are tested by the OEM +to be compatible with Linux, and those that were never tested with Linux, +but where Linux was installed to replace the original OS (Windows or OSX). + +The larger group is the systems tested to run only Windows. Not only that, +but many were tested to run with just one specific version of Windows. +So even though the BIOS may use _OSI to query what version of Windows is running, +only a single path through the BIOS has actually been tested. +Experience shows that taking untested paths through the BIOS +exposes Linux to an entire category of BIOS bugs. +For this reason, Linux _OSI defaults must continue to claim compatibility +with all versions of Windows. + +But Linux isn't actually compatible with Windows, and the Linux community +has also been hurt with regressions when Linux adds the latest version of +Windows to its list of _OSI strings. So it is possible that additional strings +will be more thoroughly vetted before shipping upstream in the future. +But it is likely that they will all eventually be added. + +What should an OEM do if they want to support Linux and Windows +using the same BIOS image? Often they need to do something different +for Linux to deal with how Linux is different from Windows. +Here the BIOS should ask exactly what it wants to know: + +_OSI("Linux-OEM-my_interface_name") +where 'OEM' is needed if this is an OEM-specific hook, +and 'my_interface_name' describes the hook, which could be a +quirk, a bug, or a bug-fix. + +In addition, the OEM should send a patch to upstream Linux +via the linux-acpi@vger.kernel.org mailing list. When that patch +is checked into Linux, the OS will answer "YES" when the BIOS +on the OEM's system uses _OSI to ask if the interface is supported +by the OS. Linux distributors can back-port that patch for Linux +pre-installs, and it will be included by all distributions that +re-base to upstream. If the distribution can not update the kernel binary, +they can also add an acpi_osi=Linux-OEM-my_interface_name +cmdline parameter to the boot loader, as needed. + +If the string refers to a feature where the upstream kernel +eventually grows support, a patch should be sent to remove +the string when that support is added to the kernel. + +That was easy. Read on, to find out how to do it wrong. + +Before _OSI, there was _OS +========================== + +ACPI 1.0 specified "_OS" as an +"object that evaluates to a string that identifies the operating system." + +The ACPI BIOS flow would include an evaluation of _OS, and the AML +interpreter in the kernel would return to it a string identifying the OS: + +Windows 98, SE: "Microsoft Windows" +Windows ME: "Microsoft WindowsME:Millenium Edition" +Windows NT: "Microsoft Windows NT" + +The idea was on a platform tasked with running multiple OS's, +the BIOS could use _OS to enable devices that an OS +might support, or enable quirks or bug workarounds +necessary to make the platform compatible with that pre-existing OS. + +But _OS had fundamental problems. First, the BIOS needed to know the name +of every possible version of the OS that would run on it, and needed to know +all the quirks of those OS's. Certainly it would make more sense +for the BIOS to ask *specific* things of the OS, such +"do you support a specific interface", and thus in ACPI 3.0, +_OSI was born to replace _OS. + +_OS was abandoned, though even today, many BIOS look for +_OS "Microsoft Windows NT", though it seems somewhat far-fetched +that anybody would install those old operating systems +over what came with the machine. + +Linux answers "Microsoft Windows NT" to please that BIOS idiom. +That is the *only* viable strategy, as that is what modern Windows does, +and so doing otherwise could steer the BIOS down an untested path. + +_OSI is born, and immediately misused +===================================== + +With _OSI, the *BIOS* provides the string describing an interface, +and asks the OS: "YES/NO, are you compatible with this interface?" + +eg. _OSI("3.0 Thermal Model") would return TRUE if the OS knows how +to deal with the thermal extensions made to the ACPI 3.0 specification. +An old OS that doesn't know about those extensions would answer FALSE, +and a new OS may be able to return TRUE. + +For an OS-specific interface, the ACPI spec said that the BIOS and the OS +were to agree on a string of the form such as "Windows-interface_name". + +But two bad things happened. First, the Windows ecosystem used _OSI +not as designed, but as a direct replacement for _OS -- identifying +the OS version, rather than an OS supported interface. Indeed, right +from the start, the ACPI 3.0 spec itself codified this misuse +in example code using _OSI("Windows 2001"). + +This misuse was adopted and continues today. + +Linux had no choice but to also return TRUE to _OSI("Windows 2001") +and its successors. To do otherwise would virtually guarantee breaking +a BIOS that has been tested only with that _OSI returning TRUE. + +This strategy is problematic, as Linux is never completely compatible with +the latest version of Windows, and sometimes it takes more than a year +to iron out incompatibilities. + +Not to be out-done, the Linux community made things worse by returning TRUE +to _OSI("Linux"). Doing so is even worse than the Windows misuse +of _OSI, as "Linux" does not even contain any version information. +_OSI("Linux") led to some BIOS' malfunctioning due to BIOS writer's +using it in untested BIOS flows. But some OEM's used _OSI("Linux") +in tested flows to support real Linux features. In 2009, Linux +removed _OSI("Linux"), and added a cmdline parameter to restore it +for legacy systems still needed it. Further a BIOS_BUG warning prints +for all BIOS's that invoke it. + +No BIOS should use _OSI("Linux"). + +The result is a strategy for Linux to maximize compatibility with +ACPI BIOS that are tested on Windows machines. There is a real risk +of over-stating that compatibility; but the alternative has often been +catastrophic failure resulting from the BIOS taking paths that +were never validated under *any* OS. + +Do not use _REV +=============== + +Since _OSI("Linux") went away, some BIOS writers used _REV +to support Linux and Windows differences in the same BIOS. + +_REV was defined in ACPI 1.0 to return the version of ACPI +supported by the OS and the OS AML interpreter. + +Modern Windows returns _REV = 2. Linux used ACPI_CA_SUPPORT_LEVEL, +which would increment, based on the version of the spec supported. + +Unfortunately, _REV was also misused. eg. some BIOS would check +for _REV = 3, and do something for Linux, but when Linux returned +_REV = 4, that support broke. + +In response to this problem, Linux returns _REV = 2 always, +from mid-2015 onward. The ACPI specification will also be updated +to reflect that _REV is deprecated, and always returns 2. + +Apple Mac and _OSI("Darwin") +============================ + +On Apple's Mac platforms, the ACPI BIOS invokes _OSI("Darwin") +to determine if the machine is running Apple OSX. + +Like Linux's _OSI("*Windows*") strategy, Linux defaults to +answering YES to _OSI("Darwin") to enable full access +to the hardware and validated BIOS paths seen by OSX. +Just like on Windows-tested platforms, this strategy has risks. + +Starting in Linux-3.18, the kernel answered YES to _OSI("Darwin") +for the purpose of enabling Mac Thunderbolt support. Further, +if the kernel noticed _OSI("Darwin") being invoked, it additionally +disabled all _OSI("*Windows*") to keep poorly written Mac BIOS +from going down untested combinations of paths. + +The Linux-3.18 change in default caused power regressions on Mac +laptops, and the 3.18 implementation did not allow changing +the default via cmdline "acpi_osi=!Darwin". Linux-4.7 fixed +the ability to use acpi_osi=!Darwin as a workaround, and +we hope to see Mac Thunderbolt power management support in Linux-4.11. -- cgit v1.2.3 From 25710e23cdee4d4cfc140d34dd627b76be62c9c1 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 01:52:47 +0800 Subject: Documentation: ACPI: move linuxized-acpica.txt to driver-api/acpi and convert to reST This converts the plain text documentation to reStructuredText format and adds it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/linuxized-acpica.txt | 262 ------------------- Documentation/driver-api/acpi/index.rst | 1 + Documentation/driver-api/acpi/linuxized-acpica.rst | 279 +++++++++++++++++++++ 3 files changed, 280 insertions(+), 262 deletions(-) delete mode 100644 Documentation/acpi/linuxized-acpica.txt create mode 100644 Documentation/driver-api/acpi/linuxized-acpica.rst (limited to 'Documentation') diff --git a/Documentation/acpi/linuxized-acpica.txt b/Documentation/acpi/linuxized-acpica.txt deleted file mode 100644 index 3ad7b0dfb083..000000000000 --- a/Documentation/acpi/linuxized-acpica.txt +++ /dev/null @@ -1,262 +0,0 @@ -Linuxized ACPICA - Introduction to ACPICA Release Automation - -Copyright (C) 2013-2016, Intel Corporation -Author: Lv Zheng - - -Abstract: - -This document describes the ACPICA project and the relationship between -ACPICA and Linux. It also describes how ACPICA code in drivers/acpi/acpica, -include/acpi and tools/power/acpi is automatically updated to follow the -upstream. - - -1. ACPICA Project - - The ACPI Component Architecture (ACPICA) project provides an operating - system (OS)-independent reference implementation of the Advanced - Configuration and Power Interface Specification (ACPI). It has been - adapted by various host OSes. By directly integrating ACPICA, Linux can - also benefit from the application experiences of ACPICA from other host - OSes. - - The homepage of ACPICA project is: www.acpica.org, it is maintained and - supported by Intel Corporation. - - The following figure depicts the Linux ACPI subsystem where the ACPICA - adaptation is included: - - +---------------------------------------------------------+ - | | - | +---------------------------------------------------+ | - | | +------------------+ | | - | | | Table Management | | | - | | +------------------+ | | - | | +----------------------+ | | - | | | Namespace Management | | | - | | +----------------------+ | | - | | +------------------+ ACPICA Components | | - | | | Event Management | | | - | | +------------------+ | | - | | +---------------------+ | | - | | | Resource Management | | | - | | +---------------------+ | | - | | +---------------------+ | | - | | | Hardware Management | | | - | | +---------------------+ | | - | +---------------------------------------------------+ | | - | | | +------------------+ | | | - | | | | OS Service Layer | | | | - | | | +------------------+ | | | - | | +-------------------------------------------------|-+ | - | | +--------------------+ | | - | | | Device Enumeration | | | - | | +--------------------+ | | - | | +------------------+ | | - | | | Power Management | | | - | | +------------------+ Linux/ACPI Components | | - | | +--------------------+ | | - | | | Thermal Management | | | - | | +--------------------+ | | - | | +--------------------------+ | | - | | | Drivers for ACPI Devices | | | - | | +--------------------------+ | | - | | +--------+ | | - | | | ...... | | | - | | +--------+ | | - | +---------------------------------------------------+ | - | | - +---------------------------------------------------------+ - - Figure 1. Linux ACPI Software Components - - NOTE: - A. OS Service Layer - Provided by Linux to offer OS dependent - implementation of the predefined ACPICA interfaces (acpi_os_*). - include/acpi/acpiosxf.h - drivers/acpi/osl.c - include/acpi/platform - include/asm/acenv.h - B. ACPICA Functionality - Released from ACPICA code base to offer - OS independent implementation of the ACPICA interfaces (acpi_*). - drivers/acpi/acpica - include/acpi/ac*.h - tools/power/acpi - C. Linux/ACPI Functionality - Providing Linux specific ACPI - functionality to the other Linux kernel subsystems and user space - programs. - drivers/acpi - include/linux/acpi.h - include/linux/acpi*.h - include/acpi - tools/power/acpi - D. Architecture Specific ACPICA/ACPI Functionalities - Provided by the - ACPI subsystem to offer architecture specific implementation of the - ACPI interfaces. They are Linux specific components and are out of - the scope of this document. - include/asm/acpi.h - include/asm/acpi*.h - arch/*/acpi - -2. ACPICA Release - - The ACPICA project maintains its code base at the following repository URL: - https://github.com/acpica/acpica.git. As a rule, a release is made every - month. - - As the coding style adopted by the ACPICA project is not acceptable by - Linux, there is a release process to convert the ACPICA git commits into - Linux patches. The patches generated by this process are referred to as - "linuxized ACPICA patches". The release process is carried out on a local - copy the ACPICA git repository. Each commit in the monthly release is - converted into a linuxized ACPICA patch. Together, they form the monthly - ACPICA release patchset for the Linux ACPI community. This process is - illustrated in the following figure: - - +-----------------------------+ - | acpica / master (-) commits | - +-----------------------------+ - /|\ | - | \|/ - | /---------------------\ +----------------------+ - | < Linuxize repo Utility >-->| old linuxized acpica |--+ - | \---------------------/ +----------------------+ | - | | - /---------\ | - < git reset > \ - \---------/ \ - /|\ /+-+ - | / | - +-----------------------------+ | | - | acpica / master (+) commits | | | - +-----------------------------+ | | - | | | - \|/ | | - /-----------------------\ +----------------------+ | | - < Linuxize repo Utilities >-->| new linuxized acpica |--+ | - \-----------------------/ +----------------------+ | - \|/ - +--------------------------+ /----------------------\ - | Linuxized ACPICA Patches |<----------------< Linuxize patch Utility > - +--------------------------+ \----------------------/ - | - \|/ - /---------------------------\ - < Linux ACPI Community Review > - \---------------------------/ - | - \|/ - +-----------------------+ /------------------\ +----------------+ - | linux-pm / linux-next |-->< Linux Merge Window >-->| linux / master | - +-----------------------+ \------------------/ +----------------+ - - Figure 2. ACPICA -> Linux Upstream Process - - NOTE: - A. Linuxize Utilities - Provided by the ACPICA repository, including a - utility located in source/tools/acpisrc folder and a number of - scripts located in generate/linux folder. - B. acpica / master - "master" branch of the git repository at - . - C. linux-pm / linux-next - "linux-next" branch of the git repository at - . - D. linux / master - "master" branch of the git repository at - . - - Before the linuxized ACPICA patches are sent to the Linux ACPI community - for review, there is a quality assurance build test process to reduce - porting issues. Currently this build process only takes care of the - following kernel configuration options: - CONFIG_ACPI/CONFIG_ACPI_DEBUG/CONFIG_ACPI_DEBUGGER - -3. ACPICA Divergences - - Ideally, all of the ACPICA commits should be converted into Linux patches - automatically without manual modifications, the "linux / master" tree should - contain the ACPICA code that exactly corresponds to the ACPICA code - contained in "new linuxized acpica" tree and it should be possible to run - the release process fully automatically. - - As a matter of fact, however, there are source code differences between - the ACPICA code in Linux and the upstream ACPICA code, referred to as - "ACPICA Divergences". - - The various sources of ACPICA divergences include: - 1. Legacy divergences - Before the current ACPICA release process was - established, there already had been divergences between Linux and - ACPICA. Over the past several years those divergences have been greatly - reduced, but there still are several ones and it takes time to figure - out the underlying reasons for their existence. - 2. Manual modifications - Any manual modification (eg. coding style fixes) - made directly in the Linux sources obviously hurts the ACPICA release - automation. Thus it is recommended to fix such issues in the ACPICA - upstream source code and generate the linuxized fix using the ACPICA - release utilities (please refer to Section 4 below for the details). - 3. Linux specific features - Sometimes it's impossible to use the - current ACPICA APIs to implement features required by the Linux kernel, - so Linux developers occasionally have to change ACPICA code directly. - Those changes may not be acceptable by ACPICA upstream and in such cases - they are left as committed ACPICA divergences unless the ACPICA side can - implement new mechanisms as replacements for them. - 4. ACPICA release fixups - ACPICA only tests commits using a set of the - user space simulation utilities, thus the linuxized ACPICA patches may - break the Linux kernel, leaving us build/boot failures. In order to - avoid breaking Linux bisection, fixes are applied directly to the - linuxized ACPICA patches during the release process. When the release - fixups are backported to the upstream ACPICA sources, they must follow - the upstream ACPICA rules and so further modifications may appear. - That may result in the appearance of new divergences. - 5. Fast tracking of ACPICA commits - Some ACPICA commits are regression - fixes or stable-candidate material, so they are applied in advance with - respect to the ACPICA release process. If such commits are reverted or - rebased on the ACPICA side in order to offer better solutions, new ACPICA - divergences are generated. - -4. ACPICA Development - - This paragraph guides Linux developers to use the ACPICA upstream release - utilities to obtain Linux patches corresponding to upstream ACPICA commits - before they become available from the ACPICA release process. - - 1. Cherry-pick an ACPICA commit - - First you need to git clone the ACPICA repository and the ACPICA change - you want to cherry pick must be committed into the local repository. - - Then the gen-patch.sh command can help to cherry-pick an ACPICA commit - from the ACPICA local repository: - - $ git clone https://github.com/acpica/acpica - $ cd acpica - $ generate/linux/gen-patch.sh -u [commit ID] - - Here the commit ID is the ACPICA local repository commit ID you want to - cherry pick. It can be omitted if the commit is "HEAD". - - 2. Cherry-pick recent ACPICA commits - - Sometimes you need to rebase your code on top of the most recent ACPICA - changes that haven't been applied to Linux yet. - - You can generate the ACPICA release series yourself and rebase your code on - top of the generated ACPICA release patches: - - $ git clone https://github.com/acpica/acpica - $ cd acpica - $ generate/linux/make-patches.sh -u [commit ID] - - The commit ID should be the last ACPICA commit accepted by Linux. Usually, - it is the commit modifying ACPI_CA_VERSION. It can be found by executing - "git blame source/include/acpixf.h" and referencing the line that contains - "ACPI_CA_VERSION". - - 3. Inspect the current divergences - - If you have local copies of both Linux and upstream ACPICA, you can generate - a diff file indicating the state of the current divergences: - - # git clone https://github.com/acpica/acpica - # git clone http://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git - # cd acpica - # generate/linux/divergences.sh -s ../linux diff --git a/Documentation/driver-api/acpi/index.rst b/Documentation/driver-api/acpi/index.rst index 898b0c60671a..12649947b19b 100644 --- a/Documentation/driver-api/acpi/index.rst +++ b/Documentation/driver-api/acpi/index.rst @@ -5,3 +5,4 @@ ACPI Support .. toctree:: :maxdepth: 2 + linuxized-acpica diff --git a/Documentation/driver-api/acpi/linuxized-acpica.rst b/Documentation/driver-api/acpi/linuxized-acpica.rst new file mode 100644 index 000000000000..0ca8f1538519 --- /dev/null +++ b/Documentation/driver-api/acpi/linuxized-acpica.rst @@ -0,0 +1,279 @@ +.. SPDX-License-Identifier: GPL-2.0 +.. include:: + +============================================================ +Linuxized ACPICA - Introduction to ACPICA Release Automation +============================================================ + +:Copyright: |copy| 2013-2016, Intel Corporation + +:Author: Lv Zheng + + +Abstract +======== +This document describes the ACPICA project and the relationship between +ACPICA and Linux. It also describes how ACPICA code in drivers/acpi/acpica, +include/acpi and tools/power/acpi is automatically updated to follow the +upstream. + +ACPICA Project +============== + +The ACPI Component Architecture (ACPICA) project provides an operating +system (OS)-independent reference implementation of the Advanced +Configuration and Power Interface Specification (ACPI). It has been +adapted by various host OSes. By directly integrating ACPICA, Linux can +also benefit from the application experiences of ACPICA from other host +OSes. + +The homepage of ACPICA project is: www.acpica.org, it is maintained and +supported by Intel Corporation. + +The following figure depicts the Linux ACPI subsystem where the ACPICA +adaptation is included:: + + +---------------------------------------------------------+ + | | + | +---------------------------------------------------+ | + | | +------------------+ | | + | | | Table Management | | | + | | +------------------+ | | + | | +----------------------+ | | + | | | Namespace Management | | | + | | +----------------------+ | | + | | +------------------+ ACPICA Components | | + | | | Event Management | | | + | | +------------------+ | | + | | +---------------------+ | | + | | | Resource Management | | | + | | +---------------------+ | | + | | +---------------------+ | | + | | | Hardware Management | | | + | | +---------------------+ | | + | +---------------------------------------------------+ | | + | | | +------------------+ | | | + | | | | OS Service Layer | | | | + | | | +------------------+ | | | + | | +-------------------------------------------------|-+ | + | | +--------------------+ | | + | | | Device Enumeration | | | + | | +--------------------+ | | + | | +------------------+ | | + | | | Power Management | | | + | | +------------------+ Linux/ACPI Components | | + | | +--------------------+ | | + | | | Thermal Management | | | + | | +--------------------+ | | + | | +--------------------------+ | | + | | | Drivers for ACPI Devices | | | + | | +--------------------------+ | | + | | +--------+ | | + | | | ...... | | | + | | +--------+ | | + | +---------------------------------------------------+ | + | | + +---------------------------------------------------------+ + + Figure 1. Linux ACPI Software Components + +.. note:: + A. OS Service Layer - Provided by Linux to offer OS dependent + implementation of the predefined ACPICA interfaces (acpi_os_*). + :: + + include/acpi/acpiosxf.h + drivers/acpi/osl.c + include/acpi/platform + include/asm/acenv.h + B. ACPICA Functionality - Released from ACPICA code base to offer + OS independent implementation of the ACPICA interfaces (acpi_*). + :: + + drivers/acpi/acpica + include/acpi/ac*.h + tools/power/acpi + C. Linux/ACPI Functionality - Providing Linux specific ACPI + functionality to the other Linux kernel subsystems and user space + programs. + :: + + drivers/acpi + include/linux/acpi.h + include/linux/acpi*.h + include/acpi + tools/power/acpi + D. Architecture Specific ACPICA/ACPI Functionalities - Provided by the + ACPI subsystem to offer architecture specific implementation of the + ACPI interfaces. They are Linux specific components and are out of + the scope of this document. + :: + + include/asm/acpi.h + include/asm/acpi*.h + arch/*/acpi + +ACPICA Release +============== + +The ACPICA project maintains its code base at the following repository URL: +https://github.com/acpica/acpica.git. As a rule, a release is made every +month. + +As the coding style adopted by the ACPICA project is not acceptable by +Linux, there is a release process to convert the ACPICA git commits into +Linux patches. The patches generated by this process are referred to as +"linuxized ACPICA patches". The release process is carried out on a local +copy the ACPICA git repository. Each commit in the monthly release is +converted into a linuxized ACPICA patch. Together, they form the monthly +ACPICA release patchset for the Linux ACPI community. This process is +illustrated in the following figure:: + + +-----------------------------+ + | acpica / master (-) commits | + +-----------------------------+ + /|\ | + | \|/ + | /---------------------\ +----------------------+ + | < Linuxize repo Utility >-->| old linuxized acpica |--+ + | \---------------------/ +----------------------+ | + | | + /---------\ | + < git reset > \ + \---------/ \ + /|\ /+-+ + | / | + +-----------------------------+ | | + | acpica / master (+) commits | | | + +-----------------------------+ | | + | | | + \|/ | | + /-----------------------\ +----------------------+ | | + < Linuxize repo Utilities >-->| new linuxized acpica |--+ | + \-----------------------/ +----------------------+ | + \|/ + +--------------------------+ /----------------------\ + | Linuxized ACPICA Patches |<----------------< Linuxize patch Utility > + +--------------------------+ \----------------------/ + | + \|/ + /---------------------------\ + < Linux ACPI Community Review > + \---------------------------/ + | + \|/ + +-----------------------+ /------------------\ +----------------+ + | linux-pm / linux-next |-->< Linux Merge Window >-->| linux / master | + +-----------------------+ \------------------/ +----------------+ + + Figure 2. ACPICA -> Linux Upstream Process + +.. note:: + A. Linuxize Utilities - Provided by the ACPICA repository, including a + utility located in source/tools/acpisrc folder and a number of + scripts located in generate/linux folder. + B. acpica / master - "master" branch of the git repository at + . + C. linux-pm / linux-next - "linux-next" branch of the git repository at + . + D. linux / master - "master" branch of the git repository at + . + + Before the linuxized ACPICA patches are sent to the Linux ACPI community + for review, there is a quality assurance build test process to reduce + porting issues. Currently this build process only takes care of the + following kernel configuration options: + CONFIG_ACPI/CONFIG_ACPI_DEBUG/CONFIG_ACPI_DEBUGGER + +ACPICA Divergences +================== + +Ideally, all of the ACPICA commits should be converted into Linux patches +automatically without manual modifications, the "linux / master" tree should +contain the ACPICA code that exactly corresponds to the ACPICA code +contained in "new linuxized acpica" tree and it should be possible to run +the release process fully automatically. + +As a matter of fact, however, there are source code differences between +the ACPICA code in Linux and the upstream ACPICA code, referred to as +"ACPICA Divergences". + +The various sources of ACPICA divergences include: + 1. Legacy divergences - Before the current ACPICA release process was + established, there already had been divergences between Linux and + ACPICA. Over the past several years those divergences have been greatly + reduced, but there still are several ones and it takes time to figure + out the underlying reasons for their existence. + 2. Manual modifications - Any manual modification (eg. coding style fixes) + made directly in the Linux sources obviously hurts the ACPICA release + automation. Thus it is recommended to fix such issues in the ACPICA + upstream source code and generate the linuxized fix using the ACPICA + release utilities (please refer to Section 4 below for the details). + 3. Linux specific features - Sometimes it's impossible to use the + current ACPICA APIs to implement features required by the Linux kernel, + so Linux developers occasionally have to change ACPICA code directly. + Those changes may not be acceptable by ACPICA upstream and in such cases + they are left as committed ACPICA divergences unless the ACPICA side can + implement new mechanisms as replacements for them. + 4. ACPICA release fixups - ACPICA only tests commits using a set of the + user space simulation utilities, thus the linuxized ACPICA patches may + break the Linux kernel, leaving us build/boot failures. In order to + avoid breaking Linux bisection, fixes are applied directly to the + linuxized ACPICA patches during the release process. When the release + fixups are backported to the upstream ACPICA sources, they must follow + the upstream ACPICA rules and so further modifications may appear. + That may result in the appearance of new divergences. + 5. Fast tracking of ACPICA commits - Some ACPICA commits are regression + fixes or stable-candidate material, so they are applied in advance with + respect to the ACPICA release process. If such commits are reverted or + rebased on the ACPICA side in order to offer better solutions, new ACPICA + divergences are generated. + +ACPICA Development +================== + +This paragraph guides Linux developers to use the ACPICA upstream release +utilities to obtain Linux patches corresponding to upstream ACPICA commits +before they become available from the ACPICA release process. + + 1. Cherry-pick an ACPICA commit + + First you need to git clone the ACPICA repository and the ACPICA change + you want to cherry pick must be committed into the local repository. + + Then the gen-patch.sh command can help to cherry-pick an ACPICA commit + from the ACPICA local repository:: + + $ git clone https://github.com/acpica/acpica + $ cd acpica + $ generate/linux/gen-patch.sh -u [commit ID] + + Here the commit ID is the ACPICA local repository commit ID you want to + cherry pick. It can be omitted if the commit is "HEAD". + + 2. Cherry-pick recent ACPICA commits + + Sometimes you need to rebase your code on top of the most recent ACPICA + changes that haven't been applied to Linux yet. + + You can generate the ACPICA release series yourself and rebase your code on + top of the generated ACPICA release patches:: + + $ git clone https://github.com/acpica/acpica + $ cd acpica + $ generate/linux/make-patches.sh -u [commit ID] + + The commit ID should be the last ACPICA commit accepted by Linux. Usually, + it is the commit modifying ACPI_CA_VERSION. It can be found by executing + "git blame source/include/acpixf.h" and referencing the line that contains + "ACPI_CA_VERSION". + + 3. Inspect the current divergences + + If you have local copies of both Linux and upstream ACPICA, you can generate + a diff file indicating the state of the current divergences:: + + # git clone https://github.com/acpica/acpica + # git clone http://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git + # cd acpica + # generate/linux/divergences.sh -s ../linux -- cgit v1.2.3 From 97a63dd43477a93fa0fc53ff082af8d64ff618e1 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 01:52:48 +0800 Subject: Documentation: ACPI: move scan_handlers.txt to driver-api/acpi and convert to reST This converts the plain text documentation to reStructuredText format and adds it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/scan_handlers.txt | 77 ----------------------- Documentation/driver-api/acpi/index.rst | 1 + Documentation/driver-api/acpi/scan_handlers.rst | 83 +++++++++++++++++++++++++ 3 files changed, 84 insertions(+), 77 deletions(-) delete mode 100644 Documentation/acpi/scan_handlers.txt create mode 100644 Documentation/driver-api/acpi/scan_handlers.rst (limited to 'Documentation') diff --git a/Documentation/acpi/scan_handlers.txt b/Documentation/acpi/scan_handlers.txt deleted file mode 100644 index 3246ccf15992..000000000000 --- a/Documentation/acpi/scan_handlers.txt +++ /dev/null @@ -1,77 +0,0 @@ -ACPI Scan Handlers - -Copyright (C) 2012, Intel Corporation -Author: Rafael J. Wysocki - -During system initialization and ACPI-based device hot-add, the ACPI namespace -is scanned in search of device objects that generally represent various pieces -of hardware. This causes a struct acpi_device object to be created and -registered with the driver core for every device object in the ACPI namespace -and the hierarchy of those struct acpi_device objects reflects the namespace -layout (i.e. parent device objects in the namespace are represented by parent -struct acpi_device objects and analogously for their children). Those struct -acpi_device objects are referred to as "device nodes" in what follows, but they -should not be confused with struct device_node objects used by the Device Trees -parsing code (although their role is analogous to the role of those objects). - -During ACPI-based device hot-remove device nodes representing pieces of hardware -being removed are unregistered and deleted. - -The core ACPI namespace scanning code in drivers/acpi/scan.c carries out basic -initialization of device nodes, such as retrieving common configuration -information from the device objects represented by them and populating them with -appropriate data, but some of them require additional handling after they have -been registered. For example, if the given device node represents a PCI host -bridge, its registration should cause the PCI bus under that bridge to be -enumerated and PCI devices on that bus to be registered with the driver core. -Similarly, if the device node represents a PCI interrupt link, it is necessary -to configure that link so that the kernel can use it. - -Those additional configuration tasks usually depend on the type of the hardware -component represented by the given device node which can be determined on the -basis of the device node's hardware ID (HID). They are performed by objects -called ACPI scan handlers represented by the following structure: - -struct acpi_scan_handler { - const struct acpi_device_id *ids; - struct list_head list_node; - int (*attach)(struct acpi_device *dev, const struct acpi_device_id *id); - void (*detach)(struct acpi_device *dev); -}; - -where ids is the list of IDs of device nodes the given handler is supposed to -take care of, list_node is the hook to the global list of ACPI scan handlers -maintained by the ACPI core and the .attach() and .detach() callbacks are -executed, respectively, after registration of new device nodes and before -unregistration of device nodes the handler attached to previously. - -The namespace scanning function, acpi_bus_scan(), first registers all of the -device nodes in the given namespace scope with the driver core. Then, it tries -to match a scan handler against each of them using the ids arrays of the -available scan handlers. If a matching scan handler is found, its .attach() -callback is executed for the given device node. If that callback returns 1, -that means that the handler has claimed the device node and is now responsible -for carrying out any additional configuration tasks related to it. It also will -be responsible for preparing the device node for unregistration in that case. -The device node's handler field is then populated with the address of the scan -handler that has claimed it. - -If the .attach() callback returns 0, it means that the device node is not -interesting to the given scan handler and may be matched against the next scan -handler in the list. If it returns a (negative) error code, that means that -the namespace scan should be terminated due to a serious error. The error code -returned should then reflect the type of the error. - -The namespace trimming function, acpi_bus_trim(), first executes .detach() -callbacks from the scan handlers of all device nodes in the given namespace -scope (if they have scan handlers). Next, it unregisters all of the device -nodes in that scope. - -ACPI scan handlers can be added to the list maintained by the ACPI core with the -help of the acpi_scan_add_handler() function taking a pointer to the new scan -handler as an argument. The order in which scan handlers are added to the list -is the order in which they are matched against device nodes during namespace -scans. - -All scan handles must be added to the list before acpi_bus_scan() is run for the -first time and they cannot be removed from it. diff --git a/Documentation/driver-api/acpi/index.rst b/Documentation/driver-api/acpi/index.rst index 12649947b19b..ace0008e54c2 100644 --- a/Documentation/driver-api/acpi/index.rst +++ b/Documentation/driver-api/acpi/index.rst @@ -6,3 +6,4 @@ ACPI Support :maxdepth: 2 linuxized-acpica + scan_handlers diff --git a/Documentation/driver-api/acpi/scan_handlers.rst b/Documentation/driver-api/acpi/scan_handlers.rst new file mode 100644 index 000000000000..7a197b3a33fc --- /dev/null +++ b/Documentation/driver-api/acpi/scan_handlers.rst @@ -0,0 +1,83 @@ +.. SPDX-License-Identifier: GPL-2.0 +.. include:: + +================== +ACPI Scan Handlers +================== + +:Copyright: |copy| 2012, Intel Corporation + +:Author: Rafael J. Wysocki + +During system initialization and ACPI-based device hot-add, the ACPI namespace +is scanned in search of device objects that generally represent various pieces +of hardware. This causes a struct acpi_device object to be created and +registered with the driver core for every device object in the ACPI namespace +and the hierarchy of those struct acpi_device objects reflects the namespace +layout (i.e. parent device objects in the namespace are represented by parent +struct acpi_device objects and analogously for their children). Those struct +acpi_device objects are referred to as "device nodes" in what follows, but they +should not be confused with struct device_node objects used by the Device Trees +parsing code (although their role is analogous to the role of those objects). + +During ACPI-based device hot-remove device nodes representing pieces of hardware +being removed are unregistered and deleted. + +The core ACPI namespace scanning code in drivers/acpi/scan.c carries out basic +initialization of device nodes, such as retrieving common configuration +information from the device objects represented by them and populating them with +appropriate data, but some of them require additional handling after they have +been registered. For example, if the given device node represents a PCI host +bridge, its registration should cause the PCI bus under that bridge to be +enumerated and PCI devices on that bus to be registered with the driver core. +Similarly, if the device node represents a PCI interrupt link, it is necessary +to configure that link so that the kernel can use it. + +Those additional configuration tasks usually depend on the type of the hardware +component represented by the given device node which can be determined on the +basis of the device node's hardware ID (HID). They are performed by objects +called ACPI scan handlers represented by the following structure:: + + struct acpi_scan_handler { + const struct acpi_device_id *ids; + struct list_head list_node; + int (*attach)(struct acpi_device *dev, const struct acpi_device_id *id); + void (*detach)(struct acpi_device *dev); + }; + +where ids is the list of IDs of device nodes the given handler is supposed to +take care of, list_node is the hook to the global list of ACPI scan handlers +maintained by the ACPI core and the .attach() and .detach() callbacks are +executed, respectively, after registration of new device nodes and before +unregistration of device nodes the handler attached to previously. + +The namespace scanning function, acpi_bus_scan(), first registers all of the +device nodes in the given namespace scope with the driver core. Then, it tries +to match a scan handler against each of them using the ids arrays of the +available scan handlers. If a matching scan handler is found, its .attach() +callback is executed for the given device node. If that callback returns 1, +that means that the handler has claimed the device node and is now responsible +for carrying out any additional configuration tasks related to it. It also will +be responsible for preparing the device node for unregistration in that case. +The device node's handler field is then populated with the address of the scan +handler that has claimed it. + +If the .attach() callback returns 0, it means that the device node is not +interesting to the given scan handler and may be matched against the next scan +handler in the list. If it returns a (negative) error code, that means that +the namespace scan should be terminated due to a serious error. The error code +returned should then reflect the type of the error. + +The namespace trimming function, acpi_bus_trim(), first executes .detach() +callbacks from the scan handlers of all device nodes in the given namespace +scope (if they have scan handlers). Next, it unregisters all of the device +nodes in that scope. + +ACPI scan handlers can be added to the list maintained by the ACPI core with the +help of the acpi_scan_add_handler() function taking a pointer to the new scan +handler as an argument. The order in which scan handlers are added to the list +is the order in which they are matched against device nodes during namespace +scans. + +All scan handles must be added to the list before acpi_bus_scan() is run for the +first time and they cannot be removed from it. -- cgit v1.2.3 From 538f6f76b9ca5cbcd521db80e137d1c43e55556b Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 01:52:49 +0800 Subject: Documentation: ACPI: move DSD-properties-rules.txt to firmware-guide/acpi and covert to reST This converts the plain text documentation to reStructuredText format and adds it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/DSD-properties-rules.txt | 97 -------------------- .../firmware-guide/acpi/DSD-properties-rules.rst | 100 +++++++++++++++++++++ Documentation/firmware-guide/acpi/index.rst | 1 + 3 files changed, 101 insertions(+), 97 deletions(-) delete mode 100644 Documentation/acpi/DSD-properties-rules.txt create mode 100644 Documentation/firmware-guide/acpi/DSD-properties-rules.rst (limited to 'Documentation') diff --git a/Documentation/acpi/DSD-properties-rules.txt b/Documentation/acpi/DSD-properties-rules.txt deleted file mode 100644 index 3e4862bdad98..000000000000 --- a/Documentation/acpi/DSD-properties-rules.txt +++ /dev/null @@ -1,97 +0,0 @@ -_DSD Device Properties Usage Rules ----------------------------------- - -Properties, Property Sets and Property Subsets ----------------------------------------------- - -The _DSD (Device Specific Data) configuration object, introduced in ACPI 5.1, -allows any type of device configuration data to be provided via the ACPI -namespace. In principle, the format of the data may be arbitrary, but it has to -be identified by a UUID which must be recognized by the driver processing the -_DSD output. However, there are generic UUIDs defined for _DSD recognized by -the ACPI subsystem in the Linux kernel which automatically processes the data -packages associated with them and makes those data available to device drivers -as "device properties". - -A device property is a data item consisting of a string key and a value (of a -specific type) associated with it. - -In the ACPI _DSD context it is an element of the sub-package following the -generic Device Properties UUID in the _DSD return package as specified in the -Device Properties UUID definition document [1]. - -It also may be regarded as the definition of a key and the associated data type -that can be returned by _DSD in the Device Properties UUID sub-package for a -given device. - -A property set is a collection of properties applicable to a hardware entity -like a device. In the ACPI _DSD context it is the set of all properties that -can be returned in the Device Properties UUID sub-package for the device in -question. - -Property subsets are nested collections of properties. Each of them is -associated with an additional key (name) allowing the subset to be referred -to as a whole (and to be treated as a separate entity). The canonical -representation of property subsets is via the mechanism specified in the -Hierarchical Properties Extension UUID definition document [2]. - -Property sets may be hierarchical. That is, a property set may contain -multiple property subsets that each may contain property subsets of its -own and so on. - -General Validity Rule for Property Sets ---------------------------------------- - -Valid property sets must follow the guidance given by the Device Properties UUID -definition document [1]. - -_DSD properties are intended to be used in addition to, and not instead of, the -existing mechanisms defined by the ACPI specification. Therefore, as a rule, -they should only be used if the ACPI specification does not make direct -provisions for handling the underlying use case. It generally is invalid to -return property sets which do not follow that rule from _DSD in data packages -associated with the Device Properties UUID. - -Additional Considerations -------------------------- - -There are cases in which, even if the general rule given above is followed in -principle, the property set may still not be regarded as a valid one. - -For example, that applies to device properties which may cause kernel code -(either a device driver or a library/subsystem) to access hardware in a way -possibly leading to a conflict with AML methods in the ACPI namespace. In -particular, that may happen if the kernel code uses device properties to -manipulate hardware normally controlled by ACPI methods related to power -management, like _PSx and _DSW (for device objects) or _ON and _OFF (for power -resource objects), or by ACPI device disabling/enabling methods, like _DIS and -_SRS. - -In all cases in which kernel code may do something that will confuse AML as a -result of using device properties, the device properties in question are not -suitable for the ACPI environment and consequently they cannot belong to a valid -property set. - -Property Sets and Device Tree Bindings --------------------------------------- - -It often is useful to make _DSD return property sets that follow Device Tree -bindings. - -In those cases, however, the above validity considerations must be taken into -account in the first place and returning invalid property sets from _DSD must be -avoided. For this reason, it may not be possible to make _DSD return a property -set following the given DT binding literally and completely. Still, for the -sake of code re-use, it may make sense to provide as much of the configuration -data as possible in the form of device properties and complement that with an -ACPI-specific mechanism suitable for the use case at hand. - -In any case, property sets following DT bindings literally should not be -expected to automatically work in the ACPI environment regardless of their -contents. - -References ----------- - -[1] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf -[2] http://www.uefi.org/sites/default/files/resources/_DSD-hierarchical-data-extension-UUID-v1.1.pdf diff --git a/Documentation/firmware-guide/acpi/DSD-properties-rules.rst b/Documentation/firmware-guide/acpi/DSD-properties-rules.rst new file mode 100644 index 000000000000..4306f29b6103 --- /dev/null +++ b/Documentation/firmware-guide/acpi/DSD-properties-rules.rst @@ -0,0 +1,100 @@ +.. SPDX-License-Identifier: GPL-2.0 + +================================== +_DSD Device Properties Usage Rules +================================== + +Properties, Property Sets and Property Subsets +============================================== + +The _DSD (Device Specific Data) configuration object, introduced in ACPI 5.1, +allows any type of device configuration data to be provided via the ACPI +namespace. In principle, the format of the data may be arbitrary, but it has to +be identified by a UUID which must be recognized by the driver processing the +_DSD output. However, there are generic UUIDs defined for _DSD recognized by +the ACPI subsystem in the Linux kernel which automatically processes the data +packages associated with them and makes those data available to device drivers +as "device properties". + +A device property is a data item consisting of a string key and a value (of a +specific type) associated with it. + +In the ACPI _DSD context it is an element of the sub-package following the +generic Device Properties UUID in the _DSD return package as specified in the +Device Properties UUID definition document [1]_. + +It also may be regarded as the definition of a key and the associated data type +that can be returned by _DSD in the Device Properties UUID sub-package for a +given device. + +A property set is a collection of properties applicable to a hardware entity +like a device. In the ACPI _DSD context it is the set of all properties that +can be returned in the Device Properties UUID sub-package for the device in +question. + +Property subsets are nested collections of properties. Each of them is +associated with an additional key (name) allowing the subset to be referred +to as a whole (and to be treated as a separate entity). The canonical +representation of property subsets is via the mechanism specified in the +Hierarchical Properties Extension UUID definition document [2]_. + +Property sets may be hierarchical. That is, a property set may contain +multiple property subsets that each may contain property subsets of its +own and so on. + +General Validity Rule for Property Sets +======================================= + +Valid property sets must follow the guidance given by the Device Properties UUID +definition document [1]. + +_DSD properties are intended to be used in addition to, and not instead of, the +existing mechanisms defined by the ACPI specification. Therefore, as a rule, +they should only be used if the ACPI specification does not make direct +provisions for handling the underlying use case. It generally is invalid to +return property sets which do not follow that rule from _DSD in data packages +associated with the Device Properties UUID. + +Additional Considerations +------------------------- + +There are cases in which, even if the general rule given above is followed in +principle, the property set may still not be regarded as a valid one. + +For example, that applies to device properties which may cause kernel code +(either a device driver or a library/subsystem) to access hardware in a way +possibly leading to a conflict with AML methods in the ACPI namespace. In +particular, that may happen if the kernel code uses device properties to +manipulate hardware normally controlled by ACPI methods related to power +management, like _PSx and _DSW (for device objects) or _ON and _OFF (for power +resource objects), or by ACPI device disabling/enabling methods, like _DIS and +_SRS. + +In all cases in which kernel code may do something that will confuse AML as a +result of using device properties, the device properties in question are not +suitable for the ACPI environment and consequently they cannot belong to a valid +property set. + +Property Sets and Device Tree Bindings +====================================== + +It often is useful to make _DSD return property sets that follow Device Tree +bindings. + +In those cases, however, the above validity considerations must be taken into +account in the first place and returning invalid property sets from _DSD must be +avoided. For this reason, it may not be possible to make _DSD return a property +set following the given DT binding literally and completely. Still, for the +sake of code re-use, it may make sense to provide as much of the configuration +data as possible in the form of device properties and complement that with an +ACPI-specific mechanism suitable for the use case at hand. + +In any case, property sets following DT bindings literally should not be +expected to automatically work in the ACPI environment regardless of their +contents. + +References +========== + +.. [1] http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf +.. [2] http://www.uefi.org/sites/default/files/resources/_DSD-hierarchical-data-extension-UUID-v1.1.pdf diff --git a/Documentation/firmware-guide/acpi/index.rst b/Documentation/firmware-guide/acpi/index.rst index 868bd25a3398..0e05b843521c 100644 --- a/Documentation/firmware-guide/acpi/index.rst +++ b/Documentation/firmware-guide/acpi/index.rst @@ -10,3 +10,4 @@ ACPI Support namespace enumeration osi + DSD-properties-rules -- cgit v1.2.3 From b6dff0e153e919b62e2a1c90fd6e5a4ba922f99b Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 01:52:50 +0800 Subject: Documentation: ACPI: move gpio-properties.txt to firmware-guide/acpi and convert to reST This converts the plain text documentation to reStructuredText format and adds it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/gpio-properties.txt | 223 -------------------- .../firmware-guide/acpi/gpio-properties.rst | 233 +++++++++++++++++++++ Documentation/firmware-guide/acpi/index.rst | 1 + MAINTAINERS | 2 +- 4 files changed, 235 insertions(+), 224 deletions(-) delete mode 100644 Documentation/acpi/gpio-properties.txt create mode 100644 Documentation/firmware-guide/acpi/gpio-properties.rst (limited to 'Documentation') diff --git a/Documentation/acpi/gpio-properties.txt b/Documentation/acpi/gpio-properties.txt deleted file mode 100644 index 88c65cb5bf0a..000000000000 --- a/Documentation/acpi/gpio-properties.txt +++ /dev/null @@ -1,223 +0,0 @@ -_DSD Device Properties Related to GPIO --------------------------------------- - -With the release of ACPI 5.1, the _DSD configuration object finally -allows names to be given to GPIOs (and other things as well) returned -by _CRS. Previously, we were only able to use an integer index to find -the corresponding GPIO, which is pretty error prone (it depends on -the _CRS output ordering, for example). - -With _DSD we can now query GPIOs using a name instead of an integer -index, like the ASL example below shows: - - // Bluetooth device with reset and shutdown GPIOs - Device (BTH) - { - Name (_HID, ...) - - Name (_CRS, ResourceTemplate () - { - GpioIo (Exclusive, PullUp, 0, 0, IoRestrictionInputOnly, - "\\_SB.GPO0", 0, ResourceConsumer) {15} - GpioIo (Exclusive, PullUp, 0, 0, IoRestrictionInputOnly, - "\\_SB.GPO0", 0, ResourceConsumer) {27, 31} - }) - - Name (_DSD, Package () - { - ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), - Package () - { - Package () {"reset-gpios", Package() {^BTH, 1, 1, 0 }}, - Package () {"shutdown-gpios", Package() {^BTH, 0, 0, 0 }}, - } - }) - } - -The format of the supported GPIO property is: - - Package () { "name", Package () { ref, index, pin, active_low }} - - ref - The device that has _CRS containing GpioIo()/GpioInt() resources, - typically this is the device itself (BTH in our case). - index - Index of the GpioIo()/GpioInt() resource in _CRS starting from zero. - pin - Pin in the GpioIo()/GpioInt() resource. Typically this is zero. - active_low - If 1 the GPIO is marked as active_low. - -Since ACPI GpioIo() resource does not have a field saying whether it is -active low or high, the "active_low" argument can be used here. Setting -it to 1 marks the GPIO as active low. - -In our Bluetooth example the "reset-gpios" refers to the second GpioIo() -resource, second pin in that resource with the GPIO number of 31. - -It is possible to leave holes in the array of GPIOs. This is useful in -cases like with SPI host controllers where some chip selects may be -implemented as GPIOs and some as native signals. For example a SPI host -controller can have chip selects 0 and 2 implemented as GPIOs and 1 as -native: - - Package () { - "cs-gpios", - Package () { - ^GPIO, 19, 0, 0, // chip select 0: GPIO - 0, // chip select 1: native signal - ^GPIO, 20, 0, 0, // chip select 2: GPIO - } - } - -Other supported properties --------------------------- - -Following Device Tree compatible device properties are also supported by -_DSD device properties for GPIO controllers: - -- gpio-hog -- output-high -- output-low -- input -- line-name - -Example: - - Name (_DSD, Package () { - // _DSD Hierarchical Properties Extension UUID - ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), - Package () { - Package () {"hog-gpio8", "G8PU"} - } - }) - - Name (G8PU, Package () { - ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), - Package () { - Package () {"gpio-hog", 1}, - Package () {"gpios", Package () {8, 0}}, - Package () {"output-high", 1}, - Package () {"line-name", "gpio8-pullup"}, - } - }) - -- gpio-line-names - -Example: - - Package () { - "gpio-line-names", - Package () { - "SPI0_CS_N", "EXP2_INT", "MUX6_IO", "UART0_RXD", "MUX7_IO", - "LVL_C_A1", "MUX0_IO", "SPI1_MISO" - } - } - -See Documentation/devicetree/bindings/gpio/gpio.txt for more information -about these properties. - -ACPI GPIO Mappings Provided by Drivers --------------------------------------- - -There are systems in which the ACPI tables do not contain _DSD but provide _CRS -with GpioIo()/GpioInt() resources and device drivers still need to work with -them. - -In those cases ACPI device identification objects, _HID, _CID, _CLS, _SUB, _HRV, -available to the driver can be used to identify the device and that is supposed -to be sufficient to determine the meaning and purpose of all of the GPIO lines -listed by the GpioIo()/GpioInt() resources returned by _CRS. In other words, -the driver is supposed to know what to use the GpioIo()/GpioInt() resources for -once it has identified the device. Having done that, it can simply assign names -to the GPIO lines it is going to use and provide the GPIO subsystem with a -mapping between those names and the ACPI GPIO resources corresponding to them. - -To do that, the driver needs to define a mapping table as a NULL-terminated -array of struct acpi_gpio_mapping objects that each contain a name, a pointer -to an array of line data (struct acpi_gpio_params) objects and the size of that -array. Each struct acpi_gpio_params object consists of three fields, -crs_entry_index, line_index, active_low, representing the index of the target -GpioIo()/GpioInt() resource in _CRS starting from zero, the index of the target -line in that resource starting from zero, and the active-low flag for that line, -respectively, in analogy with the _DSD GPIO property format specified above. - -For the example Bluetooth device discussed previously the data structures in -question would look like this: - -static const struct acpi_gpio_params reset_gpio = { 1, 1, false }; -static const struct acpi_gpio_params shutdown_gpio = { 0, 0, false }; - -static const struct acpi_gpio_mapping bluetooth_acpi_gpios[] = { - { "reset-gpios", &reset_gpio, 1 }, - { "shutdown-gpios", &shutdown_gpio, 1 }, - { }, -}; - -Next, the mapping table needs to be passed as the second argument to -acpi_dev_add_driver_gpios() that will register it with the ACPI device object -pointed to by its first argument. That should be done in the driver's .probe() -routine. On removal, the driver should unregister its GPIO mapping table by -calling acpi_dev_remove_driver_gpios() on the ACPI device object where that -table was previously registered. - -Using the _CRS fallback ------------------------ - -If a device does not have _DSD or the driver does not create ACPI GPIO -mapping, the Linux GPIO framework refuses to return any GPIOs. This is -because the driver does not know what it actually gets. For example if we -have a device like below: - - Device (BTH) - { - Name (_HID, ...) - - Name (_CRS, ResourceTemplate () { - GpioIo (Exclusive, PullNone, 0, 0, IoRestrictionNone, - "\\_SB.GPO0", 0, ResourceConsumer) {15} - GpioIo (Exclusive, PullNone, 0, 0, IoRestrictionNone, - "\\_SB.GPO0", 0, ResourceConsumer) {27} - }) - } - -The driver might expect to get the right GPIO when it does: - - desc = gpiod_get(dev, "reset", GPIOD_OUT_LOW); - -but since there is no way to know the mapping between "reset" and -the GpioIo() in _CRS desc will hold ERR_PTR(-ENOENT). - -The driver author can solve this by passing the mapping explictly -(the recommended way and documented in the above chapter). - -The ACPI GPIO mapping tables should not contaminate drivers that are not -knowing about which exact device they are servicing on. It implies that -the ACPI GPIO mapping tables are hardly linked to ACPI ID and certain -objects, as listed in the above chapter, of the device in question. - -Getting GPIO descriptor ------------------------ - -There are two main approaches to get GPIO resource from ACPI: - desc = gpiod_get(dev, connection_id, flags); - desc = gpiod_get_index(dev, connection_id, index, flags); - -We may consider two different cases here, i.e. when connection ID is -provided and otherwise. - -Case 1: - desc = gpiod_get(dev, "non-null-connection-id", flags); - desc = gpiod_get_index(dev, "non-null-connection-id", index, flags); - -Case 2: - desc = gpiod_get(dev, NULL, flags); - desc = gpiod_get_index(dev, NULL, index, flags); - -Case 1 assumes that corresponding ACPI device description must have -defined device properties and will prevent to getting any GPIO resources -otherwise. - -Case 2 explicitly tells GPIO core to look for resources in _CRS. - -Be aware that gpiod_get_index() in cases 1 and 2, assuming that there -are two versions of ACPI device description provided and no mapping is -present in the driver, will return different resources. That's why a -certain driver has to handle them carefully as explained in previous -chapter. diff --git a/Documentation/firmware-guide/acpi/gpio-properties.rst b/Documentation/firmware-guide/acpi/gpio-properties.rst new file mode 100644 index 000000000000..bb6d74f23ee0 --- /dev/null +++ b/Documentation/firmware-guide/acpi/gpio-properties.rst @@ -0,0 +1,233 @@ +.. SPDX-License-Identifier: GPL-2.0 + +====================================== +_DSD Device Properties Related to GPIO +====================================== + +With the release of ACPI 5.1, the _DSD configuration object finally +allows names to be given to GPIOs (and other things as well) returned +by _CRS. Previously, we were only able to use an integer index to find +the corresponding GPIO, which is pretty error prone (it depends on +the _CRS output ordering, for example). + +With _DSD we can now query GPIOs using a name instead of an integer +index, like the ASL example below shows:: + + // Bluetooth device with reset and shutdown GPIOs + Device (BTH) + { + Name (_HID, ...) + + Name (_CRS, ResourceTemplate () + { + GpioIo (Exclusive, PullUp, 0, 0, IoRestrictionInputOnly, + "\\_SB.GPO0", 0, ResourceConsumer) {15} + GpioIo (Exclusive, PullUp, 0, 0, IoRestrictionInputOnly, + "\\_SB.GPO0", 0, ResourceConsumer) {27, 31} + }) + + Name (_DSD, Package () + { + ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), + Package () + { + Package () {"reset-gpios", Package() {^BTH, 1, 1, 0 }}, + Package () {"shutdown-gpios", Package() {^BTH, 0, 0, 0 }}, + } + }) + } + +The format of the supported GPIO property is:: + + Package () { "name", Package () { ref, index, pin, active_low }} + +ref + The device that has _CRS containing GpioIo()/GpioInt() resources, + typically this is the device itself (BTH in our case). +index + Index of the GpioIo()/GpioInt() resource in _CRS starting from zero. +pin + Pin in the GpioIo()/GpioInt() resource. Typically this is zero. +active_low + If 1 the GPIO is marked as active_low. + +Since ACPI GpioIo() resource does not have a field saying whether it is +active low or high, the "active_low" argument can be used here. Setting +it to 1 marks the GPIO as active low. + +In our Bluetooth example the "reset-gpios" refers to the second GpioIo() +resource, second pin in that resource with the GPIO number of 31. + +It is possible to leave holes in the array of GPIOs. This is useful in +cases like with SPI host controllers where some chip selects may be +implemented as GPIOs and some as native signals. For example a SPI host +controller can have chip selects 0 and 2 implemented as GPIOs and 1 as +native:: + + Package () { + "cs-gpios", + Package () { + ^GPIO, 19, 0, 0, // chip select 0: GPIO + 0, // chip select 1: native signal + ^GPIO, 20, 0, 0, // chip select 2: GPIO + } + } + +Other supported properties +========================== + +Following Device Tree compatible device properties are also supported by +_DSD device properties for GPIO controllers: + +- gpio-hog +- output-high +- output-low +- input +- line-name + +Example:: + + Name (_DSD, Package () { + // _DSD Hierarchical Properties Extension UUID + ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), + Package () { + Package () {"hog-gpio8", "G8PU"} + } + }) + + Name (G8PU, Package () { + ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), + Package () { + Package () {"gpio-hog", 1}, + Package () {"gpios", Package () {8, 0}}, + Package () {"output-high", 1}, + Package () {"line-name", "gpio8-pullup"}, + } + }) + +- gpio-line-names + +Example:: + + Package () { + "gpio-line-names", + Package () { + "SPI0_CS_N", "EXP2_INT", "MUX6_IO", "UART0_RXD", "MUX7_IO", + "LVL_C_A1", "MUX0_IO", "SPI1_MISO" + } + } + +See Documentation/devicetree/bindings/gpio/gpio.txt for more information +about these properties. + +ACPI GPIO Mappings Provided by Drivers +====================================== + +There are systems in which the ACPI tables do not contain _DSD but provide _CRS +with GpioIo()/GpioInt() resources and device drivers still need to work with +them. + +In those cases ACPI device identification objects, _HID, _CID, _CLS, _SUB, _HRV, +available to the driver can be used to identify the device and that is supposed +to be sufficient to determine the meaning and purpose of all of the GPIO lines +listed by the GpioIo()/GpioInt() resources returned by _CRS. In other words, +the driver is supposed to know what to use the GpioIo()/GpioInt() resources for +once it has identified the device. Having done that, it can simply assign names +to the GPIO lines it is going to use and provide the GPIO subsystem with a +mapping between those names and the ACPI GPIO resources corresponding to them. + +To do that, the driver needs to define a mapping table as a NULL-terminated +array of struct acpi_gpio_mapping objects that each contain a name, a pointer +to an array of line data (struct acpi_gpio_params) objects and the size of that +array. Each struct acpi_gpio_params object consists of three fields, +crs_entry_index, line_index, active_low, representing the index of the target +GpioIo()/GpioInt() resource in _CRS starting from zero, the index of the target +line in that resource starting from zero, and the active-low flag for that line, +respectively, in analogy with the _DSD GPIO property format specified above. + +For the example Bluetooth device discussed previously the data structures in +question would look like this:: + + static const struct acpi_gpio_params reset_gpio = { 1, 1, false }; + static const struct acpi_gpio_params shutdown_gpio = { 0, 0, false }; + + static const struct acpi_gpio_mapping bluetooth_acpi_gpios[] = { + { "reset-gpios", &reset_gpio, 1 }, + { "shutdown-gpios", &shutdown_gpio, 1 }, + { }, + }; + +Next, the mapping table needs to be passed as the second argument to +acpi_dev_add_driver_gpios() that will register it with the ACPI device object +pointed to by its first argument. That should be done in the driver's .probe() +routine. On removal, the driver should unregister its GPIO mapping table by +calling acpi_dev_remove_driver_gpios() on the ACPI device object where that +table was previously registered. + +Using the _CRS fallback +======================= + +If a device does not have _DSD or the driver does not create ACPI GPIO +mapping, the Linux GPIO framework refuses to return any GPIOs. This is +because the driver does not know what it actually gets. For example if we +have a device like below:: + + Device (BTH) + { + Name (_HID, ...) + + Name (_CRS, ResourceTemplate () { + GpioIo (Exclusive, PullNone, 0, 0, IoRestrictionNone, + "\\_SB.GPO0", 0, ResourceConsumer) {15} + GpioIo (Exclusive, PullNone, 0, 0, IoRestrictionNone, + "\\_SB.GPO0", 0, ResourceConsumer) {27} + }) + } + +The driver might expect to get the right GPIO when it does:: + + desc = gpiod_get(dev, "reset", GPIOD_OUT_LOW); + +but since there is no way to know the mapping between "reset" and +the GpioIo() in _CRS desc will hold ERR_PTR(-ENOENT). + +The driver author can solve this by passing the mapping explictly +(the recommended way and documented in the above chapter). + +The ACPI GPIO mapping tables should not contaminate drivers that are not +knowing about which exact device they are servicing on. It implies that +the ACPI GPIO mapping tables are hardly linked to ACPI ID and certain +objects, as listed in the above chapter, of the device in question. + +Getting GPIO descriptor +======================= + +There are two main approaches to get GPIO resource from ACPI:: + + desc = gpiod_get(dev, connection_id, flags); + desc = gpiod_get_index(dev, connection_id, index, flags); + +We may consider two different cases here, i.e. when connection ID is +provided and otherwise. + +Case 1:: + + desc = gpiod_get(dev, "non-null-connection-id", flags); + desc = gpiod_get_index(dev, "non-null-connection-id", index, flags); + +Case 2:: + + desc = gpiod_get(dev, NULL, flags); + desc = gpiod_get_index(dev, NULL, index, flags); + +Case 1 assumes that corresponding ACPI device description must have +defined device properties and will prevent to getting any GPIO resources +otherwise. + +Case 2 explicitly tells GPIO core to look for resources in _CRS. + +Be aware that gpiod_get_index() in cases 1 and 2, assuming that there +are two versions of ACPI device description provided and no mapping is +present in the driver, will return different resources. That's why a +certain driver has to handle them carefully as explained in previous +chapter. diff --git a/Documentation/firmware-guide/acpi/index.rst b/Documentation/firmware-guide/acpi/index.rst index 0e05b843521c..61d67763851b 100644 --- a/Documentation/firmware-guide/acpi/index.rst +++ b/Documentation/firmware-guide/acpi/index.rst @@ -11,3 +11,4 @@ ACPI Support enumeration osi DSD-properties-rules + gpio-properties diff --git a/MAINTAINERS b/MAINTAINERS index 3e5a5d263f29..89c13e1ed648 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -6593,7 +6593,7 @@ M: Andy Shevchenko L: linux-gpio@vger.kernel.org L: linux-acpi@vger.kernel.org S: Maintained -F: Documentation/acpi/gpio-properties.txt +F: Documentation/firmware-guide/acpi/gpio-properties.rst F: drivers/gpio/gpiolib-acpi.c GPIO IR Transmitter -- cgit v1.2.3 From eea7803278619d1a3bda6306cd8470497cd2c5e3 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 01:52:51 +0800 Subject: Documentation: ACPI: move method-customizing.txt to firmware-guide/acpi and convert to reST This converts the plain text documentation to reStructuredText format and adds it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/method-customizing.txt | 73 ------------------ Documentation/firmware-guide/acpi/index.rst | 3 +- .../firmware-guide/acpi/method-customizing.rst | 89 ++++++++++++++++++++++ 3 files changed, 91 insertions(+), 74 deletions(-) delete mode 100644 Documentation/acpi/method-customizing.txt create mode 100644 Documentation/firmware-guide/acpi/method-customizing.rst (limited to 'Documentation') diff --git a/Documentation/acpi/method-customizing.txt b/Documentation/acpi/method-customizing.txt deleted file mode 100644 index 7235da975f23..000000000000 --- a/Documentation/acpi/method-customizing.txt +++ /dev/null @@ -1,73 +0,0 @@ -Linux ACPI Custom Control Method How To -======================================= - -Written by Zhang Rui - - -Linux supports customizing ACPI control methods at runtime. - -Users can use this to -1. override an existing method which may not work correctly, - or just for debugging purposes. -2. insert a completely new method in order to create a missing - method such as _OFF, _ON, _STA, _INI, etc. -For these cases, it is far simpler to dynamically install a single -control method rather than override the entire DSDT, because kernel -rebuild/reboot is not needed and test result can be got in minutes. - -Note: Only ACPI METHOD can be overridden, any other object types like - "Device", "OperationRegion", are not recognized. Methods - declared inside scope operators are also not supported. -Note: The same ACPI control method can be overridden for many times, - and it's always the latest one that used by Linux/kernel. -Note: To get the ACPI debug object output (Store (AAAA, Debug)), - please run "echo 1 > /sys/module/acpi/parameters/aml_debug_output". - -1. override an existing method - a) get the ACPI table via ACPI sysfs I/F. e.g. to get the DSDT, - just run "cat /sys/firmware/acpi/tables/DSDT > /tmp/dsdt.dat" - b) disassemble the table by running "iasl -d dsdt.dat". - c) rewrite the ASL code of the method and save it in a new file, - d) package the new file (psr.asl) to an ACPI table format. - Here is an example of a customized \_SB._AC._PSR method, - - DefinitionBlock ("", "SSDT", 1, "", "", 0x20080715) - { - Method (\_SB_.AC._PSR, 0, NotSerialized) - { - Store ("In AC _PSR", Debug) - Return (ACON) - } - } - Note that the full pathname of the method in ACPI namespace - should be used. - e) assemble the file to generate the AML code of the method. - e.g. "iasl -vw 6084 psr.asl" (psr.aml is generated as a result) - If parameter "-vw 6084" is not supported by your iASL compiler, - please try a newer version. - f) mount debugfs by "mount -t debugfs none /sys/kernel/debug" - g) override the old method via the debugfs by running - "cat /tmp/psr.aml > /sys/kernel/debug/acpi/custom_method" - -2. insert a new method - This is easier than overriding an existing method. - We just need to create the ASL code of the method we want to - insert and then follow the step c) ~ g) in section 1. - -3. undo your changes - The "undo" operation is not supported for a new inserted method - right now, i.e. we can not remove a method currently. - For an overridden method, in order to undo your changes, please - save a copy of the method original ASL code in step c) section 1, - and redo step c) ~ g) to override the method with the original one. - - -Note: We can use a kernel with multiple custom ACPI method running, - But each individual write to debugfs can implement a SINGLE - method override. i.e. if we want to insert/override multiple - ACPI methods, we need to redo step c) ~ g) for multiple times. - -Note: Be aware that root can mis-use this driver to modify arbitrary - memory and gain additional rights, if root's privileges got - restricted (for example if root is not allowed to load additional - modules after boot). diff --git a/Documentation/firmware-guide/acpi/index.rst b/Documentation/firmware-guide/acpi/index.rst index 61d67763851b..d1d069b26bbc 100644 --- a/Documentation/firmware-guide/acpi/index.rst +++ b/Documentation/firmware-guide/acpi/index.rst @@ -10,5 +10,6 @@ ACPI Support namespace enumeration osi + method-customizing DSD-properties-rules - gpio-properties + gpio-properties \ No newline at end of file diff --git a/Documentation/firmware-guide/acpi/method-customizing.rst b/Documentation/firmware-guide/acpi/method-customizing.rst new file mode 100644 index 000000000000..de3ebcaed4cf --- /dev/null +++ b/Documentation/firmware-guide/acpi/method-customizing.rst @@ -0,0 +1,89 @@ +.. SPDX-License-Identifier: GPL-2.0 + +======================================= +Linux ACPI Custom Control Method How To +======================================= + +:Author: Zhang Rui + + +Linux supports customizing ACPI control methods at runtime. + +Users can use this to: + +1. override an existing method which may not work correctly, + or just for debugging purposes. +2. insert a completely new method in order to create a missing + method such as _OFF, _ON, _STA, _INI, etc. + +For these cases, it is far simpler to dynamically install a single +control method rather than override the entire DSDT, because kernel +rebuild/reboot is not needed and test result can be got in minutes. + +.. note:: + + - Only ACPI METHOD can be overridden, any other object types like + "Device", "OperationRegion", are not recognized. Methods + declared inside scope operators are also not supported. + + - The same ACPI control method can be overridden for many times, + and it's always the latest one that used by Linux/kernel. + + - To get the ACPI debug object output (Store (AAAA, Debug)), + please run:: + + echo 1 > /sys/module/acpi/parameters/aml_debug_output + + +1. override an existing method +============================== +a) get the ACPI table via ACPI sysfs I/F. e.g. to get the DSDT, + just run "cat /sys/firmware/acpi/tables/DSDT > /tmp/dsdt.dat" +b) disassemble the table by running "iasl -d dsdt.dat". +c) rewrite the ASL code of the method and save it in a new file, +d) package the new file (psr.asl) to an ACPI table format. + Here is an example of a customized \_SB._AC._PSR method:: + + DefinitionBlock ("", "SSDT", 1, "", "", 0x20080715) + { + Method (\_SB_.AC._PSR, 0, NotSerialized) + { + Store ("In AC _PSR", Debug) + Return (ACON) + } + } + + Note that the full pathname of the method in ACPI namespace + should be used. +e) assemble the file to generate the AML code of the method. + e.g. "iasl -vw 6084 psr.asl" (psr.aml is generated as a result) + If parameter "-vw 6084" is not supported by your iASL compiler, + please try a newer version. +f) mount debugfs by "mount -t debugfs none /sys/kernel/debug" +g) override the old method via the debugfs by running + "cat /tmp/psr.aml > /sys/kernel/debug/acpi/custom_method" + +2. insert a new method +====================== +This is easier than overriding an existing method. +We just need to create the ASL code of the method we want to +insert and then follow the step c) ~ g) in section 1. + +3. undo your changes +==================== +The "undo" operation is not supported for a new inserted method +right now, i.e. we can not remove a method currently. +For an overridden method, in order to undo your changes, please +save a copy of the method original ASL code in step c) section 1, +and redo step c) ~ g) to override the method with the original one. + + +.. note:: We can use a kernel with multiple custom ACPI method running, + But each individual write to debugfs can implement a SINGLE + method override. i.e. if we want to insert/override multiple + ACPI methods, we need to redo step c) ~ g) for multiple times. + +.. note:: Be aware that root can mis-use this driver to modify arbitrary + memory and gain additional rights, if root's privileges got + restricted (for example if root is not allowed to load additional + modules after boot). -- cgit v1.2.3 From 59bcdcccf31f5a42cd23ea46154f9b3546d66009 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 01:52:52 +0800 Subject: Documentation: ACPI: move initrd_table_override.txt to admin-guide/acpi and convert to reST This converts the plain text documentation to reStructuredText format and adds it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/initrd_table_override.txt | 111 -------------------- Documentation/admin-guide/acpi/index.rst | 1 + .../admin-guide/acpi/initrd_table_override.rst | 115 +++++++++++++++++++++ 3 files changed, 116 insertions(+), 111 deletions(-) delete mode 100644 Documentation/acpi/initrd_table_override.txt create mode 100644 Documentation/admin-guide/acpi/initrd_table_override.rst (limited to 'Documentation') diff --git a/Documentation/acpi/initrd_table_override.txt b/Documentation/acpi/initrd_table_override.txt deleted file mode 100644 index 30437a6db373..000000000000 --- a/Documentation/acpi/initrd_table_override.txt +++ /dev/null @@ -1,111 +0,0 @@ -Upgrading ACPI tables via initrd -================================ - -1) Introduction (What is this about) -2) What is this for -3) How does it work -4) References (Where to retrieve userspace tools) - -1) What is this about ---------------------- - -If the ACPI_TABLE_UPGRADE compile option is true, it is possible to -upgrade the ACPI execution environment that is defined by the ACPI tables -via upgrading the ACPI tables provided by the BIOS with an instrumented, -modified, more recent version one, or installing brand new ACPI tables. - -When building initrd with kernel in a single image, option -ACPI_TABLE_OVERRIDE_VIA_BUILTIN_INITRD should also be true for this -feature to work. - -For a full list of ACPI tables that can be upgraded/installed, take a look -at the char *table_sigs[MAX_ACPI_SIGNATURE]; definition in -drivers/acpi/tables.c. -All ACPI tables iasl (Intel's ACPI compiler and disassembler) knows should -be overridable, except: - - ACPI_SIG_RSDP (has a signature of 6 bytes) - - ACPI_SIG_FACS (does not have an ordinary ACPI table header) -Both could get implemented as well. - - -2) What is this for -------------------- - -Complain to your platform/BIOS vendor if you find a bug which is so severe -that a workaround is not accepted in the Linux kernel. And this facility -allows you to upgrade the buggy tables before your platform/BIOS vendor -releases an upgraded BIOS binary. - -This facility can be used by platform/BIOS vendors to provide a Linux -compatible environment without modifying the underlying platform firmware. - -This facility also provides a powerful feature to easily debug and test -ACPI BIOS table compatibility with the Linux kernel by modifying old -platform provided ACPI tables or inserting new ACPI tables. - -It can and should be enabled in any kernel because there is no functional -change with not instrumented initrds. - - -3) How does it work -------------------- - -# Extract the machine's ACPI tables: -cd /tmp -acpidump >acpidump -acpixtract -a acpidump -# Disassemble, modify and recompile them: -iasl -d *.dat -# For example add this statement into a _PRT (PCI Routing Table) function -# of the DSDT: -Store("HELLO WORLD", debug) -# And increase the OEM Revision. For example, before modification: -DefinitionBlock ("DSDT.aml", "DSDT", 2, "INTEL ", "TEMPLATE", 0x00000000) -# After modification: -DefinitionBlock ("DSDT.aml", "DSDT", 2, "INTEL ", "TEMPLATE", 0x00000001) -iasl -sa dsdt.dsl -# Add the raw ACPI tables to an uncompressed cpio archive. -# They must be put into a /kernel/firmware/acpi directory inside the cpio -# archive. Note that if the table put here matches a platform table -# (similar Table Signature, and similar OEMID, and similar OEM Table ID) -# with a more recent OEM Revision, the platform table will be upgraded by -# this table. If the table put here doesn't match a platform table -# (dissimilar Table Signature, or dissimilar OEMID, or dissimilar OEM Table -# ID), this table will be appended. -mkdir -p kernel/firmware/acpi -cp dsdt.aml kernel/firmware/acpi -# A maximum of "NR_ACPI_INITRD_TABLES (64)" tables are currently allowed -# (see osl.c): -iasl -sa facp.dsl -iasl -sa ssdt1.dsl -cp facp.aml kernel/firmware/acpi -cp ssdt1.aml kernel/firmware/acpi -# The uncompressed cpio archive must be the first. Other, typically -# compressed cpio archives, must be concatenated on top of the uncompressed -# one. Following command creates the uncompressed cpio archive and -# concatenates the original initrd on top: -find kernel | cpio -H newc --create > /boot/instrumented_initrd -cat /boot/initrd >>/boot/instrumented_initrd -# reboot with increased acpi debug level, e.g. boot params: -acpi.debug_level=0x2 acpi.debug_layer=0xFFFFFFFF -# and check your syslog: -[ 1.268089] ACPI: PCI Interrupt Routing Table [\_SB_.PCI0._PRT] -[ 1.272091] [ACPI Debug] String [0x0B] "HELLO WORLD" - -iasl is able to disassemble and recompile quite a lot different, -also static ACPI tables. - - -4) Where to retrieve userspace tools ------------------------------------- - -iasl and acpixtract are part of Intel's ACPICA project: -http://acpica.org/ -and should be packaged by distributions (for example in the acpica package -on SUSE). - -acpidump can be found in Len Browns pmtools: -ftp://kernel.org/pub/linux/kernel/people/lenb/acpi/utils/pmtools/acpidump -This tool is also part of the acpica package on SUSE. -Alternatively, used ACPI tables can be retrieved via sysfs in latest kernels: -/sys/firmware/acpi/tables diff --git a/Documentation/admin-guide/acpi/index.rst b/Documentation/admin-guide/acpi/index.rst index 3e041206089d..09e4e81e4fb7 100644 --- a/Documentation/admin-guide/acpi/index.rst +++ b/Documentation/admin-guide/acpi/index.rst @@ -8,3 +8,4 @@ the Linux ACPI support. .. toctree:: :maxdepth: 1 + initrd_table_override diff --git a/Documentation/admin-guide/acpi/initrd_table_override.rst b/Documentation/admin-guide/acpi/initrd_table_override.rst new file mode 100644 index 000000000000..cbd768207631 --- /dev/null +++ b/Documentation/admin-guide/acpi/initrd_table_override.rst @@ -0,0 +1,115 @@ +.. SPDX-License-Identifier: GPL-2.0 + +================================ +Upgrading ACPI tables via initrd +================================ + +What is this about +================== + +If the ACPI_TABLE_UPGRADE compile option is true, it is possible to +upgrade the ACPI execution environment that is defined by the ACPI tables +via upgrading the ACPI tables provided by the BIOS with an instrumented, +modified, more recent version one, or installing brand new ACPI tables. + +When building initrd with kernel in a single image, option +ACPI_TABLE_OVERRIDE_VIA_BUILTIN_INITRD should also be true for this +feature to work. + +For a full list of ACPI tables that can be upgraded/installed, take a look +at the char `*table_sigs[MAX_ACPI_SIGNATURE];` definition in +drivers/acpi/tables.c. + +All ACPI tables iasl (Intel's ACPI compiler and disassembler) knows should +be overridable, except: + + - ACPI_SIG_RSDP (has a signature of 6 bytes) + - ACPI_SIG_FACS (does not have an ordinary ACPI table header) + +Both could get implemented as well. + + +What is this for +================ + +Complain to your platform/BIOS vendor if you find a bug which is so severe +that a workaround is not accepted in the Linux kernel. And this facility +allows you to upgrade the buggy tables before your platform/BIOS vendor +releases an upgraded BIOS binary. + +This facility can be used by platform/BIOS vendors to provide a Linux +compatible environment without modifying the underlying platform firmware. + +This facility also provides a powerful feature to easily debug and test +ACPI BIOS table compatibility with the Linux kernel by modifying old +platform provided ACPI tables or inserting new ACPI tables. + +It can and should be enabled in any kernel because there is no functional +change with not instrumented initrds. + + +How does it work +================ +:: + + # Extract the machine's ACPI tables: + cd /tmp + acpidump >acpidump + acpixtract -a acpidump + # Disassemble, modify and recompile them: + iasl -d *.dat + # For example add this statement into a _PRT (PCI Routing Table) function + # of the DSDT: + Store("HELLO WORLD", debug) + # And increase the OEM Revision. For example, before modification: + DefinitionBlock ("DSDT.aml", "DSDT", 2, "INTEL ", "TEMPLATE", 0x00000000) + # After modification: + DefinitionBlock ("DSDT.aml", "DSDT", 2, "INTEL ", "TEMPLATE", 0x00000001) + iasl -sa dsdt.dsl + # Add the raw ACPI tables to an uncompressed cpio archive. + # They must be put into a /kernel/firmware/acpi directory inside the cpio + # archive. Note that if the table put here matches a platform table + # (similar Table Signature, and similar OEMID, and similar OEM Table ID) + # with a more recent OEM Revision, the platform table will be upgraded by + # this table. If the table put here doesn't match a platform table + # (dissimilar Table Signature, or dissimilar OEMID, or dissimilar OEM Table + # ID), this table will be appended. + mkdir -p kernel/firmware/acpi + cp dsdt.aml kernel/firmware/acpi + # A maximum of "NR_ACPI_INITRD_TABLES (64)" tables are currently allowed + # (see osl.c): + iasl -sa facp.dsl + iasl -sa ssdt1.dsl + cp facp.aml kernel/firmware/acpi + cp ssdt1.aml kernel/firmware/acpi + # The uncompressed cpio archive must be the first. Other, typically + # compressed cpio archives, must be concatenated on top of the uncompressed + # one. Following command creates the uncompressed cpio archive and + # concatenates the original initrd on top: + find kernel | cpio -H newc --create > /boot/instrumented_initrd + cat /boot/initrd >>/boot/instrumented_initrd + # reboot with increased acpi debug level, e.g. boot params: + acpi.debug_level=0x2 acpi.debug_layer=0xFFFFFFFF + # and check your syslog: + [ 1.268089] ACPI: PCI Interrupt Routing Table [\_SB_.PCI0._PRT] + [ 1.272091] [ACPI Debug] String [0x0B] "HELLO WORLD" + +iasl is able to disassemble and recompile quite a lot different, +also static ACPI tables. + + +Where to retrieve userspace tools +================================= + +iasl and acpixtract are part of Intel's ACPICA project: +http://acpica.org/ + +and should be packaged by distributions (for example in the acpica package +on SUSE). + +acpidump can be found in Len Browns pmtools: +ftp://kernel.org/pub/linux/kernel/people/lenb/acpi/utils/pmtools/acpidump + +This tool is also part of the acpica package on SUSE. +Alternatively, used ACPI tables can be retrieved via sysfs in latest kernels: +/sys/firmware/acpi/tables -- cgit v1.2.3 From 34bf473baef086ec0e277ffb0dbddb697da9f02e Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 01:52:53 +0800 Subject: Documentation: ACPI: move dsdt-override.txt to admin-guide/acpi and convert to reST This converts the plain text documentation to reStructuredText format and adds it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/dsdt-override.txt | 7 ------- Documentation/admin-guide/acpi/dsdt-override.rst | 13 +++++++++++++ Documentation/admin-guide/acpi/index.rst | 1 + 3 files changed, 14 insertions(+), 7 deletions(-) delete mode 100644 Documentation/acpi/dsdt-override.txt create mode 100644 Documentation/admin-guide/acpi/dsdt-override.rst (limited to 'Documentation') diff --git a/Documentation/acpi/dsdt-override.txt b/Documentation/acpi/dsdt-override.txt deleted file mode 100644 index 784841caa6e6..000000000000 --- a/Documentation/acpi/dsdt-override.txt +++ /dev/null @@ -1,7 +0,0 @@ -Linux supports a method of overriding the BIOS DSDT: - -CONFIG_ACPI_CUSTOM_DSDT builds the image into the kernel. - -When to use this method is described in detail on the -Linux/ACPI home page: -https://01.org/linux-acpi/documentation/overriding-dsdt diff --git a/Documentation/admin-guide/acpi/dsdt-override.rst b/Documentation/admin-guide/acpi/dsdt-override.rst new file mode 100644 index 000000000000..50bd7f194bf4 --- /dev/null +++ b/Documentation/admin-guide/acpi/dsdt-override.rst @@ -0,0 +1,13 @@ +.. SPDX-License-Identifier: GPL-2.0 + +=============== +Overriding DSDT +=============== + +Linux supports a method of overriding the BIOS DSDT: + +CONFIG_ACPI_CUSTOM_DSDT - builds the image into the kernel. + +When to use this method is described in detail on the +Linux/ACPI home page: +https://01.org/linux-acpi/documentation/overriding-dsdt diff --git a/Documentation/admin-guide/acpi/index.rst b/Documentation/admin-guide/acpi/index.rst index 09e4e81e4fb7..d68e9914c5ff 100644 --- a/Documentation/admin-guide/acpi/index.rst +++ b/Documentation/admin-guide/acpi/index.rst @@ -9,3 +9,4 @@ the Linux ACPI support. :maxdepth: 1 initrd_table_override + dsdt-override -- cgit v1.2.3 From 572c9fa516f532d6cfd7123d7753fe52730f1c59 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 01:52:54 +0800 Subject: Documentation: ACPI: move i2c-muxes.txt to firmware-guide/acpi and convert to reST This converts the plain text documentation to reStructuredText format and adds it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/i2c-muxes.txt | 58 ----------------------- Documentation/firmware-guide/acpi/i2c-muxes.rst | 61 +++++++++++++++++++++++++ Documentation/firmware-guide/acpi/index.rst | 3 +- 3 files changed, 63 insertions(+), 59 deletions(-) delete mode 100644 Documentation/acpi/i2c-muxes.txt create mode 100644 Documentation/firmware-guide/acpi/i2c-muxes.rst (limited to 'Documentation') diff --git a/Documentation/acpi/i2c-muxes.txt b/Documentation/acpi/i2c-muxes.txt deleted file mode 100644 index 9fcc4f0b885e..000000000000 --- a/Documentation/acpi/i2c-muxes.txt +++ /dev/null @@ -1,58 +0,0 @@ -ACPI I2C Muxes --------------- - -Describing an I2C device hierarchy that includes I2C muxes requires an ACPI -Device () scope per mux channel. - -Consider this topology: - -+------+ +------+ -| SMB1 |-->| MUX0 |--CH00--> i2c client A (0x50) -| | | 0x70 |--CH01--> i2c client B (0x50) -+------+ +------+ - -which corresponds to the following ASL: - -Device (SMB1) -{ - Name (_HID, ...) - Device (MUX0) - { - Name (_HID, ...) - Name (_CRS, ResourceTemplate () { - I2cSerialBus (0x70, ControllerInitiated, I2C_SPEED, - AddressingMode7Bit, "^SMB1", 0x00, - ResourceConsumer,,) - } - - Device (CH00) - { - Name (_ADR, 0) - - Device (CLIA) - { - Name (_HID, ...) - Name (_CRS, ResourceTemplate () { - I2cSerialBus (0x50, ControllerInitiated, I2C_SPEED, - AddressingMode7Bit, "^CH00", 0x00, - ResourceConsumer,,) - } - } - } - - Device (CH01) - { - Name (_ADR, 1) - - Device (CLIB) - { - Name (_HID, ...) - Name (_CRS, ResourceTemplate () { - I2cSerialBus (0x50, ControllerInitiated, I2C_SPEED, - AddressingMode7Bit, "^CH01", 0x00, - ResourceConsumer,,) - } - } - } - } -} diff --git a/Documentation/firmware-guide/acpi/i2c-muxes.rst b/Documentation/firmware-guide/acpi/i2c-muxes.rst new file mode 100644 index 000000000000..3a8997ccd7c4 --- /dev/null +++ b/Documentation/firmware-guide/acpi/i2c-muxes.rst @@ -0,0 +1,61 @@ +.. SPDX-License-Identifier: GPL-2.0 + +============== +ACPI I2C Muxes +============== + +Describing an I2C device hierarchy that includes I2C muxes requires an ACPI +Device () scope per mux channel. + +Consider this topology:: + + +------+ +------+ + | SMB1 |-->| MUX0 |--CH00--> i2c client A (0x50) + | | | 0x70 |--CH01--> i2c client B (0x50) + +------+ +------+ + +which corresponds to the following ASL:: + + Device (SMB1) + { + Name (_HID, ...) + Device (MUX0) + { + Name (_HID, ...) + Name (_CRS, ResourceTemplate () { + I2cSerialBus (0x70, ControllerInitiated, I2C_SPEED, + AddressingMode7Bit, "^SMB1", 0x00, + ResourceConsumer,,) + } + + Device (CH00) + { + Name (_ADR, 0) + + Device (CLIA) + { + Name (_HID, ...) + Name (_CRS, ResourceTemplate () { + I2cSerialBus (0x50, ControllerInitiated, I2C_SPEED, + AddressingMode7Bit, "^CH00", 0x00, + ResourceConsumer,,) + } + } + } + + Device (CH01) + { + Name (_ADR, 1) + + Device (CLIB) + { + Name (_HID, ...) + Name (_CRS, ResourceTemplate () { + I2cSerialBus (0x50, ControllerInitiated, I2C_SPEED, + AddressingMode7Bit, "^CH01", 0x00, + ResourceConsumer,,) + } + } + } + } + } diff --git a/Documentation/firmware-guide/acpi/index.rst b/Documentation/firmware-guide/acpi/index.rst index d1d069b26bbc..1c89888f6ee8 100644 --- a/Documentation/firmware-guide/acpi/index.rst +++ b/Documentation/firmware-guide/acpi/index.rst @@ -12,4 +12,5 @@ ACPI Support osi method-customizing DSD-properties-rules - gpio-properties \ No newline at end of file + gpio-properties + i2c-muxes -- cgit v1.2.3 From 011eed59ba6df428a1380fd1419a2a422f0d807a Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 01:52:55 +0800 Subject: Documentation: ACPI: move acpi-lid.txt to firmware-guide/acpi and convert to reST This converts the plain text documentation to reStructuredText format and adds it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/acpi-lid.txt | 96 --------------------- Documentation/firmware-guide/acpi/acpi-lid.rst | 114 +++++++++++++++++++++++++ Documentation/firmware-guide/acpi/index.rst | 1 + 3 files changed, 115 insertions(+), 96 deletions(-) delete mode 100644 Documentation/acpi/acpi-lid.txt create mode 100644 Documentation/firmware-guide/acpi/acpi-lid.rst (limited to 'Documentation') diff --git a/Documentation/acpi/acpi-lid.txt b/Documentation/acpi/acpi-lid.txt deleted file mode 100644 index effe7af3a5af..000000000000 --- a/Documentation/acpi/acpi-lid.txt +++ /dev/null @@ -1,96 +0,0 @@ -Special Usage Model of the ACPI Control Method Lid Device - -Copyright (C) 2016, Intel Corporation -Author: Lv Zheng - - -Abstract: - -Platforms containing lids convey lid state (open/close) to OSPMs using a -control method lid device. To implement this, the AML tables issue -Notify(lid_device, 0x80) to notify the OSPMs whenever the lid state has -changed. The _LID control method for the lid device must be implemented to -report the "current" state of the lid as either "opened" or "closed". - -For most platforms, both the _LID method and the lid notifications are -reliable. However, there are exceptions. In order to work with these -exceptional buggy platforms, special restrictions and expections should be -taken into account. This document describes the restrictions and the -expections of the Linux ACPI lid device driver. - - -1. Restrictions of the returning value of the _LID control method - -The _LID control method is described to return the "current" lid state. -However the word of "current" has ambiguity, some buggy AML tables return -the lid state upon the last lid notification instead of returning the lid -state upon the last _LID evaluation. There won't be difference when the -_LID control method is evaluated during the runtime, the problem is its -initial returning value. When the AML tables implement this control method -with cached value, the initial returning value is likely not reliable. -There are platforms always retun "closed" as initial lid state. - -2. Restrictions of the lid state change notifications - -There are buggy AML tables never notifying when the lid device state is -changed to "opened". Thus the "opened" notification is not guaranteed. But -it is guaranteed that the AML tables always notify "closed" when the lid -state is changed to "closed". The "closed" notification is normally used to -trigger some system power saving operations on Windows. Since it is fully -tested, it is reliable from all AML tables. - -3. Expections for the userspace users of the ACPI lid device driver - -The ACPI button driver exports the lid state to the userspace via the -following file: - /proc/acpi/button/lid/LID0/state -This file actually calls the _LID control method described above. And given -the previous explanation, it is not reliable enough on some platforms. So -it is advised for the userspace program to not to solely rely on this file -to determine the actual lid state. - -The ACPI button driver emits the following input event to the userspace: - SW_LID -The ACPI lid device driver is implemented to try to deliver the platform -triggered events to the userspace. However, given the fact that the buggy -firmware cannot make sure "opened"/"closed" events are paired, the ACPI -button driver uses the following 3 modes in order not to trigger issues. - -If the userspace hasn't been prepared to ignore the unreliable "opened" -events and the unreliable initial state notification, Linux users can use -the following kernel parameters to handle the possible issues: -A. button.lid_init_state=method: - When this option is specified, the ACPI button driver reports the - initial lid state using the returning value of the _LID control method - and whether the "opened"/"closed" events are paired fully relies on the - firmware implementation. - This option can be used to fix some platforms where the returning value - of the _LID control method is reliable but the initial lid state - notification is missing. - This option is the default behavior during the period the userspace - isn't ready to handle the buggy AML tables. -B. button.lid_init_state=open: - When this option is specified, the ACPI button driver always reports the - initial lid state as "opened" and whether the "opened"/"closed" events - are paired fully relies on the firmware implementation. - This may fix some platforms where the returning value of the _LID - control method is not reliable and the initial lid state notification is - missing. - -If the userspace has been prepared to ignore the unreliable "opened" events -and the unreliable initial state notification, Linux users should always -use the following kernel parameter: -C. button.lid_init_state=ignore: - When this option is specified, the ACPI button driver never reports the - initial lid state and there is a compensation mechanism implemented to - ensure that the reliable "closed" notifications can always be delievered - to the userspace by always pairing "closed" input events with complement - "opened" input events. But there is still no guarantee that the "opened" - notifications can be delivered to the userspace when the lid is actually - opens given that some AML tables do not send "opened" notifications - reliably. - In this mode, if everything is correctly implemented by the platform - firmware, the old userspace programs should still work. Otherwise, the - new userspace programs are required to work with the ACPI button driver. - This option will be the default behavior after the userspace is ready to - handle the buggy AML tables. diff --git a/Documentation/firmware-guide/acpi/acpi-lid.rst b/Documentation/firmware-guide/acpi/acpi-lid.rst new file mode 100644 index 000000000000..874ce0ed340d --- /dev/null +++ b/Documentation/firmware-guide/acpi/acpi-lid.rst @@ -0,0 +1,114 @@ +.. SPDX-License-Identifier: GPL-2.0 +.. include:: + +========================================================= +Special Usage Model of the ACPI Control Method Lid Device +========================================================= + +:Copyright: |copy| 2016, Intel Corporation + +:Author: Lv Zheng + +Abstract +======== +Platforms containing lids convey lid state (open/close) to OSPMs +using a control method lid device. To implement this, the AML tables issue +Notify(lid_device, 0x80) to notify the OSPMs whenever the lid state has +changed. The _LID control method for the lid device must be implemented to +report the "current" state of the lid as either "opened" or "closed". + +For most platforms, both the _LID method and the lid notifications are +reliable. However, there are exceptions. In order to work with these +exceptional buggy platforms, special restrictions and expections should be +taken into account. This document describes the restrictions and the +expections of the Linux ACPI lid device driver. + + +Restrictions of the returning value of the _LID control method +============================================================== + +The _LID control method is described to return the "current" lid state. +However the word of "current" has ambiguity, some buggy AML tables return +the lid state upon the last lid notification instead of returning the lid +state upon the last _LID evaluation. There won't be difference when the +_LID control method is evaluated during the runtime, the problem is its +initial returning value. When the AML tables implement this control method +with cached value, the initial returning value is likely not reliable. +There are platforms always retun "closed" as initial lid state. + +Restrictions of the lid state change notifications +================================================== + +There are buggy AML tables never notifying when the lid device state is +changed to "opened". Thus the "opened" notification is not guaranteed. But +it is guaranteed that the AML tables always notify "closed" when the lid +state is changed to "closed". The "closed" notification is normally used to +trigger some system power saving operations on Windows. Since it is fully +tested, it is reliable from all AML tables. + +Expections for the userspace users of the ACPI lid device driver +================================================================ + +The ACPI button driver exports the lid state to the userspace via the +following file:: + + /proc/acpi/button/lid/LID0/state + +This file actually calls the _LID control method described above. And given +the previous explanation, it is not reliable enough on some platforms. So +it is advised for the userspace program to not to solely rely on this file +to determine the actual lid state. + +The ACPI button driver emits the following input event to the userspace: + * SW_LID + +The ACPI lid device driver is implemented to try to deliver the platform +triggered events to the userspace. However, given the fact that the buggy +firmware cannot make sure "opened"/"closed" events are paired, the ACPI +button driver uses the following 3 modes in order not to trigger issues. + +If the userspace hasn't been prepared to ignore the unreliable "opened" +events and the unreliable initial state notification, Linux users can use +the following kernel parameters to handle the possible issues: + +A. button.lid_init_state=method: + When this option is specified, the ACPI button driver reports the + initial lid state using the returning value of the _LID control method + and whether the "opened"/"closed" events are paired fully relies on the + firmware implementation. + + This option can be used to fix some platforms where the returning value + of the _LID control method is reliable but the initial lid state + notification is missing. + + This option is the default behavior during the period the userspace + isn't ready to handle the buggy AML tables. + +B. button.lid_init_state=open: + When this option is specified, the ACPI button driver always reports the + initial lid state as "opened" and whether the "opened"/"closed" events + are paired fully relies on the firmware implementation. + + This may fix some platforms where the returning value of the _LID + control method is not reliable and the initial lid state notification is + missing. + +If the userspace has been prepared to ignore the unreliable "opened" events +and the unreliable initial state notification, Linux users should always +use the following kernel parameter: + +C. button.lid_init_state=ignore: + When this option is specified, the ACPI button driver never reports the + initial lid state and there is a compensation mechanism implemented to + ensure that the reliable "closed" notifications can always be delievered + to the userspace by always pairing "closed" input events with complement + "opened" input events. But there is still no guarantee that the "opened" + notifications can be delivered to the userspace when the lid is actually + opens given that some AML tables do not send "opened" notifications + reliably. + + In this mode, if everything is correctly implemented by the platform + firmware, the old userspace programs should still work. Otherwise, the + new userspace programs are required to work with the ACPI button driver. + This option will be the default behavior after the userspace is ready to + handle the buggy AML tables. diff --git a/Documentation/firmware-guide/acpi/index.rst b/Documentation/firmware-guide/acpi/index.rst index 1c89888f6ee8..bedcb0b242a2 100644 --- a/Documentation/firmware-guide/acpi/index.rst +++ b/Documentation/firmware-guide/acpi/index.rst @@ -14,3 +14,4 @@ ACPI Support DSD-properties-rules gpio-properties i2c-muxes + acpi-lid \ No newline at end of file -- cgit v1.2.3 From f2dde1ed0f2818405b371c2b65a98fece221b7a0 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 01:52:56 +0800 Subject: Documentation: ACPI: move dsd/graph.txt to firmware-guide/acpi and convert to reST This converts the plain text documentation to reStructuredText format and adds it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/dsd/graph.txt | 174 ----------------------- Documentation/firmware-guide/acpi/dsd/graph.rst | 177 ++++++++++++++++++++++++ Documentation/firmware-guide/acpi/index.rst | 1 + 3 files changed, 178 insertions(+), 174 deletions(-) delete mode 100644 Documentation/acpi/dsd/graph.txt create mode 100644 Documentation/firmware-guide/acpi/dsd/graph.rst (limited to 'Documentation') diff --git a/Documentation/acpi/dsd/graph.txt b/Documentation/acpi/dsd/graph.txt deleted file mode 100644 index b9ce910781dc..000000000000 --- a/Documentation/acpi/dsd/graph.txt +++ /dev/null @@ -1,174 +0,0 @@ -Graphs - - -_DSD ----- - -_DSD (Device Specific Data) [7] is a predefined ACPI device -configuration object that can be used to convey information on -hardware features which are not specifically covered by the ACPI -specification [1][6]. There are two _DSD extensions that are relevant -for graphs: property [4] and hierarchical data extensions [5]. The -property extension provides generic key-value pairs whereas the -hierarchical data extension supports nodes with references to other -nodes, forming a tree. The nodes in the tree may contain properties as -defined by the property extension. The two extensions together provide -a tree-like structure with zero or more properties (key-value pairs) -in each node of the tree. - -The data structure may be accessed at runtime by using the device_* -and fwnode_* functions defined in include/linux/fwnode.h . - -Fwnode represents a generic firmware node object. It is independent on -the firmware type. In ACPI, fwnodes are _DSD hierarchical data -extensions objects. A device's _DSD object is represented by an -fwnode. - -The data structure may be referenced to elsewhere in the ACPI tables -by using a hard reference to the device itself and an index to the -hierarchical data extension array on each depth. - - -Ports and endpoints -------------------- - -The port and endpoint concepts are very similar to those in Devicetree -[3]. A port represents an interface in a device, and an endpoint -represents a connection to that interface. - -All port nodes are located under the device's "_DSD" node in the hierarchical -data extension tree. The data extension related to each port node must begin -with "port" and must be followed by the "@" character and the number of the port -as its key. The target object it refers to should be called "PRTX", where "X" is -the number of the port. An example of such a package would be: - - Package() { "port@4", PRT4 } - -Further on, endpoints are located under the port nodes. The hierarchical -data extension key of the endpoint nodes must begin with -"endpoint" and must be followed by the "@" character and the number of the -endpoint. The object it refers to should be called "EPXY", where "X" is the -number of the port and "Y" is the number of the endpoint. An example of such a -package would be: - - Package() { "endpoint@0", EP40 } - -Each port node contains a property extension key "port", the value of which is -the number of the port. Each endpoint is similarly numbered with a property -extension key "reg", the value of which is the number of the endpoint. Port -numbers must be unique within a device and endpoint numbers must be unique -within a port. If a device object may only has a single port, then the number -of that port shall be zero. Similarly, if a port may only have a single -endpoint, the number of that endpoint shall be zero. - -The endpoint reference uses property extension with "remote-endpoint" property -name followed by a reference in the same package. Such references consist of the -the remote device reference, the first package entry of the port data extension -reference under the device and finally the first package entry of the endpoint -data extension reference under the port. Individual references thus appear as: - - Package() { device, "port@X", "endpoint@Y" } - -In the above example, "X" is the number of the port and "Y" is the number of the -endpoint. - -The references to endpoints must be always done both ways, to the -remote endpoint and back from the referred remote endpoint node. - -A simple example of this is show below: - - Scope (\_SB.PCI0.I2C2) - { - Device (CAM0) - { - Name (_DSD, Package () { - ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), - Package () { - Package () { "compatible", Package () { "nokia,smia" } }, - }, - ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), - Package () { - Package () { "port@0", PRT0 }, - } - }) - Name (PRT0, Package() { - ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), - Package () { - Package () { "reg", 0 }, - }, - ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), - Package () { - Package () { "endpoint@0", EP00 }, - } - }) - Name (EP00, Package() { - ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), - Package () { - Package () { "reg", 0 }, - Package () { "remote-endpoint", Package() { \_SB.PCI0.ISP, "port@4", "endpoint@0" } }, - } - }) - } - } - - Scope (\_SB.PCI0) - { - Device (ISP) - { - Name (_DSD, Package () { - ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), - Package () { - Package () { "port@4", PRT4 }, - } - }) - - Name (PRT4, Package() { - ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), - Package () { - Package () { "reg", 4 }, /* CSI-2 port number */ - }, - ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), - Package () { - Package () { "endpoint@0", EP40 }, - } - }) - - Name (EP40, Package() { - ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), - Package () { - Package () { "reg", 0 }, - Package () { "remote-endpoint", Package () { \_SB.PCI0.I2C2.CAM0, "port@0", "endpoint@0" } }, - } - }) - } - } - -Here, the port 0 of the "CAM0" device is connected to the port 4 of -the "ISP" device and vice versa. - - -References ----------- - -[1] _DSD (Device Specific Data) Implementation Guide. - , - referenced 2016-10-03. - -[2] Devicetree. , referenced 2016-10-03. - -[3] Documentation/devicetree/bindings/graph.txt - -[4] Device Properties UUID For _DSD. - , - referenced 2016-10-04. - -[5] Hierarchical Data Extension UUID For _DSD. - , - referenced 2016-10-04. - -[6] Advanced Configuration and Power Interface Specification. - , - referenced 2016-10-04. - -[7] _DSD Device Properties Usage Rules. - Documentation/acpi/DSD-properties-rules.txt diff --git a/Documentation/firmware-guide/acpi/dsd/graph.rst b/Documentation/firmware-guide/acpi/dsd/graph.rst new file mode 100644 index 000000000000..e0baed35b037 --- /dev/null +++ b/Documentation/firmware-guide/acpi/dsd/graph.rst @@ -0,0 +1,177 @@ +.. SPDX-License-Identifier: GPL-2.0 + +====== +Graphs +====== + +_DSD +==== + +_DSD (Device Specific Data) [7] is a predefined ACPI device +configuration object that can be used to convey information on +hardware features which are not specifically covered by the ACPI +specification [1][6]. There are two _DSD extensions that are relevant +for graphs: property [4] and hierarchical data extensions [5]. The +property extension provides generic key-value pairs whereas the +hierarchical data extension supports nodes with references to other +nodes, forming a tree. The nodes in the tree may contain properties as +defined by the property extension. The two extensions together provide +a tree-like structure with zero or more properties (key-value pairs) +in each node of the tree. + +The data structure may be accessed at runtime by using the device_* +and fwnode_* functions defined in include/linux/fwnode.h . + +Fwnode represents a generic firmware node object. It is independent on +the firmware type. In ACPI, fwnodes are _DSD hierarchical data +extensions objects. A device's _DSD object is represented by an +fwnode. + +The data structure may be referenced to elsewhere in the ACPI tables +by using a hard reference to the device itself and an index to the +hierarchical data extension array on each depth. + + +Ports and endpoints +=================== + +The port and endpoint concepts are very similar to those in Devicetree +[3]. A port represents an interface in a device, and an endpoint +represents a connection to that interface. + +All port nodes are located under the device's "_DSD" node in the hierarchical +data extension tree. The data extension related to each port node must begin +with "port" and must be followed by the "@" character and the number of the +port as its key. The target object it refers to should be called "PRTX", where +"X" is the number of the port. An example of such a package would be:: + + Package() { "port@4", PRT4 } + +Further on, endpoints are located under the port nodes. The hierarchical +data extension key of the endpoint nodes must begin with +"endpoint" and must be followed by the "@" character and the number of the +endpoint. The object it refers to should be called "EPXY", where "X" is the +number of the port and "Y" is the number of the endpoint. An example of such a +package would be:: + + Package() { "endpoint@0", EP40 } + +Each port node contains a property extension key "port", the value of which is +the number of the port. Each endpoint is similarly numbered with a property +extension key "reg", the value of which is the number of the endpoint. Port +numbers must be unique within a device and endpoint numbers must be unique +within a port. If a device object may only has a single port, then the number +of that port shall be zero. Similarly, if a port may only have a single +endpoint, the number of that endpoint shall be zero. + +The endpoint reference uses property extension with "remote-endpoint" property +name followed by a reference in the same package. Such references consist of +the remote device reference, the first package entry of the port data extension +reference under the device and finally the first package entry of the endpoint +data extension reference under the port. Individual references thus appear as:: + + Package() { device, "port@X", "endpoint@Y" } + +In the above example, "X" is the number of the port and "Y" is the number of +the endpoint. + +The references to endpoints must be always done both ways, to the +remote endpoint and back from the referred remote endpoint node. + +A simple example of this is show below:: + + Scope (\_SB.PCI0.I2C2) + { + Device (CAM0) + { + Name (_DSD, Package () { + ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), + Package () { + Package () { "compatible", Package () { "nokia,smia" } }, + }, + ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), + Package () { + Package () { "port@0", PRT0 }, + } + }) + Name (PRT0, Package() { + ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), + Package () { + Package () { "reg", 0 }, + }, + ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), + Package () { + Package () { "endpoint@0", EP00 }, + } + }) + Name (EP00, Package() { + ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), + Package () { + Package () { "reg", 0 }, + Package () { "remote-endpoint", Package() { \_SB.PCI0.ISP, "port@4", "endpoint@0" } }, + } + }) + } + } + + Scope (\_SB.PCI0) + { + Device (ISP) + { + Name (_DSD, Package () { + ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), + Package () { + Package () { "port@4", PRT4 }, + } + }) + + Name (PRT4, Package() { + ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), + Package () { + Package () { "reg", 4 }, /* CSI-2 port number */ + }, + ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), + Package () { + Package () { "endpoint@0", EP40 }, + } + }) + + Name (EP40, Package() { + ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), + Package () { + Package () { "reg", 0 }, + Package () { "remote-endpoint", Package () { \_SB.PCI0.I2C2.CAM0, "port@0", "endpoint@0" } }, + } + }) + } + } + +Here, the port 0 of the "CAM0" device is connected to the port 4 of +the "ISP" device and vice versa. + + +References +========== + +[1] _DSD (Device Specific Data) Implementation Guide. + http://www.uefi.org/sites/default/files/resources/_DSD-implementation-guide-toplevel-1_1.htm, + referenced 2016-10-03. + +[2] Devicetree. http://www.devicetree.org, referenced 2016-10-03. + +[3] Documentation/devicetree/bindings/graph.txt + +[4] Device Properties UUID For _DSD. + http://www.uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf, + referenced 2016-10-04. + +[5] Hierarchical Data Extension UUID For _DSD. + http://www.uefi.org/sites/default/files/resources/_DSD-hierarchical-data-extension-UUID-v1.1.pdf, + referenced 2016-10-04. + +[6] Advanced Configuration and Power Interface Specification. + http://www.uefi.org/sites/default/files/resources/ACPI_6_1.pdf, + referenced 2016-10-04. + +[7] _DSD Device Properties Usage Rules. + :doc:`../DSD-properties-rules` diff --git a/Documentation/firmware-guide/acpi/index.rst b/Documentation/firmware-guide/acpi/index.rst index bedcb0b242a2..f81cfbcb6878 100644 --- a/Documentation/firmware-guide/acpi/index.rst +++ b/Documentation/firmware-guide/acpi/index.rst @@ -8,6 +8,7 @@ ACPI Support :maxdepth: 1 namespace + dsd/graph enumeration osi method-customizing -- cgit v1.2.3 From 05000042f33dd8b2afbeedc1d8fd499486d14b0d Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 01:52:57 +0800 Subject: Documentation: ACPI: move dsd/data-node-references.txt to firmware-guide/acpi and convert to reST This converts the plain text documentation to reStructuredText format and adds it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/dsd/data-node-references.txt | 89 --------------------- .../acpi/dsd/data-node-references.rst | 93 ++++++++++++++++++++++ Documentation/firmware-guide/acpi/index.rst | 1 + 3 files changed, 94 insertions(+), 89 deletions(-) delete mode 100644 Documentation/acpi/dsd/data-node-references.txt create mode 100644 Documentation/firmware-guide/acpi/dsd/data-node-references.rst (limited to 'Documentation') diff --git a/Documentation/acpi/dsd/data-node-references.txt b/Documentation/acpi/dsd/data-node-references.txt deleted file mode 100644 index c3871565c8cf..000000000000 --- a/Documentation/acpi/dsd/data-node-references.txt +++ /dev/null @@ -1,89 +0,0 @@ -Copyright (C) 2018 Intel Corporation -Author: Sakari Ailus - - -Referencing hierarchical data nodes ------------------------------------ - -ACPI in general allows referring to device objects in the tree only. -Hierarchical data extension nodes may not be referred to directly, hence this -document defines a scheme to implement such references. - -A reference consist of the device object name followed by one or more -hierarchical data extension [1] keys. Specifically, the hierarchical data -extension node which is referred to by the key shall lie directly under the -parent object i.e. either the device object or another hierarchical data -extension node. - -The keys in the hierarchical data nodes shall consist of the name of the node, -"@" character and the number of the node in hexadecimal notation (without pre- -or postfixes). The same ACPI object shall include the _DSD property extension -with a property "reg" that shall have the same numerical value as the number of -the node. - -In case a hierarchical data extensions node has no numerical value, then the -"reg" property shall be omitted from the ACPI object's _DSD properties and the -"@" character and the number shall be omitted from the hierarchical data -extension key. - - -Example -------- - - In the ASL snippet below, the "reference" _DSD property [2] contains a - device object reference to DEV0 and under that device object, a - hierarchical data extension key "node@1" referring to the NOD1 object - and lastly, a hierarchical data extension key "anothernode" referring to - the ANOD object which is also the final target node of the reference. - - Device (DEV0) - { - Name (_DSD, Package () { - ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), - Package () { - Package () { "node@0", NOD0 }, - Package () { "node@1", NOD1 }, - } - }) - Name (NOD0, Package() { - ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), - Package () { - Package () { "random-property", 3 }, - } - }) - Name (NOD1, Package() { - ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), - Package () { - Package () { "anothernode", ANOD }, - } - }) - Name (ANOD, Package() { - ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), - Package () { - Package () { "random-property", 0 }, - } - }) - } - - Device (DEV1) - { - Name (_DSD, Package () { - ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), - Package () { - Package () { "reference", ^DEV0, "node@1", "anothernode" }, - } - }) - } - -Please also see a graph example in graph.txt . - -References ----------- - -[1] Hierarchical Data Extension UUID For _DSD. - , - referenced 2018-07-17. - -[2] Device Properties UUID For _DSD. - , - referenced 2016-10-04. diff --git a/Documentation/firmware-guide/acpi/dsd/data-node-references.rst b/Documentation/firmware-guide/acpi/dsd/data-node-references.rst new file mode 100644 index 000000000000..1351984e767c --- /dev/null +++ b/Documentation/firmware-guide/acpi/dsd/data-node-references.rst @@ -0,0 +1,93 @@ +.. SPDX-License-Identifier: GPL-2.0 +.. include:: + +=================================== +Referencing hierarchical data nodes +=================================== + +:Copyright: |copy| 2018 Intel Corporation +:Author: Sakari Ailus + +ACPI in general allows referring to device objects in the tree only. +Hierarchical data extension nodes may not be referred to directly, hence this +document defines a scheme to implement such references. + +A reference consist of the device object name followed by one or more +hierarchical data extension [1] keys. Specifically, the hierarchical data +extension node which is referred to by the key shall lie directly under the +parent object i.e. either the device object or another hierarchical data +extension node. + +The keys in the hierarchical data nodes shall consist of the name of the node, +"@" character and the number of the node in hexadecimal notation (without pre- +or postfixes). The same ACPI object shall include the _DSD property extension +with a property "reg" that shall have the same numerical value as the number of +the node. + +In case a hierarchical data extensions node has no numerical value, then the +"reg" property shall be omitted from the ACPI object's _DSD properties and the +"@" character and the number shall be omitted from the hierarchical data +extension key. + + +Example +======= + +In the ASL snippet below, the "reference" _DSD property [2] contains a +device object reference to DEV0 and under that device object, a +hierarchical data extension key "node@1" referring to the NOD1 object +and lastly, a hierarchical data extension key "anothernode" referring to +the ANOD object which is also the final target node of the reference. +:: + + Device (DEV0) + { + Name (_DSD, Package () { + ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), + Package () { + Package () { "node@0", NOD0 }, + Package () { "node@1", NOD1 }, + } + }) + Name (NOD0, Package() { + ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), + Package () { + Package () { "random-property", 3 }, + } + }) + Name (NOD1, Package() { + ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), + Package () { + Package () { "anothernode", ANOD }, + } + }) + Name (ANOD, Package() { + ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), + Package () { + Package () { "random-property", 0 }, + } + }) + } + + Device (DEV1) + { + Name (_DSD, Package () { + ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), + Package () { + Package () { "reference", ^DEV0, "node@1", "anothernode" }, + } + }) + } + +Please also see a graph example in :doc:`graph`. + +References +========== + +[1] Hierarchical Data Extension UUID For _DSD. +, +referenced 2018-07-17. + +[2] Device Properties UUID For _DSD. +, +referenced 2016-10-04. diff --git a/Documentation/firmware-guide/acpi/index.rst b/Documentation/firmware-guide/acpi/index.rst index f81cfbcb6878..6d4e0df4f063 100644 --- a/Documentation/firmware-guide/acpi/index.rst +++ b/Documentation/firmware-guide/acpi/index.rst @@ -9,6 +9,7 @@ ACPI Support namespace dsd/graph + dsd/data-node-references enumeration osi method-customizing -- cgit v1.2.3 From 99ed6bfaa5a0a4bffc10ff3ffe9c599bcf59236e Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 01:52:58 +0800 Subject: Documentation: ACPI: move debug.txt to firmware-guide/acpi and convert to reST This converts the plain text documentation to reStructuredText format and adds it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/debug.txt | 148 --------------------------- Documentation/firmware-guide/acpi/debug.rst | 151 ++++++++++++++++++++++++++++ Documentation/firmware-guide/acpi/index.rst | 3 +- 3 files changed, 153 insertions(+), 149 deletions(-) delete mode 100644 Documentation/acpi/debug.txt create mode 100644 Documentation/firmware-guide/acpi/debug.rst (limited to 'Documentation') diff --git a/Documentation/acpi/debug.txt b/Documentation/acpi/debug.txt deleted file mode 100644 index 65bf47c46b6d..000000000000 --- a/Documentation/acpi/debug.txt +++ /dev/null @@ -1,148 +0,0 @@ - ACPI Debug Output - - -The ACPI CA, the Linux ACPI core, and some ACPI drivers can generate debug -output. This document describes how to use this facility. - -Compile-time configuration --------------------------- - -ACPI debug output is globally enabled by CONFIG_ACPI_DEBUG. If this config -option is turned off, the debug messages are not even built into the -kernel. - -Boot- and run-time configuration --------------------------------- - -When CONFIG_ACPI_DEBUG=y, you can select the component and level of messages -you're interested in. At boot-time, use the acpi.debug_layer and -acpi.debug_level kernel command line options. After boot, you can use the -debug_layer and debug_level files in /sys/module/acpi/parameters/ to control -the debug messages. - -debug_layer (component) ------------------------ - -The "debug_layer" is a mask that selects components of interest, e.g., a -specific driver or part of the ACPI interpreter. To build the debug_layer -bitmask, look for the "#define _COMPONENT" in an ACPI source file. - -You can set the debug_layer mask at boot-time using the acpi.debug_layer -command line argument, and you can change it after boot by writing values -to /sys/module/acpi/parameters/debug_layer. - -The possible components are defined in include/acpi/acoutput.h and -include/acpi/acpi_drivers.h. Reading /sys/module/acpi/parameters/debug_layer -shows the supported mask values, currently these: - - ACPI_UTILITIES 0x00000001 - ACPI_HARDWARE 0x00000002 - ACPI_EVENTS 0x00000004 - ACPI_TABLES 0x00000008 - ACPI_NAMESPACE 0x00000010 - ACPI_PARSER 0x00000020 - ACPI_DISPATCHER 0x00000040 - ACPI_EXECUTER 0x00000080 - ACPI_RESOURCES 0x00000100 - ACPI_CA_DEBUGGER 0x00000200 - ACPI_OS_SERVICES 0x00000400 - ACPI_CA_DISASSEMBLER 0x00000800 - ACPI_COMPILER 0x00001000 - ACPI_TOOLS 0x00002000 - ACPI_BUS_COMPONENT 0x00010000 - ACPI_AC_COMPONENT 0x00020000 - ACPI_BATTERY_COMPONENT 0x00040000 - ACPI_BUTTON_COMPONENT 0x00080000 - ACPI_SBS_COMPONENT 0x00100000 - ACPI_FAN_COMPONENT 0x00200000 - ACPI_PCI_COMPONENT 0x00400000 - ACPI_POWER_COMPONENT 0x00800000 - ACPI_CONTAINER_COMPONENT 0x01000000 - ACPI_SYSTEM_COMPONENT 0x02000000 - ACPI_THERMAL_COMPONENT 0x04000000 - ACPI_MEMORY_DEVICE_COMPONENT 0x08000000 - ACPI_VIDEO_COMPONENT 0x10000000 - ACPI_PROCESSOR_COMPONENT 0x20000000 - -debug_level ------------ - -The "debug_level" is a mask that selects different types of messages, e.g., -those related to initialization, method execution, informational messages, etc. -To build debug_level, look at the level specified in an ACPI_DEBUG_PRINT() -statement. - -The ACPI interpreter uses several different levels, but the Linux -ACPI core and ACPI drivers generally only use ACPI_LV_INFO. - -You can set the debug_level mask at boot-time using the acpi.debug_level -command line argument, and you can change it after boot by writing values -to /sys/module/acpi/parameters/debug_level. - -The possible levels are defined in include/acpi/acoutput.h. Reading -/sys/module/acpi/parameters/debug_level shows the supported mask values, -currently these: - - ACPI_LV_INIT 0x00000001 - ACPI_LV_DEBUG_OBJECT 0x00000002 - ACPI_LV_INFO 0x00000004 - ACPI_LV_INIT_NAMES 0x00000020 - ACPI_LV_PARSE 0x00000040 - ACPI_LV_LOAD 0x00000080 - ACPI_LV_DISPATCH 0x00000100 - ACPI_LV_EXEC 0x00000200 - ACPI_LV_NAMES 0x00000400 - ACPI_LV_OPREGION 0x00000800 - ACPI_LV_BFIELD 0x00001000 - ACPI_LV_TABLES 0x00002000 - ACPI_LV_VALUES 0x00004000 - ACPI_LV_OBJECTS 0x00008000 - ACPI_LV_RESOURCES 0x00010000 - ACPI_LV_USER_REQUESTS 0x00020000 - ACPI_LV_PACKAGE 0x00040000 - ACPI_LV_ALLOCATIONS 0x00100000 - ACPI_LV_FUNCTIONS 0x00200000 - ACPI_LV_OPTIMIZATIONS 0x00400000 - ACPI_LV_MUTEX 0x01000000 - ACPI_LV_THREADS 0x02000000 - ACPI_LV_IO 0x04000000 - ACPI_LV_INTERRUPTS 0x08000000 - ACPI_LV_AML_DISASSEMBLE 0x10000000 - ACPI_LV_VERBOSE_INFO 0x20000000 - ACPI_LV_FULL_TABLES 0x40000000 - ACPI_LV_EVENTS 0x80000000 - -Examples --------- - -For example, drivers/acpi/bus.c contains this: - - #define _COMPONENT ACPI_BUS_COMPONENT - ... - ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Device insertion detected\n")); - -To turn on this message, set the ACPI_BUS_COMPONENT bit in acpi.debug_layer -and the ACPI_LV_INFO bit in acpi.debug_level. (The ACPI_DEBUG_PRINT -statement uses ACPI_DB_INFO, which is macro based on the ACPI_LV_INFO -definition.) - -Enable all AML "Debug" output (stores to the Debug object while interpreting -AML) during boot: - - acpi.debug_layer=0xffffffff acpi.debug_level=0x2 - -Enable PCI and PCI interrupt routing debug messages: - - acpi.debug_layer=0x400000 acpi.debug_level=0x4 - -Enable all ACPI hardware-related messages: - - acpi.debug_layer=0x2 acpi.debug_level=0xffffffff - -Enable all ACPI_DB_INFO messages after boot: - - # echo 0x4 > /sys/module/acpi/parameters/debug_level - -Show all valid component values: - - # cat /sys/module/acpi/parameters/debug_layer diff --git a/Documentation/firmware-guide/acpi/debug.rst b/Documentation/firmware-guide/acpi/debug.rst new file mode 100644 index 000000000000..1a152dd1d765 --- /dev/null +++ b/Documentation/firmware-guide/acpi/debug.rst @@ -0,0 +1,151 @@ +.. SPDX-License-Identifier: GPL-2.0 + +================= +ACPI Debug Output +================= + +The ACPI CA, the Linux ACPI core, and some ACPI drivers can generate debug +output. This document describes how to use this facility. + +Compile-time configuration +========================== + +ACPI debug output is globally enabled by CONFIG_ACPI_DEBUG. If this config +option is turned off, the debug messages are not even built into the +kernel. + +Boot- and run-time configuration +================================ + +When CONFIG_ACPI_DEBUG=y, you can select the component and level of messages +you're interested in. At boot-time, use the acpi.debug_layer and +acpi.debug_level kernel command line options. After boot, you can use the +debug_layer and debug_level files in /sys/module/acpi/parameters/ to control +the debug messages. + +debug_layer (component) +======================= + +The "debug_layer" is a mask that selects components of interest, e.g., a +specific driver or part of the ACPI interpreter. To build the debug_layer +bitmask, look for the "#define _COMPONENT" in an ACPI source file. + +You can set the debug_layer mask at boot-time using the acpi.debug_layer +command line argument, and you can change it after boot by writing values +to /sys/module/acpi/parameters/debug_layer. + +The possible components are defined in include/acpi/acoutput.h and +include/acpi/acpi_drivers.h. Reading /sys/module/acpi/parameters/debug_layer +shows the supported mask values, currently these:: + + ACPI_UTILITIES 0x00000001 + ACPI_HARDWARE 0x00000002 + ACPI_EVENTS 0x00000004 + ACPI_TABLES 0x00000008 + ACPI_NAMESPACE 0x00000010 + ACPI_PARSER 0x00000020 + ACPI_DISPATCHER 0x00000040 + ACPI_EXECUTER 0x00000080 + ACPI_RESOURCES 0x00000100 + ACPI_CA_DEBUGGER 0x00000200 + ACPI_OS_SERVICES 0x00000400 + ACPI_CA_DISASSEMBLER 0x00000800 + ACPI_COMPILER 0x00001000 + ACPI_TOOLS 0x00002000 + ACPI_BUS_COMPONENT 0x00010000 + ACPI_AC_COMPONENT 0x00020000 + ACPI_BATTERY_COMPONENT 0x00040000 + ACPI_BUTTON_COMPONENT 0x00080000 + ACPI_SBS_COMPONENT 0x00100000 + ACPI_FAN_COMPONENT 0x00200000 + ACPI_PCI_COMPONENT 0x00400000 + ACPI_POWER_COMPONENT 0x00800000 + ACPI_CONTAINER_COMPONENT 0x01000000 + ACPI_SYSTEM_COMPONENT 0x02000000 + ACPI_THERMAL_COMPONENT 0x04000000 + ACPI_MEMORY_DEVICE_COMPONENT 0x08000000 + ACPI_VIDEO_COMPONENT 0x10000000 + ACPI_PROCESSOR_COMPONENT 0x20000000 + +debug_level +=========== + +The "debug_level" is a mask that selects different types of messages, e.g., +those related to initialization, method execution, informational messages, etc. +To build debug_level, look at the level specified in an ACPI_DEBUG_PRINT() +statement. + +The ACPI interpreter uses several different levels, but the Linux +ACPI core and ACPI drivers generally only use ACPI_LV_INFO. + +You can set the debug_level mask at boot-time using the acpi.debug_level +command line argument, and you can change it after boot by writing values +to /sys/module/acpi/parameters/debug_level. + +The possible levels are defined in include/acpi/acoutput.h. Reading +/sys/module/acpi/parameters/debug_level shows the supported mask values, +currently these:: + + ACPI_LV_INIT 0x00000001 + ACPI_LV_DEBUG_OBJECT 0x00000002 + ACPI_LV_INFO 0x00000004 + ACPI_LV_INIT_NAMES 0x00000020 + ACPI_LV_PARSE 0x00000040 + ACPI_LV_LOAD 0x00000080 + ACPI_LV_DISPATCH 0x00000100 + ACPI_LV_EXEC 0x00000200 + ACPI_LV_NAMES 0x00000400 + ACPI_LV_OPREGION 0x00000800 + ACPI_LV_BFIELD 0x00001000 + ACPI_LV_TABLES 0x00002000 + ACPI_LV_VALUES 0x00004000 + ACPI_LV_OBJECTS 0x00008000 + ACPI_LV_RESOURCES 0x00010000 + ACPI_LV_USER_REQUESTS 0x00020000 + ACPI_LV_PACKAGE 0x00040000 + ACPI_LV_ALLOCATIONS 0x00100000 + ACPI_LV_FUNCTIONS 0x00200000 + ACPI_LV_OPTIMIZATIONS 0x00400000 + ACPI_LV_MUTEX 0x01000000 + ACPI_LV_THREADS 0x02000000 + ACPI_LV_IO 0x04000000 + ACPI_LV_INTERRUPTS 0x08000000 + ACPI_LV_AML_DISASSEMBLE 0x10000000 + ACPI_LV_VERBOSE_INFO 0x20000000 + ACPI_LV_FULL_TABLES 0x40000000 + ACPI_LV_EVENTS 0x80000000 + +Examples +======== + +For example, drivers/acpi/bus.c contains this:: + + #define _COMPONENT ACPI_BUS_COMPONENT + ... + ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Device insertion detected\n")); + +To turn on this message, set the ACPI_BUS_COMPONENT bit in acpi.debug_layer +and the ACPI_LV_INFO bit in acpi.debug_level. (The ACPI_DEBUG_PRINT +statement uses ACPI_DB_INFO, which is macro based on the ACPI_LV_INFO +definition.) + +Enable all AML "Debug" output (stores to the Debug object while interpreting +AML) during boot:: + + acpi.debug_layer=0xffffffff acpi.debug_level=0x2 + +Enable PCI and PCI interrupt routing debug messages:: + + acpi.debug_layer=0x400000 acpi.debug_level=0x4 + +Enable all ACPI hardware-related messages:: + + acpi.debug_layer=0x2 acpi.debug_level=0xffffffff + +Enable all ACPI_DB_INFO messages after boot:: + + # echo 0x4 > /sys/module/acpi/parameters/debug_level + +Show all valid component values:: + + # cat /sys/module/acpi/parameters/debug_layer diff --git a/Documentation/firmware-guide/acpi/index.rst b/Documentation/firmware-guide/acpi/index.rst index 6d4e0df4f063..a45fea11f998 100644 --- a/Documentation/firmware-guide/acpi/index.rst +++ b/Documentation/firmware-guide/acpi/index.rst @@ -14,6 +14,7 @@ ACPI Support osi method-customizing DSD-properties-rules + debug gpio-properties i2c-muxes - acpi-lid \ No newline at end of file + acpi-lid -- cgit v1.2.3 From 3c03a1bde4dcedef8fb287e348de959d81d04ca6 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 01:52:59 +0800 Subject: Documentation: ACPI: move method-tracing.txt to firmware-guide/acpi and convert to rsST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/method-tracing.txt | 192 ----------------- Documentation/firmware-guide/acpi/index.rst | 1 + .../firmware-guide/acpi/method-tracing.rst | 238 +++++++++++++++++++++ 3 files changed, 239 insertions(+), 192 deletions(-) delete mode 100644 Documentation/acpi/method-tracing.txt create mode 100644 Documentation/firmware-guide/acpi/method-tracing.rst (limited to 'Documentation') diff --git a/Documentation/acpi/method-tracing.txt b/Documentation/acpi/method-tracing.txt deleted file mode 100644 index 0aba14c8f459..000000000000 --- a/Documentation/acpi/method-tracing.txt +++ /dev/null @@ -1,192 +0,0 @@ -ACPICA Trace Facility - -Copyright (C) 2015, Intel Corporation -Author: Lv Zheng - - -Abstract: - -This document describes the functions and the interfaces of the method -tracing facility. - -1. Functionalities and usage examples: - - ACPICA provides method tracing capability. And two functions are - currently implemented using this capability. - - A. Log reducer - ACPICA subsystem provides debugging outputs when CONFIG_ACPI_DEBUG is - enabled. The debugging messages which are deployed via - ACPI_DEBUG_PRINT() macro can be reduced at 2 levels - per-component - level (known as debug layer, configured via - /sys/module/acpi/parameters/debug_layer) and per-type level (known as - debug level, configured via /sys/module/acpi/parameters/debug_level). - - But when the particular layer/level is applied to the control method - evaluations, the quantity of the debugging outputs may still be too - large to be put into the kernel log buffer. The idea thus is worked out - to only enable the particular debug layer/level (normally more detailed) - logs when the control method evaluation is started, and disable the - detailed logging when the control method evaluation is stopped. - - The following command examples illustrate the usage of the "log reducer" - functionality: - a. Filter out the debug layer/level matched logs when control methods - are being evaluated: - # cd /sys/module/acpi/parameters - # echo "0xXXXXXXXX" > trace_debug_layer - # echo "0xYYYYYYYY" > trace_debug_level - # echo "enable" > trace_state - b. Filter out the debug layer/level matched logs when the specified - control method is being evaluated: - # cd /sys/module/acpi/parameters - # echo "0xXXXXXXXX" > trace_debug_layer - # echo "0xYYYYYYYY" > trace_debug_level - # echo "\PPPP.AAAA.TTTT.HHHH" > trace_method_name - # echo "method" > /sys/module/acpi/parameters/trace_state - c. Filter out the debug layer/level matched logs when the specified - control method is being evaluated for the first time: - # cd /sys/module/acpi/parameters - # echo "0xXXXXXXXX" > trace_debug_layer - # echo "0xYYYYYYYY" > trace_debug_level - # echo "\PPPP.AAAA.TTTT.HHHH" > trace_method_name - # echo "method-once" > /sys/module/acpi/parameters/trace_state - Where: - 0xXXXXXXXX/0xYYYYYYYY: Refer to Documentation/acpi/debug.txt for - possible debug layer/level masking values. - \PPPP.AAAA.TTTT.HHHH: Full path of a control method that can be found - in the ACPI namespace. It needn't be an entry - of a control method evaluation. - - B. AML tracer - - There are special log entries added by the method tracing facility at - the "trace points" the AML interpreter starts/stops to execute a control - method, or an AML opcode. Note that the format of the log entries are - subject to change: - [ 0.186427] exdebug-0398 ex_trace_point : Method Begin [0xf58394d8:\_SB.PCI0.LPCB.ECOK] execution. - [ 0.186630] exdebug-0398 ex_trace_point : Opcode Begin [0xf5905c88:If] execution. - [ 0.186820] exdebug-0398 ex_trace_point : Opcode Begin [0xf5905cc0:LEqual] execution. - [ 0.187010] exdebug-0398 ex_trace_point : Opcode Begin [0xf5905a20:-NamePath-] execution. - [ 0.187214] exdebug-0398 ex_trace_point : Opcode End [0xf5905a20:-NamePath-] execution. - [ 0.187407] exdebug-0398 ex_trace_point : Opcode Begin [0xf5905f60:One] execution. - [ 0.187594] exdebug-0398 ex_trace_point : Opcode End [0xf5905f60:One] execution. - [ 0.187789] exdebug-0398 ex_trace_point : Opcode End [0xf5905cc0:LEqual] execution. - [ 0.187980] exdebug-0398 ex_trace_point : Opcode Begin [0xf5905cc0:Return] execution. - [ 0.188146] exdebug-0398 ex_trace_point : Opcode Begin [0xf5905f60:One] execution. - [ 0.188334] exdebug-0398 ex_trace_point : Opcode End [0xf5905f60:One] execution. - [ 0.188524] exdebug-0398 ex_trace_point : Opcode End [0xf5905cc0:Return] execution. - [ 0.188712] exdebug-0398 ex_trace_point : Opcode End [0xf5905c88:If] execution. - [ 0.188903] exdebug-0398 ex_trace_point : Method End [0xf58394d8:\_SB.PCI0.LPCB.ECOK] execution. - - Developers can utilize these special log entries to track the AML - interpretion, thus can aid issue debugging and performance tuning. Note - that, as the "AML tracer" logs are implemented via ACPI_DEBUG_PRINT() - macro, CONFIG_ACPI_DEBUG is also required to be enabled for enabling - "AML tracer" logs. - - The following command examples illustrate the usage of the "AML tracer" - functionality: - a. Filter out the method start/stop "AML tracer" logs when control - methods are being evaluated: - # cd /sys/module/acpi/parameters - # echo "0x80" > trace_debug_layer - # echo "0x10" > trace_debug_level - # echo "enable" > trace_state - b. Filter out the method start/stop "AML tracer" when the specified - control method is being evaluated: - # cd /sys/module/acpi/parameters - # echo "0x80" > trace_debug_layer - # echo "0x10" > trace_debug_level - # echo "\PPPP.AAAA.TTTT.HHHH" > trace_method_name - # echo "method" > trace_state - c. Filter out the method start/stop "AML tracer" logs when the specified - control method is being evaluated for the first time: - # cd /sys/module/acpi/parameters - # echo "0x80" > trace_debug_layer - # echo "0x10" > trace_debug_level - # echo "\PPPP.AAAA.TTTT.HHHH" > trace_method_name - # echo "method-once" > trace_state - d. Filter out the method/opcode start/stop "AML tracer" when the - specified control method is being evaluated: - # cd /sys/module/acpi/parameters - # echo "0x80" > trace_debug_layer - # echo "0x10" > trace_debug_level - # echo "\PPPP.AAAA.TTTT.HHHH" > trace_method_name - # echo "opcode" > trace_state - e. Filter out the method/opcode start/stop "AML tracer" when the - specified control method is being evaluated for the first time: - # cd /sys/module/acpi/parameters - # echo "0x80" > trace_debug_layer - # echo "0x10" > trace_debug_level - # echo "\PPPP.AAAA.TTTT.HHHH" > trace_method_name - # echo "opcode-opcode" > trace_state - - Note that all above method tracing facility related module parameters can - be used as the boot parameters, for example: - acpi.trace_debug_layer=0x80 acpi.trace_debug_level=0x10 \ - acpi.trace_method_name=\_SB.LID0._LID acpi.trace_state=opcode-once - -2. Interface descriptions: - - All method tracing functions can be configured via ACPI module - parameters that are accessible at /sys/module/acpi/parameters/: - - trace_method_name - The full path of the AML method that the user wants to trace. - Note that the full path shouldn't contain the trailing "_"s in its - name segments but may contain "\" to form an absolute path. - - trace_debug_layer - The temporary debug_layer used when the tracing feature is enabled. - Using ACPI_EXECUTER (0x80) by default, which is the debug_layer - used to match all "AML tracer" logs. - - trace_debug_level - The temporary debug_level used when the tracing feature is enabled. - Using ACPI_LV_TRACE_POINT (0x10) by default, which is the - debug_level used to match all "AML tracer" logs. - - trace_state - The status of the tracing feature. - Users can enable/disable this debug tracing feature by executing - the following command: - # echo string > /sys/module/acpi/parameters/trace_state - Where "string" should be one of the following: - "disable" - Disable the method tracing feature. - "enable" - Enable the method tracing feature. - ACPICA debugging messages matching - "trace_debug_layer/trace_debug_level" during any method - execution will be logged. - "method" - Enable the method tracing feature. - ACPICA debugging messages matching - "trace_debug_layer/trace_debug_level" during method execution - of "trace_method_name" will be logged. - "method-once" - Enable the method tracing feature. - ACPICA debugging messages matching - "trace_debug_layer/trace_debug_level" during method execution - of "trace_method_name" will be logged only once. - "opcode" - Enable the method tracing feature. - ACPICA debugging messages matching - "trace_debug_layer/trace_debug_level" during method/opcode - execution of "trace_method_name" will be logged. - "opcode-once" - Enable the method tracing feature. - ACPICA debugging messages matching - "trace_debug_layer/trace_debug_level" during method/opcode - execution of "trace_method_name" will be logged only once. - Note that, the difference between the "enable" and other feature - enabling options are: - 1. When "enable" is specified, since - "trace_debug_layer/trace_debug_level" shall apply to all control - method evaluations, after configuring "trace_state" to "enable", - "trace_method_name" will be reset to NULL. - 2. When "method/opcode" is specified, if - "trace_method_name" is NULL when "trace_state" is configured to - these options, the "trace_debug_layer/trace_debug_level" will - apply to all control method evaluations. diff --git a/Documentation/firmware-guide/acpi/index.rst b/Documentation/firmware-guide/acpi/index.rst index a45fea11f998..287a7cbd82ac 100644 --- a/Documentation/firmware-guide/acpi/index.rst +++ b/Documentation/firmware-guide/acpi/index.rst @@ -13,6 +13,7 @@ ACPI Support enumeration osi method-customizing + method-tracing DSD-properties-rules debug gpio-properties diff --git a/Documentation/firmware-guide/acpi/method-tracing.rst b/Documentation/firmware-guide/acpi/method-tracing.rst new file mode 100644 index 000000000000..d0b077b73f5f --- /dev/null +++ b/Documentation/firmware-guide/acpi/method-tracing.rst @@ -0,0 +1,238 @@ +.. SPDX-License-Identifier: GPL-2.0 +.. include:: + +===================== +ACPICA Trace Facility +===================== + +:Copyright: |copy| 2015, Intel Corporation +:Author: Lv Zheng + + +Abstract +======== +This document describes the functions and the interfaces of the +method tracing facility. + +Functionalities and usage examples +================================== + +ACPICA provides method tracing capability. And two functions are +currently implemented using this capability. + +Log reducer +----------- + +ACPICA subsystem provides debugging outputs when CONFIG_ACPI_DEBUG is +enabled. The debugging messages which are deployed via +ACPI_DEBUG_PRINT() macro can be reduced at 2 levels - per-component +level (known as debug layer, configured via +/sys/module/acpi/parameters/debug_layer) and per-type level (known as +debug level, configured via /sys/module/acpi/parameters/debug_level). + +But when the particular layer/level is applied to the control method +evaluations, the quantity of the debugging outputs may still be too +large to be put into the kernel log buffer. The idea thus is worked out +to only enable the particular debug layer/level (normally more detailed) +logs when the control method evaluation is started, and disable the +detailed logging when the control method evaluation is stopped. + +The following command examples illustrate the usage of the "log reducer" +functionality: + +a. Filter out the debug layer/level matched logs when control methods + are being evaluated:: + + # cd /sys/module/acpi/parameters + # echo "0xXXXXXXXX" > trace_debug_layer + # echo "0xYYYYYYYY" > trace_debug_level + # echo "enable" > trace_state + +b. Filter out the debug layer/level matched logs when the specified + control method is being evaluated:: + + # cd /sys/module/acpi/parameters + # echo "0xXXXXXXXX" > trace_debug_layer + # echo "0xYYYYYYYY" > trace_debug_level + # echo "\PPPP.AAAA.TTTT.HHHH" > trace_method_name + # echo "method" > /sys/module/acpi/parameters/trace_state + +c. Filter out the debug layer/level matched logs when the specified + control method is being evaluated for the first time:: + + # cd /sys/module/acpi/parameters + # echo "0xXXXXXXXX" > trace_debug_layer + # echo "0xYYYYYYYY" > trace_debug_level + # echo "\PPPP.AAAA.TTTT.HHHH" > trace_method_name + # echo "method-once" > /sys/module/acpi/parameters/trace_state + +Where: + 0xXXXXXXXX/0xYYYYYYYY + Refer to Documentation/acpi/debug.txt for possible debug layer/level + masking values. + \PPPP.AAAA.TTTT.HHHH + Full path of a control method that can be found in the ACPI namespace. + It needn't be an entry of a control method evaluation. + +AML tracer +---------- + +There are special log entries added by the method tracing facility at +the "trace points" the AML interpreter starts/stops to execute a control +method, or an AML opcode. Note that the format of the log entries are +subject to change:: + + [ 0.186427] exdebug-0398 ex_trace_point : Method Begin [0xf58394d8:\_SB.PCI0.LPCB.ECOK] execution. + [ 0.186630] exdebug-0398 ex_trace_point : Opcode Begin [0xf5905c88:If] execution. + [ 0.186820] exdebug-0398 ex_trace_point : Opcode Begin [0xf5905cc0:LEqual] execution. + [ 0.187010] exdebug-0398 ex_trace_point : Opcode Begin [0xf5905a20:-NamePath-] execution. + [ 0.187214] exdebug-0398 ex_trace_point : Opcode End [0xf5905a20:-NamePath-] execution. + [ 0.187407] exdebug-0398 ex_trace_point : Opcode Begin [0xf5905f60:One] execution. + [ 0.187594] exdebug-0398 ex_trace_point : Opcode End [0xf5905f60:One] execution. + [ 0.187789] exdebug-0398 ex_trace_point : Opcode End [0xf5905cc0:LEqual] execution. + [ 0.187980] exdebug-0398 ex_trace_point : Opcode Begin [0xf5905cc0:Return] execution. + [ 0.188146] exdebug-0398 ex_trace_point : Opcode Begin [0xf5905f60:One] execution. + [ 0.188334] exdebug-0398 ex_trace_point : Opcode End [0xf5905f60:One] execution. + [ 0.188524] exdebug-0398 ex_trace_point : Opcode End [0xf5905cc0:Return] execution. + [ 0.188712] exdebug-0398 ex_trace_point : Opcode End [0xf5905c88:If] execution. + [ 0.188903] exdebug-0398 ex_trace_point : Method End [0xf58394d8:\_SB.PCI0.LPCB.ECOK] execution. + +Developers can utilize these special log entries to track the AML +interpretion, thus can aid issue debugging and performance tuning. Note +that, as the "AML tracer" logs are implemented via ACPI_DEBUG_PRINT() +macro, CONFIG_ACPI_DEBUG is also required to be enabled for enabling +"AML tracer" logs. + +The following command examples illustrate the usage of the "AML tracer" +functionality: + +a. Filter out the method start/stop "AML tracer" logs when control + methods are being evaluated:: + + # cd /sys/module/acpi/parameters + # echo "0x80" > trace_debug_layer + # echo "0x10" > trace_debug_level + # echo "enable" > trace_state + +b. Filter out the method start/stop "AML tracer" when the specified + control method is being evaluated:: + + # cd /sys/module/acpi/parameters + # echo "0x80" > trace_debug_layer + # echo "0x10" > trace_debug_level + # echo "\PPPP.AAAA.TTTT.HHHH" > trace_method_name + # echo "method" > trace_state + +c. Filter out the method start/stop "AML tracer" logs when the specified + control method is being evaluated for the first time:: + + # cd /sys/module/acpi/parameters + # echo "0x80" > trace_debug_layer + # echo "0x10" > trace_debug_level + # echo "\PPPP.AAAA.TTTT.HHHH" > trace_method_name + # echo "method-once" > trace_state + +d. Filter out the method/opcode start/stop "AML tracer" when the + specified control method is being evaluated:: + + # cd /sys/module/acpi/parameters + # echo "0x80" > trace_debug_layer + # echo "0x10" > trace_debug_level + # echo "\PPPP.AAAA.TTTT.HHHH" > trace_method_name + # echo "opcode" > trace_state + +e. Filter out the method/opcode start/stop "AML tracer" when the + specified control method is being evaluated for the first time:: + + # cd /sys/module/acpi/parameters + # echo "0x80" > trace_debug_layer + # echo "0x10" > trace_debug_level + # echo "\PPPP.AAAA.TTTT.HHHH" > trace_method_name + # echo "opcode-opcode" > trace_state + +Note that all above method tracing facility related module parameters can +be used as the boot parameters, for example:: + + acpi.trace_debug_layer=0x80 acpi.trace_debug_level=0x10 \ + acpi.trace_method_name=\_SB.LID0._LID acpi.trace_state=opcode-once + + +Interface descriptions +====================== + +All method tracing functions can be configured via ACPI module +parameters that are accessible at /sys/module/acpi/parameters/: + +trace_method_name + The full path of the AML method that the user wants to trace. + + Note that the full path shouldn't contain the trailing "_"s in its + name segments but may contain "\" to form an absolute path. + +trace_debug_layer + The temporary debug_layer used when the tracing feature is enabled. + + Using ACPI_EXECUTER (0x80) by default, which is the debug_layer + used to match all "AML tracer" logs. + +trace_debug_level + The temporary debug_level used when the tracing feature is enabled. + + Using ACPI_LV_TRACE_POINT (0x10) by default, which is the + debug_level used to match all "AML tracer" logs. + +trace_state + The status of the tracing feature. + + Users can enable/disable this debug tracing feature by executing + the following command:: + + # echo string > /sys/module/acpi/parameters/trace_state + +Where "string" should be one of the following: + +"disable" + Disable the method tracing feature. + +"enable" + Enable the method tracing feature. + + ACPICA debugging messages matching "trace_debug_layer/trace_debug_level" + during any method execution will be logged. + +"method" + Enable the method tracing feature. + + ACPICA debugging messages matching "trace_debug_layer/trace_debug_level" + during method execution of "trace_method_name" will be logged. + +"method-once" + Enable the method tracing feature. + + ACPICA debugging messages matching "trace_debug_layer/trace_debug_level" + during method execution of "trace_method_name" will be logged only once. + +"opcode" + Enable the method tracing feature. + + ACPICA debugging messages matching "trace_debug_layer/trace_debug_level" + during method/opcode execution of "trace_method_name" will be logged. + +"opcode-once" + Enable the method tracing feature. + + ACPICA debugging messages matching "trace_debug_layer/trace_debug_level" + during method/opcode execution of "trace_method_name" will be logged only + once. + +Note that, the difference between the "enable" and other feature +enabling options are: + +1. When "enable" is specified, since + "trace_debug_layer/trace_debug_level" shall apply to all control + method evaluations, after configuring "trace_state" to "enable", + "trace_method_name" will be reset to NULL. +2. When "method/opcode" is specified, if + "trace_method_name" is NULL when "trace_state" is configured to + these options, the "trace_debug_layer/trace_debug_level" will + apply to all control method evaluations. -- cgit v1.2.3 From 472e89b4e1a87cd7f9b5ae99759a635711cf00fb Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 01:53:00 +0800 Subject: Documentation: ACPI: move aml-debugger.txt to firmware-guide/acpi and convert to reST This converts the plain text documentation to reStructuredText format and adds it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/aml-debugger.txt | 66 ------------------- Documentation/firmware-guide/acpi/aml-debugger.rst | 75 ++++++++++++++++++++++ Documentation/firmware-guide/acpi/index.rst | 1 + 3 files changed, 76 insertions(+), 66 deletions(-) delete mode 100644 Documentation/acpi/aml-debugger.txt create mode 100644 Documentation/firmware-guide/acpi/aml-debugger.rst (limited to 'Documentation') diff --git a/Documentation/acpi/aml-debugger.txt b/Documentation/acpi/aml-debugger.txt deleted file mode 100644 index 75ebeb64ab29..000000000000 --- a/Documentation/acpi/aml-debugger.txt +++ /dev/null @@ -1,66 +0,0 @@ -The AML Debugger - -Copyright (C) 2016, Intel Corporation -Author: Lv Zheng - - -This document describes the usage of the AML debugger embedded in the Linux -kernel. - -1. Build the debugger - - The following kernel configuration items are required to enable the AML - debugger interface from the Linux kernel: - - CONFIG_ACPI_DEBUGGER=y - CONFIG_ACPI_DEBUGGER_USER=m - - The userspace utilities can be built from the kernel source tree using - the following commands: - - $ cd tools - $ make acpi - - The resultant userspace tool binary is then located at: - - tools/power/acpi/acpidbg - - It can be installed to system directories by running "make install" (as a - sufficiently privileged user). - -2. Start the userspace debugger interface - - After booting the kernel with the debugger built-in, the debugger can be - started by using the following commands: - - # mount -t debugfs none /sys/kernel/debug - # modprobe acpi_dbg - # tools/power/acpi/acpidbg - - That spawns the interactive AML debugger environment where you can execute - debugger commands. - - The commands are documented in the "ACPICA Overview and Programmer Reference" - that can be downloaded from - - https://acpica.org/documentation - - The detailed debugger commands reference is located in Chapter 12 "ACPICA - Debugger Reference". The "help" command can be used for a quick reference. - -3. Stop the userspace debugger interface - - The interactive debugger interface can be closed by pressing Ctrl+C or using - the "quit" or "exit" commands. When finished, unload the module with: - - # rmmod acpi_dbg - - The module unloading may fail if there is an acpidbg instance running. - -4. Run the debugger in a script - - It may be useful to run the AML debugger in a test script. "acpidbg" supports - this in a special "batch" mode. For example, the following command outputs - the entire ACPI namespace: - - # acpidbg -b "namespace" diff --git a/Documentation/firmware-guide/acpi/aml-debugger.rst b/Documentation/firmware-guide/acpi/aml-debugger.rst new file mode 100644 index 000000000000..a889d43bc6c5 --- /dev/null +++ b/Documentation/firmware-guide/acpi/aml-debugger.rst @@ -0,0 +1,75 @@ +.. SPDX-License-Identifier: GPL-2.0 +.. include:: + +================ +The AML Debugger +================ + +:Copyright: |copy| 2016, Intel Corporation +:Author: Lv Zheng + + +This document describes the usage of the AML debugger embedded in the Linux +kernel. + +1. Build the debugger +===================== + +The following kernel configuration items are required to enable the AML +debugger interface from the Linux kernel:: + + CONFIG_ACPI_DEBUGGER=y + CONFIG_ACPI_DEBUGGER_USER=m + +The userspace utilities can be built from the kernel source tree using +the following commands:: + + $ cd tools + $ make acpi + +The resultant userspace tool binary is then located at:: + + tools/power/acpi/acpidbg + +It can be installed to system directories by running "make install" (as a +sufficiently privileged user). + +2. Start the userspace debugger interface +========================================= + +After booting the kernel with the debugger built-in, the debugger can be +started by using the following commands:: + + # mount -t debugfs none /sys/kernel/debug + # modprobe acpi_dbg + # tools/power/acpi/acpidbg + +That spawns the interactive AML debugger environment where you can execute +debugger commands. + +The commands are documented in the "ACPICA Overview and Programmer Reference" +that can be downloaded from + +https://acpica.org/documentation + +The detailed debugger commands reference is located in Chapter 12 "ACPICA +Debugger Reference". The "help" command can be used for a quick reference. + +3. Stop the userspace debugger interface +======================================== + +The interactive debugger interface can be closed by pressing Ctrl+C or using +the "quit" or "exit" commands. When finished, unload the module with:: + + # rmmod acpi_dbg + +The module unloading may fail if there is an acpidbg instance running. + +4. Run the debugger in a script +=============================== + +It may be useful to run the AML debugger in a test script. "acpidbg" supports +this in a special "batch" mode. For example, the following command outputs +the entire ACPI namespace:: + + # acpidbg -b "namespace" diff --git a/Documentation/firmware-guide/acpi/index.rst b/Documentation/firmware-guide/acpi/index.rst index 287a7cbd82ac..e9f253d54897 100644 --- a/Documentation/firmware-guide/acpi/index.rst +++ b/Documentation/firmware-guide/acpi/index.rst @@ -16,6 +16,7 @@ ACPI Support method-tracing DSD-properties-rules debug + aml-debugger gpio-properties i2c-muxes acpi-lid -- cgit v1.2.3 From deb95169ef4279362f4c6167c4c59c8d68711d97 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 01:53:01 +0800 Subject: Documentation: ACPI: move apei/output_format.txt to firmware-guide/acpi and convert to reST This converts the plain text documentation to reStructuredText format and adds it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/apei/output_format.txt | 147 -------------------- .../firmware-guide/acpi/apei/output_format.rst | 150 +++++++++++++++++++++ Documentation/firmware-guide/acpi/index.rst | 1 + 3 files changed, 151 insertions(+), 147 deletions(-) delete mode 100644 Documentation/acpi/apei/output_format.txt create mode 100644 Documentation/firmware-guide/acpi/apei/output_format.rst (limited to 'Documentation') diff --git a/Documentation/acpi/apei/output_format.txt b/Documentation/acpi/apei/output_format.txt deleted file mode 100644 index 0c49c197c47a..000000000000 --- a/Documentation/acpi/apei/output_format.txt +++ /dev/null @@ -1,147 +0,0 @@ - APEI output format - ~~~~~~~~~~~~~~~~~~ - -APEI uses printk as hardware error reporting interface, the output -format is as follow. - - := -APEI generic hardware error status -severity: , -section: , severity: , -flags: -
-fru_id: -fru_text: -section_type:
-
- -* := recoverable | fatal | corrected | info - -
# := -[primary][, containment warning][, reset][, threshold exceeded]\ -[, resource not accessible][, latent error] - -
:= generic processor error | memory error | \ -PCIe error | unknown, - -
:= - | | \ - | - - := -[processor_type: , ] -[processor_isa: , ] -[error_type: -] -[operation: , ] -[flags: -] -[level: ] -[version_info: ] -[processor_id: ] -[target_address: ] -[requestor_id: ] -[responder_id: ] -[IP: ] - -* := IA32/X64 | IA64 - -* := IA32 | IA64 | X64 - -# := -[cache error][, TLB error][, bus error][, micro-architectural error] - -* := unknown or generic | data read | data write | \ -instruction execution - -# := -[restartable][, precise IP][, overflow][, corrected] - - := -[error_status: ] -[physical_address: ] -[physical_address_mask: ] -[node: ] -[card: ] -[module: ] -[bank: ] -[device: ] -[row: ] -[column: ] -[bit_position: ] -[requestor_id: ] -[responder_id: ] -[target_id: ] -[error_type: , ] - -* := -unknown | no error | single-bit ECC | multi-bit ECC | \ -single-symbol chipkill ECC | multi-symbol chipkill ECC | master abort | \ -target abort | parity error | watchdog timeout | invalid address | \ -mirror Broken | memory sparing | scrub corrected error | \ -scrub uncorrected error - - := -[port_type: , ] -[version: .] -[command: , status: ] -[device_id: ::. -slot: -secondary_bus: -vendor_id: , device_id: -class_code: ] -[serial number: , ] -[bridge: secondary_status: , control: ] -[aer_status: , aer_mask: - -[aer_uncor_severity: ] -aer_layer=, aer_agent= -aer_tlp_header: ] - -* := PCIe end point | legacy PCI end point | \ -unknown | unknown | root port | upstream switch port | \ -downstream switch port | PCIe to PCI/PCI-X bridge | \ -PCI/PCI-X to PCIe bridge | root complex integrated endpoint device | \ -root complex event collector - -if section severity is fatal or recoverable -# := -unknown | unknown | unknown | unknown | Data Link Protocol | \ -unknown | unknown | unknown | unknown | unknown | unknown | unknown | \ -Poisoned TLP | Flow Control Protocol | Completion Timeout | \ -Completer Abort | Unexpected Completion | Receiver Overflow | \ -Malformed TLP | ECRC | Unsupported Request -else -# := -Receiver Error | unknown | unknown | unknown | unknown | unknown | \ -Bad TLP | Bad DLLP | RELAY_NUM Rollover | unknown | unknown | unknown | \ -Replay Timer Timeout | Advisory Non-Fatal -fi - - := -Physical Layer | Data Link Layer | Transaction Layer - - := -Receiver ID | Requester ID | Completer ID | Transmitter ID - -Where, [] designate corresponding content is optional - -All description with * has the following format: - -field: , - -Where value of should be the position of "string" in description. Otherwise, will be "unknown". - -All description with # has the following format: - -field: - - -Where each string in corresponding to one set bit of -. The bit position is the position of "string" in description. - -For more detailed explanation of every field, please refer to UEFI -specification version 2.3 or later, section Appendix N: Common -Platform Error Record. diff --git a/Documentation/firmware-guide/acpi/apei/output_format.rst b/Documentation/firmware-guide/acpi/apei/output_format.rst new file mode 100644 index 000000000000..c2e7ebddb529 --- /dev/null +++ b/Documentation/firmware-guide/acpi/apei/output_format.rst @@ -0,0 +1,150 @@ +.. SPDX-License-Identifier: GPL-2.0 + +================== +APEI output format +================== + +APEI uses printk as hardware error reporting interface, the output +format is as follow:: + + := + APEI generic hardware error status + severity: , + section: , severity: , + flags: +
+ fru_id: + fru_text: + section_type:
+
+ + * := recoverable | fatal | corrected | info + +
# := + [primary][, containment warning][, reset][, threshold exceeded]\ + [, resource not accessible][, latent error] + +
:= generic processor error | memory error | \ + PCIe error | unknown, + +
:= + | | \ + | + + := + [processor_type: , ] + [processor_isa: , ] + [error_type: + ] + [operation: , ] + [flags: + ] + [level: ] + [version_info: ] + [processor_id: ] + [target_address: ] + [requestor_id: ] + [responder_id: ] + [IP: ] + + * := IA32/X64 | IA64 + + * := IA32 | IA64 | X64 + + # := + [cache error][, TLB error][, bus error][, micro-architectural error] + + * := unknown or generic | data read | data write | \ + instruction execution + + # := + [restartable][, precise IP][, overflow][, corrected] + + := + [error_status: ] + [physical_address: ] + [physical_address_mask: ] + [node: ] + [card: ] + [module: ] + [bank: ] + [device: ] + [row: ] + [column: ] + [bit_position: ] + [requestor_id: ] + [responder_id: ] + [target_id: ] + [error_type: , ] + + * := + unknown | no error | single-bit ECC | multi-bit ECC | \ + single-symbol chipkill ECC | multi-symbol chipkill ECC | master abort | \ + target abort | parity error | watchdog timeout | invalid address | \ + mirror Broken | memory sparing | scrub corrected error | \ + scrub uncorrected error + + := + [port_type: , ] + [version: .] + [command: , status: ] + [device_id: ::. + slot: + secondary_bus: + vendor_id: , device_id: + class_code: ] + [serial number: , ] + [bridge: secondary_status: , control: ] + [aer_status: , aer_mask: + + [aer_uncor_severity: ] + aer_layer=, aer_agent= + aer_tlp_header: ] + + * := PCIe end point | legacy PCI end point | \ + unknown | unknown | root port | upstream switch port | \ + downstream switch port | PCIe to PCI/PCI-X bridge | \ + PCI/PCI-X to PCIe bridge | root complex integrated endpoint device | \ + root complex event collector + + if section severity is fatal or recoverable + # := + unknown | unknown | unknown | unknown | Data Link Protocol | \ + unknown | unknown | unknown | unknown | unknown | unknown | unknown | \ + Poisoned TLP | Flow Control Protocol | Completion Timeout | \ + Completer Abort | Unexpected Completion | Receiver Overflow | \ + Malformed TLP | ECRC | Unsupported Request + else + # := + Receiver Error | unknown | unknown | unknown | unknown | unknown | \ + Bad TLP | Bad DLLP | RELAY_NUM Rollover | unknown | unknown | unknown | \ + Replay Timer Timeout | Advisory Non-Fatal + fi + + := + Physical Layer | Data Link Layer | Transaction Layer + + := + Receiver ID | Requester ID | Completer ID | Transmitter ID + +Where, [] designate corresponding content is optional + +All description with * has the following format:: + + field: , + +Where value of should be the position of "string" in description. Otherwise, will be "unknown". + +All description with # has the following format:: + + field: + + +Where each string in corresponding to one set bit of +. The bit position is the position of "string" in description. + +For more detailed explanation of every field, please refer to UEFI +specification version 2.3 or later, section Appendix N: Common +Platform Error Record. diff --git a/Documentation/firmware-guide/acpi/index.rst b/Documentation/firmware-guide/acpi/index.rst index e9f253d54897..869badba6d7a 100644 --- a/Documentation/firmware-guide/acpi/index.rst +++ b/Documentation/firmware-guide/acpi/index.rst @@ -17,6 +17,7 @@ ACPI Support DSD-properties-rules debug aml-debugger + apei/output_format gpio-properties i2c-muxes acpi-lid -- cgit v1.2.3 From 440ebec745dcbc44866f6b19e5145a12d4494a5f Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 01:53:02 +0800 Subject: Documentation: ACPI: move apei/einj.txt to firmware-guide/acpi and convert to reST This converts the plain text documentation to reStructuredText format and adds it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/apei/einj.txt | 177 ----------------------- Documentation/firmware-guide/acpi/apei/einj.rst | 185 ++++++++++++++++++++++++ Documentation/firmware-guide/acpi/index.rst | 1 + 3 files changed, 186 insertions(+), 177 deletions(-) delete mode 100644 Documentation/acpi/apei/einj.txt create mode 100644 Documentation/firmware-guide/acpi/apei/einj.rst (limited to 'Documentation') diff --git a/Documentation/acpi/apei/einj.txt b/Documentation/acpi/apei/einj.txt deleted file mode 100644 index e550c8b98139..000000000000 --- a/Documentation/acpi/apei/einj.txt +++ /dev/null @@ -1,177 +0,0 @@ - APEI Error INJection - ~~~~~~~~~~~~~~~~~~~~ - -EINJ provides a hardware error injection mechanism. It is very useful -for debugging and testing APEI and RAS features in general. - -You need to check whether your BIOS supports EINJ first. For that, look -for early boot messages similar to this one: - -ACPI: EINJ 0x000000007370A000 000150 (v01 INTEL 00000001 INTL 00000001) - -which shows that the BIOS is exposing an EINJ table - it is the -mechanism through which the injection is done. - -Alternatively, look in /sys/firmware/acpi/tables for an "EINJ" file, -which is a different representation of the same thing. - -It doesn't necessarily mean that EINJ is not supported if those above -don't exist: before you give up, go into BIOS setup to see if the BIOS -has an option to enable error injection. Look for something called WHEA -or similar. Often, you need to enable an ACPI5 support option prior, in -order to see the APEI,EINJ,... functionality supported and exposed by -the BIOS menu. - -To use EINJ, make sure the following are options enabled in your kernel -configuration: - -CONFIG_DEBUG_FS -CONFIG_ACPI_APEI -CONFIG_ACPI_APEI_EINJ - -The EINJ user interface is in /apei/einj. - -The following files belong to it: - -- available_error_type - - This file shows which error types are supported: - - Error Type Value Error Description - ================ ================= - 0x00000001 Processor Correctable - 0x00000002 Processor Uncorrectable non-fatal - 0x00000004 Processor Uncorrectable fatal - 0x00000008 Memory Correctable - 0x00000010 Memory Uncorrectable non-fatal - 0x00000020 Memory Uncorrectable fatal - 0x00000040 PCI Express Correctable - 0x00000080 PCI Express Uncorrectable fatal - 0x00000100 PCI Express Uncorrectable non-fatal - 0x00000200 Platform Correctable - 0x00000400 Platform Uncorrectable non-fatal - 0x00000800 Platform Uncorrectable fatal - - The format of the file contents are as above, except present are only - the available error types. - -- error_type - - Set the value of the error type being injected. Possible error types - are defined in the file available_error_type above. - -- error_inject - - Write any integer to this file to trigger the error injection. Make - sure you have specified all necessary error parameters, i.e. this - write should be the last step when injecting errors. - -- flags - - Present for kernel versions 3.13 and above. Used to specify which - of param{1..4} are valid and should be used by the firmware during - injection. Value is a bitmask as specified in ACPI5.0 spec for the - SET_ERROR_TYPE_WITH_ADDRESS data structure: - - Bit 0 - Processor APIC field valid (see param3 below). - Bit 1 - Memory address and mask valid (param1 and param2). - Bit 2 - PCIe (seg,bus,dev,fn) valid (see param4 below). - - If set to zero, legacy behavior is mimicked where the type of - injection specifies just one bit set, and param1 is multiplexed. - -- param1 - - This file is used to set the first error parameter value. Its effect - depends on the error type specified in error_type. For example, if - error type is memory related type, the param1 should be a valid - physical memory address. [Unless "flag" is set - see above] - -- param2 - - Same use as param1 above. For example, if error type is of memory - related type, then param2 should be a physical memory address mask. - Linux requires page or narrower granularity, say, 0xfffffffffffff000. - -- param3 - - Used when the 0x1 bit is set in "flags" to specify the APIC id - -- param4 - Used when the 0x4 bit is set in "flags" to specify target PCIe device - -- notrigger - - The error injection mechanism is a two-step process. First inject the - error, then perform some actions to trigger it. Setting "notrigger" - to 1 skips the trigger phase, which *may* allow the user to cause the - error in some other context by a simple access to the CPU, memory - location, or device that is the target of the error injection. Whether - this actually works depends on what operations the BIOS actually - includes in the trigger phase. - -BIOS versions based on the ACPI 4.0 specification have limited options -in controlling where the errors are injected. Your BIOS may support an -extension (enabled with the param_extension=1 module parameter, or boot -command line einj.param_extension=1). This allows the address and mask -for memory injections to be specified by the param1 and param2 files in -apei/einj. - -BIOS versions based on the ACPI 5.0 specification have more control over -the target of the injection. For processor-related errors (type 0x1, 0x2 -and 0x4), you can set flags to 0x3 (param3 for bit 0, and param1 and -param2 for bit 1) so that you have more information added to the error -signature being injected. The actual data passed is this: - - memory_address = param1; - memory_address_range = param2; - apicid = param3; - pcie_sbdf = param4; - -For memory errors (type 0x8, 0x10 and 0x20) the address is set using -param1 with a mask in param2 (0x0 is equivalent to all ones). For PCI -express errors (type 0x40, 0x80 and 0x100) the segment, bus, device and -function are specified using param1: - - 31 24 23 16 15 11 10 8 7 0 - +-------------------------------------------------+ - | segment | bus | device | function | reserved | - +-------------------------------------------------+ - -Anyway, you get the idea, if there's doubt just take a look at the code -in drivers/acpi/apei/einj.c. - -An ACPI 5.0 BIOS may also allow vendor-specific errors to be injected. -In this case a file named vendor will contain identifying information -from the BIOS that hopefully will allow an application wishing to use -the vendor-specific extension to tell that they are running on a BIOS -that supports it. All vendor extensions have the 0x80000000 bit set in -error_type. A file vendor_flags controls the interpretation of param1 -and param2 (1 = PROCESSOR, 2 = MEMORY, 4 = PCI). See your BIOS vendor -documentation for details (and expect changes to this API if vendors -creativity in using this feature expands beyond our expectations). - - -An error injection example: - -# cd /sys/kernel/debug/apei/einj -# cat available_error_type # See which errors can be injected -0x00000002 Processor Uncorrectable non-fatal -0x00000008 Memory Correctable -0x00000010 Memory Uncorrectable non-fatal -# echo 0x12345000 > param1 # Set memory address for injection -# echo $((-1 << 12)) > param2 # Mask 0xfffffffffffff000 - anywhere in this page -# echo 0x8 > error_type # Choose correctable memory error -# echo 1 > error_inject # Inject now - -You should see something like this in dmesg: - -[22715.830801] EDAC sbridge MC3: HANDLING MCE MEMORY ERROR -[22715.834759] EDAC sbridge MC3: CPU 0: Machine Check Event: 0 Bank 7: 8c00004000010090 -[22715.834759] EDAC sbridge MC3: TSC 0 -[22715.834759] EDAC sbridge MC3: ADDR 12345000 EDAC sbridge MC3: MISC 144780c86 -[22715.834759] EDAC sbridge MC3: PROCESSOR 0:306e7 TIME 1422553404 SOCKET 0 APIC 0 -[22716.616173] EDAC MC3: 1 CE memory read error on CPU_SrcID#0_Channel#0_DIMM#0 (channel:0 slot:0 page:0x12345 offset:0x0 grain:32 syndrome:0x0 - area:DRAM err_code:0001:0090 socket:0 channel_mask:1 rank:0) - -For more information about EINJ, please refer to ACPI specification -version 4.0, section 17.5 and ACPI 5.0, section 18.6. diff --git a/Documentation/firmware-guide/acpi/apei/einj.rst b/Documentation/firmware-guide/acpi/apei/einj.rst new file mode 100644 index 000000000000..e588bccf5158 --- /dev/null +++ b/Documentation/firmware-guide/acpi/apei/einj.rst @@ -0,0 +1,185 @@ +.. SPDX-License-Identifier: GPL-2.0 + +==================== +APEI Error INJection +==================== + +EINJ provides a hardware error injection mechanism. It is very useful +for debugging and testing APEI and RAS features in general. + +You need to check whether your BIOS supports EINJ first. For that, look +for early boot messages similar to this one:: + + ACPI: EINJ 0x000000007370A000 000150 (v01 INTEL 00000001 INTL 00000001) + +which shows that the BIOS is exposing an EINJ table - it is the +mechanism through which the injection is done. + +Alternatively, look in /sys/firmware/acpi/tables for an "EINJ" file, +which is a different representation of the same thing. + +It doesn't necessarily mean that EINJ is not supported if those above +don't exist: before you give up, go into BIOS setup to see if the BIOS +has an option to enable error injection. Look for something called WHEA +or similar. Often, you need to enable an ACPI5 support option prior, in +order to see the APEI,EINJ,... functionality supported and exposed by +the BIOS menu. + +To use EINJ, make sure the following are options enabled in your kernel +configuration:: + + CONFIG_DEBUG_FS + CONFIG_ACPI_APEI + CONFIG_ACPI_APEI_EINJ + +The EINJ user interface is in /apei/einj. + +The following files belong to it: + +- available_error_type + + This file shows which error types are supported: + + ================ =================================== + Error Type Value Error Description + ================ =================================== + 0x00000001 Processor Correctable + 0x00000002 Processor Uncorrectable non-fatal + 0x00000004 Processor Uncorrectable fatal + 0x00000008 Memory Correctable + 0x00000010 Memory Uncorrectable non-fatal + 0x00000020 Memory Uncorrectable fatal + 0x00000040 PCI Express Correctable + 0x00000080 PCI Express Uncorrectable fatal + 0x00000100 PCI Express Uncorrectable non-fatal + 0x00000200 Platform Correctable + 0x00000400 Platform Uncorrectable non-fatal + 0x00000800 Platform Uncorrectable fatal + ================ =================================== + + The format of the file contents are as above, except present are only + the available error types. + +- error_type + + Set the value of the error type being injected. Possible error types + are defined in the file available_error_type above. + +- error_inject + + Write any integer to this file to trigger the error injection. Make + sure you have specified all necessary error parameters, i.e. this + write should be the last step when injecting errors. + +- flags + + Present for kernel versions 3.13 and above. Used to specify which + of param{1..4} are valid and should be used by the firmware during + injection. Value is a bitmask as specified in ACPI5.0 spec for the + SET_ERROR_TYPE_WITH_ADDRESS data structure: + + Bit 0 + Processor APIC field valid (see param3 below). + Bit 1 + Memory address and mask valid (param1 and param2). + Bit 2 + PCIe (seg,bus,dev,fn) valid (see param4 below). + + If set to zero, legacy behavior is mimicked where the type of + injection specifies just one bit set, and param1 is multiplexed. + +- param1 + + This file is used to set the first error parameter value. Its effect + depends on the error type specified in error_type. For example, if + error type is memory related type, the param1 should be a valid + physical memory address. [Unless "flag" is set - see above] + +- param2 + + Same use as param1 above. For example, if error type is of memory + related type, then param2 should be a physical memory address mask. + Linux requires page or narrower granularity, say, 0xfffffffffffff000. + +- param3 + + Used when the 0x1 bit is set in "flags" to specify the APIC id + +- param4 + Used when the 0x4 bit is set in "flags" to specify target PCIe device + +- notrigger + + The error injection mechanism is a two-step process. First inject the + error, then perform some actions to trigger it. Setting "notrigger" + to 1 skips the trigger phase, which *may* allow the user to cause the + error in some other context by a simple access to the CPU, memory + location, or device that is the target of the error injection. Whether + this actually works depends on what operations the BIOS actually + includes in the trigger phase. + +BIOS versions based on the ACPI 4.0 specification have limited options +in controlling where the errors are injected. Your BIOS may support an +extension (enabled with the param_extension=1 module parameter, or boot +command line einj.param_extension=1). This allows the address and mask +for memory injections to be specified by the param1 and param2 files in +apei/einj. + +BIOS versions based on the ACPI 5.0 specification have more control over +the target of the injection. For processor-related errors (type 0x1, 0x2 +and 0x4), you can set flags to 0x3 (param3 for bit 0, and param1 and +param2 for bit 1) so that you have more information added to the error +signature being injected. The actual data passed is this:: + + memory_address = param1; + memory_address_range = param2; + apicid = param3; + pcie_sbdf = param4; + +For memory errors (type 0x8, 0x10 and 0x20) the address is set using +param1 with a mask in param2 (0x0 is equivalent to all ones). For PCI +express errors (type 0x40, 0x80 and 0x100) the segment, bus, device and +function are specified using param1:: + + 31 24 23 16 15 11 10 8 7 0 + +-------------------------------------------------+ + | segment | bus | device | function | reserved | + +-------------------------------------------------+ + +Anyway, you get the idea, if there's doubt just take a look at the code +in drivers/acpi/apei/einj.c. + +An ACPI 5.0 BIOS may also allow vendor-specific errors to be injected. +In this case a file named vendor will contain identifying information +from the BIOS that hopefully will allow an application wishing to use +the vendor-specific extension to tell that they are running on a BIOS +that supports it. All vendor extensions have the 0x80000000 bit set in +error_type. A file vendor_flags controls the interpretation of param1 +and param2 (1 = PROCESSOR, 2 = MEMORY, 4 = PCI). See your BIOS vendor +documentation for details (and expect changes to this API if vendors +creativity in using this feature expands beyond our expectations). + + +An error injection example:: + + # cd /sys/kernel/debug/apei/einj + # cat available_error_type # See which errors can be injected + 0x00000002 Processor Uncorrectable non-fatal + 0x00000008 Memory Correctable + 0x00000010 Memory Uncorrectable non-fatal + # echo 0x12345000 > param1 # Set memory address for injection + # echo $((-1 << 12)) > param2 # Mask 0xfffffffffffff000 - anywhere in this page + # echo 0x8 > error_type # Choose correctable memory error + # echo 1 > error_inject # Inject now + +You should see something like this in dmesg:: + + [22715.830801] EDAC sbridge MC3: HANDLING MCE MEMORY ERROR + [22715.834759] EDAC sbridge MC3: CPU 0: Machine Check Event: 0 Bank 7: 8c00004000010090 + [22715.834759] EDAC sbridge MC3: TSC 0 + [22715.834759] EDAC sbridge MC3: ADDR 12345000 EDAC sbridge MC3: MISC 144780c86 + [22715.834759] EDAC sbridge MC3: PROCESSOR 0:306e7 TIME 1422553404 SOCKET 0 APIC 0 + [22716.616173] EDAC MC3: 1 CE memory read error on CPU_SrcID#0_Channel#0_DIMM#0 (channel:0 slot:0 page:0x12345 offset:0x0 grain:32 syndrome:0x0 - area:DRAM err_code:0001:0090 socket:0 channel_mask:1 rank:0) + +For more information about EINJ, please refer to ACPI specification +version 4.0, section 17.5 and ACPI 5.0, section 18.6. diff --git a/Documentation/firmware-guide/acpi/index.rst b/Documentation/firmware-guide/acpi/index.rst index 869badba6d7a..fca854f017d8 100644 --- a/Documentation/firmware-guide/acpi/index.rst +++ b/Documentation/firmware-guide/acpi/index.rst @@ -18,6 +18,7 @@ ACPI Support debug aml-debugger apei/output_format + apei/einj gpio-properties i2c-muxes acpi-lid -- cgit v1.2.3 From 3e57460f007c86476c376a08e31da441cae0b195 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 01:53:03 +0800 Subject: Documentation: ACPI: move cppc_sysfs.txt to admin-guide/acpi and convert to reST This converts the plain text documentation to reStructuredText format and adds it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/cppc_sysfs.txt | 69 ------------------------ Documentation/admin-guide/acpi/cppc_sysfs.rst | 76 +++++++++++++++++++++++++++ Documentation/admin-guide/acpi/index.rst | 1 + 3 files changed, 77 insertions(+), 69 deletions(-) delete mode 100644 Documentation/acpi/cppc_sysfs.txt create mode 100644 Documentation/admin-guide/acpi/cppc_sysfs.rst (limited to 'Documentation') diff --git a/Documentation/acpi/cppc_sysfs.txt b/Documentation/acpi/cppc_sysfs.txt deleted file mode 100644 index f20fb445135d..000000000000 --- a/Documentation/acpi/cppc_sysfs.txt +++ /dev/null @@ -1,69 +0,0 @@ - - Collaborative Processor Performance Control (CPPC) - -CPPC defined in the ACPI spec describes a mechanism for the OS to manage the -performance of a logical processor on a contigious and abstract performance -scale. CPPC exposes a set of registers to describe abstract performance scale, -to request performance levels and to measure per-cpu delivered performance. - -For more details on CPPC please refer to the ACPI specification at: - -http://uefi.org/specifications - -Some of the CPPC registers are exposed via sysfs under: - -/sys/devices/system/cpu/cpuX/acpi_cppc/ - -for each cpu X - --------------------------------------------------------------------------------- - -$ ls -lR /sys/devices/system/cpu/cpu0/acpi_cppc/ -/sys/devices/system/cpu/cpu0/acpi_cppc/: -total 0 --r--r--r-- 1 root root 65536 Mar 5 19:38 feedback_ctrs --r--r--r-- 1 root root 65536 Mar 5 19:38 highest_perf --r--r--r-- 1 root root 65536 Mar 5 19:38 lowest_freq --r--r--r-- 1 root root 65536 Mar 5 19:38 lowest_nonlinear_perf --r--r--r-- 1 root root 65536 Mar 5 19:38 lowest_perf --r--r--r-- 1 root root 65536 Mar 5 19:38 nominal_freq --r--r--r-- 1 root root 65536 Mar 5 19:38 nominal_perf --r--r--r-- 1 root root 65536 Mar 5 19:38 reference_perf --r--r--r-- 1 root root 65536 Mar 5 19:38 wraparound_time - --------------------------------------------------------------------------------- - -* highest_perf : Highest performance of this processor (abstract scale). -* nominal_perf : Highest sustained performance of this processor (abstract scale). -* lowest_nonlinear_perf : Lowest performance of this processor with nonlinear - power savings (abstract scale). -* lowest_perf : Lowest performance of this processor (abstract scale). - -* lowest_freq : CPU frequency corresponding to lowest_perf (in MHz). -* nominal_freq : CPU frequency corresponding to nominal_perf (in MHz). - The above frequencies should only be used to report processor performance in - freqency instead of abstract scale. These values should not be used for any - functional decisions. - -* feedback_ctrs : Includes both Reference and delivered performance counter. - Reference counter ticks up proportional to processor's reference performance. - Delivered counter ticks up proportional to processor's delivered performance. -* wraparound_time: Minimum time for the feedback counters to wraparound (seconds). -* reference_perf : Performance level at which reference performance counter - accumulates (abstract scale). - --------------------------------------------------------------------------------- - - Computing Average Delivered Performance - -Below describes the steps to compute the average performance delivered by taking -two different snapshots of feedback counters at time T1 and T2. - -T1: Read feedback_ctrs as fbc_t1 - Wait or run some workload -T2: Read feedback_ctrs as fbc_t2 - -delivered_counter_delta = fbc_t2[del] - fbc_t1[del] -reference_counter_delta = fbc_t2[ref] - fbc_t1[ref] - -delivered_perf = (refernce_perf x delivered_counter_delta) / reference_counter_delta diff --git a/Documentation/admin-guide/acpi/cppc_sysfs.rst b/Documentation/admin-guide/acpi/cppc_sysfs.rst new file mode 100644 index 000000000000..a4b99afbe331 --- /dev/null +++ b/Documentation/admin-guide/acpi/cppc_sysfs.rst @@ -0,0 +1,76 @@ +.. SPDX-License-Identifier: GPL-2.0 + +================================================== +Collaborative Processor Performance Control (CPPC) +================================================== + +CPPC +==== + +CPPC defined in the ACPI spec describes a mechanism for the OS to manage the +performance of a logical processor on a contigious and abstract performance +scale. CPPC exposes a set of registers to describe abstract performance scale, +to request performance levels and to measure per-cpu delivered performance. + +For more details on CPPC please refer to the ACPI specification at: + +http://uefi.org/specifications + +Some of the CPPC registers are exposed via sysfs under:: + + /sys/devices/system/cpu/cpuX/acpi_cppc/ + +for each cpu X:: + + $ ls -lR /sys/devices/system/cpu/cpu0/acpi_cppc/ + /sys/devices/system/cpu/cpu0/acpi_cppc/: + total 0 + -r--r--r-- 1 root root 65536 Mar 5 19:38 feedback_ctrs + -r--r--r-- 1 root root 65536 Mar 5 19:38 highest_perf + -r--r--r-- 1 root root 65536 Mar 5 19:38 lowest_freq + -r--r--r-- 1 root root 65536 Mar 5 19:38 lowest_nonlinear_perf + -r--r--r-- 1 root root 65536 Mar 5 19:38 lowest_perf + -r--r--r-- 1 root root 65536 Mar 5 19:38 nominal_freq + -r--r--r-- 1 root root 65536 Mar 5 19:38 nominal_perf + -r--r--r-- 1 root root 65536 Mar 5 19:38 reference_perf + -r--r--r-- 1 root root 65536 Mar 5 19:38 wraparound_time + +* highest_perf : Highest performance of this processor (abstract scale). +* nominal_perf : Highest sustained performance of this processor + (abstract scale). +* lowest_nonlinear_perf : Lowest performance of this processor with nonlinear + power savings (abstract scale). +* lowest_perf : Lowest performance of this processor (abstract scale). + +* lowest_freq : CPU frequency corresponding to lowest_perf (in MHz). +* nominal_freq : CPU frequency corresponding to nominal_perf (in MHz). + The above frequencies should only be used to report processor performance in + freqency instead of abstract scale. These values should not be used for any + functional decisions. + +* feedback_ctrs : Includes both Reference and delivered performance counter. + Reference counter ticks up proportional to processor's reference performance. + Delivered counter ticks up proportional to processor's delivered performance. +* wraparound_time: Minimum time for the feedback counters to wraparound + (seconds). +* reference_perf : Performance level at which reference performance counter + accumulates (abstract scale). + + +Computing Average Delivered Performance +======================================= + +Below describes the steps to compute the average performance delivered by +taking two different snapshots of feedback counters at time T1 and T2. + + T1: Read feedback_ctrs as fbc_t1 + Wait or run some workload + + T2: Read feedback_ctrs as fbc_t2 + +:: + + delivered_counter_delta = fbc_t2[del] - fbc_t1[del] + reference_counter_delta = fbc_t2[ref] - fbc_t1[ref] + + delivered_perf = (refernce_perf x delivered_counter_delta) / reference_counter_delta diff --git a/Documentation/admin-guide/acpi/index.rst b/Documentation/admin-guide/acpi/index.rst index d68e9914c5ff..9049a7b9f065 100644 --- a/Documentation/admin-guide/acpi/index.rst +++ b/Documentation/admin-guide/acpi/index.rst @@ -10,3 +10,4 @@ the Linux ACPI support. initrd_table_override dsdt-override + cppc_sysfs -- cgit v1.2.3 From 4887954cac779abe38d3ba6446dec341ccca04ea Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 01:53:04 +0800 Subject: Documentation: ACPI: move lpit.txt to firmware-guide/acpi and convert to reST This converts the plain text documentation to reStructuredText format and adds it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/lpit.txt | 25 ---------------------- Documentation/firmware-guide/acpi/index.rst | 1 + Documentation/firmware-guide/acpi/lpit.rst | 33 +++++++++++++++++++++++++++++ 3 files changed, 34 insertions(+), 25 deletions(-) delete mode 100644 Documentation/acpi/lpit.txt create mode 100644 Documentation/firmware-guide/acpi/lpit.rst (limited to 'Documentation') diff --git a/Documentation/acpi/lpit.txt b/Documentation/acpi/lpit.txt deleted file mode 100644 index b426398d2e97..000000000000 --- a/Documentation/acpi/lpit.txt +++ /dev/null @@ -1,25 +0,0 @@ -To enumerate platform Low Power Idle states, Intel platforms are using -“Low Power Idle Table” (LPIT). More details about this table can be -downloaded from: -http://www.uefi.org/sites/default/files/resources/Intel_ACPI_Low_Power_S0_Idle.pdf - -Residencies for each low power state can be read via FFH -(Function fixed hardware) or a memory mapped interface. - -On platforms supporting S0ix sleep states, there can be two types of -residencies: -- CPU PKG C10 (Read via FFH interface) -- Platform Controller Hub (PCH) SLP_S0 (Read via memory mapped interface) - -The following attributes are added dynamically to the cpuidle -sysfs attribute group: - /sys/devices/system/cpu/cpuidle/low_power_idle_cpu_residency_us - /sys/devices/system/cpu/cpuidle/low_power_idle_system_residency_us - -The "low_power_idle_cpu_residency_us" attribute shows time spent -by the CPU package in PKG C10 - -The "low_power_idle_system_residency_us" attribute shows SLP_S0 -residency, or system time spent with the SLP_S0# signal asserted. -This is the lowest possible system power state, achieved only when CPU is in -PKG C10 and all functional blocks in PCH are in a low power state. diff --git a/Documentation/firmware-guide/acpi/index.rst b/Documentation/firmware-guide/acpi/index.rst index fca854f017d8..0e60f4b7129a 100644 --- a/Documentation/firmware-guide/acpi/index.rst +++ b/Documentation/firmware-guide/acpi/index.rst @@ -22,3 +22,4 @@ ACPI Support gpio-properties i2c-muxes acpi-lid + lpit diff --git a/Documentation/firmware-guide/acpi/lpit.rst b/Documentation/firmware-guide/acpi/lpit.rst new file mode 100644 index 000000000000..aca928fab027 --- /dev/null +++ b/Documentation/firmware-guide/acpi/lpit.rst @@ -0,0 +1,33 @@ +.. SPDX-License-Identifier: GPL-2.0 + +=========================== +Low Power Idle Table (LPIT) +=========================== + +To enumerate platform Low Power Idle states, Intel platforms are using +“Low Power Idle Table” (LPIT). More details about this table can be +downloaded from: +http://www.uefi.org/sites/default/files/resources/Intel_ACPI_Low_Power_S0_Idle.pdf + +Residencies for each low power state can be read via FFH +(Function fixed hardware) or a memory mapped interface. + +On platforms supporting S0ix sleep states, there can be two types of +residencies: + + - CPU PKG C10 (Read via FFH interface) + - Platform Controller Hub (PCH) SLP_S0 (Read via memory mapped interface) + +The following attributes are added dynamically to the cpuidle +sysfs attribute group:: + + /sys/devices/system/cpu/cpuidle/low_power_idle_cpu_residency_us + /sys/devices/system/cpu/cpuidle/low_power_idle_system_residency_us + +The "low_power_idle_cpu_residency_us" attribute shows time spent +by the CPU package in PKG C10 + +The "low_power_idle_system_residency_us" attribute shows SLP_S0 +residency, or system time spent with the SLP_S0# signal asserted. +This is the lowest possible system power state, achieved only when CPU is in +PKG C10 and all functional blocks in PCH are in a low power state. -- cgit v1.2.3 From 7fe19072df5555425268f9452059d3c514c6780f Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 01:53:05 +0800 Subject: Documentation: ACPI: move ssdt-overlays.txt to admin-guide/acpi and convert to reST This converts the plain text documentation to reStructuredText format and adds it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/ssdt-overlays.txt | 172 ---------------------- Documentation/admin-guide/acpi/index.rst | 1 + Documentation/admin-guide/acpi/ssdt-overlays.rst | 180 +++++++++++++++++++++++ 3 files changed, 181 insertions(+), 172 deletions(-) delete mode 100644 Documentation/acpi/ssdt-overlays.txt create mode 100644 Documentation/admin-guide/acpi/ssdt-overlays.rst (limited to 'Documentation') diff --git a/Documentation/acpi/ssdt-overlays.txt b/Documentation/acpi/ssdt-overlays.txt deleted file mode 100644 index 5ae13f161ea2..000000000000 --- a/Documentation/acpi/ssdt-overlays.txt +++ /dev/null @@ -1,172 +0,0 @@ - -In order to support ACPI open-ended hardware configurations (e.g. development -boards) we need a way to augment the ACPI configuration provided by the firmware -image. A common example is connecting sensors on I2C / SPI buses on development -boards. - -Although this can be accomplished by creating a kernel platform driver or -recompiling the firmware image with updated ACPI tables, neither is practical: -the former proliferates board specific kernel code while the latter requires -access to firmware tools which are often not publicly available. - -Because ACPI supports external references in AML code a more practical -way to augment firmware ACPI configuration is by dynamically loading -user defined SSDT tables that contain the board specific information. - -For example, to enumerate a Bosch BMA222E accelerometer on the I2C bus of the -Minnowboard MAX development board exposed via the LSE connector [1], the -following ASL code can be used: - -DefinitionBlock ("minnowmax.aml", "SSDT", 1, "Vendor", "Accel", 0x00000003) -{ - External (\_SB.I2C6, DeviceObj) - - Scope (\_SB.I2C6) - { - Device (STAC) - { - Name (_ADR, Zero) - Name (_HID, "BMA222E") - - Method (_CRS, 0, Serialized) - { - Name (RBUF, ResourceTemplate () - { - I2cSerialBus (0x0018, ControllerInitiated, 0x00061A80, - AddressingMode7Bit, "\\_SB.I2C6", 0x00, - ResourceConsumer, ,) - GpioInt (Edge, ActiveHigh, Exclusive, PullDown, 0x0000, - "\\_SB.GPO2", 0x00, ResourceConsumer, , ) - { // Pin list - 0 - } - }) - Return (RBUF) - } - } - } -} - -which can then be compiled to AML binary format: - -$ iasl minnowmax.asl - -Intel ACPI Component Architecture -ASL Optimizing Compiler version 20140214-64 [Mar 29 2014] -Copyright (c) 2000 - 2014 Intel Corporation - -ASL Input: minnomax.asl - 30 lines, 614 bytes, 7 keywords -AML Output: minnowmax.aml - 165 bytes, 6 named objects, 1 executable opcodes - -[1] http://wiki.minnowboard.org/MinnowBoard_MAX#Low_Speed_Expansion_Connector_.28Top.29 - -The resulting AML code can then be loaded by the kernel using one of the methods -below. - -== Loading ACPI SSDTs from initrd == - -This option allows loading of user defined SSDTs from initrd and it is useful -when the system does not support EFI or when there is not enough EFI storage. - -It works in a similar way with initrd based ACPI tables override/upgrade: SSDT -aml code must be placed in the first, uncompressed, initrd under the -"kernel/firmware/acpi" path. Multiple files can be used and this will translate -in loading multiple tables. Only SSDT and OEM tables are allowed. See -initrd_table_override.txt for more details. - -Here is an example: - -# Add the raw ACPI tables to an uncompressed cpio archive. -# They must be put into a /kernel/firmware/acpi directory inside the -# cpio archive. -# The uncompressed cpio archive must be the first. -# Other, typically compressed cpio archives, must be -# concatenated on top of the uncompressed one. -mkdir -p kernel/firmware/acpi -cp ssdt.aml kernel/firmware/acpi - -# Create the uncompressed cpio archive and concatenate the original initrd -# on top: -find kernel | cpio -H newc --create > /boot/instrumented_initrd -cat /boot/initrd >>/boot/instrumented_initrd - -== Loading ACPI SSDTs from EFI variables == - -This is the preferred method, when EFI is supported on the platform, because it -allows a persistent, OS independent way of storing the user defined SSDTs. There -is also work underway to implement EFI support for loading user defined SSDTs -and using this method will make it easier to convert to the EFI loading -mechanism when that will arrive. - -In order to load SSDTs from an EFI variable the efivar_ssdt kernel command line -parameter can be used. The argument for the option is the variable name to -use. If there are multiple variables with the same name but with different -vendor GUIDs, all of them will be loaded. - -In order to store the AML code in an EFI variable the efivarfs filesystem can be -used. It is enabled and mounted by default in /sys/firmware/efi/efivars in all -recent distribution. - -Creating a new file in /sys/firmware/efi/efivars will automatically create a new -EFI variable. Updating a file in /sys/firmware/efi/efivars will update the EFI -variable. Please note that the file name needs to be specially formatted as -"Name-GUID" and that the first 4 bytes in the file (little-endian format) -represent the attributes of the EFI variable (see EFI_VARIABLE_MASK in -include/linux/efi.h). Writing to the file must also be done with one write -operation. - -For example, you can use the following bash script to create/update an EFI -variable with the content from a given file: - -#!/bin/sh -e - -while ! [ -z "$1" ]; do - case "$1" in - "-f") filename="$2"; shift;; - "-g") guid="$2"; shift;; - *) name="$1";; - esac - shift -done - -usage() -{ - echo "Syntax: ${0##*/} -f filename [ -g guid ] name" - exit 1 -} - -[ -n "$name" -a -f "$filename" ] || usage - -EFIVARFS="/sys/firmware/efi/efivars" - -[ -d "$EFIVARFS" ] || exit 2 - -if stat -tf $EFIVARFS | grep -q -v de5e81e4; then - mount -t efivarfs none $EFIVARFS -fi - -# try to pick up an existing GUID -[ -n "$guid" ] || guid=$(find "$EFIVARFS" -name "$name-*" | head -n1 | cut -f2- -d-) - -# use a randomly generated GUID -[ -n "$guid" ] || guid="$(cat /proc/sys/kernel/random/uuid)" - -# efivarfs expects all of the data in one write -tmp=$(mktemp) -/bin/echo -ne "\007\000\000\000" | cat - $filename > $tmp -dd if=$tmp of="$EFIVARFS/$name-$guid" bs=$(stat -c %s $tmp) -rm $tmp - -== Loading ACPI SSDTs from configfs == - -This option allows loading of user defined SSDTs from userspace via the configfs -interface. The CONFIG_ACPI_CONFIGFS option must be select and configfs must be -mounted. In the following examples, we assume that configfs has been mounted in -/config. - -New tables can be loading by creating new directories in /config/acpi/table/ and -writing the SSDT aml code in the aml attribute: - -cd /config/acpi/table -mkdir my_ssdt -cat ~/ssdt.aml > my_ssdt/aml diff --git a/Documentation/admin-guide/acpi/index.rst b/Documentation/admin-guide/acpi/index.rst index 9049a7b9f065..4d13eeea1eca 100644 --- a/Documentation/admin-guide/acpi/index.rst +++ b/Documentation/admin-guide/acpi/index.rst @@ -10,4 +10,5 @@ the Linux ACPI support. initrd_table_override dsdt-override + ssdt-overlays cppc_sysfs diff --git a/Documentation/admin-guide/acpi/ssdt-overlays.rst b/Documentation/admin-guide/acpi/ssdt-overlays.rst new file mode 100644 index 000000000000..da37455f96c9 --- /dev/null +++ b/Documentation/admin-guide/acpi/ssdt-overlays.rst @@ -0,0 +1,180 @@ +.. SPDX-License-Identifier: GPL-2.0 + +============= +SSDT Overlays +============= + +In order to support ACPI open-ended hardware configurations (e.g. development +boards) we need a way to augment the ACPI configuration provided by the firmware +image. A common example is connecting sensors on I2C / SPI buses on development +boards. + +Although this can be accomplished by creating a kernel platform driver or +recompiling the firmware image with updated ACPI tables, neither is practical: +the former proliferates board specific kernel code while the latter requires +access to firmware tools which are often not publicly available. + +Because ACPI supports external references in AML code a more practical +way to augment firmware ACPI configuration is by dynamically loading +user defined SSDT tables that contain the board specific information. + +For example, to enumerate a Bosch BMA222E accelerometer on the I2C bus of the +Minnowboard MAX development board exposed via the LSE connector [1], the +following ASL code can be used:: + + DefinitionBlock ("minnowmax.aml", "SSDT", 1, "Vendor", "Accel", 0x00000003) + { + External (\_SB.I2C6, DeviceObj) + + Scope (\_SB.I2C6) + { + Device (STAC) + { + Name (_ADR, Zero) + Name (_HID, "BMA222E") + + Method (_CRS, 0, Serialized) + { + Name (RBUF, ResourceTemplate () + { + I2cSerialBus (0x0018, ControllerInitiated, 0x00061A80, + AddressingMode7Bit, "\\_SB.I2C6", 0x00, + ResourceConsumer, ,) + GpioInt (Edge, ActiveHigh, Exclusive, PullDown, 0x0000, + "\\_SB.GPO2", 0x00, ResourceConsumer, , ) + { // Pin list + 0 + } + }) + Return (RBUF) + } + } + } + } + +which can then be compiled to AML binary format:: + + $ iasl minnowmax.asl + + Intel ACPI Component Architecture + ASL Optimizing Compiler version 20140214-64 [Mar 29 2014] + Copyright (c) 2000 - 2014 Intel Corporation + + ASL Input: minnomax.asl - 30 lines, 614 bytes, 7 keywords + AML Output: minnowmax.aml - 165 bytes, 6 named objects, 1 executable opcodes + +[1] http://wiki.minnowboard.org/MinnowBoard_MAX#Low_Speed_Expansion_Connector_.28Top.29 + +The resulting AML code can then be loaded by the kernel using one of the methods +below. + +Loading ACPI SSDTs from initrd +============================== + +This option allows loading of user defined SSDTs from initrd and it is useful +when the system does not support EFI or when there is not enough EFI storage. + +It works in a similar way with initrd based ACPI tables override/upgrade: SSDT +aml code must be placed in the first, uncompressed, initrd under the +"kernel/firmware/acpi" path. Multiple files can be used and this will translate +in loading multiple tables. Only SSDT and OEM tables are allowed. See +initrd_table_override.txt for more details. + +Here is an example:: + + # Add the raw ACPI tables to an uncompressed cpio archive. + # They must be put into a /kernel/firmware/acpi directory inside the + # cpio archive. + # The uncompressed cpio archive must be the first. + # Other, typically compressed cpio archives, must be + # concatenated on top of the uncompressed one. + mkdir -p kernel/firmware/acpi + cp ssdt.aml kernel/firmware/acpi + + # Create the uncompressed cpio archive and concatenate the original initrd + # on top: + find kernel | cpio -H newc --create > /boot/instrumented_initrd + cat /boot/initrd >>/boot/instrumented_initrd + +Loading ACPI SSDTs from EFI variables +===================================== + +This is the preferred method, when EFI is supported on the platform, because it +allows a persistent, OS independent way of storing the user defined SSDTs. There +is also work underway to implement EFI support for loading user defined SSDTs +and using this method will make it easier to convert to the EFI loading +mechanism when that will arrive. + +In order to load SSDTs from an EFI variable the efivar_ssdt kernel command line +parameter can be used. The argument for the option is the variable name to +use. If there are multiple variables with the same name but with different +vendor GUIDs, all of them will be loaded. + +In order to store the AML code in an EFI variable the efivarfs filesystem can be +used. It is enabled and mounted by default in /sys/firmware/efi/efivars in all +recent distribution. + +Creating a new file in /sys/firmware/efi/efivars will automatically create a new +EFI variable. Updating a file in /sys/firmware/efi/efivars will update the EFI +variable. Please note that the file name needs to be specially formatted as +"Name-GUID" and that the first 4 bytes in the file (little-endian format) +represent the attributes of the EFI variable (see EFI_VARIABLE_MASK in +include/linux/efi.h). Writing to the file must also be done with one write +operation. + +For example, you can use the following bash script to create/update an EFI +variable with the content from a given file:: + + #!/bin/sh -e + + while ! [ -z "$1" ]; do + case "$1" in + "-f") filename="$2"; shift;; + "-g") guid="$2"; shift;; + *) name="$1";; + esac + shift + done + + usage() + { + echo "Syntax: ${0##*/} -f filename [ -g guid ] name" + exit 1 + } + + [ -n "$name" -a -f "$filename" ] || usage + + EFIVARFS="/sys/firmware/efi/efivars" + + [ -d "$EFIVARFS" ] || exit 2 + + if stat -tf $EFIVARFS | grep -q -v de5e81e4; then + mount -t efivarfs none $EFIVARFS + fi + + # try to pick up an existing GUID + [ -n "$guid" ] || guid=$(find "$EFIVARFS" -name "$name-*" | head -n1 | cut -f2- -d-) + + # use a randomly generated GUID + [ -n "$guid" ] || guid="$(cat /proc/sys/kernel/random/uuid)" + + # efivarfs expects all of the data in one write + tmp=$(mktemp) + /bin/echo -ne "\007\000\000\000" | cat - $filename > $tmp + dd if=$tmp of="$EFIVARFS/$name-$guid" bs=$(stat -c %s $tmp) + rm $tmp + +Loading ACPI SSDTs from configfs +================================ + +This option allows loading of user defined SSDTs from userspace via the configfs +interface. The CONFIG_ACPI_CONFIGFS option must be select and configfs must be +mounted. In the following examples, we assume that configfs has been mounted in +/config. + +New tables can be loading by creating new directories in /config/acpi/table/ and +writing the SSDT aml code in the aml attribute:: + + cd /config/acpi/table + mkdir my_ssdt + cat ~/ssdt.aml > my_ssdt/aml -- cgit v1.2.3 From 7fb091f806c55da593b93bc858d81203a9597257 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Thu, 25 Apr 2019 01:53:06 +0800 Subject: Documentation: ACPI: move video_extension.txt to firmware-guide/acpi and convert to reST This converts the plain text documentation to reStructuredText format and adds it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Rafael J. Wysocki --- Documentation/acpi/video_extension.txt | 106 ------------------ Documentation/firmware-guide/acpi/index.rst | 1 + .../firmware-guide/acpi/video_extension.rst | 121 +++++++++++++++++++++ 3 files changed, 122 insertions(+), 106 deletions(-) delete mode 100644 Documentation/acpi/video_extension.txt create mode 100644 Documentation/firmware-guide/acpi/video_extension.rst (limited to 'Documentation') diff --git a/Documentation/acpi/video_extension.txt b/Documentation/acpi/video_extension.txt deleted file mode 100644 index 79bf6a4921be..000000000000 --- a/Documentation/acpi/video_extension.txt +++ /dev/null @@ -1,106 +0,0 @@ -ACPI video extensions -~~~~~~~~~~~~~~~~~~~~~ - -This driver implement the ACPI Extensions For Display Adapters for -integrated graphics devices on motherboard, as specified in ACPI 2.0 -Specification, Appendix B, allowing to perform some basic control like -defining the video POST device, retrieving EDID information or to -setup a video output, etc. Note that this is an ref. implementation -only. It may or may not work for your integrated video device. - -The ACPI video driver does 3 things regarding backlight control: - -1 Export a sysfs interface for user space to control backlight level - -If the ACPI table has a video device, and acpi_backlight=vendor kernel -command line is not present, the driver will register a backlight device -and set the required backlight operation structure for it for the sysfs -interface control. For every registered class device, there will be a -directory named acpi_videoX under /sys/class/backlight. - -The backlight sysfs interface has a standard definition here: -Documentation/ABI/stable/sysfs-class-backlight. - -And what ACPI video driver does is: -actual_brightness: on read, control method _BQC will be evaluated to -get the brightness level the firmware thinks it is at; -bl_power: not implemented, will set the current brightness instead; -brightness: on write, control method _BCM will run to set the requested -brightness level; -max_brightness: Derived from the _BCL package(see below); -type: firmware - -Note that ACPI video backlight driver will always use index for -brightness, actual_brightness and max_brightness. So if we have -the following _BCL package: - -Method (_BCL, 0, NotSerialized) -{ - Return (Package (0x0C) - { - 0x64, - 0x32, - 0x0A, - 0x14, - 0x1E, - 0x28, - 0x32, - 0x3C, - 0x46, - 0x50, - 0x5A, - 0x64 - }) -} - -The first two levels are for when laptop are on AC or on battery and are -not used by Linux currently. The remaining 10 levels are supported levels -that we can choose from. The applicable index values are from 0 (that -corresponds to the 0x0A brightness value) to 9 (that corresponds to the -0x64 brightness value) inclusive. Each of those index values is regarded -as a "brightness level" indicator. Thus from the user space perspective -the range of available brightness levels is from 0 to 9 (max_brightness) -inclusive. - -2 Notify user space about hotkey event - -There are generally two cases for hotkey event reporting: -i) For some laptops, when user presses the hotkey, a scancode will be - generated and sent to user space through the input device created by - the keyboard driver as a key type input event, with proper remap, the - following key code will appear to user space: - - EV_KEY, KEY_BRIGHTNESSUP - EV_KEY, KEY_BRIGHTNESSDOWN - etc. - -For this case, ACPI video driver does not need to do anything(actually, -it doesn't even know this happened). - -ii) For some laptops, the press of the hotkey will not generate the - scancode, instead, firmware will notify the video device ACPI node - about the event. The event value is defined in the ACPI spec. ACPI - video driver will generate an key type input event according to the - notify value it received and send the event to user space through the - input device it created: - - event keycode - 0x86 KEY_BRIGHTNESSUP - 0x87 KEY_BRIGHTNESSDOWN - etc. - -so this would lead to the same effect as case i) now. - -Once user space tool receives this event, it can modify the backlight -level through the sysfs interface. - -3 Change backlight level in the kernel - -This works for machines covered by case ii) in Section 2. Once the driver -received a notification, it will set the backlight level accordingly. This does -not affect the sending of event to user space, they are always sent to user -space regardless of whether or not the video module controls the backlight level -directly. This behaviour can be controlled through the brightness_switch_enabled -module parameter as documented in admin-guide/kernel-parameters.rst. It is recommended to -disable this behaviour once a GUI environment starts up and wants to have full -control of the backlight level. diff --git a/Documentation/firmware-guide/acpi/index.rst b/Documentation/firmware-guide/acpi/index.rst index 0e60f4b7129a..ae609eec4679 100644 --- a/Documentation/firmware-guide/acpi/index.rst +++ b/Documentation/firmware-guide/acpi/index.rst @@ -23,3 +23,4 @@ ACPI Support i2c-muxes acpi-lid lpit + video_extension diff --git a/Documentation/firmware-guide/acpi/video_extension.rst b/Documentation/firmware-guide/acpi/video_extension.rst new file mode 100644 index 000000000000..099b8607e07b --- /dev/null +++ b/Documentation/firmware-guide/acpi/video_extension.rst @@ -0,0 +1,121 @@ +.. SPDX-License-Identifier: GPL-2.0 + +===================== +ACPI video extensions +===================== + +This driver implement the ACPI Extensions For Display Adapters for +integrated graphics devices on motherboard, as specified in ACPI 2.0 +Specification, Appendix B, allowing to perform some basic control like +defining the video POST device, retrieving EDID information or to +setup a video output, etc. Note that this is an ref. implementation +only. It may or may not work for your integrated video device. + +The ACPI video driver does 3 things regarding backlight control. + +Export a sysfs interface for user space to control backlight level +================================================================== + +If the ACPI table has a video device, and acpi_backlight=vendor kernel +command line is not present, the driver will register a backlight device +and set the required backlight operation structure for it for the sysfs +interface control. For every registered class device, there will be a +directory named acpi_videoX under /sys/class/backlight. + +The backlight sysfs interface has a standard definition here: +Documentation/ABI/stable/sysfs-class-backlight. + +And what ACPI video driver does is: + +actual_brightness: + on read, control method _BQC will be evaluated to + get the brightness level the firmware thinks it is at; +bl_power: + not implemented, will set the current brightness instead; +brightness: + on write, control method _BCM will run to set the requested brightness level; +max_brightness: + Derived from the _BCL package(see below); +type: + firmware + +Note that ACPI video backlight driver will always use index for +brightness, actual_brightness and max_brightness. So if we have +the following _BCL package:: + + Method (_BCL, 0, NotSerialized) + { + Return (Package (0x0C) + { + 0x64, + 0x32, + 0x0A, + 0x14, + 0x1E, + 0x28, + 0x32, + 0x3C, + 0x46, + 0x50, + 0x5A, + 0x64 + }) + } + +The first two levels are for when laptop are on AC or on battery and are +not used by Linux currently. The remaining 10 levels are supported levels +that we can choose from. The applicable index values are from 0 (that +corresponds to the 0x0A brightness value) to 9 (that corresponds to the +0x64 brightness value) inclusive. Each of those index values is regarded +as a "brightness level" indicator. Thus from the user space perspective +the range of available brightness levels is from 0 to 9 (max_brightness) +inclusive. + +Notify user space about hotkey event +==================================== + +There are generally two cases for hotkey event reporting: + +i) For some laptops, when user presses the hotkey, a scancode will be + generated and sent to user space through the input device created by + the keyboard driver as a key type input event, with proper remap, the + following key code will appear to user space:: + + EV_KEY, KEY_BRIGHTNESSUP + EV_KEY, KEY_BRIGHTNESSDOWN + etc. + +For this case, ACPI video driver does not need to do anything(actually, +it doesn't even know this happened). + +ii) For some laptops, the press of the hotkey will not generate the + scancode, instead, firmware will notify the video device ACPI node + about the event. The event value is defined in the ACPI spec. ACPI + video driver will generate an key type input event according to the + notify value it received and send the event to user space through the + input device it created: + + ===== ================== + event keycode + ===== ================== + 0x86 KEY_BRIGHTNESSUP + 0x87 KEY_BRIGHTNESSDOWN + etc. + ===== ================== + +so this would lead to the same effect as case i) now. + +Once user space tool receives this event, it can modify the backlight +level through the sysfs interface. + +Change backlight level in the kernel +==================================== + +This works for machines covered by case ii) in Section 2. Once the driver +received a notification, it will set the backlight level accordingly. This does +not affect the sending of event to user space, they are always sent to user +space regardless of whether or not the video module controls the backlight level +directly. This behaviour can be controlled through the brightness_switch_enabled +module parameter as documented in admin-guide/kernel-parameters.rst. It is +recommended to disable this behaviour once a GUI environment starts up and +wants to have full control of the backlight level. -- cgit v1.2.3 From 67ea15169b35216bd741bc36ce11cf424245eb88 Mon Sep 17 00:00:00 2001 From: Fabien Parent Date: Sat, 23 Mar 2019 22:15:59 +0100 Subject: dt-bindings: mediatek: topckgen: add support for MT8516 Add binding documentation of topckgen for MT8516 SoC. Signed-off-by: Fabien Parent Acked-by: Rob Herring Signed-off-by: Stephen Boyd --- .../bindings/arm/mediatek/mediatek,topckgen.txt | 1 + include/dt-bindings/clock/mt8516-clk.h | 192 +++++++++++++++++++++ 2 files changed, 193 insertions(+) create mode 100644 include/dt-bindings/clock/mt8516-clk.h (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/mediatek/mediatek,topckgen.txt b/Documentation/devicetree/bindings/arm/mediatek/mediatek,topckgen.txt index 46a1cfeb8b1d..a023b8338960 100644 --- a/Documentation/devicetree/bindings/arm/mediatek/mediatek,topckgen.txt +++ b/Documentation/devicetree/bindings/arm/mediatek/mediatek,topckgen.txt @@ -15,6 +15,7 @@ Required Properties: - "mediatek,mt8135-topckgen" - "mediatek,mt8173-topckgen" - "mediatek,mt8183-topckgen", "syscon" + - "mediatek,mt8516-topckgen" - #clock-cells: Must be 1 The topckgen controller uses the common clk binding from diff --git a/include/dt-bindings/clock/mt8516-clk.h b/include/dt-bindings/clock/mt8516-clk.h new file mode 100644 index 000000000000..8d44cb32efba --- /dev/null +++ b/include/dt-bindings/clock/mt8516-clk.h @@ -0,0 +1,192 @@ +/* SPDX-License-Identifier: GPL-2.0 */ +/* + * Copyright (c) 2019 MediaTek Inc. + * Copyright (c) 2019 BayLibre, SAS. + * Author: James Liao + */ + +#ifndef _DT_BINDINGS_CLK_MT8516_H +#define _DT_BINDINGS_CLK_MT8516_H + +/* TOPCKGEN */ + +#define CLK_TOP_CLK_NULL 0 +#define CLK_TOP_I2S_INFRA_BCK 1 +#define CLK_TOP_MEMPLL 2 +#define CLK_TOP_DMPLL 3 +#define CLK_TOP_MAINPLL_D2 4 +#define CLK_TOP_MAINPLL_D4 5 +#define CLK_TOP_MAINPLL_D8 6 +#define CLK_TOP_MAINPLL_D16 7 +#define CLK_TOP_MAINPLL_D11 8 +#define CLK_TOP_MAINPLL_D22 9 +#define CLK_TOP_MAINPLL_D3 10 +#define CLK_TOP_MAINPLL_D6 11 +#define CLK_TOP_MAINPLL_D12 12 +#define CLK_TOP_MAINPLL_D5 13 +#define CLK_TOP_MAINPLL_D10 14 +#define CLK_TOP_MAINPLL_D20 15 +#define CLK_TOP_MAINPLL_D40 16 +#define CLK_TOP_MAINPLL_D7 17 +#define CLK_TOP_MAINPLL_D14 18 +#define CLK_TOP_UNIVPLL_D2 19 +#define CLK_TOP_UNIVPLL_D4 20 +#define CLK_TOP_UNIVPLL_D8 21 +#define CLK_TOP_UNIVPLL_D16 22 +#define CLK_TOP_UNIVPLL_D3 23 +#define CLK_TOP_UNIVPLL_D6 24 +#define CLK_TOP_UNIVPLL_D12 25 +#define CLK_TOP_UNIVPLL_D24 26 +#define CLK_TOP_UNIVPLL_D5 27 +#define CLK_TOP_UNIVPLL_D20 28 +#define CLK_TOP_MMPLL380M 29 +#define CLK_TOP_MMPLL_D2 30 +#define CLK_TOP_MMPLL_200M 31 +#define CLK_TOP_USB_PHY48M 32 +#define CLK_TOP_APLL1 33 +#define CLK_TOP_APLL1_D2 34 +#define CLK_TOP_APLL1_D4 35 +#define CLK_TOP_APLL1_D8 36 +#define CLK_TOP_APLL2 37 +#define CLK_TOP_APLL2_D2 38 +#define CLK_TOP_APLL2_D4 39 +#define CLK_TOP_APLL2_D8 40 +#define CLK_TOP_CLK26M 41 +#define CLK_TOP_CLK26M_D2 42 +#define CLK_TOP_AHB_INFRA_D2 43 +#define CLK_TOP_NFI1X 44 +#define CLK_TOP_ETH_D2 45 +#define CLK_TOP_THEM 46 +#define CLK_TOP_APDMA 47 +#define CLK_TOP_I2C0 48 +#define CLK_TOP_I2C1 49 +#define CLK_TOP_AUXADC1 50 +#define CLK_TOP_NFI 51 +#define CLK_TOP_NFIECC 52 +#define CLK_TOP_DEBUGSYS 53 +#define CLK_TOP_PWM 54 +#define CLK_TOP_UART0 55 +#define CLK_TOP_UART1 56 +#define CLK_TOP_BTIF 57 +#define CLK_TOP_USB 58 +#define CLK_TOP_FLASHIF_26M 59 +#define CLK_TOP_AUXADC2 60 +#define CLK_TOP_I2C2 61 +#define CLK_TOP_MSDC0 62 +#define CLK_TOP_MSDC1 63 +#define CLK_TOP_NFI2X 64 +#define CLK_TOP_PMICWRAP_AP 65 +#define CLK_TOP_SEJ 66 +#define CLK_TOP_MEMSLP_DLYER 67 +#define CLK_TOP_SPI 68 +#define CLK_TOP_APXGPT 69 +#define CLK_TOP_AUDIO 70 +#define CLK_TOP_PMICWRAP_MD 71 +#define CLK_TOP_PMICWRAP_CONN 72 +#define CLK_TOP_PMICWRAP_26M 73 +#define CLK_TOP_AUX_ADC 74 +#define CLK_TOP_AUX_TP 75 +#define CLK_TOP_MSDC2 76 +#define CLK_TOP_RBIST 77 +#define CLK_TOP_NFI_BUS 78 +#define CLK_TOP_GCE 79 +#define CLK_TOP_TRNG 80 +#define CLK_TOP_SEJ_13M 81 +#define CLK_TOP_AES 82 +#define CLK_TOP_PWM_B 83 +#define CLK_TOP_PWM1_FB 84 +#define CLK_TOP_PWM2_FB 85 +#define CLK_TOP_PWM3_FB 86 +#define CLK_TOP_PWM4_FB 87 +#define CLK_TOP_PWM5_FB 88 +#define CLK_TOP_USB_1P 89 +#define CLK_TOP_FLASHIF_FREERUN 90 +#define CLK_TOP_66M_ETH 91 +#define CLK_TOP_133M_ETH 92 +#define CLK_TOP_FETH_25M 93 +#define CLK_TOP_FETH_50M 94 +#define CLK_TOP_FLASHIF_AXI 95 +#define CLK_TOP_USBIF 96 +#define CLK_TOP_UART2 97 +#define CLK_TOP_BSI 98 +#define CLK_TOP_RG_SPINOR 99 +#define CLK_TOP_RG_MSDC2 100 +#define CLK_TOP_RG_ETH 101 +#define CLK_TOP_RG_AUD1 102 +#define CLK_TOP_RG_AUD2 103 +#define CLK_TOP_RG_AUD_ENGEN1 104 +#define CLK_TOP_RG_AUD_ENGEN2 105 +#define CLK_TOP_RG_I2C 106 +#define CLK_TOP_RG_PWM_INFRA 107 +#define CLK_TOP_RG_AUD_SPDIF_IN 108 +#define CLK_TOP_RG_UART2 109 +#define CLK_TOP_RG_BSI 110 +#define CLK_TOP_RG_DBG_ATCLK 111 +#define CLK_TOP_RG_NFIECC 112 +#define CLK_TOP_RG_APLL1_D2_EN 113 +#define CLK_TOP_RG_APLL1_D4_EN 114 +#define CLK_TOP_RG_APLL1_D8_EN 115 +#define CLK_TOP_RG_APLL2_D2_EN 116 +#define CLK_TOP_RG_APLL2_D4_EN 117 +#define CLK_TOP_RG_APLL2_D8_EN 118 +#define CLK_TOP_APLL12_DIV0 119 +#define CLK_TOP_APLL12_DIV1 120 +#define CLK_TOP_APLL12_DIV2 121 +#define CLK_TOP_APLL12_DIV3 122 +#define CLK_TOP_APLL12_DIV4 123 +#define CLK_TOP_APLL12_DIV4B 124 +#define CLK_TOP_APLL12_DIV5 125 +#define CLK_TOP_APLL12_DIV5B 126 +#define CLK_TOP_APLL12_DIV6 127 +#define CLK_TOP_UART0_SEL 128 +#define CLK_TOP_EMI_DDRPHY_SEL 129 +#define CLK_TOP_AHB_INFRA_SEL 130 +#define CLK_TOP_MSDC0_SEL 131 +#define CLK_TOP_UART1_SEL 132 +#define CLK_TOP_MSDC1_SEL 133 +#define CLK_TOP_PMICSPI_SEL 134 +#define CLK_TOP_QAXI_AUD26M_SEL 135 +#define CLK_TOP_AUD_INTBUS_SEL 136 +#define CLK_TOP_NFI2X_PAD_SEL 137 +#define CLK_TOP_NFI1X_PAD_SEL 138 +#define CLK_TOP_DDRPHYCFG_SEL 139 +#define CLK_TOP_USB_78M_SEL 140 +#define CLK_TOP_SPINOR_SEL 141 +#define CLK_TOP_MSDC2_SEL 142 +#define CLK_TOP_ETH_SEL 143 +#define CLK_TOP_AUD1_SEL 144 +#define CLK_TOP_AUD2_SEL 145 +#define CLK_TOP_AUD_ENGEN1_SEL 146 +#define CLK_TOP_AUD_ENGEN2_SEL 147 +#define CLK_TOP_I2C_SEL 148 +#define CLK_TOP_AUD_I2S0_M_SEL 149 +#define CLK_TOP_AUD_I2S1_M_SEL 150 +#define CLK_TOP_AUD_I2S2_M_SEL 151 +#define CLK_TOP_AUD_I2S3_M_SEL 152 +#define CLK_TOP_AUD_I2S4_M_SEL 153 +#define CLK_TOP_AUD_I2S5_M_SEL 154 +#define CLK_TOP_AUD_SPDIF_B_SEL 155 +#define CLK_TOP_PWM_SEL 156 +#define CLK_TOP_SPI_SEL 157 +#define CLK_TOP_AUD_SPDIFIN_SEL 158 +#define CLK_TOP_UART2_SEL 159 +#define CLK_TOP_BSI_SEL 160 +#define CLK_TOP_DBG_ATCLK_SEL 161 +#define CLK_TOP_CSW_NFIECC_SEL 162 +#define CLK_TOP_NFIECC_SEL 163 +#define CLK_TOP_APLL12_CK_DIV0 164 +#define CLK_TOP_APLL12_CK_DIV1 165 +#define CLK_TOP_APLL12_CK_DIV2 166 +#define CLK_TOP_APLL12_CK_DIV3 167 +#define CLK_TOP_APLL12_CK_DIV4 168 +#define CLK_TOP_APLL12_CK_DIV4B 169 +#define CLK_TOP_APLL12_CK_DIV5 170 +#define CLK_TOP_APLL12_CK_DIV5B 171 +#define CLK_TOP_APLL12_CK_DIV6 172 +#define CLK_TOP_USB_78M 173 +#define CLK_TOP_MSDC0_INFRA 174 +#define CLK_TOP_MSDC1_INFRA 175 +#define CLK_TOP_MSDC2_INFRA 176 +#define CLK_TOP_NR_CLK 177 + +#endif /* _DT_BINDINGS_CLK_MT8516_H */ -- cgit v1.2.3 From eb2814bc60d93ef65b0e0f6db456b4f58ff02a06 Mon Sep 17 00:00:00 2001 From: Fabien Parent Date: Sat, 23 Mar 2019 22:16:00 +0100 Subject: dt-bindings: mediatek: infracfg: add support for MT8516 Add binding documentation of infracfg for MT8516 SoC. Signed-off-by: Fabien Parent Acked-by: Rob Herring Signed-off-by: Stephen Boyd --- .../devicetree/bindings/arm/mediatek/mediatek,infracfg.txt | 1 + include/dt-bindings/clock/mt8516-clk.h | 9 +++++++++ 2 files changed, 10 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/mediatek/mediatek,infracfg.txt b/Documentation/devicetree/bindings/arm/mediatek/mediatek,infracfg.txt index 0b324d216724..a90913988d7e 100644 --- a/Documentation/devicetree/bindings/arm/mediatek/mediatek,infracfg.txt +++ b/Documentation/devicetree/bindings/arm/mediatek/mediatek,infracfg.txt @@ -16,6 +16,7 @@ Required Properties: - "mediatek,mt8135-infracfg", "syscon" - "mediatek,mt8173-infracfg", "syscon" - "mediatek,mt8183-infracfg", "syscon" + - "mediatek,mt8516-infracfg", "syscon" - #clock-cells: Must be 1 - #reset-cells: Must be 1 diff --git a/include/dt-bindings/clock/mt8516-clk.h b/include/dt-bindings/clock/mt8516-clk.h index 8d44cb32efba..956ee2c0748e 100644 --- a/include/dt-bindings/clock/mt8516-clk.h +++ b/include/dt-bindings/clock/mt8516-clk.h @@ -8,6 +8,15 @@ #ifndef _DT_BINDINGS_CLK_MT8516_H #define _DT_BINDINGS_CLK_MT8516_H +/* INFRACFG */ + +#define CLK_IFR_MUX1_SEL 0 +#define CLK_IFR_ETH_25M_SEL 1 +#define CLK_IFR_I2C0_SEL 2 +#define CLK_IFR_I2C1_SEL 3 +#define CLK_IFR_I2C2_SEL 4 +#define CLK_IFR_NR_CLK 5 + /* TOPCKGEN */ #define CLK_TOP_CLK_NULL 0 -- cgit v1.2.3 From 699480d062e06b174ee8aabd094b084deb2688b2 Mon Sep 17 00:00:00 2001 From: Fabien Parent Date: Sat, 23 Mar 2019 22:16:01 +0100 Subject: dt-bindings: mediatek: apmixedsys: add support for MT8516 Add binding documentation of apmixedsys for MT8516 SoC. Signed-off-by: Fabien Parent Acked-by: Rob Herring Signed-off-by: Stephen Boyd --- .../devicetree/bindings/arm/mediatek/mediatek,apmixedsys.txt | 1 + include/dt-bindings/clock/mt8516-clk.h | 10 ++++++++++ 2 files changed, 11 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/mediatek/mediatek,apmixedsys.txt b/Documentation/devicetree/bindings/arm/mediatek/mediatek,apmixedsys.txt index 9adf28d0141b..161e63a6c254 100644 --- a/Documentation/devicetree/bindings/arm/mediatek/mediatek,apmixedsys.txt +++ b/Documentation/devicetree/bindings/arm/mediatek/mediatek,apmixedsys.txt @@ -15,6 +15,7 @@ Required Properties: - "mediatek,mt8135-apmixedsys" - "mediatek,mt8173-apmixedsys" - "mediatek,mt8183-apmixedsys", "syscon" + - "mediatek,mt8516-apmixedsys" - #clock-cells: Must be 1 The apmixedsys controller uses the common clk binding from diff --git a/include/dt-bindings/clock/mt8516-clk.h b/include/dt-bindings/clock/mt8516-clk.h index 956ee2c0748e..9cfca53cd78d 100644 --- a/include/dt-bindings/clock/mt8516-clk.h +++ b/include/dt-bindings/clock/mt8516-clk.h @@ -8,6 +8,16 @@ #ifndef _DT_BINDINGS_CLK_MT8516_H #define _DT_BINDINGS_CLK_MT8516_H +/* APMIXEDSYS */ + +#define CLK_APMIXED_ARMPLL 0 +#define CLK_APMIXED_MAINPLL 1 +#define CLK_APMIXED_UNIVPLL 2 +#define CLK_APMIXED_MMPLL 3 +#define CLK_APMIXED_APLL1 4 +#define CLK_APMIXED_APLL2 5 +#define CLK_APMIXED_NR_CLK 6 + /* INFRACFG */ #define CLK_IFR_MUX1_SEL 0 -- cgit v1.2.3 From e3ee1f21b3b7c7c83f298ddece72b8779aa3dca3 Mon Sep 17 00:00:00 2001 From: Sugaya Taichi Date: Thu, 25 Apr 2019 19:41:00 +0900 Subject: dt-bindings: clock: milbeaut: add Milbeaut clock description Add DT bindings document for Milbeaut clock. Signed-off-by: Sugaya Taichi Signed-off-by: Stephen Boyd --- .../devicetree/bindings/clock/milbeaut-clock.yaml | 73 ++++++++++++++++++++++ 1 file changed, 73 insertions(+) create mode 100644 Documentation/devicetree/bindings/clock/milbeaut-clock.yaml (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/clock/milbeaut-clock.yaml b/Documentation/devicetree/bindings/clock/milbeaut-clock.yaml new file mode 100644 index 000000000000..5cf0b811821e --- /dev/null +++ b/Documentation/devicetree/bindings/clock/milbeaut-clock.yaml @@ -0,0 +1,73 @@ +# SPDX-License-Identifier: GPL-2.0 +%YAML 1.2 +--- +$id: http://devicetree.org/schemas/bindings/clock/milbeaut-clock.yaml# +$schema: http://devicetree.org/meta-schemas/core.yaml# + +title: Milbeaut SoCs Clock Controller Binding + +maintainers: + - Taichi Sugaya + +description: | + Milbeaut SoCs Clock controller is an integrated clock controller, which + generates and supplies to all modules. + + This binding uses common clock bindings + [1] Documentation/devicetree/bindings/clock/clock-bindings.txt + +properties: + compatible: + oneOf: + - items: + - enum: + - socionext,milbeaut-m10v-ccu + clocks: + maxItems: 1 + description: external clock + + '#clock-cells': + const: 1 + +required: + - compatible + - reg + - clocks + - '#clock-cells' + +examples: + # Clock controller node: + - | + m10v-clk-ctrl@1d021000 { + compatible = "socionext,milbeaut-m10v-clk-ccu"; + reg = <0x1d021000 0x4000>; + #clock-cells = <1>; + clocks = <&clki40mhz>; + }; + + # Required an external clock for Clock controller node: + - | + clocks { + clki40mhz: clki40mhz { + compatible = "fixed-clock"; + #clock-cells = <0>; + clock-frequency = <40000000>; + }; + /* other clocks */ + }; + + # The clock consumer shall specify the desired clock-output of the clock + # controller as below by specifying output-id in its "clk" phandle cell. + # 2: uart + # 4: 32-bit timer + # 7: UHS-I/II + - | + serial@1e700010 { + compatible = "socionext,milbeaut-usio-uart"; + reg = <0x1e700010 0x10>; + interrupts = <0 141 0x4>, <0 149 0x4>; + interrupt-names = "rx", "tx"; + clocks = <&clk 2>; + }; + +... -- cgit v1.2.3 From 427503519739e779c0db8afe876c1b33f3ac60ae Mon Sep 17 00:00:00 2001 From: Will Deacon Date: Wed, 10 Apr 2019 11:51:54 +0100 Subject: futex: Update comments and docs about return values of arch futex code The architecture implementations of 'arch_futex_atomic_op_inuser()' and 'futex_atomic_cmpxchg_inatomic()' are permitted to return only -EFAULT, -EAGAIN or -ENOSYS in the case of failure. Update the comments in the asm-generic/ implementation and also a stray reference in the robust futex documentation. Signed-off-by: Will Deacon --- Documentation/robust-futexes.txt | 3 +-- include/asm-generic/futex.h | 8 ++++++-- 2 files changed, 7 insertions(+), 4 deletions(-) (limited to 'Documentation') diff --git a/Documentation/robust-futexes.txt b/Documentation/robust-futexes.txt index 6c42c75103eb..6361fb01c9c1 100644 --- a/Documentation/robust-futexes.txt +++ b/Documentation/robust-futexes.txt @@ -218,5 +218,4 @@ All other architectures should build just fine too - but they won't have the new syscalls yet. Architectures need to implement the new futex_atomic_cmpxchg_inatomic() -inline function before writing up the syscalls (that function returns --ENOSYS right now). +inline function before writing up the syscalls. diff --git a/include/asm-generic/futex.h b/include/asm-generic/futex.h index fcb61b4659b3..8666fe7f35d7 100644 --- a/include/asm-generic/futex.h +++ b/include/asm-generic/futex.h @@ -23,7 +23,9 @@ * * Return: * 0 - On success - * <0 - On error + * -EFAULT - User access resulted in a page fault + * -EAGAIN - Atomic operation was unable to complete due to contention + * -ENOSYS - Operation not supported */ static inline int arch_futex_atomic_op_inuser(int op, u32 oparg, int *oval, u32 __user *uaddr) @@ -85,7 +87,9 @@ out_pagefault_enable: * * Return: * 0 - On success - * <0 - On error + * -EFAULT - User access resulted in a page fault + * -EAGAIN - Atomic operation was unable to complete due to contention + * -ENOSYS - Function not implemented (only if !HAVE_FUTEX_CMPXCHG) */ static inline int futex_atomic_cmpxchg_inatomic(u32 *uval, u32 __user *uaddr, -- cgit v1.2.3 From 3e5903eb9cff707301712498aed9e34b3e2ee883 Mon Sep 17 00:00:00 2001 From: Petr Mladek Date: Wed, 17 Apr 2019 13:53:48 +0200 Subject: vsprintf: Prevent crash when dereferencing invalid pointers We already prevent crash when dereferencing some obviously broken pointers. But the handling is not consistent. Sometimes we print "(null)" only for pure NULL pointer, sometimes for pointers in the first page and sometimes also for pointers in the last page (error codes). Note that printk() call this code under logbuf_lock. Any recursive printks are redirected to the printk_safe implementation and the messages are stored into per-CPU buffers. These buffers might be eventually flushed in printk_safe_flush_on_panic() but it is not guaranteed. This patch adds a check using probe_kernel_read(). It is not a full-proof test. But it should help to see the error message in 99% situations where the kernel would silently crash otherwise. Also it makes the error handling unified for "%s" and the many %p* specifiers that need to read the data from a given address. We print: + (null) when accessing data on pure pure NULL address + (efault) when accessing data on an invalid address It does not affect the %p* specifiers that just print the given address in some form, namely %pF, %pf, %pS, %ps, %pB, %pK, %px, and plain %p. Note that we print (efault) from security reasons. In fact, the real address can be seen only by %px or eventually %pK. Link: http://lkml.kernel.org/r/20190417115350.20479-9-pmladek@suse.com To: Rasmus Villemoes Cc: Linus Torvalds Cc: "Tobin C . Harding" Cc: Joe Perches Cc: Andrew Morton Cc: Michal Hocko Cc: Steven Rostedt Cc: Sergey Senozhatsky Cc: linux-kernel@vger.kernel.org Reviewed-by: Sergey Senozhatsky Reviewed-by: Andy Shevchenko Signed-off-by: Petr Mladek --- Documentation/core-api/printk-formats.rst | 7 ++ lib/test_printf.c | 22 ++++- lib/vsprintf.c | 136 ++++++++++++++++++++++-------- 3 files changed, 129 insertions(+), 36 deletions(-) (limited to 'Documentation') diff --git a/Documentation/core-api/printk-formats.rst b/Documentation/core-api/printk-formats.rst index c37ec7cd9c06..b2cac8d76b66 100644 --- a/Documentation/core-api/printk-formats.rst +++ b/Documentation/core-api/printk-formats.rst @@ -58,6 +58,13 @@ A raw pointer value may be printed with %p which will hash the address before printing. The kernel also supports extended specifiers for printing pointers of different types. +Some of the extended specifiers print the data on the given address instead +of printing the address itself. In this case, the following error messages +might be printed instead of the unreachable information:: + + (null) data on plain NULL address + (efault) data on invalid address + Plain Pointers -------------- diff --git a/lib/test_printf.c b/lib/test_printf.c index 250ee864b8b8..359ae4fb1ece 100644 --- a/lib/test_printf.c +++ b/lib/test_printf.c @@ -239,6 +239,7 @@ plain_format(void) #define PTR ((void *)0x456789ab) #define PTR_STR "456789ab" #define PTR_VAL_NO_CRNG "(ptrval)" +#define ZEROS "" static int __init plain_format(void) @@ -268,7 +269,6 @@ plain_hash_to_buffer(const void *p, char *buf, size_t len) return 0; } - static int __init plain_hash(void) { @@ -325,6 +325,24 @@ test_hashed(const char *fmt, const void *p) test(buf, fmt, p); } +static void __init +null_pointer(void) +{ + test_hashed("%p", NULL); + test(ZEROS "00000000", "%px", NULL); + test("(null)", "%pE", NULL); +} + +#define PTR_INVALID ((void *)0x000000ab) + +static void __init +invalid_pointer(void) +{ + test_hashed("%p", PTR_INVALID); + test(ZEROS "000000ab", "%px", PTR_INVALID); + test("(efault)", "%pE", PTR_INVALID); +} + static void __init symbol_ptr(void) { @@ -571,6 +589,8 @@ static void __init test_pointer(void) { plain(); + null_pointer(); + invalid_pointer(); symbol_ptr(); kernel_ptr(); struct_resource(); diff --git a/lib/vsprintf.c b/lib/vsprintf.c index f471a658422f..b989f1e8f35b 100644 --- a/lib/vsprintf.c +++ b/lib/vsprintf.c @@ -612,12 +612,45 @@ static char *string_nocheck(char *buf, char *end, const char *s, return widen_string(buf, len, end, spec); } +/* + * This is not a fool-proof test. 99% of the time that this will fault is + * due to a bad pointer, not one that crosses into bad memory. Just test + * the address to make sure it doesn't fault due to a poorly added printk + * during debugging. + */ +static const char *check_pointer_msg(const void *ptr) +{ + char byte; + + if (!ptr) + return "(null)"; + + if (probe_kernel_address(ptr, byte)) + return "(efault)"; + + return NULL; +} + +static int check_pointer(char **buf, char *end, const void *ptr, + struct printf_spec spec) +{ + const char *err_msg; + + err_msg = check_pointer_msg(ptr); + if (err_msg) { + *buf = string_nocheck(*buf, end, err_msg, spec); + return -EFAULT; + } + + return 0; +} + static noinline_for_stack char *string(char *buf, char *end, const char *s, struct printf_spec spec) { - if ((unsigned long)s < PAGE_SIZE) - s = "(null)"; + if (check_pointer(&buf, end, s, spec)) + return buf; return string_nocheck(buf, end, s, spec); } @@ -792,6 +825,11 @@ char *dentry_name(char *buf, char *end, const struct dentry *d, struct printf_sp rcu_read_lock(); for (i = 0; i < depth; i++, d = p) { + if (check_pointer(&buf, end, d, spec)) { + rcu_read_unlock(); + return buf; + } + p = READ_ONCE(d->d_parent); array[i] = READ_ONCE(d->d_name.name); if (p == d) { @@ -822,8 +860,12 @@ static noinline_for_stack char *bdev_name(char *buf, char *end, struct block_device *bdev, struct printf_spec spec, const char *fmt) { - struct gendisk *hd = bdev->bd_disk; - + struct gendisk *hd; + + if (check_pointer(&buf, end, bdev, spec)) + return buf; + + hd = bdev->bd_disk; buf = string(buf, end, hd->disk_name, spec); if (bdev->bd_part->partno) { if (isdigit(hd->disk_name[strlen(hd->disk_name)-1])) { @@ -942,6 +984,9 @@ char *resource_string(char *buf, char *end, struct resource *res, int decode = (fmt[0] == 'R') ? 1 : 0; const struct printf_spec *specp; + if (check_pointer(&buf, end, res, spec)) + return buf; + *p++ = '['; if (res->flags & IORESOURCE_IO) { p = string_nocheck(p, pend, "io ", str_spec); @@ -1004,9 +1049,8 @@ char *hex_string(char *buf, char *end, u8 *addr, struct printf_spec spec, /* nothing to print */ return buf; - if (ZERO_OR_NULL_PTR(addr)) - /* NULL pointer */ - return string(buf, end, NULL, spec); + if (check_pointer(&buf, end, addr, spec)) + return buf; switch (fmt[1]) { case 'C': @@ -1053,6 +1097,9 @@ char *bitmap_string(char *buf, char *end, unsigned long *bitmap, int i, chunksz; bool first = true; + if (check_pointer(&buf, end, bitmap, spec)) + return buf; + /* reused to print numbers */ spec = (struct printf_spec){ .flags = SMALL | ZEROPAD, .base = 16 }; @@ -1094,6 +1141,9 @@ char *bitmap_list_string(char *buf, char *end, unsigned long *bitmap, int cur, rbot, rtop; bool first = true; + if (check_pointer(&buf, end, bitmap, spec)) + return buf; + rbot = cur = find_first_bit(bitmap, nr_bits); while (cur < nr_bits) { rtop = cur; @@ -1132,6 +1182,9 @@ char *mac_address_string(char *buf, char *end, u8 *addr, char separator; bool reversed = false; + if (check_pointer(&buf, end, addr, spec)) + return buf; + switch (fmt[1]) { case 'F': separator = '-'; @@ -1437,6 +1490,9 @@ char *ip_addr_string(char *buf, char *end, const void *ptr, { char *err_fmt_msg; + if (check_pointer(&buf, end, ptr, spec)) + return buf; + switch (fmt[1]) { case '6': return ip6_addr_string(buf, end, ptr, spec, fmt); @@ -1475,9 +1531,8 @@ char *escaped_string(char *buf, char *end, u8 *addr, struct printf_spec spec, if (spec.field_width == 0) return buf; /* nothing to print */ - if (ZERO_OR_NULL_PTR(addr)) - return string(buf, end, NULL, spec); /* NULL pointer */ - + if (check_pointer(&buf, end, addr, spec)) + return buf; do { switch (fmt[count++]) { @@ -1523,10 +1578,14 @@ char *escaped_string(char *buf, char *end, u8 *addr, struct printf_spec spec, return buf; } -static char *va_format(char *buf, char *end, struct va_format *va_fmt) +static char *va_format(char *buf, char *end, struct va_format *va_fmt, + struct printf_spec spec, const char *fmt) { va_list va; + if (check_pointer(&buf, end, va_fmt, spec)) + return buf; + va_copy(va, *va_fmt->va); buf += vsnprintf(buf, end > buf ? end - buf : 0, va_fmt->fmt, va); va_end(va); @@ -1544,6 +1603,9 @@ char *uuid_string(char *buf, char *end, const u8 *addr, const u8 *index = uuid_index; bool uc = false; + if (check_pointer(&buf, end, addr, spec)) + return buf; + switch (*(++fmt)) { case 'L': uc = true; /* fall-through */ @@ -1582,6 +1644,9 @@ char *netdev_bits(char *buf, char *end, const void *addr, unsigned long long num; int size; + if (check_pointer(&buf, end, addr, spec)) + return buf; + switch (fmt[1]) { case 'F': num = *(const netdev_features_t *)addr; @@ -1595,11 +1660,15 @@ char *netdev_bits(char *buf, char *end, const void *addr, } static noinline_for_stack -char *address_val(char *buf, char *end, const void *addr, const char *fmt) +char *address_val(char *buf, char *end, const void *addr, + struct printf_spec spec, const char *fmt) { unsigned long long num; int size; + if (check_pointer(&buf, end, addr, spec)) + return buf; + switch (fmt[1]) { case 'd': num = *(const dma_addr_t *)addr; @@ -1651,12 +1720,16 @@ char *time_str(char *buf, char *end, const struct rtc_time *tm, bool r) } static noinline_for_stack -char *rtc_str(char *buf, char *end, const struct rtc_time *tm, const char *fmt) +char *rtc_str(char *buf, char *end, const struct rtc_time *tm, + struct printf_spec spec, const char *fmt) { bool have_t = true, have_d = true; bool raw = false; int count = 2; + if (check_pointer(&buf, end, tm, spec)) + return buf; + switch (fmt[count]) { case 'd': have_t = false; @@ -1690,7 +1763,7 @@ char *time_and_date(char *buf, char *end, void *ptr, struct printf_spec spec, { switch (fmt[1]) { case 'R': - return rtc_str(buf, end, (const struct rtc_time *)ptr, fmt); + return rtc_str(buf, end, (const struct rtc_time *)ptr, spec, fmt); default: return string_nocheck(buf, end, "(%ptR?)", spec); } @@ -1703,8 +1776,8 @@ char *clock(char *buf, char *end, struct clk *clk, struct printf_spec spec, if (!IS_ENABLED(CONFIG_HAVE_CLK)) return string_nocheck(buf, end, "(%pC?)", spec); - if (!clk) - return string(buf, end, NULL, spec); + if (check_pointer(&buf, end, clk, spec)) + return buf; switch (fmt[1]) { case 'n': @@ -1751,6 +1824,9 @@ char *flags_string(char *buf, char *end, void *flags_ptr, unsigned long flags; const struct trace_print_flags *names; + if (check_pointer(&buf, end, flags_ptr, spec)) + return buf; + switch (fmt[1]) { case 'p': flags = *(unsigned long *)flags_ptr; @@ -1825,8 +1901,8 @@ char *device_node_string(char *buf, char *end, struct device_node *dn, if (!IS_ENABLED(CONFIG_OF)) return string_nocheck(buf, end, "(%pOF?)", spec); - if ((unsigned long)dn < PAGE_SIZE) - return string_nocheck(buf, end, "(null)", spec); + if (check_pointer(&buf, end, dn, spec)) + return buf; /* simple case without anything any more format specifiers */ fmt++; @@ -2021,18 +2097,6 @@ static noinline_for_stack char *pointer(const char *fmt, char *buf, char *end, void *ptr, struct printf_spec spec) { - const int default_width = 2 * sizeof(void *); - - if (!ptr && *fmt != 'K' && *fmt != 'x') { - /* - * Print (null) with the same width as a pointer so it makes - * tabular output look nice. - */ - if (spec.field_width == -1) - spec.field_width = default_width; - return string_nocheck(buf, end, "(null)", spec); - } - switch (*fmt) { case 'F': case 'f': @@ -2074,13 +2138,13 @@ char *pointer(const char *fmt, char *buf, char *end, void *ptr, case 'U': return uuid_string(buf, end, ptr, spec, fmt); case 'V': - return va_format(buf, end, ptr); + return va_format(buf, end, ptr, spec, fmt); case 'K': return restricted_pointer(buf, end, ptr, spec); case 'N': return netdev_bits(buf, end, ptr, spec, fmt); case 'a': - return address_val(buf, end, ptr, fmt); + return address_val(buf, end, ptr, spec, fmt); case 'd': return dentry_name(buf, end, ptr, spec, fmt); case 't': @@ -2714,11 +2778,13 @@ int vbin_printf(u32 *bin_buf, size_t size, const char *fmt, va_list args) case FORMAT_TYPE_STR: { const char *save_str = va_arg(args, char *); + const char *err_msg; size_t len; - if ((unsigned long)save_str > (unsigned long)-PAGE_SIZE - || (unsigned long)save_str < PAGE_SIZE) - save_str = "(null)"; + err_msg = check_pointer_msg(save_str); + if (err_msg) + save_str = err_msg; + len = strlen(save_str) + 1; if (str + len < end) memcpy(str, save_str, len); -- cgit v1.2.3 From 635720ac75a51092b456bed517ff170047883252 Mon Sep 17 00:00:00 2001 From: Petr Mladek Date: Wed, 17 Apr 2019 13:53:49 +0200 Subject: vsprintf: Avoid confusion between invalid address and value We are able to detect invalid values handled by %p[iI] printk specifier. The current error message is "invalid address". It might cause confusion against "(efault)" reported by the generic valid_pointer_address() check. Let's unify the style and use the more appropriate error code description "(einval)". Link: http://lkml.kernel.org/r/20190417115350.20479-10-pmladek@suse.com To: Rasmus Villemoes Cc: Linus Torvalds Cc: "Tobin C . Harding" Cc: Joe Perches Cc: Andrew Morton Cc: Michal Hocko Cc: Steven Rostedt Cc: Sergey Senozhatsky Cc: linux-kernel@vger.kernel.org Reviewed-by: Sergey Senozhatsky Reviewed-by: Andy Shevchenko Signed-off-by: Petr Mladek --- Documentation/core-api/printk-formats.rst | 1 + lib/vsprintf.c | 2 +- 2 files changed, 2 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/core-api/printk-formats.rst b/Documentation/core-api/printk-formats.rst index b2cac8d76b66..75d2bbe9813f 100644 --- a/Documentation/core-api/printk-formats.rst +++ b/Documentation/core-api/printk-formats.rst @@ -64,6 +64,7 @@ might be printed instead of the unreachable information:: (null) data on plain NULL address (efault) data on invalid address + (einval) invalid data on a valid address Plain Pointers -------------- diff --git a/lib/vsprintf.c b/lib/vsprintf.c index b989f1e8f35b..4e5666035b74 100644 --- a/lib/vsprintf.c +++ b/lib/vsprintf.c @@ -1511,7 +1511,7 @@ char *ip_addr_string(char *buf, char *end, const void *ptr, case AF_INET6: return ip6_addr_string_sa(buf, end, &sa->v6, spec, fmt); default: - return string_nocheck(buf, end, "(invalid address)", spec); + return string_nocheck(buf, end, "(einval)", spec); }} } -- cgit v1.2.3 From e5ce5e7267ddcbe13ab9ead2542524e1b7993e5a Mon Sep 17 00:00:00 2001 From: Jeremy Linton Date: Mon, 15 Apr 2019 16:21:20 -0500 Subject: arm64: Provide a command line to disable spectre_v2 mitigation There are various reasons, such as benchmarking, to disable spectrev2 mitigation on a machine. Provide a command-line option to do so. Signed-off-by: Jeremy Linton Reviewed-by: Suzuki K Poulose Reviewed-by: Andre Przywara Reviewed-by: Catalin Marinas Tested-by: Stefan Wahren Cc: Jonathan Corbet Cc: linux-doc@vger.kernel.org Signed-off-by: Will Deacon --- Documentation/admin-guide/kernel-parameters.txt | 8 ++++---- arch/arm64/kernel/cpu_errata.c | 13 +++++++++++++ 2 files changed, 17 insertions(+), 4 deletions(-) (limited to 'Documentation') diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt index cf82bac648cd..6a929258faf7 100644 --- a/Documentation/admin-guide/kernel-parameters.txt +++ b/Documentation/admin-guide/kernel-parameters.txt @@ -2905,10 +2905,10 @@ check bypass). With this option data leaks are possible in the system. - nospectre_v2 [X86,PPC_FSL_BOOK3E] Disable all mitigations for the Spectre variant 2 - (indirect branch prediction) vulnerability. System may - allow data leaks with this option, which is equivalent - to spectre_v2=off. + nospectre_v2 [X86,PPC_FSL_BOOK3E,ARM64] Disable all mitigations for + the Spectre variant 2 (indirect branch prediction) + vulnerability. System may allow data leaks with this + option. nospec_store_bypass_disable [HW] Disable all mitigations for the Speculative Store Bypass vulnerability diff --git a/arch/arm64/kernel/cpu_errata.c b/arch/arm64/kernel/cpu_errata.c index 9950bb0cbd52..d2b2c69d31bb 100644 --- a/arch/arm64/kernel/cpu_errata.c +++ b/arch/arm64/kernel/cpu_errata.c @@ -220,6 +220,14 @@ static void qcom_link_stack_sanitization(void) : "=&r" (tmp)); } +static bool __nospectre_v2; +static int __init parse_nospectre_v2(char *str) +{ + __nospectre_v2 = true; + return 0; +} +early_param("nospectre_v2", parse_nospectre_v2); + static void enable_smccc_arch_workaround_1(const struct arm64_cpu_capabilities *entry) { @@ -231,6 +239,11 @@ enable_smccc_arch_workaround_1(const struct arm64_cpu_capabilities *entry) if (!entry->matches(entry, SCOPE_LOCAL_CPU)) return; + if (__nospectre_v2) { + pr_info_once("spectrev2 mitigation disabled by command line option\n"); + return; + } + if (psci_ops.smccc_version == SMCCC_VERSION_1_0) return; -- cgit v1.2.3 From 24512228b7a3f412b5a51f189df302616b021c33 Mon Sep 17 00:00:00 2001 From: Mel Gorman Date: Thu, 25 Apr 2019 22:23:51 -0700 Subject: mm: do not boost watermarks to avoid fragmentation for the DISCONTIG memory model Mikulas Patocka reported that commit 1c30844d2dfe ("mm: reclaim small amounts of memory when an external fragmentation event occurs") "broke" memory management on parisc. The machine is not NUMA but the DISCONTIG model creates three pgdats even though it's a UMA machine for the following ranges 0) Start 0x0000000000000000 End 0x000000003fffffff Size 1024 MB 1) Start 0x0000000100000000 End 0x00000001bfdfffff Size 3070 MB 2) Start 0x0000004040000000 End 0x00000040ffffffff Size 3072 MB Mikulas reported: With the patch 1c30844d2, the kernel will incorrectly reclaim the first zone when it fills up, ignoring the fact that there are two completely free zones. Basiscally, it limits cache size to 1GiB. For example, if I run: # dd if=/dev/sda of=/dev/null bs=1M count=2048 - with the proper kernel, there should be "Buffers - 2GiB" when this command finishes. With the patch 1c30844d2, buffers will consume just 1GiB or slightly more, because the kernel was incorrectly reclaiming them. The page allocator and reclaim makes assumptions that pgdats really represent NUMA nodes and zones represent ranges and makes decisions on that basis. Watermark boosting for small pgdats leads to unexpected results even though this would have behaved reasonably on SPARSEMEM. DISCONTIG is essentially deprecated and even parisc plans to move to SPARSEMEM so there is no need to be fancy, this patch simply disables watermark boosting by default on DISCONTIGMEM. Link: http://lkml.kernel.org/r/20190419094335.GJ18914@techsingularity.net Fixes: 1c30844d2dfe ("mm: reclaim small amounts of memory when an external fragmentation event occurs") Signed-off-by: Mel Gorman Reported-by: Mikulas Patocka Tested-by: Mikulas Patocka Acked-by: Vlastimil Babka Cc: James Bottomley Cc: Matthew Wilcox Cc: Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- Documentation/sysctl/vm.txt | 16 ++++++++-------- mm/page_alloc.c | 13 +++++++++++++ 2 files changed, 21 insertions(+), 8 deletions(-) (limited to 'Documentation') diff --git a/Documentation/sysctl/vm.txt b/Documentation/sysctl/vm.txt index 6af24cdb25cc..3f13d8599337 100644 --- a/Documentation/sysctl/vm.txt +++ b/Documentation/sysctl/vm.txt @@ -866,14 +866,14 @@ The intent is that compaction has less work to do in the future and to increase the success rate of future high-order allocations such as SLUB allocations, THP and hugetlbfs pages. -To make it sensible with respect to the watermark_scale_factor parameter, -the unit is in fractions of 10,000. The default value of 15,000 means -that up to 150% of the high watermark will be reclaimed in the event of -a pageblock being mixed due to fragmentation. The level of reclaim is -determined by the number of fragmentation events that occurred in the -recent past. If this value is smaller than a pageblock then a pageblocks -worth of pages will be reclaimed (e.g. 2MB on 64-bit x86). A boost factor -of 0 will disable the feature. +To make it sensible with respect to the watermark_scale_factor +parameter, the unit is in fractions of 10,000. The default value of +15,000 on !DISCONTIGMEM configurations means that up to 150% of the high +watermark will be reclaimed in the event of a pageblock being mixed due +to fragmentation. The level of reclaim is determined by the number of +fragmentation events that occurred in the recent past. If this value is +smaller than a pageblock then a pageblocks worth of pages will be reclaimed +(e.g. 2MB on 64-bit x86). A boost factor of 0 will disable the feature. ============================================================= diff --git a/mm/page_alloc.c b/mm/page_alloc.c index c6ce20aaf80b..6c6d9f1c404e 100644 --- a/mm/page_alloc.c +++ b/mm/page_alloc.c @@ -266,7 +266,20 @@ compound_page_dtor * const compound_page_dtors[] = { int min_free_kbytes = 1024; int user_min_free_kbytes = -1; +#ifdef CONFIG_DISCONTIGMEM +/* + * DiscontigMem defines memory ranges as separate pg_data_t even if the ranges + * are not on separate NUMA nodes. Functionally this works but with + * watermark_boost_factor, it can reclaim prematurely as the ranges can be + * quite small. By default, do not boost watermarks on discontigmem as in + * many cases very high-order allocations like THP are likely to be + * unsupported and the premature reclaim offsets the advantage of long-term + * fragmentation avoidance. + */ +int watermark_boost_factor __read_mostly; +#else int watermark_boost_factor __read_mostly = 15000; +#endif int watermark_scale_factor = 10; static unsigned long nr_kernel_pages __initdata; -- cgit v1.2.3 From 28ba53c07638f31b153e3a32672a6124d0ff2a97 Mon Sep 17 00:00:00 2001 From: Masahiro Yamada Date: Sun, 28 Apr 2019 13:45:36 -0400 Subject: unicode: refactor the rule for regenerating utf8data.h scripts/mkutf8data is used only when regenerating utf8data.h, which never happens in the normal kernel build. However, it is irrespectively built if CONFIG_UNICODE is enabled. Moreover, there is no good reason for it to reside in the scripts/ directory since it is only used in fs/unicode/. Hence, move it from scripts/ to fs/unicode/. In some cases, we bypass build artifacts in the normal build. The conventional way to do so is to surround the code with ifdef REGENERATE_*. For example, - 7373f4f83c71 ("kbuild: add implicit rules for parser generation") - 6aaf49b495b4 ("crypto: arm,arm64 - Fix random regeneration of S_shipped") I rewrote the rule in a more kbuild'ish style. In the normal build, utf8data.h is just shipped from the check-in file. $ make [ snip ] SHIPPED fs/unicode/utf8data.h CC fs/unicode/utf8-norm.o CC fs/unicode/utf8-core.o CC fs/unicode/utf8-selftest.o AR fs/unicode/built-in.a If you want to generate utf8data.h based on UCD, put *.txt files into fs/unicode/, then pass REGENERATE_UTF8DATA=1 from the command line. The mkutf8data tool will be automatically compiled to generate the utf8data.h from the *.txt files. $ make REGENERATE_UTF8DATA=1 [ snip ] HOSTCC fs/unicode/mkutf8data GEN fs/unicode/utf8data.h CC fs/unicode/utf8-norm.o CC fs/unicode/utf8-core.o CC fs/unicode/utf8-selftest.o AR fs/unicode/built-in.a I renamed the check-in utf8data.h to utf8data.h_shipped so that this will work for the out-of-tree build. You can update it based on the latest UCD like this: $ make REGENERATE_UTF8DATA=1 fs/unicode/ $ cp fs/unicode/utf8data.h fs/unicode/utf8data.h_shipped Also, I added entries to .gitignore and dontdiff. Signed-off-by: Masahiro Yamada Signed-off-by: Theodore Ts'o --- Documentation/dontdiff | 2 + fs/unicode/.gitignore | 2 + fs/unicode/Makefile | 41 +- fs/unicode/README.utf8data | 9 +- fs/unicode/mkutf8data.c | 3419 ++++++++++++++++++++++++++++++++++ fs/unicode/utf8data.h | 4109 ----------------------------------------- fs/unicode/utf8data.h_shipped | 4109 +++++++++++++++++++++++++++++++++++++++++ scripts/Makefile | 1 - scripts/mkutf8data.c | 3419 ---------------------------------- 9 files changed, 7566 insertions(+), 7545 deletions(-) create mode 100644 fs/unicode/.gitignore create mode 100644 fs/unicode/mkutf8data.c delete mode 100644 fs/unicode/utf8data.h create mode 100644 fs/unicode/utf8data.h_shipped delete mode 100644 scripts/mkutf8data.c (limited to 'Documentation') diff --git a/Documentation/dontdiff b/Documentation/dontdiff index ef25a066d952..93693775639f 100644 --- a/Documentation/dontdiff +++ b/Documentation/dontdiff @@ -176,6 +176,7 @@ mkprep mkregtable mktables mktree +mkutf8data modpost modules.builtin modules.order @@ -254,6 +255,7 @@ vsyscall_32.lds wanxlfw.inc uImage unifdef +utf8data.h wakeup.bin wakeup.elf wakeup.lds diff --git a/fs/unicode/.gitignore b/fs/unicode/.gitignore new file mode 100644 index 000000000000..0381e2221480 --- /dev/null +++ b/fs/unicode/.gitignore @@ -0,0 +1,2 @@ +mkutf8data +utf8data.h diff --git a/fs/unicode/Makefile b/fs/unicode/Makefile index 671d31f83006..d46e9baee285 100644 --- a/fs/unicode/Makefile +++ b/fs/unicode/Makefile @@ -5,15 +5,34 @@ obj-$(CONFIG_UNICODE_NORMALIZATION_SELFTEST) += utf8-selftest.o unicode-y := utf8-norm.o utf8-core.o -# This rule is not invoked during the kernel compilation. It is used to -# regenerate the utf8data.h header file. -utf8data.h.new: *.txt $(objdir)/scripts/mkutf8data - $(objdir)/scripts/mkutf8data \ - -a DerivedAge.txt \ - -c DerivedCombiningClass.txt \ - -p DerivedCoreProperties.txt \ - -d UnicodeData.txt \ - -f CaseFolding.txt \ - -n NormalizationCorrections.txt \ - -t NormalizationTest.txt \ +$(obj)/utf8-norm.o: $(obj)/utf8data.h + +# In the normal build, the checked-in utf8data.h is just shipped. +# +# To generate utf8data.h from UCD, put *.txt files in this directory +# and pass REGENERATE_UTF8DATA=1 from the command line. +ifdef REGENERATE_UTF8DATA + +quiet_cmd_utf8data = GEN $@ + cmd_utf8data = $< \ + -a $(srctree)/$(src)/DerivedAge.txt \ + -c $(srctree)/$(src)/DerivedCombiningClass.txt \ + -p $(srctree)/$(src)/DerivedCoreProperties.txt \ + -d $(srctree)/$(src)/UnicodeData.txt \ + -f $(srctree)/$(src)/CaseFolding.txt \ + -n $(srctree)/$(src)/NormalizationCorrections.txt \ + -t $(srctree)/$(src)/NormalizationTest.txt \ -o $@ + +$(obj)/utf8data.h: $(obj)/mkutf8data $(filter %.txt, $(cmd_utf8data)) FORCE + $(call if_changed,utf8data) + +else + +$(obj)/utf8data.h: $(src)/utf8data.h_shipped FORCE + $(call if_changed,shipped) + +endif + +targets += utf8data.h +hostprogs-y += mkutf8data diff --git a/fs/unicode/README.utf8data b/fs/unicode/README.utf8data index dd56ef50c5d5..9307cf0727de 100644 --- a/fs/unicode/README.utf8data +++ b/fs/unicode/README.utf8data @@ -55,15 +55,14 @@ released version of the UCD can be found here: http://www.unicode.org/Public/UCD/latest/ -To build the utf8data.h file, from a kernel tree that has been built, -cd to this directory (fs/unicode) and run this command: +Then, build under fs/unicode/ with REGENERATE_UTF8DATA=1: - make C=../.. objdir=../.. utf8data.h.new + make REGENERATE_UTF8DATA=1 fs/unicode/ -After sanity checking the newly generated utf8data.h.new file (the +After sanity checking the newly generated utf8data.h file (the version generated from the 12.1.0 UCD should be 4,109 lines long, and have a total size of 324k) and/or comparing it with the older version -of utf8data.h, rename it to utf8data.h. +of utf8data.h_shipped, rename it to utf8data.h_shipped. If you are a kernel developer updating to a newer version of the Unicode Character Database, please update this README.utf8data file diff --git a/fs/unicode/mkutf8data.c b/fs/unicode/mkutf8data.c new file mode 100644 index 000000000000..ff2025ac5a32 --- /dev/null +++ b/fs/unicode/mkutf8data.c @@ -0,0 +1,3419 @@ +/* + * Copyright (c) 2014 SGI. + * All rights reserved. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it would be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + */ + +/* Generator for a compact trie for unicode normalization */ + +#include +#include +#include +#include +#include +#include +#include +#include + +/* Default names of the in- and output files. */ + +#define AGE_NAME "DerivedAge.txt" +#define CCC_NAME "DerivedCombiningClass.txt" +#define PROP_NAME "DerivedCoreProperties.txt" +#define DATA_NAME "UnicodeData.txt" +#define FOLD_NAME "CaseFolding.txt" +#define NORM_NAME "NormalizationCorrections.txt" +#define TEST_NAME "NormalizationTest.txt" +#define UTF8_NAME "utf8data.h" + +const char *age_name = AGE_NAME; +const char *ccc_name = CCC_NAME; +const char *prop_name = PROP_NAME; +const char *data_name = DATA_NAME; +const char *fold_name = FOLD_NAME; +const char *norm_name = NORM_NAME; +const char *test_name = TEST_NAME; +const char *utf8_name = UTF8_NAME; + +int verbose = 0; + +/* An arbitrary line size limit on input lines. */ + +#define LINESIZE 1024 +char line[LINESIZE]; +char buf0[LINESIZE]; +char buf1[LINESIZE]; +char buf2[LINESIZE]; +char buf3[LINESIZE]; + +const char *argv0; + +#define ARRAY_SIZE(x) (sizeof(x) / sizeof((x)[0])) + +/* ------------------------------------------------------------------ */ + +/* + * Unicode version numbers consist of three parts: major, minor, and a + * revision. These numbers are packed into an unsigned int to obtain + * a single version number. + * + * To save space in the generated trie, the unicode version is not + * stored directly, instead we calculate a generation number from the + * unicode versions seen in the DerivedAge file, and use that as an + * index into a table of unicode versions. + */ +#define UNICODE_MAJ_SHIFT (16) +#define UNICODE_MIN_SHIFT (8) + +#define UNICODE_MAJ_MAX ((unsigned short)-1) +#define UNICODE_MIN_MAX ((unsigned char)-1) +#define UNICODE_REV_MAX ((unsigned char)-1) + +#define UNICODE_AGE(MAJ,MIN,REV) \ + (((unsigned int)(MAJ) << UNICODE_MAJ_SHIFT) | \ + ((unsigned int)(MIN) << UNICODE_MIN_SHIFT) | \ + ((unsigned int)(REV))) + +unsigned int *ages; +int ages_count; + +unsigned int unicode_maxage; + +static int age_valid(unsigned int major, unsigned int minor, + unsigned int revision) +{ + if (major > UNICODE_MAJ_MAX) + return 0; + if (minor > UNICODE_MIN_MAX) + return 0; + if (revision > UNICODE_REV_MAX) + return 0; + return 1; +} + +/* ------------------------------------------------------------------ */ + +/* + * utf8trie_t + * + * A compact binary tree, used to decode UTF-8 characters. + * + * Internal nodes are one byte for the node itself, and up to three + * bytes for an offset into the tree. The first byte contains the + * following information: + * NEXTBYTE - flag - advance to next byte if set + * BITNUM - 3 bit field - the bit number to tested + * OFFLEN - 2 bit field - number of bytes in the offset + * if offlen == 0 (non-branching node) + * RIGHTPATH - 1 bit field - set if the following node is for the + * right-hand path (tested bit is set) + * TRIENODE - 1 bit field - set if the following node is an internal + * node, otherwise it is a leaf node + * if offlen != 0 (branching node) + * LEFTNODE - 1 bit field - set if the left-hand node is internal + * RIGHTNODE - 1 bit field - set if the right-hand node is internal + * + * Due to the way utf8 works, there cannot be branching nodes with + * NEXTBYTE set, and moreover those nodes always have a righthand + * descendant. + */ +typedef unsigned char utf8trie_t; +#define BITNUM 0x07 +#define NEXTBYTE 0x08 +#define OFFLEN 0x30 +#define OFFLEN_SHIFT 4 +#define RIGHTPATH 0x40 +#define TRIENODE 0x80 +#define RIGHTNODE 0x40 +#define LEFTNODE 0x80 + +/* + * utf8leaf_t + * + * The leaves of the trie are embedded in the trie, and so the same + * underlying datatype, unsigned char. + * + * leaf[0]: The unicode version, stored as a generation number that is + * an index into utf8agetab[]. With this we can filter code + * points based on the unicode version in which they were + * defined. The CCC of a non-defined code point is 0. + * leaf[1]: Canonical Combining Class. During normalization, we need + * to do a stable sort into ascending order of all characters + * with a non-zero CCC that occur between two characters with + * a CCC of 0, or at the begin or end of a string. + * The unicode standard guarantees that all CCC values are + * between 0 and 254 inclusive, which leaves 255 available as + * a special value. + * Code points with CCC 0 are known as stoppers. + * leaf[2]: Decomposition. If leaf[1] == 255, then leaf[2] is the + * start of a NUL-terminated string that is the decomposition + * of the character. + * The CCC of a decomposable character is the same as the CCC + * of the first character of its decomposition. + * Some characters decompose as the empty string: these are + * characters with the Default_Ignorable_Code_Point property. + * These do affect normalization, as they all have CCC 0. + * + * The decompositions in the trie have been fully expanded. + * + * Casefolding, if applicable, is also done using decompositions. + */ +typedef unsigned char utf8leaf_t; + +#define LEAF_GEN(LEAF) ((LEAF)[0]) +#define LEAF_CCC(LEAF) ((LEAF)[1]) +#define LEAF_STR(LEAF) ((const char*)((LEAF) + 2)) + +#define MAXGEN (255) + +#define MINCCC (0) +#define MAXCCC (254) +#define STOPPER (0) +#define DECOMPOSE (255) +#define HANGUL ((char)(255)) + +#define UTF8HANGULLEAF (12) + +struct tree; +static utf8leaf_t *utf8nlookup(struct tree *, unsigned char *, + const char *, size_t); +static utf8leaf_t *utf8lookup(struct tree *, unsigned char *, const char *); + +unsigned char *utf8data; +size_t utf8data_size; + +utf8trie_t *nfdi; +utf8trie_t *nfdicf; + +/* ------------------------------------------------------------------ */ + +/* + * UTF8 valid ranges. + * + * The UTF-8 encoding spreads the bits of a 32bit word over several + * bytes. This table gives the ranges that can be held and how they'd + * be represented. + * + * 0x00000000 0x0000007F: 0xxxxxxx + * 0x00000000 0x000007FF: 110xxxxx 10xxxxxx + * 0x00000000 0x0000FFFF: 1110xxxx 10xxxxxx 10xxxxxx + * 0x00000000 0x001FFFFF: 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx + * 0x00000000 0x03FFFFFF: 111110xx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx + * 0x00000000 0x7FFFFFFF: 1111110x 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx + * + * There is an additional requirement on UTF-8, in that only the + * shortest representation of a 32bit value is to be used. A decoder + * must not decode sequences that do not satisfy this requirement. + * Thus the allowed ranges have a lower bound. + * + * 0x00000000 0x0000007F: 0xxxxxxx + * 0x00000080 0x000007FF: 110xxxxx 10xxxxxx + * 0x00000800 0x0000FFFF: 1110xxxx 10xxxxxx 10xxxxxx + * 0x00010000 0x001FFFFF: 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx + * 0x00200000 0x03FFFFFF: 111110xx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx + * 0x04000000 0x7FFFFFFF: 1111110x 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx + * + * Actual unicode characters are limited to the range 0x0 - 0x10FFFF, + * 17 planes of 65536 values. This limits the sequences actually seen + * even more, to just the following. + * + * 0 - 0x7f: 0 0x7f + * 0x80 - 0x7ff: 0xc2 0x80 0xdf 0xbf + * 0x800 - 0xffff: 0xe0 0xa0 0x80 0xef 0xbf 0xbf + * 0x10000 - 0x10ffff: 0xf0 0x90 0x80 0x80 0xf4 0x8f 0xbf 0xbf + * + * Even within those ranges not all values are allowed: the surrogates + * 0xd800 - 0xdfff should never be seen. + * + * Note that the longest sequence seen with valid usage is 4 bytes, + * the same a single UTF-32 character. This makes the UTF-8 + * representation of Unicode strictly smaller than UTF-32. + * + * The shortest sequence requirement was introduced by: + * Corrigendum #1: UTF-8 Shortest Form + * It can be found here: + * http://www.unicode.org/versions/corrigendum1.html + * + */ + +#define UTF8_2_BITS 0xC0 +#define UTF8_3_BITS 0xE0 +#define UTF8_4_BITS 0xF0 +#define UTF8_N_BITS 0x80 +#define UTF8_2_MASK 0xE0 +#define UTF8_3_MASK 0xF0 +#define UTF8_4_MASK 0xF8 +#define UTF8_N_MASK 0xC0 +#define UTF8_V_MASK 0x3F +#define UTF8_V_SHIFT 6 + +static int utf8encode(char *str, unsigned int val) +{ + int len; + + if (val < 0x80) { + str[0] = val; + len = 1; + } else if (val < 0x800) { + str[1] = val & UTF8_V_MASK; + str[1] |= UTF8_N_BITS; + val >>= UTF8_V_SHIFT; + str[0] = val; + str[0] |= UTF8_2_BITS; + len = 2; + } else if (val < 0x10000) { + str[2] = val & UTF8_V_MASK; + str[2] |= UTF8_N_BITS; + val >>= UTF8_V_SHIFT; + str[1] = val & UTF8_V_MASK; + str[1] |= UTF8_N_BITS; + val >>= UTF8_V_SHIFT; + str[0] = val; + str[0] |= UTF8_3_BITS; + len = 3; + } else if (val < 0x110000) { + str[3] = val & UTF8_V_MASK; + str[3] |= UTF8_N_BITS; + val >>= UTF8_V_SHIFT; + str[2] = val & UTF8_V_MASK; + str[2] |= UTF8_N_BITS; + val >>= UTF8_V_SHIFT; + str[1] = val & UTF8_V_MASK; + str[1] |= UTF8_N_BITS; + val >>= UTF8_V_SHIFT; + str[0] = val; + str[0] |= UTF8_4_BITS; + len = 4; + } else { + printf("%#x: illegal val\n", val); + len = 0; + } + return len; +} + +static unsigned int utf8decode(const char *str) +{ + const unsigned char *s = (const unsigned char*)str; + unsigned int unichar = 0; + + if (*s < 0x80) { + unichar = *s; + } else if (*s < UTF8_3_BITS) { + unichar = *s++ & 0x1F; + unichar <<= UTF8_V_SHIFT; + unichar |= *s & 0x3F; + } else if (*s < UTF8_4_BITS) { + unichar = *s++ & 0x0F; + unichar <<= UTF8_V_SHIFT; + unichar |= *s++ & 0x3F; + unichar <<= UTF8_V_SHIFT; + unichar |= *s & 0x3F; + } else { + unichar = *s++ & 0x0F; + unichar <<= UTF8_V_SHIFT; + unichar |= *s++ & 0x3F; + unichar <<= UTF8_V_SHIFT; + unichar |= *s++ & 0x3F; + unichar <<= UTF8_V_SHIFT; + unichar |= *s & 0x3F; + } + return unichar; +} + +static int utf32valid(unsigned int unichar) +{ + return unichar < 0x110000; +} + +#define HANGUL_SYLLABLE(U) ((U) >= 0xAC00 && (U) <= 0xD7A3) + +#define NODE 1 +#define LEAF 0 + +struct tree { + void *root; + int childnode; + const char *type; + unsigned int maxage; + struct tree *next; + int (*leaf_equal)(void *, void *); + void (*leaf_print)(void *, int); + int (*leaf_mark)(void *); + int (*leaf_size)(void *); + int *(*leaf_index)(struct tree *, void *); + unsigned char *(*leaf_emit)(void *, unsigned char *); + int leafindex[0x110000]; + int index; +}; + +struct node { + int index; + int offset; + int mark; + int size; + struct node *parent; + void *left; + void *right; + unsigned char bitnum; + unsigned char nextbyte; + unsigned char leftnode; + unsigned char rightnode; + unsigned int keybits; + unsigned int keymask; +}; + +/* + * Example lookup function for a tree. + */ +static void *lookup(struct tree *tree, const char *key) +{ + struct node *node; + void *leaf = NULL; + + node = tree->root; + while (!leaf && node) { + if (node->nextbyte) + key++; + if (*key & (1 << (node->bitnum & 7))) { + /* Right leg */ + if (node->rightnode == NODE) { + node = node->right; + } else if (node->rightnode == LEAF) { + leaf = node->right; + } else { + node = NULL; + } + } else { + /* Left leg */ + if (node->leftnode == NODE) { + node = node->left; + } else if (node->leftnode == LEAF) { + leaf = node->left; + } else { + node = NULL; + } + } + } + + return leaf; +} + +/* + * A simple non-recursive tree walker: keep track of visits to the + * left and right branches in the leftmask and rightmask. + */ +static void tree_walk(struct tree *tree) +{ + struct node *node; + unsigned int leftmask; + unsigned int rightmask; + unsigned int bitmask; + int indent = 1; + int nodes, singletons, leaves; + + nodes = singletons = leaves = 0; + + printf("%s_%x root %p\n", tree->type, tree->maxage, tree->root); + if (tree->childnode == LEAF) { + assert(tree->root); + tree->leaf_print(tree->root, indent); + leaves = 1; + } else { + assert(tree->childnode == NODE); + node = tree->root; + leftmask = rightmask = 0; + while (node) { + printf("%*snode @ %p bitnum %d nextbyte %d" + " left %p right %p mask %x bits %x\n", + indent, "", node, + node->bitnum, node->nextbyte, + node->left, node->right, + node->keymask, node->keybits); + nodes += 1; + if (!(node->left && node->right)) + singletons += 1; + + while (node) { + bitmask = 1 << node->bitnum; + if ((leftmask & bitmask) == 0) { + leftmask |= bitmask; + if (node->leftnode == LEAF) { + assert(node->left); + tree->leaf_print(node->left, + indent+1); + leaves += 1; + } else if (node->left) { + assert(node->leftnode == NODE); + indent += 1; + node = node->left; + break; + } + } + if ((rightmask & bitmask) == 0) { + rightmask |= bitmask; + if (node->rightnode == LEAF) { + assert(node->right); + tree->leaf_print(node->right, + indent+1); + leaves += 1; + } else if (node->right) { + assert(node->rightnode == NODE); + indent += 1; + node = node->right; + break; + } + } + leftmask &= ~bitmask; + rightmask &= ~bitmask; + node = node->parent; + indent -= 1; + } + } + } + printf("nodes %d leaves %d singletons %d\n", + nodes, leaves, singletons); +} + +/* + * Allocate an initialize a new internal node. + */ +static struct node *alloc_node(struct node *parent) +{ + struct node *node; + int bitnum; + + node = malloc(sizeof(*node)); + node->left = node->right = NULL; + node->parent = parent; + node->leftnode = NODE; + node->rightnode = NODE; + node->keybits = 0; + node->keymask = 0; + node->mark = 0; + node->index = 0; + node->offset = -1; + node->size = 4; + + if (node->parent) { + bitnum = parent->bitnum; + if ((bitnum & 7) == 0) { + node->bitnum = bitnum + 7 + 8; + node->nextbyte = 1; + } else { + node->bitnum = bitnum - 1; + node->nextbyte = 0; + } + } else { + node->bitnum = 7; + node->nextbyte = 0; + } + + return node; +} + +/* + * Insert a new leaf into the tree, and collapse any subtrees that are + * fully populated and end in identical leaves. A nextbyte tagged + * internal node will not be removed to preserve the tree's integrity. + * Note that due to the structure of utf8, no nextbyte tagged node + * will be a candidate for removal. + */ +static int insert(struct tree *tree, char *key, int keylen, void *leaf) +{ + struct node *node; + struct node *parent; + void **cursor; + int keybits; + + assert(keylen >= 1 && keylen <= 4); + + node = NULL; + cursor = &tree->root; + keybits = 8 * keylen; + + /* Insert, creating path along the way. */ + while (keybits) { + if (!*cursor) + *cursor = alloc_node(node); + node = *cursor; + if (node->nextbyte) + key++; + if (*key & (1 << (node->bitnum & 7))) + cursor = &node->right; + else + cursor = &node->left; + keybits--; + } + *cursor = leaf; + + /* Merge subtrees if possible. */ + while (node) { + if (*key & (1 << (node->bitnum & 7))) + node->rightnode = LEAF; + else + node->leftnode = LEAF; + if (node->nextbyte) + break; + if (node->leftnode == NODE || node->rightnode == NODE) + break; + assert(node->left); + assert(node->right); + /* Compare */ + if (! tree->leaf_equal(node->left, node->right)) + break; + /* Keep left, drop right leaf. */ + leaf = node->left; + /* Check in parent */ + parent = node->parent; + if (!parent) { + /* root of tree! */ + tree->root = leaf; + tree->childnode = LEAF; + } else if (parent->left == node) { + parent->left = leaf; + parent->leftnode = LEAF; + if (parent->right) { + parent->keymask = 0; + parent->keybits = 0; + } else { + parent->keymask |= (1 << node->bitnum); + } + } else if (parent->right == node) { + parent->right = leaf; + parent->rightnode = LEAF; + if (parent->left) { + parent->keymask = 0; + parent->keybits = 0; + } else { + parent->keymask |= (1 << node->bitnum); + parent->keybits |= (1 << node->bitnum); + } + } else { + /* internal tree error */ + assert(0); + } + free(node); + node = parent; + } + + /* Propagate keymasks up along singleton chains. */ + while (node) { + parent = node->parent; + if (!parent) + break; + /* Nix the mask for parents with two children. */ + if (node->keymask == 0) { + parent->keymask = 0; + parent->keybits = 0; + } else if (parent->left && parent->right) { + parent->keymask = 0; + parent->keybits = 0; + } else { + assert((parent->keymask & node->keymask) == 0); + parent->keymask |= node->keymask; + parent->keymask |= (1 << parent->bitnum); + parent->keybits |= node->keybits; + if (parent->right) + parent->keybits |= (1 << parent->bitnum); + } + node = parent; + } + + return 0; +} + +/* + * Prune internal nodes. + * + * Fully populated subtrees that end at the same leaf have already + * been collapsed. There are still internal nodes that have for both + * their left and right branches a sequence of singletons that make + * identical choices and end in identical leaves. The keymask and + * keybits collected in the nodes describe the choices made in these + * singleton chains. When they are identical for the left and right + * branch of a node, and the two leaves comare identical, the node in + * question can be removed. + * + * Note that nodes with the nextbyte tag set will not be removed by + * this to ensure tree integrity. Note as well that the structure of + * utf8 ensures that these nodes would not have been candidates for + * removal in any case. + */ +static void prune(struct tree *tree) +{ + struct node *node; + struct node *left; + struct node *right; + struct node *parent; + void *leftleaf; + void *rightleaf; + unsigned int leftmask; + unsigned int rightmask; + unsigned int bitmask; + int count; + + if (verbose > 0) + printf("Pruning %s_%x\n", tree->type, tree->maxage); + + count = 0; + if (tree->childnode == LEAF) + return; + if (!tree->root) + return; + + leftmask = rightmask = 0; + node = tree->root; + while (node) { + if (node->nextbyte) + goto advance; + if (node->leftnode == LEAF) + goto advance; + if (node->rightnode == LEAF) + goto advance; + if (!node->left) + goto advance; + if (!node->right) + goto advance; + left = node->left; + right = node->right; + if (left->keymask == 0) + goto advance; + if (right->keymask == 0) + goto advance; + if (left->keymask != right->keymask) + goto advance; + if (left->keybits != right->keybits) + goto advance; + leftleaf = NULL; + while (!leftleaf) { + assert(left->left || left->right); + if (left->leftnode == LEAF) + leftleaf = left->left; + else if (left->rightnode == LEAF) + leftleaf = left->right; + else if (left->left) + left = left->left; + else if (left->right) + left = left->right; + else + assert(0); + } + rightleaf = NULL; + while (!rightleaf) { + assert(right->left || right->right); + if (right->leftnode == LEAF) + rightleaf = right->left; + else if (right->rightnode == LEAF) + rightleaf = right->right; + else if (right->left) + right = right->left; + else if (right->right) + right = right->right; + else + assert(0); + } + if (! tree->leaf_equal(leftleaf, rightleaf)) + goto advance; + /* + * This node has identical singleton-only subtrees. + * Remove it. + */ + parent = node->parent; + left = node->left; + right = node->right; + if (parent->left == node) + parent->left = left; + else if (parent->right == node) + parent->right = left; + else + assert(0); + left->parent = parent; + left->keymask |= (1 << node->bitnum); + node->left = NULL; + while (node) { + bitmask = 1 << node->bitnum; + leftmask &= ~bitmask; + rightmask &= ~bitmask; + if (node->leftnode == NODE && node->left) { + left = node->left; + free(node); + count++; + node = left; + } else if (node->rightnode == NODE && node->right) { + right = node->right; + free(node); + count++; + node = right; + } else { + node = NULL; + } + } + /* Propagate keymasks up along singleton chains. */ + node = parent; + /* Force re-check */ + bitmask = 1 << node->bitnum; + leftmask &= ~bitmask; + rightmask &= ~bitmask; + for (;;) { + if (node->left && node->right) + break; + if (node->left) { + left = node->left; + node->keymask |= left->keymask; + node->keybits |= left->keybits; + } + if (node->right) { + right = node->right; + node->keymask |= right->keymask; + node->keybits |= right->keybits; + } + node->keymask |= (1 << node->bitnum); + node = node->parent; + /* Force re-check */ + bitmask = 1 << node->bitnum; + leftmask &= ~bitmask; + rightmask &= ~bitmask; + } + advance: + bitmask = 1 << node->bitnum; + if ((leftmask & bitmask) == 0 && + node->leftnode == NODE && + node->left) { + leftmask |= bitmask; + node = node->left; + } else if ((rightmask & bitmask) == 0 && + node->rightnode == NODE && + node->right) { + rightmask |= bitmask; + node = node->right; + } else { + leftmask &= ~bitmask; + rightmask &= ~bitmask; + node = node->parent; + } + } + if (verbose > 0) + printf("Pruned %d nodes\n", count); +} + +/* + * Mark the nodes in the tree that lead to leaves that must be + * emitted. + */ +static void mark_nodes(struct tree *tree) +{ + struct node *node; + struct node *n; + unsigned int leftmask; + unsigned int rightmask; + unsigned int bitmask; + int marked; + + marked = 0; + if (verbose > 0) + printf("Marking %s_%x\n", tree->type, tree->maxage); + if (tree->childnode == LEAF) + goto done; + + assert(tree->childnode == NODE); + node = tree->root; + leftmask = rightmask = 0; + while (node) { + bitmask = 1 << node->bitnum; + if ((leftmask & bitmask) == 0) { + leftmask |= bitmask; + if (node->leftnode == LEAF) { + assert(node->left); + if (tree->leaf_mark(node->left)) { + n = node; + while (n && !n->mark) { + marked++; + n->mark = 1; + n = n->parent; + } + } + } else if (node->left) { + assert(node->leftnode == NODE); + node = node->left; + continue; + } + } + if ((rightmask & bitmask) == 0) { + rightmask |= bitmask; + if (node->rightnode == LEAF) { + assert(node->right); + if (tree->leaf_mark(node->right)) { + n = node; + while (n && !n->mark) { + marked++; + n->mark = 1; + n = n->parent; + } + } + } else if (node->right) { + assert(node->rightnode == NODE); + node = node->right; + continue; + } + } + leftmask &= ~bitmask; + rightmask &= ~bitmask; + node = node->parent; + } + + /* second pass: left siblings and singletons */ + + assert(tree->childnode == NODE); + node = tree->root; + leftmask = rightmask = 0; + while (node) { + bitmask = 1 << node->bitnum; + if ((leftmask & bitmask) == 0) { + leftmask |= bitmask; + if (node->leftnode == LEAF) { + assert(node->left); + if (tree->leaf_mark(node->left)) { + n = node; + while (n && !n->mark) { + marked++; + n->mark = 1; + n = n->parent; + } + } + } else if (node->left) { + assert(node->leftnode == NODE); + node = node->left; + if (!node->mark && node->parent->mark) { + marked++; + node->mark = 1; + } + continue; + } + } + if ((rightmask & bitmask) == 0) { + rightmask |= bitmask; + if (node->rightnode == LEAF) { + assert(node->right); + if (tree->leaf_mark(node->right)) { + n = node; + while (n && !n->mark) { + marked++; + n->mark = 1; + n = n->parent; + } + } + } else if (node->right) { + assert(node->rightnode == NODE); + node = node->right; + if (!node->mark && node->parent->mark && + !node->parent->left) { + marked++; + node->mark = 1; + } + continue; + } + } + leftmask &= ~bitmask; + rightmask &= ~bitmask; + node = node->parent; + } +done: + if (verbose > 0) + printf("Marked %d nodes\n", marked); +} + +/* + * Compute the index of each node and leaf, which is the offset in the + * emitted trie. These values must be pre-computed because relative + * offsets between nodes are used to navigate the tree. + */ +static int index_nodes(struct tree *tree, int index) +{ + struct node *node; + unsigned int leftmask; + unsigned int rightmask; + unsigned int bitmask; + int count; + int indent; + + /* Align to a cache line (or half a cache line?). */ + while (index % 64) + index++; + tree->index = index; + indent = 1; + count = 0; + + if (verbose > 0) + printf("Indexing %s_%x: %d\n", tree->type, tree->maxage, index); + if (tree->childnode == LEAF) { + index += tree->leaf_size(tree->root); + goto done; + } + + assert(tree->childnode == NODE); + node = tree->root; + leftmask = rightmask = 0; + while (node) { + if (!node->mark) + goto skip; + count++; + if (node->index != index) + node->index = index; + index += node->size; +skip: + while (node) { + bitmask = 1 << node->bitnum; + if (node->mark && (leftmask & bitmask) == 0) { + leftmask |= bitmask; + if (node->leftnode == LEAF) { + assert(node->left); + *tree->leaf_index(tree, node->left) = + index; + index += tree->leaf_size(node->left); + count++; + } else if (node->left) { + assert(node->leftnode == NODE); + indent += 1; + node = node->left; + break; + } + } + if (node->mark && (rightmask & bitmask) == 0) { + rightmask |= bitmask; + if (node->rightnode == LEAF) { + assert(node->right); + *tree->leaf_index(tree, node->right) = index; + index += tree->leaf_size(node->right); + count++; + } else if (node->right) { + assert(node->rightnode == NODE); + indent += 1; + node = node->right; + break; + } + } + leftmask &= ~bitmask; + rightmask &= ~bitmask; + node = node->parent; + indent -= 1; + } + } +done: + /* Round up to a multiple of 16 */ + while (index % 16) + index++; + if (verbose > 0) + printf("Final index %d\n", index); + return index; +} + +/* + * Mark the nodes in a subtree, helper for size_nodes(). + */ +static int mark_subtree(struct node *node) +{ + int changed; + + if (!node || node->mark) + return 0; + node->mark = 1; + node->index = node->parent->index; + changed = 1; + if (node->leftnode == NODE) + changed += mark_subtree(node->left); + if (node->rightnode == NODE) + changed += mark_subtree(node->right); + return changed; +} + +/* + * Compute the size of nodes and leaves. We start by assuming that + * each node needs to store a three-byte offset. The indexes of the + * nodes are calculated based on that, and then this function is + * called to see if the sizes of some nodes can be reduced. This is + * repeated until no more changes are seen. + */ +static int size_nodes(struct tree *tree) +{ + struct tree *next; + struct node *node; + struct node *right; + struct node *n; + unsigned int leftmask; + unsigned int rightmask; + unsigned int bitmask; + unsigned int pathbits; + unsigned int pathmask; + unsigned int nbit; + int changed; + int offset; + int size; + int indent; + + indent = 1; + changed = 0; + size = 0; + + if (verbose > 0) + printf("Sizing %s_%x\n", tree->type, tree->maxage); + if (tree->childnode == LEAF) + goto done; + + assert(tree->childnode == NODE); + pathbits = 0; + pathmask = 0; + node = tree->root; + leftmask = rightmask = 0; + while (node) { + if (!node->mark) + goto skip; + offset = 0; + if (!node->left || !node->right) { + size = 1; + } else { + if (node->rightnode == NODE) { + /* + * If the right node is not marked, + * look for a corresponding node in + * the next tree. Such a node need + * not exist. + */ + right = node->right; + next = tree->next; + while (!right->mark) { + assert(next); + n = next->root; + while (n->bitnum != node->bitnum) { + nbit = 1 << n->bitnum; + if (!(pathmask & nbit)) + break; + if (pathbits & nbit) { + if (n->rightnode == LEAF) + break; + n = n->right; + } else { + if (n->leftnode == LEAF) + break; + n = n->left; + } + } + if (n->bitnum != node->bitnum) + break; + n = n->right; + right = n; + next = next->next; + } + /* Make sure the right node is marked. */ + if (!right->mark) + changed += mark_subtree(right); + offset = right->index - node->index; + } else { + offset = *tree->leaf_index(tree, node->right); + offset -= node->index; + } + assert(offset >= 0); + assert(offset <= 0xffffff); + if (offset <= 0xff) { + size = 2; + } else if (offset <= 0xffff) { + size = 3; + } else { /* offset <= 0xffffff */ + size = 4; + } + } + if (node->size != size || node->offset != offset) { + node->size = size; + node->offset = offset; + changed++; + } +skip: + while (node) { + bitmask = 1 << node->bitnum; + pathmask |= bitmask; + if (node->mark && (leftmask & bitmask) == 0) { + leftmask |= bitmask; + if (node->leftnode == LEAF) { + assert(node->left); + } else if (node->left) { + assert(node->leftnode == NODE); + indent += 1; + node = node->left; + break; + } + } + if (node->mark && (rightmask & bitmask) == 0) { + rightmask |= bitmask; + pathbits |= bitmask; + if (node->rightnode == LEAF) { + assert(node->right); + } else if (node->right) { + assert(node->rightnode == NODE); + indent += 1; + node = node->right; + break; + } + } + leftmask &= ~bitmask; + rightmask &= ~bitmask; + pathmask &= ~bitmask; + pathbits &= ~bitmask; + node = node->parent; + indent -= 1; + } + } +done: + if (verbose > 0) + printf("Found %d changes\n", changed); + return changed; +} + +/* + * Emit a trie for the given tree into the data array. + */ +static void emit(struct tree *tree, unsigned char *data) +{ + struct node *node; + unsigned int leftmask; + unsigned int rightmask; + unsigned int bitmask; + int offlen; + int offset; + int index; + int indent; + int size; + int bytes; + int leaves; + int nodes[4]; + unsigned char byte; + + nodes[0] = nodes[1] = nodes[2] = nodes[3] = 0; + leaves = 0; + bytes = 0; + index = tree->index; + data += index; + indent = 1; + if (verbose > 0) + printf("Emitting %s_%x\n", tree->type, tree->maxage); + if (tree->childnode == LEAF) { + assert(tree->root); + tree->leaf_emit(tree->root, data); + size = tree->leaf_size(tree->root); + index += size; + leaves++; + goto done; + } + + assert(tree->childnode == NODE); + node = tree->root; + leftmask = rightmask = 0; + while (node) { + if (!node->mark) + goto skip; + assert(node->offset != -1); + assert(node->index == index); + + byte = 0; + if (node->nextbyte) + byte |= NEXTBYTE; + byte |= (node->bitnum & BITNUM); + if (node->left && node->right) { + if (node->leftnode == NODE) + byte |= LEFTNODE; + if (node->rightnode == NODE) + byte |= RIGHTNODE; + if (node->offset <= 0xff) + offlen = 1; + else if (node->offset <= 0xffff) + offlen = 2; + else + offlen = 3; + nodes[offlen]++; + offset = node->offset; + byte |= offlen << OFFLEN_SHIFT; + *data++ = byte; + index++; + while (offlen--) { + *data++ = offset & 0xff; + index++; + offset >>= 8; + } + } else if (node->left) { + if (node->leftnode == NODE) + byte |= TRIENODE; + nodes[0]++; + *data++ = byte; + index++; + } else if (node->right) { + byte |= RIGHTNODE; + if (node->rightnode == NODE) + byte |= TRIENODE; + nodes[0]++; + *data++ = byte; + index++; + } else { + assert(0); + } +skip: + while (node) { + bitmask = 1 << node->bitnum; + if (node->mark && (leftmask & bitmask) == 0) { + leftmask |= bitmask; + if (node->leftnode == LEAF) { + assert(node->left); + data = tree->leaf_emit(node->left, + data); + size = tree->leaf_size(node->left); + index += size; + bytes += size; + leaves++; + } else if (node->left) { + assert(node->leftnode == NODE); + indent += 1; + node = node->left; + break; + } + } + if (node->mark && (rightmask & bitmask) == 0) { + rightmask |= bitmask; + if (node->rightnode == LEAF) { + assert(node->right); + data = tree->leaf_emit(node->right, + data); + size = tree->leaf_size(node->right); + index += size; + bytes += size; + leaves++; + } else if (node->right) { + assert(node->rightnode == NODE); + indent += 1; + node = node->right; + break; + } + } + leftmask &= ~bitmask; + rightmask &= ~bitmask; + node = node->parent; + indent -= 1; + } + } +done: + if (verbose > 0) { + printf("Emitted %d (%d) leaves", + leaves, bytes); + printf(" %d (%d+%d+%d+%d) nodes", + nodes[0] + nodes[1] + nodes[2] + nodes[3], + nodes[0], nodes[1], nodes[2], nodes[3]); + printf(" %d total\n", index - tree->index); + } +} + +/* ------------------------------------------------------------------ */ + +/* + * Unicode data. + * + * We need to keep track of the Canonical Combining Class, the Age, + * and decompositions for a code point. + * + * For the Age, we store the index into the ages table. Effectively + * this is a generation number that the table maps to a unicode + * version. + * + * The correction field is used to indicate that this entry is in the + * corrections array, which contains decompositions that were + * corrected in later revisions. The value of the correction field is + * the Unicode version in which the mapping was corrected. + */ +struct unicode_data { + unsigned int code; + int ccc; + int gen; + int correction; + unsigned int *utf32nfdi; + unsigned int *utf32nfdicf; + char *utf8nfdi; + char *utf8nfdicf; +}; + +struct unicode_data unicode_data[0x110000]; +struct unicode_data *corrections; +int corrections_count; + +struct tree *nfdi_tree; +struct tree *nfdicf_tree; + +struct tree *trees; +int trees_count; + +/* + * Check the corrections array to see if this entry was corrected at + * some point. + */ +static struct unicode_data *corrections_lookup(struct unicode_data *u) +{ + int i; + + for (i = 0; i != corrections_count; i++) + if (u->code == corrections[i].code) + return &corrections[i]; + return u; +} + +static int nfdi_equal(void *l, void *r) +{ + struct unicode_data *left = l; + struct unicode_data *right = r; + + if (left->gen != right->gen) + return 0; + if (left->ccc != right->ccc) + return 0; + if (left->utf8nfdi && right->utf8nfdi && + strcmp(left->utf8nfdi, right->utf8nfdi) == 0) + return 1; + if (left->utf8nfdi || right->utf8nfdi) + return 0; + return 1; +} + +static int nfdicf_equal(void *l, void *r) +{ + struct unicode_data *left = l; + struct unicode_data *right = r; + + if (left->gen != right->gen) + return 0; + if (left->ccc != right->ccc) + return 0; + if (left->utf8nfdicf && right->utf8nfdicf && + strcmp(left->utf8nfdicf, right->utf8nfdicf) == 0) + return 1; + if (left->utf8nfdicf && right->utf8nfdicf) + return 0; + if (left->utf8nfdicf || right->utf8nfdicf) + return 0; + if (left->utf8nfdi && right->utf8nfdi && + strcmp(left->utf8nfdi, right->utf8nfdi) == 0) + return 1; + if (left->utf8nfdi || right->utf8nfdi) + return 0; + return 1; +} + +static void nfdi_print(void *l, int indent) +{ + struct unicode_data *leaf = l; + + printf("%*sleaf @ %p code %X ccc %d gen %d", indent, "", leaf, + leaf->code, leaf->ccc, leaf->gen); + + if (leaf->utf8nfdi && leaf->utf8nfdi[0] == HANGUL) + printf(" nfdi \"%s\"", "HANGUL SYLLABLE"); + else if (leaf->utf8nfdi) + printf(" nfdi \"%s\"", (const char*)leaf->utf8nfdi); + + printf("\n"); +} + +static void nfdicf_print(void *l, int indent) +{ + struct unicode_data *leaf = l; + + printf("%*sleaf @ %p code %X ccc %d gen %d", indent, "", leaf, + leaf->code, leaf->ccc, leaf->gen); + + if (leaf->utf8nfdicf) + printf(" nfdicf \"%s\"", (const char*)leaf->utf8nfdicf); + else if (leaf->utf8nfdi && leaf->utf8nfdi[0] == HANGUL) + printf(" nfdi \"%s\"", "HANGUL SYLLABLE"); + else if (leaf->utf8nfdi) + printf(" nfdi \"%s\"", (const char*)leaf->utf8nfdi); + printf("\n"); +} + +static int nfdi_mark(void *l) +{ + return 1; +} + +static int nfdicf_mark(void *l) +{ + struct unicode_data *leaf = l; + + if (leaf->utf8nfdicf) + return 1; + return 0; +} + +static int correction_mark(void *l) +{ + struct unicode_data *leaf = l; + + return leaf->correction; +} + +static int nfdi_size(void *l) +{ + struct unicode_data *leaf = l; + int size = 2; + + if (HANGUL_SYLLABLE(leaf->code)) + size += 1; + else if (leaf->utf8nfdi) + size += strlen(leaf->utf8nfdi) + 1; + return size; +} + +static int nfdicf_size(void *l) +{ + struct unicode_data *leaf = l; + int size = 2; + + if (HANGUL_SYLLABLE(leaf->code)) + size += 1; + else if (leaf->utf8nfdicf) + size += strlen(leaf->utf8nfdicf) + 1; + else if (leaf->utf8nfdi) + size += strlen(leaf->utf8nfdi) + 1; + return size; +} + +static int *nfdi_index(struct tree *tree, void *l) +{ + struct unicode_data *leaf = l; + + return &tree->leafindex[leaf->code]; +} + +static int *nfdicf_index(struct tree *tree, void *l) +{ + struct unicode_data *leaf = l; + + return &tree->leafindex[leaf->code]; +} + +static unsigned char *nfdi_emit(void *l, unsigned char *data) +{ + struct unicode_data *leaf = l; + unsigned char *s; + + *data++ = leaf->gen; + + if (HANGUL_SYLLABLE(leaf->code)) { + *data++ = DECOMPOSE; + *data++ = HANGUL; + } else if (leaf->utf8nfdi) { + *data++ = DECOMPOSE; + s = (unsigned char*)leaf->utf8nfdi; + while ((*data++ = *s++) != 0) + ; + } else { + *data++ = leaf->ccc; + } + return data; +} + +static unsigned char *nfdicf_emit(void *l, unsigned char *data) +{ + struct unicode_data *leaf = l; + unsigned char *s; + + *data++ = leaf->gen; + + if (HANGUL_SYLLABLE(leaf->code)) { + *data++ = DECOMPOSE; + *data++ = HANGUL; + } else if (leaf->utf8nfdicf) { + *data++ = DECOMPOSE; + s = (unsigned char*)leaf->utf8nfdicf; + while ((*data++ = *s++) != 0) + ; + } else if (leaf->utf8nfdi) { + *data++ = DECOMPOSE; + s = (unsigned char*)leaf->utf8nfdi; + while ((*data++ = *s++) != 0) + ; + } else { + *data++ = leaf->ccc; + } + return data; +} + +static void utf8_create(struct unicode_data *data) +{ + char utf[18*4+1]; + char *u; + unsigned int *um; + int i; + + if (data->utf8nfdi) { + assert(data->utf8nfdi[0] == HANGUL); + return; + } + + u = utf; + um = data->utf32nfdi; + if (um) { + for (i = 0; um[i]; i++) + u += utf8encode(u, um[i]); + *u = '\0'; + data->utf8nfdi = strdup(utf); + } + u = utf; + um = data->utf32nfdicf; + if (um) { + for (i = 0; um[i]; i++) + u += utf8encode(u, um[i]); + *u = '\0'; + if (!data->utf8nfdi || strcmp(data->utf8nfdi, utf)) + data->utf8nfdicf = strdup(utf); + } +} + +static void utf8_init(void) +{ + unsigned int unichar; + int i; + + for (unichar = 0; unichar != 0x110000; unichar++) + utf8_create(&unicode_data[unichar]); + + for (i = 0; i != corrections_count; i++) + utf8_create(&corrections[i]); +} + +static void trees_init(void) +{ + struct unicode_data *data; + unsigned int maxage; + unsigned int nextage; + int count; + int i; + int j; + + /* Count the number of different ages. */ + count = 0; + nextage = (unsigned int)-1; + do { + maxage = nextage; + nextage = 0; + for (i = 0; i <= corrections_count; i++) { + data = &corrections[i]; + if (nextage < data->correction && + data->correction < maxage) + nextage = data->correction; + } + count++; + } while (nextage); + + /* Two trees per age: nfdi and nfdicf */ + trees_count = count * 2; + trees = calloc(trees_count, sizeof(struct tree)); + + /* Assign ages to the trees. */ + count = trees_count; + nextage = (unsigned int)-1; + do { + maxage = nextage; + trees[--count].maxage = maxage; + trees[--count].maxage = maxage; + nextage = 0; + for (i = 0; i <= corrections_count; i++) { + data = &corrections[i]; + if (nextage < data->correction && + data->correction < maxage) + nextage = data->correction; + } + } while (nextage); + + /* The ages assigned above are off by one. */ + for (i = 0; i != trees_count; i++) { + j = 0; + while (ages[j] < trees[i].maxage) + j++; + trees[i].maxage = ages[j-1]; + } + + /* Set up the forwarding between trees. */ + trees[trees_count-2].next = &trees[trees_count-1]; + trees[trees_count-1].leaf_mark = nfdi_mark; + trees[trees_count-2].leaf_mark = nfdicf_mark; + for (i = 0; i != trees_count-2; i += 2) { + trees[i].next = &trees[trees_count-2]; + trees[i].leaf_mark = correction_mark; + trees[i+1].next = &trees[trees_count-1]; + trees[i+1].leaf_mark = correction_mark; + } + + /* Assign the callouts. */ + for (i = 0; i != trees_count; i += 2) { + trees[i].type = "nfdicf"; + trees[i].leaf_equal = nfdicf_equal; + trees[i].leaf_print = nfdicf_print; + trees[i].leaf_size = nfdicf_size; + trees[i].leaf_index = nfdicf_index; + trees[i].leaf_emit = nfdicf_emit; + + trees[i+1].type = "nfdi"; + trees[i+1].leaf_equal = nfdi_equal; + trees[i+1].leaf_print = nfdi_print; + trees[i+1].leaf_size = nfdi_size; + trees[i+1].leaf_index = nfdi_index; + trees[i+1].leaf_emit = nfdi_emit; + } + + /* Finish init. */ + for (i = 0; i != trees_count; i++) + trees[i].childnode = NODE; +} + +static void trees_populate(void) +{ + struct unicode_data *data; + unsigned int unichar; + char keyval[4]; + int keylen; + int i; + + for (i = 0; i != trees_count; i++) { + if (verbose > 0) { + printf("Populating %s_%x\n", + trees[i].type, trees[i].maxage); + } + for (unichar = 0; unichar != 0x110000; unichar++) { + if (unicode_data[unichar].gen < 0) + continue; + keylen = utf8encode(keyval, unichar); + data = corrections_lookup(&unicode_data[unichar]); + if (data->correction <= trees[i].maxage) + data = &unicode_data[unichar]; + insert(&trees[i], keyval, keylen, data); + } + } +} + +static void trees_reduce(void) +{ + int i; + int size; + int changed; + + for (i = 0; i != trees_count; i++) + prune(&trees[i]); + for (i = 0; i != trees_count; i++) + mark_nodes(&trees[i]); + do { + size = 0; + for (i = 0; i != trees_count; i++) + size = index_nodes(&trees[i], size); + changed = 0; + for (i = 0; i != trees_count; i++) + changed += size_nodes(&trees[i]); + } while (changed); + + utf8data = calloc(size, 1); + utf8data_size = size; + for (i = 0; i != trees_count; i++) + emit(&trees[i], utf8data); + + if (verbose > 0) { + for (i = 0; i != trees_count; i++) { + printf("%s_%x idx %d\n", + trees[i].type, trees[i].maxage, trees[i].index); + } + } + + nfdi = utf8data + trees[trees_count-1].index; + nfdicf = utf8data + trees[trees_count-2].index; + + nfdi_tree = &trees[trees_count-1]; + nfdicf_tree = &trees[trees_count-2]; +} + +static void verify(struct tree *tree) +{ + struct unicode_data *data; + utf8leaf_t *leaf; + unsigned int unichar; + char key[4]; + unsigned char hangul[UTF8HANGULLEAF]; + int report; + int nocf; + + if (verbose > 0) + printf("Verifying %s_%x\n", tree->type, tree->maxage); + nocf = strcmp(tree->type, "nfdicf"); + + for (unichar = 0; unichar != 0x110000; unichar++) { + report = 0; + data = corrections_lookup(&unicode_data[unichar]); + if (data->correction <= tree->maxage) + data = &unicode_data[unichar]; + utf8encode(key,unichar); + leaf = utf8lookup(tree, hangul, key); + + if (!leaf) { + if (data->gen != -1) + report++; + if (unichar < 0xd800 || unichar > 0xdfff) + report++; + } else { + if (unichar >= 0xd800 && unichar <= 0xdfff) + report++; + if (data->gen == -1) + report++; + if (data->gen != LEAF_GEN(leaf)) + report++; + if (LEAF_CCC(leaf) == DECOMPOSE) { + if (HANGUL_SYLLABLE(data->code)) { + if (data->utf8nfdi[0] != HANGUL) + report++; + } else if (nocf) { + if (!data->utf8nfdi) { + report++; + } else if (strcmp(data->utf8nfdi, + LEAF_STR(leaf))) { + report++; + } + } else { + if (!data->utf8nfdicf && + !data->utf8nfdi) { + report++; + } else if (data->utf8nfdicf) { + if (strcmp(data->utf8nfdicf, + LEAF_STR(leaf))) + report++; + } else if (strcmp(data->utf8nfdi, + LEAF_STR(leaf))) { + report++; + } + } + } else if (data->ccc != LEAF_CCC(leaf)) { + report++; + } + } + if (report) { + printf("%X code %X gen %d ccc %d" + " nfdi -> \"%s\"", + unichar, data->code, data->gen, + data->ccc, + data->utf8nfdi); + if (leaf) { + printf(" gen %d ccc %d" + " nfdi -> \"%s\"", + LEAF_GEN(leaf), + LEAF_CCC(leaf), + LEAF_CCC(leaf) == DECOMPOSE ? + LEAF_STR(leaf) : ""); + } + printf("\n"); + } + } +} + +static void trees_verify(void) +{ + int i; + + for (i = 0; i != trees_count; i++) + verify(&trees[i]); +} + +/* ------------------------------------------------------------------ */ + +static void help(void) +{ + printf("Usage: %s [options]\n", argv0); + printf("\n"); + printf("This program creates an a data trie used for parsing and\n"); + printf("normalization of UTF-8 strings. The trie is derived from\n"); + printf("a set of input files from the Unicode character database\n"); + printf("found at: http://www.unicode.org/Public/UCD/latest/ucd/\n"); + printf("\n"); + printf("The generated tree supports two normalization forms:\n"); + printf("\n"); + printf("\tnfdi:\n"); + printf("\t- Apply unicode normalization form NFD.\n"); + printf("\t- Remove any Default_Ignorable_Code_Point.\n"); + printf("\n"); + printf("\tnfdicf:\n"); + printf("\t- Apply unicode normalization form NFD.\n"); + printf("\t- Remove any Default_Ignorable_Code_Point.\n"); + printf("\t- Apply a full casefold (C + F).\n"); + printf("\n"); + printf("These forms were chosen as being most useful when dealing\n"); + printf("with file names: NFD catches most cases where characters\n"); + printf("should be considered equivalent. The ignorables are mostly\n"); + printf("invisible, making names hard to type.\n"); + printf("\n"); + printf("The options to specify the files to be used are listed\n"); + printf("below with their default values, which are the names used\n"); + printf("by version 11.0.0 of the Unicode Character Database.\n"); + printf("\n"); + printf("The input files:\n"); + printf("\t-a %s\n", AGE_NAME); + printf("\t-c %s\n", CCC_NAME); + printf("\t-p %s\n", PROP_NAME); + printf("\t-d %s\n", DATA_NAME); + printf("\t-f %s\n", FOLD_NAME); + printf("\t-n %s\n", NORM_NAME); + printf("\n"); + printf("Additionally, the generated tables are tested using:\n"); + printf("\t-t %s\n", TEST_NAME); + printf("\n"); + printf("Finally, the output file:\n"); + printf("\t-o %s\n", UTF8_NAME); + printf("\n"); +} + +static void usage(void) +{ + help(); + exit(1); +} + +static void open_fail(const char *name, int error) +{ + printf("Error %d opening %s: %s\n", error, name, strerror(error)); + exit(1); +} + +static void file_fail(const char *filename) +{ + printf("Error parsing %s\n", filename); + exit(1); +} + +static void line_fail(const char *filename, const char *line) +{ + printf("Error parsing %s:%s\n", filename, line); + exit(1); +} + +/* ------------------------------------------------------------------ */ + +static void print_utf32(unsigned int *utf32str) +{ + int i; + + for (i = 0; utf32str[i]; i++) + printf(" %X", utf32str[i]); +} + +static void print_utf32nfdi(unsigned int unichar) +{ + printf(" %X ->", unichar); + print_utf32(unicode_data[unichar].utf32nfdi); + printf("\n"); +} + +static void print_utf32nfdicf(unsigned int unichar) +{ + printf(" %X ->", unichar); + print_utf32(unicode_data[unichar].utf32nfdicf); + printf("\n"); +} + +/* ------------------------------------------------------------------ */ + +static void age_init(void) +{ + FILE *file; + unsigned int first; + unsigned int last; + unsigned int unichar; + unsigned int major; + unsigned int minor; + unsigned int revision; + int gen; + int count; + int ret; + + if (verbose > 0) + printf("Parsing %s\n", age_name); + + file = fopen(age_name, "r"); + if (!file) + open_fail(age_name, errno); + count = 0; + + gen = 0; + while (fgets(line, LINESIZE, file)) { + ret = sscanf(line, "# Age=V%d_%d_%d", + &major, &minor, &revision); + if (ret == 3) { + ages_count++; + if (verbose > 1) + printf(" Age V%d_%d_%d\n", + major, minor, revision); + if (!age_valid(major, minor, revision)) + line_fail(age_name, line); + continue; + } + ret = sscanf(line, "# Age=V%d_%d", &major, &minor); + if (ret == 2) { + ages_count++; + if (verbose > 1) + printf(" Age V%d_%d\n", major, minor); + if (!age_valid(major, minor, 0)) + line_fail(age_name, line); + continue; + } + } + + /* We must have found something above. */ + if (verbose > 1) + printf("%d age entries\n", ages_count); + if (ages_count == 0 || ages_count > MAXGEN) + file_fail(age_name); + + /* There is a 0 entry. */ + ages_count++; + ages = calloc(ages_count + 1, sizeof(*ages)); + /* And a guard entry. */ + ages[ages_count] = (unsigned int)-1; + + rewind(file); + count = 0; + gen = 0; + while (fgets(line, LINESIZE, file)) { + ret = sscanf(line, "# Age=V%d_%d_%d", + &major, &minor, &revision); + if (ret == 3) { + ages[++gen] = + UNICODE_AGE(major, minor, revision); + if (verbose > 1) + printf(" Age V%d_%d_%d = gen %d\n", + major, minor, revision, gen); + if (!age_valid(major, minor, revision)) + line_fail(age_name, line); + continue; + } + ret = sscanf(line, "# Age=V%d_%d", &major, &minor); + if (ret == 2) { + ages[++gen] = UNICODE_AGE(major, minor, 0); + if (verbose > 1) + printf(" Age V%d_%d = %d\n", + major, minor, gen); + if (!age_valid(major, minor, 0)) + line_fail(age_name, line); + continue; + } + ret = sscanf(line, "%X..%X ; %d.%d #", + &first, &last, &major, &minor); + if (ret == 4) { + for (unichar = first; unichar <= last; unichar++) + unicode_data[unichar].gen = gen; + count += 1 + last - first; + if (verbose > 1) + printf(" %X..%X gen %d\n", first, last, gen); + if (!utf32valid(first) || !utf32valid(last)) + line_fail(age_name, line); + continue; + } + ret = sscanf(line, "%X ; %d.%d #", &unichar, &major, &minor); + if (ret == 3) { + unicode_data[unichar].gen = gen; + count++; + if (verbose > 1) + printf(" %X gen %d\n", unichar, gen); + if (!utf32valid(unichar)) + line_fail(age_name, line); + continue; + } + } + unicode_maxage = ages[gen]; + fclose(file); + + /* Nix surrogate block */ + if (verbose > 1) + printf(" Removing surrogate block D800..DFFF\n"); + for (unichar = 0xd800; unichar <= 0xdfff; unichar++) + unicode_data[unichar].gen = -1; + + if (verbose > 0) + printf("Found %d entries\n", count); + if (count == 0) + file_fail(age_name); +} + +static void ccc_init(void) +{ + FILE *file; + unsigned int first; + unsigned int last; + unsigned int unichar; + unsigned int value; + int count; + int ret; + + if (verbose > 0) + printf("Parsing %s\n", ccc_name); + + file = fopen(ccc_name, "r"); + if (!file) + open_fail(ccc_name, errno); + + count = 0; + while (fgets(line, LINESIZE, file)) { + ret = sscanf(line, "%X..%X ; %d #", &first, &last, &value); + if (ret == 3) { + for (unichar = first; unichar <= last; unichar++) { + unicode_data[unichar].ccc = value; + count++; + } + if (verbose > 1) + printf(" %X..%X ccc %d\n", first, last, value); + if (!utf32valid(first) || !utf32valid(last)) + line_fail(ccc_name, line); + continue; + } + ret = sscanf(line, "%X ; %d #", &unichar, &value); + if (ret == 2) { + unicode_data[unichar].ccc = value; + count++; + if (verbose > 1) + printf(" %X ccc %d\n", unichar, value); + if (!utf32valid(unichar)) + line_fail(ccc_name, line); + continue; + } + } + fclose(file); + + if (verbose > 0) + printf("Found %d entries\n", count); + if (count == 0) + file_fail(ccc_name); +} + +static int ignore_compatibility_form(char *type) +{ + int i; + char *ignored_types[] = {"font", "noBreak", "initial", "medial", + "final", "isolated", "circle", "super", + "sub", "vertical", "wide", "narrow", + "small", "square", "fraction", "compat"}; + + for (i = 0 ; i < ARRAY_SIZE(ignored_types); i++) + if (strcmp(type, ignored_types[i]) == 0) + return 1; + return 0; +} + +static void nfdi_init(void) +{ + FILE *file; + unsigned int unichar; + unsigned int mapping[19]; /* Magic - guaranteed not to be exceeded. */ + char *s; + char *type; + unsigned int *um; + int count; + int i; + int ret; + + if (verbose > 0) + printf("Parsing %s\n", data_name); + file = fopen(data_name, "r"); + if (!file) + open_fail(data_name, errno); + + count = 0; + while (fgets(line, LINESIZE, file)) { + ret = sscanf(line, "%X;%*[^;];%*[^;];%*[^;];%*[^;];%[^;];", + &unichar, buf0); + if (ret != 2) + continue; + if (!utf32valid(unichar)) + line_fail(data_name, line); + + s = buf0; + /* skip over */ + if (*s == '<') { + type = ++s; + while (*++s != '>'); + *s++ = '\0'; + if(ignore_compatibility_form(type)) + continue; + } + /* decode the decomposition into UTF-32 */ + i = 0; + while (*s) { + mapping[i] = strtoul(s, &s, 16); + if (!utf32valid(mapping[i])) + line_fail(data_name, line); + i++; + } + mapping[i++] = 0; + + um = malloc(i * sizeof(unsigned int)); + memcpy(um, mapping, i * sizeof(unsigned int)); + unicode_data[unichar].utf32nfdi = um; + + if (verbose > 1) + print_utf32nfdi(unichar); + count++; + } + fclose(file); + if (verbose > 0) + printf("Found %d entries\n", count); + if (count == 0) + file_fail(data_name); +} + +static void nfdicf_init(void) +{ + FILE *file; + unsigned int unichar; + unsigned int mapping[19]; /* Magic - guaranteed not to be exceeded. */ + char status; + char *s; + unsigned int *um; + int i; + int count; + int ret; + + if (verbose > 0) + printf("Parsing %s\n", fold_name); + file = fopen(fold_name, "r"); + if (!file) + open_fail(fold_name, errno); + + count = 0; + while (fgets(line, LINESIZE, file)) { + ret = sscanf(line, "%X; %c; %[^;];", &unichar, &status, buf0); + if (ret != 3) + continue; + if (!utf32valid(unichar)) + line_fail(fold_name, line); + /* Use the C+F casefold. */ + if (status != 'C' && status != 'F') + continue; + s = buf0; + if (*s == '<') + while (*s++ != ' ') + ; + i = 0; + while (*s) { + mapping[i] = strtoul(s, &s, 16); + if (!utf32valid(mapping[i])) + line_fail(fold_name, line); + i++; + } + mapping[i++] = 0; + + um = malloc(i * sizeof(unsigned int)); + memcpy(um, mapping, i * sizeof(unsigned int)); + unicode_data[unichar].utf32nfdicf = um; + + if (verbose > 1) + print_utf32nfdicf(unichar); + count++; + } + fclose(file); + if (verbose > 0) + printf("Found %d entries\n", count); + if (count == 0) + file_fail(fold_name); +} + +static void ignore_init(void) +{ + FILE *file; + unsigned int unichar; + unsigned int first; + unsigned int last; + unsigned int *um; + int count; + int ret; + + if (verbose > 0) + printf("Parsing %s\n", prop_name); + file = fopen(prop_name, "r"); + if (!file) + open_fail(prop_name, errno); + assert(file); + count = 0; + while (fgets(line, LINESIZE, file)) { + ret = sscanf(line, "%X..%X ; %s # ", &first, &last, buf0); + if (ret == 3) { + if (strcmp(buf0, "Default_Ignorable_Code_Point")) + continue; + if (!utf32valid(first) || !utf32valid(last)) + line_fail(prop_name, line); + for (unichar = first; unichar <= last; unichar++) { + free(unicode_data[unichar].utf32nfdi); + um = malloc(sizeof(unsigned int)); + *um = 0; + unicode_data[unichar].utf32nfdi = um; + free(unicode_data[unichar].utf32nfdicf); + um = malloc(sizeof(unsigned int)); + *um = 0; + unicode_data[unichar].utf32nfdicf = um; + count++; + } + if (verbose > 1) + printf(" %X..%X Default_Ignorable_Code_Point\n", + first, last); + continue; + } + ret = sscanf(line, "%X ; %s # ", &unichar, buf0); + if (ret == 2) { + if (strcmp(buf0, "Default_Ignorable_Code_Point")) + continue; + if (!utf32valid(unichar)) + line_fail(prop_name, line); + free(unicode_data[unichar].utf32nfdi); + um = malloc(sizeof(unsigned int)); + *um = 0; + unicode_data[unichar].utf32nfdi = um; + free(unicode_data[unichar].utf32nfdicf); + um = malloc(sizeof(unsigned int)); + *um = 0; + unicode_data[unichar].utf32nfdicf = um; + if (verbose > 1) + printf(" %X Default_Ignorable_Code_Point\n", + unichar); + count++; + continue; + } + } + fclose(file); + + if (verbose > 0) + printf("Found %d entries\n", count); + if (count == 0) + file_fail(prop_name); +} + +static void corrections_init(void) +{ + FILE *file; + unsigned int unichar; + unsigned int major; + unsigned int minor; + unsigned int revision; + unsigned int age; + unsigned int *um; + unsigned int mapping[19]; /* Magic - guaranteed not to be exceeded. */ + char *s; + int i; + int count; + int ret; + + if (verbose > 0) + printf("Parsing %s\n", norm_name); + file = fopen(norm_name, "r"); + if (!file) + open_fail(norm_name, errno); + + count = 0; + while (fgets(line, LINESIZE, file)) { + ret = sscanf(line, "%X;%[^;];%[^;];%d.%d.%d #", + &unichar, buf0, buf1, + &major, &minor, &revision); + if (ret != 6) + continue; + if (!utf32valid(unichar) || !age_valid(major, minor, revision)) + line_fail(norm_name, line); + count++; + } + corrections = calloc(count, sizeof(struct unicode_data)); + corrections_count = count; + rewind(file); + + count = 0; + while (fgets(line, LINESIZE, file)) { + ret = sscanf(line, "%X;%[^;];%[^;];%d.%d.%d #", + &unichar, buf0, buf1, + &major, &minor, &revision); + if (ret != 6) + continue; + if (!utf32valid(unichar) || !age_valid(major, minor, revision)) + line_fail(norm_name, line); + corrections[count] = unicode_data[unichar]; + assert(corrections[count].code == unichar); + age = UNICODE_AGE(major, minor, revision); + corrections[count].correction = age; + + i = 0; + s = buf0; + while (*s) { + mapping[i] = strtoul(s, &s, 16); + if (!utf32valid(mapping[i])) + line_fail(norm_name, line); + i++; + } + mapping[i++] = 0; + + um = malloc(i * sizeof(unsigned int)); + memcpy(um, mapping, i * sizeof(unsigned int)); + corrections[count].utf32nfdi = um; + + if (verbose > 1) + printf(" %X -> %s -> %s V%d_%d_%d\n", + unichar, buf0, buf1, major, minor, revision); + count++; + } + fclose(file); + + if (verbose > 0) + printf("Found %d entries\n", count); + if (count == 0) + file_fail(norm_name); +} + +/* ------------------------------------------------------------------ */ + +/* + * Hangul decomposition (algorithm from Section 3.12 of Unicode 6.3.0) + * + * AC00;;Lo;0;L;;;;;N;;;;; + * D7A3;;Lo;0;L;;;;;N;;;;; + * + * SBase = 0xAC00 + * LBase = 0x1100 + * VBase = 0x1161 + * TBase = 0x11A7 + * LCount = 19 + * VCount = 21 + * TCount = 28 + * NCount = 588 (VCount * TCount) + * SCount = 11172 (LCount * NCount) + * + * Decomposition: + * SIndex = s - SBase + * + * LV (Canonical/Full) + * LIndex = SIndex / NCount + * VIndex = (Sindex % NCount) / TCount + * LPart = LBase + LIndex + * VPart = VBase + VIndex + * + * LVT (Canonical) + * LVIndex = (SIndex / TCount) * TCount + * TIndex = (Sindex % TCount) + * LVPart = SBase + LVIndex + * TPart = TBase + TIndex + * + * LVT (Full) + * LIndex = SIndex / NCount + * VIndex = (Sindex % NCount) / TCount + * TIndex = (Sindex % TCount) + * LPart = LBase + LIndex + * VPart = VBase + VIndex + * if (TIndex == 0) { + * d = + * } else { + * TPart = TBase + TIndex + * d = + * } + * + */ + +static void hangul_decompose(void) +{ + unsigned int sb = 0xAC00; + unsigned int lb = 0x1100; + unsigned int vb = 0x1161; + unsigned int tb = 0x11a7; + /* unsigned int lc = 19; */ + unsigned int vc = 21; + unsigned int tc = 28; + unsigned int nc = (vc * tc); + /* unsigned int sc = (lc * nc); */ + unsigned int unichar; + unsigned int mapping[4]; + unsigned int *um; + int count; + int i; + + if (verbose > 0) + printf("Decomposing hangul\n"); + /* Hangul */ + count = 0; + for (unichar = 0xAC00; unichar <= 0xD7A3; unichar++) { + unsigned int si = unichar - sb; + unsigned int li = si / nc; + unsigned int vi = (si % nc) / tc; + unsigned int ti = si % tc; + + i = 0; + mapping[i++] = lb + li; + mapping[i++] = vb + vi; + if (ti) + mapping[i++] = tb + ti; + mapping[i++] = 0; + + assert(!unicode_data[unichar].utf32nfdi); + um = malloc(i * sizeof(unsigned int)); + memcpy(um, mapping, i * sizeof(unsigned int)); + unicode_data[unichar].utf32nfdi = um; + + assert(!unicode_data[unichar].utf32nfdicf); + um = malloc(i * sizeof(unsigned int)); + memcpy(um, mapping, i * sizeof(unsigned int)); + unicode_data[unichar].utf32nfdicf = um; + + /* + * Add a cookie as a reminder that the hangul syllable + * decompositions must not be stored in the generated + * trie. + */ + unicode_data[unichar].utf8nfdi = malloc(2); + unicode_data[unichar].utf8nfdi[0] = HANGUL; + unicode_data[unichar].utf8nfdi[1] = '\0'; + + if (verbose > 1) + print_utf32nfdi(unichar); + + count++; + } + if (verbose > 0) + printf("Created %d entries\n", count); +} + +static void nfdi_decompose(void) +{ + unsigned int unichar; + unsigned int mapping[19]; /* Magic - guaranteed not to be exceeded. */ + unsigned int *um; + unsigned int *dc; + int count; + int i; + int j; + int ret; + + if (verbose > 0) + printf("Decomposing nfdi\n"); + + count = 0; + for (unichar = 0; unichar != 0x110000; unichar++) { + if (!unicode_data[unichar].utf32nfdi) + continue; + for (;;) { + ret = 1; + i = 0; + um = unicode_data[unichar].utf32nfdi; + while (*um) { + dc = unicode_data[*um].utf32nfdi; + if (dc) { + for (j = 0; dc[j]; j++) + mapping[i++] = dc[j]; + ret = 0; + } else { + mapping[i++] = *um; + } + um++; + } + mapping[i++] = 0; + if (ret) + break; + free(unicode_data[unichar].utf32nfdi); + um = malloc(i * sizeof(unsigned int)); + memcpy(um, mapping, i * sizeof(unsigned int)); + unicode_data[unichar].utf32nfdi = um; + } + /* Add this decomposition to nfdicf if there is no entry. */ + if (!unicode_data[unichar].utf32nfdicf) { + um = malloc(i * sizeof(unsigned int)); + memcpy(um, mapping, i * sizeof(unsigned int)); + unicode_data[unichar].utf32nfdicf = um; + } + if (verbose > 1) + print_utf32nfdi(unichar); + count++; + } + if (verbose > 0) + printf("Processed %d entries\n", count); +} + +static void nfdicf_decompose(void) +{ + unsigned int unichar; + unsigned int mapping[19]; /* Magic - guaranteed not to be exceeded. */ + unsigned int *um; + unsigned int *dc; + int count; + int i; + int j; + int ret; + + if (verbose > 0) + printf("Decomposing nfdicf\n"); + count = 0; + for (unichar = 0; unichar != 0x110000; unichar++) { + if (!unicode_data[unichar].utf32nfdicf) + continue; + for (;;) { + ret = 1; + i = 0; + um = unicode_data[unichar].utf32nfdicf; + while (*um) { + dc = unicode_data[*um].utf32nfdicf; + if (dc) { + for (j = 0; dc[j]; j++) + mapping[i++] = dc[j]; + ret = 0; + } else { + mapping[i++] = *um; + } + um++; + } + mapping[i++] = 0; + if (ret) + break; + free(unicode_data[unichar].utf32nfdicf); + um = malloc(i * sizeof(unsigned int)); + memcpy(um, mapping, i * sizeof(unsigned int)); + unicode_data[unichar].utf32nfdicf = um; + } + if (verbose > 1) + print_utf32nfdicf(unichar); + count++; + } + if (verbose > 0) + printf("Processed %d entries\n", count); +} + +/* ------------------------------------------------------------------ */ + +int utf8agemax(struct tree *, const char *); +int utf8nagemax(struct tree *, const char *, size_t); +int utf8agemin(struct tree *, const char *); +int utf8nagemin(struct tree *, const char *, size_t); +ssize_t utf8len(struct tree *, const char *); +ssize_t utf8nlen(struct tree *, const char *, size_t); +struct utf8cursor; +int utf8cursor(struct utf8cursor *, struct tree *, const char *); +int utf8ncursor(struct utf8cursor *, struct tree *, const char *, size_t); +int utf8byte(struct utf8cursor *); + +/* + * Hangul decomposition (algorithm from Section 3.12 of Unicode 6.3.0) + * + * AC00;;Lo;0;L;;;;;N;;;;; + * D7A3;;Lo;0;L;;;;;N;;;;; + * + * SBase = 0xAC00 + * LBase = 0x1100 + * VBase = 0x1161 + * TBase = 0x11A7 + * LCount = 19 + * VCount = 21 + * TCount = 28 + * NCount = 588 (VCount * TCount) + * SCount = 11172 (LCount * NCount) + * + * Decomposition: + * SIndex = s - SBase + * + * LV (Canonical/Full) + * LIndex = SIndex / NCount + * VIndex = (Sindex % NCount) / TCount + * LPart = LBase + LIndex + * VPart = VBase + VIndex + * + * LVT (Canonical) + * LVIndex = (SIndex / TCount) * TCount + * TIndex = (Sindex % TCount) + * LVPart = SBase + LVIndex + * TPart = TBase + TIndex + * + * LVT (Full) + * LIndex = SIndex / NCount + * VIndex = (Sindex % NCount) / TCount + * TIndex = (Sindex % TCount) + * LPart = LBase + LIndex + * VPart = VBase + VIndex + * if (TIndex == 0) { + * d = + * } else { + * TPart = TBase + TIndex + * d = + * } + */ + +/* Constants */ +#define SB (0xAC00) +#define LB (0x1100) +#define VB (0x1161) +#define TB (0x11A7) +#define LC (19) +#define VC (21) +#define TC (28) +#define NC (VC * TC) +#define SC (LC * NC) + +/* Algorithmic decomposition of hangul syllable. */ +static utf8leaf_t *utf8hangul(const char *str, unsigned char *hangul) +{ + unsigned int si; + unsigned int li; + unsigned int vi; + unsigned int ti; + unsigned char *h; + + /* Calculate the SI, LI, VI, and TI values. */ + si = utf8decode(str) - SB; + li = si / NC; + vi = (si % NC) / TC; + ti = si % TC; + + /* Fill in base of leaf. */ + h = hangul; + LEAF_GEN(h) = 2; + LEAF_CCC(h) = DECOMPOSE; + h += 2; + + /* Add LPart, a 3-byte UTF-8 sequence. */ + h += utf8encode((char *)h, li + LB); + + /* Add VPart, a 3-byte UTF-8 sequence. */ + h += utf8encode((char *)h, vi + VB); + + /* Add TPart if required, also a 3-byte UTF-8 sequence. */ + if (ti) + h += utf8encode((char *)h, ti + TB); + + /* Terminate string. */ + h[0] = '\0'; + + return hangul; +} + +/* + * Use trie to scan s, touching at most len bytes. + * Returns the leaf if one exists, NULL otherwise. + * + * A non-NULL return guarantees that the UTF-8 sequence starting at s + * is well-formed and corresponds to a known unicode code point. The + * shorthand for this will be "is valid UTF-8 unicode". + */ +static utf8leaf_t *utf8nlookup(struct tree *tree, unsigned char *hangul, + const char *s, size_t len) +{ + utf8trie_t *trie; + int offlen; + int offset; + int mask; + int node; + + if (!tree) + return NULL; + if (len == 0) + return NULL; + node = 1; + trie = utf8data + tree->index; + while (node) { + offlen = (*trie & OFFLEN) >> OFFLEN_SHIFT; + if (*trie & NEXTBYTE) { + if (--len == 0) + return NULL; + s++; + } + mask = 1 << (*trie & BITNUM); + if (*s & mask) { + /* Right leg */ + if (offlen) { + /* Right node at offset of trie */ + node = (*trie & RIGHTNODE); + offset = trie[offlen]; + while (--offlen) { + offset <<= 8; + offset |= trie[offlen]; + } + trie += offset; + } else if (*trie & RIGHTPATH) { + /* Right node after this node */ + node = (*trie & TRIENODE); + trie++; + } else { + /* No right node. */ + return NULL; + } + } else { + /* Left leg */ + if (offlen) { + /* Left node after this node. */ + node = (*trie & LEFTNODE); + trie += offlen + 1; + } else if (*trie & RIGHTPATH) { + /* No left node. */ + return NULL; + } else { + /* Left node after this node */ + node = (*trie & TRIENODE); + trie++; + } + } + } + /* + * Hangul decomposition is done algorithmically. These are the + * codepoints >= 0xAC00 and <= 0xD7A3. Their UTF-8 encoding is + * always 3 bytes long, so s has been advanced twice, and the + * start of the sequence is at s-2. + */ + if (LEAF_CCC(trie) == DECOMPOSE && LEAF_STR(trie)[0] == HANGUL) + trie = utf8hangul(s - 2, hangul); + return trie; +} + +/* + * Use trie to scan s. + * Returns the leaf if one exists, NULL otherwise. + * + * Forwards to trie_nlookup(). + */ +static utf8leaf_t *utf8lookup(struct tree *tree, unsigned char *hangul, + const char *s) +{ + return utf8nlookup(tree, hangul, s, (size_t)-1); +} + +/* + * Return the number of bytes used by the current UTF-8 sequence. + * Assumes the input points to the first byte of a valid UTF-8 + * sequence. + */ +static inline int utf8clen(const char *s) +{ + unsigned char c = *s; + return 1 + (c >= 0xC0) + (c >= 0xE0) + (c >= 0xF0); +} + +/* + * Maximum age of any character in s. + * Return -1 if s is not valid UTF-8 unicode. + * Return 0 if only non-assigned code points are used. + */ +int utf8agemax(struct tree *tree, const char *s) +{ + utf8leaf_t *leaf; + int age = 0; + int leaf_age; + unsigned char hangul[UTF8HANGULLEAF]; + + if (!tree) + return -1; + + while (*s) { + leaf = utf8lookup(tree, hangul, s); + if (!leaf) + return -1; + leaf_age = ages[LEAF_GEN(leaf)]; + if (leaf_age <= tree->maxage && leaf_age > age) + age = leaf_age; + s += utf8clen(s); + } + return age; +} + +/* + * Minimum age of any character in s. + * Return -1 if s is not valid UTF-8 unicode. + * Return 0 if non-assigned code points are used. + */ +int utf8agemin(struct tree *tree, const char *s) +{ + utf8leaf_t *leaf; + int age; + int leaf_age; + unsigned char hangul[UTF8HANGULLEAF]; + + if (!tree) + return -1; + age = tree->maxage; + while (*s) { + leaf = utf8lookup(tree, hangul, s); + if (!leaf) + return -1; + leaf_age = ages[LEAF_GEN(leaf)]; + if (leaf_age <= tree->maxage && leaf_age < age) + age = leaf_age; + s += utf8clen(s); + } + return age; +} + +/* + * Maximum age of any character in s, touch at most len bytes. + * Return -1 if s is not valid UTF-8 unicode. + */ +int utf8nagemax(struct tree *tree, const char *s, size_t len) +{ + utf8leaf_t *leaf; + int age = 0; + int leaf_age; + unsigned char hangul[UTF8HANGULLEAF]; + + if (!tree) + return -1; + + while (len && *s) { + leaf = utf8nlookup(tree, hangul, s, len); + if (!leaf) + return -1; + leaf_age = ages[LEAF_GEN(leaf)]; + if (leaf_age <= tree->maxage && leaf_age > age) + age = leaf_age; + len -= utf8clen(s); + s += utf8clen(s); + } + return age; +} + +/* + * Maximum age of any character in s, touch at most len bytes. + * Return -1 if s is not valid UTF-8 unicode. + */ +int utf8nagemin(struct tree *tree, const char *s, size_t len) +{ + utf8leaf_t *leaf; + int leaf_age; + int age; + unsigned char hangul[UTF8HANGULLEAF]; + + if (!tree) + return -1; + age = tree->maxage; + while (len && *s) { + leaf = utf8nlookup(tree, hangul, s, len); + if (!leaf) + return -1; + leaf_age = ages[LEAF_GEN(leaf)]; + if (leaf_age <= tree->maxage && leaf_age < age) + age = leaf_age; + len -= utf8clen(s); + s += utf8clen(s); + } + return age; +} + +/* + * Length of the normalization of s. + * Return -1 if s is not valid UTF-8 unicode. + * + * A string of Default_Ignorable_Code_Point has length 0. + */ +ssize_t utf8len(struct tree *tree, const char *s) +{ + utf8leaf_t *leaf; + size_t ret = 0; + unsigned char hangul[UTF8HANGULLEAF]; + + if (!tree) + return -1; + while (*s) { + leaf = utf8lookup(tree, hangul, s); + if (!leaf) + return -1; + if (ages[LEAF_GEN(leaf)] > tree->maxage) + ret += utf8clen(s); + else if (LEAF_CCC(leaf) == DECOMPOSE) + ret += strlen(LEAF_STR(leaf)); + else + ret += utf8clen(s); + s += utf8clen(s); + } + return ret; +} + +/* + * Length of the normalization of s, touch at most len bytes. + * Return -1 if s is not valid UTF-8 unicode. + */ +ssize_t utf8nlen(struct tree *tree, const char *s, size_t len) +{ + utf8leaf_t *leaf; + size_t ret = 0; + unsigned char hangul[UTF8HANGULLEAF]; + + if (!tree) + return -1; + while (len && *s) { + leaf = utf8nlookup(tree, hangul, s, len); + if (!leaf) + return -1; + if (ages[LEAF_GEN(leaf)] > tree->maxage) + ret += utf8clen(s); + else if (LEAF_CCC(leaf) == DECOMPOSE) + ret += strlen(LEAF_STR(leaf)); + else + ret += utf8clen(s); + len -= utf8clen(s); + s += utf8clen(s); + } + return ret; +} + +/* + * Cursor structure used by the normalizer. + */ +struct utf8cursor { + struct tree *tree; + const char *s; + const char *p; + const char *ss; + const char *sp; + unsigned int len; + unsigned int slen; + short int ccc; + short int nccc; + unsigned int unichar; + unsigned char hangul[UTF8HANGULLEAF]; +}; + +/* + * Set up an utf8cursor for use by utf8byte(). + * + * s : string. + * len : length of s. + * u8c : pointer to cursor. + * trie : utf8trie_t to use for normalization. + * + * Returns -1 on error, 0 on success. + */ +int utf8ncursor(struct utf8cursor *u8c, struct tree *tree, const char *s, + size_t len) +{ + if (!tree) + return -1; + if (!s) + return -1; + u8c->tree = tree; + u8c->s = s; + u8c->p = NULL; + u8c->ss = NULL; + u8c->sp = NULL; + u8c->len = len; + u8c->slen = 0; + u8c->ccc = STOPPER; + u8c->nccc = STOPPER; + u8c->unichar = 0; + /* Check we didn't clobber the maximum length. */ + if (u8c->len != len) + return -1; + /* The first byte of s may not be an utf8 continuation. */ + if (len > 0 && (*s & 0xC0) == 0x80) + return -1; + return 0; +} + +/* + * Set up an utf8cursor for use by utf8byte(). + * + * s : NUL-terminated string. + * u8c : pointer to cursor. + * trie : utf8trie_t to use for normalization. + * + * Returns -1 on error, 0 on success. + */ +int utf8cursor(struct utf8cursor *u8c, struct tree *tree, const char *s) +{ + return utf8ncursor(u8c, tree, s, (unsigned int)-1); +} + +/* + * Get one byte from the normalized form of the string described by u8c. + * + * Returns the byte cast to an unsigned char on succes, and -1 on failure. + * + * The cursor keeps track of the location in the string in u8c->s. + * When a character is decomposed, the current location is stored in + * u8c->p, and u8c->s is set to the start of the decomposition. Note + * that bytes from a decomposition do not count against u8c->len. + * + * Characters are emitted if they match the current CCC in u8c->ccc. + * Hitting end-of-string while u8c->ccc == STOPPER means we're done, + * and the function returns 0 in that case. + * + * Sorting by CCC is done by repeatedly scanning the string. The + * values of u8c->s and u8c->p are stored in u8c->ss and u8c->sp at + * the start of the scan. The first pass finds the lowest CCC to be + * emitted and stores it in u8c->nccc, the second pass emits the + * characters with this CCC and finds the next lowest CCC. This limits + * the number of passes to 1 + the number of different CCCs in the + * sequence being scanned. + * + * Therefore: + * u8c->p != NULL -> a decomposition is being scanned. + * u8c->ss != NULL -> this is a repeating scan. + * u8c->ccc == -1 -> this is the first scan of a repeating scan. + */ +int utf8byte(struct utf8cursor *u8c) +{ + utf8leaf_t *leaf; + int ccc; + + for (;;) { + /* Check for the end of a decomposed character. */ + if (u8c->p && *u8c->s == '\0') { + u8c->s = u8c->p; + u8c->p = NULL; + } + + /* Check for end-of-string. */ + if (!u8c->p && (u8c->len == 0 || *u8c->s == '\0')) { + /* There is no next byte. */ + if (u8c->ccc == STOPPER) + return 0; + /* End-of-string during a scan counts as a stopper. */ + ccc = STOPPER; + goto ccc_mismatch; + } else if ((*u8c->s & 0xC0) == 0x80) { + /* This is a continuation of the current character. */ + if (!u8c->p) + u8c->len--; + return (unsigned char)*u8c->s++; + } + + /* Look up the data for the current character. */ + if (u8c->p) { + leaf = utf8lookup(u8c->tree, u8c->hangul, u8c->s); + } else { + leaf = utf8nlookup(u8c->tree, u8c->hangul, + u8c->s, u8c->len); + } + + /* No leaf found implies that the input is a binary blob. */ + if (!leaf) + return -1; + + /* Characters that are too new have CCC 0. */ + if (ages[LEAF_GEN(leaf)] > u8c->tree->maxage) { + ccc = STOPPER; + } else if ((ccc = LEAF_CCC(leaf)) == DECOMPOSE) { + u8c->len -= utf8clen(u8c->s); + u8c->p = u8c->s + utf8clen(u8c->s); + u8c->s = LEAF_STR(leaf); + /* Empty decomposition implies CCC 0. */ + if (*u8c->s == '\0') { + if (u8c->ccc == STOPPER) + continue; + ccc = STOPPER; + goto ccc_mismatch; + } + leaf = utf8lookup(u8c->tree, u8c->hangul, u8c->s); + ccc = LEAF_CCC(leaf); + } + u8c->unichar = utf8decode(u8c->s); + + /* + * If this is not a stopper, then see if it updates + * the next canonical class to be emitted. + */ + if (ccc != STOPPER && u8c->ccc < ccc && ccc < u8c->nccc) + u8c->nccc = ccc; + + /* + * Return the current byte if this is the current + * combining class. + */ + if (ccc == u8c->ccc) { + if (!u8c->p) + u8c->len--; + return (unsigned char)*u8c->s++; + } + + /* Current combining class mismatch. */ + ccc_mismatch: + if (u8c->nccc == STOPPER) { + /* + * Scan forward for the first canonical class + * to be emitted. Save the position from + * which to restart. + */ + assert(u8c->ccc == STOPPER); + u8c->ccc = MINCCC - 1; + u8c->nccc = ccc; + u8c->sp = u8c->p; + u8c->ss = u8c->s; + u8c->slen = u8c->len; + if (!u8c->p) + u8c->len -= utf8clen(u8c->s); + u8c->s += utf8clen(u8c->s); + } else if (ccc != STOPPER) { + /* Not a stopper, and not the ccc we're emitting. */ + if (!u8c->p) + u8c->len -= utf8clen(u8c->s); + u8c->s += utf8clen(u8c->s); + } else if (u8c->nccc != MAXCCC + 1) { + /* At a stopper, restart for next ccc. */ + u8c->ccc = u8c->nccc; + u8c->nccc = MAXCCC + 1; + u8c->s = u8c->ss; + u8c->p = u8c->sp; + u8c->len = u8c->slen; + } else { + /* All done, proceed from here. */ + u8c->ccc = STOPPER; + u8c->nccc = STOPPER; + u8c->sp = NULL; + u8c->ss = NULL; + u8c->slen = 0; + } + } +} + +/* ------------------------------------------------------------------ */ + +static int normalize_line(struct tree *tree) +{ + char *s; + char *t; + int c; + struct utf8cursor u8c; + + /* First test: null-terminated string. */ + s = buf2; + t = buf3; + if (utf8cursor(&u8c, tree, s)) + return -1; + while ((c = utf8byte(&u8c)) > 0) + if (c != (unsigned char)*t++) + return -1; + if (c < 0) + return -1; + if (*t != 0) + return -1; + + /* Second test: length-limited string. */ + s = buf2; + /* Replace NUL with a value that will cause an error if seen. */ + s[strlen(s) + 1] = -1; + t = buf3; + if (utf8cursor(&u8c, tree, s)) + return -1; + while ((c = utf8byte(&u8c)) > 0) + if (c != (unsigned char)*t++) + return -1; + if (c < 0) + return -1; + if (*t != 0) + return -1; + + return 0; +} + +static void normalization_test(void) +{ + FILE *file; + unsigned int unichar; + struct unicode_data *data; + char *s; + char *t; + int ret; + int ignorables; + int tests = 0; + int failures = 0; + + if (verbose > 0) + printf("Parsing %s\n", test_name); + /* Step one, read data from file. */ + file = fopen(test_name, "r"); + if (!file) + open_fail(test_name, errno); + + while (fgets(line, LINESIZE, file)) { + ret = sscanf(line, "%[^;];%*[^;];%[^;];%*[^;];%*[^;];", + buf0, buf1); + if (ret != 2 || *line == '#') + continue; + s = buf0; + t = buf2; + while (*s) { + unichar = strtoul(s, &s, 16); + t += utf8encode(t, unichar); + } + *t = '\0'; + + ignorables = 0; + s = buf1; + t = buf3; + while (*s) { + unichar = strtoul(s, &s, 16); + data = &unicode_data[unichar]; + if (data->utf8nfdi && !*data->utf8nfdi) + ignorables = 1; + else + t += utf8encode(t, unichar); + } + *t = '\0'; + + tests++; + if (normalize_line(nfdi_tree) < 0) { + printf("Line %s -> %s", buf0, buf1); + if (ignorables) + printf(" (ignorables removed)"); + printf(" failure\n"); + failures++; + } + } + fclose(file); + if (verbose > 0) + printf("Ran %d tests with %d failures\n", tests, failures); + if (failures) + file_fail(test_name); +} + +/* ------------------------------------------------------------------ */ + +static void write_file(void) +{ + FILE *file; + int i; + int j; + int t; + int gen; + + if (verbose > 0) + printf("Writing %s\n", utf8_name); + file = fopen(utf8_name, "w"); + if (!file) + open_fail(utf8_name, errno); + + fprintf(file, "/* This file is generated code, do not edit. */\n"); + fprintf(file, "#ifndef __INCLUDED_FROM_UTF8NORM_C__\n"); + fprintf(file, "#error Only nls_utf8-norm.c should include this file.\n"); + fprintf(file, "#endif\n"); + fprintf(file, "\n"); + fprintf(file, "static const unsigned int utf8vers = %#x;\n", + unicode_maxage); + fprintf(file, "\n"); + fprintf(file, "static const unsigned int utf8agetab[] = {\n"); + for (i = 0; i != ages_count; i++) + fprintf(file, "\t%#x%s\n", ages[i], + ages[i] == unicode_maxage ? "" : ","); + fprintf(file, "};\n"); + fprintf(file, "\n"); + fprintf(file, "static const struct utf8data utf8nfdicfdata[] = {\n"); + t = 0; + for (gen = 0; gen < ages_count; gen++) { + fprintf(file, "\t{ %#x, %d }%s\n", + ages[gen], trees[t].index, + ages[gen] == unicode_maxage ? "" : ","); + if (trees[t].maxage == ages[gen]) + t += 2; + } + fprintf(file, "};\n"); + fprintf(file, "\n"); + fprintf(file, "static const struct utf8data utf8nfdidata[] = {\n"); + t = 1; + for (gen = 0; gen < ages_count; gen++) { + fprintf(file, "\t{ %#x, %d }%s\n", + ages[gen], trees[t].index, + ages[gen] == unicode_maxage ? "" : ","); + if (trees[t].maxage == ages[gen]) + t += 2; + } + fprintf(file, "};\n"); + fprintf(file, "\n"); + fprintf(file, "static const unsigned char utf8data[%zd] = {\n", + utf8data_size); + t = 0; + for (i = 0; i != utf8data_size; i += 16) { + if (i == trees[t].index) { + fprintf(file, "\t/* %s_%x */\n", + trees[t].type, trees[t].maxage); + if (t < trees_count-1) + t++; + } + fprintf(file, "\t"); + for (j = i; j != i + 16; j++) + fprintf(file, "0x%.2x%s", utf8data[j], + (j < utf8data_size -1 ? "," : "")); + fprintf(file, "\n"); + } + fprintf(file, "};\n"); + fclose(file); +} + +/* ------------------------------------------------------------------ */ + +int main(int argc, char *argv[]) +{ + unsigned int unichar; + int opt; + + argv0 = argv[0]; + + while ((opt = getopt(argc, argv, "a:c:d:f:hn:o:p:t:v")) != -1) { + switch (opt) { + case 'a': + age_name = optarg; + break; + case 'c': + ccc_name = optarg; + break; + case 'd': + data_name = optarg; + break; + case 'f': + fold_name = optarg; + break; + case 'n': + norm_name = optarg; + break; + case 'o': + utf8_name = optarg; + break; + case 'p': + prop_name = optarg; + break; + case 't': + test_name = optarg; + break; + case 'v': + verbose++; + break; + case 'h': + help(); + exit(0); + default: + usage(); + } + } + + if (verbose > 1) + help(); + for (unichar = 0; unichar != 0x110000; unichar++) + unicode_data[unichar].code = unichar; + age_init(); + ccc_init(); + nfdi_init(); + nfdicf_init(); + ignore_init(); + corrections_init(); + hangul_decompose(); + nfdi_decompose(); + nfdicf_decompose(); + utf8_init(); + trees_init(); + trees_populate(); + trees_reduce(); + trees_verify(); + /* Prevent "unused function" warning. */ + (void)lookup(nfdi_tree, " "); + if (verbose > 2) + tree_walk(nfdi_tree); + if (verbose > 2) + tree_walk(nfdicf_tree); + normalization_test(); + write_file(); + + return 0; +} diff --git a/fs/unicode/utf8data.h b/fs/unicode/utf8data.h deleted file mode 100644 index 76e4f0e1b089..000000000000 --- a/fs/unicode/utf8data.h +++ /dev/null @@ -1,4109 +0,0 @@ -/* This file is generated code, do not edit. */ -#ifndef __INCLUDED_FROM_UTF8NORM_C__ -#error Only nls_utf8-norm.c should include this file. -#endif - -static const unsigned int utf8vers = 0xc0100; - -static const unsigned int utf8agetab[] = { - 0, - 0x10100, - 0x20000, - 0x20100, - 0x30000, - 0x30100, - 0x30200, - 0x40000, - 0x40100, - 0x50000, - 0x50100, - 0x50200, - 0x60000, - 0x60100, - 0x60200, - 0x60300, - 0x70000, - 0x80000, - 0x90000, - 0xa0000, - 0xb0000, - 0xc0000, - 0xc0100 -}; - -static const struct utf8data utf8nfdicfdata[] = { - { 0, 0 }, - { 0x10100, 0 }, - { 0x20000, 0 }, - { 0x20100, 0 }, - { 0x30000, 0 }, - { 0x30100, 0 }, - { 0x30200, 1792 }, - { 0x40000, 3200 }, - { 0x40100, 3200 }, - { 0x50000, 3200 }, - { 0x50100, 3200 }, - { 0x50200, 3200 }, - { 0x60000, 3200 }, - { 0x60100, 3200 }, - { 0x60200, 3200 }, - { 0x60300, 3200 }, - { 0x70000, 3200 }, - { 0x80000, 3200 }, - { 0x90000, 3200 }, - { 0xa0000, 3200 }, - { 0xb0000, 3200 }, - { 0xc0000, 3200 }, - { 0xc0100, 3200 } -}; - -static const struct utf8data utf8nfdidata[] = { - { 0, 896 }, - { 0x10100, 896 }, - { 0x20000, 896 }, - { 0x20100, 896 }, - { 0x30000, 896 }, - { 0x30100, 896 }, - { 0x30200, 2496 }, - { 0x40000, 20736 }, - { 0x40100, 20736 }, - { 0x50000, 20736 }, - { 0x50100, 20736 }, - { 0x50200, 20736 }, - { 0x60000, 20736 }, - { 0x60100, 20736 }, - { 0x60200, 20736 }, - { 0x60300, 20736 }, - { 0x70000, 20736 }, - { 0x80000, 20736 }, - { 0x90000, 20736 }, - { 0xa0000, 20736 }, - { 0xb0000, 20736 }, - { 0xc0000, 20736 }, - { 0xc0100, 20736 } -}; - -static const unsigned char utf8data[64256] = { - /* nfdicf_30100 */ - 0xd7,0x07,0x66,0x84,0x0c,0x01,0x00,0xc6,0xd5,0x16,0xe4,0x99,0x1a,0xe3,0x63,0x15, - 0xe2,0x4c,0x0e,0xc1,0xe0,0x4e,0x0d,0xcf,0x86,0x65,0x2d,0x0d,0x01,0x00,0xd4,0xb8, - 0xd3,0x27,0xe2,0x89,0xa3,0xe1,0xce,0x35,0xe0,0x2c,0x22,0xcf,0x86,0xc5,0xe4,0x15, - 0x6d,0xe3,0x60,0x68,0xe2,0xf6,0x65,0xe1,0x29,0x65,0xe0,0xee,0x64,0xcf,0x86,0xe5, - 0xb3,0x64,0x64,0x96,0x64,0x0b,0x00,0xd2,0x0e,0xe1,0xb5,0x3c,0xe0,0xba,0xa3,0xcf, - 0x86,0xcf,0x06,0x01,0x00,0xd1,0x0c,0xe0,0x1e,0xa9,0xcf,0x86,0xcf,0x06,0x02,0xff, - 0xff,0xd0,0x08,0xcf,0x86,0xcf,0x06,0x01,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x01, - 0x00,0xe4,0xe1,0x45,0xe3,0x3b,0x45,0xd2,0x06,0xcf,0x06,0x01,0x00,0xe1,0x87,0xad, - 0xd0,0x21,0xcf,0x86,0xe5,0x81,0xaa,0xe4,0x00,0xaa,0xe3,0xbf,0xa9,0xe2,0x9e,0xa9, - 0xe1,0x8d,0xa9,0x10,0x08,0x01,0xff,0xe8,0xb1,0x88,0x00,0x01,0xff,0xe6,0x9b,0xb4, - 0x00,0xcf,0x86,0xe5,0x63,0xac,0xd4,0x19,0xe3,0xa2,0xab,0xe2,0x81,0xab,0xe1,0x70, - 0xab,0x10,0x08,0x01,0xff,0xe9,0xb9,0xbf,0x00,0x01,0xff,0xe8,0xab,0x96,0x00,0xe3, - 0x09,0xac,0xe2,0xe8,0xab,0xe1,0xd7,0xab,0x10,0x08,0x01,0xff,0xe7,0xb8,0xb7,0x00, - 0x01,0xff,0xe9,0x9b,0xbb,0x00,0x83,0xe2,0x19,0xfa,0xe1,0xf2,0xf6,0xe0,0x6f,0xf5, - 0xcf,0x86,0xd5,0x31,0xc4,0xe3,0x54,0x4e,0xe2,0xf5,0x4c,0xe1,0xa4,0xcc,0xe0,0x9c, - 0x4b,0xcf,0x86,0xe5,0x8e,0x49,0xe4,0xaf,0x46,0xe3,0x11,0xbd,0xe2,0x68,0xbc,0xe1, - 0x43,0xbc,0xe0,0x1c,0xbc,0xcf,0x86,0xe5,0xe9,0xbb,0x94,0x07,0x63,0xd4,0xbb,0x07, - 0x00,0x07,0x00,0xe4,0xdb,0xf4,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x05,0x00,0xd2,0x0b, - 0xe1,0xea,0xe1,0xcf,0x86,0xcf,0x06,0x05,0x00,0xd1,0x0e,0xe0,0xd9,0xe2,0xcf,0x86, - 0xe5,0x9e,0xe2,0xcf,0x06,0x11,0x00,0xd0,0x0b,0xcf,0x86,0xe5,0xd9,0xe2,0xcf,0x06, - 0x13,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xe4,0x74,0xf4,0xe3,0x5d,0xf3, - 0xd2,0xa0,0xe1,0x13,0xe7,0xd0,0x21,0xcf,0x86,0xe5,0x14,0xe4,0xe4,0x90,0xe3,0xe3, - 0x4e,0xe3,0xe2,0x2d,0xe3,0xe1,0x1b,0xe3,0x10,0x08,0x05,0xff,0xe4,0xb8,0xbd,0x00, - 0x05,0xff,0xe4,0xb8,0xb8,0x00,0xcf,0x86,0xd5,0x1c,0xe4,0x70,0xe5,0xe3,0x2f,0xe5, - 0xe2,0x0e,0xe5,0xe1,0xfd,0xe4,0x10,0x08,0x05,0xff,0xe5,0x92,0xa2,0x00,0x05,0xff, - 0xe5,0x93,0xb6,0x00,0xd4,0x34,0xd3,0x18,0xe2,0xf7,0xe5,0xe1,0xe6,0xe5,0x10,0x09, - 0x05,0xff,0xf0,0xa1,0x9a,0xa8,0x00,0x05,0xff,0xf0,0xa1,0x9b,0xaa,0x00,0xe2,0x17, - 0xe6,0x91,0x11,0x10,0x09,0x05,0xff,0xf0,0xa1,0x8d,0xaa,0x00,0x05,0xff,0xe5,0xac, - 0x88,0x00,0x05,0xff,0xe5,0xac,0xbe,0x00,0xe3,0x5d,0xe6,0xd2,0x14,0xe1,0x2c,0xe6, - 0x10,0x08,0x05,0xff,0xe5,0xaf,0xb3,0x00,0x05,0xff,0xf0,0xa1,0xac,0x98,0x00,0xe1, - 0x38,0xe6,0x10,0x08,0x05,0xff,0xe5,0xbc,0xb3,0x00,0x05,0xff,0xe5,0xb0,0xa2,0x00, - 0xd1,0xd5,0xd0,0x6a,0xcf,0x86,0xe5,0x8d,0xeb,0xd4,0x19,0xe3,0xc6,0xea,0xe2,0xa4, - 0xea,0xe1,0x93,0xea,0x10,0x08,0x05,0xff,0xe6,0xb4,0xbe,0x00,0x05,0xff,0xe6,0xb5, - 0xb7,0x00,0xd3,0x18,0xe2,0x10,0xeb,0xe1,0xff,0xea,0x10,0x09,0x05,0xff,0xf0,0xa3, - 0xbd,0x9e,0x00,0x05,0xff,0xf0,0xa3,0xbe,0x8e,0x00,0xd2,0x13,0xe1,0x28,0xeb,0x10, - 0x08,0x05,0xff,0xe7,0x81,0xbd,0x00,0x05,0xff,0xe7,0x81,0xb7,0x00,0xd1,0x11,0x10, - 0x08,0x05,0xff,0xe7,0x85,0x85,0x00,0x05,0xff,0xf0,0xa4,0x89,0xa3,0x00,0x10,0x08, - 0x05,0xff,0xe7,0x86,0x9c,0x00,0x05,0xff,0xe4,0x8e,0xab,0x00,0xcf,0x86,0xe5,0x2a, - 0xed,0xd4,0x1a,0xe3,0x62,0xec,0xe2,0x48,0xec,0xe1,0x35,0xec,0x10,0x08,0x05,0xff, - 0xe7,0x9b,0xb4,0x00,0x05,0xff,0xf0,0xa5,0x83,0xb3,0x00,0xd3,0x16,0xe2,0xaa,0xec, - 0xe1,0x98,0xec,0x10,0x08,0x05,0xff,0xe7,0xa3,0x8c,0x00,0x05,0xff,0xe4,0x83,0xa3, - 0x00,0xd2,0x13,0xe1,0xc6,0xec,0x10,0x08,0x05,0xff,0xe4,0x84,0xaf,0x00,0x05,0xff, - 0xe7,0xa9,0x80,0x00,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa5,0xa5,0xbc,0x00,0x05, - 0xff,0xf0,0xa5,0xaa,0xa7,0x00,0x10,0x09,0x05,0xff,0xf0,0xa5,0xaa,0xa7,0x00,0x05, - 0xff,0xe7,0xaa,0xae,0x00,0xe0,0xdc,0xef,0xcf,0x86,0xd5,0x1d,0xe4,0x51,0xee,0xe3, - 0x0d,0xee,0xe2,0xeb,0xed,0xe1,0xda,0xed,0x10,0x09,0x05,0xff,0xf0,0xa3,0x8d,0x9f, - 0x00,0x05,0xff,0xe4,0x8f,0x95,0x00,0xd4,0x19,0xe3,0xf8,0xee,0xe2,0xd4,0xee,0xe1, - 0xc3,0xee,0x10,0x08,0x05,0xff,0xe8,0x8d,0x93,0x00,0x05,0xff,0xe8,0x8f,0x8a,0x00, - 0xd3,0x18,0xe2,0x43,0xef,0xe1,0x32,0xef,0x10,0x09,0x05,0xff,0xf0,0xa6,0xbe,0xb1, - 0x00,0x05,0xff,0xf0,0xa7,0x83,0x92,0x00,0xd2,0x13,0xe1,0x5b,0xef,0x10,0x08,0x05, - 0xff,0xe8,0x9a,0x88,0x00,0x05,0xff,0xe8,0x9c,0x8e,0x00,0xd1,0x10,0x10,0x08,0x05, - 0xff,0xe8,0x9c,0xa8,0x00,0x05,0xff,0xe8,0x9d,0xab,0x00,0x10,0x08,0x05,0xff,0xe8, - 0x9e,0x86,0x00,0x05,0xff,0xe4,0xb5,0x97,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - /* nfdi_30100 */ - 0x57,0x04,0x01,0x00,0xc6,0xd5,0x16,0xe4,0xc2,0x59,0xe3,0xfb,0x54,0xe2,0x74,0x4f, - 0xc1,0xe0,0xa0,0x4d,0xcf,0x86,0x65,0x84,0x4d,0x01,0x00,0xd4,0xb8,0xd3,0x27,0xe2, - 0x0c,0xa0,0xe1,0xdf,0x8d,0xe0,0x39,0x71,0xcf,0x86,0xc5,0xe4,0x98,0x69,0xe3,0xe3, - 0x64,0xe2,0x79,0x62,0xe1,0xac,0x61,0xe0,0x71,0x61,0xcf,0x86,0xe5,0x36,0x61,0x64, - 0x19,0x61,0x0b,0x00,0xd2,0x0e,0xe1,0xc2,0xa0,0xe0,0x3d,0xa0,0xcf,0x86,0xcf,0x06, - 0x01,0x00,0xd1,0x0c,0xe0,0xa1,0xa5,0xcf,0x86,0xcf,0x06,0x02,0xff,0xff,0xd0,0x08, - 0xcf,0x86,0xcf,0x06,0x01,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x01,0x00,0xe4,0x9e, - 0xb6,0xe3,0x18,0xae,0xd2,0x06,0xcf,0x06,0x01,0x00,0xe1,0x0a,0xaa,0xd0,0x21,0xcf, - 0x86,0xe5,0x04,0xa7,0xe4,0x83,0xa6,0xe3,0x42,0xa6,0xe2,0x21,0xa6,0xe1,0x10,0xa6, - 0x10,0x08,0x01,0xff,0xe8,0xb1,0x88,0x00,0x01,0xff,0xe6,0x9b,0xb4,0x00,0xcf,0x86, - 0xe5,0xe6,0xa8,0xd4,0x19,0xe3,0x25,0xa8,0xe2,0x04,0xa8,0xe1,0xf3,0xa7,0x10,0x08, - 0x01,0xff,0xe9,0xb9,0xbf,0x00,0x01,0xff,0xe8,0xab,0x96,0x00,0xe3,0x8c,0xa8,0xe2, - 0x6b,0xa8,0xe1,0x5a,0xa8,0x10,0x08,0x01,0xff,0xe7,0xb8,0xb7,0x00,0x01,0xff,0xe9, - 0x9b,0xbb,0x00,0x83,0xe2,0x9c,0xf6,0xe1,0x75,0xf3,0xe0,0xf2,0xf1,0xcf,0x86,0xd5, - 0x31,0xc4,0xe3,0x6d,0xcc,0xe2,0x46,0xca,0xe1,0x27,0xc9,0xe0,0xb7,0xbf,0xcf,0x86, - 0xe5,0xaa,0xbb,0xe4,0xa3,0xba,0xe3,0x94,0xb9,0xe2,0xeb,0xb8,0xe1,0xc6,0xb8,0xe0, - 0x9f,0xb8,0xcf,0x86,0xe5,0x6c,0xb8,0x94,0x07,0x63,0x57,0xb8,0x07,0x00,0x07,0x00, - 0xe4,0x5e,0xf1,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x05,0x00,0xd2,0x0b,0xe1,0x6d,0xde, - 0xcf,0x86,0xcf,0x06,0x05,0x00,0xd1,0x0e,0xe0,0x5c,0xdf,0xcf,0x86,0xe5,0x21,0xdf, - 0xcf,0x06,0x11,0x00,0xd0,0x0b,0xcf,0x86,0xe5,0x5c,0xdf,0xcf,0x06,0x13,0x00,0xcf, - 0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xe4,0xf7,0xf0,0xe3,0xe0,0xef,0xd2,0xa0,0xe1, - 0x96,0xe3,0xd0,0x21,0xcf,0x86,0xe5,0x97,0xe0,0xe4,0x13,0xe0,0xe3,0xd1,0xdf,0xe2, - 0xb0,0xdf,0xe1,0x9e,0xdf,0x10,0x08,0x05,0xff,0xe4,0xb8,0xbd,0x00,0x05,0xff,0xe4, - 0xb8,0xb8,0x00,0xcf,0x86,0xd5,0x1c,0xe4,0xf3,0xe1,0xe3,0xb2,0xe1,0xe2,0x91,0xe1, - 0xe1,0x80,0xe1,0x10,0x08,0x05,0xff,0xe5,0x92,0xa2,0x00,0x05,0xff,0xe5,0x93,0xb6, - 0x00,0xd4,0x34,0xd3,0x18,0xe2,0x7a,0xe2,0xe1,0x69,0xe2,0x10,0x09,0x05,0xff,0xf0, - 0xa1,0x9a,0xa8,0x00,0x05,0xff,0xf0,0xa1,0x9b,0xaa,0x00,0xe2,0x9a,0xe2,0x91,0x11, - 0x10,0x09,0x05,0xff,0xf0,0xa1,0x8d,0xaa,0x00,0x05,0xff,0xe5,0xac,0x88,0x00,0x05, - 0xff,0xe5,0xac,0xbe,0x00,0xe3,0xe0,0xe2,0xd2,0x14,0xe1,0xaf,0xe2,0x10,0x08,0x05, - 0xff,0xe5,0xaf,0xb3,0x00,0x05,0xff,0xf0,0xa1,0xac,0x98,0x00,0xe1,0xbb,0xe2,0x10, - 0x08,0x05,0xff,0xe5,0xbc,0xb3,0x00,0x05,0xff,0xe5,0xb0,0xa2,0x00,0xd1,0xd5,0xd0, - 0x6a,0xcf,0x86,0xe5,0x10,0xe8,0xd4,0x19,0xe3,0x49,0xe7,0xe2,0x27,0xe7,0xe1,0x16, - 0xe7,0x10,0x08,0x05,0xff,0xe6,0xb4,0xbe,0x00,0x05,0xff,0xe6,0xb5,0xb7,0x00,0xd3, - 0x18,0xe2,0x93,0xe7,0xe1,0x82,0xe7,0x10,0x09,0x05,0xff,0xf0,0xa3,0xbd,0x9e,0x00, - 0x05,0xff,0xf0,0xa3,0xbe,0x8e,0x00,0xd2,0x13,0xe1,0xab,0xe7,0x10,0x08,0x05,0xff, - 0xe7,0x81,0xbd,0x00,0x05,0xff,0xe7,0x81,0xb7,0x00,0xd1,0x11,0x10,0x08,0x05,0xff, - 0xe7,0x85,0x85,0x00,0x05,0xff,0xf0,0xa4,0x89,0xa3,0x00,0x10,0x08,0x05,0xff,0xe7, - 0x86,0x9c,0x00,0x05,0xff,0xe4,0x8e,0xab,0x00,0xcf,0x86,0xe5,0xad,0xe9,0xd4,0x1a, - 0xe3,0xe5,0xe8,0xe2,0xcb,0xe8,0xe1,0xb8,0xe8,0x10,0x08,0x05,0xff,0xe7,0x9b,0xb4, - 0x00,0x05,0xff,0xf0,0xa5,0x83,0xb3,0x00,0xd3,0x16,0xe2,0x2d,0xe9,0xe1,0x1b,0xe9, - 0x10,0x08,0x05,0xff,0xe7,0xa3,0x8c,0x00,0x05,0xff,0xe4,0x83,0xa3,0x00,0xd2,0x13, - 0xe1,0x49,0xe9,0x10,0x08,0x05,0xff,0xe4,0x84,0xaf,0x00,0x05,0xff,0xe7,0xa9,0x80, - 0x00,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa5,0xa5,0xbc,0x00,0x05,0xff,0xf0,0xa5, - 0xaa,0xa7,0x00,0x10,0x09,0x05,0xff,0xf0,0xa5,0xaa,0xa7,0x00,0x05,0xff,0xe7,0xaa, - 0xae,0x00,0xe0,0x5f,0xec,0xcf,0x86,0xd5,0x1d,0xe4,0xd4,0xea,0xe3,0x90,0xea,0xe2, - 0x6e,0xea,0xe1,0x5d,0xea,0x10,0x09,0x05,0xff,0xf0,0xa3,0x8d,0x9f,0x00,0x05,0xff, - 0xe4,0x8f,0x95,0x00,0xd4,0x19,0xe3,0x7b,0xeb,0xe2,0x57,0xeb,0xe1,0x46,0xeb,0x10, - 0x08,0x05,0xff,0xe8,0x8d,0x93,0x00,0x05,0xff,0xe8,0x8f,0x8a,0x00,0xd3,0x18,0xe2, - 0xc6,0xeb,0xe1,0xb5,0xeb,0x10,0x09,0x05,0xff,0xf0,0xa6,0xbe,0xb1,0x00,0x05,0xff, - 0xf0,0xa7,0x83,0x92,0x00,0xd2,0x13,0xe1,0xde,0xeb,0x10,0x08,0x05,0xff,0xe8,0x9a, - 0x88,0x00,0x05,0xff,0xe8,0x9c,0x8e,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe8,0x9c, - 0xa8,0x00,0x05,0xff,0xe8,0x9d,0xab,0x00,0x10,0x08,0x05,0xff,0xe8,0x9e,0x86,0x00, - 0x05,0xff,0xe4,0xb5,0x97,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - /* nfdicf_30200 */ - 0xd7,0x07,0x66,0x84,0x05,0x01,0x00,0xc6,0xd5,0x16,0xe4,0x99,0x13,0xe3,0x63,0x0e, - 0xe2,0x4c,0x07,0xc1,0xe0,0x4e,0x06,0xcf,0x86,0x65,0x2d,0x06,0x01,0x00,0xd4,0x2a, - 0xe3,0xd0,0x35,0xe2,0x88,0x9c,0xe1,0xcd,0x2e,0xe0,0x2b,0x1b,0xcf,0x86,0xc5,0xe4, - 0x14,0x66,0xe3,0x5f,0x61,0xe2,0xf5,0x5e,0xe1,0x28,0x5e,0xe0,0xed,0x5d,0xcf,0x86, - 0xe5,0xb2,0x5d,0x64,0x95,0x5d,0x0b,0x00,0x83,0xe2,0xa7,0xf3,0xe1,0x80,0xf0,0xe0, - 0xfd,0xee,0xcf,0x86,0xd5,0x31,0xc4,0xe3,0xe2,0x47,0xe2,0x83,0x46,0xe1,0x32,0xc6, - 0xe0,0x2a,0x45,0xcf,0x86,0xe5,0x1c,0x43,0xe4,0x3d,0x40,0xe3,0x9f,0xb6,0xe2,0xf6, - 0xb5,0xe1,0xd1,0xb5,0xe0,0xaa,0xb5,0xcf,0x86,0xe5,0x77,0xb5,0x94,0x07,0x63,0x62, - 0xb5,0x07,0x00,0x07,0x00,0xe4,0x69,0xee,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x05,0x00, - 0xd2,0x0b,0xe1,0x78,0xdb,0xcf,0x86,0xcf,0x06,0x05,0x00,0xd1,0x0e,0xe0,0x67,0xdc, - 0xcf,0x86,0xe5,0x2c,0xdc,0xcf,0x06,0x11,0x00,0xd0,0x0b,0xcf,0x86,0xe5,0x67,0xdc, - 0xcf,0x06,0x13,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xe4,0x02,0xee,0xe3, - 0xeb,0xec,0xd2,0xa0,0xe1,0xa1,0xe0,0xd0,0x21,0xcf,0x86,0xe5,0xa2,0xdd,0xe4,0x1e, - 0xdd,0xe3,0xdc,0xdc,0xe2,0xbb,0xdc,0xe1,0xa9,0xdc,0x10,0x08,0x05,0xff,0xe4,0xb8, - 0xbd,0x00,0x05,0xff,0xe4,0xb8,0xb8,0x00,0xcf,0x86,0xd5,0x1c,0xe4,0xfe,0xde,0xe3, - 0xbd,0xde,0xe2,0x9c,0xde,0xe1,0x8b,0xde,0x10,0x08,0x05,0xff,0xe5,0x92,0xa2,0x00, - 0x05,0xff,0xe5,0x93,0xb6,0x00,0xd4,0x34,0xd3,0x18,0xe2,0x85,0xdf,0xe1,0x74,0xdf, - 0x10,0x09,0x05,0xff,0xf0,0xa1,0x9a,0xa8,0x00,0x05,0xff,0xf0,0xa1,0x9b,0xaa,0x00, - 0xe2,0xa5,0xdf,0x91,0x11,0x10,0x09,0x05,0xff,0xf0,0xa1,0x8d,0xaa,0x00,0x05,0xff, - 0xe5,0xac,0x88,0x00,0x05,0xff,0xe5,0xac,0xbe,0x00,0xe3,0xeb,0xdf,0xd2,0x14,0xe1, - 0xba,0xdf,0x10,0x08,0x05,0xff,0xe5,0xaf,0xb3,0x00,0x05,0xff,0xf0,0xa1,0xac,0x98, - 0x00,0xe1,0xc6,0xdf,0x10,0x08,0x05,0xff,0xe5,0xbc,0xb3,0x00,0x05,0xff,0xe5,0xb0, - 0xa2,0x00,0xd1,0xd5,0xd0,0x6a,0xcf,0x86,0xe5,0x1b,0xe5,0xd4,0x19,0xe3,0x54,0xe4, - 0xe2,0x32,0xe4,0xe1,0x21,0xe4,0x10,0x08,0x05,0xff,0xe6,0xb4,0xbe,0x00,0x05,0xff, - 0xe6,0xb5,0xb7,0x00,0xd3,0x18,0xe2,0x9e,0xe4,0xe1,0x8d,0xe4,0x10,0x09,0x05,0xff, - 0xf0,0xa3,0xbd,0x9e,0x00,0x05,0xff,0xf0,0xa3,0xbe,0x8e,0x00,0xd2,0x13,0xe1,0xb6, - 0xe4,0x10,0x08,0x05,0xff,0xe7,0x81,0xbd,0x00,0x05,0xff,0xe7,0x81,0xb7,0x00,0xd1, - 0x11,0x10,0x08,0x05,0xff,0xe7,0x85,0x85,0x00,0x05,0xff,0xf0,0xa4,0x89,0xa3,0x00, - 0x10,0x08,0x05,0xff,0xe7,0x86,0x9c,0x00,0x05,0xff,0xe4,0x8e,0xab,0x00,0xcf,0x86, - 0xe5,0xb8,0xe6,0xd4,0x1a,0xe3,0xf0,0xe5,0xe2,0xd6,0xe5,0xe1,0xc3,0xe5,0x10,0x08, - 0x05,0xff,0xe7,0x9b,0xb4,0x00,0x05,0xff,0xf0,0xa5,0x83,0xb3,0x00,0xd3,0x16,0xe2, - 0x38,0xe6,0xe1,0x26,0xe6,0x10,0x08,0x05,0xff,0xe7,0xa3,0x8c,0x00,0x05,0xff,0xe4, - 0x83,0xa3,0x00,0xd2,0x13,0xe1,0x54,0xe6,0x10,0x08,0x05,0xff,0xe4,0x84,0xaf,0x00, - 0x05,0xff,0xe7,0xa9,0x80,0x00,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa5,0xa5,0xbc, - 0x00,0x05,0xff,0xf0,0xa5,0xaa,0xa7,0x00,0x10,0x09,0x05,0xff,0xf0,0xa5,0xaa,0xa7, - 0x00,0x05,0xff,0xe7,0xaa,0xae,0x00,0xe0,0x6a,0xe9,0xcf,0x86,0xd5,0x1d,0xe4,0xdf, - 0xe7,0xe3,0x9b,0xe7,0xe2,0x79,0xe7,0xe1,0x68,0xe7,0x10,0x09,0x05,0xff,0xf0,0xa3, - 0x8d,0x9f,0x00,0x05,0xff,0xe4,0x8f,0x95,0x00,0xd4,0x19,0xe3,0x86,0xe8,0xe2,0x62, - 0xe8,0xe1,0x51,0xe8,0x10,0x08,0x05,0xff,0xe8,0x8d,0x93,0x00,0x05,0xff,0xe8,0x8f, - 0x8a,0x00,0xd3,0x18,0xe2,0xd1,0xe8,0xe1,0xc0,0xe8,0x10,0x09,0x05,0xff,0xf0,0xa6, - 0xbe,0xb1,0x00,0x05,0xff,0xf0,0xa7,0x83,0x92,0x00,0xd2,0x13,0xe1,0xe9,0xe8,0x10, - 0x08,0x05,0xff,0xe8,0x9a,0x88,0x00,0x05,0xff,0xe8,0x9c,0x8e,0x00,0xd1,0x10,0x10, - 0x08,0x05,0xff,0xe8,0x9c,0xa8,0x00,0x05,0xff,0xe8,0x9d,0xab,0x00,0x10,0x08,0x05, - 0xff,0xe8,0x9e,0x86,0x00,0x05,0xff,0xe4,0xb5,0x97,0x00,0x00,0x00,0x00,0x00,0x00, - /* nfdi_30200 */ - 0x57,0x04,0x01,0x00,0xc6,0xd5,0x16,0xe4,0x82,0x53,0xe3,0xbb,0x4e,0xe2,0x34,0x49, - 0xc1,0xe0,0x60,0x47,0xcf,0x86,0x65,0x44,0x47,0x01,0x00,0xd4,0x2a,0xe3,0x1c,0x9a, - 0xe2,0xcb,0x99,0xe1,0x9e,0x87,0xe0,0xf8,0x6a,0xcf,0x86,0xc5,0xe4,0x57,0x63,0xe3, - 0xa2,0x5e,0xe2,0x38,0x5c,0xe1,0x6b,0x5b,0xe0,0x30,0x5b,0xcf,0x86,0xe5,0xf5,0x5a, - 0x64,0xd8,0x5a,0x0b,0x00,0x83,0xe2,0xea,0xf0,0xe1,0xc3,0xed,0xe0,0x40,0xec,0xcf, - 0x86,0xd5,0x31,0xc4,0xe3,0xbb,0xc6,0xe2,0x94,0xc4,0xe1,0x75,0xc3,0xe0,0x05,0xba, - 0xcf,0x86,0xe5,0xf8,0xb5,0xe4,0xf1,0xb4,0xe3,0xe2,0xb3,0xe2,0x39,0xb3,0xe1,0x14, - 0xb3,0xe0,0xed,0xb2,0xcf,0x86,0xe5,0xba,0xb2,0x94,0x07,0x63,0xa5,0xb2,0x07,0x00, - 0x07,0x00,0xe4,0xac,0xeb,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x05,0x00,0xd2,0x0b,0xe1, - 0xbb,0xd8,0xcf,0x86,0xcf,0x06,0x05,0x00,0xd1,0x0e,0xe0,0xaa,0xd9,0xcf,0x86,0xe5, - 0x6f,0xd9,0xcf,0x06,0x11,0x00,0xd0,0x0b,0xcf,0x86,0xe5,0xaa,0xd9,0xcf,0x06,0x13, - 0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xe4,0x45,0xeb,0xe3,0x2e,0xea,0xd2, - 0xa0,0xe1,0xe4,0xdd,0xd0,0x21,0xcf,0x86,0xe5,0xe5,0xda,0xe4,0x61,0xda,0xe3,0x1f, - 0xda,0xe2,0xfe,0xd9,0xe1,0xec,0xd9,0x10,0x08,0x05,0xff,0xe4,0xb8,0xbd,0x00,0x05, - 0xff,0xe4,0xb8,0xb8,0x00,0xcf,0x86,0xd5,0x1c,0xe4,0x41,0xdc,0xe3,0x00,0xdc,0xe2, - 0xdf,0xdb,0xe1,0xce,0xdb,0x10,0x08,0x05,0xff,0xe5,0x92,0xa2,0x00,0x05,0xff,0xe5, - 0x93,0xb6,0x00,0xd4,0x34,0xd3,0x18,0xe2,0xc8,0xdc,0xe1,0xb7,0xdc,0x10,0x09,0x05, - 0xff,0xf0,0xa1,0x9a,0xa8,0x00,0x05,0xff,0xf0,0xa1,0x9b,0xaa,0x00,0xe2,0xe8,0xdc, - 0x91,0x11,0x10,0x09,0x05,0xff,0xf0,0xa1,0x8d,0xaa,0x00,0x05,0xff,0xe5,0xac,0x88, - 0x00,0x05,0xff,0xe5,0xac,0xbe,0x00,0xe3,0x2e,0xdd,0xd2,0x14,0xe1,0xfd,0xdc,0x10, - 0x08,0x05,0xff,0xe5,0xaf,0xb3,0x00,0x05,0xff,0xf0,0xa1,0xac,0x98,0x00,0xe1,0x09, - 0xdd,0x10,0x08,0x05,0xff,0xe5,0xbc,0xb3,0x00,0x05,0xff,0xe5,0xb0,0xa2,0x00,0xd1, - 0xd5,0xd0,0x6a,0xcf,0x86,0xe5,0x5e,0xe2,0xd4,0x19,0xe3,0x97,0xe1,0xe2,0x75,0xe1, - 0xe1,0x64,0xe1,0x10,0x08,0x05,0xff,0xe6,0xb4,0xbe,0x00,0x05,0xff,0xe6,0xb5,0xb7, - 0x00,0xd3,0x18,0xe2,0xe1,0xe1,0xe1,0xd0,0xe1,0x10,0x09,0x05,0xff,0xf0,0xa3,0xbd, - 0x9e,0x00,0x05,0xff,0xf0,0xa3,0xbe,0x8e,0x00,0xd2,0x13,0xe1,0xf9,0xe1,0x10,0x08, - 0x05,0xff,0xe7,0x81,0xbd,0x00,0x05,0xff,0xe7,0x81,0xb7,0x00,0xd1,0x11,0x10,0x08, - 0x05,0xff,0xe7,0x85,0x85,0x00,0x05,0xff,0xf0,0xa4,0x89,0xa3,0x00,0x10,0x08,0x05, - 0xff,0xe7,0x86,0x9c,0x00,0x05,0xff,0xe4,0x8e,0xab,0x00,0xcf,0x86,0xe5,0xfb,0xe3, - 0xd4,0x1a,0xe3,0x33,0xe3,0xe2,0x19,0xe3,0xe1,0x06,0xe3,0x10,0x08,0x05,0xff,0xe7, - 0x9b,0xb4,0x00,0x05,0xff,0xf0,0xa5,0x83,0xb3,0x00,0xd3,0x16,0xe2,0x7b,0xe3,0xe1, - 0x69,0xe3,0x10,0x08,0x05,0xff,0xe7,0xa3,0x8c,0x00,0x05,0xff,0xe4,0x83,0xa3,0x00, - 0xd2,0x13,0xe1,0x97,0xe3,0x10,0x08,0x05,0xff,0xe4,0x84,0xaf,0x00,0x05,0xff,0xe7, - 0xa9,0x80,0x00,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa5,0xa5,0xbc,0x00,0x05,0xff, - 0xf0,0xa5,0xaa,0xa7,0x00,0x10,0x09,0x05,0xff,0xf0,0xa5,0xaa,0xa7,0x00,0x05,0xff, - 0xe7,0xaa,0xae,0x00,0xe0,0xad,0xe6,0xcf,0x86,0xd5,0x1d,0xe4,0x22,0xe5,0xe3,0xde, - 0xe4,0xe2,0xbc,0xe4,0xe1,0xab,0xe4,0x10,0x09,0x05,0xff,0xf0,0xa3,0x8d,0x9f,0x00, - 0x05,0xff,0xe4,0x8f,0x95,0x00,0xd4,0x19,0xe3,0xc9,0xe5,0xe2,0xa5,0xe5,0xe1,0x94, - 0xe5,0x10,0x08,0x05,0xff,0xe8,0x8d,0x93,0x00,0x05,0xff,0xe8,0x8f,0x8a,0x00,0xd3, - 0x18,0xe2,0x14,0xe6,0xe1,0x03,0xe6,0x10,0x09,0x05,0xff,0xf0,0xa6,0xbe,0xb1,0x00, - 0x05,0xff,0xf0,0xa7,0x83,0x92,0x00,0xd2,0x13,0xe1,0x2c,0xe6,0x10,0x08,0x05,0xff, - 0xe8,0x9a,0x88,0x00,0x05,0xff,0xe8,0x9c,0x8e,0x00,0xd1,0x10,0x10,0x08,0x05,0xff, - 0xe8,0x9c,0xa8,0x00,0x05,0xff,0xe8,0x9d,0xab,0x00,0x10,0x08,0x05,0xff,0xe8,0x9e, - 0x86,0x00,0x05,0xff,0xe4,0xb5,0x97,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - /* nfdicf_c0100 */ - 0xd7,0xb0,0x56,0x04,0x01,0x00,0x95,0xa8,0xd4,0x5e,0xd3,0x2e,0xd2,0x16,0xd1,0x0a, - 0x10,0x04,0x01,0x00,0x01,0xff,0x61,0x00,0x10,0x06,0x01,0xff,0x62,0x00,0x01,0xff, - 0x63,0x00,0xd1,0x0c,0x10,0x06,0x01,0xff,0x64,0x00,0x01,0xff,0x65,0x00,0x10,0x06, - 0x01,0xff,0x66,0x00,0x01,0xff,0x67,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x06,0x01,0xff, - 0x68,0x00,0x01,0xff,0x69,0x00,0x10,0x06,0x01,0xff,0x6a,0x00,0x01,0xff,0x6b,0x00, - 0xd1,0x0c,0x10,0x06,0x01,0xff,0x6c,0x00,0x01,0xff,0x6d,0x00,0x10,0x06,0x01,0xff, - 0x6e,0x00,0x01,0xff,0x6f,0x00,0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x06,0x01,0xff, - 0x70,0x00,0x01,0xff,0x71,0x00,0x10,0x06,0x01,0xff,0x72,0x00,0x01,0xff,0x73,0x00, - 0xd1,0x0c,0x10,0x06,0x01,0xff,0x74,0x00,0x01,0xff,0x75,0x00,0x10,0x06,0x01,0xff, - 0x76,0x00,0x01,0xff,0x77,0x00,0x92,0x16,0xd1,0x0c,0x10,0x06,0x01,0xff,0x78,0x00, - 0x01,0xff,0x79,0x00,0x10,0x06,0x01,0xff,0x7a,0x00,0x01,0x00,0x01,0x00,0x01,0x00, - 0xc6,0xe5,0xf9,0x14,0xe4,0x6f,0x0d,0xe3,0x39,0x08,0xe2,0x22,0x01,0xc1,0xd0,0x24, - 0xcf,0x86,0x55,0x04,0x01,0x00,0xd4,0x07,0x63,0xd8,0x43,0x01,0x00,0x93,0x13,0x52, - 0x04,0x01,0x00,0x91,0x0b,0x10,0x04,0x01,0x00,0x01,0xff,0xce,0xbc,0x00,0x01,0x00, - 0x01,0x00,0xcf,0x86,0xe5,0xb3,0x44,0xd4,0x7f,0xd3,0x3f,0xd2,0x20,0xd1,0x10,0x10, - 0x08,0x01,0xff,0x61,0xcc,0x80,0x00,0x01,0xff,0x61,0xcc,0x81,0x00,0x10,0x08,0x01, - 0xff,0x61,0xcc,0x82,0x00,0x01,0xff,0x61,0xcc,0x83,0x00,0xd1,0x10,0x10,0x08,0x01, - 0xff,0x61,0xcc,0x88,0x00,0x01,0xff,0x61,0xcc,0x8a,0x00,0x10,0x07,0x01,0xff,0xc3, - 0xa6,0x00,0x01,0xff,0x63,0xcc,0xa7,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff, - 0x65,0xcc,0x80,0x00,0x01,0xff,0x65,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x65,0xcc, - 0x82,0x00,0x01,0xff,0x65,0xcc,0x88,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x69,0xcc, - 0x80,0x00,0x01,0xff,0x69,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x69,0xcc,0x82,0x00, - 0x01,0xff,0x69,0xcc,0x88,0x00,0xd3,0x3b,0xd2,0x1f,0xd1,0x0f,0x10,0x07,0x01,0xff, - 0xc3,0xb0,0x00,0x01,0xff,0x6e,0xcc,0x83,0x00,0x10,0x08,0x01,0xff,0x6f,0xcc,0x80, - 0x00,0x01,0xff,0x6f,0xcc,0x81,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x6f,0xcc,0x82, - 0x00,0x01,0xff,0x6f,0xcc,0x83,0x00,0x10,0x08,0x01,0xff,0x6f,0xcc,0x88,0x00,0x01, - 0x00,0xd2,0x1f,0xd1,0x0f,0x10,0x07,0x01,0xff,0xc3,0xb8,0x00,0x01,0xff,0x75,0xcc, - 0x80,0x00,0x10,0x08,0x01,0xff,0x75,0xcc,0x81,0x00,0x01,0xff,0x75,0xcc,0x82,0x00, - 0xd1,0x10,0x10,0x08,0x01,0xff,0x75,0xcc,0x88,0x00,0x01,0xff,0x79,0xcc,0x81,0x00, - 0x10,0x07,0x01,0xff,0xc3,0xbe,0x00,0x01,0xff,0x73,0x73,0x00,0xe1,0xd4,0x03,0xe0, - 0xeb,0x01,0xcf,0x86,0xd5,0xfb,0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08, - 0x01,0xff,0x61,0xcc,0x84,0x00,0x01,0xff,0x61,0xcc,0x84,0x00,0x10,0x08,0x01,0xff, - 0x61,0xcc,0x86,0x00,0x01,0xff,0x61,0xcc,0x86,0x00,0xd1,0x10,0x10,0x08,0x01,0xff, - 0x61,0xcc,0xa8,0x00,0x01,0xff,0x61,0xcc,0xa8,0x00,0x10,0x08,0x01,0xff,0x63,0xcc, - 0x81,0x00,0x01,0xff,0x63,0xcc,0x81,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff, - 0x63,0xcc,0x82,0x00,0x01,0xff,0x63,0xcc,0x82,0x00,0x10,0x08,0x01,0xff,0x63,0xcc, - 0x87,0x00,0x01,0xff,0x63,0xcc,0x87,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x63,0xcc, - 0x8c,0x00,0x01,0xff,0x63,0xcc,0x8c,0x00,0x10,0x08,0x01,0xff,0x64,0xcc,0x8c,0x00, - 0x01,0xff,0x64,0xcc,0x8c,0x00,0xd3,0x3b,0xd2,0x1b,0xd1,0x0b,0x10,0x07,0x01,0xff, - 0xc4,0x91,0x00,0x01,0x00,0x10,0x08,0x01,0xff,0x65,0xcc,0x84,0x00,0x01,0xff,0x65, - 0xcc,0x84,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x65,0xcc,0x86,0x00,0x01,0xff,0x65, - 0xcc,0x86,0x00,0x10,0x08,0x01,0xff,0x65,0xcc,0x87,0x00,0x01,0xff,0x65,0xcc,0x87, - 0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x65,0xcc,0xa8,0x00,0x01,0xff,0x65, - 0xcc,0xa8,0x00,0x10,0x08,0x01,0xff,0x65,0xcc,0x8c,0x00,0x01,0xff,0x65,0xcc,0x8c, - 0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x67,0xcc,0x82,0x00,0x01,0xff,0x67,0xcc,0x82, - 0x00,0x10,0x08,0x01,0xff,0x67,0xcc,0x86,0x00,0x01,0xff,0x67,0xcc,0x86,0x00,0xd4, - 0x7b,0xd3,0x3b,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x67,0xcc,0x87,0x00,0x01, - 0xff,0x67,0xcc,0x87,0x00,0x10,0x08,0x01,0xff,0x67,0xcc,0xa7,0x00,0x01,0xff,0x67, - 0xcc,0xa7,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x68,0xcc,0x82,0x00,0x01,0xff,0x68, - 0xcc,0x82,0x00,0x10,0x07,0x01,0xff,0xc4,0xa7,0x00,0x01,0x00,0xd2,0x20,0xd1,0x10, - 0x10,0x08,0x01,0xff,0x69,0xcc,0x83,0x00,0x01,0xff,0x69,0xcc,0x83,0x00,0x10,0x08, - 0x01,0xff,0x69,0xcc,0x84,0x00,0x01,0xff,0x69,0xcc,0x84,0x00,0xd1,0x10,0x10,0x08, - 0x01,0xff,0x69,0xcc,0x86,0x00,0x01,0xff,0x69,0xcc,0x86,0x00,0x10,0x08,0x01,0xff, - 0x69,0xcc,0xa8,0x00,0x01,0xff,0x69,0xcc,0xa8,0x00,0xd3,0x37,0xd2,0x17,0xd1,0x0c, - 0x10,0x08,0x01,0xff,0x69,0xcc,0x87,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xc4,0xb3, - 0x00,0x01,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x6a,0xcc,0x82,0x00,0x01,0xff,0x6a, - 0xcc,0x82,0x00,0x10,0x08,0x01,0xff,0x6b,0xcc,0xa7,0x00,0x01,0xff,0x6b,0xcc,0xa7, - 0x00,0xd2,0x1c,0xd1,0x0c,0x10,0x04,0x01,0x00,0x01,0xff,0x6c,0xcc,0x81,0x00,0x10, - 0x08,0x01,0xff,0x6c,0xcc,0x81,0x00,0x01,0xff,0x6c,0xcc,0xa7,0x00,0xd1,0x10,0x10, - 0x08,0x01,0xff,0x6c,0xcc,0xa7,0x00,0x01,0xff,0x6c,0xcc,0x8c,0x00,0x10,0x08,0x01, - 0xff,0x6c,0xcc,0x8c,0x00,0x01,0xff,0xc5,0x80,0x00,0xcf,0x86,0xd5,0xed,0xd4,0x72, - 0xd3,0x37,0xd2,0x17,0xd1,0x0b,0x10,0x04,0x01,0x00,0x01,0xff,0xc5,0x82,0x00,0x10, - 0x04,0x01,0x00,0x01,0xff,0x6e,0xcc,0x81,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x6e, - 0xcc,0x81,0x00,0x01,0xff,0x6e,0xcc,0xa7,0x00,0x10,0x08,0x01,0xff,0x6e,0xcc,0xa7, - 0x00,0x01,0xff,0x6e,0xcc,0x8c,0x00,0xd2,0x1b,0xd1,0x10,0x10,0x08,0x01,0xff,0x6e, - 0xcc,0x8c,0x00,0x01,0xff,0xca,0xbc,0x6e,0x00,0x10,0x07,0x01,0xff,0xc5,0x8b,0x00, - 0x01,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x6f,0xcc,0x84,0x00,0x01,0xff,0x6f,0xcc, - 0x84,0x00,0x10,0x08,0x01,0xff,0x6f,0xcc,0x86,0x00,0x01,0xff,0x6f,0xcc,0x86,0x00, - 0xd3,0x3b,0xd2,0x1b,0xd1,0x10,0x10,0x08,0x01,0xff,0x6f,0xcc,0x8b,0x00,0x01,0xff, - 0x6f,0xcc,0x8b,0x00,0x10,0x07,0x01,0xff,0xc5,0x93,0x00,0x01,0x00,0xd1,0x10,0x10, - 0x08,0x01,0xff,0x72,0xcc,0x81,0x00,0x01,0xff,0x72,0xcc,0x81,0x00,0x10,0x08,0x01, - 0xff,0x72,0xcc,0xa7,0x00,0x01,0xff,0x72,0xcc,0xa7,0x00,0xd2,0x20,0xd1,0x10,0x10, - 0x08,0x01,0xff,0x72,0xcc,0x8c,0x00,0x01,0xff,0x72,0xcc,0x8c,0x00,0x10,0x08,0x01, - 0xff,0x73,0xcc,0x81,0x00,0x01,0xff,0x73,0xcc,0x81,0x00,0xd1,0x10,0x10,0x08,0x01, - 0xff,0x73,0xcc,0x82,0x00,0x01,0xff,0x73,0xcc,0x82,0x00,0x10,0x08,0x01,0xff,0x73, - 0xcc,0xa7,0x00,0x01,0xff,0x73,0xcc,0xa7,0x00,0xd4,0x7b,0xd3,0x3b,0xd2,0x20,0xd1, - 0x10,0x10,0x08,0x01,0xff,0x73,0xcc,0x8c,0x00,0x01,0xff,0x73,0xcc,0x8c,0x00,0x10, - 0x08,0x01,0xff,0x74,0xcc,0xa7,0x00,0x01,0xff,0x74,0xcc,0xa7,0x00,0xd1,0x10,0x10, - 0x08,0x01,0xff,0x74,0xcc,0x8c,0x00,0x01,0xff,0x74,0xcc,0x8c,0x00,0x10,0x07,0x01, - 0xff,0xc5,0xa7,0x00,0x01,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x75,0xcc, - 0x83,0x00,0x01,0xff,0x75,0xcc,0x83,0x00,0x10,0x08,0x01,0xff,0x75,0xcc,0x84,0x00, - 0x01,0xff,0x75,0xcc,0x84,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x75,0xcc,0x86,0x00, - 0x01,0xff,0x75,0xcc,0x86,0x00,0x10,0x08,0x01,0xff,0x75,0xcc,0x8a,0x00,0x01,0xff, - 0x75,0xcc,0x8a,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x75,0xcc, - 0x8b,0x00,0x01,0xff,0x75,0xcc,0x8b,0x00,0x10,0x08,0x01,0xff,0x75,0xcc,0xa8,0x00, - 0x01,0xff,0x75,0xcc,0xa8,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x77,0xcc,0x82,0x00, - 0x01,0xff,0x77,0xcc,0x82,0x00,0x10,0x08,0x01,0xff,0x79,0xcc,0x82,0x00,0x01,0xff, - 0x79,0xcc,0x82,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x79,0xcc,0x88,0x00, - 0x01,0xff,0x7a,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x7a,0xcc,0x81,0x00,0x01,0xff, - 0x7a,0xcc,0x87,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x7a,0xcc,0x87,0x00,0x01,0xff, - 0x7a,0xcc,0x8c,0x00,0x10,0x08,0x01,0xff,0x7a,0xcc,0x8c,0x00,0x01,0xff,0x73,0x00, - 0xe0,0x65,0x01,0xcf,0x86,0xd5,0xb4,0xd4,0x5a,0xd3,0x2f,0xd2,0x16,0xd1,0x0b,0x10, - 0x04,0x01,0x00,0x01,0xff,0xc9,0x93,0x00,0x10,0x07,0x01,0xff,0xc6,0x83,0x00,0x01, - 0x00,0xd1,0x0b,0x10,0x07,0x01,0xff,0xc6,0x85,0x00,0x01,0x00,0x10,0x07,0x01,0xff, - 0xc9,0x94,0x00,0x01,0xff,0xc6,0x88,0x00,0xd2,0x19,0xd1,0x0b,0x10,0x04,0x01,0x00, - 0x01,0xff,0xc9,0x96,0x00,0x10,0x07,0x01,0xff,0xc9,0x97,0x00,0x01,0xff,0xc6,0x8c, - 0x00,0x51,0x04,0x01,0x00,0x10,0x07,0x01,0xff,0xc7,0x9d,0x00,0x01,0xff,0xc9,0x99, - 0x00,0xd3,0x32,0xd2,0x19,0xd1,0x0e,0x10,0x07,0x01,0xff,0xc9,0x9b,0x00,0x01,0xff, - 0xc6,0x92,0x00,0x10,0x04,0x01,0x00,0x01,0xff,0xc9,0xa0,0x00,0xd1,0x0b,0x10,0x07, - 0x01,0xff,0xc9,0xa3,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xc9,0xa9,0x00,0x01,0xff, - 0xc9,0xa8,0x00,0xd2,0x0f,0x91,0x0b,0x10,0x07,0x01,0xff,0xc6,0x99,0x00,0x01,0x00, - 0x01,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff,0xc9,0xaf,0x00,0x01,0xff,0xc9,0xb2,0x00, - 0x10,0x04,0x01,0x00,0x01,0xff,0xc9,0xb5,0x00,0xd4,0x5d,0xd3,0x34,0xd2,0x1b,0xd1, - 0x10,0x10,0x08,0x01,0xff,0x6f,0xcc,0x9b,0x00,0x01,0xff,0x6f,0xcc,0x9b,0x00,0x10, - 0x07,0x01,0xff,0xc6,0xa3,0x00,0x01,0x00,0xd1,0x0b,0x10,0x07,0x01,0xff,0xc6,0xa5, - 0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xca,0x80,0x00,0x01,0xff,0xc6,0xa8,0x00,0xd2, - 0x0f,0x91,0x0b,0x10,0x04,0x01,0x00,0x01,0xff,0xca,0x83,0x00,0x01,0x00,0xd1,0x0b, - 0x10,0x07,0x01,0xff,0xc6,0xad,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xca,0x88,0x00, - 0x01,0xff,0x75,0xcc,0x9b,0x00,0xd3,0x33,0xd2,0x1d,0xd1,0x0f,0x10,0x08,0x01,0xff, - 0x75,0xcc,0x9b,0x00,0x01,0xff,0xca,0x8a,0x00,0x10,0x07,0x01,0xff,0xca,0x8b,0x00, - 0x01,0xff,0xc6,0xb4,0x00,0xd1,0x0b,0x10,0x04,0x01,0x00,0x01,0xff,0xc6,0xb6,0x00, - 0x10,0x04,0x01,0x00,0x01,0xff,0xca,0x92,0x00,0xd2,0x0f,0x91,0x0b,0x10,0x07,0x01, - 0xff,0xc6,0xb9,0x00,0x01,0x00,0x01,0x00,0x91,0x0b,0x10,0x07,0x01,0xff,0xc6,0xbd, - 0x00,0x01,0x00,0x01,0x00,0xcf,0x86,0xd5,0xd4,0xd4,0x44,0xd3,0x16,0x52,0x04,0x01, - 0x00,0x51,0x07,0x01,0xff,0xc7,0x86,0x00,0x10,0x04,0x01,0x00,0x01,0xff,0xc7,0x89, - 0x00,0xd2,0x12,0x91,0x0b,0x10,0x07,0x01,0xff,0xc7,0x89,0x00,0x01,0x00,0x01,0xff, - 0xc7,0x8c,0x00,0xd1,0x0c,0x10,0x04,0x01,0x00,0x01,0xff,0x61,0xcc,0x8c,0x00,0x10, - 0x08,0x01,0xff,0x61,0xcc,0x8c,0x00,0x01,0xff,0x69,0xcc,0x8c,0x00,0xd3,0x46,0xd2, - 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x69,0xcc,0x8c,0x00,0x01,0xff,0x6f,0xcc,0x8c, - 0x00,0x10,0x08,0x01,0xff,0x6f,0xcc,0x8c,0x00,0x01,0xff,0x75,0xcc,0x8c,0x00,0xd1, - 0x12,0x10,0x08,0x01,0xff,0x75,0xcc,0x8c,0x00,0x01,0xff,0x75,0xcc,0x88,0xcc,0x84, - 0x00,0x10,0x0a,0x01,0xff,0x75,0xcc,0x88,0xcc,0x84,0x00,0x01,0xff,0x75,0xcc,0x88, - 0xcc,0x81,0x00,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x75,0xcc,0x88,0xcc,0x81, - 0x00,0x01,0xff,0x75,0xcc,0x88,0xcc,0x8c,0x00,0x10,0x0a,0x01,0xff,0x75,0xcc,0x88, - 0xcc,0x8c,0x00,0x01,0xff,0x75,0xcc,0x88,0xcc,0x80,0x00,0xd1,0x0e,0x10,0x0a,0x01, - 0xff,0x75,0xcc,0x88,0xcc,0x80,0x00,0x01,0x00,0x10,0x0a,0x01,0xff,0x61,0xcc,0x88, - 0xcc,0x84,0x00,0x01,0xff,0x61,0xcc,0x88,0xcc,0x84,0x00,0xd4,0x87,0xd3,0x41,0xd2, - 0x26,0xd1,0x14,0x10,0x0a,0x01,0xff,0x61,0xcc,0x87,0xcc,0x84,0x00,0x01,0xff,0x61, - 0xcc,0x87,0xcc,0x84,0x00,0x10,0x09,0x01,0xff,0xc3,0xa6,0xcc,0x84,0x00,0x01,0xff, - 0xc3,0xa6,0xcc,0x84,0x00,0xd1,0x0b,0x10,0x07,0x01,0xff,0xc7,0xa5,0x00,0x01,0x00, - 0x10,0x08,0x01,0xff,0x67,0xcc,0x8c,0x00,0x01,0xff,0x67,0xcc,0x8c,0x00,0xd2,0x20, - 0xd1,0x10,0x10,0x08,0x01,0xff,0x6b,0xcc,0x8c,0x00,0x01,0xff,0x6b,0xcc,0x8c,0x00, - 0x10,0x08,0x01,0xff,0x6f,0xcc,0xa8,0x00,0x01,0xff,0x6f,0xcc,0xa8,0x00,0xd1,0x14, - 0x10,0x0a,0x01,0xff,0x6f,0xcc,0xa8,0xcc,0x84,0x00,0x01,0xff,0x6f,0xcc,0xa8,0xcc, - 0x84,0x00,0x10,0x09,0x01,0xff,0xca,0x92,0xcc,0x8c,0x00,0x01,0xff,0xca,0x92,0xcc, - 0x8c,0x00,0xd3,0x38,0xd2,0x1a,0xd1,0x0f,0x10,0x08,0x01,0xff,0x6a,0xcc,0x8c,0x00, - 0x01,0xff,0xc7,0xb3,0x00,0x10,0x07,0x01,0xff,0xc7,0xb3,0x00,0x01,0x00,0xd1,0x10, - 0x10,0x08,0x01,0xff,0x67,0xcc,0x81,0x00,0x01,0xff,0x67,0xcc,0x81,0x00,0x10,0x07, - 0x04,0xff,0xc6,0x95,0x00,0x04,0xff,0xc6,0xbf,0x00,0xd2,0x24,0xd1,0x10,0x10,0x08, - 0x04,0xff,0x6e,0xcc,0x80,0x00,0x04,0xff,0x6e,0xcc,0x80,0x00,0x10,0x0a,0x01,0xff, - 0x61,0xcc,0x8a,0xcc,0x81,0x00,0x01,0xff,0x61,0xcc,0x8a,0xcc,0x81,0x00,0xd1,0x12, - 0x10,0x09,0x01,0xff,0xc3,0xa6,0xcc,0x81,0x00,0x01,0xff,0xc3,0xa6,0xcc,0x81,0x00, - 0x10,0x09,0x01,0xff,0xc3,0xb8,0xcc,0x81,0x00,0x01,0xff,0xc3,0xb8,0xcc,0x81,0x00, - 0xe2,0x31,0x02,0xe1,0xc3,0x44,0xe0,0xc8,0x01,0xcf,0x86,0xd5,0xfb,0xd4,0x80,0xd3, - 0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x61,0xcc,0x8f,0x00,0x01,0xff,0x61, - 0xcc,0x8f,0x00,0x10,0x08,0x01,0xff,0x61,0xcc,0x91,0x00,0x01,0xff,0x61,0xcc,0x91, - 0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x65,0xcc,0x8f,0x00,0x01,0xff,0x65,0xcc,0x8f, - 0x00,0x10,0x08,0x01,0xff,0x65,0xcc,0x91,0x00,0x01,0xff,0x65,0xcc,0x91,0x00,0xd2, - 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x69,0xcc,0x8f,0x00,0x01,0xff,0x69,0xcc,0x8f, - 0x00,0x10,0x08,0x01,0xff,0x69,0xcc,0x91,0x00,0x01,0xff,0x69,0xcc,0x91,0x00,0xd1, - 0x10,0x10,0x08,0x01,0xff,0x6f,0xcc,0x8f,0x00,0x01,0xff,0x6f,0xcc,0x8f,0x00,0x10, - 0x08,0x01,0xff,0x6f,0xcc,0x91,0x00,0x01,0xff,0x6f,0xcc,0x91,0x00,0xd3,0x40,0xd2, - 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x72,0xcc,0x8f,0x00,0x01,0xff,0x72,0xcc,0x8f, - 0x00,0x10,0x08,0x01,0xff,0x72,0xcc,0x91,0x00,0x01,0xff,0x72,0xcc,0x91,0x00,0xd1, - 0x10,0x10,0x08,0x01,0xff,0x75,0xcc,0x8f,0x00,0x01,0xff,0x75,0xcc,0x8f,0x00,0x10, - 0x08,0x01,0xff,0x75,0xcc,0x91,0x00,0x01,0xff,0x75,0xcc,0x91,0x00,0xd2,0x20,0xd1, - 0x10,0x10,0x08,0x04,0xff,0x73,0xcc,0xa6,0x00,0x04,0xff,0x73,0xcc,0xa6,0x00,0x10, - 0x08,0x04,0xff,0x74,0xcc,0xa6,0x00,0x04,0xff,0x74,0xcc,0xa6,0x00,0xd1,0x0b,0x10, - 0x07,0x04,0xff,0xc8,0x9d,0x00,0x04,0x00,0x10,0x08,0x04,0xff,0x68,0xcc,0x8c,0x00, - 0x04,0xff,0x68,0xcc,0x8c,0x00,0xd4,0x79,0xd3,0x31,0xd2,0x16,0xd1,0x0b,0x10,0x07, - 0x06,0xff,0xc6,0x9e,0x00,0x07,0x00,0x10,0x07,0x04,0xff,0xc8,0xa3,0x00,0x04,0x00, - 0xd1,0x0b,0x10,0x07,0x04,0xff,0xc8,0xa5,0x00,0x04,0x00,0x10,0x08,0x04,0xff,0x61, - 0xcc,0x87,0x00,0x04,0xff,0x61,0xcc,0x87,0x00,0xd2,0x24,0xd1,0x10,0x10,0x08,0x04, - 0xff,0x65,0xcc,0xa7,0x00,0x04,0xff,0x65,0xcc,0xa7,0x00,0x10,0x0a,0x04,0xff,0x6f, - 0xcc,0x88,0xcc,0x84,0x00,0x04,0xff,0x6f,0xcc,0x88,0xcc,0x84,0x00,0xd1,0x14,0x10, - 0x0a,0x04,0xff,0x6f,0xcc,0x83,0xcc,0x84,0x00,0x04,0xff,0x6f,0xcc,0x83,0xcc,0x84, - 0x00,0x10,0x08,0x04,0xff,0x6f,0xcc,0x87,0x00,0x04,0xff,0x6f,0xcc,0x87,0x00,0xd3, - 0x27,0xe2,0x21,0x43,0xd1,0x14,0x10,0x0a,0x04,0xff,0x6f,0xcc,0x87,0xcc,0x84,0x00, - 0x04,0xff,0x6f,0xcc,0x87,0xcc,0x84,0x00,0x10,0x08,0x04,0xff,0x79,0xcc,0x84,0x00, - 0x04,0xff,0x79,0xcc,0x84,0x00,0xd2,0x13,0x51,0x04,0x08,0x00,0x10,0x08,0x08,0xff, - 0xe2,0xb1,0xa5,0x00,0x08,0xff,0xc8,0xbc,0x00,0xd1,0x0b,0x10,0x04,0x08,0x00,0x08, - 0xff,0xc6,0x9a,0x00,0x10,0x08,0x08,0xff,0xe2,0xb1,0xa6,0x00,0x08,0x00,0xcf,0x86, - 0x95,0x5f,0x94,0x5b,0xd3,0x2f,0xd2,0x16,0xd1,0x0b,0x10,0x04,0x08,0x00,0x08,0xff, - 0xc9,0x82,0x00,0x10,0x04,0x09,0x00,0x09,0xff,0xc6,0x80,0x00,0xd1,0x0e,0x10,0x07, - 0x09,0xff,0xca,0x89,0x00,0x09,0xff,0xca,0x8c,0x00,0x10,0x07,0x09,0xff,0xc9,0x87, - 0x00,0x09,0x00,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x09,0xff,0xc9,0x89,0x00,0x09,0x00, - 0x10,0x07,0x09,0xff,0xc9,0x8b,0x00,0x09,0x00,0xd1,0x0b,0x10,0x07,0x09,0xff,0xc9, - 0x8d,0x00,0x09,0x00,0x10,0x07,0x09,0xff,0xc9,0x8f,0x00,0x09,0x00,0x01,0x00,0x01, - 0x00,0xd1,0x8b,0xd0,0x0c,0xcf,0x86,0xe5,0x10,0x43,0x64,0xef,0x42,0x01,0xe6,0xcf, - 0x86,0xd5,0x2a,0xe4,0x99,0x43,0xe3,0x7f,0x43,0xd2,0x11,0xe1,0x5e,0x43,0x10,0x07, - 0x01,0xff,0xcc,0x80,0x00,0x01,0xff,0xcc,0x81,0x00,0xe1,0x65,0x43,0x10,0x09,0x01, - 0xff,0xcc,0x88,0xcc,0x81,0x00,0x01,0xff,0xce,0xb9,0x00,0xd4,0x0f,0x93,0x0b,0x92, - 0x07,0x61,0xab,0x43,0x01,0xea,0x06,0xe6,0x06,0xe6,0xd3,0x2c,0xd2,0x16,0xd1,0x0b, - 0x10,0x07,0x0a,0xff,0xcd,0xb1,0x00,0x0a,0x00,0x10,0x07,0x0a,0xff,0xcd,0xb3,0x00, - 0x0a,0x00,0xd1,0x0b,0x10,0x07,0x01,0xff,0xca,0xb9,0x00,0x01,0x00,0x10,0x07,0x0a, - 0xff,0xcd,0xb7,0x00,0x0a,0x00,0xd2,0x07,0x61,0x97,0x43,0x00,0x00,0x51,0x04,0x09, - 0x00,0x10,0x06,0x01,0xff,0x3b,0x00,0x10,0xff,0xcf,0xb3,0x00,0xe0,0x31,0x01,0xcf, - 0x86,0xd5,0xd3,0xd4,0x5f,0xd3,0x21,0x52,0x04,0x00,0x00,0xd1,0x0d,0x10,0x04,0x01, - 0x00,0x01,0xff,0xc2,0xa8,0xcc,0x81,0x00,0x10,0x09,0x01,0xff,0xce,0xb1,0xcc,0x81, - 0x00,0x01,0xff,0xc2,0xb7,0x00,0xd2,0x1f,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb5, - 0xcc,0x81,0x00,0x01,0xff,0xce,0xb7,0xcc,0x81,0x00,0x10,0x09,0x01,0xff,0xce,0xb9, - 0xcc,0x81,0x00,0x00,0x00,0xd1,0x0d,0x10,0x09,0x01,0xff,0xce,0xbf,0xcc,0x81,0x00, - 0x00,0x00,0x10,0x09,0x01,0xff,0xcf,0x85,0xcc,0x81,0x00,0x01,0xff,0xcf,0x89,0xcc, - 0x81,0x00,0xd3,0x3c,0xd2,0x20,0xd1,0x12,0x10,0x0b,0x01,0xff,0xce,0xb9,0xcc,0x88, - 0xcc,0x81,0x00,0x01,0xff,0xce,0xb1,0x00,0x10,0x07,0x01,0xff,0xce,0xb2,0x00,0x01, - 0xff,0xce,0xb3,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff,0xce,0xb4,0x00,0x01,0xff,0xce, - 0xb5,0x00,0x10,0x07,0x01,0xff,0xce,0xb6,0x00,0x01,0xff,0xce,0xb7,0x00,0xd2,0x1c, - 0xd1,0x0e,0x10,0x07,0x01,0xff,0xce,0xb8,0x00,0x01,0xff,0xce,0xb9,0x00,0x10,0x07, - 0x01,0xff,0xce,0xba,0x00,0x01,0xff,0xce,0xbb,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff, - 0xce,0xbc,0x00,0x01,0xff,0xce,0xbd,0x00,0x10,0x07,0x01,0xff,0xce,0xbe,0x00,0x01, - 0xff,0xce,0xbf,0x00,0xe4,0x85,0x43,0xd3,0x35,0xd2,0x19,0xd1,0x0e,0x10,0x07,0x01, - 0xff,0xcf,0x80,0x00,0x01,0xff,0xcf,0x81,0x00,0x10,0x04,0x00,0x00,0x01,0xff,0xcf, - 0x83,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff,0xcf,0x84,0x00,0x01,0xff,0xcf,0x85,0x00, - 0x10,0x07,0x01,0xff,0xcf,0x86,0x00,0x01,0xff,0xcf,0x87,0x00,0xe2,0x2b,0x43,0xd1, - 0x0e,0x10,0x07,0x01,0xff,0xcf,0x88,0x00,0x01,0xff,0xcf,0x89,0x00,0x10,0x09,0x01, - 0xff,0xce,0xb9,0xcc,0x88,0x00,0x01,0xff,0xcf,0x85,0xcc,0x88,0x00,0xcf,0x86,0xd5, - 0x94,0xd4,0x3c,0xd3,0x13,0x92,0x0f,0x51,0x04,0x01,0x00,0x10,0x07,0x01,0xff,0xcf, - 0x83,0x00,0x01,0x00,0x01,0x00,0xd2,0x07,0x61,0x3a,0x43,0x01,0x00,0xd1,0x12,0x10, - 0x09,0x01,0xff,0xce,0xbf,0xcc,0x81,0x00,0x01,0xff,0xcf,0x85,0xcc,0x81,0x00,0x10, - 0x09,0x01,0xff,0xcf,0x89,0xcc,0x81,0x00,0x0a,0xff,0xcf,0x97,0x00,0xd3,0x2c,0xd2, - 0x11,0xe1,0x46,0x43,0x10,0x07,0x01,0xff,0xce,0xb2,0x00,0x01,0xff,0xce,0xb8,0x00, - 0xd1,0x10,0x10,0x09,0x01,0xff,0xcf,0x92,0xcc,0x88,0x00,0x01,0xff,0xcf,0x86,0x00, - 0x10,0x07,0x01,0xff,0xcf,0x80,0x00,0x04,0x00,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x06, - 0xff,0xcf,0x99,0x00,0x06,0x00,0x10,0x07,0x01,0xff,0xcf,0x9b,0x00,0x04,0x00,0xd1, - 0x0b,0x10,0x07,0x01,0xff,0xcf,0x9d,0x00,0x04,0x00,0x10,0x07,0x01,0xff,0xcf,0x9f, - 0x00,0x04,0x00,0xd4,0x58,0xd3,0x2c,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x01,0xff,0xcf, - 0xa1,0x00,0x04,0x00,0x10,0x07,0x01,0xff,0xcf,0xa3,0x00,0x01,0x00,0xd1,0x0b,0x10, - 0x07,0x01,0xff,0xcf,0xa5,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xcf,0xa7,0x00,0x01, - 0x00,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x01,0xff,0xcf,0xa9,0x00,0x01,0x00,0x10,0x07, - 0x01,0xff,0xcf,0xab,0x00,0x01,0x00,0xd1,0x0b,0x10,0x07,0x01,0xff,0xcf,0xad,0x00, - 0x01,0x00,0x10,0x07,0x01,0xff,0xcf,0xaf,0x00,0x01,0x00,0xd3,0x2b,0xd2,0x12,0x91, - 0x0e,0x10,0x07,0x01,0xff,0xce,0xba,0x00,0x01,0xff,0xcf,0x81,0x00,0x01,0x00,0xd1, - 0x0e,0x10,0x07,0x05,0xff,0xce,0xb8,0x00,0x05,0xff,0xce,0xb5,0x00,0x10,0x04,0x06, - 0x00,0x07,0xff,0xcf,0xb8,0x00,0xd2,0x16,0xd1,0x0b,0x10,0x04,0x07,0x00,0x07,0xff, - 0xcf,0xb2,0x00,0x10,0x07,0x07,0xff,0xcf,0xbb,0x00,0x07,0x00,0xd1,0x0b,0x10,0x04, - 0x08,0x00,0x08,0xff,0xcd,0xbb,0x00,0x10,0x07,0x08,0xff,0xcd,0xbc,0x00,0x08,0xff, - 0xcd,0xbd,0x00,0xe3,0xed,0x46,0xe2,0x3d,0x05,0xe1,0x27,0x02,0xe0,0x66,0x01,0xcf, - 0x86,0xd5,0xf0,0xd4,0x7e,0xd3,0x40,0xd2,0x22,0xd1,0x12,0x10,0x09,0x04,0xff,0xd0, - 0xb5,0xcc,0x80,0x00,0x01,0xff,0xd0,0xb5,0xcc,0x88,0x00,0x10,0x07,0x01,0xff,0xd1, - 0x92,0x00,0x01,0xff,0xd0,0xb3,0xcc,0x81,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd1, - 0x94,0x00,0x01,0xff,0xd1,0x95,0x00,0x10,0x07,0x01,0xff,0xd1,0x96,0x00,0x01,0xff, - 0xd1,0x96,0xcc,0x88,0x00,0xd2,0x1c,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd1,0x98,0x00, - 0x01,0xff,0xd1,0x99,0x00,0x10,0x07,0x01,0xff,0xd1,0x9a,0x00,0x01,0xff,0xd1,0x9b, - 0x00,0xd1,0x12,0x10,0x09,0x01,0xff,0xd0,0xba,0xcc,0x81,0x00,0x04,0xff,0xd0,0xb8, - 0xcc,0x80,0x00,0x10,0x09,0x01,0xff,0xd1,0x83,0xcc,0x86,0x00,0x01,0xff,0xd1,0x9f, - 0x00,0xd3,0x38,0xd2,0x1c,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd0,0xb0,0x00,0x01,0xff, - 0xd0,0xb1,0x00,0x10,0x07,0x01,0xff,0xd0,0xb2,0x00,0x01,0xff,0xd0,0xb3,0x00,0xd1, - 0x0e,0x10,0x07,0x01,0xff,0xd0,0xb4,0x00,0x01,0xff,0xd0,0xb5,0x00,0x10,0x07,0x01, - 0xff,0xd0,0xb6,0x00,0x01,0xff,0xd0,0xb7,0x00,0xd2,0x1e,0xd1,0x10,0x10,0x07,0x01, - 0xff,0xd0,0xb8,0x00,0x01,0xff,0xd0,0xb8,0xcc,0x86,0x00,0x10,0x07,0x01,0xff,0xd0, - 0xba,0x00,0x01,0xff,0xd0,0xbb,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd0,0xbc,0x00, - 0x01,0xff,0xd0,0xbd,0x00,0x10,0x07,0x01,0xff,0xd0,0xbe,0x00,0x01,0xff,0xd0,0xbf, - 0x00,0xe4,0x25,0x42,0xd3,0x38,0xd2,0x1c,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd1,0x80, - 0x00,0x01,0xff,0xd1,0x81,0x00,0x10,0x07,0x01,0xff,0xd1,0x82,0x00,0x01,0xff,0xd1, - 0x83,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd1,0x84,0x00,0x01,0xff,0xd1,0x85,0x00, - 0x10,0x07,0x01,0xff,0xd1,0x86,0x00,0x01,0xff,0xd1,0x87,0x00,0xd2,0x1c,0xd1,0x0e, - 0x10,0x07,0x01,0xff,0xd1,0x88,0x00,0x01,0xff,0xd1,0x89,0x00,0x10,0x07,0x01,0xff, - 0xd1,0x8a,0x00,0x01,0xff,0xd1,0x8b,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd1,0x8c, - 0x00,0x01,0xff,0xd1,0x8d,0x00,0x10,0x07,0x01,0xff,0xd1,0x8e,0x00,0x01,0xff,0xd1, - 0x8f,0x00,0xcf,0x86,0xd5,0x07,0x64,0xcf,0x41,0x01,0x00,0xd4,0x58,0xd3,0x2c,0xd2, - 0x16,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd1,0xa1,0x00,0x01,0x00,0x10,0x07,0x01,0xff, - 0xd1,0xa3,0x00,0x01,0x00,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd1,0xa5,0x00,0x01,0x00, - 0x10,0x07,0x01,0xff,0xd1,0xa7,0x00,0x01,0x00,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x01, - 0xff,0xd1,0xa9,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xd1,0xab,0x00,0x01,0x00,0xd1, - 0x0b,0x10,0x07,0x01,0xff,0xd1,0xad,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xd1,0xaf, - 0x00,0x01,0x00,0xd3,0x33,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd1,0xb1,0x00, - 0x01,0x00,0x10,0x07,0x01,0xff,0xd1,0xb3,0x00,0x01,0x00,0xd1,0x0b,0x10,0x07,0x01, - 0xff,0xd1,0xb5,0x00,0x01,0x00,0x10,0x09,0x01,0xff,0xd1,0xb5,0xcc,0x8f,0x00,0x01, - 0xff,0xd1,0xb5,0xcc,0x8f,0x00,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd1,0xb9, - 0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xd1,0xbb,0x00,0x01,0x00,0xd1,0x0b,0x10,0x07, - 0x01,0xff,0xd1,0xbd,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xd1,0xbf,0x00,0x01,0x00, - 0xe0,0x41,0x01,0xcf,0x86,0xd5,0x8e,0xd4,0x36,0xd3,0x11,0xe2,0x91,0x41,0xe1,0x88, - 0x41,0x10,0x07,0x01,0xff,0xd2,0x81,0x00,0x01,0x00,0xd2,0x0f,0x51,0x04,0x04,0x00, - 0x10,0x07,0x06,0xff,0xd2,0x8b,0x00,0x06,0x00,0xd1,0x0b,0x10,0x07,0x04,0xff,0xd2, - 0x8d,0x00,0x04,0x00,0x10,0x07,0x04,0xff,0xd2,0x8f,0x00,0x04,0x00,0xd3,0x2c,0xd2, - 0x16,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd2,0x91,0x00,0x01,0x00,0x10,0x07,0x01,0xff, - 0xd2,0x93,0x00,0x01,0x00,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd2,0x95,0x00,0x01,0x00, - 0x10,0x07,0x01,0xff,0xd2,0x97,0x00,0x01,0x00,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x01, - 0xff,0xd2,0x99,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xd2,0x9b,0x00,0x01,0x00,0xd1, - 0x0b,0x10,0x07,0x01,0xff,0xd2,0x9d,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xd2,0x9f, - 0x00,0x01,0x00,0xd4,0x58,0xd3,0x2c,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd2, - 0xa1,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xd2,0xa3,0x00,0x01,0x00,0xd1,0x0b,0x10, - 0x07,0x01,0xff,0xd2,0xa5,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xd2,0xa7,0x00,0x01, - 0x00,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd2,0xa9,0x00,0x01,0x00,0x10,0x07, - 0x01,0xff,0xd2,0xab,0x00,0x01,0x00,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd2,0xad,0x00, - 0x01,0x00,0x10,0x07,0x01,0xff,0xd2,0xaf,0x00,0x01,0x00,0xd3,0x2c,0xd2,0x16,0xd1, - 0x0b,0x10,0x07,0x01,0xff,0xd2,0xb1,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xd2,0xb3, - 0x00,0x01,0x00,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd2,0xb5,0x00,0x01,0x00,0x10,0x07, - 0x01,0xff,0xd2,0xb7,0x00,0x01,0x00,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd2, - 0xb9,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xd2,0xbb,0x00,0x01,0x00,0xd1,0x0b,0x10, - 0x07,0x01,0xff,0xd2,0xbd,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xd2,0xbf,0x00,0x01, - 0x00,0xcf,0x86,0xd5,0xdc,0xd4,0x5a,0xd3,0x36,0xd2,0x20,0xd1,0x10,0x10,0x07,0x01, - 0xff,0xd3,0x8f,0x00,0x01,0xff,0xd0,0xb6,0xcc,0x86,0x00,0x10,0x09,0x01,0xff,0xd0, - 0xb6,0xcc,0x86,0x00,0x01,0xff,0xd3,0x84,0x00,0xd1,0x0b,0x10,0x04,0x01,0x00,0x06, - 0xff,0xd3,0x86,0x00,0x10,0x04,0x06,0x00,0x01,0xff,0xd3,0x88,0x00,0xd2,0x16,0xd1, - 0x0b,0x10,0x04,0x01,0x00,0x06,0xff,0xd3,0x8a,0x00,0x10,0x04,0x06,0x00,0x01,0xff, - 0xd3,0x8c,0x00,0xe1,0x69,0x40,0x10,0x04,0x01,0x00,0x06,0xff,0xd3,0x8e,0x00,0xd3, - 0x41,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff,0xd0,0xb0,0xcc,0x86,0x00,0x01,0xff, - 0xd0,0xb0,0xcc,0x86,0x00,0x10,0x09,0x01,0xff,0xd0,0xb0,0xcc,0x88,0x00,0x01,0xff, - 0xd0,0xb0,0xcc,0x88,0x00,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd3,0x95,0x00,0x01,0x00, - 0x10,0x09,0x01,0xff,0xd0,0xb5,0xcc,0x86,0x00,0x01,0xff,0xd0,0xb5,0xcc,0x86,0x00, - 0xd2,0x1d,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd3,0x99,0x00,0x01,0x00,0x10,0x09,0x01, - 0xff,0xd3,0x99,0xcc,0x88,0x00,0x01,0xff,0xd3,0x99,0xcc,0x88,0x00,0xd1,0x12,0x10, - 0x09,0x01,0xff,0xd0,0xb6,0xcc,0x88,0x00,0x01,0xff,0xd0,0xb6,0xcc,0x88,0x00,0x10, - 0x09,0x01,0xff,0xd0,0xb7,0xcc,0x88,0x00,0x01,0xff,0xd0,0xb7,0xcc,0x88,0x00,0xd4, - 0x82,0xd3,0x41,0xd2,0x1d,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd3,0xa1,0x00,0x01,0x00, - 0x10,0x09,0x01,0xff,0xd0,0xb8,0xcc,0x84,0x00,0x01,0xff,0xd0,0xb8,0xcc,0x84,0x00, - 0xd1,0x12,0x10,0x09,0x01,0xff,0xd0,0xb8,0xcc,0x88,0x00,0x01,0xff,0xd0,0xb8,0xcc, - 0x88,0x00,0x10,0x09,0x01,0xff,0xd0,0xbe,0xcc,0x88,0x00,0x01,0xff,0xd0,0xbe,0xcc, - 0x88,0x00,0xd2,0x1d,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd3,0xa9,0x00,0x01,0x00,0x10, - 0x09,0x01,0xff,0xd3,0xa9,0xcc,0x88,0x00,0x01,0xff,0xd3,0xa9,0xcc,0x88,0x00,0xd1, - 0x12,0x10,0x09,0x04,0xff,0xd1,0x8d,0xcc,0x88,0x00,0x04,0xff,0xd1,0x8d,0xcc,0x88, - 0x00,0x10,0x09,0x01,0xff,0xd1,0x83,0xcc,0x84,0x00,0x01,0xff,0xd1,0x83,0xcc,0x84, - 0x00,0xd3,0x41,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff,0xd1,0x83,0xcc,0x88,0x00, - 0x01,0xff,0xd1,0x83,0xcc,0x88,0x00,0x10,0x09,0x01,0xff,0xd1,0x83,0xcc,0x8b,0x00, - 0x01,0xff,0xd1,0x83,0xcc,0x8b,0x00,0xd1,0x12,0x10,0x09,0x01,0xff,0xd1,0x87,0xcc, - 0x88,0x00,0x01,0xff,0xd1,0x87,0xcc,0x88,0x00,0x10,0x07,0x08,0xff,0xd3,0xb7,0x00, - 0x08,0x00,0xd2,0x1d,0xd1,0x12,0x10,0x09,0x01,0xff,0xd1,0x8b,0xcc,0x88,0x00,0x01, - 0xff,0xd1,0x8b,0xcc,0x88,0x00,0x10,0x07,0x09,0xff,0xd3,0xbb,0x00,0x09,0x00,0xd1, - 0x0b,0x10,0x07,0x09,0xff,0xd3,0xbd,0x00,0x09,0x00,0x10,0x07,0x09,0xff,0xd3,0xbf, - 0x00,0x09,0x00,0xe1,0x26,0x02,0xe0,0x78,0x01,0xcf,0x86,0xd5,0xb0,0xd4,0x58,0xd3, - 0x2c,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x06,0xff,0xd4,0x81,0x00,0x06,0x00,0x10,0x07, - 0x06,0xff,0xd4,0x83,0x00,0x06,0x00,0xd1,0x0b,0x10,0x07,0x06,0xff,0xd4,0x85,0x00, - 0x06,0x00,0x10,0x07,0x06,0xff,0xd4,0x87,0x00,0x06,0x00,0xd2,0x16,0xd1,0x0b,0x10, - 0x07,0x06,0xff,0xd4,0x89,0x00,0x06,0x00,0x10,0x07,0x06,0xff,0xd4,0x8b,0x00,0x06, - 0x00,0xd1,0x0b,0x10,0x07,0x06,0xff,0xd4,0x8d,0x00,0x06,0x00,0x10,0x07,0x06,0xff, - 0xd4,0x8f,0x00,0x06,0x00,0xd3,0x2c,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x09,0xff,0xd4, - 0x91,0x00,0x09,0x00,0x10,0x07,0x09,0xff,0xd4,0x93,0x00,0x09,0x00,0xd1,0x0b,0x10, - 0x07,0x0a,0xff,0xd4,0x95,0x00,0x0a,0x00,0x10,0x07,0x0a,0xff,0xd4,0x97,0x00,0x0a, - 0x00,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x0a,0xff,0xd4,0x99,0x00,0x0a,0x00,0x10,0x07, - 0x0a,0xff,0xd4,0x9b,0x00,0x0a,0x00,0xd1,0x0b,0x10,0x07,0x0a,0xff,0xd4,0x9d,0x00, - 0x0a,0x00,0x10,0x07,0x0a,0xff,0xd4,0x9f,0x00,0x0a,0x00,0xd4,0x58,0xd3,0x2c,0xd2, - 0x16,0xd1,0x0b,0x10,0x07,0x0a,0xff,0xd4,0xa1,0x00,0x0a,0x00,0x10,0x07,0x0a,0xff, - 0xd4,0xa3,0x00,0x0a,0x00,0xd1,0x0b,0x10,0x07,0x0b,0xff,0xd4,0xa5,0x00,0x0b,0x00, - 0x10,0x07,0x0c,0xff,0xd4,0xa7,0x00,0x0c,0x00,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x10, - 0xff,0xd4,0xa9,0x00,0x10,0x00,0x10,0x07,0x10,0xff,0xd4,0xab,0x00,0x10,0x00,0xd1, - 0x0b,0x10,0x07,0x10,0xff,0xd4,0xad,0x00,0x10,0x00,0x10,0x07,0x10,0xff,0xd4,0xaf, - 0x00,0x10,0x00,0xd3,0x35,0xd2,0x19,0xd1,0x0b,0x10,0x04,0x00,0x00,0x01,0xff,0xd5, - 0xa1,0x00,0x10,0x07,0x01,0xff,0xd5,0xa2,0x00,0x01,0xff,0xd5,0xa3,0x00,0xd1,0x0e, - 0x10,0x07,0x01,0xff,0xd5,0xa4,0x00,0x01,0xff,0xd5,0xa5,0x00,0x10,0x07,0x01,0xff, - 0xd5,0xa6,0x00,0x01,0xff,0xd5,0xa7,0x00,0xd2,0x1c,0xd1,0x0e,0x10,0x07,0x01,0xff, - 0xd5,0xa8,0x00,0x01,0xff,0xd5,0xa9,0x00,0x10,0x07,0x01,0xff,0xd5,0xaa,0x00,0x01, - 0xff,0xd5,0xab,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd5,0xac,0x00,0x01,0xff,0xd5, - 0xad,0x00,0x10,0x07,0x01,0xff,0xd5,0xae,0x00,0x01,0xff,0xd5,0xaf,0x00,0xcf,0x86, - 0xe5,0x08,0x3f,0xd4,0x70,0xd3,0x38,0xd2,0x1c,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd5, - 0xb0,0x00,0x01,0xff,0xd5,0xb1,0x00,0x10,0x07,0x01,0xff,0xd5,0xb2,0x00,0x01,0xff, - 0xd5,0xb3,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd5,0xb4,0x00,0x01,0xff,0xd5,0xb5, - 0x00,0x10,0x07,0x01,0xff,0xd5,0xb6,0x00,0x01,0xff,0xd5,0xb7,0x00,0xd2,0x1c,0xd1, - 0x0e,0x10,0x07,0x01,0xff,0xd5,0xb8,0x00,0x01,0xff,0xd5,0xb9,0x00,0x10,0x07,0x01, - 0xff,0xd5,0xba,0x00,0x01,0xff,0xd5,0xbb,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd5, - 0xbc,0x00,0x01,0xff,0xd5,0xbd,0x00,0x10,0x07,0x01,0xff,0xd5,0xbe,0x00,0x01,0xff, - 0xd5,0xbf,0x00,0xe3,0x87,0x3e,0xd2,0x1c,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd6,0x80, - 0x00,0x01,0xff,0xd6,0x81,0x00,0x10,0x07,0x01,0xff,0xd6,0x82,0x00,0x01,0xff,0xd6, - 0x83,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd6,0x84,0x00,0x01,0xff,0xd6,0x85,0x00, - 0x10,0x07,0x01,0xff,0xd6,0x86,0x00,0x00,0x00,0xe0,0x2f,0x3f,0xcf,0x86,0xe5,0xc0, - 0x3e,0xe4,0x97,0x3e,0xe3,0x76,0x3e,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10, - 0x04,0x01,0x00,0x01,0xff,0xd5,0xa5,0xd6,0x82,0x00,0xe4,0x3e,0x25,0xe3,0xc3,0x1a, - 0xe2,0x7b,0x81,0xe1,0xc0,0x13,0xd0,0x1e,0xcf,0x86,0xc5,0xe4,0x08,0x4b,0xe3,0x53, - 0x46,0xe2,0xe9,0x43,0xe1,0x1c,0x43,0xe0,0xe1,0x42,0xcf,0x86,0xe5,0xa6,0x42,0x64, - 0x89,0x42,0x0b,0x00,0xcf,0x86,0xe5,0xfa,0x01,0xe4,0x03,0x56,0xe3,0x76,0x01,0xe2, - 0x8e,0x53,0xd1,0x0c,0xe0,0xef,0x52,0xcf,0x86,0x65,0x8d,0x52,0x04,0x00,0xe0,0x0d, - 0x01,0xcf,0x86,0xd5,0x0a,0xe4,0x10,0x53,0x63,0xff,0x52,0x0a,0x00,0xd4,0x80,0xd3, - 0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0xb4,0x80,0x00,0x01,0xff,0xe2, - 0xb4,0x81,0x00,0x10,0x08,0x01,0xff,0xe2,0xb4,0x82,0x00,0x01,0xff,0xe2,0xb4,0x83, - 0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0xb4,0x84,0x00,0x01,0xff,0xe2,0xb4,0x85, - 0x00,0x10,0x08,0x01,0xff,0xe2,0xb4,0x86,0x00,0x01,0xff,0xe2,0xb4,0x87,0x00,0xd2, - 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0xb4,0x88,0x00,0x01,0xff,0xe2,0xb4,0x89, - 0x00,0x10,0x08,0x01,0xff,0xe2,0xb4,0x8a,0x00,0x01,0xff,0xe2,0xb4,0x8b,0x00,0xd1, - 0x10,0x10,0x08,0x01,0xff,0xe2,0xb4,0x8c,0x00,0x01,0xff,0xe2,0xb4,0x8d,0x00,0x10, - 0x08,0x01,0xff,0xe2,0xb4,0x8e,0x00,0x01,0xff,0xe2,0xb4,0x8f,0x00,0xd3,0x40,0xd2, - 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0xb4,0x90,0x00,0x01,0xff,0xe2,0xb4,0x91, - 0x00,0x10,0x08,0x01,0xff,0xe2,0xb4,0x92,0x00,0x01,0xff,0xe2,0xb4,0x93,0x00,0xd1, - 0x10,0x10,0x08,0x01,0xff,0xe2,0xb4,0x94,0x00,0x01,0xff,0xe2,0xb4,0x95,0x00,0x10, - 0x08,0x01,0xff,0xe2,0xb4,0x96,0x00,0x01,0xff,0xe2,0xb4,0x97,0x00,0xd2,0x20,0xd1, - 0x10,0x10,0x08,0x01,0xff,0xe2,0xb4,0x98,0x00,0x01,0xff,0xe2,0xb4,0x99,0x00,0x10, - 0x08,0x01,0xff,0xe2,0xb4,0x9a,0x00,0x01,0xff,0xe2,0xb4,0x9b,0x00,0xd1,0x10,0x10, - 0x08,0x01,0xff,0xe2,0xb4,0x9c,0x00,0x01,0xff,0xe2,0xb4,0x9d,0x00,0x10,0x08,0x01, - 0xff,0xe2,0xb4,0x9e,0x00,0x01,0xff,0xe2,0xb4,0x9f,0x00,0xcf,0x86,0xe5,0x42,0x52, - 0x94,0x50,0xd3,0x3c,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0xb4,0xa0,0x00, - 0x01,0xff,0xe2,0xb4,0xa1,0x00,0x10,0x08,0x01,0xff,0xe2,0xb4,0xa2,0x00,0x01,0xff, - 0xe2,0xb4,0xa3,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0xb4,0xa4,0x00,0x01,0xff, - 0xe2,0xb4,0xa5,0x00,0x10,0x04,0x00,0x00,0x0d,0xff,0xe2,0xb4,0xa7,0x00,0x52,0x04, - 0x00,0x00,0x91,0x0c,0x10,0x04,0x00,0x00,0x0d,0xff,0xe2,0xb4,0xad,0x00,0x00,0x00, - 0x01,0x00,0xd2,0x1b,0xe1,0xfc,0x52,0xe0,0xad,0x52,0xcf,0x86,0x95,0x0f,0x94,0x0b, - 0x93,0x07,0x62,0x92,0x52,0x04,0x00,0x04,0x00,0x04,0x00,0x04,0x00,0xd1,0x13,0xe0, - 0xd3,0x53,0xcf,0x86,0x95,0x0a,0xe4,0xa8,0x53,0x63,0x97,0x53,0x04,0x00,0x04,0x00, - 0xd0,0x0d,0xcf,0x86,0x95,0x07,0x64,0x22,0x54,0x08,0x00,0x04,0x00,0xcf,0x86,0x55, - 0x04,0x04,0x00,0x54,0x04,0x04,0x00,0xd3,0x07,0x62,0x2f,0x54,0x04,0x00,0xd2,0x20, - 0xd1,0x10,0x10,0x08,0x11,0xff,0xe1,0x8f,0xb0,0x00,0x11,0xff,0xe1,0x8f,0xb1,0x00, - 0x10,0x08,0x11,0xff,0xe1,0x8f,0xb2,0x00,0x11,0xff,0xe1,0x8f,0xb3,0x00,0x91,0x10, - 0x10,0x08,0x11,0xff,0xe1,0x8f,0xb4,0x00,0x11,0xff,0xe1,0x8f,0xb5,0x00,0x00,0x00, - 0xd4,0x1c,0xe3,0xe0,0x56,0xe2,0x17,0x56,0xe1,0xda,0x55,0xe0,0xbb,0x55,0xcf,0x86, - 0x95,0x0a,0xe4,0xa4,0x55,0x63,0x88,0x55,0x04,0x00,0x04,0x00,0xe3,0xd2,0x01,0xe2, - 0x2b,0x5a,0xd1,0x0c,0xe0,0x4c,0x59,0xcf,0x86,0x65,0x25,0x59,0x0a,0x00,0xe0,0x9c, - 0x59,0xcf,0x86,0xd5,0xc5,0xd4,0x45,0xd3,0x31,0xd2,0x1c,0xd1,0x0e,0x10,0x07,0x12, - 0xff,0xd0,0xb2,0x00,0x12,0xff,0xd0,0xb4,0x00,0x10,0x07,0x12,0xff,0xd0,0xbe,0x00, - 0x12,0xff,0xd1,0x81,0x00,0x51,0x07,0x12,0xff,0xd1,0x82,0x00,0x10,0x07,0x12,0xff, - 0xd1,0x8a,0x00,0x12,0xff,0xd1,0xa3,0x00,0x92,0x10,0x91,0x0c,0x10,0x08,0x12,0xff, - 0xea,0x99,0x8b,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10, - 0x10,0x08,0x14,0xff,0xe1,0x83,0x90,0x00,0x14,0xff,0xe1,0x83,0x91,0x00,0x10,0x08, - 0x14,0xff,0xe1,0x83,0x92,0x00,0x14,0xff,0xe1,0x83,0x93,0x00,0xd1,0x10,0x10,0x08, - 0x14,0xff,0xe1,0x83,0x94,0x00,0x14,0xff,0xe1,0x83,0x95,0x00,0x10,0x08,0x14,0xff, - 0xe1,0x83,0x96,0x00,0x14,0xff,0xe1,0x83,0x97,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08, - 0x14,0xff,0xe1,0x83,0x98,0x00,0x14,0xff,0xe1,0x83,0x99,0x00,0x10,0x08,0x14,0xff, - 0xe1,0x83,0x9a,0x00,0x14,0xff,0xe1,0x83,0x9b,0x00,0xd1,0x10,0x10,0x08,0x14,0xff, - 0xe1,0x83,0x9c,0x00,0x14,0xff,0xe1,0x83,0x9d,0x00,0x10,0x08,0x14,0xff,0xe1,0x83, - 0x9e,0x00,0x14,0xff,0xe1,0x83,0x9f,0x00,0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10, - 0x10,0x08,0x14,0xff,0xe1,0x83,0xa0,0x00,0x14,0xff,0xe1,0x83,0xa1,0x00,0x10,0x08, - 0x14,0xff,0xe1,0x83,0xa2,0x00,0x14,0xff,0xe1,0x83,0xa3,0x00,0xd1,0x10,0x10,0x08, - 0x14,0xff,0xe1,0x83,0xa4,0x00,0x14,0xff,0xe1,0x83,0xa5,0x00,0x10,0x08,0x14,0xff, - 0xe1,0x83,0xa6,0x00,0x14,0xff,0xe1,0x83,0xa7,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08, - 0x14,0xff,0xe1,0x83,0xa8,0x00,0x14,0xff,0xe1,0x83,0xa9,0x00,0x10,0x08,0x14,0xff, - 0xe1,0x83,0xaa,0x00,0x14,0xff,0xe1,0x83,0xab,0x00,0xd1,0x10,0x10,0x08,0x14,0xff, - 0xe1,0x83,0xac,0x00,0x14,0xff,0xe1,0x83,0xad,0x00,0x10,0x08,0x14,0xff,0xe1,0x83, - 0xae,0x00,0x14,0xff,0xe1,0x83,0xaf,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08, - 0x14,0xff,0xe1,0x83,0xb0,0x00,0x14,0xff,0xe1,0x83,0xb1,0x00,0x10,0x08,0x14,0xff, - 0xe1,0x83,0xb2,0x00,0x14,0xff,0xe1,0x83,0xb3,0x00,0xd1,0x10,0x10,0x08,0x14,0xff, - 0xe1,0x83,0xb4,0x00,0x14,0xff,0xe1,0x83,0xb5,0x00,0x10,0x08,0x14,0xff,0xe1,0x83, - 0xb6,0x00,0x14,0xff,0xe1,0x83,0xb7,0x00,0xd2,0x1c,0xd1,0x10,0x10,0x08,0x14,0xff, - 0xe1,0x83,0xb8,0x00,0x14,0xff,0xe1,0x83,0xb9,0x00,0x10,0x08,0x14,0xff,0xe1,0x83, - 0xba,0x00,0x00,0x00,0xd1,0x0c,0x10,0x04,0x00,0x00,0x14,0xff,0xe1,0x83,0xbd,0x00, - 0x10,0x08,0x14,0xff,0xe1,0x83,0xbe,0x00,0x14,0xff,0xe1,0x83,0xbf,0x00,0xe2,0x9d, - 0x08,0xe1,0x48,0x04,0xe0,0x1c,0x02,0xcf,0x86,0xe5,0x11,0x01,0xd4,0x84,0xd3,0x40, - 0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x61,0xcc,0xa5,0x00,0x01,0xff,0x61,0xcc, - 0xa5,0x00,0x10,0x08,0x01,0xff,0x62,0xcc,0x87,0x00,0x01,0xff,0x62,0xcc,0x87,0x00, - 0xd1,0x10,0x10,0x08,0x01,0xff,0x62,0xcc,0xa3,0x00,0x01,0xff,0x62,0xcc,0xa3,0x00, - 0x10,0x08,0x01,0xff,0x62,0xcc,0xb1,0x00,0x01,0xff,0x62,0xcc,0xb1,0x00,0xd2,0x24, - 0xd1,0x14,0x10,0x0a,0x01,0xff,0x63,0xcc,0xa7,0xcc,0x81,0x00,0x01,0xff,0x63,0xcc, - 0xa7,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x64,0xcc,0x87,0x00,0x01,0xff,0x64,0xcc, - 0x87,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x64,0xcc,0xa3,0x00,0x01,0xff,0x64,0xcc, - 0xa3,0x00,0x10,0x08,0x01,0xff,0x64,0xcc,0xb1,0x00,0x01,0xff,0x64,0xcc,0xb1,0x00, - 0xd3,0x48,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x64,0xcc,0xa7,0x00,0x01,0xff, - 0x64,0xcc,0xa7,0x00,0x10,0x08,0x01,0xff,0x64,0xcc,0xad,0x00,0x01,0xff,0x64,0xcc, - 0xad,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x65,0xcc,0x84,0xcc,0x80,0x00,0x01,0xff, - 0x65,0xcc,0x84,0xcc,0x80,0x00,0x10,0x0a,0x01,0xff,0x65,0xcc,0x84,0xcc,0x81,0x00, - 0x01,0xff,0x65,0xcc,0x84,0xcc,0x81,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff, - 0x65,0xcc,0xad,0x00,0x01,0xff,0x65,0xcc,0xad,0x00,0x10,0x08,0x01,0xff,0x65,0xcc, - 0xb0,0x00,0x01,0xff,0x65,0xcc,0xb0,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x65,0xcc, - 0xa7,0xcc,0x86,0x00,0x01,0xff,0x65,0xcc,0xa7,0xcc,0x86,0x00,0x10,0x08,0x01,0xff, - 0x66,0xcc,0x87,0x00,0x01,0xff,0x66,0xcc,0x87,0x00,0xd4,0x84,0xd3,0x40,0xd2,0x20, - 0xd1,0x10,0x10,0x08,0x01,0xff,0x67,0xcc,0x84,0x00,0x01,0xff,0x67,0xcc,0x84,0x00, - 0x10,0x08,0x01,0xff,0x68,0xcc,0x87,0x00,0x01,0xff,0x68,0xcc,0x87,0x00,0xd1,0x10, - 0x10,0x08,0x01,0xff,0x68,0xcc,0xa3,0x00,0x01,0xff,0x68,0xcc,0xa3,0x00,0x10,0x08, - 0x01,0xff,0x68,0xcc,0x88,0x00,0x01,0xff,0x68,0xcc,0x88,0x00,0xd2,0x20,0xd1,0x10, - 0x10,0x08,0x01,0xff,0x68,0xcc,0xa7,0x00,0x01,0xff,0x68,0xcc,0xa7,0x00,0x10,0x08, - 0x01,0xff,0x68,0xcc,0xae,0x00,0x01,0xff,0x68,0xcc,0xae,0x00,0xd1,0x10,0x10,0x08, - 0x01,0xff,0x69,0xcc,0xb0,0x00,0x01,0xff,0x69,0xcc,0xb0,0x00,0x10,0x0a,0x01,0xff, - 0x69,0xcc,0x88,0xcc,0x81,0x00,0x01,0xff,0x69,0xcc,0x88,0xcc,0x81,0x00,0xd3,0x40, - 0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x6b,0xcc,0x81,0x00,0x01,0xff,0x6b,0xcc, - 0x81,0x00,0x10,0x08,0x01,0xff,0x6b,0xcc,0xa3,0x00,0x01,0xff,0x6b,0xcc,0xa3,0x00, - 0xd1,0x10,0x10,0x08,0x01,0xff,0x6b,0xcc,0xb1,0x00,0x01,0xff,0x6b,0xcc,0xb1,0x00, - 0x10,0x08,0x01,0xff,0x6c,0xcc,0xa3,0x00,0x01,0xff,0x6c,0xcc,0xa3,0x00,0xd2,0x24, - 0xd1,0x14,0x10,0x0a,0x01,0xff,0x6c,0xcc,0xa3,0xcc,0x84,0x00,0x01,0xff,0x6c,0xcc, - 0xa3,0xcc,0x84,0x00,0x10,0x08,0x01,0xff,0x6c,0xcc,0xb1,0x00,0x01,0xff,0x6c,0xcc, - 0xb1,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x6c,0xcc,0xad,0x00,0x01,0xff,0x6c,0xcc, - 0xad,0x00,0x10,0x08,0x01,0xff,0x6d,0xcc,0x81,0x00,0x01,0xff,0x6d,0xcc,0x81,0x00, - 0xcf,0x86,0xe5,0x15,0x01,0xd4,0x88,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01, - 0xff,0x6d,0xcc,0x87,0x00,0x01,0xff,0x6d,0xcc,0x87,0x00,0x10,0x08,0x01,0xff,0x6d, - 0xcc,0xa3,0x00,0x01,0xff,0x6d,0xcc,0xa3,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x6e, - 0xcc,0x87,0x00,0x01,0xff,0x6e,0xcc,0x87,0x00,0x10,0x08,0x01,0xff,0x6e,0xcc,0xa3, - 0x00,0x01,0xff,0x6e,0xcc,0xa3,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x6e, - 0xcc,0xb1,0x00,0x01,0xff,0x6e,0xcc,0xb1,0x00,0x10,0x08,0x01,0xff,0x6e,0xcc,0xad, - 0x00,0x01,0xff,0x6e,0xcc,0xad,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x6f,0xcc,0x83, - 0xcc,0x81,0x00,0x01,0xff,0x6f,0xcc,0x83,0xcc,0x81,0x00,0x10,0x0a,0x01,0xff,0x6f, - 0xcc,0x83,0xcc,0x88,0x00,0x01,0xff,0x6f,0xcc,0x83,0xcc,0x88,0x00,0xd3,0x48,0xd2, - 0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x6f,0xcc,0x84,0xcc,0x80,0x00,0x01,0xff,0x6f, - 0xcc,0x84,0xcc,0x80,0x00,0x10,0x0a,0x01,0xff,0x6f,0xcc,0x84,0xcc,0x81,0x00,0x01, - 0xff,0x6f,0xcc,0x84,0xcc,0x81,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x70,0xcc,0x81, - 0x00,0x01,0xff,0x70,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x70,0xcc,0x87,0x00,0x01, - 0xff,0x70,0xcc,0x87,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x72,0xcc,0x87, - 0x00,0x01,0xff,0x72,0xcc,0x87,0x00,0x10,0x08,0x01,0xff,0x72,0xcc,0xa3,0x00,0x01, - 0xff,0x72,0xcc,0xa3,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x72,0xcc,0xa3,0xcc,0x84, - 0x00,0x01,0xff,0x72,0xcc,0xa3,0xcc,0x84,0x00,0x10,0x08,0x01,0xff,0x72,0xcc,0xb1, - 0x00,0x01,0xff,0x72,0xcc,0xb1,0x00,0xd4,0x8c,0xd3,0x48,0xd2,0x20,0xd1,0x10,0x10, - 0x08,0x01,0xff,0x73,0xcc,0x87,0x00,0x01,0xff,0x73,0xcc,0x87,0x00,0x10,0x08,0x01, - 0xff,0x73,0xcc,0xa3,0x00,0x01,0xff,0x73,0xcc,0xa3,0x00,0xd1,0x14,0x10,0x0a,0x01, - 0xff,0x73,0xcc,0x81,0xcc,0x87,0x00,0x01,0xff,0x73,0xcc,0x81,0xcc,0x87,0x00,0x10, - 0x0a,0x01,0xff,0x73,0xcc,0x8c,0xcc,0x87,0x00,0x01,0xff,0x73,0xcc,0x8c,0xcc,0x87, - 0x00,0xd2,0x24,0xd1,0x14,0x10,0x0a,0x01,0xff,0x73,0xcc,0xa3,0xcc,0x87,0x00,0x01, - 0xff,0x73,0xcc,0xa3,0xcc,0x87,0x00,0x10,0x08,0x01,0xff,0x74,0xcc,0x87,0x00,0x01, - 0xff,0x74,0xcc,0x87,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x74,0xcc,0xa3,0x00,0x01, - 0xff,0x74,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x74,0xcc,0xb1,0x00,0x01,0xff,0x74, - 0xcc,0xb1,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x74,0xcc,0xad, - 0x00,0x01,0xff,0x74,0xcc,0xad,0x00,0x10,0x08,0x01,0xff,0x75,0xcc,0xa4,0x00,0x01, - 0xff,0x75,0xcc,0xa4,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x75,0xcc,0xb0,0x00,0x01, - 0xff,0x75,0xcc,0xb0,0x00,0x10,0x08,0x01,0xff,0x75,0xcc,0xad,0x00,0x01,0xff,0x75, - 0xcc,0xad,0x00,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x75,0xcc,0x83,0xcc,0x81, - 0x00,0x01,0xff,0x75,0xcc,0x83,0xcc,0x81,0x00,0x10,0x0a,0x01,0xff,0x75,0xcc,0x84, - 0xcc,0x88,0x00,0x01,0xff,0x75,0xcc,0x84,0xcc,0x88,0x00,0xd1,0x10,0x10,0x08,0x01, - 0xff,0x76,0xcc,0x83,0x00,0x01,0xff,0x76,0xcc,0x83,0x00,0x10,0x08,0x01,0xff,0x76, - 0xcc,0xa3,0x00,0x01,0xff,0x76,0xcc,0xa3,0x00,0xe0,0x11,0x02,0xcf,0x86,0xd5,0xe2, - 0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x77,0xcc,0x80,0x00, - 0x01,0xff,0x77,0xcc,0x80,0x00,0x10,0x08,0x01,0xff,0x77,0xcc,0x81,0x00,0x01,0xff, - 0x77,0xcc,0x81,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x77,0xcc,0x88,0x00,0x01,0xff, - 0x77,0xcc,0x88,0x00,0x10,0x08,0x01,0xff,0x77,0xcc,0x87,0x00,0x01,0xff,0x77,0xcc, - 0x87,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x77,0xcc,0xa3,0x00,0x01,0xff, - 0x77,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x78,0xcc,0x87,0x00,0x01,0xff,0x78,0xcc, - 0x87,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x78,0xcc,0x88,0x00,0x01,0xff,0x78,0xcc, - 0x88,0x00,0x10,0x08,0x01,0xff,0x79,0xcc,0x87,0x00,0x01,0xff,0x79,0xcc,0x87,0x00, - 0xd3,0x33,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x7a,0xcc,0x82,0x00,0x01,0xff, - 0x7a,0xcc,0x82,0x00,0x10,0x08,0x01,0xff,0x7a,0xcc,0xa3,0x00,0x01,0xff,0x7a,0xcc, - 0xa3,0x00,0xe1,0x12,0x59,0x10,0x08,0x01,0xff,0x7a,0xcc,0xb1,0x00,0x01,0xff,0x7a, - 0xcc,0xb1,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x77,0xcc,0x8a,0x00,0x01, - 0xff,0x79,0xcc,0x8a,0x00,0x10,0x08,0x01,0xff,0x61,0xca,0xbe,0x00,0x02,0xff,0x73, - 0xcc,0x87,0x00,0x51,0x04,0x0a,0x00,0x10,0x07,0x0a,0xff,0x73,0x73,0x00,0x0a,0x00, - 0xd4,0x98,0xd3,0x48,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x61,0xcc,0xa3,0x00, - 0x01,0xff,0x61,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x61,0xcc,0x89,0x00,0x01,0xff, - 0x61,0xcc,0x89,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x61,0xcc,0x82,0xcc,0x81,0x00, - 0x01,0xff,0x61,0xcc,0x82,0xcc,0x81,0x00,0x10,0x0a,0x01,0xff,0x61,0xcc,0x82,0xcc, - 0x80,0x00,0x01,0xff,0x61,0xcc,0x82,0xcc,0x80,0x00,0xd2,0x28,0xd1,0x14,0x10,0x0a, - 0x01,0xff,0x61,0xcc,0x82,0xcc,0x89,0x00,0x01,0xff,0x61,0xcc,0x82,0xcc,0x89,0x00, - 0x10,0x0a,0x01,0xff,0x61,0xcc,0x82,0xcc,0x83,0x00,0x01,0xff,0x61,0xcc,0x82,0xcc, - 0x83,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x61,0xcc,0xa3,0xcc,0x82,0x00,0x01,0xff, - 0x61,0xcc,0xa3,0xcc,0x82,0x00,0x10,0x0a,0x01,0xff,0x61,0xcc,0x86,0xcc,0x81,0x00, - 0x01,0xff,0x61,0xcc,0x86,0xcc,0x81,0x00,0xd3,0x50,0xd2,0x28,0xd1,0x14,0x10,0x0a, - 0x01,0xff,0x61,0xcc,0x86,0xcc,0x80,0x00,0x01,0xff,0x61,0xcc,0x86,0xcc,0x80,0x00, - 0x10,0x0a,0x01,0xff,0x61,0xcc,0x86,0xcc,0x89,0x00,0x01,0xff,0x61,0xcc,0x86,0xcc, - 0x89,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x61,0xcc,0x86,0xcc,0x83,0x00,0x01,0xff, - 0x61,0xcc,0x86,0xcc,0x83,0x00,0x10,0x0a,0x01,0xff,0x61,0xcc,0xa3,0xcc,0x86,0x00, - 0x01,0xff,0x61,0xcc,0xa3,0xcc,0x86,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff, - 0x65,0xcc,0xa3,0x00,0x01,0xff,0x65,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x65,0xcc, - 0x89,0x00,0x01,0xff,0x65,0xcc,0x89,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x65,0xcc, - 0x83,0x00,0x01,0xff,0x65,0xcc,0x83,0x00,0x10,0x0a,0x01,0xff,0x65,0xcc,0x82,0xcc, - 0x81,0x00,0x01,0xff,0x65,0xcc,0x82,0xcc,0x81,0x00,0xcf,0x86,0xe5,0x31,0x01,0xd4, - 0x90,0xd3,0x50,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x65,0xcc,0x82,0xcc,0x80, - 0x00,0x01,0xff,0x65,0xcc,0x82,0xcc,0x80,0x00,0x10,0x0a,0x01,0xff,0x65,0xcc,0x82, - 0xcc,0x89,0x00,0x01,0xff,0x65,0xcc,0x82,0xcc,0x89,0x00,0xd1,0x14,0x10,0x0a,0x01, - 0xff,0x65,0xcc,0x82,0xcc,0x83,0x00,0x01,0xff,0x65,0xcc,0x82,0xcc,0x83,0x00,0x10, - 0x0a,0x01,0xff,0x65,0xcc,0xa3,0xcc,0x82,0x00,0x01,0xff,0x65,0xcc,0xa3,0xcc,0x82, - 0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x69,0xcc,0x89,0x00,0x01,0xff,0x69, - 0xcc,0x89,0x00,0x10,0x08,0x01,0xff,0x69,0xcc,0xa3,0x00,0x01,0xff,0x69,0xcc,0xa3, - 0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x6f,0xcc,0xa3,0x00,0x01,0xff,0x6f,0xcc,0xa3, - 0x00,0x10,0x08,0x01,0xff,0x6f,0xcc,0x89,0x00,0x01,0xff,0x6f,0xcc,0x89,0x00,0xd3, - 0x50,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x6f,0xcc,0x82,0xcc,0x81,0x00,0x01, - 0xff,0x6f,0xcc,0x82,0xcc,0x81,0x00,0x10,0x0a,0x01,0xff,0x6f,0xcc,0x82,0xcc,0x80, - 0x00,0x01,0xff,0x6f,0xcc,0x82,0xcc,0x80,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x6f, - 0xcc,0x82,0xcc,0x89,0x00,0x01,0xff,0x6f,0xcc,0x82,0xcc,0x89,0x00,0x10,0x0a,0x01, - 0xff,0x6f,0xcc,0x82,0xcc,0x83,0x00,0x01,0xff,0x6f,0xcc,0x82,0xcc,0x83,0x00,0xd2, - 0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x6f,0xcc,0xa3,0xcc,0x82,0x00,0x01,0xff,0x6f, - 0xcc,0xa3,0xcc,0x82,0x00,0x10,0x0a,0x01,0xff,0x6f,0xcc,0x9b,0xcc,0x81,0x00,0x01, - 0xff,0x6f,0xcc,0x9b,0xcc,0x81,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x6f,0xcc,0x9b, - 0xcc,0x80,0x00,0x01,0xff,0x6f,0xcc,0x9b,0xcc,0x80,0x00,0x10,0x0a,0x01,0xff,0x6f, - 0xcc,0x9b,0xcc,0x89,0x00,0x01,0xff,0x6f,0xcc,0x9b,0xcc,0x89,0x00,0xd4,0x98,0xd3, - 0x48,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x6f,0xcc,0x9b,0xcc,0x83,0x00,0x01, - 0xff,0x6f,0xcc,0x9b,0xcc,0x83,0x00,0x10,0x0a,0x01,0xff,0x6f,0xcc,0x9b,0xcc,0xa3, - 0x00,0x01,0xff,0x6f,0xcc,0x9b,0xcc,0xa3,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x75, - 0xcc,0xa3,0x00,0x01,0xff,0x75,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x75,0xcc,0x89, - 0x00,0x01,0xff,0x75,0xcc,0x89,0x00,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x75, - 0xcc,0x9b,0xcc,0x81,0x00,0x01,0xff,0x75,0xcc,0x9b,0xcc,0x81,0x00,0x10,0x0a,0x01, - 0xff,0x75,0xcc,0x9b,0xcc,0x80,0x00,0x01,0xff,0x75,0xcc,0x9b,0xcc,0x80,0x00,0xd1, - 0x14,0x10,0x0a,0x01,0xff,0x75,0xcc,0x9b,0xcc,0x89,0x00,0x01,0xff,0x75,0xcc,0x9b, - 0xcc,0x89,0x00,0x10,0x0a,0x01,0xff,0x75,0xcc,0x9b,0xcc,0x83,0x00,0x01,0xff,0x75, - 0xcc,0x9b,0xcc,0x83,0x00,0xd3,0x44,0xd2,0x24,0xd1,0x14,0x10,0x0a,0x01,0xff,0x75, - 0xcc,0x9b,0xcc,0xa3,0x00,0x01,0xff,0x75,0xcc,0x9b,0xcc,0xa3,0x00,0x10,0x08,0x01, - 0xff,0x79,0xcc,0x80,0x00,0x01,0xff,0x79,0xcc,0x80,0x00,0xd1,0x10,0x10,0x08,0x01, - 0xff,0x79,0xcc,0xa3,0x00,0x01,0xff,0x79,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x79, - 0xcc,0x89,0x00,0x01,0xff,0x79,0xcc,0x89,0x00,0xd2,0x1c,0xd1,0x10,0x10,0x08,0x01, - 0xff,0x79,0xcc,0x83,0x00,0x01,0xff,0x79,0xcc,0x83,0x00,0x10,0x08,0x0a,0xff,0xe1, - 0xbb,0xbb,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xe1,0xbb,0xbd,0x00,0x0a, - 0x00,0x10,0x08,0x0a,0xff,0xe1,0xbb,0xbf,0x00,0x0a,0x00,0xe1,0xbf,0x02,0xe0,0xa1, - 0x01,0xcf,0x86,0xd5,0xc6,0xd4,0x6c,0xd3,0x18,0xe2,0x0e,0x59,0xe1,0xf7,0x58,0x10, - 0x09,0x01,0xff,0xce,0xb1,0xcc,0x93,0x00,0x01,0xff,0xce,0xb1,0xcc,0x94,0x00,0xd2, - 0x28,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb1,0xcc,0x93,0x00,0x01,0xff,0xce,0xb1, - 0xcc,0x94,0x00,0x10,0x0b,0x01,0xff,0xce,0xb1,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff, - 0xce,0xb1,0xcc,0x94,0xcc,0x80,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0xb1,0xcc, - 0x93,0xcc,0x81,0x00,0x01,0xff,0xce,0xb1,0xcc,0x94,0xcc,0x81,0x00,0x10,0x0b,0x01, - 0xff,0xce,0xb1,0xcc,0x93,0xcd,0x82,0x00,0x01,0xff,0xce,0xb1,0xcc,0x94,0xcd,0x82, - 0x00,0xd3,0x18,0xe2,0x4a,0x59,0xe1,0x33,0x59,0x10,0x09,0x01,0xff,0xce,0xb5,0xcc, - 0x93,0x00,0x01,0xff,0xce,0xb5,0xcc,0x94,0x00,0xd2,0x28,0xd1,0x12,0x10,0x09,0x01, - 0xff,0xce,0xb5,0xcc,0x93,0x00,0x01,0xff,0xce,0xb5,0xcc,0x94,0x00,0x10,0x0b,0x01, - 0xff,0xce,0xb5,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff,0xce,0xb5,0xcc,0x94,0xcc,0x80, - 0x00,0x91,0x16,0x10,0x0b,0x01,0xff,0xce,0xb5,0xcc,0x93,0xcc,0x81,0x00,0x01,0xff, - 0xce,0xb5,0xcc,0x94,0xcc,0x81,0x00,0x00,0x00,0xd4,0x6c,0xd3,0x18,0xe2,0x74,0x59, - 0xe1,0x5d,0x59,0x10,0x09,0x01,0xff,0xce,0xb7,0xcc,0x93,0x00,0x01,0xff,0xce,0xb7, - 0xcc,0x94,0x00,0xd2,0x28,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb7,0xcc,0x93,0x00, - 0x01,0xff,0xce,0xb7,0xcc,0x94,0x00,0x10,0x0b,0x01,0xff,0xce,0xb7,0xcc,0x93,0xcc, - 0x80,0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcc,0x80,0x00,0xd1,0x16,0x10,0x0b,0x01, - 0xff,0xce,0xb7,0xcc,0x93,0xcc,0x81,0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcc,0x81, - 0x00,0x10,0x0b,0x01,0xff,0xce,0xb7,0xcc,0x93,0xcd,0x82,0x00,0x01,0xff,0xce,0xb7, - 0xcc,0x94,0xcd,0x82,0x00,0xd3,0x18,0xe2,0xb0,0x59,0xe1,0x99,0x59,0x10,0x09,0x01, - 0xff,0xce,0xb9,0xcc,0x93,0x00,0x01,0xff,0xce,0xb9,0xcc,0x94,0x00,0xd2,0x28,0xd1, - 0x12,0x10,0x09,0x01,0xff,0xce,0xb9,0xcc,0x93,0x00,0x01,0xff,0xce,0xb9,0xcc,0x94, - 0x00,0x10,0x0b,0x01,0xff,0xce,0xb9,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff,0xce,0xb9, - 0xcc,0x94,0xcc,0x80,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0xb9,0xcc,0x93,0xcc, - 0x81,0x00,0x01,0xff,0xce,0xb9,0xcc,0x94,0xcc,0x81,0x00,0x10,0x0b,0x01,0xff,0xce, - 0xb9,0xcc,0x93,0xcd,0x82,0x00,0x01,0xff,0xce,0xb9,0xcc,0x94,0xcd,0x82,0x00,0xcf, - 0x86,0xd5,0xac,0xd4,0x5a,0xd3,0x18,0xe2,0xed,0x59,0xe1,0xd6,0x59,0x10,0x09,0x01, - 0xff,0xce,0xbf,0xcc,0x93,0x00,0x01,0xff,0xce,0xbf,0xcc,0x94,0x00,0xd2,0x28,0xd1, - 0x12,0x10,0x09,0x01,0xff,0xce,0xbf,0xcc,0x93,0x00,0x01,0xff,0xce,0xbf,0xcc,0x94, - 0x00,0x10,0x0b,0x01,0xff,0xce,0xbf,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff,0xce,0xbf, - 0xcc,0x94,0xcc,0x80,0x00,0x91,0x16,0x10,0x0b,0x01,0xff,0xce,0xbf,0xcc,0x93,0xcc, - 0x81,0x00,0x01,0xff,0xce,0xbf,0xcc,0x94,0xcc,0x81,0x00,0x00,0x00,0xd3,0x18,0xe2, - 0x17,0x5a,0xe1,0x00,0x5a,0x10,0x09,0x01,0xff,0xcf,0x85,0xcc,0x93,0x00,0x01,0xff, - 0xcf,0x85,0xcc,0x94,0x00,0xd2,0x1c,0xd1,0x0d,0x10,0x04,0x00,0x00,0x01,0xff,0xcf, - 0x85,0xcc,0x94,0x00,0x10,0x04,0x00,0x00,0x01,0xff,0xcf,0x85,0xcc,0x94,0xcc,0x80, - 0x00,0xd1,0x0f,0x10,0x04,0x00,0x00,0x01,0xff,0xcf,0x85,0xcc,0x94,0xcc,0x81,0x00, - 0x10,0x04,0x00,0x00,0x01,0xff,0xcf,0x85,0xcc,0x94,0xcd,0x82,0x00,0xe4,0xd3,0x5a, - 0xd3,0x18,0xe2,0x52,0x5a,0xe1,0x3b,0x5a,0x10,0x09,0x01,0xff,0xcf,0x89,0xcc,0x93, - 0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0x00,0xd2,0x28,0xd1,0x12,0x10,0x09,0x01,0xff, - 0xcf,0x89,0xcc,0x93,0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0x00,0x10,0x0b,0x01,0xff, - 0xcf,0x89,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xcc,0x80,0x00, - 0xd1,0x16,0x10,0x0b,0x01,0xff,0xcf,0x89,0xcc,0x93,0xcc,0x81,0x00,0x01,0xff,0xcf, - 0x89,0xcc,0x94,0xcc,0x81,0x00,0x10,0x0b,0x01,0xff,0xcf,0x89,0xcc,0x93,0xcd,0x82, - 0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xcd,0x82,0x00,0xe0,0xd9,0x02,0xcf,0x86,0xe5, - 0x91,0x01,0xd4,0xc8,0xd3,0x64,0xd2,0x30,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0xb1, - 0xcc,0x93,0xce,0xb9,0x00,0x01,0xff,0xce,0xb1,0xcc,0x94,0xce,0xb9,0x00,0x10,0x0d, - 0x01,0xff,0xce,0xb1,0xcc,0x93,0xcc,0x80,0xce,0xb9,0x00,0x01,0xff,0xce,0xb1,0xcc, - 0x94,0xcc,0x80,0xce,0xb9,0x00,0xd1,0x1a,0x10,0x0d,0x01,0xff,0xce,0xb1,0xcc,0x93, - 0xcc,0x81,0xce,0xb9,0x00,0x01,0xff,0xce,0xb1,0xcc,0x94,0xcc,0x81,0xce,0xb9,0x00, - 0x10,0x0d,0x01,0xff,0xce,0xb1,0xcc,0x93,0xcd,0x82,0xce,0xb9,0x00,0x01,0xff,0xce, - 0xb1,0xcc,0x94,0xcd,0x82,0xce,0xb9,0x00,0xd2,0x30,0xd1,0x16,0x10,0x0b,0x01,0xff, - 0xce,0xb1,0xcc,0x93,0xce,0xb9,0x00,0x01,0xff,0xce,0xb1,0xcc,0x94,0xce,0xb9,0x00, - 0x10,0x0d,0x01,0xff,0xce,0xb1,0xcc,0x93,0xcc,0x80,0xce,0xb9,0x00,0x01,0xff,0xce, - 0xb1,0xcc,0x94,0xcc,0x80,0xce,0xb9,0x00,0xd1,0x1a,0x10,0x0d,0x01,0xff,0xce,0xb1, - 0xcc,0x93,0xcc,0x81,0xce,0xb9,0x00,0x01,0xff,0xce,0xb1,0xcc,0x94,0xcc,0x81,0xce, - 0xb9,0x00,0x10,0x0d,0x01,0xff,0xce,0xb1,0xcc,0x93,0xcd,0x82,0xce,0xb9,0x00,0x01, - 0xff,0xce,0xb1,0xcc,0x94,0xcd,0x82,0xce,0xb9,0x00,0xd3,0x64,0xd2,0x30,0xd1,0x16, - 0x10,0x0b,0x01,0xff,0xce,0xb7,0xcc,0x93,0xce,0xb9,0x00,0x01,0xff,0xce,0xb7,0xcc, - 0x94,0xce,0xb9,0x00,0x10,0x0d,0x01,0xff,0xce,0xb7,0xcc,0x93,0xcc,0x80,0xce,0xb9, - 0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcc,0x80,0xce,0xb9,0x00,0xd1,0x1a,0x10,0x0d, - 0x01,0xff,0xce,0xb7,0xcc,0x93,0xcc,0x81,0xce,0xb9,0x00,0x01,0xff,0xce,0xb7,0xcc, - 0x94,0xcc,0x81,0xce,0xb9,0x00,0x10,0x0d,0x01,0xff,0xce,0xb7,0xcc,0x93,0xcd,0x82, - 0xce,0xb9,0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcd,0x82,0xce,0xb9,0x00,0xd2,0x30, - 0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0xb7,0xcc,0x93,0xce,0xb9,0x00,0x01,0xff,0xce, - 0xb7,0xcc,0x94,0xce,0xb9,0x00,0x10,0x0d,0x01,0xff,0xce,0xb7,0xcc,0x93,0xcc,0x80, - 0xce,0xb9,0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcc,0x80,0xce,0xb9,0x00,0xd1,0x1a, - 0x10,0x0d,0x01,0xff,0xce,0xb7,0xcc,0x93,0xcc,0x81,0xce,0xb9,0x00,0x01,0xff,0xce, - 0xb7,0xcc,0x94,0xcc,0x81,0xce,0xb9,0x00,0x10,0x0d,0x01,0xff,0xce,0xb7,0xcc,0x93, - 0xcd,0x82,0xce,0xb9,0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcd,0x82,0xce,0xb9,0x00, - 0xd4,0xc8,0xd3,0x64,0xd2,0x30,0xd1,0x16,0x10,0x0b,0x01,0xff,0xcf,0x89,0xcc,0x93, - 0xce,0xb9,0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xce,0xb9,0x00,0x10,0x0d,0x01,0xff, - 0xcf,0x89,0xcc,0x93,0xcc,0x80,0xce,0xb9,0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xcc, - 0x80,0xce,0xb9,0x00,0xd1,0x1a,0x10,0x0d,0x01,0xff,0xcf,0x89,0xcc,0x93,0xcc,0x81, - 0xce,0xb9,0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xcc,0x81,0xce,0xb9,0x00,0x10,0x0d, - 0x01,0xff,0xcf,0x89,0xcc,0x93,0xcd,0x82,0xce,0xb9,0x00,0x01,0xff,0xcf,0x89,0xcc, - 0x94,0xcd,0x82,0xce,0xb9,0x00,0xd2,0x30,0xd1,0x16,0x10,0x0b,0x01,0xff,0xcf,0x89, - 0xcc,0x93,0xce,0xb9,0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xce,0xb9,0x00,0x10,0x0d, - 0x01,0xff,0xcf,0x89,0xcc,0x93,0xcc,0x80,0xce,0xb9,0x00,0x01,0xff,0xcf,0x89,0xcc, - 0x94,0xcc,0x80,0xce,0xb9,0x00,0xd1,0x1a,0x10,0x0d,0x01,0xff,0xcf,0x89,0xcc,0x93, - 0xcc,0x81,0xce,0xb9,0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xcc,0x81,0xce,0xb9,0x00, - 0x10,0x0d,0x01,0xff,0xcf,0x89,0xcc,0x93,0xcd,0x82,0xce,0xb9,0x00,0x01,0xff,0xcf, - 0x89,0xcc,0x94,0xcd,0x82,0xce,0xb9,0x00,0xd3,0x49,0xd2,0x26,0xd1,0x12,0x10,0x09, - 0x01,0xff,0xce,0xb1,0xcc,0x86,0x00,0x01,0xff,0xce,0xb1,0xcc,0x84,0x00,0x10,0x0b, - 0x01,0xff,0xce,0xb1,0xcc,0x80,0xce,0xb9,0x00,0x01,0xff,0xce,0xb1,0xce,0xb9,0x00, - 0xd1,0x0f,0x10,0x0b,0x01,0xff,0xce,0xb1,0xcc,0x81,0xce,0xb9,0x00,0x00,0x00,0x10, - 0x09,0x01,0xff,0xce,0xb1,0xcd,0x82,0x00,0x01,0xff,0xce,0xb1,0xcd,0x82,0xce,0xb9, - 0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb1,0xcc,0x86,0x00,0x01,0xff, - 0xce,0xb1,0xcc,0x84,0x00,0x10,0x09,0x01,0xff,0xce,0xb1,0xcc,0x80,0x00,0x01,0xff, - 0xce,0xb1,0xcc,0x81,0x00,0xe1,0xf3,0x5a,0x10,0x09,0x01,0xff,0xce,0xb1,0xce,0xb9, - 0x00,0x01,0x00,0xcf,0x86,0xd5,0xbd,0xd4,0x7e,0xd3,0x44,0xd2,0x21,0xd1,0x0d,0x10, - 0x04,0x01,0x00,0x01,0xff,0xc2,0xa8,0xcd,0x82,0x00,0x10,0x0b,0x01,0xff,0xce,0xb7, - 0xcc,0x80,0xce,0xb9,0x00,0x01,0xff,0xce,0xb7,0xce,0xb9,0x00,0xd1,0x0f,0x10,0x0b, - 0x01,0xff,0xce,0xb7,0xcc,0x81,0xce,0xb9,0x00,0x00,0x00,0x10,0x09,0x01,0xff,0xce, - 0xb7,0xcd,0x82,0x00,0x01,0xff,0xce,0xb7,0xcd,0x82,0xce,0xb9,0x00,0xd2,0x24,0xd1, - 0x12,0x10,0x09,0x01,0xff,0xce,0xb5,0xcc,0x80,0x00,0x01,0xff,0xce,0xb5,0xcc,0x81, - 0x00,0x10,0x09,0x01,0xff,0xce,0xb7,0xcc,0x80,0x00,0x01,0xff,0xce,0xb7,0xcc,0x81, - 0x00,0xe1,0x02,0x5b,0x10,0x09,0x01,0xff,0xce,0xb7,0xce,0xb9,0x00,0x01,0xff,0xe1, - 0xbe,0xbf,0xcc,0x80,0x00,0xd3,0x18,0xe2,0x28,0x5b,0xe1,0x11,0x5b,0x10,0x09,0x01, - 0xff,0xce,0xb9,0xcc,0x86,0x00,0x01,0xff,0xce,0xb9,0xcc,0x84,0x00,0xe2,0x4c,0x5b, - 0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb9,0xcc,0x86,0x00,0x01,0xff,0xce,0xb9,0xcc, - 0x84,0x00,0x10,0x09,0x01,0xff,0xce,0xb9,0xcc,0x80,0x00,0x01,0xff,0xce,0xb9,0xcc, - 0x81,0x00,0xd4,0x51,0xd3,0x18,0xe2,0x6f,0x5b,0xe1,0x58,0x5b,0x10,0x09,0x01,0xff, - 0xcf,0x85,0xcc,0x86,0x00,0x01,0xff,0xcf,0x85,0xcc,0x84,0x00,0xd2,0x24,0xd1,0x12, - 0x10,0x09,0x01,0xff,0xcf,0x85,0xcc,0x86,0x00,0x01,0xff,0xcf,0x85,0xcc,0x84,0x00, - 0x10,0x09,0x01,0xff,0xcf,0x85,0xcc,0x80,0x00,0x01,0xff,0xcf,0x85,0xcc,0x81,0x00, - 0xe1,0x8f,0x5b,0x10,0x09,0x01,0xff,0xcf,0x81,0xcc,0x94,0x00,0x01,0xff,0xc2,0xa8, - 0xcc,0x80,0x00,0xd3,0x3b,0xd2,0x18,0x51,0x04,0x00,0x00,0x10,0x0b,0x01,0xff,0xcf, - 0x89,0xcc,0x80,0xce,0xb9,0x00,0x01,0xff,0xcf,0x89,0xce,0xb9,0x00,0xd1,0x0f,0x10, - 0x0b,0x01,0xff,0xcf,0x89,0xcc,0x81,0xce,0xb9,0x00,0x00,0x00,0x10,0x09,0x01,0xff, - 0xcf,0x89,0xcd,0x82,0x00,0x01,0xff,0xcf,0x89,0xcd,0x82,0xce,0xb9,0x00,0xd2,0x24, - 0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xbf,0xcc,0x80,0x00,0x01,0xff,0xce,0xbf,0xcc, - 0x81,0x00,0x10,0x09,0x01,0xff,0xcf,0x89,0xcc,0x80,0x00,0x01,0xff,0xcf,0x89,0xcc, - 0x81,0x00,0xe1,0x99,0x5b,0x10,0x09,0x01,0xff,0xcf,0x89,0xce,0xb9,0x00,0x01,0xff, - 0xc2,0xb4,0x00,0xe0,0x0c,0x68,0xcf,0x86,0xe5,0x23,0x02,0xe4,0x25,0x01,0xe3,0x85, - 0x5e,0xd2,0x2a,0xe1,0x5f,0x5c,0xe0,0xdd,0x5b,0xcf,0x86,0xe5,0xbb,0x5b,0x94,0x1b, - 0xe3,0xa4,0x5b,0x92,0x14,0x91,0x10,0x10,0x08,0x01,0xff,0xe2,0x80,0x82,0x00,0x01, - 0xff,0xe2,0x80,0x83,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd1,0xd6,0xd0,0x46,0xcf, - 0x86,0x55,0x04,0x01,0x00,0xd4,0x29,0xd3,0x13,0x52,0x04,0x01,0x00,0x51,0x04,0x01, - 0x00,0x10,0x07,0x01,0xff,0xcf,0x89,0x00,0x01,0x00,0x92,0x12,0x51,0x04,0x01,0x00, - 0x10,0x06,0x01,0xff,0x6b,0x00,0x01,0xff,0x61,0xcc,0x8a,0x00,0x01,0x00,0xe3,0x25, - 0x5d,0x92,0x10,0x51,0x04,0x01,0x00,0x10,0x08,0x01,0xff,0xe2,0x85,0x8e,0x00,0x01, - 0x00,0x01,0x00,0xcf,0x86,0xd5,0x0a,0xe4,0x42,0x5d,0x63,0x2d,0x5d,0x06,0x00,0x94, - 0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0x85,0xb0,0x00,0x01, - 0xff,0xe2,0x85,0xb1,0x00,0x10,0x08,0x01,0xff,0xe2,0x85,0xb2,0x00,0x01,0xff,0xe2, - 0x85,0xb3,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0x85,0xb4,0x00,0x01,0xff,0xe2, - 0x85,0xb5,0x00,0x10,0x08,0x01,0xff,0xe2,0x85,0xb6,0x00,0x01,0xff,0xe2,0x85,0xb7, - 0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0x85,0xb8,0x00,0x01,0xff,0xe2, - 0x85,0xb9,0x00,0x10,0x08,0x01,0xff,0xe2,0x85,0xba,0x00,0x01,0xff,0xe2,0x85,0xbb, - 0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0x85,0xbc,0x00,0x01,0xff,0xe2,0x85,0xbd, - 0x00,0x10,0x08,0x01,0xff,0xe2,0x85,0xbe,0x00,0x01,0xff,0xe2,0x85,0xbf,0x00,0x01, - 0x00,0xe0,0x34,0x5d,0xcf,0x86,0xe5,0x13,0x5d,0xe4,0xf2,0x5c,0xe3,0xe1,0x5c,0xe2, - 0xd4,0x5c,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x04,0xff,0xe2,0x86,0x84,0x00, - 0xe3,0x23,0x61,0xe2,0xf0,0x60,0xd1,0x0c,0xe0,0x9d,0x60,0xcf,0x86,0x65,0x7e,0x60, - 0x01,0x00,0xd0,0x62,0xcf,0x86,0x55,0x04,0x01,0x00,0x54,0x04,0x01,0x00,0xd3,0x18, - 0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x08,0x01,0xff,0xe2,0x93,0x90,0x00, - 0x01,0xff,0xe2,0x93,0x91,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0x93, - 0x92,0x00,0x01,0xff,0xe2,0x93,0x93,0x00,0x10,0x08,0x01,0xff,0xe2,0x93,0x94,0x00, - 0x01,0xff,0xe2,0x93,0x95,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0x93,0x96,0x00, - 0x01,0xff,0xe2,0x93,0x97,0x00,0x10,0x08,0x01,0xff,0xe2,0x93,0x98,0x00,0x01,0xff, - 0xe2,0x93,0x99,0x00,0xcf,0x86,0xe5,0x57,0x60,0x94,0x80,0xd3,0x40,0xd2,0x20,0xd1, - 0x10,0x10,0x08,0x01,0xff,0xe2,0x93,0x9a,0x00,0x01,0xff,0xe2,0x93,0x9b,0x00,0x10, - 0x08,0x01,0xff,0xe2,0x93,0x9c,0x00,0x01,0xff,0xe2,0x93,0x9d,0x00,0xd1,0x10,0x10, - 0x08,0x01,0xff,0xe2,0x93,0x9e,0x00,0x01,0xff,0xe2,0x93,0x9f,0x00,0x10,0x08,0x01, - 0xff,0xe2,0x93,0xa0,0x00,0x01,0xff,0xe2,0x93,0xa1,0x00,0xd2,0x20,0xd1,0x10,0x10, - 0x08,0x01,0xff,0xe2,0x93,0xa2,0x00,0x01,0xff,0xe2,0x93,0xa3,0x00,0x10,0x08,0x01, - 0xff,0xe2,0x93,0xa4,0x00,0x01,0xff,0xe2,0x93,0xa5,0x00,0xd1,0x10,0x10,0x08,0x01, - 0xff,0xe2,0x93,0xa6,0x00,0x01,0xff,0xe2,0x93,0xa7,0x00,0x10,0x08,0x01,0xff,0xe2, - 0x93,0xa8,0x00,0x01,0xff,0xe2,0x93,0xa9,0x00,0x01,0x00,0xd4,0x0c,0xe3,0x33,0x62, - 0xe2,0x2c,0x62,0xcf,0x06,0x04,0x00,0xe3,0x0c,0x65,0xe2,0xff,0x63,0xe1,0x2e,0x02, - 0xe0,0x84,0x01,0xcf,0x86,0xe5,0x01,0x01,0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10, - 0x10,0x08,0x08,0xff,0xe2,0xb0,0xb0,0x00,0x08,0xff,0xe2,0xb0,0xb1,0x00,0x10,0x08, - 0x08,0xff,0xe2,0xb0,0xb2,0x00,0x08,0xff,0xe2,0xb0,0xb3,0x00,0xd1,0x10,0x10,0x08, - 0x08,0xff,0xe2,0xb0,0xb4,0x00,0x08,0xff,0xe2,0xb0,0xb5,0x00,0x10,0x08,0x08,0xff, - 0xe2,0xb0,0xb6,0x00,0x08,0xff,0xe2,0xb0,0xb7,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08, - 0x08,0xff,0xe2,0xb0,0xb8,0x00,0x08,0xff,0xe2,0xb0,0xb9,0x00,0x10,0x08,0x08,0xff, - 0xe2,0xb0,0xba,0x00,0x08,0xff,0xe2,0xb0,0xbb,0x00,0xd1,0x10,0x10,0x08,0x08,0xff, - 0xe2,0xb0,0xbc,0x00,0x08,0xff,0xe2,0xb0,0xbd,0x00,0x10,0x08,0x08,0xff,0xe2,0xb0, - 0xbe,0x00,0x08,0xff,0xe2,0xb0,0xbf,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08, - 0x08,0xff,0xe2,0xb1,0x80,0x00,0x08,0xff,0xe2,0xb1,0x81,0x00,0x10,0x08,0x08,0xff, - 0xe2,0xb1,0x82,0x00,0x08,0xff,0xe2,0xb1,0x83,0x00,0xd1,0x10,0x10,0x08,0x08,0xff, - 0xe2,0xb1,0x84,0x00,0x08,0xff,0xe2,0xb1,0x85,0x00,0x10,0x08,0x08,0xff,0xe2,0xb1, - 0x86,0x00,0x08,0xff,0xe2,0xb1,0x87,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x08,0xff, - 0xe2,0xb1,0x88,0x00,0x08,0xff,0xe2,0xb1,0x89,0x00,0x10,0x08,0x08,0xff,0xe2,0xb1, - 0x8a,0x00,0x08,0xff,0xe2,0xb1,0x8b,0x00,0xd1,0x10,0x10,0x08,0x08,0xff,0xe2,0xb1, - 0x8c,0x00,0x08,0xff,0xe2,0xb1,0x8d,0x00,0x10,0x08,0x08,0xff,0xe2,0xb1,0x8e,0x00, - 0x08,0xff,0xe2,0xb1,0x8f,0x00,0x94,0x7c,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08, - 0x08,0xff,0xe2,0xb1,0x90,0x00,0x08,0xff,0xe2,0xb1,0x91,0x00,0x10,0x08,0x08,0xff, - 0xe2,0xb1,0x92,0x00,0x08,0xff,0xe2,0xb1,0x93,0x00,0xd1,0x10,0x10,0x08,0x08,0xff, - 0xe2,0xb1,0x94,0x00,0x08,0xff,0xe2,0xb1,0x95,0x00,0x10,0x08,0x08,0xff,0xe2,0xb1, - 0x96,0x00,0x08,0xff,0xe2,0xb1,0x97,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x08,0xff, - 0xe2,0xb1,0x98,0x00,0x08,0xff,0xe2,0xb1,0x99,0x00,0x10,0x08,0x08,0xff,0xe2,0xb1, - 0x9a,0x00,0x08,0xff,0xe2,0xb1,0x9b,0x00,0xd1,0x10,0x10,0x08,0x08,0xff,0xe2,0xb1, - 0x9c,0x00,0x08,0xff,0xe2,0xb1,0x9d,0x00,0x10,0x08,0x08,0xff,0xe2,0xb1,0x9e,0x00, - 0x00,0x00,0x08,0x00,0xcf,0x86,0xd5,0x07,0x64,0xef,0x61,0x08,0x00,0xd4,0x63,0xd3, - 0x32,0xd2,0x1b,0xd1,0x0c,0x10,0x08,0x09,0xff,0xe2,0xb1,0xa1,0x00,0x09,0x00,0x10, - 0x07,0x09,0xff,0xc9,0xab,0x00,0x09,0xff,0xe1,0xb5,0xbd,0x00,0xd1,0x0b,0x10,0x07, - 0x09,0xff,0xc9,0xbd,0x00,0x09,0x00,0x10,0x04,0x09,0x00,0x09,0xff,0xe2,0xb1,0xa8, - 0x00,0xd2,0x18,0xd1,0x0c,0x10,0x04,0x09,0x00,0x09,0xff,0xe2,0xb1,0xaa,0x00,0x10, - 0x04,0x09,0x00,0x09,0xff,0xe2,0xb1,0xac,0x00,0xd1,0x0b,0x10,0x04,0x09,0x00,0x0a, - 0xff,0xc9,0x91,0x00,0x10,0x07,0x0a,0xff,0xc9,0xb1,0x00,0x0a,0xff,0xc9,0x90,0x00, - 0xd3,0x27,0xd2,0x17,0xd1,0x0b,0x10,0x07,0x0b,0xff,0xc9,0x92,0x00,0x0a,0x00,0x10, - 0x08,0x0a,0xff,0xe2,0xb1,0xb3,0x00,0x0a,0x00,0x91,0x0c,0x10,0x04,0x09,0x00,0x09, - 0xff,0xe2,0xb1,0xb6,0x00,0x09,0x00,0x52,0x04,0x0a,0x00,0x51,0x04,0x0a,0x00,0x10, - 0x07,0x0b,0xff,0xc8,0xbf,0x00,0x0b,0xff,0xc9,0x80,0x00,0xe0,0x83,0x01,0xcf,0x86, - 0xd5,0xc0,0xd4,0x60,0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb2, - 0x81,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2,0x83,0x00,0x08,0x00,0xd1,0x0c, - 0x10,0x08,0x08,0xff,0xe2,0xb2,0x85,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2, - 0x87,0x00,0x08,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb2,0x89,0x00, - 0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2,0x8b,0x00,0x08,0x00,0xd1,0x0c,0x10,0x08, - 0x08,0xff,0xe2,0xb2,0x8d,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2,0x8f,0x00, - 0x08,0x00,0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb2,0x91,0x00, - 0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2,0x93,0x00,0x08,0x00,0xd1,0x0c,0x10,0x08, - 0x08,0xff,0xe2,0xb2,0x95,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2,0x97,0x00, - 0x08,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb2,0x99,0x00,0x08,0x00, - 0x10,0x08,0x08,0xff,0xe2,0xb2,0x9b,0x00,0x08,0x00,0xd1,0x0c,0x10,0x08,0x08,0xff, - 0xe2,0xb2,0x9d,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2,0x9f,0x00,0x08,0x00, - 0xd4,0x60,0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb2,0xa1,0x00, - 0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2,0xa3,0x00,0x08,0x00,0xd1,0x0c,0x10,0x08, - 0x08,0xff,0xe2,0xb2,0xa5,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2,0xa7,0x00, - 0x08,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb2,0xa9,0x00,0x08,0x00, - 0x10,0x08,0x08,0xff,0xe2,0xb2,0xab,0x00,0x08,0x00,0xd1,0x0c,0x10,0x08,0x08,0xff, - 0xe2,0xb2,0xad,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2,0xaf,0x00,0x08,0x00, - 0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb2,0xb1,0x00,0x08,0x00, - 0x10,0x08,0x08,0xff,0xe2,0xb2,0xb3,0x00,0x08,0x00,0xd1,0x0c,0x10,0x08,0x08,0xff, - 0xe2,0xb2,0xb5,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2,0xb7,0x00,0x08,0x00, - 0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb2,0xb9,0x00,0x08,0x00,0x10,0x08, - 0x08,0xff,0xe2,0xb2,0xbb,0x00,0x08,0x00,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb2, - 0xbd,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2,0xbf,0x00,0x08,0x00,0xcf,0x86, - 0xd5,0xc0,0xd4,0x60,0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb3, - 0x81,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb3,0x83,0x00,0x08,0x00,0xd1,0x0c, - 0x10,0x08,0x08,0xff,0xe2,0xb3,0x85,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb3, - 0x87,0x00,0x08,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb3,0x89,0x00, - 0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb3,0x8b,0x00,0x08,0x00,0xd1,0x0c,0x10,0x08, - 0x08,0xff,0xe2,0xb3,0x8d,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb3,0x8f,0x00, - 0x08,0x00,0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb3,0x91,0x00, - 0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb3,0x93,0x00,0x08,0x00,0xd1,0x0c,0x10,0x08, - 0x08,0xff,0xe2,0xb3,0x95,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb3,0x97,0x00, - 0x08,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb3,0x99,0x00,0x08,0x00, - 0x10,0x08,0x08,0xff,0xe2,0xb3,0x9b,0x00,0x08,0x00,0xd1,0x0c,0x10,0x08,0x08,0xff, - 0xe2,0xb3,0x9d,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb3,0x9f,0x00,0x08,0x00, - 0xd4,0x3b,0xd3,0x1c,0x92,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb3,0xa1,0x00, - 0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb3,0xa3,0x00,0x08,0x00,0x08,0x00,0xd2,0x10, - 0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x0b,0xff,0xe2,0xb3,0xac,0x00,0xe1,0x3b, - 0x5f,0x10,0x04,0x0b,0x00,0x0b,0xff,0xe2,0xb3,0xae,0x00,0xe3,0x40,0x5f,0x92,0x10, - 0x51,0x04,0x0b,0xe6,0x10,0x08,0x0d,0xff,0xe2,0xb3,0xb3,0x00,0x0d,0x00,0x00,0x00, - 0xe2,0x98,0x08,0xd1,0x0b,0xe0,0x11,0x67,0xcf,0x86,0xcf,0x06,0x01,0x00,0xe0,0x65, - 0x6c,0xcf,0x86,0xe5,0xa7,0x05,0xd4,0x06,0xcf,0x06,0x04,0x00,0xd3,0x0c,0xe2,0xf8, - 0x67,0xe1,0x8f,0x67,0xcf,0x06,0x04,0x00,0xe2,0xdb,0x01,0xe1,0x26,0x01,0xd0,0x09, - 0xcf,0x86,0x65,0xf4,0x67,0x0a,0x00,0xcf,0x86,0xd5,0xc0,0xd4,0x60,0xd3,0x30,0xd2, - 0x18,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x99,0x81,0x00,0x0a,0x00,0x10,0x08,0x0a, - 0xff,0xea,0x99,0x83,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x99,0x85, - 0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x99,0x87,0x00,0x0a,0x00,0xd2,0x18,0xd1, - 0x0c,0x10,0x08,0x0a,0xff,0xea,0x99,0x89,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea, - 0x99,0x8b,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x99,0x8d,0x00,0x0a, - 0x00,0x10,0x08,0x0a,0xff,0xea,0x99,0x8f,0x00,0x0a,0x00,0xd3,0x30,0xd2,0x18,0xd1, - 0x0c,0x10,0x08,0x0a,0xff,0xea,0x99,0x91,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea, - 0x99,0x93,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x99,0x95,0x00,0x0a, - 0x00,0x10,0x08,0x0a,0xff,0xea,0x99,0x97,0x00,0x0a,0x00,0xd2,0x18,0xd1,0x0c,0x10, - 0x08,0x0a,0xff,0xea,0x99,0x99,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x99,0x9b, - 0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x99,0x9d,0x00,0x0a,0x00,0x10, - 0x08,0x0a,0xff,0xea,0x99,0x9f,0x00,0x0a,0x00,0xe4,0x5d,0x67,0xd3,0x30,0xd2,0x18, - 0xd1,0x0c,0x10,0x08,0x0c,0xff,0xea,0x99,0xa1,0x00,0x0c,0x00,0x10,0x08,0x0a,0xff, - 0xea,0x99,0xa3,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x99,0xa5,0x00, - 0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x99,0xa7,0x00,0x0a,0x00,0xd2,0x18,0xd1,0x0c, - 0x10,0x08,0x0a,0xff,0xea,0x99,0xa9,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x99, - 0xab,0x00,0x0a,0x00,0xe1,0x0c,0x67,0x10,0x08,0x0a,0xff,0xea,0x99,0xad,0x00,0x0a, - 0x00,0xe0,0x35,0x67,0xcf,0x86,0x95,0xab,0xd4,0x60,0xd3,0x30,0xd2,0x18,0xd1,0x0c, - 0x10,0x08,0x0a,0xff,0xea,0x9a,0x81,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9a, - 0x83,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9a,0x85,0x00,0x0a,0x00, - 0x10,0x08,0x0a,0xff,0xea,0x9a,0x87,0x00,0x0a,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x08, - 0x0a,0xff,0xea,0x9a,0x89,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9a,0x8b,0x00, - 0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9a,0x8d,0x00,0x0a,0x00,0x10,0x08, - 0x0a,0xff,0xea,0x9a,0x8f,0x00,0x0a,0x00,0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x08, - 0x0a,0xff,0xea,0x9a,0x91,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9a,0x93,0x00, - 0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9a,0x95,0x00,0x0a,0x00,0x10,0x08, - 0x0a,0xff,0xea,0x9a,0x97,0x00,0x0a,0x00,0xe2,0x92,0x66,0xd1,0x0c,0x10,0x08,0x10, - 0xff,0xea,0x9a,0x99,0x00,0x10,0x00,0x10,0x08,0x10,0xff,0xea,0x9a,0x9b,0x00,0x10, - 0x00,0x0b,0x00,0xe1,0x10,0x02,0xd0,0xb9,0xcf,0x86,0xd5,0x07,0x64,0x9e,0x66,0x08, - 0x00,0xd4,0x58,0xd3,0x28,0xd2,0x10,0x51,0x04,0x09,0x00,0x10,0x08,0x0a,0xff,0xea, - 0x9c,0xa3,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9c,0xa5,0x00,0x0a, - 0x00,0x10,0x08,0x0a,0xff,0xea,0x9c,0xa7,0x00,0x0a,0x00,0xd2,0x18,0xd1,0x0c,0x10, - 0x08,0x0a,0xff,0xea,0x9c,0xa9,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9c,0xab, - 0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9c,0xad,0x00,0x0a,0x00,0x10, - 0x08,0x0a,0xff,0xea,0x9c,0xaf,0x00,0x0a,0x00,0xd3,0x28,0xd2,0x10,0x51,0x04,0x0a, - 0x00,0x10,0x08,0x0a,0xff,0xea,0x9c,0xb3,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a, - 0xff,0xea,0x9c,0xb5,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9c,0xb7,0x00,0x0a, - 0x00,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9c,0xb9,0x00,0x0a,0x00,0x10, - 0x08,0x0a,0xff,0xea,0x9c,0xbb,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea, - 0x9c,0xbd,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9c,0xbf,0x00,0x0a,0x00,0xcf, - 0x86,0xd5,0xc0,0xd4,0x60,0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea, - 0x9d,0x81,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0x83,0x00,0x0a,0x00,0xd1, - 0x0c,0x10,0x08,0x0a,0xff,0xea,0x9d,0x85,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea, - 0x9d,0x87,0x00,0x0a,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9d,0x89, - 0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0x8b,0x00,0x0a,0x00,0xd1,0x0c,0x10, - 0x08,0x0a,0xff,0xea,0x9d,0x8d,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0x8f, - 0x00,0x0a,0x00,0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9d,0x91, - 0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0x93,0x00,0x0a,0x00,0xd1,0x0c,0x10, - 0x08,0x0a,0xff,0xea,0x9d,0x95,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0x97, - 0x00,0x0a,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9d,0x99,0x00,0x0a, - 0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0x9b,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a, - 0xff,0xea,0x9d,0x9d,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0x9f,0x00,0x0a, - 0x00,0xd4,0x60,0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9d,0xa1, - 0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0xa3,0x00,0x0a,0x00,0xd1,0x0c,0x10, - 0x08,0x0a,0xff,0xea,0x9d,0xa5,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0xa7, - 0x00,0x0a,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9d,0xa9,0x00,0x0a, - 0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0xab,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a, - 0xff,0xea,0x9d,0xad,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0xaf,0x00,0x0a, - 0x00,0x53,0x04,0x0a,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x04,0x0a,0x00,0x0a,0xff,0xea, - 0x9d,0xba,0x00,0x10,0x04,0x0a,0x00,0x0a,0xff,0xea,0x9d,0xbc,0x00,0xd1,0x0c,0x10, - 0x04,0x0a,0x00,0x0a,0xff,0xe1,0xb5,0xb9,0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0xbf, - 0x00,0x0a,0x00,0xe0,0x71,0x01,0xcf,0x86,0xd5,0xa6,0xd4,0x4e,0xd3,0x30,0xd2,0x18, - 0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9e,0x81,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff, - 0xea,0x9e,0x83,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9e,0x85,0x00, - 0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9e,0x87,0x00,0x0a,0x00,0xd2,0x10,0x51,0x04, - 0x0a,0x00,0x10,0x04,0x0a,0x00,0x0a,0xff,0xea,0x9e,0x8c,0x00,0xe1,0x9a,0x64,0x10, - 0x04,0x0a,0x00,0x0c,0xff,0xc9,0xa5,0x00,0xd3,0x28,0xd2,0x18,0xd1,0x0c,0x10,0x08, - 0x0c,0xff,0xea,0x9e,0x91,0x00,0x0c,0x00,0x10,0x08,0x0d,0xff,0xea,0x9e,0x93,0x00, - 0x0d,0x00,0x51,0x04,0x10,0x00,0x10,0x08,0x10,0xff,0xea,0x9e,0x97,0x00,0x10,0x00, - 0xd2,0x18,0xd1,0x0c,0x10,0x08,0x10,0xff,0xea,0x9e,0x99,0x00,0x10,0x00,0x10,0x08, - 0x10,0xff,0xea,0x9e,0x9b,0x00,0x10,0x00,0xd1,0x0c,0x10,0x08,0x10,0xff,0xea,0x9e, - 0x9d,0x00,0x10,0x00,0x10,0x08,0x10,0xff,0xea,0x9e,0x9f,0x00,0x10,0x00,0xd4,0x63, - 0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x0c,0xff,0xea,0x9e,0xa1,0x00,0x0c,0x00, - 0x10,0x08,0x0c,0xff,0xea,0x9e,0xa3,0x00,0x0c,0x00,0xd1,0x0c,0x10,0x08,0x0c,0xff, - 0xea,0x9e,0xa5,0x00,0x0c,0x00,0x10,0x08,0x0c,0xff,0xea,0x9e,0xa7,0x00,0x0c,0x00, - 0xd2,0x1a,0xd1,0x0c,0x10,0x08,0x0c,0xff,0xea,0x9e,0xa9,0x00,0x0c,0x00,0x10,0x07, - 0x0d,0xff,0xc9,0xa6,0x00,0x10,0xff,0xc9,0x9c,0x00,0xd1,0x0e,0x10,0x07,0x10,0xff, - 0xc9,0xa1,0x00,0x10,0xff,0xc9,0xac,0x00,0x10,0x07,0x12,0xff,0xc9,0xaa,0x00,0x14, - 0x00,0xd3,0x35,0xd2,0x1d,0xd1,0x0e,0x10,0x07,0x10,0xff,0xca,0x9e,0x00,0x10,0xff, - 0xca,0x87,0x00,0x10,0x07,0x11,0xff,0xca,0x9d,0x00,0x11,0xff,0xea,0xad,0x93,0x00, - 0xd1,0x0c,0x10,0x08,0x11,0xff,0xea,0x9e,0xb5,0x00,0x11,0x00,0x10,0x08,0x11,0xff, - 0xea,0x9e,0xb7,0x00,0x11,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x14,0xff,0xea,0x9e, - 0xb9,0x00,0x14,0x00,0x10,0x08,0x15,0xff,0xea,0x9e,0xbb,0x00,0x15,0x00,0xd1,0x0c, - 0x10,0x08,0x15,0xff,0xea,0x9e,0xbd,0x00,0x15,0x00,0x10,0x08,0x15,0xff,0xea,0x9e, - 0xbf,0x00,0x15,0x00,0xcf,0x86,0xe5,0xd4,0x63,0x94,0x2f,0x93,0x2b,0xd2,0x10,0x51, - 0x04,0x00,0x00,0x10,0x08,0x15,0xff,0xea,0x9f,0x83,0x00,0x15,0x00,0xd1,0x0f,0x10, - 0x08,0x15,0xff,0xea,0x9e,0x94,0x00,0x15,0xff,0xca,0x82,0x00,0x10,0x08,0x15,0xff, - 0xe1,0xb6,0x8e,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xe4,0xb4,0x66,0xd3,0x1d,0xe2, - 0x5b,0x64,0xe1,0x0a,0x64,0xe0,0xf7,0x63,0xcf,0x86,0xe5,0xd8,0x63,0x94,0x0b,0x93, - 0x07,0x62,0xc3,0x63,0x08,0x00,0x08,0x00,0x08,0x00,0xd2,0x0f,0xe1,0x5a,0x65,0xe0, - 0x27,0x65,0xcf,0x86,0x65,0x0c,0x65,0x0a,0x00,0xd1,0xab,0xd0,0x1a,0xcf,0x86,0xe5, - 0x17,0x66,0xe4,0xfa,0x65,0xe3,0xe1,0x65,0xe2,0xd4,0x65,0x91,0x08,0x10,0x04,0x00, - 0x00,0x0c,0x00,0x0c,0x00,0xcf,0x86,0x55,0x04,0x10,0x00,0xd4,0x0b,0x93,0x07,0x62, - 0x27,0x66,0x11,0x00,0x00,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x11,0xff, - 0xe1,0x8e,0xa0,0x00,0x11,0xff,0xe1,0x8e,0xa1,0x00,0x10,0x08,0x11,0xff,0xe1,0x8e, - 0xa2,0x00,0x11,0xff,0xe1,0x8e,0xa3,0x00,0xd1,0x10,0x10,0x08,0x11,0xff,0xe1,0x8e, - 0xa4,0x00,0x11,0xff,0xe1,0x8e,0xa5,0x00,0x10,0x08,0x11,0xff,0xe1,0x8e,0xa6,0x00, - 0x11,0xff,0xe1,0x8e,0xa7,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x11,0xff,0xe1,0x8e, - 0xa8,0x00,0x11,0xff,0xe1,0x8e,0xa9,0x00,0x10,0x08,0x11,0xff,0xe1,0x8e,0xaa,0x00, - 0x11,0xff,0xe1,0x8e,0xab,0x00,0xd1,0x10,0x10,0x08,0x11,0xff,0xe1,0x8e,0xac,0x00, - 0x11,0xff,0xe1,0x8e,0xad,0x00,0x10,0x08,0x11,0xff,0xe1,0x8e,0xae,0x00,0x11,0xff, - 0xe1,0x8e,0xaf,0x00,0xe0,0xb2,0x65,0xcf,0x86,0xe5,0x01,0x01,0xd4,0x80,0xd3,0x40, - 0xd2,0x20,0xd1,0x10,0x10,0x08,0x11,0xff,0xe1,0x8e,0xb0,0x00,0x11,0xff,0xe1,0x8e, - 0xb1,0x00,0x10,0x08,0x11,0xff,0xe1,0x8e,0xb2,0x00,0x11,0xff,0xe1,0x8e,0xb3,0x00, - 0xd1,0x10,0x10,0x08,0x11,0xff,0xe1,0x8e,0xb4,0x00,0x11,0xff,0xe1,0x8e,0xb5,0x00, - 0x10,0x08,0x11,0xff,0xe1,0x8e,0xb6,0x00,0x11,0xff,0xe1,0x8e,0xb7,0x00,0xd2,0x20, - 0xd1,0x10,0x10,0x08,0x11,0xff,0xe1,0x8e,0xb8,0x00,0x11,0xff,0xe1,0x8e,0xb9,0x00, - 0x10,0x08,0x11,0xff,0xe1,0x8e,0xba,0x00,0x11,0xff,0xe1,0x8e,0xbb,0x00,0xd1,0x10, - 0x10,0x08,0x11,0xff,0xe1,0x8e,0xbc,0x00,0x11,0xff,0xe1,0x8e,0xbd,0x00,0x10,0x08, - 0x11,0xff,0xe1,0x8e,0xbe,0x00,0x11,0xff,0xe1,0x8e,0xbf,0x00,0xd3,0x40,0xd2,0x20, - 0xd1,0x10,0x10,0x08,0x11,0xff,0xe1,0x8f,0x80,0x00,0x11,0xff,0xe1,0x8f,0x81,0x00, - 0x10,0x08,0x11,0xff,0xe1,0x8f,0x82,0x00,0x11,0xff,0xe1,0x8f,0x83,0x00,0xd1,0x10, - 0x10,0x08,0x11,0xff,0xe1,0x8f,0x84,0x00,0x11,0xff,0xe1,0x8f,0x85,0x00,0x10,0x08, - 0x11,0xff,0xe1,0x8f,0x86,0x00,0x11,0xff,0xe1,0x8f,0x87,0x00,0xd2,0x20,0xd1,0x10, - 0x10,0x08,0x11,0xff,0xe1,0x8f,0x88,0x00,0x11,0xff,0xe1,0x8f,0x89,0x00,0x10,0x08, - 0x11,0xff,0xe1,0x8f,0x8a,0x00,0x11,0xff,0xe1,0x8f,0x8b,0x00,0xd1,0x10,0x10,0x08, - 0x11,0xff,0xe1,0x8f,0x8c,0x00,0x11,0xff,0xe1,0x8f,0x8d,0x00,0x10,0x08,0x11,0xff, - 0xe1,0x8f,0x8e,0x00,0x11,0xff,0xe1,0x8f,0x8f,0x00,0xd4,0x80,0xd3,0x40,0xd2,0x20, - 0xd1,0x10,0x10,0x08,0x11,0xff,0xe1,0x8f,0x90,0x00,0x11,0xff,0xe1,0x8f,0x91,0x00, - 0x10,0x08,0x11,0xff,0xe1,0x8f,0x92,0x00,0x11,0xff,0xe1,0x8f,0x93,0x00,0xd1,0x10, - 0x10,0x08,0x11,0xff,0xe1,0x8f,0x94,0x00,0x11,0xff,0xe1,0x8f,0x95,0x00,0x10,0x08, - 0x11,0xff,0xe1,0x8f,0x96,0x00,0x11,0xff,0xe1,0x8f,0x97,0x00,0xd2,0x20,0xd1,0x10, - 0x10,0x08,0x11,0xff,0xe1,0x8f,0x98,0x00,0x11,0xff,0xe1,0x8f,0x99,0x00,0x10,0x08, - 0x11,0xff,0xe1,0x8f,0x9a,0x00,0x11,0xff,0xe1,0x8f,0x9b,0x00,0xd1,0x10,0x10,0x08, - 0x11,0xff,0xe1,0x8f,0x9c,0x00,0x11,0xff,0xe1,0x8f,0x9d,0x00,0x10,0x08,0x11,0xff, - 0xe1,0x8f,0x9e,0x00,0x11,0xff,0xe1,0x8f,0x9f,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10, - 0x10,0x08,0x11,0xff,0xe1,0x8f,0xa0,0x00,0x11,0xff,0xe1,0x8f,0xa1,0x00,0x10,0x08, - 0x11,0xff,0xe1,0x8f,0xa2,0x00,0x11,0xff,0xe1,0x8f,0xa3,0x00,0xd1,0x10,0x10,0x08, - 0x11,0xff,0xe1,0x8f,0xa4,0x00,0x11,0xff,0xe1,0x8f,0xa5,0x00,0x10,0x08,0x11,0xff, - 0xe1,0x8f,0xa6,0x00,0x11,0xff,0xe1,0x8f,0xa7,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08, - 0x11,0xff,0xe1,0x8f,0xa8,0x00,0x11,0xff,0xe1,0x8f,0xa9,0x00,0x10,0x08,0x11,0xff, - 0xe1,0x8f,0xaa,0x00,0x11,0xff,0xe1,0x8f,0xab,0x00,0xd1,0x10,0x10,0x08,0x11,0xff, - 0xe1,0x8f,0xac,0x00,0x11,0xff,0xe1,0x8f,0xad,0x00,0x10,0x08,0x11,0xff,0xe1,0x8f, - 0xae,0x00,0x11,0xff,0xe1,0x8f,0xaf,0x00,0xd1,0x0c,0xe0,0xeb,0x63,0xcf,0x86,0xcf, - 0x06,0x02,0xff,0xff,0xd0,0x08,0xcf,0x86,0xcf,0x06,0x01,0x00,0xcf,0x86,0xd5,0x06, - 0xcf,0x06,0x01,0x00,0xd4,0xae,0xd3,0x09,0xe2,0x54,0x64,0xcf,0x06,0x01,0x00,0xd2, - 0x27,0xe1,0x1f,0x70,0xe0,0x26,0x6e,0xcf,0x86,0xe5,0x3f,0x6d,0xe4,0xce,0x6c,0xe3, - 0x99,0x6c,0xe2,0x78,0x6c,0xe1,0x67,0x6c,0x10,0x08,0x01,0xff,0xe5,0x88,0x87,0x00, - 0x01,0xff,0xe5,0xba,0xa6,0x00,0xe1,0x74,0x74,0xe0,0xe8,0x73,0xcf,0x86,0xe5,0x22, - 0x73,0xd4,0x3b,0x93,0x37,0xd2,0x1d,0xd1,0x0e,0x10,0x07,0x01,0xff,0x66,0x66,0x00, - 0x01,0xff,0x66,0x69,0x00,0x10,0x07,0x01,0xff,0x66,0x6c,0x00,0x01,0xff,0x66,0x66, - 0x69,0x00,0xd1,0x0f,0x10,0x08,0x01,0xff,0x66,0x66,0x6c,0x00,0x01,0xff,0x73,0x74, - 0x00,0x10,0x07,0x01,0xff,0x73,0x74,0x00,0x00,0x00,0x00,0x00,0xe3,0xc8,0x72,0xd2, - 0x11,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x01,0xff,0xd5,0xb4,0xd5,0xb6,0x00, - 0xd1,0x12,0x10,0x09,0x01,0xff,0xd5,0xb4,0xd5,0xa5,0x00,0x01,0xff,0xd5,0xb4,0xd5, - 0xab,0x00,0x10,0x09,0x01,0xff,0xd5,0xbe,0xd5,0xb6,0x00,0x01,0xff,0xd5,0xb4,0xd5, - 0xad,0x00,0xd3,0x09,0xe2,0x40,0x74,0xcf,0x06,0x01,0x00,0xd2,0x13,0xe1,0x30,0x75, - 0xe0,0xc1,0x74,0xcf,0x86,0xe5,0x9e,0x74,0x64,0x8d,0x74,0x06,0xff,0x00,0xe1,0x96, - 0x75,0xe0,0x63,0x75,0xcf,0x86,0xd5,0x18,0x94,0x14,0x93,0x10,0x92,0x0c,0x91,0x08, - 0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd4,0x7c, - 0xd3,0x3c,0xd2,0x1c,0xd1,0x0c,0x10,0x04,0x01,0x00,0x01,0xff,0xef,0xbd,0x81,0x00, - 0x10,0x08,0x01,0xff,0xef,0xbd,0x82,0x00,0x01,0xff,0xef,0xbd,0x83,0x00,0xd1,0x10, - 0x10,0x08,0x01,0xff,0xef,0xbd,0x84,0x00,0x01,0xff,0xef,0xbd,0x85,0x00,0x10,0x08, - 0x01,0xff,0xef,0xbd,0x86,0x00,0x01,0xff,0xef,0xbd,0x87,0x00,0xd2,0x20,0xd1,0x10, - 0x10,0x08,0x01,0xff,0xef,0xbd,0x88,0x00,0x01,0xff,0xef,0xbd,0x89,0x00,0x10,0x08, - 0x01,0xff,0xef,0xbd,0x8a,0x00,0x01,0xff,0xef,0xbd,0x8b,0x00,0xd1,0x10,0x10,0x08, - 0x01,0xff,0xef,0xbd,0x8c,0x00,0x01,0xff,0xef,0xbd,0x8d,0x00,0x10,0x08,0x01,0xff, - 0xef,0xbd,0x8e,0x00,0x01,0xff,0xef,0xbd,0x8f,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10, - 0x10,0x08,0x01,0xff,0xef,0xbd,0x90,0x00,0x01,0xff,0xef,0xbd,0x91,0x00,0x10,0x08, - 0x01,0xff,0xef,0xbd,0x92,0x00,0x01,0xff,0xef,0xbd,0x93,0x00,0xd1,0x10,0x10,0x08, - 0x01,0xff,0xef,0xbd,0x94,0x00,0x01,0xff,0xef,0xbd,0x95,0x00,0x10,0x08,0x01,0xff, - 0xef,0xbd,0x96,0x00,0x01,0xff,0xef,0xbd,0x97,0x00,0x92,0x1c,0xd1,0x10,0x10,0x08, - 0x01,0xff,0xef,0xbd,0x98,0x00,0x01,0xff,0xef,0xbd,0x99,0x00,0x10,0x08,0x01,0xff, - 0xef,0xbd,0x9a,0x00,0x01,0x00,0x01,0x00,0x83,0xe2,0x87,0xb3,0xe1,0x60,0xb0,0xe0, - 0xdd,0xae,0xcf,0x86,0xe5,0x81,0x9b,0xc4,0xe3,0xc1,0x07,0xe2,0x62,0x06,0xe1,0x11, - 0x86,0xe0,0x09,0x05,0xcf,0x86,0xe5,0xfb,0x02,0xd4,0x1c,0xe3,0x7f,0x76,0xe2,0xd6, - 0x75,0xe1,0xb1,0x75,0xe0,0x8a,0x75,0xcf,0x86,0xe5,0x57,0x75,0x94,0x07,0x63,0x42, - 0x75,0x07,0x00,0x07,0x00,0xe3,0x2b,0x78,0xe2,0xf0,0x77,0xe1,0x77,0x01,0xe0,0x88, - 0x77,0xcf,0x86,0xe5,0x21,0x01,0xd4,0x90,0xd3,0x48,0xd2,0x24,0xd1,0x12,0x10,0x09, - 0x05,0xff,0xf0,0x90,0x90,0xa8,0x00,0x05,0xff,0xf0,0x90,0x90,0xa9,0x00,0x10,0x09, - 0x05,0xff,0xf0,0x90,0x90,0xaa,0x00,0x05,0xff,0xf0,0x90,0x90,0xab,0x00,0xd1,0x12, - 0x10,0x09,0x05,0xff,0xf0,0x90,0x90,0xac,0x00,0x05,0xff,0xf0,0x90,0x90,0xad,0x00, - 0x10,0x09,0x05,0xff,0xf0,0x90,0x90,0xae,0x00,0x05,0xff,0xf0,0x90,0x90,0xaf,0x00, - 0xd2,0x24,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0x90,0x90,0xb0,0x00,0x05,0xff,0xf0, - 0x90,0x90,0xb1,0x00,0x10,0x09,0x05,0xff,0xf0,0x90,0x90,0xb2,0x00,0x05,0xff,0xf0, - 0x90,0x90,0xb3,0x00,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0x90,0x90,0xb4,0x00,0x05, - 0xff,0xf0,0x90,0x90,0xb5,0x00,0x10,0x09,0x05,0xff,0xf0,0x90,0x90,0xb6,0x00,0x05, - 0xff,0xf0,0x90,0x90,0xb7,0x00,0xd3,0x48,0xd2,0x24,0xd1,0x12,0x10,0x09,0x05,0xff, - 0xf0,0x90,0x90,0xb8,0x00,0x05,0xff,0xf0,0x90,0x90,0xb9,0x00,0x10,0x09,0x05,0xff, - 0xf0,0x90,0x90,0xba,0x00,0x05,0xff,0xf0,0x90,0x90,0xbb,0x00,0xd1,0x12,0x10,0x09, - 0x05,0xff,0xf0,0x90,0x90,0xbc,0x00,0x05,0xff,0xf0,0x90,0x90,0xbd,0x00,0x10,0x09, - 0x05,0xff,0xf0,0x90,0x90,0xbe,0x00,0x05,0xff,0xf0,0x90,0x90,0xbf,0x00,0xd2,0x24, - 0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0x90,0x91,0x80,0x00,0x05,0xff,0xf0,0x90,0x91, - 0x81,0x00,0x10,0x09,0x05,0xff,0xf0,0x90,0x91,0x82,0x00,0x05,0xff,0xf0,0x90,0x91, - 0x83,0x00,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0x90,0x91,0x84,0x00,0x05,0xff,0xf0, - 0x90,0x91,0x85,0x00,0x10,0x09,0x05,0xff,0xf0,0x90,0x91,0x86,0x00,0x05,0xff,0xf0, - 0x90,0x91,0x87,0x00,0x94,0x4c,0x93,0x48,0xd2,0x24,0xd1,0x12,0x10,0x09,0x05,0xff, - 0xf0,0x90,0x91,0x88,0x00,0x05,0xff,0xf0,0x90,0x91,0x89,0x00,0x10,0x09,0x05,0xff, - 0xf0,0x90,0x91,0x8a,0x00,0x05,0xff,0xf0,0x90,0x91,0x8b,0x00,0xd1,0x12,0x10,0x09, - 0x05,0xff,0xf0,0x90,0x91,0x8c,0x00,0x05,0xff,0xf0,0x90,0x91,0x8d,0x00,0x10,0x09, - 0x07,0xff,0xf0,0x90,0x91,0x8e,0x00,0x07,0xff,0xf0,0x90,0x91,0x8f,0x00,0x05,0x00, - 0x05,0x00,0xd0,0xa0,0xcf,0x86,0xd5,0x07,0x64,0x30,0x76,0x07,0x00,0xd4,0x07,0x63, - 0x3d,0x76,0x07,0x00,0xd3,0x48,0xd2,0x24,0xd1,0x12,0x10,0x09,0x12,0xff,0xf0,0x90, - 0x93,0x98,0x00,0x12,0xff,0xf0,0x90,0x93,0x99,0x00,0x10,0x09,0x12,0xff,0xf0,0x90, - 0x93,0x9a,0x00,0x12,0xff,0xf0,0x90,0x93,0x9b,0x00,0xd1,0x12,0x10,0x09,0x12,0xff, - 0xf0,0x90,0x93,0x9c,0x00,0x12,0xff,0xf0,0x90,0x93,0x9d,0x00,0x10,0x09,0x12,0xff, - 0xf0,0x90,0x93,0x9e,0x00,0x12,0xff,0xf0,0x90,0x93,0x9f,0x00,0xd2,0x24,0xd1,0x12, - 0x10,0x09,0x12,0xff,0xf0,0x90,0x93,0xa0,0x00,0x12,0xff,0xf0,0x90,0x93,0xa1,0x00, - 0x10,0x09,0x12,0xff,0xf0,0x90,0x93,0xa2,0x00,0x12,0xff,0xf0,0x90,0x93,0xa3,0x00, - 0xd1,0x12,0x10,0x09,0x12,0xff,0xf0,0x90,0x93,0xa4,0x00,0x12,0xff,0xf0,0x90,0x93, - 0xa5,0x00,0x10,0x09,0x12,0xff,0xf0,0x90,0x93,0xa6,0x00,0x12,0xff,0xf0,0x90,0x93, - 0xa7,0x00,0xcf,0x86,0xe5,0xc6,0x75,0xd4,0x90,0xd3,0x48,0xd2,0x24,0xd1,0x12,0x10, - 0x09,0x12,0xff,0xf0,0x90,0x93,0xa8,0x00,0x12,0xff,0xf0,0x90,0x93,0xa9,0x00,0x10, - 0x09,0x12,0xff,0xf0,0x90,0x93,0xaa,0x00,0x12,0xff,0xf0,0x90,0x93,0xab,0x00,0xd1, - 0x12,0x10,0x09,0x12,0xff,0xf0,0x90,0x93,0xac,0x00,0x12,0xff,0xf0,0x90,0x93,0xad, - 0x00,0x10,0x09,0x12,0xff,0xf0,0x90,0x93,0xae,0x00,0x12,0xff,0xf0,0x90,0x93,0xaf, - 0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x12,0xff,0xf0,0x90,0x93,0xb0,0x00,0x12,0xff, - 0xf0,0x90,0x93,0xb1,0x00,0x10,0x09,0x12,0xff,0xf0,0x90,0x93,0xb2,0x00,0x12,0xff, - 0xf0,0x90,0x93,0xb3,0x00,0xd1,0x12,0x10,0x09,0x12,0xff,0xf0,0x90,0x93,0xb4,0x00, - 0x12,0xff,0xf0,0x90,0x93,0xb5,0x00,0x10,0x09,0x12,0xff,0xf0,0x90,0x93,0xb6,0x00, - 0x12,0xff,0xf0,0x90,0x93,0xb7,0x00,0x93,0x28,0x92,0x24,0xd1,0x12,0x10,0x09,0x12, - 0xff,0xf0,0x90,0x93,0xb8,0x00,0x12,0xff,0xf0,0x90,0x93,0xb9,0x00,0x10,0x09,0x12, - 0xff,0xf0,0x90,0x93,0xba,0x00,0x12,0xff,0xf0,0x90,0x93,0xbb,0x00,0x00,0x00,0x12, - 0x00,0xd4,0x1f,0xe3,0xdf,0x76,0xe2,0x6a,0x76,0xe1,0x09,0x76,0xe0,0xea,0x75,0xcf, - 0x86,0xe5,0xb7,0x75,0x94,0x0a,0xe3,0xa2,0x75,0x62,0x99,0x75,0x07,0x00,0x07,0x00, - 0xe3,0xde,0x78,0xe2,0xaf,0x78,0xd1,0x09,0xe0,0x4c,0x78,0xcf,0x06,0x0b,0x00,0xe0, - 0x7f,0x78,0xcf,0x86,0xe5,0x21,0x01,0xd4,0x90,0xd3,0x48,0xd2,0x24,0xd1,0x12,0x10, - 0x09,0x11,0xff,0xf0,0x90,0xb3,0x80,0x00,0x11,0xff,0xf0,0x90,0xb3,0x81,0x00,0x10, - 0x09,0x11,0xff,0xf0,0x90,0xb3,0x82,0x00,0x11,0xff,0xf0,0x90,0xb3,0x83,0x00,0xd1, - 0x12,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0x84,0x00,0x11,0xff,0xf0,0x90,0xb3,0x85, - 0x00,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0x86,0x00,0x11,0xff,0xf0,0x90,0xb3,0x87, - 0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0x88,0x00,0x11,0xff, - 0xf0,0x90,0xb3,0x89,0x00,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0x8a,0x00,0x11,0xff, - 0xf0,0x90,0xb3,0x8b,0x00,0xd1,0x12,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0x8c,0x00, - 0x11,0xff,0xf0,0x90,0xb3,0x8d,0x00,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0x8e,0x00, - 0x11,0xff,0xf0,0x90,0xb3,0x8f,0x00,0xd3,0x48,0xd2,0x24,0xd1,0x12,0x10,0x09,0x11, - 0xff,0xf0,0x90,0xb3,0x90,0x00,0x11,0xff,0xf0,0x90,0xb3,0x91,0x00,0x10,0x09,0x11, - 0xff,0xf0,0x90,0xb3,0x92,0x00,0x11,0xff,0xf0,0x90,0xb3,0x93,0x00,0xd1,0x12,0x10, - 0x09,0x11,0xff,0xf0,0x90,0xb3,0x94,0x00,0x11,0xff,0xf0,0x90,0xb3,0x95,0x00,0x10, - 0x09,0x11,0xff,0xf0,0x90,0xb3,0x96,0x00,0x11,0xff,0xf0,0x90,0xb3,0x97,0x00,0xd2, - 0x24,0xd1,0x12,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0x98,0x00,0x11,0xff,0xf0,0x90, - 0xb3,0x99,0x00,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0x9a,0x00,0x11,0xff,0xf0,0x90, - 0xb3,0x9b,0x00,0xd1,0x12,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0x9c,0x00,0x11,0xff, - 0xf0,0x90,0xb3,0x9d,0x00,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0x9e,0x00,0x11,0xff, - 0xf0,0x90,0xb3,0x9f,0x00,0xd4,0x90,0xd3,0x48,0xd2,0x24,0xd1,0x12,0x10,0x09,0x11, - 0xff,0xf0,0x90,0xb3,0xa0,0x00,0x11,0xff,0xf0,0x90,0xb3,0xa1,0x00,0x10,0x09,0x11, - 0xff,0xf0,0x90,0xb3,0xa2,0x00,0x11,0xff,0xf0,0x90,0xb3,0xa3,0x00,0xd1,0x12,0x10, - 0x09,0x11,0xff,0xf0,0x90,0xb3,0xa4,0x00,0x11,0xff,0xf0,0x90,0xb3,0xa5,0x00,0x10, - 0x09,0x11,0xff,0xf0,0x90,0xb3,0xa6,0x00,0x11,0xff,0xf0,0x90,0xb3,0xa7,0x00,0xd2, - 0x24,0xd1,0x12,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0xa8,0x00,0x11,0xff,0xf0,0x90, - 0xb3,0xa9,0x00,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0xaa,0x00,0x11,0xff,0xf0,0x90, - 0xb3,0xab,0x00,0xd1,0x12,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0xac,0x00,0x11,0xff, - 0xf0,0x90,0xb3,0xad,0x00,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0xae,0x00,0x11,0xff, - 0xf0,0x90,0xb3,0xaf,0x00,0x93,0x23,0x92,0x1f,0xd1,0x12,0x10,0x09,0x11,0xff,0xf0, - 0x90,0xb3,0xb0,0x00,0x11,0xff,0xf0,0x90,0xb3,0xb1,0x00,0x10,0x09,0x11,0xff,0xf0, - 0x90,0xb3,0xb2,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0xd5,0x15,0xe4,0x91, - 0x7b,0xe3,0x9b,0x79,0xe2,0x94,0x78,0xe1,0xe4,0x77,0xe0,0x9d,0x77,0xcf,0x06,0x0c, - 0x00,0xe4,0xeb,0x7e,0xe3,0x44,0x7e,0xe2,0xed,0x7d,0xd1,0x0c,0xe0,0xb2,0x7d,0xcf, - 0x86,0x65,0x93,0x7d,0x14,0x00,0xe0,0xb6,0x7d,0xcf,0x86,0x55,0x04,0x00,0x00,0xd4, - 0x90,0xd3,0x48,0xd2,0x24,0xd1,0x12,0x10,0x09,0x10,0xff,0xf0,0x91,0xa3,0x80,0x00, - 0x10,0xff,0xf0,0x91,0xa3,0x81,0x00,0x10,0x09,0x10,0xff,0xf0,0x91,0xa3,0x82,0x00, - 0x10,0xff,0xf0,0x91,0xa3,0x83,0x00,0xd1,0x12,0x10,0x09,0x10,0xff,0xf0,0x91,0xa3, - 0x84,0x00,0x10,0xff,0xf0,0x91,0xa3,0x85,0x00,0x10,0x09,0x10,0xff,0xf0,0x91,0xa3, - 0x86,0x00,0x10,0xff,0xf0,0x91,0xa3,0x87,0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x10, - 0xff,0xf0,0x91,0xa3,0x88,0x00,0x10,0xff,0xf0,0x91,0xa3,0x89,0x00,0x10,0x09,0x10, - 0xff,0xf0,0x91,0xa3,0x8a,0x00,0x10,0xff,0xf0,0x91,0xa3,0x8b,0x00,0xd1,0x12,0x10, - 0x09,0x10,0xff,0xf0,0x91,0xa3,0x8c,0x00,0x10,0xff,0xf0,0x91,0xa3,0x8d,0x00,0x10, - 0x09,0x10,0xff,0xf0,0x91,0xa3,0x8e,0x00,0x10,0xff,0xf0,0x91,0xa3,0x8f,0x00,0xd3, - 0x48,0xd2,0x24,0xd1,0x12,0x10,0x09,0x10,0xff,0xf0,0x91,0xa3,0x90,0x00,0x10,0xff, - 0xf0,0x91,0xa3,0x91,0x00,0x10,0x09,0x10,0xff,0xf0,0x91,0xa3,0x92,0x00,0x10,0xff, - 0xf0,0x91,0xa3,0x93,0x00,0xd1,0x12,0x10,0x09,0x10,0xff,0xf0,0x91,0xa3,0x94,0x00, - 0x10,0xff,0xf0,0x91,0xa3,0x95,0x00,0x10,0x09,0x10,0xff,0xf0,0x91,0xa3,0x96,0x00, - 0x10,0xff,0xf0,0x91,0xa3,0x97,0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x10,0xff,0xf0, - 0x91,0xa3,0x98,0x00,0x10,0xff,0xf0,0x91,0xa3,0x99,0x00,0x10,0x09,0x10,0xff,0xf0, - 0x91,0xa3,0x9a,0x00,0x10,0xff,0xf0,0x91,0xa3,0x9b,0x00,0xd1,0x12,0x10,0x09,0x10, - 0xff,0xf0,0x91,0xa3,0x9c,0x00,0x10,0xff,0xf0,0x91,0xa3,0x9d,0x00,0x10,0x09,0x10, - 0xff,0xf0,0x91,0xa3,0x9e,0x00,0x10,0xff,0xf0,0x91,0xa3,0x9f,0x00,0xd1,0x11,0xe0, - 0x12,0x81,0xcf,0x86,0xe5,0x09,0x81,0xe4,0xd2,0x80,0xcf,0x06,0x00,0x00,0xe0,0xdb, - 0x82,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x09,0xe3,0x10,0x81,0xcf,0x06, - 0x0c,0x00,0xd3,0x06,0xcf,0x06,0x00,0x00,0xe2,0x3b,0x82,0xe1,0x16,0x82,0xd0,0x06, - 0xcf,0x06,0x00,0x00,0xcf,0x86,0xa5,0x21,0x01,0xd4,0x90,0xd3,0x48,0xd2,0x24,0xd1, - 0x12,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xa0,0x00,0x14,0xff,0xf0,0x96,0xb9,0xa1, - 0x00,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xa2,0x00,0x14,0xff,0xf0,0x96,0xb9,0xa3, - 0x00,0xd1,0x12,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xa4,0x00,0x14,0xff,0xf0,0x96, - 0xb9,0xa5,0x00,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xa6,0x00,0x14,0xff,0xf0,0x96, - 0xb9,0xa7,0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xa8,0x00, - 0x14,0xff,0xf0,0x96,0xb9,0xa9,0x00,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xaa,0x00, - 0x14,0xff,0xf0,0x96,0xb9,0xab,0x00,0xd1,0x12,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9, - 0xac,0x00,0x14,0xff,0xf0,0x96,0xb9,0xad,0x00,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9, - 0xae,0x00,0x14,0xff,0xf0,0x96,0xb9,0xaf,0x00,0xd3,0x48,0xd2,0x24,0xd1,0x12,0x10, - 0x09,0x14,0xff,0xf0,0x96,0xb9,0xb0,0x00,0x14,0xff,0xf0,0x96,0xb9,0xb1,0x00,0x10, - 0x09,0x14,0xff,0xf0,0x96,0xb9,0xb2,0x00,0x14,0xff,0xf0,0x96,0xb9,0xb3,0x00,0xd1, - 0x12,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xb4,0x00,0x14,0xff,0xf0,0x96,0xb9,0xb5, - 0x00,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xb6,0x00,0x14,0xff,0xf0,0x96,0xb9,0xb7, - 0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xb8,0x00,0x14,0xff, - 0xf0,0x96,0xb9,0xb9,0x00,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xba,0x00,0x14,0xff, - 0xf0,0x96,0xb9,0xbb,0x00,0xd1,0x12,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xbc,0x00, - 0x14,0xff,0xf0,0x96,0xb9,0xbd,0x00,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xbe,0x00, - 0x14,0xff,0xf0,0x96,0xb9,0xbf,0x00,0x14,0x00,0xd2,0x14,0xe1,0x25,0x82,0xe0,0x1c, - 0x82,0xcf,0x86,0xe5,0xdd,0x81,0xe4,0x9a,0x81,0xcf,0x06,0x12,0x00,0xd1,0x0b,0xe0, - 0x51,0x83,0xcf,0x86,0xcf,0x06,0x00,0x00,0xe0,0x95,0x8b,0xcf,0x86,0xd5,0x22,0xe4, - 0xd0,0x88,0xe3,0x93,0x88,0xe2,0x38,0x88,0xe1,0x31,0x88,0xe0,0x2a,0x88,0xcf,0x86, - 0xe5,0xfb,0x87,0xe4,0xe2,0x87,0x93,0x07,0x62,0xd1,0x87,0x12,0xe6,0x12,0xe6,0xe4, - 0x36,0x89,0xe3,0x2f,0x89,0xd2,0x09,0xe1,0xb8,0x88,0xcf,0x06,0x10,0x00,0xe1,0x1f, - 0x89,0xe0,0xec,0x88,0xcf,0x86,0xe5,0x21,0x01,0xd4,0x90,0xd3,0x48,0xd2,0x24,0xd1, - 0x12,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4,0xa2,0x00,0x12,0xff,0xf0,0x9e,0xa4,0xa3, - 0x00,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4,0xa4,0x00,0x12,0xff,0xf0,0x9e,0xa4,0xa5, - 0x00,0xd1,0x12,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4,0xa6,0x00,0x12,0xff,0xf0,0x9e, - 0xa4,0xa7,0x00,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4,0xa8,0x00,0x12,0xff,0xf0,0x9e, - 0xa4,0xa9,0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4,0xaa,0x00, - 0x12,0xff,0xf0,0x9e,0xa4,0xab,0x00,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4,0xac,0x00, - 0x12,0xff,0xf0,0x9e,0xa4,0xad,0x00,0xd1,0x12,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4, - 0xae,0x00,0x12,0xff,0xf0,0x9e,0xa4,0xaf,0x00,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4, - 0xb0,0x00,0x12,0xff,0xf0,0x9e,0xa4,0xb1,0x00,0xd3,0x48,0xd2,0x24,0xd1,0x12,0x10, - 0x09,0x12,0xff,0xf0,0x9e,0xa4,0xb2,0x00,0x12,0xff,0xf0,0x9e,0xa4,0xb3,0x00,0x10, - 0x09,0x12,0xff,0xf0,0x9e,0xa4,0xb4,0x00,0x12,0xff,0xf0,0x9e,0xa4,0xb5,0x00,0xd1, - 0x12,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4,0xb6,0x00,0x12,0xff,0xf0,0x9e,0xa4,0xb7, - 0x00,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4,0xb8,0x00,0x12,0xff,0xf0,0x9e,0xa4,0xb9, - 0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4,0xba,0x00,0x12,0xff, - 0xf0,0x9e,0xa4,0xbb,0x00,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4,0xbc,0x00,0x12,0xff, - 0xf0,0x9e,0xa4,0xbd,0x00,0xd1,0x12,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4,0xbe,0x00, - 0x12,0xff,0xf0,0x9e,0xa4,0xbf,0x00,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa5,0x80,0x00, - 0x12,0xff,0xf0,0x9e,0xa5,0x81,0x00,0x94,0x1e,0x93,0x1a,0x92,0x16,0x91,0x12,0x10, - 0x09,0x12,0xff,0xf0,0x9e,0xa5,0x82,0x00,0x12,0xff,0xf0,0x9e,0xa5,0x83,0x00,0x12, - 0x00,0x12,0x00,0x12,0x00,0x12,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - /* nfdi_c0100 */ - 0x57,0x04,0x01,0x00,0xc6,0xe5,0xac,0x13,0xe4,0x41,0x0c,0xe3,0x7a,0x07,0xe2,0xf3, - 0x01,0xc1,0xd0,0x1f,0xcf,0x86,0x55,0x04,0x01,0x00,0x94,0x15,0x53,0x04,0x01,0x00, - 0x52,0x04,0x01,0x00,0x91,0x09,0x10,0x04,0x01,0x00,0x01,0xff,0x00,0x01,0x00,0x01, - 0x00,0xcf,0x86,0xd5,0xe4,0xd4,0x7c,0xd3,0x3c,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01, - 0xff,0x41,0xcc,0x80,0x00,0x01,0xff,0x41,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x41, - 0xcc,0x82,0x00,0x01,0xff,0x41,0xcc,0x83,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x41, - 0xcc,0x88,0x00,0x01,0xff,0x41,0xcc,0x8a,0x00,0x10,0x04,0x01,0x00,0x01,0xff,0x43, - 0xcc,0xa7,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x45,0xcc,0x80,0x00,0x01, - 0xff,0x45,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x45,0xcc,0x82,0x00,0x01,0xff,0x45, - 0xcc,0x88,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x49,0xcc,0x80,0x00,0x01,0xff,0x49, - 0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x49,0xcc,0x82,0x00,0x01,0xff,0x49,0xcc,0x88, - 0x00,0xd3,0x38,0xd2,0x1c,0xd1,0x0c,0x10,0x04,0x01,0x00,0x01,0xff,0x4e,0xcc,0x83, - 0x00,0x10,0x08,0x01,0xff,0x4f,0xcc,0x80,0x00,0x01,0xff,0x4f,0xcc,0x81,0x00,0xd1, - 0x10,0x10,0x08,0x01,0xff,0x4f,0xcc,0x82,0x00,0x01,0xff,0x4f,0xcc,0x83,0x00,0x10, - 0x08,0x01,0xff,0x4f,0xcc,0x88,0x00,0x01,0x00,0xd2,0x1c,0xd1,0x0c,0x10,0x04,0x01, - 0x00,0x01,0xff,0x55,0xcc,0x80,0x00,0x10,0x08,0x01,0xff,0x55,0xcc,0x81,0x00,0x01, - 0xff,0x55,0xcc,0x82,0x00,0x91,0x10,0x10,0x08,0x01,0xff,0x55,0xcc,0x88,0x00,0x01, - 0xff,0x59,0xcc,0x81,0x00,0x01,0x00,0xd4,0x7c,0xd3,0x3c,0xd2,0x20,0xd1,0x10,0x10, - 0x08,0x01,0xff,0x61,0xcc,0x80,0x00,0x01,0xff,0x61,0xcc,0x81,0x00,0x10,0x08,0x01, - 0xff,0x61,0xcc,0x82,0x00,0x01,0xff,0x61,0xcc,0x83,0x00,0xd1,0x10,0x10,0x08,0x01, - 0xff,0x61,0xcc,0x88,0x00,0x01,0xff,0x61,0xcc,0x8a,0x00,0x10,0x04,0x01,0x00,0x01, - 0xff,0x63,0xcc,0xa7,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x65,0xcc,0x80, - 0x00,0x01,0xff,0x65,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x65,0xcc,0x82,0x00,0x01, - 0xff,0x65,0xcc,0x88,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x69,0xcc,0x80,0x00,0x01, - 0xff,0x69,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x69,0xcc,0x82,0x00,0x01,0xff,0x69, - 0xcc,0x88,0x00,0xd3,0x38,0xd2,0x1c,0xd1,0x0c,0x10,0x04,0x01,0x00,0x01,0xff,0x6e, - 0xcc,0x83,0x00,0x10,0x08,0x01,0xff,0x6f,0xcc,0x80,0x00,0x01,0xff,0x6f,0xcc,0x81, - 0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x6f,0xcc,0x82,0x00,0x01,0xff,0x6f,0xcc,0x83, - 0x00,0x10,0x08,0x01,0xff,0x6f,0xcc,0x88,0x00,0x01,0x00,0xd2,0x1c,0xd1,0x0c,0x10, - 0x04,0x01,0x00,0x01,0xff,0x75,0xcc,0x80,0x00,0x10,0x08,0x01,0xff,0x75,0xcc,0x81, - 0x00,0x01,0xff,0x75,0xcc,0x82,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x75,0xcc,0x88, - 0x00,0x01,0xff,0x79,0xcc,0x81,0x00,0x10,0x04,0x01,0x00,0x01,0xff,0x79,0xcc,0x88, - 0x00,0xe1,0x9a,0x03,0xe0,0xd3,0x01,0xcf,0x86,0xd5,0xf4,0xd4,0x80,0xd3,0x40,0xd2, - 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x41,0xcc,0x84,0x00,0x01,0xff,0x61,0xcc,0x84, - 0x00,0x10,0x08,0x01,0xff,0x41,0xcc,0x86,0x00,0x01,0xff,0x61,0xcc,0x86,0x00,0xd1, - 0x10,0x10,0x08,0x01,0xff,0x41,0xcc,0xa8,0x00,0x01,0xff,0x61,0xcc,0xa8,0x00,0x10, - 0x08,0x01,0xff,0x43,0xcc,0x81,0x00,0x01,0xff,0x63,0xcc,0x81,0x00,0xd2,0x20,0xd1, - 0x10,0x10,0x08,0x01,0xff,0x43,0xcc,0x82,0x00,0x01,0xff,0x63,0xcc,0x82,0x00,0x10, - 0x08,0x01,0xff,0x43,0xcc,0x87,0x00,0x01,0xff,0x63,0xcc,0x87,0x00,0xd1,0x10,0x10, - 0x08,0x01,0xff,0x43,0xcc,0x8c,0x00,0x01,0xff,0x63,0xcc,0x8c,0x00,0x10,0x08,0x01, - 0xff,0x44,0xcc,0x8c,0x00,0x01,0xff,0x64,0xcc,0x8c,0x00,0xd3,0x34,0xd2,0x14,0x51, - 0x04,0x01,0x00,0x10,0x08,0x01,0xff,0x45,0xcc,0x84,0x00,0x01,0xff,0x65,0xcc,0x84, - 0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x45,0xcc,0x86,0x00,0x01,0xff,0x65,0xcc,0x86, - 0x00,0x10,0x08,0x01,0xff,0x45,0xcc,0x87,0x00,0x01,0xff,0x65,0xcc,0x87,0x00,0xd2, - 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x45,0xcc,0xa8,0x00,0x01,0xff,0x65,0xcc,0xa8, - 0x00,0x10,0x08,0x01,0xff,0x45,0xcc,0x8c,0x00,0x01,0xff,0x65,0xcc,0x8c,0x00,0xd1, - 0x10,0x10,0x08,0x01,0xff,0x47,0xcc,0x82,0x00,0x01,0xff,0x67,0xcc,0x82,0x00,0x10, - 0x08,0x01,0xff,0x47,0xcc,0x86,0x00,0x01,0xff,0x67,0xcc,0x86,0x00,0xd4,0x74,0xd3, - 0x34,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x47,0xcc,0x87,0x00,0x01,0xff,0x67, - 0xcc,0x87,0x00,0x10,0x08,0x01,0xff,0x47,0xcc,0xa7,0x00,0x01,0xff,0x67,0xcc,0xa7, - 0x00,0x91,0x10,0x10,0x08,0x01,0xff,0x48,0xcc,0x82,0x00,0x01,0xff,0x68,0xcc,0x82, - 0x00,0x01,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x49,0xcc,0x83,0x00,0x01, - 0xff,0x69,0xcc,0x83,0x00,0x10,0x08,0x01,0xff,0x49,0xcc,0x84,0x00,0x01,0xff,0x69, - 0xcc,0x84,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x49,0xcc,0x86,0x00,0x01,0xff,0x69, - 0xcc,0x86,0x00,0x10,0x08,0x01,0xff,0x49,0xcc,0xa8,0x00,0x01,0xff,0x69,0xcc,0xa8, - 0x00,0xd3,0x30,0xd2,0x10,0x91,0x0c,0x10,0x08,0x01,0xff,0x49,0xcc,0x87,0x00,0x01, - 0x00,0x01,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x4a,0xcc,0x82,0x00,0x01,0xff,0x6a, - 0xcc,0x82,0x00,0x10,0x08,0x01,0xff,0x4b,0xcc,0xa7,0x00,0x01,0xff,0x6b,0xcc,0xa7, - 0x00,0xd2,0x1c,0xd1,0x0c,0x10,0x04,0x01,0x00,0x01,0xff,0x4c,0xcc,0x81,0x00,0x10, - 0x08,0x01,0xff,0x6c,0xcc,0x81,0x00,0x01,0xff,0x4c,0xcc,0xa7,0x00,0xd1,0x10,0x10, - 0x08,0x01,0xff,0x6c,0xcc,0xa7,0x00,0x01,0xff,0x4c,0xcc,0x8c,0x00,0x10,0x08,0x01, - 0xff,0x6c,0xcc,0x8c,0x00,0x01,0x00,0xcf,0x86,0xd5,0xd4,0xd4,0x60,0xd3,0x30,0xd2, - 0x10,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x01,0xff,0x4e,0xcc,0x81,0x00,0xd1, - 0x10,0x10,0x08,0x01,0xff,0x6e,0xcc,0x81,0x00,0x01,0xff,0x4e,0xcc,0xa7,0x00,0x10, - 0x08,0x01,0xff,0x6e,0xcc,0xa7,0x00,0x01,0xff,0x4e,0xcc,0x8c,0x00,0xd2,0x10,0x91, - 0x0c,0x10,0x08,0x01,0xff,0x6e,0xcc,0x8c,0x00,0x01,0x00,0x01,0x00,0xd1,0x10,0x10, - 0x08,0x01,0xff,0x4f,0xcc,0x84,0x00,0x01,0xff,0x6f,0xcc,0x84,0x00,0x10,0x08,0x01, - 0xff,0x4f,0xcc,0x86,0x00,0x01,0xff,0x6f,0xcc,0x86,0x00,0xd3,0x34,0xd2,0x14,0x91, - 0x10,0x10,0x08,0x01,0xff,0x4f,0xcc,0x8b,0x00,0x01,0xff,0x6f,0xcc,0x8b,0x00,0x01, - 0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x52,0xcc,0x81,0x00,0x01,0xff,0x72,0xcc,0x81, - 0x00,0x10,0x08,0x01,0xff,0x52,0xcc,0xa7,0x00,0x01,0xff,0x72,0xcc,0xa7,0x00,0xd2, - 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x52,0xcc,0x8c,0x00,0x01,0xff,0x72,0xcc,0x8c, - 0x00,0x10,0x08,0x01,0xff,0x53,0xcc,0x81,0x00,0x01,0xff,0x73,0xcc,0x81,0x00,0xd1, - 0x10,0x10,0x08,0x01,0xff,0x53,0xcc,0x82,0x00,0x01,0xff,0x73,0xcc,0x82,0x00,0x10, - 0x08,0x01,0xff,0x53,0xcc,0xa7,0x00,0x01,0xff,0x73,0xcc,0xa7,0x00,0xd4,0x74,0xd3, - 0x34,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x53,0xcc,0x8c,0x00,0x01,0xff,0x73, - 0xcc,0x8c,0x00,0x10,0x08,0x01,0xff,0x54,0xcc,0xa7,0x00,0x01,0xff,0x74,0xcc,0xa7, - 0x00,0x91,0x10,0x10,0x08,0x01,0xff,0x54,0xcc,0x8c,0x00,0x01,0xff,0x74,0xcc,0x8c, - 0x00,0x01,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x55,0xcc,0x83,0x00,0x01, - 0xff,0x75,0xcc,0x83,0x00,0x10,0x08,0x01,0xff,0x55,0xcc,0x84,0x00,0x01,0xff,0x75, - 0xcc,0x84,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x55,0xcc,0x86,0x00,0x01,0xff,0x75, - 0xcc,0x86,0x00,0x10,0x08,0x01,0xff,0x55,0xcc,0x8a,0x00,0x01,0xff,0x75,0xcc,0x8a, - 0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x55,0xcc,0x8b,0x00,0x01, - 0xff,0x75,0xcc,0x8b,0x00,0x10,0x08,0x01,0xff,0x55,0xcc,0xa8,0x00,0x01,0xff,0x75, - 0xcc,0xa8,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x57,0xcc,0x82,0x00,0x01,0xff,0x77, - 0xcc,0x82,0x00,0x10,0x08,0x01,0xff,0x59,0xcc,0x82,0x00,0x01,0xff,0x79,0xcc,0x82, - 0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x59,0xcc,0x88,0x00,0x01,0xff,0x5a, - 0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x7a,0xcc,0x81,0x00,0x01,0xff,0x5a,0xcc,0x87, - 0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x7a,0xcc,0x87,0x00,0x01,0xff,0x5a,0xcc,0x8c, - 0x00,0x10,0x08,0x01,0xff,0x7a,0xcc,0x8c,0x00,0x01,0x00,0xd0,0x4a,0xcf,0x86,0x55, - 0x04,0x01,0x00,0xd4,0x2c,0xd3,0x18,0x92,0x14,0x91,0x10,0x10,0x08,0x01,0xff,0x4f, - 0xcc,0x9b,0x00,0x01,0xff,0x6f,0xcc,0x9b,0x00,0x01,0x00,0x01,0x00,0x52,0x04,0x01, - 0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x01,0xff,0x55,0xcc,0x9b,0x00,0x93, - 0x14,0x92,0x10,0x91,0x0c,0x10,0x08,0x01,0xff,0x75,0xcc,0x9b,0x00,0x01,0x00,0x01, - 0x00,0x01,0x00,0x01,0x00,0xcf,0x86,0xd5,0xb4,0xd4,0x24,0x53,0x04,0x01,0x00,0x52, - 0x04,0x01,0x00,0xd1,0x0c,0x10,0x04,0x01,0x00,0x01,0xff,0x41,0xcc,0x8c,0x00,0x10, - 0x08,0x01,0xff,0x61,0xcc,0x8c,0x00,0x01,0xff,0x49,0xcc,0x8c,0x00,0xd3,0x46,0xd2, - 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x69,0xcc,0x8c,0x00,0x01,0xff,0x4f,0xcc,0x8c, - 0x00,0x10,0x08,0x01,0xff,0x6f,0xcc,0x8c,0x00,0x01,0xff,0x55,0xcc,0x8c,0x00,0xd1, - 0x12,0x10,0x08,0x01,0xff,0x75,0xcc,0x8c,0x00,0x01,0xff,0x55,0xcc,0x88,0xcc,0x84, - 0x00,0x10,0x0a,0x01,0xff,0x75,0xcc,0x88,0xcc,0x84,0x00,0x01,0xff,0x55,0xcc,0x88, - 0xcc,0x81,0x00,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x75,0xcc,0x88,0xcc,0x81, - 0x00,0x01,0xff,0x55,0xcc,0x88,0xcc,0x8c,0x00,0x10,0x0a,0x01,0xff,0x75,0xcc,0x88, - 0xcc,0x8c,0x00,0x01,0xff,0x55,0xcc,0x88,0xcc,0x80,0x00,0xd1,0x0e,0x10,0x0a,0x01, - 0xff,0x75,0xcc,0x88,0xcc,0x80,0x00,0x01,0x00,0x10,0x0a,0x01,0xff,0x41,0xcc,0x88, - 0xcc,0x84,0x00,0x01,0xff,0x61,0xcc,0x88,0xcc,0x84,0x00,0xd4,0x80,0xd3,0x3a,0xd2, - 0x26,0xd1,0x14,0x10,0x0a,0x01,0xff,0x41,0xcc,0x87,0xcc,0x84,0x00,0x01,0xff,0x61, - 0xcc,0x87,0xcc,0x84,0x00,0x10,0x09,0x01,0xff,0xc3,0x86,0xcc,0x84,0x00,0x01,0xff, - 0xc3,0xa6,0xcc,0x84,0x00,0x51,0x04,0x01,0x00,0x10,0x08,0x01,0xff,0x47,0xcc,0x8c, - 0x00,0x01,0xff,0x67,0xcc,0x8c,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x4b, - 0xcc,0x8c,0x00,0x01,0xff,0x6b,0xcc,0x8c,0x00,0x10,0x08,0x01,0xff,0x4f,0xcc,0xa8, - 0x00,0x01,0xff,0x6f,0xcc,0xa8,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x4f,0xcc,0xa8, - 0xcc,0x84,0x00,0x01,0xff,0x6f,0xcc,0xa8,0xcc,0x84,0x00,0x10,0x09,0x01,0xff,0xc6, - 0xb7,0xcc,0x8c,0x00,0x01,0xff,0xca,0x92,0xcc,0x8c,0x00,0xd3,0x24,0xd2,0x10,0x91, - 0x0c,0x10,0x08,0x01,0xff,0x6a,0xcc,0x8c,0x00,0x01,0x00,0x01,0x00,0x91,0x10,0x10, - 0x08,0x01,0xff,0x47,0xcc,0x81,0x00,0x01,0xff,0x67,0xcc,0x81,0x00,0x04,0x00,0xd2, - 0x24,0xd1,0x10,0x10,0x08,0x04,0xff,0x4e,0xcc,0x80,0x00,0x04,0xff,0x6e,0xcc,0x80, - 0x00,0x10,0x0a,0x01,0xff,0x41,0xcc,0x8a,0xcc,0x81,0x00,0x01,0xff,0x61,0xcc,0x8a, - 0xcc,0x81,0x00,0xd1,0x12,0x10,0x09,0x01,0xff,0xc3,0x86,0xcc,0x81,0x00,0x01,0xff, - 0xc3,0xa6,0xcc,0x81,0x00,0x10,0x09,0x01,0xff,0xc3,0x98,0xcc,0x81,0x00,0x01,0xff, - 0xc3,0xb8,0xcc,0x81,0x00,0xe2,0x07,0x02,0xe1,0xae,0x01,0xe0,0x93,0x01,0xcf,0x86, - 0xd5,0xf4,0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x41,0xcc, - 0x8f,0x00,0x01,0xff,0x61,0xcc,0x8f,0x00,0x10,0x08,0x01,0xff,0x41,0xcc,0x91,0x00, - 0x01,0xff,0x61,0xcc,0x91,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x45,0xcc,0x8f,0x00, - 0x01,0xff,0x65,0xcc,0x8f,0x00,0x10,0x08,0x01,0xff,0x45,0xcc,0x91,0x00,0x01,0xff, - 0x65,0xcc,0x91,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x49,0xcc,0x8f,0x00, - 0x01,0xff,0x69,0xcc,0x8f,0x00,0x10,0x08,0x01,0xff,0x49,0xcc,0x91,0x00,0x01,0xff, - 0x69,0xcc,0x91,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x4f,0xcc,0x8f,0x00,0x01,0xff, - 0x6f,0xcc,0x8f,0x00,0x10,0x08,0x01,0xff,0x4f,0xcc,0x91,0x00,0x01,0xff,0x6f,0xcc, - 0x91,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x52,0xcc,0x8f,0x00, - 0x01,0xff,0x72,0xcc,0x8f,0x00,0x10,0x08,0x01,0xff,0x52,0xcc,0x91,0x00,0x01,0xff, - 0x72,0xcc,0x91,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x55,0xcc,0x8f,0x00,0x01,0xff, - 0x75,0xcc,0x8f,0x00,0x10,0x08,0x01,0xff,0x55,0xcc,0x91,0x00,0x01,0xff,0x75,0xcc, - 0x91,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x04,0xff,0x53,0xcc,0xa6,0x00,0x04,0xff, - 0x73,0xcc,0xa6,0x00,0x10,0x08,0x04,0xff,0x54,0xcc,0xa6,0x00,0x04,0xff,0x74,0xcc, - 0xa6,0x00,0x51,0x04,0x04,0x00,0x10,0x08,0x04,0xff,0x48,0xcc,0x8c,0x00,0x04,0xff, - 0x68,0xcc,0x8c,0x00,0xd4,0x68,0xd3,0x20,0xd2,0x0c,0x91,0x08,0x10,0x04,0x06,0x00, - 0x07,0x00,0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x08,0x04,0xff,0x41,0xcc,0x87,0x00, - 0x04,0xff,0x61,0xcc,0x87,0x00,0xd2,0x24,0xd1,0x10,0x10,0x08,0x04,0xff,0x45,0xcc, - 0xa7,0x00,0x04,0xff,0x65,0xcc,0xa7,0x00,0x10,0x0a,0x04,0xff,0x4f,0xcc,0x88,0xcc, - 0x84,0x00,0x04,0xff,0x6f,0xcc,0x88,0xcc,0x84,0x00,0xd1,0x14,0x10,0x0a,0x04,0xff, - 0x4f,0xcc,0x83,0xcc,0x84,0x00,0x04,0xff,0x6f,0xcc,0x83,0xcc,0x84,0x00,0x10,0x08, - 0x04,0xff,0x4f,0xcc,0x87,0x00,0x04,0xff,0x6f,0xcc,0x87,0x00,0x93,0x30,0xd2,0x24, - 0xd1,0x14,0x10,0x0a,0x04,0xff,0x4f,0xcc,0x87,0xcc,0x84,0x00,0x04,0xff,0x6f,0xcc, - 0x87,0xcc,0x84,0x00,0x10,0x08,0x04,0xff,0x59,0xcc,0x84,0x00,0x04,0xff,0x79,0xcc, - 0x84,0x00,0x51,0x04,0x07,0x00,0x10,0x04,0x07,0x00,0x08,0x00,0x08,0x00,0xcf,0x86, - 0x95,0x14,0x94,0x10,0x93,0x0c,0x92,0x08,0x11,0x04,0x08,0x00,0x09,0x00,0x09,0x00, - 0x09,0x00,0x01,0x00,0x01,0x00,0xd0,0x22,0xcf,0x86,0x55,0x04,0x01,0x00,0x94,0x18, - 0x53,0x04,0x01,0x00,0xd2,0x0c,0x91,0x08,0x10,0x04,0x01,0x00,0x04,0x00,0x04,0x00, - 0x11,0x04,0x04,0x00,0x07,0x00,0x01,0x00,0xcf,0x86,0xd5,0x18,0x54,0x04,0x01,0x00, - 0x53,0x04,0x01,0x00,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00, - 0x04,0x00,0x94,0x18,0x53,0x04,0x01,0x00,0xd2,0x08,0x11,0x04,0x01,0x00,0x04,0x00, - 0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x07,0x00,0x07,0x00,0xe1,0x35,0x01,0xd0, - 0x72,0xcf,0x86,0xd5,0x24,0x54,0x04,0x01,0xe6,0xd3,0x10,0x52,0x04,0x01,0xe6,0x91, - 0x08,0x10,0x04,0x01,0xe6,0x01,0xe8,0x01,0xdc,0x92,0x0c,0x51,0x04,0x01,0xdc,0x10, - 0x04,0x01,0xe8,0x01,0xd8,0x01,0xdc,0xd4,0x2c,0xd3,0x1c,0xd2,0x10,0xd1,0x08,0x10, - 0x04,0x01,0xdc,0x01,0xca,0x10,0x04,0x01,0xca,0x01,0xdc,0x51,0x04,0x01,0xdc,0x10, - 0x04,0x01,0xdc,0x01,0xca,0x92,0x0c,0x91,0x08,0x10,0x04,0x01,0xca,0x01,0xdc,0x01, - 0xdc,0x01,0xdc,0xd3,0x08,0x12,0x04,0x01,0xdc,0x01,0x01,0xd2,0x0c,0x91,0x08,0x10, - 0x04,0x01,0x01,0x01,0xdc,0x01,0xdc,0x91,0x08,0x10,0x04,0x01,0xdc,0x01,0xe6,0x01, - 0xe6,0xcf,0x86,0xd5,0x7f,0xd4,0x47,0xd3,0x2e,0xd2,0x19,0xd1,0x0e,0x10,0x07,0x01, - 0xff,0xcc,0x80,0x00,0x01,0xff,0xcc,0x81,0x00,0x10,0x04,0x01,0xe6,0x01,0xff,0xcc, - 0x93,0x00,0xd1,0x0d,0x10,0x09,0x01,0xff,0xcc,0x88,0xcc,0x81,0x00,0x01,0xf0,0x10, - 0x04,0x04,0xe6,0x04,0xdc,0xd2,0x08,0x11,0x04,0x04,0xdc,0x04,0xe6,0xd1,0x08,0x10, - 0x04,0x04,0xe6,0x04,0xdc,0x10,0x04,0x04,0xdc,0x06,0xff,0x00,0xd3,0x18,0xd2,0x0c, - 0x51,0x04,0x07,0xe6,0x10,0x04,0x07,0xe6,0x07,0xdc,0x51,0x04,0x07,0xdc,0x10,0x04, - 0x07,0xdc,0x07,0xe6,0xd2,0x10,0xd1,0x08,0x10,0x04,0x08,0xe8,0x08,0xdc,0x10,0x04, - 0x08,0xdc,0x08,0xe6,0xd1,0x08,0x10,0x04,0x08,0xe9,0x07,0xea,0x10,0x04,0x07,0xea, - 0x07,0xe9,0xd4,0x14,0x93,0x10,0x92,0x0c,0x51,0x04,0x01,0xea,0x10,0x04,0x04,0xe9, - 0x06,0xe6,0x06,0xe6,0x06,0xe6,0xd3,0x13,0x52,0x04,0x0a,0x00,0x91,0x0b,0x10,0x07, - 0x01,0xff,0xca,0xb9,0x00,0x01,0x00,0x0a,0x00,0xd2,0x0c,0x51,0x04,0x00,0x00,0x10, - 0x04,0x01,0x00,0x09,0x00,0x51,0x04,0x09,0x00,0x10,0x06,0x01,0xff,0x3b,0x00,0x10, - 0x00,0xd0,0xe1,0xcf,0x86,0xd5,0x7a,0xd4,0x5f,0xd3,0x21,0x52,0x04,0x00,0x00,0xd1, - 0x0d,0x10,0x04,0x01,0x00,0x01,0xff,0xc2,0xa8,0xcc,0x81,0x00,0x10,0x09,0x01,0xff, - 0xce,0x91,0xcc,0x81,0x00,0x01,0xff,0xc2,0xb7,0x00,0xd2,0x1f,0xd1,0x12,0x10,0x09, - 0x01,0xff,0xce,0x95,0xcc,0x81,0x00,0x01,0xff,0xce,0x97,0xcc,0x81,0x00,0x10,0x09, - 0x01,0xff,0xce,0x99,0xcc,0x81,0x00,0x00,0x00,0xd1,0x0d,0x10,0x09,0x01,0xff,0xce, - 0x9f,0xcc,0x81,0x00,0x00,0x00,0x10,0x09,0x01,0xff,0xce,0xa5,0xcc,0x81,0x00,0x01, - 0xff,0xce,0xa9,0xcc,0x81,0x00,0x93,0x17,0x92,0x13,0x91,0x0f,0x10,0x0b,0x01,0xff, - 0xce,0xb9,0xcc,0x88,0xcc,0x81,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd4, - 0x4a,0xd3,0x10,0x92,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x00,0x00,0x01,0x00,0x01, - 0x00,0xd2,0x16,0x51,0x04,0x01,0x00,0x10,0x09,0x01,0xff,0xce,0x99,0xcc,0x88,0x00, - 0x01,0xff,0xce,0xa5,0xcc,0x88,0x00,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb1,0xcc, - 0x81,0x00,0x01,0xff,0xce,0xb5,0xcc,0x81,0x00,0x10,0x09,0x01,0xff,0xce,0xb7,0xcc, - 0x81,0x00,0x01,0xff,0xce,0xb9,0xcc,0x81,0x00,0x93,0x17,0x92,0x13,0x91,0x0f,0x10, - 0x0b,0x01,0xff,0xcf,0x85,0xcc,0x88,0xcc,0x81,0x00,0x01,0x00,0x01,0x00,0x01,0x00, - 0x01,0x00,0xcf,0x86,0xd5,0x7b,0xd4,0x39,0x53,0x04,0x01,0x00,0xd2,0x16,0x51,0x04, - 0x01,0x00,0x10,0x09,0x01,0xff,0xce,0xb9,0xcc,0x88,0x00,0x01,0xff,0xcf,0x85,0xcc, - 0x88,0x00,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xbf,0xcc,0x81,0x00,0x01,0xff,0xcf, - 0x85,0xcc,0x81,0x00,0x10,0x09,0x01,0xff,0xcf,0x89,0xcc,0x81,0x00,0x0a,0x00,0xd3, - 0x26,0xd2,0x11,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x01,0xff,0xcf,0x92,0xcc, - 0x81,0x00,0xd1,0x0d,0x10,0x09,0x01,0xff,0xcf,0x92,0xcc,0x88,0x00,0x01,0x00,0x10, - 0x04,0x01,0x00,0x04,0x00,0xd2,0x0c,0x51,0x04,0x06,0x00,0x10,0x04,0x01,0x00,0x04, - 0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x04,0x00,0x10,0x04,0x01,0x00,0x04,0x00,0xd4, - 0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x01,0x00,0x04,0x00,0x01,0x00,0x01, - 0x00,0x01,0x00,0xd3,0x10,0x52,0x04,0x01,0x00,0x51,0x04,0x05,0x00,0x10,0x04,0x06, - 0x00,0x07,0x00,0x12,0x04,0x07,0x00,0x08,0x00,0xe3,0x47,0x04,0xe2,0xbe,0x02,0xe1, - 0x07,0x01,0xd0,0x8b,0xcf,0x86,0xd5,0x6c,0xd4,0x53,0xd3,0x30,0xd2,0x1f,0xd1,0x12, - 0x10,0x09,0x04,0xff,0xd0,0x95,0xcc,0x80,0x00,0x01,0xff,0xd0,0x95,0xcc,0x88,0x00, - 0x10,0x04,0x01,0x00,0x01,0xff,0xd0,0x93,0xcc,0x81,0x00,0x51,0x04,0x01,0x00,0x10, - 0x04,0x01,0x00,0x01,0xff,0xd0,0x86,0xcc,0x88,0x00,0x52,0x04,0x01,0x00,0xd1,0x12, - 0x10,0x09,0x01,0xff,0xd0,0x9a,0xcc,0x81,0x00,0x04,0xff,0xd0,0x98,0xcc,0x80,0x00, - 0x10,0x09,0x01,0xff,0xd0,0xa3,0xcc,0x86,0x00,0x01,0x00,0x53,0x04,0x01,0x00,0x92, - 0x11,0x91,0x0d,0x10,0x04,0x01,0x00,0x01,0xff,0xd0,0x98,0xcc,0x86,0x00,0x01,0x00, - 0x01,0x00,0x54,0x04,0x01,0x00,0x53,0x04,0x01,0x00,0x92,0x11,0x91,0x0d,0x10,0x04, - 0x01,0x00,0x01,0xff,0xd0,0xb8,0xcc,0x86,0x00,0x01,0x00,0x01,0x00,0xcf,0x86,0xd5, - 0x57,0x54,0x04,0x01,0x00,0xd3,0x30,0xd2,0x1f,0xd1,0x12,0x10,0x09,0x04,0xff,0xd0, - 0xb5,0xcc,0x80,0x00,0x01,0xff,0xd0,0xb5,0xcc,0x88,0x00,0x10,0x04,0x01,0x00,0x01, - 0xff,0xd0,0xb3,0xcc,0x81,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x01,0xff, - 0xd1,0x96,0xcc,0x88,0x00,0x52,0x04,0x01,0x00,0xd1,0x12,0x10,0x09,0x01,0xff,0xd0, - 0xba,0xcc,0x81,0x00,0x04,0xff,0xd0,0xb8,0xcc,0x80,0x00,0x10,0x09,0x01,0xff,0xd1, - 0x83,0xcc,0x86,0x00,0x01,0x00,0x54,0x04,0x01,0x00,0x93,0x1a,0x52,0x04,0x01,0x00, - 0x51,0x04,0x01,0x00,0x10,0x09,0x01,0xff,0xd1,0xb4,0xcc,0x8f,0x00,0x01,0xff,0xd1, - 0xb5,0xcc,0x8f,0x00,0x01,0x00,0xd0,0x2e,0xcf,0x86,0x95,0x28,0x94,0x24,0xd3,0x18, - 0xd2,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x01,0xe6,0x51,0x04,0x01,0xe6, - 0x10,0x04,0x01,0xe6,0x0a,0xe6,0x92,0x08,0x11,0x04,0x04,0x00,0x06,0x00,0x04,0x00, - 0x01,0x00,0x01,0x00,0xcf,0x86,0xd5,0xbe,0xd4,0x4a,0xd3,0x2a,0xd2,0x1a,0xd1,0x0d, - 0x10,0x04,0x01,0x00,0x01,0xff,0xd0,0x96,0xcc,0x86,0x00,0x10,0x09,0x01,0xff,0xd0, - 0xb6,0xcc,0x86,0x00,0x01,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x06,0x00,0x10,0x04, - 0x06,0x00,0x01,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04,0x01,0x00,0x06,0x00,0x10,0x04, - 0x06,0x00,0x01,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x06,0x00,0x10,0x04,0x06,0x00, - 0x09,0x00,0xd3,0x3a,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff,0xd0,0x90,0xcc,0x86, - 0x00,0x01,0xff,0xd0,0xb0,0xcc,0x86,0x00,0x10,0x09,0x01,0xff,0xd0,0x90,0xcc,0x88, - 0x00,0x01,0xff,0xd0,0xb0,0xcc,0x88,0x00,0x51,0x04,0x01,0x00,0x10,0x09,0x01,0xff, - 0xd0,0x95,0xcc,0x86,0x00,0x01,0xff,0xd0,0xb5,0xcc,0x86,0x00,0xd2,0x16,0x51,0x04, - 0x01,0x00,0x10,0x09,0x01,0xff,0xd3,0x98,0xcc,0x88,0x00,0x01,0xff,0xd3,0x99,0xcc, - 0x88,0x00,0xd1,0x12,0x10,0x09,0x01,0xff,0xd0,0x96,0xcc,0x88,0x00,0x01,0xff,0xd0, - 0xb6,0xcc,0x88,0x00,0x10,0x09,0x01,0xff,0xd0,0x97,0xcc,0x88,0x00,0x01,0xff,0xd0, - 0xb7,0xcc,0x88,0x00,0xd4,0x74,0xd3,0x3a,0xd2,0x16,0x51,0x04,0x01,0x00,0x10,0x09, - 0x01,0xff,0xd0,0x98,0xcc,0x84,0x00,0x01,0xff,0xd0,0xb8,0xcc,0x84,0x00,0xd1,0x12, - 0x10,0x09,0x01,0xff,0xd0,0x98,0xcc,0x88,0x00,0x01,0xff,0xd0,0xb8,0xcc,0x88,0x00, - 0x10,0x09,0x01,0xff,0xd0,0x9e,0xcc,0x88,0x00,0x01,0xff,0xd0,0xbe,0xcc,0x88,0x00, - 0xd2,0x16,0x51,0x04,0x01,0x00,0x10,0x09,0x01,0xff,0xd3,0xa8,0xcc,0x88,0x00,0x01, - 0xff,0xd3,0xa9,0xcc,0x88,0x00,0xd1,0x12,0x10,0x09,0x04,0xff,0xd0,0xad,0xcc,0x88, - 0x00,0x04,0xff,0xd1,0x8d,0xcc,0x88,0x00,0x10,0x09,0x01,0xff,0xd0,0xa3,0xcc,0x84, - 0x00,0x01,0xff,0xd1,0x83,0xcc,0x84,0x00,0xd3,0x3a,0xd2,0x24,0xd1,0x12,0x10,0x09, - 0x01,0xff,0xd0,0xa3,0xcc,0x88,0x00,0x01,0xff,0xd1,0x83,0xcc,0x88,0x00,0x10,0x09, - 0x01,0xff,0xd0,0xa3,0xcc,0x8b,0x00,0x01,0xff,0xd1,0x83,0xcc,0x8b,0x00,0x91,0x12, - 0x10,0x09,0x01,0xff,0xd0,0xa7,0xcc,0x88,0x00,0x01,0xff,0xd1,0x87,0xcc,0x88,0x00, - 0x08,0x00,0x92,0x16,0x91,0x12,0x10,0x09,0x01,0xff,0xd0,0xab,0xcc,0x88,0x00,0x01, - 0xff,0xd1,0x8b,0xcc,0x88,0x00,0x09,0x00,0x09,0x00,0xd1,0x74,0xd0,0x36,0xcf,0x86, - 0xd5,0x10,0x54,0x04,0x06,0x00,0x93,0x08,0x12,0x04,0x09,0x00,0x0a,0x00,0x0a,0x00, - 0xd4,0x10,0x93,0x0c,0x52,0x04,0x0a,0x00,0x11,0x04,0x0b,0x00,0x0c,0x00,0x10,0x00, - 0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x01,0x00, - 0x01,0x00,0xcf,0x86,0xd5,0x24,0x54,0x04,0x01,0x00,0xd3,0x10,0x52,0x04,0x01,0x00, - 0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x92,0x0c,0x91,0x08,0x10,0x04, - 0x00,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x94,0x14,0x93,0x10,0x92,0x0c,0x91,0x08, - 0x10,0x04,0x14,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd0,0xba, - 0xcf,0x86,0xd5,0x4c,0xd4,0x24,0x53,0x04,0x01,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04, - 0x14,0x00,0x01,0x00,0x10,0x04,0x04,0x00,0x00,0x00,0xd1,0x08,0x10,0x04,0x00,0x00, - 0x10,0x00,0x10,0x04,0x10,0x00,0x0d,0x00,0xd3,0x18,0xd2,0x0c,0x91,0x08,0x10,0x04, - 0x00,0x00,0x02,0xdc,0x02,0xe6,0x51,0x04,0x02,0xe6,0x10,0x04,0x02,0xdc,0x02,0xe6, - 0x92,0x0c,0x51,0x04,0x02,0xe6,0x10,0x04,0x02,0xde,0x02,0xdc,0x02,0xe6,0xd4,0x2c, - 0xd3,0x10,0x92,0x0c,0x51,0x04,0x02,0xe6,0x10,0x04,0x08,0xdc,0x02,0xdc,0x02,0xdc, - 0xd2,0x0c,0x51,0x04,0x02,0xe6,0x10,0x04,0x02,0xdc,0x02,0xe6,0xd1,0x08,0x10,0x04, - 0x02,0xe6,0x02,0xde,0x10,0x04,0x02,0xe4,0x02,0xe6,0xd3,0x20,0xd2,0x10,0xd1,0x08, - 0x10,0x04,0x01,0x0a,0x01,0x0b,0x10,0x04,0x01,0x0c,0x01,0x0d,0xd1,0x08,0x10,0x04, - 0x01,0x0e,0x01,0x0f,0x10,0x04,0x01,0x10,0x01,0x11,0xd2,0x10,0xd1,0x08,0x10,0x04, - 0x01,0x12,0x01,0x13,0x10,0x04,0x09,0x13,0x01,0x14,0xd1,0x08,0x10,0x04,0x01,0x15, - 0x01,0x16,0x10,0x04,0x01,0x00,0x01,0x17,0xcf,0x86,0xd5,0x28,0x94,0x24,0x93,0x20, - 0xd2,0x10,0xd1,0x08,0x10,0x04,0x01,0x00,0x01,0x18,0x10,0x04,0x01,0x19,0x01,0x00, - 0xd1,0x08,0x10,0x04,0x02,0xe6,0x08,0xdc,0x10,0x04,0x08,0x00,0x08,0x12,0x00,0x00, - 0x01,0x00,0xd4,0x1c,0x53,0x04,0x01,0x00,0xd2,0x0c,0x51,0x04,0x01,0x00,0x10,0x04, - 0x01,0x00,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x14,0x00,0x93,0x10, - 0x52,0x04,0x01,0x00,0x91,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - 0xe2,0xfb,0x01,0xe1,0x2b,0x01,0xd0,0xa8,0xcf,0x86,0xd5,0x55,0xd4,0x28,0xd3,0x10, - 0x52,0x04,0x07,0x00,0x91,0x08,0x10,0x04,0x0d,0x00,0x10,0x00,0x0a,0x00,0xd2,0x0c, - 0x51,0x04,0x0a,0x00,0x10,0x04,0x0a,0x00,0x08,0x00,0x91,0x08,0x10,0x04,0x01,0x00, - 0x07,0x00,0x07,0x00,0xd3,0x0c,0x52,0x04,0x07,0xe6,0x11,0x04,0x07,0xe6,0x0a,0xe6, - 0xd2,0x10,0xd1,0x08,0x10,0x04,0x0a,0x1e,0x0a,0x1f,0x10,0x04,0x0a,0x20,0x01,0x00, - 0xd1,0x09,0x10,0x05,0x0f,0xff,0x00,0x00,0x00,0x10,0x04,0x08,0x00,0x01,0x00,0xd4, - 0x3d,0x93,0x39,0xd2,0x1a,0xd1,0x08,0x10,0x04,0x0c,0x00,0x01,0x00,0x10,0x09,0x01, - 0xff,0xd8,0xa7,0xd9,0x93,0x00,0x01,0xff,0xd8,0xa7,0xd9,0x94,0x00,0xd1,0x12,0x10, - 0x09,0x01,0xff,0xd9,0x88,0xd9,0x94,0x00,0x01,0xff,0xd8,0xa7,0xd9,0x95,0x00,0x10, - 0x09,0x01,0xff,0xd9,0x8a,0xd9,0x94,0x00,0x01,0x00,0x01,0x00,0x53,0x04,0x01,0x00, - 0x92,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x0a,0x00,0x0a,0x00,0xcf,0x86, - 0xd5,0x5c,0xd4,0x20,0x53,0x04,0x01,0x00,0xd2,0x0c,0x51,0x04,0x01,0x00,0x10,0x04, - 0x01,0x00,0x01,0x1b,0xd1,0x08,0x10,0x04,0x01,0x1c,0x01,0x1d,0x10,0x04,0x01,0x1e, - 0x01,0x1f,0xd3,0x20,0xd2,0x10,0xd1,0x08,0x10,0x04,0x01,0x20,0x01,0x21,0x10,0x04, - 0x01,0x22,0x04,0xe6,0xd1,0x08,0x10,0x04,0x04,0xe6,0x04,0xdc,0x10,0x04,0x07,0xdc, - 0x07,0xe6,0xd2,0x0c,0x91,0x08,0x10,0x04,0x07,0xe6,0x08,0xe6,0x08,0xe6,0xd1,0x08, - 0x10,0x04,0x08,0xdc,0x08,0xe6,0x10,0x04,0x08,0xe6,0x0c,0xdc,0xd4,0x10,0x53,0x04, - 0x01,0x00,0x52,0x04,0x01,0x00,0x11,0x04,0x01,0x00,0x06,0x00,0x93,0x10,0x92,0x0c, - 0x91,0x08,0x10,0x04,0x01,0x23,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd0,0x22, - 0xcf,0x86,0x55,0x04,0x01,0x00,0x54,0x04,0x01,0x00,0x53,0x04,0x01,0x00,0xd2,0x08, - 0x11,0x04,0x04,0x00,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x04,0x00, - 0xcf,0x86,0xd5,0x5b,0xd4,0x2e,0xd3,0x1e,0x92,0x1a,0xd1,0x0d,0x10,0x09,0x01,0xff, - 0xdb,0x95,0xd9,0x94,0x00,0x01,0x00,0x10,0x09,0x01,0xff,0xdb,0x81,0xd9,0x94,0x00, - 0x01,0x00,0x01,0x00,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00, - 0x04,0x00,0xd3,0x19,0xd2,0x11,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x01,0xff, - 0xdb,0x92,0xd9,0x94,0x00,0x11,0x04,0x01,0x00,0x01,0xe6,0x52,0x04,0x01,0xe6,0xd1, - 0x08,0x10,0x04,0x01,0xe6,0x01,0x00,0x10,0x04,0x01,0x00,0x01,0xe6,0xd4,0x38,0xd3, - 0x1c,0xd2,0x0c,0x51,0x04,0x01,0xe6,0x10,0x04,0x01,0xe6,0x01,0xdc,0xd1,0x08,0x10, - 0x04,0x01,0xe6,0x01,0x00,0x10,0x04,0x01,0x00,0x01,0xe6,0xd2,0x10,0xd1,0x08,0x10, - 0x04,0x01,0xe6,0x01,0x00,0x10,0x04,0x01,0xdc,0x01,0xe6,0x91,0x08,0x10,0x04,0x01, - 0xe6,0x01,0xdc,0x07,0x00,0x53,0x04,0x01,0x00,0xd2,0x08,0x11,0x04,0x01,0x00,0x04, - 0x00,0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x07,0x00,0xd1,0xc8,0xd0,0x76,0xcf, - 0x86,0xd5,0x28,0xd4,0x14,0x53,0x04,0x04,0x00,0x52,0x04,0x04,0x00,0x51,0x04,0x04, - 0x00,0x10,0x04,0x00,0x00,0x04,0x00,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x04, - 0x00,0x04,0x24,0x04,0x00,0x04,0x00,0x04,0x00,0xd4,0x14,0x53,0x04,0x04,0x00,0x52, - 0x04,0x04,0x00,0x91,0x08,0x10,0x04,0x04,0x00,0x07,0x00,0x07,0x00,0xd3,0x1c,0xd2, - 0x0c,0x91,0x08,0x10,0x04,0x04,0xe6,0x04,0xdc,0x04,0xe6,0xd1,0x08,0x10,0x04,0x04, - 0xdc,0x04,0xe6,0x10,0x04,0x04,0xe6,0x04,0xdc,0xd2,0x0c,0x51,0x04,0x04,0xdc,0x10, - 0x04,0x04,0xe6,0x04,0xdc,0xd1,0x08,0x10,0x04,0x04,0xdc,0x04,0xe6,0x10,0x04,0x04, - 0xdc,0x04,0xe6,0xcf,0x86,0xd5,0x3c,0x94,0x38,0xd3,0x1c,0xd2,0x0c,0x51,0x04,0x04, - 0xe6,0x10,0x04,0x04,0xdc,0x04,0xe6,0xd1,0x08,0x10,0x04,0x04,0xdc,0x04,0xe6,0x10, - 0x04,0x04,0xdc,0x04,0xe6,0xd2,0x10,0xd1,0x08,0x10,0x04,0x04,0xdc,0x04,0xe6,0x10, - 0x04,0x04,0xe6,0x00,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x07,0x00,0x07,0x00,0x08, - 0x00,0x94,0x10,0x53,0x04,0x08,0x00,0x52,0x04,0x08,0x00,0x11,0x04,0x08,0x00,0x0a, - 0x00,0x0a,0x00,0xd0,0x1e,0xcf,0x86,0x55,0x04,0x04,0x00,0x54,0x04,0x04,0x00,0x93, - 0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x04,0x00,0x06,0x00,0x00,0x00,0x00,0x00,0x00, - 0x00,0xcf,0x86,0x55,0x04,0x09,0x00,0xd4,0x14,0x53,0x04,0x09,0x00,0x92,0x0c,0x51, - 0x04,0x09,0x00,0x10,0x04,0x09,0x00,0x09,0xe6,0x09,0xe6,0xd3,0x10,0x92,0x0c,0x51, - 0x04,0x09,0xe6,0x10,0x04,0x09,0xdc,0x09,0xe6,0x09,0x00,0xd2,0x0c,0x51,0x04,0x09, - 0x00,0x10,0x04,0x09,0x00,0x00,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x14,0xdc,0x14, - 0x00,0xe4,0xf8,0x57,0xe3,0x45,0x3f,0xe2,0xf4,0x3e,0xe1,0xc7,0x2c,0xe0,0x21,0x10, - 0xcf,0x86,0xc5,0xe4,0x80,0x08,0xe3,0xcb,0x03,0xe2,0x61,0x01,0xd1,0x94,0xd0,0x5a, - 0xcf,0x86,0xd5,0x20,0x54,0x04,0x0b,0x00,0xd3,0x0c,0x52,0x04,0x0b,0x00,0x11,0x04, - 0x0b,0x00,0x0b,0xe6,0x92,0x0c,0x51,0x04,0x0b,0xe6,0x10,0x04,0x0b,0x00,0x0b,0xe6, - 0x0b,0xe6,0xd4,0x24,0xd3,0x10,0x52,0x04,0x0b,0xe6,0x91,0x08,0x10,0x04,0x0b,0x00, - 0x0b,0xe6,0x0b,0xe6,0xd2,0x0c,0x91,0x08,0x10,0x04,0x0b,0x00,0x0b,0xe6,0x0b,0xe6, - 0x11,0x04,0x0b,0xe6,0x00,0x00,0x53,0x04,0x0b,0x00,0x52,0x04,0x0b,0x00,0x51,0x04, - 0x0b,0x00,0x10,0x04,0x0b,0x00,0x00,0x00,0xcf,0x86,0xd5,0x20,0x54,0x04,0x0c,0x00, - 0x53,0x04,0x0c,0x00,0xd2,0x0c,0x91,0x08,0x10,0x04,0x0c,0x00,0x0c,0xdc,0x0c,0xdc, - 0x51,0x04,0x00,0x00,0x10,0x04,0x0c,0x00,0x00,0x00,0x94,0x14,0x53,0x04,0x13,0x00, - 0x92,0x0c,0x51,0x04,0x13,0x00,0x10,0x04,0x13,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - 0xd0,0x4a,0xcf,0x86,0x55,0x04,0x00,0x00,0xd4,0x20,0xd3,0x10,0x92,0x0c,0x91,0x08, - 0x10,0x04,0x0d,0x00,0x10,0x00,0x0d,0x00,0x0d,0x00,0x52,0x04,0x0d,0x00,0x91,0x08, - 0x10,0x04,0x0d,0x00,0x10,0x00,0x10,0x00,0xd3,0x18,0xd2,0x0c,0x51,0x04,0x10,0x00, - 0x10,0x04,0x10,0x00,0x11,0x00,0x91,0x08,0x10,0x04,0x11,0x00,0x00,0x00,0x12,0x00, - 0x52,0x04,0x12,0x00,0x11,0x04,0x12,0x00,0x00,0x00,0xcf,0x86,0xd5,0x18,0x54,0x04, - 0x00,0x00,0x93,0x10,0x92,0x0c,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x14,0xdc, - 0x12,0xe6,0x12,0xe6,0xd4,0x30,0xd3,0x18,0xd2,0x0c,0x51,0x04,0x12,0xe6,0x10,0x04, - 0x12,0x00,0x11,0xdc,0x51,0x04,0x0d,0xe6,0x10,0x04,0x0d,0xdc,0x0d,0xe6,0xd2,0x0c, - 0x91,0x08,0x10,0x04,0x0d,0xe6,0x0d,0xdc,0x0d,0xe6,0x91,0x08,0x10,0x04,0x0d,0xe6, - 0x0d,0xdc,0x0d,0xdc,0xd3,0x1c,0xd2,0x10,0xd1,0x08,0x10,0x04,0x0d,0x1b,0x0d,0x1c, - 0x10,0x04,0x0d,0x1d,0x0d,0xe6,0x51,0x04,0x0d,0xe6,0x10,0x04,0x0d,0xdc,0x0d,0xe6, - 0xd2,0x10,0xd1,0x08,0x10,0x04,0x0d,0xe6,0x0d,0xdc,0x10,0x04,0x0d,0xdc,0x0d,0xe6, - 0x51,0x04,0x0d,0xe6,0x10,0x04,0x0d,0xe6,0x10,0xe6,0xe1,0x3a,0x01,0xd0,0x77,0xcf, - 0x86,0xd5,0x20,0x94,0x1c,0x93,0x18,0xd2,0x0c,0x91,0x08,0x10,0x04,0x0b,0x00,0x01, - 0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x07,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01, - 0x00,0xd4,0x1b,0x53,0x04,0x01,0x00,0x92,0x13,0x91,0x0f,0x10,0x04,0x01,0x00,0x01, - 0xff,0xe0,0xa4,0xa8,0xe0,0xa4,0xbc,0x00,0x01,0x00,0x01,0x00,0xd3,0x26,0xd2,0x13, - 0x91,0x0f,0x10,0x04,0x01,0x00,0x01,0xff,0xe0,0xa4,0xb0,0xe0,0xa4,0xbc,0x00,0x01, - 0x00,0x91,0x0f,0x10,0x0b,0x01,0xff,0xe0,0xa4,0xb3,0xe0,0xa4,0xbc,0x00,0x01,0x00, - 0x01,0x00,0xd2,0x08,0x11,0x04,0x01,0x00,0x0c,0x00,0x91,0x08,0x10,0x04,0x01,0x07, - 0x01,0x00,0x01,0x00,0xcf,0x86,0xd5,0x8c,0xd4,0x18,0x53,0x04,0x01,0x00,0x52,0x04, - 0x01,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x01,0x09,0x10,0x04,0x0b,0x00,0x0c,0x00, - 0xd3,0x1c,0xd2,0x10,0xd1,0x08,0x10,0x04,0x01,0x00,0x01,0xe6,0x10,0x04,0x01,0xdc, - 0x01,0xe6,0x91,0x08,0x10,0x04,0x01,0xe6,0x0b,0x00,0x0c,0x00,0xd2,0x2c,0xd1,0x16, - 0x10,0x0b,0x01,0xff,0xe0,0xa4,0x95,0xe0,0xa4,0xbc,0x00,0x01,0xff,0xe0,0xa4,0x96, - 0xe0,0xa4,0xbc,0x00,0x10,0x0b,0x01,0xff,0xe0,0xa4,0x97,0xe0,0xa4,0xbc,0x00,0x01, - 0xff,0xe0,0xa4,0x9c,0xe0,0xa4,0xbc,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xe0,0xa4, - 0xa1,0xe0,0xa4,0xbc,0x00,0x01,0xff,0xe0,0xa4,0xa2,0xe0,0xa4,0xbc,0x00,0x10,0x0b, - 0x01,0xff,0xe0,0xa4,0xab,0xe0,0xa4,0xbc,0x00,0x01,0xff,0xe0,0xa4,0xaf,0xe0,0xa4, - 0xbc,0x00,0x54,0x04,0x01,0x00,0xd3,0x14,0x92,0x10,0xd1,0x08,0x10,0x04,0x01,0x00, - 0x0a,0x00,0x10,0x04,0x0a,0x00,0x0c,0x00,0x0c,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04, - 0x10,0x00,0x0b,0x00,0x10,0x04,0x0b,0x00,0x09,0x00,0x91,0x08,0x10,0x04,0x09,0x00, - 0x08,0x00,0x09,0x00,0xd0,0x86,0xcf,0x86,0xd5,0x44,0xd4,0x2c,0xd3,0x18,0xd2,0x0c, - 0x91,0x08,0x10,0x04,0x10,0x00,0x01,0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x00,0x00, - 0x01,0x00,0x01,0x00,0x52,0x04,0x01,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x00,0x00, - 0x10,0x04,0x00,0x00,0x01,0x00,0x93,0x14,0x92,0x10,0xd1,0x08,0x10,0x04,0x01,0x00, - 0x00,0x00,0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd4,0x14,0x53,0x04, - 0x01,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x01,0x00, - 0xd3,0x18,0xd2,0x10,0xd1,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x10,0x04,0x01,0x00, - 0x00,0x00,0x11,0x04,0x00,0x00,0x01,0x00,0xd2,0x08,0x11,0x04,0x01,0x00,0x00,0x00, - 0x91,0x08,0x10,0x04,0x01,0x07,0x07,0x00,0x01,0x00,0xcf,0x86,0xd5,0x7b,0xd4,0x42, - 0xd3,0x14,0x52,0x04,0x01,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x10,0x04, - 0x00,0x00,0x01,0x00,0xd2,0x17,0xd1,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x10,0x04, - 0x00,0x00,0x01,0xff,0xe0,0xa7,0x87,0xe0,0xa6,0xbe,0x00,0xd1,0x0f,0x10,0x0b,0x01, - 0xff,0xe0,0xa7,0x87,0xe0,0xa7,0x97,0x00,0x01,0x09,0x10,0x04,0x08,0x00,0x00,0x00, - 0xd3,0x10,0x52,0x04,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x01,0x00, - 0x52,0x04,0x00,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xe0,0xa6,0xa1,0xe0,0xa6,0xbc, - 0x00,0x01,0xff,0xe0,0xa6,0xa2,0xe0,0xa6,0xbc,0x00,0x10,0x04,0x00,0x00,0x01,0xff, - 0xe0,0xa6,0xaf,0xe0,0xa6,0xbc,0x00,0xd4,0x10,0x93,0x0c,0x52,0x04,0x01,0x00,0x11, - 0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x53,0x04,0x01,0x00,0xd2,0x0c,0x51,0x04,0x01, - 0x00,0x10,0x04,0x01,0x00,0x0b,0x00,0x51,0x04,0x13,0x00,0x10,0x04,0x14,0xe6,0x00, - 0x00,0xe2,0x48,0x02,0xe1,0x4f,0x01,0xd0,0xa4,0xcf,0x86,0xd5,0x4c,0xd4,0x34,0xd3, - 0x1c,0xd2,0x10,0xd1,0x08,0x10,0x04,0x00,0x00,0x07,0x00,0x10,0x04,0x01,0x00,0x07, - 0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0xd2,0x0c,0x51,0x04,0x01, - 0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x01, - 0x00,0x93,0x14,0x92,0x10,0xd1,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x10,0x04,0x00, - 0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd4,0x14,0x53,0x04,0x01,0x00,0x92,0x0c,0x91, - 0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x01,0x00,0xd3,0x2e,0xd2,0x17,0xd1, - 0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x10,0x04,0x01,0x00,0x01,0xff,0xe0,0xa8,0xb2, - 0xe0,0xa8,0xbc,0x00,0xd1,0x08,0x10,0x04,0x00,0x00,0x01,0x00,0x10,0x0b,0x01,0xff, - 0xe0,0xa8,0xb8,0xe0,0xa8,0xbc,0x00,0x00,0x00,0xd2,0x08,0x11,0x04,0x01,0x00,0x00, - 0x00,0x91,0x08,0x10,0x04,0x01,0x07,0x00,0x00,0x01,0x00,0xcf,0x86,0xd5,0x80,0xd4, - 0x34,0xd3,0x18,0xd2,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x51, - 0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x01,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04,0x01, - 0x00,0x00,0x00,0x10,0x04,0x00,0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x01,0x00,0x01, - 0x09,0x00,0x00,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x0a,0x00,0x00, - 0x00,0x00,0x00,0xd2,0x25,0xd1,0x0f,0x10,0x04,0x00,0x00,0x01,0xff,0xe0,0xa8,0x96, - 0xe0,0xa8,0xbc,0x00,0x10,0x0b,0x01,0xff,0xe0,0xa8,0x97,0xe0,0xa8,0xbc,0x00,0x01, - 0xff,0xe0,0xa8,0x9c,0xe0,0xa8,0xbc,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x00,0x00, - 0x10,0x0b,0x01,0xff,0xe0,0xa8,0xab,0xe0,0xa8,0xbc,0x00,0x00,0x00,0xd4,0x10,0x93, - 0x0c,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x93,0x14,0x52, - 0x04,0x01,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x0a,0x00,0x10,0x04,0x14,0x00,0x00, - 0x00,0x00,0x00,0xd0,0x82,0xcf,0x86,0xd5,0x40,0xd4,0x2c,0xd3,0x18,0xd2,0x0c,0x91, - 0x08,0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x01, - 0x00,0x01,0x00,0x52,0x04,0x01,0x00,0xd1,0x08,0x10,0x04,0x07,0x00,0x01,0x00,0x10, - 0x04,0x00,0x00,0x01,0x00,0x93,0x10,0x92,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x00, - 0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd4,0x14,0x53,0x04,0x01,0x00,0x92,0x0c,0x91, - 0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x01,0x00,0xd3,0x18,0xd2,0x0c,0x91, - 0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x01, - 0x00,0x01,0x00,0xd2,0x08,0x11,0x04,0x01,0x00,0x00,0x00,0x91,0x08,0x10,0x04,0x01, - 0x07,0x01,0x00,0x01,0x00,0xcf,0x86,0xd5,0x3c,0xd4,0x28,0xd3,0x10,0x52,0x04,0x01, - 0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x00,0x00,0x01,0x00,0xd2,0x0c,0x51,0x04,0x01, - 0x00,0x10,0x04,0x00,0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x01,0x00,0x01,0x09,0x00, - 0x00,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x00,0x00,0x00, - 0x00,0x00,0x00,0xd4,0x18,0x93,0x14,0xd2,0x0c,0x91,0x08,0x10,0x04,0x01,0x00,0x07, - 0x00,0x07,0x00,0x11,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0xd3,0x10,0x92,0x0c,0x91, - 0x08,0x10,0x04,0x0d,0x00,0x07,0x00,0x00,0x00,0x00,0x00,0x92,0x0c,0x91,0x08,0x10, - 0x04,0x00,0x00,0x11,0x00,0x13,0x00,0x13,0x00,0xe1,0x24,0x01,0xd0,0x86,0xcf,0x86, - 0xd5,0x44,0xd4,0x2c,0xd3,0x18,0xd2,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x01,0x00, - 0x01,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x52,0x04,0x01,0x00, - 0xd1,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x10,0x04,0x00,0x00,0x01,0x00,0x93,0x14, - 0x92,0x10,0xd1,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x10,0x04,0x00,0x00,0x01,0x00, - 0x01,0x00,0x01,0x00,0xd4,0x14,0x53,0x04,0x01,0x00,0x92,0x0c,0x91,0x08,0x10,0x04, - 0x01,0x00,0x00,0x00,0x01,0x00,0x01,0x00,0xd3,0x18,0xd2,0x0c,0x91,0x08,0x10,0x04, - 0x01,0x00,0x00,0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x07,0x00,0x01,0x00, - 0xd2,0x08,0x11,0x04,0x01,0x00,0x00,0x00,0x91,0x08,0x10,0x04,0x01,0x07,0x01,0x00, - 0x01,0x00,0xcf,0x86,0xd5,0x73,0xd4,0x45,0xd3,0x14,0x52,0x04,0x01,0x00,0xd1,0x08, - 0x10,0x04,0x0a,0x00,0x00,0x00,0x10,0x04,0x00,0x00,0x01,0x00,0xd2,0x1e,0xd1,0x0f, - 0x10,0x0b,0x01,0xff,0xe0,0xad,0x87,0xe0,0xad,0x96,0x00,0x00,0x00,0x10,0x04,0x00, - 0x00,0x01,0xff,0xe0,0xad,0x87,0xe0,0xac,0xbe,0x00,0x91,0x0f,0x10,0x0b,0x01,0xff, - 0xe0,0xad,0x87,0xe0,0xad,0x97,0x00,0x01,0x09,0x00,0x00,0xd3,0x0c,0x52,0x04,0x00, - 0x00,0x11,0x04,0x00,0x00,0x01,0x00,0x52,0x04,0x00,0x00,0xd1,0x16,0x10,0x0b,0x01, - 0xff,0xe0,0xac,0xa1,0xe0,0xac,0xbc,0x00,0x01,0xff,0xe0,0xac,0xa2,0xe0,0xac,0xbc, - 0x00,0x10,0x04,0x00,0x00,0x01,0x00,0xd4,0x14,0x93,0x10,0xd2,0x08,0x11,0x04,0x01, - 0x00,0x0a,0x00,0x11,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x93,0x10,0x92,0x0c,0x91, - 0x08,0x10,0x04,0x01,0x00,0x07,0x00,0x0c,0x00,0x0c,0x00,0x00,0x00,0xd0,0xb1,0xcf, - 0x86,0xd5,0x63,0xd4,0x28,0xd3,0x14,0xd2,0x08,0x11,0x04,0x00,0x00,0x01,0x00,0x91, - 0x08,0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0xd2,0x0c,0x51,0x04,0x01,0x00,0x10, - 0x04,0x01,0x00,0x00,0x00,0x11,0x04,0x00,0x00,0x01,0x00,0xd3,0x1f,0xd2,0x0c,0x91, - 0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x91,0x0f,0x10,0x0b,0x01,0xff,0xe0, - 0xae,0x92,0xe0,0xaf,0x97,0x00,0x01,0x00,0x00,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04, - 0x00,0x00,0x01,0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x91,0x08,0x10,0x04,0x01,0x00, - 0x00,0x00,0x01,0x00,0xd4,0x2c,0xd3,0x18,0xd2,0x0c,0x51,0x04,0x00,0x00,0x10,0x04, - 0x00,0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x00,0x00,0xd2,0x0c, - 0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x11,0x04,0x00,0x00,0x01,0x00, - 0xd3,0x10,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x08,0x00,0x01,0x00, - 0xd2,0x08,0x11,0x04,0x01,0x00,0x00,0x00,0x11,0x04,0x00,0x00,0x01,0x00,0xcf,0x86, - 0xd5,0x61,0xd4,0x45,0xd3,0x14,0xd2,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00, - 0x00,0x00,0x11,0x04,0x00,0x00,0x01,0x00,0xd2,0x1e,0xd1,0x08,0x10,0x04,0x01,0x00, - 0x00,0x00,0x10,0x0b,0x01,0xff,0xe0,0xaf,0x86,0xe0,0xae,0xbe,0x00,0x01,0xff,0xe0, - 0xaf,0x87,0xe0,0xae,0xbe,0x00,0x91,0x0f,0x10,0x0b,0x01,0xff,0xe0,0xaf,0x86,0xe0, - 0xaf,0x97,0x00,0x01,0x09,0x00,0x00,0x93,0x18,0xd2,0x0c,0x91,0x08,0x10,0x04,0x0a, - 0x00,0x00,0x00,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x01,0x00,0x00, - 0x00,0xd4,0x14,0x93,0x10,0x52,0x04,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x08, - 0x00,0x01,0x00,0x01,0x00,0xd3,0x10,0x92,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01, - 0x00,0x07,0x00,0x07,0x00,0x92,0x0c,0x51,0x04,0x07,0x00,0x10,0x04,0x07,0x00,0x00, - 0x00,0x00,0x00,0xe3,0x1c,0x04,0xe2,0x1a,0x02,0xd1,0xf3,0xd0,0x76,0xcf,0x86,0xd5, - 0x3c,0xd4,0x28,0xd3,0x18,0xd2,0x0c,0x91,0x08,0x10,0x04,0x10,0x00,0x01,0x00,0x01, - 0x00,0x91,0x08,0x10,0x04,0x14,0x00,0x01,0x00,0x01,0x00,0x52,0x04,0x01,0x00,0x91, - 0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x93,0x10,0x92,0x0c,0x91,0x08,0x10, - 0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd4,0x14,0x53,0x04,0x01, - 0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x01,0x00,0xd3, - 0x10,0x52,0x04,0x01,0x00,0x91,0x08,0x10,0x04,0x10,0x00,0x01,0x00,0x01,0x00,0xd2, - 0x08,0x11,0x04,0x01,0x00,0x00,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x0a,0x00,0x01, - 0x00,0xcf,0x86,0xd5,0x53,0xd4,0x2f,0xd3,0x10,0x52,0x04,0x01,0x00,0x91,0x08,0x10, - 0x04,0x01,0x00,0x00,0x00,0x01,0x00,0xd2,0x13,0x91,0x0f,0x10,0x0b,0x01,0xff,0xe0, - 0xb1,0x86,0xe0,0xb1,0x96,0x00,0x00,0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x01,0x00, - 0x01,0x09,0x00,0x00,0xd3,0x14,0x52,0x04,0x00,0x00,0xd1,0x08,0x10,0x04,0x00,0x00, - 0x01,0x54,0x10,0x04,0x01,0x5b,0x00,0x00,0x92,0x0c,0x51,0x04,0x0a,0x00,0x10,0x04, - 0x11,0x00,0x00,0x00,0x00,0x00,0xd4,0x14,0x93,0x10,0xd2,0x08,0x11,0x04,0x01,0x00, - 0x0a,0x00,0x11,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x93,0x10,0x52,0x04,0x00,0x00, - 0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x15,0x00,0x0a,0x00,0xd0,0x76,0xcf,0x86, - 0xd5,0x3c,0xd4,0x28,0xd3,0x18,0xd2,0x0c,0x91,0x08,0x10,0x04,0x12,0x00,0x10,0x00, - 0x01,0x00,0x91,0x08,0x10,0x04,0x14,0x00,0x01,0x00,0x01,0x00,0x52,0x04,0x01,0x00, - 0x91,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x93,0x10,0x92,0x0c,0x91,0x08, - 0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd4,0x14,0x53,0x04, - 0x01,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x01,0x00, - 0xd3,0x10,0x52,0x04,0x01,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00, - 0xd2,0x08,0x11,0x04,0x01,0x00,0x00,0x00,0x91,0x08,0x10,0x04,0x07,0x07,0x07,0x00, - 0x01,0x00,0xcf,0x86,0xd5,0x82,0xd4,0x5e,0xd3,0x2a,0xd2,0x13,0x91,0x0f,0x10,0x0b, - 0x01,0xff,0xe0,0xb2,0xbf,0xe0,0xb3,0x95,0x00,0x01,0x00,0x01,0x00,0xd1,0x08,0x10, - 0x04,0x01,0x00,0x00,0x00,0x10,0x04,0x01,0x00,0x01,0xff,0xe0,0xb3,0x86,0xe0,0xb3, - 0x95,0x00,0xd2,0x28,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe0,0xb3,0x86,0xe0,0xb3,0x96, - 0x00,0x00,0x00,0x10,0x0b,0x01,0xff,0xe0,0xb3,0x86,0xe0,0xb3,0x82,0x00,0x01,0xff, - 0xe0,0xb3,0x86,0xe0,0xb3,0x82,0xe0,0xb3,0x95,0x00,0x91,0x08,0x10,0x04,0x01,0x00, - 0x01,0x09,0x00,0x00,0xd3,0x14,0x52,0x04,0x00,0x00,0xd1,0x08,0x10,0x04,0x00,0x00, - 0x01,0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x52,0x04,0x00,0x00,0x51,0x04,0x00,0x00, - 0x10,0x04,0x01,0x00,0x00,0x00,0xd4,0x14,0x93,0x10,0xd2,0x08,0x11,0x04,0x01,0x00, - 0x09,0x00,0x11,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x93,0x14,0x92,0x10,0xd1,0x08, - 0x10,0x04,0x00,0x00,0x09,0x00,0x10,0x04,0x09,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - 0xe1,0x06,0x01,0xd0,0x6e,0xcf,0x86,0xd5,0x3c,0xd4,0x28,0xd3,0x18,0xd2,0x0c,0x91, - 0x08,0x10,0x04,0x13,0x00,0x10,0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x01, - 0x00,0x01,0x00,0x52,0x04,0x01,0x00,0x91,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01, - 0x00,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x01, - 0x00,0x01,0x00,0xd4,0x14,0x53,0x04,0x01,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x01, - 0x00,0x0c,0x00,0x01,0x00,0x01,0x00,0x53,0x04,0x01,0x00,0xd2,0x0c,0x51,0x04,0x01, - 0x00,0x10,0x04,0x0c,0x00,0x13,0x09,0x91,0x08,0x10,0x04,0x13,0x09,0x0a,0x00,0x01, - 0x00,0xcf,0x86,0xd5,0x65,0xd4,0x45,0xd3,0x10,0x52,0x04,0x01,0x00,0x91,0x08,0x10, - 0x04,0x0a,0x00,0x00,0x00,0x01,0x00,0xd2,0x1e,0xd1,0x08,0x10,0x04,0x01,0x00,0x00, - 0x00,0x10,0x0b,0x01,0xff,0xe0,0xb5,0x86,0xe0,0xb4,0xbe,0x00,0x01,0xff,0xe0,0xb5, - 0x87,0xe0,0xb4,0xbe,0x00,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe0,0xb5,0x86,0xe0,0xb5, - 0x97,0x00,0x01,0x09,0x10,0x04,0x0c,0x00,0x12,0x00,0xd3,0x10,0x52,0x04,0x00,0x00, - 0x51,0x04,0x12,0x00,0x10,0x04,0x12,0x00,0x01,0x00,0x52,0x04,0x12,0x00,0x51,0x04, - 0x12,0x00,0x10,0x04,0x12,0x00,0x11,0x00,0xd4,0x14,0x93,0x10,0xd2,0x08,0x11,0x04, - 0x01,0x00,0x0a,0x00,0x11,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0xd3,0x0c,0x52,0x04, - 0x0a,0x00,0x11,0x04,0x0a,0x00,0x12,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x12,0x00, - 0x0a,0x00,0x0a,0x00,0x0a,0x00,0xd0,0x5a,0xcf,0x86,0xd5,0x34,0xd4,0x18,0x93,0x14, - 0xd2,0x08,0x11,0x04,0x00,0x00,0x04,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x04,0x00, - 0x04,0x00,0x04,0x00,0xd3,0x10,0x52,0x04,0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x04, - 0x04,0x00,0x00,0x00,0x92,0x08,0x11,0x04,0x00,0x00,0x04,0x00,0x04,0x00,0x54,0x04, - 0x04,0x00,0xd3,0x10,0x92,0x0c,0x51,0x04,0x04,0x00,0x10,0x04,0x00,0x00,0x04,0x00, - 0x04,0x00,0x52,0x04,0x04,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x04,0x00,0x00,0x00, - 0xcf,0x86,0xd5,0x77,0xd4,0x28,0xd3,0x10,0x52,0x04,0x04,0x00,0x51,0x04,0x04,0x00, - 0x10,0x04,0x04,0x00,0x00,0x00,0xd2,0x0c,0x51,0x04,0x00,0x00,0x10,0x04,0x04,0x09, - 0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x04,0x00,0xd3,0x14,0x52,0x04, - 0x04,0x00,0xd1,0x08,0x10,0x04,0x04,0x00,0x00,0x00,0x10,0x04,0x04,0x00,0x00,0x00, - 0xd2,0x13,0x51,0x04,0x04,0x00,0x10,0x0b,0x04,0xff,0xe0,0xb7,0x99,0xe0,0xb7,0x8a, - 0x00,0x04,0x00,0xd1,0x19,0x10,0x0b,0x04,0xff,0xe0,0xb7,0x99,0xe0,0xb7,0x8f,0x00, - 0x04,0xff,0xe0,0xb7,0x99,0xe0,0xb7,0x8f,0xe0,0xb7,0x8a,0x00,0x10,0x0b,0x04,0xff, - 0xe0,0xb7,0x99,0xe0,0xb7,0x9f,0x00,0x04,0x00,0xd4,0x10,0x93,0x0c,0x52,0x04,0x00, - 0x00,0x11,0x04,0x00,0x00,0x10,0x00,0x10,0x00,0x93,0x14,0xd2,0x08,0x11,0x04,0x00, - 0x00,0x04,0x00,0x91,0x08,0x10,0x04,0x04,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xe2, - 0x31,0x01,0xd1,0x58,0xd0,0x3a,0xcf,0x86,0xd5,0x18,0x94,0x14,0x93,0x10,0x92,0x0c, - 0x91,0x08,0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00, - 0x54,0x04,0x01,0x00,0x53,0x04,0x01,0x00,0xd2,0x0c,0x51,0x04,0x01,0x67,0x10,0x04, - 0x01,0x09,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x01,0x00,0xcf,0x86, - 0x95,0x18,0xd4,0x0c,0x53,0x04,0x01,0x00,0x12,0x04,0x01,0x6b,0x01,0x00,0x53,0x04, - 0x01,0x00,0x12,0x04,0x01,0x00,0x00,0x00,0x00,0x00,0xd0,0x9e,0xcf,0x86,0xd5,0x54, - 0xd4,0x3c,0xd3,0x20,0xd2,0x10,0xd1,0x08,0x10,0x04,0x00,0x00,0x01,0x00,0x10,0x04, - 0x01,0x00,0x00,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x10,0x04,0x15,0x00, - 0x01,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04,0x01,0x00,0x15,0x00,0x10,0x04,0x01,0x00, - 0x00,0x00,0x91,0x08,0x10,0x04,0x15,0x00,0x01,0x00,0x15,0x00,0xd3,0x08,0x12,0x04, - 0x15,0x00,0x01,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x15,0x00,0x01,0x00,0x01,0x00, - 0x01,0x00,0xd4,0x30,0xd3,0x1c,0xd2,0x0c,0x91,0x08,0x10,0x04,0x15,0x00,0x01,0x00, - 0x01,0x00,0xd1,0x08,0x10,0x04,0x00,0x00,0x01,0x00,0x10,0x04,0x00,0x00,0x01,0x00, - 0xd2,0x08,0x11,0x04,0x15,0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x15,0x00,0x01,0x00, - 0x01,0x00,0x53,0x04,0x01,0x00,0xd2,0x0c,0x51,0x04,0x01,0x76,0x10,0x04,0x15,0x09, - 0x01,0x00,0x11,0x04,0x01,0x00,0x00,0x00,0xcf,0x86,0x95,0x34,0xd4,0x20,0xd3,0x14, - 0x52,0x04,0x01,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x10,0x04,0x01,0x00, - 0x00,0x00,0x52,0x04,0x01,0x7a,0x11,0x04,0x01,0x00,0x00,0x00,0x53,0x04,0x01,0x00, - 0xd2,0x08,0x11,0x04,0x01,0x00,0x00,0x00,0x11,0x04,0x01,0x00,0x0d,0x00,0x00,0x00, - 0xe1,0x2b,0x01,0xd0,0x3e,0xcf,0x86,0xd5,0x14,0x54,0x04,0x02,0x00,0x53,0x04,0x02, - 0x00,0x92,0x08,0x11,0x04,0x02,0xdc,0x02,0x00,0x02,0x00,0x54,0x04,0x02,0x00,0xd3, - 0x14,0x52,0x04,0x02,0x00,0xd1,0x08,0x10,0x04,0x02,0x00,0x02,0xdc,0x10,0x04,0x02, - 0x00,0x02,0xdc,0x92,0x0c,0x91,0x08,0x10,0x04,0x02,0x00,0x02,0xd8,0x02,0x00,0x02, - 0x00,0xcf,0x86,0xd5,0x73,0xd4,0x36,0xd3,0x17,0x92,0x13,0x51,0x04,0x02,0x00,0x10, - 0x04,0x02,0x00,0x02,0xff,0xe0,0xbd,0x82,0xe0,0xbe,0xb7,0x00,0x02,0x00,0xd2,0x0c, - 0x91,0x08,0x10,0x04,0x00,0x00,0x02,0x00,0x02,0x00,0x91,0x0f,0x10,0x04,0x02,0x00, - 0x02,0xff,0xe0,0xbd,0x8c,0xe0,0xbe,0xb7,0x00,0x02,0x00,0xd3,0x26,0xd2,0x13,0x51, - 0x04,0x02,0x00,0x10,0x0b,0x02,0xff,0xe0,0xbd,0x91,0xe0,0xbe,0xb7,0x00,0x02,0x00, - 0x51,0x04,0x02,0x00,0x10,0x04,0x02,0x00,0x02,0xff,0xe0,0xbd,0x96,0xe0,0xbe,0xb7, - 0x00,0x52,0x04,0x02,0x00,0x91,0x0f,0x10,0x0b,0x02,0xff,0xe0,0xbd,0x9b,0xe0,0xbe, - 0xb7,0x00,0x02,0x00,0x02,0x00,0xd4,0x27,0x53,0x04,0x02,0x00,0xd2,0x17,0xd1,0x0f, - 0x10,0x04,0x02,0x00,0x02,0xff,0xe0,0xbd,0x80,0xe0,0xbe,0xb5,0x00,0x10,0x04,0x04, - 0x00,0x0a,0x00,0x91,0x08,0x10,0x04,0x0a,0x00,0x00,0x00,0x00,0x00,0xd3,0x35,0xd2, - 0x17,0xd1,0x08,0x10,0x04,0x00,0x00,0x02,0x81,0x10,0x04,0x02,0x82,0x02,0xff,0xe0, - 0xbd,0xb1,0xe0,0xbd,0xb2,0x00,0xd1,0x0f,0x10,0x04,0x02,0x84,0x02,0xff,0xe0,0xbd, - 0xb1,0xe0,0xbd,0xb4,0x00,0x10,0x0b,0x02,0xff,0xe0,0xbe,0xb2,0xe0,0xbe,0x80,0x00, - 0x02,0x00,0xd2,0x13,0x91,0x0f,0x10,0x0b,0x02,0xff,0xe0,0xbe,0xb3,0xe0,0xbe,0x80, - 0x00,0x02,0x00,0x02,0x82,0x11,0x04,0x02,0x82,0x02,0x00,0xd0,0xd3,0xcf,0x86,0xd5, - 0x65,0xd4,0x27,0xd3,0x1f,0xd2,0x13,0x91,0x0f,0x10,0x04,0x02,0x82,0x02,0xff,0xe0, - 0xbd,0xb1,0xe0,0xbe,0x80,0x00,0x02,0xe6,0x91,0x08,0x10,0x04,0x02,0x09,0x02,0x00, - 0x02,0xe6,0x12,0x04,0x02,0x00,0x0c,0x00,0xd3,0x1f,0xd2,0x13,0x51,0x04,0x02,0x00, - 0x10,0x04,0x02,0x00,0x02,0xff,0xe0,0xbe,0x92,0xe0,0xbe,0xb7,0x00,0x51,0x04,0x02, - 0x00,0x10,0x04,0x04,0x00,0x02,0x00,0xd2,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x02, - 0x00,0x02,0x00,0x91,0x0f,0x10,0x04,0x02,0x00,0x02,0xff,0xe0,0xbe,0x9c,0xe0,0xbe, - 0xb7,0x00,0x02,0x00,0xd4,0x3d,0xd3,0x26,0xd2,0x13,0x51,0x04,0x02,0x00,0x10,0x0b, - 0x02,0xff,0xe0,0xbe,0xa1,0xe0,0xbe,0xb7,0x00,0x02,0x00,0x51,0x04,0x02,0x00,0x10, - 0x04,0x02,0x00,0x02,0xff,0xe0,0xbe,0xa6,0xe0,0xbe,0xb7,0x00,0x52,0x04,0x02,0x00, - 0x91,0x0f,0x10,0x0b,0x02,0xff,0xe0,0xbe,0xab,0xe0,0xbe,0xb7,0x00,0x02,0x00,0x04, - 0x00,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x04,0x00,0x02,0x00,0x02,0x00,0x02, - 0x00,0xd2,0x13,0x91,0x0f,0x10,0x04,0x04,0x00,0x02,0xff,0xe0,0xbe,0x90,0xe0,0xbe, - 0xb5,0x00,0x04,0x00,0x91,0x08,0x10,0x04,0x04,0x00,0x00,0x00,0x04,0x00,0xcf,0x86, - 0x95,0x4c,0xd4,0x24,0xd3,0x10,0x52,0x04,0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x04, - 0x04,0xdc,0x04,0x00,0x52,0x04,0x04,0x00,0xd1,0x08,0x10,0x04,0x04,0x00,0x00,0x00, - 0x10,0x04,0x0a,0x00,0x04,0x00,0xd3,0x14,0xd2,0x08,0x11,0x04,0x08,0x00,0x0a,0x00, - 0x91,0x08,0x10,0x04,0x0a,0x00,0x0b,0x00,0x0b,0x00,0x92,0x10,0xd1,0x08,0x10,0x04, - 0x0b,0x00,0x0c,0x00,0x10,0x04,0x0c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x86, - 0xe5,0xf7,0x04,0xe4,0x79,0x03,0xe3,0x7b,0x01,0xe2,0x04,0x01,0xd1,0x7f,0xd0,0x65, - 0xcf,0x86,0x55,0x04,0x04,0x00,0xd4,0x33,0xd3,0x1f,0xd2,0x0c,0x51,0x04,0x04,0x00, - 0x10,0x04,0x0a,0x00,0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x0b,0x04,0xff,0xe1,0x80, - 0xa5,0xe1,0x80,0xae,0x00,0x04,0x00,0x92,0x10,0xd1,0x08,0x10,0x04,0x0a,0x00,0x04, - 0x00,0x10,0x04,0x04,0x00,0x0a,0x00,0x04,0x00,0xd3,0x18,0xd2,0x0c,0x51,0x04,0x04, - 0x00,0x10,0x04,0x04,0x00,0x0a,0x00,0x51,0x04,0x0a,0x00,0x10,0x04,0x04,0x00,0x04, - 0x07,0x92,0x10,0xd1,0x08,0x10,0x04,0x04,0x00,0x04,0x09,0x10,0x04,0x0a,0x09,0x0a, - 0x00,0x0a,0x00,0xcf,0x86,0x95,0x14,0x54,0x04,0x04,0x00,0x53,0x04,0x04,0x00,0x92, - 0x08,0x11,0x04,0x04,0x00,0x0a,0x00,0x0a,0x00,0x0a,0x00,0xd0,0x2e,0xcf,0x86,0x95, - 0x28,0xd4,0x14,0x53,0x04,0x0a,0x00,0x52,0x04,0x0a,0x00,0x91,0x08,0x10,0x04,0x0a, - 0x00,0x0a,0xdc,0x0a,0x00,0x53,0x04,0x0a,0x00,0xd2,0x08,0x11,0x04,0x0a,0x00,0x0b, - 0x00,0x11,0x04,0x0b,0x00,0x0a,0x00,0x01,0x00,0xcf,0x86,0xd5,0x24,0x94,0x20,0xd3, - 0x10,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x00,0x00,0x0d,0x00,0x52, - 0x04,0x00,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x0d,0x00,0x00,0x00,0x01,0x00,0x54, - 0x04,0x01,0x00,0xd3,0x10,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01, - 0x00,0x06,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04,0x06,0x00,0x08,0x00,0x10,0x04,0x08, - 0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x08,0x00,0x0d,0x00,0x0d,0x00,0xd1,0x3e,0xd0, - 0x06,0xcf,0x06,0x01,0x00,0xcf,0x86,0xd5,0x1d,0x54,0x04,0x01,0x00,0x53,0x04,0x01, - 0x00,0xd2,0x08,0x11,0x04,0x01,0x00,0x0b,0x00,0x51,0x04,0x0b,0x00,0x10,0x04,0x0b, - 0x00,0x01,0xff,0x00,0x94,0x15,0x93,0x11,0x92,0x0d,0x91,0x09,0x10,0x05,0x01,0xff, - 0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd0,0x1e,0xcf,0x86,0x55, - 0x04,0x01,0x00,0x94,0x14,0x93,0x10,0x92,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01, - 0x00,0x0b,0x00,0x0b,0x00,0x01,0x00,0x01,0x00,0xcf,0x86,0x55,0x04,0x01,0x00,0x54, - 0x04,0x01,0x00,0x53,0x04,0x01,0x00,0x92,0x08,0x11,0x04,0x01,0x00,0x0b,0x00,0x0b, - 0x00,0xe2,0x21,0x01,0xd1,0x6c,0xd0,0x1e,0xcf,0x86,0x95,0x18,0x94,0x14,0x93,0x10, - 0x52,0x04,0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x08,0x00,0x04,0x00, - 0x04,0x00,0x04,0x00,0xcf,0x86,0x95,0x48,0xd4,0x24,0xd3,0x10,0x52,0x04,0x04,0x00, - 0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x08,0x00,0xd2,0x0c,0x91,0x08,0x10,0x04, - 0x04,0x00,0x00,0x00,0x04,0x00,0x11,0x04,0x04,0x00,0x00,0x00,0xd3,0x10,0x52,0x04, - 0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x00,0x00,0xd2,0x0c,0x91,0x08, - 0x10,0x04,0x04,0x00,0x00,0x00,0x04,0x00,0x11,0x04,0x04,0x00,0x00,0x00,0x04,0x00, - 0xd0,0x62,0xcf,0x86,0xd5,0x28,0x94,0x24,0xd3,0x10,0x52,0x04,0x04,0x00,0x51,0x04, - 0x04,0x00,0x10,0x04,0x04,0x00,0x08,0x00,0xd2,0x0c,0x91,0x08,0x10,0x04,0x04,0x00, - 0x00,0x00,0x04,0x00,0x11,0x04,0x04,0x00,0x00,0x00,0x04,0x00,0xd4,0x14,0x53,0x04, - 0x04,0x00,0x52,0x04,0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x08,0x00, - 0xd3,0x14,0xd2,0x0c,0x91,0x08,0x10,0x04,0x04,0x00,0x00,0x00,0x04,0x00,0x11,0x04, - 0x04,0x00,0x00,0x00,0x52,0x04,0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00, - 0x00,0x00,0xcf,0x86,0xd5,0x38,0xd4,0x24,0xd3,0x14,0xd2,0x0c,0x91,0x08,0x10,0x04, - 0x04,0x00,0x00,0x00,0x04,0x00,0x11,0x04,0x04,0x00,0x00,0x00,0x52,0x04,0x04,0x00, - 0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x08,0x00,0x93,0x10,0x52,0x04,0x04,0x00, - 0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x00,0x00,0x04,0x00,0x94,0x14,0x53,0x04, - 0x04,0x00,0x52,0x04,0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x08,0x00, - 0x04,0x00,0xd1,0x9c,0xd0,0x3e,0xcf,0x86,0x95,0x38,0xd4,0x14,0x53,0x04,0x04,0x00, - 0x52,0x04,0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x08,0x00,0xd3,0x14, - 0xd2,0x0c,0x91,0x08,0x10,0x04,0x04,0x00,0x00,0x00,0x04,0x00,0x11,0x04,0x04,0x00, - 0x00,0x00,0x52,0x04,0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x08,0x00, - 0x04,0x00,0xcf,0x86,0xd5,0x34,0xd4,0x14,0x93,0x10,0x52,0x04,0x04,0x00,0x51,0x04, - 0x04,0x00,0x10,0x04,0x04,0x00,0x08,0x00,0x04,0x00,0x53,0x04,0x04,0x00,0xd2,0x0c, - 0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x00,0x00,0xd1,0x08,0x10,0x04,0x00,0x00, - 0x0c,0xe6,0x10,0x04,0x0c,0xe6,0x08,0xe6,0xd4,0x14,0x93,0x10,0x92,0x0c,0x91,0x08, - 0x10,0x04,0x08,0x00,0x04,0x00,0x04,0x00,0x04,0x00,0x04,0x00,0x53,0x04,0x04,0x00, - 0x52,0x04,0x04,0x00,0x91,0x08,0x10,0x04,0x04,0x00,0x00,0x00,0x00,0x00,0xd0,0x1a, - 0xcf,0x86,0x95,0x14,0x54,0x04,0x08,0x00,0x53,0x04,0x08,0x00,0x92,0x08,0x11,0x04, - 0x08,0x00,0x00,0x00,0x00,0x00,0x04,0x00,0xcf,0x86,0x55,0x04,0x04,0x00,0x54,0x04, - 0x04,0x00,0xd3,0x10,0x52,0x04,0x04,0x00,0x91,0x08,0x10,0x04,0x04,0x00,0x11,0x00, - 0x00,0x00,0x52,0x04,0x11,0x00,0x11,0x04,0x11,0x00,0x00,0x00,0xd3,0x30,0xd2,0x2a, - 0xd1,0x24,0xd0,0x1e,0xcf,0x86,0x95,0x18,0x94,0x14,0x93,0x10,0x92,0x0c,0x91,0x08, - 0x10,0x04,0x0b,0x00,0x04,0x00,0x04,0x00,0x04,0x00,0x04,0x00,0x04,0x00,0x04,0x00, - 0xcf,0x06,0x04,0x00,0xcf,0x06,0x04,0x00,0xcf,0x06,0x04,0x00,0xd2,0x6c,0xd1,0x24, - 0xd0,0x06,0xcf,0x06,0x04,0x00,0xcf,0x86,0x55,0x04,0x04,0x00,0x54,0x04,0x04,0x00, - 0x93,0x10,0x52,0x04,0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x0b,0x00, - 0x0b,0x00,0xd0,0x1e,0xcf,0x86,0x95,0x18,0x54,0x04,0x04,0x00,0x53,0x04,0x04,0x00, - 0x52,0x04,0x04,0x00,0x91,0x08,0x10,0x04,0x04,0x00,0x00,0x00,0x00,0x00,0x04,0x00, - 0xcf,0x86,0x55,0x04,0x04,0x00,0x54,0x04,0x04,0x00,0xd3,0x10,0x92,0x0c,0x91,0x08, - 0x10,0x04,0x04,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x92,0x0c,0x91,0x08,0x10,0x04, - 0x10,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd1,0x80,0xd0,0x46,0xcf,0x86,0xd5,0x28, - 0xd4,0x14,0x53,0x04,0x06,0x00,0x52,0x04,0x06,0x00,0x91,0x08,0x10,0x04,0x06,0x00, - 0x00,0x00,0x06,0x00,0x93,0x10,0x52,0x04,0x06,0x00,0x91,0x08,0x10,0x04,0x06,0x09, - 0x00,0x00,0x00,0x00,0x00,0x00,0x54,0x04,0x06,0x00,0x93,0x14,0x52,0x04,0x06,0x00, - 0xd1,0x08,0x10,0x04,0x06,0x09,0x06,0x00,0x10,0x04,0x06,0x00,0x00,0x00,0x00,0x00, - 0xcf,0x86,0xd5,0x10,0x54,0x04,0x06,0x00,0x93,0x08,0x12,0x04,0x06,0x00,0x00,0x00, - 0x00,0x00,0xd4,0x14,0x53,0x04,0x06,0x00,0x52,0x04,0x06,0x00,0x91,0x08,0x10,0x04, - 0x06,0x00,0x00,0x00,0x06,0x00,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x06,0x00, - 0x00,0x00,0x06,0x00,0x00,0x00,0x00,0x00,0xd0,0x1b,0xcf,0x86,0x55,0x04,0x04,0x00, - 0x54,0x04,0x04,0x00,0x93,0x0d,0x52,0x04,0x04,0x00,0x11,0x05,0x04,0xff,0x00,0x04, - 0x00,0x04,0x00,0xcf,0x86,0xd5,0x24,0x54,0x04,0x04,0x00,0xd3,0x10,0x92,0x0c,0x51, - 0x04,0x04,0x00,0x10,0x04,0x04,0x09,0x04,0x00,0x04,0x00,0x52,0x04,0x04,0x00,0x91, - 0x08,0x10,0x04,0x04,0x00,0x07,0xe6,0x00,0x00,0xd4,0x10,0x53,0x04,0x04,0x00,0x92, - 0x08,0x11,0x04,0x04,0x00,0x00,0x00,0x00,0x00,0x53,0x04,0x07,0x00,0x92,0x08,0x11, - 0x04,0x07,0x00,0x00,0x00,0x00,0x00,0xe4,0xb7,0x03,0xe3,0x58,0x01,0xd2,0x8f,0xd1, - 0x53,0xd0,0x35,0xcf,0x86,0x95,0x2f,0xd4,0x1f,0x53,0x04,0x04,0x00,0xd2,0x0d,0x51, - 0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x04,0xff,0x00,0x51,0x05,0x04,0xff,0x00,0x10, - 0x05,0x04,0xff,0x00,0x00,0x00,0x53,0x04,0x04,0x00,0x92,0x08,0x11,0x04,0x04,0x00, - 0x00,0x00,0x00,0x00,0x04,0x00,0xcf,0x86,0x55,0x04,0x04,0x00,0x54,0x04,0x04,0x00, - 0x53,0x04,0x04,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x14,0x00,0x00,0x00,0x00,0x00, - 0x00,0x00,0xd0,0x22,0xcf,0x86,0x55,0x04,0x04,0x00,0x94,0x18,0x53,0x04,0x04,0x00, - 0x92,0x10,0xd1,0x08,0x10,0x04,0x04,0x00,0x04,0xe4,0x10,0x04,0x0a,0x00,0x00,0x00, - 0x00,0x00,0x0b,0x00,0xcf,0x86,0x55,0x04,0x0b,0x00,0x54,0x04,0x0b,0x00,0x93,0x0c, - 0x52,0x04,0x0b,0x00,0x11,0x04,0x0b,0x00,0x00,0x00,0x00,0x00,0xd1,0x80,0xd0,0x42, - 0xcf,0x86,0xd5,0x1c,0x54,0x04,0x07,0x00,0x53,0x04,0x07,0x00,0x52,0x04,0x07,0x00, - 0xd1,0x08,0x10,0x04,0x07,0x00,0x10,0x00,0x10,0x04,0x10,0x00,0x00,0x00,0xd4,0x0c, - 0x53,0x04,0x07,0x00,0x12,0x04,0x07,0x00,0x00,0x00,0x53,0x04,0x07,0x00,0x92,0x10, - 0xd1,0x08,0x10,0x04,0x07,0x00,0x07,0xde,0x10,0x04,0x07,0xe6,0x07,0xdc,0x00,0x00, - 0xcf,0x86,0xd5,0x18,0x94,0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x07,0x00, - 0x00,0x00,0x00,0x00,0x07,0x00,0x07,0x00,0x07,0x00,0xd4,0x10,0x53,0x04,0x07,0x00, - 0x52,0x04,0x07,0x00,0x11,0x04,0x07,0x00,0x00,0x00,0x93,0x10,0x52,0x04,0x07,0x00, - 0x91,0x08,0x10,0x04,0x07,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd0,0x1a,0xcf,0x86, - 0x55,0x04,0x08,0x00,0x94,0x10,0x53,0x04,0x08,0x00,0x92,0x08,0x11,0x04,0x08,0x00, - 0x0b,0x00,0x00,0x00,0x08,0x00,0xcf,0x86,0x95,0x28,0xd4,0x10,0x53,0x04,0x08,0x00, - 0x92,0x08,0x11,0x04,0x08,0x00,0x00,0x00,0x00,0x00,0x53,0x04,0x08,0x00,0xd2,0x0c, - 0x51,0x04,0x08,0x00,0x10,0x04,0x0b,0x00,0x00,0x00,0x11,0x04,0x00,0x00,0x08,0x00, - 0x07,0x00,0xd2,0xe4,0xd1,0x80,0xd0,0x2e,0xcf,0x86,0x95,0x28,0x54,0x04,0x08,0x00, - 0xd3,0x10,0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x08,0xe6, - 0xd2,0x0c,0x91,0x08,0x10,0x04,0x08,0xdc,0x08,0x00,0x08,0x00,0x11,0x04,0x00,0x00, - 0x08,0x00,0x0b,0x00,0xcf,0x86,0xd5,0x18,0x54,0x04,0x0b,0x00,0x53,0x04,0x0b,0x00, - 0x52,0x04,0x0b,0x00,0x51,0x04,0x0b,0x00,0x10,0x04,0x0b,0x00,0x00,0x00,0xd4,0x14, - 0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x0b,0x09,0x0b,0x00,0x0b,0x00,0x0b,0x00, - 0x0b,0x00,0xd3,0x10,0x52,0x04,0x0b,0x00,0x91,0x08,0x10,0x04,0x0b,0x00,0x0b,0xe6, - 0x0b,0xe6,0x52,0x04,0x0b,0xe6,0xd1,0x08,0x10,0x04,0x0b,0xe6,0x00,0x00,0x10,0x04, - 0x00,0x00,0x0b,0xdc,0xd0,0x5e,0xcf,0x86,0xd5,0x20,0xd4,0x10,0x53,0x04,0x0b,0x00, - 0x92,0x08,0x11,0x04,0x0b,0x00,0x00,0x00,0x00,0x00,0x53,0x04,0x0b,0x00,0x92,0x08, - 0x11,0x04,0x0b,0x00,0x00,0x00,0x00,0x00,0xd4,0x10,0x53,0x04,0x0b,0x00,0x52,0x04, - 0x0b,0x00,0x11,0x04,0x0b,0x00,0x00,0x00,0xd3,0x10,0x52,0x04,0x10,0xe6,0x91,0x08, - 0x10,0x04,0x10,0xe6,0x10,0xdc,0x10,0xdc,0xd2,0x0c,0x51,0x04,0x10,0xdc,0x10,0x04, - 0x10,0xdc,0x10,0xe6,0xd1,0x08,0x10,0x04,0x10,0xe6,0x10,0xdc,0x10,0x04,0x10,0x00, - 0x00,0x00,0xcf,0x06,0x00,0x00,0xe1,0x1e,0x01,0xd0,0xaa,0xcf,0x86,0xd5,0x6e,0xd4, - 0x53,0xd3,0x17,0x52,0x04,0x09,0x00,0x51,0x04,0x09,0x00,0x10,0x0b,0x09,0xff,0xe1, - 0xac,0x85,0xe1,0xac,0xb5,0x00,0x09,0x00,0xd2,0x1e,0xd1,0x0f,0x10,0x0b,0x09,0xff, - 0xe1,0xac,0x87,0xe1,0xac,0xb5,0x00,0x09,0x00,0x10,0x0b,0x09,0xff,0xe1,0xac,0x89, - 0xe1,0xac,0xb5,0x00,0x09,0x00,0xd1,0x0f,0x10,0x0b,0x09,0xff,0xe1,0xac,0x8b,0xe1, - 0xac,0xb5,0x00,0x09,0x00,0x10,0x0b,0x09,0xff,0xe1,0xac,0x8d,0xe1,0xac,0xb5,0x00, - 0x09,0x00,0x93,0x17,0x92,0x13,0x51,0x04,0x09,0x00,0x10,0x0b,0x09,0xff,0xe1,0xac, - 0x91,0xe1,0xac,0xb5,0x00,0x09,0x00,0x09,0x00,0x09,0x00,0x54,0x04,0x09,0x00,0xd3, - 0x10,0x52,0x04,0x09,0x00,0x91,0x08,0x10,0x04,0x09,0x07,0x09,0x00,0x09,0x00,0xd2, - 0x13,0x51,0x04,0x09,0x00,0x10,0x04,0x09,0x00,0x09,0xff,0xe1,0xac,0xba,0xe1,0xac, - 0xb5,0x00,0x91,0x0f,0x10,0x04,0x09,0x00,0x09,0xff,0xe1,0xac,0xbc,0xe1,0xac,0xb5, - 0x00,0x09,0x00,0xcf,0x86,0xd5,0x3d,0x94,0x39,0xd3,0x31,0xd2,0x25,0xd1,0x16,0x10, - 0x0b,0x09,0xff,0xe1,0xac,0xbe,0xe1,0xac,0xb5,0x00,0x09,0xff,0xe1,0xac,0xbf,0xe1, - 0xac,0xb5,0x00,0x10,0x04,0x09,0x00,0x09,0xff,0xe1,0xad,0x82,0xe1,0xac,0xb5,0x00, - 0x91,0x08,0x10,0x04,0x09,0x09,0x09,0x00,0x09,0x00,0x12,0x04,0x09,0x00,0x00,0x00, - 0x09,0x00,0xd4,0x1c,0x53,0x04,0x09,0x00,0xd2,0x0c,0x51,0x04,0x09,0x00,0x10,0x04, - 0x09,0x00,0x09,0xe6,0x91,0x08,0x10,0x04,0x09,0xdc,0x09,0xe6,0x09,0xe6,0xd3,0x08, - 0x12,0x04,0x09,0xe6,0x09,0x00,0x52,0x04,0x09,0x00,0x91,0x08,0x10,0x04,0x09,0x00, - 0x00,0x00,0x00,0x00,0xd0,0x2e,0xcf,0x86,0x55,0x04,0x0a,0x00,0xd4,0x18,0x53,0x04, - 0x0a,0x00,0xd2,0x0c,0x51,0x04,0x0a,0x00,0x10,0x04,0x0a,0x09,0x0d,0x09,0x11,0x04, - 0x0d,0x00,0x0a,0x00,0x53,0x04,0x0a,0x00,0x92,0x08,0x11,0x04,0x0a,0x00,0x0d,0x00, - 0x0d,0x00,0xcf,0x86,0x55,0x04,0x0c,0x00,0xd4,0x14,0x93,0x10,0x52,0x04,0x0c,0x00, - 0x51,0x04,0x0c,0x00,0x10,0x04,0x0c,0x07,0x0c,0x00,0x0c,0x00,0xd3,0x0c,0x92,0x08, - 0x11,0x04,0x0c,0x00,0x0c,0x09,0x00,0x00,0x12,0x04,0x00,0x00,0x0c,0x00,0xe3,0xb2, - 0x01,0xe2,0x09,0x01,0xd1,0x4c,0xd0,0x2a,0xcf,0x86,0x55,0x04,0x0a,0x00,0x54,0x04, - 0x0a,0x00,0xd3,0x10,0x52,0x04,0x0a,0x00,0x51,0x04,0x0a,0x00,0x10,0x04,0x0a,0x00, - 0x0a,0x07,0x92,0x0c,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x0a,0x00,0x0a,0x00, - 0xcf,0x86,0x95,0x1c,0x94,0x18,0x53,0x04,0x0a,0x00,0xd2,0x08,0x11,0x04,0x0a,0x00, - 0x00,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x0a,0x00,0x0a,0x00,0x0a,0x00,0x0a,0x00, - 0xd0,0x3a,0xcf,0x86,0xd5,0x18,0x94,0x14,0x53,0x04,0x12,0x00,0x92,0x0c,0x91,0x08, - 0x10,0x04,0x12,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x14,0x00,0x54,0x04,0x14,0x00, - 0x53,0x04,0x14,0x00,0xd2,0x0c,0x51,0x04,0x14,0x00,0x10,0x04,0x14,0x00,0x00,0x00, - 0x91,0x08,0x10,0x04,0x00,0x00,0x14,0x00,0x14,0x00,0xcf,0x86,0xd5,0x2c,0xd4,0x08, - 0x13,0x04,0x0d,0x00,0x00,0x00,0xd3,0x18,0xd2,0x0c,0x51,0x04,0x0b,0xe6,0x10,0x04, - 0x0b,0xe6,0x0b,0x00,0x91,0x08,0x10,0x04,0x0b,0x01,0x0b,0xdc,0x0b,0xdc,0x92,0x08, - 0x11,0x04,0x0b,0xdc,0x0b,0xe6,0x0b,0xdc,0xd4,0x28,0xd3,0x10,0x92,0x0c,0x91,0x08, - 0x10,0x04,0x0b,0xe6,0x0b,0x00,0x0b,0x01,0x0b,0x01,0xd2,0x0c,0x91,0x08,0x10,0x04, - 0x0b,0x01,0x0b,0x00,0x0b,0x00,0x91,0x08,0x10,0x04,0x0b,0x00,0x0b,0xdc,0x0b,0x00, - 0xd3,0x1c,0xd2,0x0c,0x51,0x04,0x0b,0x00,0x10,0x04,0x0b,0x00,0x0d,0x00,0xd1,0x08, - 0x10,0x04,0x0d,0xe6,0x0d,0x00,0x10,0x04,0x0d,0x00,0x13,0x00,0x92,0x0c,0x51,0x04, - 0x10,0xe6,0x10,0x04,0x15,0x00,0x00,0x00,0x00,0x00,0xd1,0x1c,0xd0,0x06,0xcf,0x06, - 0x07,0x00,0xcf,0x86,0x55,0x04,0x07,0x00,0x94,0x0c,0x53,0x04,0x07,0x00,0x12,0x04, - 0x07,0x00,0x08,0x00,0x08,0x00,0xd0,0x06,0xcf,0x06,0x08,0x00,0xcf,0x86,0xd5,0x40, - 0xd4,0x2c,0xd3,0x10,0x92,0x0c,0x51,0x04,0x08,0xe6,0x10,0x04,0x08,0xdc,0x08,0xe6, - 0x09,0xe6,0xd2,0x0c,0x51,0x04,0x09,0xe6,0x10,0x04,0x09,0xdc,0x0a,0xe6,0xd1,0x08, - 0x10,0x04,0x0a,0xe6,0x0a,0xea,0x10,0x04,0x0a,0xd6,0x0a,0xdc,0x93,0x10,0x92,0x0c, - 0x91,0x08,0x10,0x04,0x0a,0xca,0x0a,0xe6,0x0a,0xe6,0x0a,0xe6,0x0a,0xe6,0xd4,0x14, - 0x93,0x10,0x52,0x04,0x0a,0xe6,0x51,0x04,0x0a,0xe6,0x10,0x04,0x0a,0xe6,0x10,0xe6, - 0x10,0xe6,0xd3,0x10,0x52,0x04,0x10,0xe6,0x51,0x04,0x10,0xe6,0x10,0x04,0x13,0xe8, - 0x13,0xe4,0xd2,0x10,0xd1,0x08,0x10,0x04,0x13,0xe4,0x13,0xdc,0x10,0x04,0x00,0x00, - 0x12,0xe6,0xd1,0x08,0x10,0x04,0x0c,0xe9,0x0b,0xdc,0x10,0x04,0x09,0xe6,0x09,0xdc, - 0xe2,0x80,0x08,0xe1,0x48,0x04,0xe0,0x1c,0x02,0xcf,0x86,0xe5,0x11,0x01,0xd4,0x84, - 0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x41,0xcc,0xa5,0x00,0x01,0xff, - 0x61,0xcc,0xa5,0x00,0x10,0x08,0x01,0xff,0x42,0xcc,0x87,0x00,0x01,0xff,0x62,0xcc, - 0x87,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x42,0xcc,0xa3,0x00,0x01,0xff,0x62,0xcc, - 0xa3,0x00,0x10,0x08,0x01,0xff,0x42,0xcc,0xb1,0x00,0x01,0xff,0x62,0xcc,0xb1,0x00, - 0xd2,0x24,0xd1,0x14,0x10,0x0a,0x01,0xff,0x43,0xcc,0xa7,0xcc,0x81,0x00,0x01,0xff, - 0x63,0xcc,0xa7,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x44,0xcc,0x87,0x00,0x01,0xff, - 0x64,0xcc,0x87,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x44,0xcc,0xa3,0x00,0x01,0xff, - 0x64,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x44,0xcc,0xb1,0x00,0x01,0xff,0x64,0xcc, - 0xb1,0x00,0xd3,0x48,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x44,0xcc,0xa7,0x00, - 0x01,0xff,0x64,0xcc,0xa7,0x00,0x10,0x08,0x01,0xff,0x44,0xcc,0xad,0x00,0x01,0xff, - 0x64,0xcc,0xad,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x45,0xcc,0x84,0xcc,0x80,0x00, - 0x01,0xff,0x65,0xcc,0x84,0xcc,0x80,0x00,0x10,0x0a,0x01,0xff,0x45,0xcc,0x84,0xcc, - 0x81,0x00,0x01,0xff,0x65,0xcc,0x84,0xcc,0x81,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08, - 0x01,0xff,0x45,0xcc,0xad,0x00,0x01,0xff,0x65,0xcc,0xad,0x00,0x10,0x08,0x01,0xff, - 0x45,0xcc,0xb0,0x00,0x01,0xff,0x65,0xcc,0xb0,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff, - 0x45,0xcc,0xa7,0xcc,0x86,0x00,0x01,0xff,0x65,0xcc,0xa7,0xcc,0x86,0x00,0x10,0x08, - 0x01,0xff,0x46,0xcc,0x87,0x00,0x01,0xff,0x66,0xcc,0x87,0x00,0xd4,0x84,0xd3,0x40, - 0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x47,0xcc,0x84,0x00,0x01,0xff,0x67,0xcc, - 0x84,0x00,0x10,0x08,0x01,0xff,0x48,0xcc,0x87,0x00,0x01,0xff,0x68,0xcc,0x87,0x00, - 0xd1,0x10,0x10,0x08,0x01,0xff,0x48,0xcc,0xa3,0x00,0x01,0xff,0x68,0xcc,0xa3,0x00, - 0x10,0x08,0x01,0xff,0x48,0xcc,0x88,0x00,0x01,0xff,0x68,0xcc,0x88,0x00,0xd2,0x20, - 0xd1,0x10,0x10,0x08,0x01,0xff,0x48,0xcc,0xa7,0x00,0x01,0xff,0x68,0xcc,0xa7,0x00, - 0x10,0x08,0x01,0xff,0x48,0xcc,0xae,0x00,0x01,0xff,0x68,0xcc,0xae,0x00,0xd1,0x10, - 0x10,0x08,0x01,0xff,0x49,0xcc,0xb0,0x00,0x01,0xff,0x69,0xcc,0xb0,0x00,0x10,0x0a, - 0x01,0xff,0x49,0xcc,0x88,0xcc,0x81,0x00,0x01,0xff,0x69,0xcc,0x88,0xcc,0x81,0x00, - 0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x4b,0xcc,0x81,0x00,0x01,0xff, - 0x6b,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x4b,0xcc,0xa3,0x00,0x01,0xff,0x6b,0xcc, - 0xa3,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x4b,0xcc,0xb1,0x00,0x01,0xff,0x6b,0xcc, - 0xb1,0x00,0x10,0x08,0x01,0xff,0x4c,0xcc,0xa3,0x00,0x01,0xff,0x6c,0xcc,0xa3,0x00, - 0xd2,0x24,0xd1,0x14,0x10,0x0a,0x01,0xff,0x4c,0xcc,0xa3,0xcc,0x84,0x00,0x01,0xff, - 0x6c,0xcc,0xa3,0xcc,0x84,0x00,0x10,0x08,0x01,0xff,0x4c,0xcc,0xb1,0x00,0x01,0xff, - 0x6c,0xcc,0xb1,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x4c,0xcc,0xad,0x00,0x01,0xff, - 0x6c,0xcc,0xad,0x00,0x10,0x08,0x01,0xff,0x4d,0xcc,0x81,0x00,0x01,0xff,0x6d,0xcc, - 0x81,0x00,0xcf,0x86,0xe5,0x15,0x01,0xd4,0x88,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10, - 0x08,0x01,0xff,0x4d,0xcc,0x87,0x00,0x01,0xff,0x6d,0xcc,0x87,0x00,0x10,0x08,0x01, - 0xff,0x4d,0xcc,0xa3,0x00,0x01,0xff,0x6d,0xcc,0xa3,0x00,0xd1,0x10,0x10,0x08,0x01, - 0xff,0x4e,0xcc,0x87,0x00,0x01,0xff,0x6e,0xcc,0x87,0x00,0x10,0x08,0x01,0xff,0x4e, - 0xcc,0xa3,0x00,0x01,0xff,0x6e,0xcc,0xa3,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01, - 0xff,0x4e,0xcc,0xb1,0x00,0x01,0xff,0x6e,0xcc,0xb1,0x00,0x10,0x08,0x01,0xff,0x4e, - 0xcc,0xad,0x00,0x01,0xff,0x6e,0xcc,0xad,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x4f, - 0xcc,0x83,0xcc,0x81,0x00,0x01,0xff,0x6f,0xcc,0x83,0xcc,0x81,0x00,0x10,0x0a,0x01, - 0xff,0x4f,0xcc,0x83,0xcc,0x88,0x00,0x01,0xff,0x6f,0xcc,0x83,0xcc,0x88,0x00,0xd3, - 0x48,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x4f,0xcc,0x84,0xcc,0x80,0x00,0x01, - 0xff,0x6f,0xcc,0x84,0xcc,0x80,0x00,0x10,0x0a,0x01,0xff,0x4f,0xcc,0x84,0xcc,0x81, - 0x00,0x01,0xff,0x6f,0xcc,0x84,0xcc,0x81,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x50, - 0xcc,0x81,0x00,0x01,0xff,0x70,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x50,0xcc,0x87, - 0x00,0x01,0xff,0x70,0xcc,0x87,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x52, - 0xcc,0x87,0x00,0x01,0xff,0x72,0xcc,0x87,0x00,0x10,0x08,0x01,0xff,0x52,0xcc,0xa3, - 0x00,0x01,0xff,0x72,0xcc,0xa3,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x52,0xcc,0xa3, - 0xcc,0x84,0x00,0x01,0xff,0x72,0xcc,0xa3,0xcc,0x84,0x00,0x10,0x08,0x01,0xff,0x52, - 0xcc,0xb1,0x00,0x01,0xff,0x72,0xcc,0xb1,0x00,0xd4,0x8c,0xd3,0x48,0xd2,0x20,0xd1, - 0x10,0x10,0x08,0x01,0xff,0x53,0xcc,0x87,0x00,0x01,0xff,0x73,0xcc,0x87,0x00,0x10, - 0x08,0x01,0xff,0x53,0xcc,0xa3,0x00,0x01,0xff,0x73,0xcc,0xa3,0x00,0xd1,0x14,0x10, - 0x0a,0x01,0xff,0x53,0xcc,0x81,0xcc,0x87,0x00,0x01,0xff,0x73,0xcc,0x81,0xcc,0x87, - 0x00,0x10,0x0a,0x01,0xff,0x53,0xcc,0x8c,0xcc,0x87,0x00,0x01,0xff,0x73,0xcc,0x8c, - 0xcc,0x87,0x00,0xd2,0x24,0xd1,0x14,0x10,0x0a,0x01,0xff,0x53,0xcc,0xa3,0xcc,0x87, - 0x00,0x01,0xff,0x73,0xcc,0xa3,0xcc,0x87,0x00,0x10,0x08,0x01,0xff,0x54,0xcc,0x87, - 0x00,0x01,0xff,0x74,0xcc,0x87,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x54,0xcc,0xa3, - 0x00,0x01,0xff,0x74,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x54,0xcc,0xb1,0x00,0x01, - 0xff,0x74,0xcc,0xb1,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x54, - 0xcc,0xad,0x00,0x01,0xff,0x74,0xcc,0xad,0x00,0x10,0x08,0x01,0xff,0x55,0xcc,0xa4, - 0x00,0x01,0xff,0x75,0xcc,0xa4,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x55,0xcc,0xb0, - 0x00,0x01,0xff,0x75,0xcc,0xb0,0x00,0x10,0x08,0x01,0xff,0x55,0xcc,0xad,0x00,0x01, - 0xff,0x75,0xcc,0xad,0x00,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x55,0xcc,0x83, - 0xcc,0x81,0x00,0x01,0xff,0x75,0xcc,0x83,0xcc,0x81,0x00,0x10,0x0a,0x01,0xff,0x55, - 0xcc,0x84,0xcc,0x88,0x00,0x01,0xff,0x75,0xcc,0x84,0xcc,0x88,0x00,0xd1,0x10,0x10, - 0x08,0x01,0xff,0x56,0xcc,0x83,0x00,0x01,0xff,0x76,0xcc,0x83,0x00,0x10,0x08,0x01, - 0xff,0x56,0xcc,0xa3,0x00,0x01,0xff,0x76,0xcc,0xa3,0x00,0xe0,0x10,0x02,0xcf,0x86, - 0xd5,0xe1,0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x57,0xcc, - 0x80,0x00,0x01,0xff,0x77,0xcc,0x80,0x00,0x10,0x08,0x01,0xff,0x57,0xcc,0x81,0x00, - 0x01,0xff,0x77,0xcc,0x81,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x57,0xcc,0x88,0x00, - 0x01,0xff,0x77,0xcc,0x88,0x00,0x10,0x08,0x01,0xff,0x57,0xcc,0x87,0x00,0x01,0xff, - 0x77,0xcc,0x87,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x57,0xcc,0xa3,0x00, - 0x01,0xff,0x77,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x58,0xcc,0x87,0x00,0x01,0xff, - 0x78,0xcc,0x87,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x58,0xcc,0x88,0x00,0x01,0xff, - 0x78,0xcc,0x88,0x00,0x10,0x08,0x01,0xff,0x59,0xcc,0x87,0x00,0x01,0xff,0x79,0xcc, - 0x87,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x5a,0xcc,0x82,0x00, - 0x01,0xff,0x7a,0xcc,0x82,0x00,0x10,0x08,0x01,0xff,0x5a,0xcc,0xa3,0x00,0x01,0xff, - 0x7a,0xcc,0xa3,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x5a,0xcc,0xb1,0x00,0x01,0xff, - 0x7a,0xcc,0xb1,0x00,0x10,0x08,0x01,0xff,0x68,0xcc,0xb1,0x00,0x01,0xff,0x74,0xcc, - 0x88,0x00,0x92,0x1d,0xd1,0x10,0x10,0x08,0x01,0xff,0x77,0xcc,0x8a,0x00,0x01,0xff, - 0x79,0xcc,0x8a,0x00,0x10,0x04,0x01,0x00,0x02,0xff,0xc5,0xbf,0xcc,0x87,0x00,0x0a, - 0x00,0xd4,0x98,0xd3,0x48,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x41,0xcc,0xa3, - 0x00,0x01,0xff,0x61,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x41,0xcc,0x89,0x00,0x01, - 0xff,0x61,0xcc,0x89,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x41,0xcc,0x82,0xcc,0x81, - 0x00,0x01,0xff,0x61,0xcc,0x82,0xcc,0x81,0x00,0x10,0x0a,0x01,0xff,0x41,0xcc,0x82, - 0xcc,0x80,0x00,0x01,0xff,0x61,0xcc,0x82,0xcc,0x80,0x00,0xd2,0x28,0xd1,0x14,0x10, - 0x0a,0x01,0xff,0x41,0xcc,0x82,0xcc,0x89,0x00,0x01,0xff,0x61,0xcc,0x82,0xcc,0x89, - 0x00,0x10,0x0a,0x01,0xff,0x41,0xcc,0x82,0xcc,0x83,0x00,0x01,0xff,0x61,0xcc,0x82, - 0xcc,0x83,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x41,0xcc,0xa3,0xcc,0x82,0x00,0x01, - 0xff,0x61,0xcc,0xa3,0xcc,0x82,0x00,0x10,0x0a,0x01,0xff,0x41,0xcc,0x86,0xcc,0x81, - 0x00,0x01,0xff,0x61,0xcc,0x86,0xcc,0x81,0x00,0xd3,0x50,0xd2,0x28,0xd1,0x14,0x10, - 0x0a,0x01,0xff,0x41,0xcc,0x86,0xcc,0x80,0x00,0x01,0xff,0x61,0xcc,0x86,0xcc,0x80, - 0x00,0x10,0x0a,0x01,0xff,0x41,0xcc,0x86,0xcc,0x89,0x00,0x01,0xff,0x61,0xcc,0x86, - 0xcc,0x89,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x41,0xcc,0x86,0xcc,0x83,0x00,0x01, - 0xff,0x61,0xcc,0x86,0xcc,0x83,0x00,0x10,0x0a,0x01,0xff,0x41,0xcc,0xa3,0xcc,0x86, - 0x00,0x01,0xff,0x61,0xcc,0xa3,0xcc,0x86,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01, - 0xff,0x45,0xcc,0xa3,0x00,0x01,0xff,0x65,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x45, - 0xcc,0x89,0x00,0x01,0xff,0x65,0xcc,0x89,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x45, - 0xcc,0x83,0x00,0x01,0xff,0x65,0xcc,0x83,0x00,0x10,0x0a,0x01,0xff,0x45,0xcc,0x82, - 0xcc,0x81,0x00,0x01,0xff,0x65,0xcc,0x82,0xcc,0x81,0x00,0xcf,0x86,0xe5,0x31,0x01, - 0xd4,0x90,0xd3,0x50,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x45,0xcc,0x82,0xcc, - 0x80,0x00,0x01,0xff,0x65,0xcc,0x82,0xcc,0x80,0x00,0x10,0x0a,0x01,0xff,0x45,0xcc, - 0x82,0xcc,0x89,0x00,0x01,0xff,0x65,0xcc,0x82,0xcc,0x89,0x00,0xd1,0x14,0x10,0x0a, - 0x01,0xff,0x45,0xcc,0x82,0xcc,0x83,0x00,0x01,0xff,0x65,0xcc,0x82,0xcc,0x83,0x00, - 0x10,0x0a,0x01,0xff,0x45,0xcc,0xa3,0xcc,0x82,0x00,0x01,0xff,0x65,0xcc,0xa3,0xcc, - 0x82,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x49,0xcc,0x89,0x00,0x01,0xff, - 0x69,0xcc,0x89,0x00,0x10,0x08,0x01,0xff,0x49,0xcc,0xa3,0x00,0x01,0xff,0x69,0xcc, - 0xa3,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x4f,0xcc,0xa3,0x00,0x01,0xff,0x6f,0xcc, - 0xa3,0x00,0x10,0x08,0x01,0xff,0x4f,0xcc,0x89,0x00,0x01,0xff,0x6f,0xcc,0x89,0x00, - 0xd3,0x50,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x4f,0xcc,0x82,0xcc,0x81,0x00, - 0x01,0xff,0x6f,0xcc,0x82,0xcc,0x81,0x00,0x10,0x0a,0x01,0xff,0x4f,0xcc,0x82,0xcc, - 0x80,0x00,0x01,0xff,0x6f,0xcc,0x82,0xcc,0x80,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff, - 0x4f,0xcc,0x82,0xcc,0x89,0x00,0x01,0xff,0x6f,0xcc,0x82,0xcc,0x89,0x00,0x10,0x0a, - 0x01,0xff,0x4f,0xcc,0x82,0xcc,0x83,0x00,0x01,0xff,0x6f,0xcc,0x82,0xcc,0x83,0x00, - 0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x4f,0xcc,0xa3,0xcc,0x82,0x00,0x01,0xff, - 0x6f,0xcc,0xa3,0xcc,0x82,0x00,0x10,0x0a,0x01,0xff,0x4f,0xcc,0x9b,0xcc,0x81,0x00, - 0x01,0xff,0x6f,0xcc,0x9b,0xcc,0x81,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x4f,0xcc, - 0x9b,0xcc,0x80,0x00,0x01,0xff,0x6f,0xcc,0x9b,0xcc,0x80,0x00,0x10,0x0a,0x01,0xff, - 0x4f,0xcc,0x9b,0xcc,0x89,0x00,0x01,0xff,0x6f,0xcc,0x9b,0xcc,0x89,0x00,0xd4,0x98, - 0xd3,0x48,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x4f,0xcc,0x9b,0xcc,0x83,0x00, - 0x01,0xff,0x6f,0xcc,0x9b,0xcc,0x83,0x00,0x10,0x0a,0x01,0xff,0x4f,0xcc,0x9b,0xcc, - 0xa3,0x00,0x01,0xff,0x6f,0xcc,0x9b,0xcc,0xa3,0x00,0xd1,0x10,0x10,0x08,0x01,0xff, - 0x55,0xcc,0xa3,0x00,0x01,0xff,0x75,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x55,0xcc, - 0x89,0x00,0x01,0xff,0x75,0xcc,0x89,0x00,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff, - 0x55,0xcc,0x9b,0xcc,0x81,0x00,0x01,0xff,0x75,0xcc,0x9b,0xcc,0x81,0x00,0x10,0x0a, - 0x01,0xff,0x55,0xcc,0x9b,0xcc,0x80,0x00,0x01,0xff,0x75,0xcc,0x9b,0xcc,0x80,0x00, - 0xd1,0x14,0x10,0x0a,0x01,0xff,0x55,0xcc,0x9b,0xcc,0x89,0x00,0x01,0xff,0x75,0xcc, - 0x9b,0xcc,0x89,0x00,0x10,0x0a,0x01,0xff,0x55,0xcc,0x9b,0xcc,0x83,0x00,0x01,0xff, - 0x75,0xcc,0x9b,0xcc,0x83,0x00,0xd3,0x44,0xd2,0x24,0xd1,0x14,0x10,0x0a,0x01,0xff, - 0x55,0xcc,0x9b,0xcc,0xa3,0x00,0x01,0xff,0x75,0xcc,0x9b,0xcc,0xa3,0x00,0x10,0x08, - 0x01,0xff,0x59,0xcc,0x80,0x00,0x01,0xff,0x79,0xcc,0x80,0x00,0xd1,0x10,0x10,0x08, - 0x01,0xff,0x59,0xcc,0xa3,0x00,0x01,0xff,0x79,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff, - 0x59,0xcc,0x89,0x00,0x01,0xff,0x79,0xcc,0x89,0x00,0x92,0x14,0x91,0x10,0x10,0x08, - 0x01,0xff,0x59,0xcc,0x83,0x00,0x01,0xff,0x79,0xcc,0x83,0x00,0x0a,0x00,0x0a,0x00, - 0xe1,0xc0,0x04,0xe0,0x80,0x02,0xcf,0x86,0xe5,0x2d,0x01,0xd4,0xa8,0xd3,0x54,0xd2, - 0x28,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb1,0xcc,0x93,0x00,0x01,0xff,0xce,0xb1, - 0xcc,0x94,0x00,0x10,0x0b,0x01,0xff,0xce,0xb1,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff, - 0xce,0xb1,0xcc,0x94,0xcc,0x80,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0xb1,0xcc, - 0x93,0xcc,0x81,0x00,0x01,0xff,0xce,0xb1,0xcc,0x94,0xcc,0x81,0x00,0x10,0x0b,0x01, - 0xff,0xce,0xb1,0xcc,0x93,0xcd,0x82,0x00,0x01,0xff,0xce,0xb1,0xcc,0x94,0xcd,0x82, - 0x00,0xd2,0x28,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0x91,0xcc,0x93,0x00,0x01,0xff, - 0xce,0x91,0xcc,0x94,0x00,0x10,0x0b,0x01,0xff,0xce,0x91,0xcc,0x93,0xcc,0x80,0x00, - 0x01,0xff,0xce,0x91,0xcc,0x94,0xcc,0x80,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce, - 0x91,0xcc,0x93,0xcc,0x81,0x00,0x01,0xff,0xce,0x91,0xcc,0x94,0xcc,0x81,0x00,0x10, - 0x0b,0x01,0xff,0xce,0x91,0xcc,0x93,0xcd,0x82,0x00,0x01,0xff,0xce,0x91,0xcc,0x94, - 0xcd,0x82,0x00,0xd3,0x42,0xd2,0x28,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb5,0xcc, - 0x93,0x00,0x01,0xff,0xce,0xb5,0xcc,0x94,0x00,0x10,0x0b,0x01,0xff,0xce,0xb5,0xcc, - 0x93,0xcc,0x80,0x00,0x01,0xff,0xce,0xb5,0xcc,0x94,0xcc,0x80,0x00,0x91,0x16,0x10, - 0x0b,0x01,0xff,0xce,0xb5,0xcc,0x93,0xcc,0x81,0x00,0x01,0xff,0xce,0xb5,0xcc,0x94, - 0xcc,0x81,0x00,0x00,0x00,0xd2,0x28,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0x95,0xcc, - 0x93,0x00,0x01,0xff,0xce,0x95,0xcc,0x94,0x00,0x10,0x0b,0x01,0xff,0xce,0x95,0xcc, - 0x93,0xcc,0x80,0x00,0x01,0xff,0xce,0x95,0xcc,0x94,0xcc,0x80,0x00,0x91,0x16,0x10, - 0x0b,0x01,0xff,0xce,0x95,0xcc,0x93,0xcc,0x81,0x00,0x01,0xff,0xce,0x95,0xcc,0x94, - 0xcc,0x81,0x00,0x00,0x00,0xd4,0xa8,0xd3,0x54,0xd2,0x28,0xd1,0x12,0x10,0x09,0x01, - 0xff,0xce,0xb7,0xcc,0x93,0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0x00,0x10,0x0b,0x01, - 0xff,0xce,0xb7,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcc,0x80, - 0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0xb7,0xcc,0x93,0xcc,0x81,0x00,0x01,0xff, - 0xce,0xb7,0xcc,0x94,0xcc,0x81,0x00,0x10,0x0b,0x01,0xff,0xce,0xb7,0xcc,0x93,0xcd, - 0x82,0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcd,0x82,0x00,0xd2,0x28,0xd1,0x12,0x10, - 0x09,0x01,0xff,0xce,0x97,0xcc,0x93,0x00,0x01,0xff,0xce,0x97,0xcc,0x94,0x00,0x10, - 0x0b,0x01,0xff,0xce,0x97,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff,0xce,0x97,0xcc,0x94, - 0xcc,0x80,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0x97,0xcc,0x93,0xcc,0x81,0x00, - 0x01,0xff,0xce,0x97,0xcc,0x94,0xcc,0x81,0x00,0x10,0x0b,0x01,0xff,0xce,0x97,0xcc, - 0x93,0xcd,0x82,0x00,0x01,0xff,0xce,0x97,0xcc,0x94,0xcd,0x82,0x00,0xd3,0x54,0xd2, - 0x28,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb9,0xcc,0x93,0x00,0x01,0xff,0xce,0xb9, - 0xcc,0x94,0x00,0x10,0x0b,0x01,0xff,0xce,0xb9,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff, - 0xce,0xb9,0xcc,0x94,0xcc,0x80,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0xb9,0xcc, - 0x93,0xcc,0x81,0x00,0x01,0xff,0xce,0xb9,0xcc,0x94,0xcc,0x81,0x00,0x10,0x0b,0x01, - 0xff,0xce,0xb9,0xcc,0x93,0xcd,0x82,0x00,0x01,0xff,0xce,0xb9,0xcc,0x94,0xcd,0x82, - 0x00,0xd2,0x28,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0x99,0xcc,0x93,0x00,0x01,0xff, - 0xce,0x99,0xcc,0x94,0x00,0x10,0x0b,0x01,0xff,0xce,0x99,0xcc,0x93,0xcc,0x80,0x00, - 0x01,0xff,0xce,0x99,0xcc,0x94,0xcc,0x80,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce, - 0x99,0xcc,0x93,0xcc,0x81,0x00,0x01,0xff,0xce,0x99,0xcc,0x94,0xcc,0x81,0x00,0x10, - 0x0b,0x01,0xff,0xce,0x99,0xcc,0x93,0xcd,0x82,0x00,0x01,0xff,0xce,0x99,0xcc,0x94, - 0xcd,0x82,0x00,0xcf,0x86,0xe5,0x13,0x01,0xd4,0x84,0xd3,0x42,0xd2,0x28,0xd1,0x12, - 0x10,0x09,0x01,0xff,0xce,0xbf,0xcc,0x93,0x00,0x01,0xff,0xce,0xbf,0xcc,0x94,0x00, - 0x10,0x0b,0x01,0xff,0xce,0xbf,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff,0xce,0xbf,0xcc, - 0x94,0xcc,0x80,0x00,0x91,0x16,0x10,0x0b,0x01,0xff,0xce,0xbf,0xcc,0x93,0xcc,0x81, - 0x00,0x01,0xff,0xce,0xbf,0xcc,0x94,0xcc,0x81,0x00,0x00,0x00,0xd2,0x28,0xd1,0x12, - 0x10,0x09,0x01,0xff,0xce,0x9f,0xcc,0x93,0x00,0x01,0xff,0xce,0x9f,0xcc,0x94,0x00, - 0x10,0x0b,0x01,0xff,0xce,0x9f,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff,0xce,0x9f,0xcc, - 0x94,0xcc,0x80,0x00,0x91,0x16,0x10,0x0b,0x01,0xff,0xce,0x9f,0xcc,0x93,0xcc,0x81, - 0x00,0x01,0xff,0xce,0x9f,0xcc,0x94,0xcc,0x81,0x00,0x00,0x00,0xd3,0x54,0xd2,0x28, - 0xd1,0x12,0x10,0x09,0x01,0xff,0xcf,0x85,0xcc,0x93,0x00,0x01,0xff,0xcf,0x85,0xcc, - 0x94,0x00,0x10,0x0b,0x01,0xff,0xcf,0x85,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff,0xcf, - 0x85,0xcc,0x94,0xcc,0x80,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xcf,0x85,0xcc,0x93, - 0xcc,0x81,0x00,0x01,0xff,0xcf,0x85,0xcc,0x94,0xcc,0x81,0x00,0x10,0x0b,0x01,0xff, - 0xcf,0x85,0xcc,0x93,0xcd,0x82,0x00,0x01,0xff,0xcf,0x85,0xcc,0x94,0xcd,0x82,0x00, - 0xd2,0x1c,0xd1,0x0d,0x10,0x04,0x00,0x00,0x01,0xff,0xce,0xa5,0xcc,0x94,0x00,0x10, - 0x04,0x00,0x00,0x01,0xff,0xce,0xa5,0xcc,0x94,0xcc,0x80,0x00,0xd1,0x0f,0x10,0x04, - 0x00,0x00,0x01,0xff,0xce,0xa5,0xcc,0x94,0xcc,0x81,0x00,0x10,0x04,0x00,0x00,0x01, - 0xff,0xce,0xa5,0xcc,0x94,0xcd,0x82,0x00,0xd4,0xa8,0xd3,0x54,0xd2,0x28,0xd1,0x12, - 0x10,0x09,0x01,0xff,0xcf,0x89,0xcc,0x93,0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0x00, - 0x10,0x0b,0x01,0xff,0xcf,0x89,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff,0xcf,0x89,0xcc, - 0x94,0xcc,0x80,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xcf,0x89,0xcc,0x93,0xcc,0x81, - 0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xcc,0x81,0x00,0x10,0x0b,0x01,0xff,0xcf,0x89, - 0xcc,0x93,0xcd,0x82,0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xcd,0x82,0x00,0xd2,0x28, - 0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xa9,0xcc,0x93,0x00,0x01,0xff,0xce,0xa9,0xcc, - 0x94,0x00,0x10,0x0b,0x01,0xff,0xce,0xa9,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff,0xce, - 0xa9,0xcc,0x94,0xcc,0x80,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0xa9,0xcc,0x93, - 0xcc,0x81,0x00,0x01,0xff,0xce,0xa9,0xcc,0x94,0xcc,0x81,0x00,0x10,0x0b,0x01,0xff, - 0xce,0xa9,0xcc,0x93,0xcd,0x82,0x00,0x01,0xff,0xce,0xa9,0xcc,0x94,0xcd,0x82,0x00, - 0xd3,0x48,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb1,0xcc,0x80,0x00,0x01, - 0xff,0xce,0xb1,0xcc,0x81,0x00,0x10,0x09,0x01,0xff,0xce,0xb5,0xcc,0x80,0x00,0x01, - 0xff,0xce,0xb5,0xcc,0x81,0x00,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb7,0xcc,0x80, - 0x00,0x01,0xff,0xce,0xb7,0xcc,0x81,0x00,0x10,0x09,0x01,0xff,0xce,0xb9,0xcc,0x80, - 0x00,0x01,0xff,0xce,0xb9,0xcc,0x81,0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff, - 0xce,0xbf,0xcc,0x80,0x00,0x01,0xff,0xce,0xbf,0xcc,0x81,0x00,0x10,0x09,0x01,0xff, - 0xcf,0x85,0xcc,0x80,0x00,0x01,0xff,0xcf,0x85,0xcc,0x81,0x00,0x91,0x12,0x10,0x09, - 0x01,0xff,0xcf,0x89,0xcc,0x80,0x00,0x01,0xff,0xcf,0x89,0xcc,0x81,0x00,0x00,0x00, - 0xe0,0xe1,0x02,0xcf,0x86,0xe5,0x91,0x01,0xd4,0xc8,0xd3,0x64,0xd2,0x30,0xd1,0x16, - 0x10,0x0b,0x01,0xff,0xce,0xb1,0xcc,0x93,0xcd,0x85,0x00,0x01,0xff,0xce,0xb1,0xcc, - 0x94,0xcd,0x85,0x00,0x10,0x0d,0x01,0xff,0xce,0xb1,0xcc,0x93,0xcc,0x80,0xcd,0x85, - 0x00,0x01,0xff,0xce,0xb1,0xcc,0x94,0xcc,0x80,0xcd,0x85,0x00,0xd1,0x1a,0x10,0x0d, - 0x01,0xff,0xce,0xb1,0xcc,0x93,0xcc,0x81,0xcd,0x85,0x00,0x01,0xff,0xce,0xb1,0xcc, - 0x94,0xcc,0x81,0xcd,0x85,0x00,0x10,0x0d,0x01,0xff,0xce,0xb1,0xcc,0x93,0xcd,0x82, - 0xcd,0x85,0x00,0x01,0xff,0xce,0xb1,0xcc,0x94,0xcd,0x82,0xcd,0x85,0x00,0xd2,0x30, - 0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0x91,0xcc,0x93,0xcd,0x85,0x00,0x01,0xff,0xce, - 0x91,0xcc,0x94,0xcd,0x85,0x00,0x10,0x0d,0x01,0xff,0xce,0x91,0xcc,0x93,0xcc,0x80, - 0xcd,0x85,0x00,0x01,0xff,0xce,0x91,0xcc,0x94,0xcc,0x80,0xcd,0x85,0x00,0xd1,0x1a, - 0x10,0x0d,0x01,0xff,0xce,0x91,0xcc,0x93,0xcc,0x81,0xcd,0x85,0x00,0x01,0xff,0xce, - 0x91,0xcc,0x94,0xcc,0x81,0xcd,0x85,0x00,0x10,0x0d,0x01,0xff,0xce,0x91,0xcc,0x93, - 0xcd,0x82,0xcd,0x85,0x00,0x01,0xff,0xce,0x91,0xcc,0x94,0xcd,0x82,0xcd,0x85,0x00, - 0xd3,0x64,0xd2,0x30,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0xb7,0xcc,0x93,0xcd,0x85, - 0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcd,0x85,0x00,0x10,0x0d,0x01,0xff,0xce,0xb7, - 0xcc,0x93,0xcc,0x80,0xcd,0x85,0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcc,0x80,0xcd, - 0x85,0x00,0xd1,0x1a,0x10,0x0d,0x01,0xff,0xce,0xb7,0xcc,0x93,0xcc,0x81,0xcd,0x85, - 0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcc,0x81,0xcd,0x85,0x00,0x10,0x0d,0x01,0xff, - 0xce,0xb7,0xcc,0x93,0xcd,0x82,0xcd,0x85,0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcd, - 0x82,0xcd,0x85,0x00,0xd2,0x30,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0x97,0xcc,0x93, - 0xcd,0x85,0x00,0x01,0xff,0xce,0x97,0xcc,0x94,0xcd,0x85,0x00,0x10,0x0d,0x01,0xff, - 0xce,0x97,0xcc,0x93,0xcc,0x80,0xcd,0x85,0x00,0x01,0xff,0xce,0x97,0xcc,0x94,0xcc, - 0x80,0xcd,0x85,0x00,0xd1,0x1a,0x10,0x0d,0x01,0xff,0xce,0x97,0xcc,0x93,0xcc,0x81, - 0xcd,0x85,0x00,0x01,0xff,0xce,0x97,0xcc,0x94,0xcc,0x81,0xcd,0x85,0x00,0x10,0x0d, - 0x01,0xff,0xce,0x97,0xcc,0x93,0xcd,0x82,0xcd,0x85,0x00,0x01,0xff,0xce,0x97,0xcc, - 0x94,0xcd,0x82,0xcd,0x85,0x00,0xd4,0xc8,0xd3,0x64,0xd2,0x30,0xd1,0x16,0x10,0x0b, - 0x01,0xff,0xcf,0x89,0xcc,0x93,0xcd,0x85,0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xcd, - 0x85,0x00,0x10,0x0d,0x01,0xff,0xcf,0x89,0xcc,0x93,0xcc,0x80,0xcd,0x85,0x00,0x01, - 0xff,0xcf,0x89,0xcc,0x94,0xcc,0x80,0xcd,0x85,0x00,0xd1,0x1a,0x10,0x0d,0x01,0xff, - 0xcf,0x89,0xcc,0x93,0xcc,0x81,0xcd,0x85,0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xcc, - 0x81,0xcd,0x85,0x00,0x10,0x0d,0x01,0xff,0xcf,0x89,0xcc,0x93,0xcd,0x82,0xcd,0x85, - 0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xcd,0x82,0xcd,0x85,0x00,0xd2,0x30,0xd1,0x16, - 0x10,0x0b,0x01,0xff,0xce,0xa9,0xcc,0x93,0xcd,0x85,0x00,0x01,0xff,0xce,0xa9,0xcc, - 0x94,0xcd,0x85,0x00,0x10,0x0d,0x01,0xff,0xce,0xa9,0xcc,0x93,0xcc,0x80,0xcd,0x85, - 0x00,0x01,0xff,0xce,0xa9,0xcc,0x94,0xcc,0x80,0xcd,0x85,0x00,0xd1,0x1a,0x10,0x0d, - 0x01,0xff,0xce,0xa9,0xcc,0x93,0xcc,0x81,0xcd,0x85,0x00,0x01,0xff,0xce,0xa9,0xcc, - 0x94,0xcc,0x81,0xcd,0x85,0x00,0x10,0x0d,0x01,0xff,0xce,0xa9,0xcc,0x93,0xcd,0x82, - 0xcd,0x85,0x00,0x01,0xff,0xce,0xa9,0xcc,0x94,0xcd,0x82,0xcd,0x85,0x00,0xd3,0x49, - 0xd2,0x26,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb1,0xcc,0x86,0x00,0x01,0xff,0xce, - 0xb1,0xcc,0x84,0x00,0x10,0x0b,0x01,0xff,0xce,0xb1,0xcc,0x80,0xcd,0x85,0x00,0x01, - 0xff,0xce,0xb1,0xcd,0x85,0x00,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xce,0xb1,0xcc,0x81, - 0xcd,0x85,0x00,0x00,0x00,0x10,0x09,0x01,0xff,0xce,0xb1,0xcd,0x82,0x00,0x01,0xff, - 0xce,0xb1,0xcd,0x82,0xcd,0x85,0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff,0xce, - 0x91,0xcc,0x86,0x00,0x01,0xff,0xce,0x91,0xcc,0x84,0x00,0x10,0x09,0x01,0xff,0xce, - 0x91,0xcc,0x80,0x00,0x01,0xff,0xce,0x91,0xcc,0x81,0x00,0xd1,0x0d,0x10,0x09,0x01, - 0xff,0xce,0x91,0xcd,0x85,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xce,0xb9,0x00,0x01, - 0x00,0xcf,0x86,0xe5,0x16,0x01,0xd4,0x8f,0xd3,0x44,0xd2,0x21,0xd1,0x0d,0x10,0x04, - 0x01,0x00,0x01,0xff,0xc2,0xa8,0xcd,0x82,0x00,0x10,0x0b,0x01,0xff,0xce,0xb7,0xcc, - 0x80,0xcd,0x85,0x00,0x01,0xff,0xce,0xb7,0xcd,0x85,0x00,0xd1,0x0f,0x10,0x0b,0x01, - 0xff,0xce,0xb7,0xcc,0x81,0xcd,0x85,0x00,0x00,0x00,0x10,0x09,0x01,0xff,0xce,0xb7, - 0xcd,0x82,0x00,0x01,0xff,0xce,0xb7,0xcd,0x82,0xcd,0x85,0x00,0xd2,0x24,0xd1,0x12, - 0x10,0x09,0x01,0xff,0xce,0x95,0xcc,0x80,0x00,0x01,0xff,0xce,0x95,0xcc,0x81,0x00, - 0x10,0x09,0x01,0xff,0xce,0x97,0xcc,0x80,0x00,0x01,0xff,0xce,0x97,0xcc,0x81,0x00, - 0xd1,0x13,0x10,0x09,0x01,0xff,0xce,0x97,0xcd,0x85,0x00,0x01,0xff,0xe1,0xbe,0xbf, - 0xcc,0x80,0x00,0x10,0x0a,0x01,0xff,0xe1,0xbe,0xbf,0xcc,0x81,0x00,0x01,0xff,0xe1, - 0xbe,0xbf,0xcd,0x82,0x00,0xd3,0x40,0xd2,0x28,0xd1,0x12,0x10,0x09,0x01,0xff,0xce, - 0xb9,0xcc,0x86,0x00,0x01,0xff,0xce,0xb9,0xcc,0x84,0x00,0x10,0x0b,0x01,0xff,0xce, - 0xb9,0xcc,0x88,0xcc,0x80,0x00,0x01,0xff,0xce,0xb9,0xcc,0x88,0xcc,0x81,0x00,0x51, - 0x04,0x00,0x00,0x10,0x09,0x01,0xff,0xce,0xb9,0xcd,0x82,0x00,0x01,0xff,0xce,0xb9, - 0xcc,0x88,0xcd,0x82,0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0x99,0xcc, - 0x86,0x00,0x01,0xff,0xce,0x99,0xcc,0x84,0x00,0x10,0x09,0x01,0xff,0xce,0x99,0xcc, - 0x80,0x00,0x01,0xff,0xce,0x99,0xcc,0x81,0x00,0xd1,0x0e,0x10,0x04,0x00,0x00,0x01, - 0xff,0xe1,0xbf,0xbe,0xcc,0x80,0x00,0x10,0x0a,0x01,0xff,0xe1,0xbf,0xbe,0xcc,0x81, - 0x00,0x01,0xff,0xe1,0xbf,0xbe,0xcd,0x82,0x00,0xd4,0x93,0xd3,0x4e,0xd2,0x28,0xd1, - 0x12,0x10,0x09,0x01,0xff,0xcf,0x85,0xcc,0x86,0x00,0x01,0xff,0xcf,0x85,0xcc,0x84, - 0x00,0x10,0x0b,0x01,0xff,0xcf,0x85,0xcc,0x88,0xcc,0x80,0x00,0x01,0xff,0xcf,0x85, - 0xcc,0x88,0xcc,0x81,0x00,0xd1,0x12,0x10,0x09,0x01,0xff,0xcf,0x81,0xcc,0x93,0x00, - 0x01,0xff,0xcf,0x81,0xcc,0x94,0x00,0x10,0x09,0x01,0xff,0xcf,0x85,0xcd,0x82,0x00, - 0x01,0xff,0xcf,0x85,0xcc,0x88,0xcd,0x82,0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01, - 0xff,0xce,0xa5,0xcc,0x86,0x00,0x01,0xff,0xce,0xa5,0xcc,0x84,0x00,0x10,0x09,0x01, - 0xff,0xce,0xa5,0xcc,0x80,0x00,0x01,0xff,0xce,0xa5,0xcc,0x81,0x00,0xd1,0x12,0x10, - 0x09,0x01,0xff,0xce,0xa1,0xcc,0x94,0x00,0x01,0xff,0xc2,0xa8,0xcc,0x80,0x00,0x10, - 0x09,0x01,0xff,0xc2,0xa8,0xcc,0x81,0x00,0x01,0xff,0x60,0x00,0xd3,0x3b,0xd2,0x18, - 0x51,0x04,0x00,0x00,0x10,0x0b,0x01,0xff,0xcf,0x89,0xcc,0x80,0xcd,0x85,0x00,0x01, - 0xff,0xcf,0x89,0xcd,0x85,0x00,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xcf,0x89,0xcc,0x81, - 0xcd,0x85,0x00,0x00,0x00,0x10,0x09,0x01,0xff,0xcf,0x89,0xcd,0x82,0x00,0x01,0xff, - 0xcf,0x89,0xcd,0x82,0xcd,0x85,0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff,0xce, - 0x9f,0xcc,0x80,0x00,0x01,0xff,0xce,0x9f,0xcc,0x81,0x00,0x10,0x09,0x01,0xff,0xce, - 0xa9,0xcc,0x80,0x00,0x01,0xff,0xce,0xa9,0xcc,0x81,0x00,0xd1,0x10,0x10,0x09,0x01, - 0xff,0xce,0xa9,0xcd,0x85,0x00,0x01,0xff,0xc2,0xb4,0x00,0x10,0x04,0x01,0x00,0x00, - 0x00,0xe0,0x7e,0x0c,0xcf,0x86,0xe5,0xbb,0x08,0xe4,0x14,0x06,0xe3,0xf7,0x02,0xe2, - 0xbd,0x01,0xd1,0xd0,0xd0,0x4f,0xcf,0x86,0xd5,0x2e,0x94,0x2a,0xd3,0x18,0x92,0x14, - 0x91,0x10,0x10,0x08,0x01,0xff,0xe2,0x80,0x82,0x00,0x01,0xff,0xe2,0x80,0x83,0x00, - 0x01,0x00,0x01,0x00,0x92,0x0d,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x01,0xff, - 0x00,0x01,0xff,0x00,0x01,0x00,0x94,0x1b,0x53,0x04,0x01,0x00,0xd2,0x09,0x11,0x04, - 0x01,0x00,0x01,0xff,0x00,0x51,0x05,0x01,0xff,0x00,0x10,0x05,0x01,0xff,0x00,0x04, - 0x00,0x01,0x00,0xcf,0x86,0xd5,0x48,0xd4,0x1c,0xd3,0x10,0x52,0x04,0x01,0x00,0x51, - 0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x06,0x00,0x52,0x04,0x04,0x00,0x11,0x04,0x04, - 0x00,0x06,0x00,0xd3,0x1c,0xd2,0x0c,0x51,0x04,0x06,0x00,0x10,0x04,0x06,0x00,0x07, - 0x00,0xd1,0x08,0x10,0x04,0x07,0x00,0x08,0x00,0x10,0x04,0x08,0x00,0x06,0x00,0x52, - 0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x06,0x00,0xd4,0x23,0xd3, - 0x14,0x52,0x05,0x06,0xff,0x00,0x91,0x0a,0x10,0x05,0x0a,0xff,0x00,0x00,0xff,0x00, - 0x0f,0xff,0x00,0x92,0x0a,0x11,0x05,0x0f,0xff,0x00,0x01,0xff,0x00,0x01,0xff,0x00, - 0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x01,0x00,0x06,0x00,0x00,0x00,0x01,0x00, - 0x01,0x00,0xd0,0x7e,0xcf,0x86,0xd5,0x34,0xd4,0x14,0x53,0x04,0x01,0x00,0x52,0x04, - 0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x00,0x00,0xd3,0x10,0x52,0x04, - 0x08,0x00,0x91,0x08,0x10,0x04,0x08,0x00,0x0c,0x00,0x0c,0x00,0x52,0x04,0x0c,0x00, - 0x91,0x08,0x10,0x04,0x0c,0x00,0x00,0x00,0x00,0x00,0xd4,0x1c,0x53,0x04,0x01,0x00, - 0xd2,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x02,0x00,0x91,0x08,0x10,0x04, - 0x03,0x00,0x04,0x00,0x04,0x00,0xd3,0x10,0xd2,0x08,0x11,0x04,0x06,0x00,0x08,0x00, - 0x11,0x04,0x08,0x00,0x0b,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04,0x0b,0x00,0x0c,0x00, - 0x10,0x04,0x0e,0x00,0x10,0x00,0x51,0x04,0x10,0x00,0x10,0x04,0x11,0x00,0x13,0x00, - 0xcf,0x86,0xd5,0x28,0x54,0x04,0x00,0x00,0xd3,0x0c,0x92,0x08,0x11,0x04,0x01,0xe6, - 0x01,0x01,0x01,0xe6,0xd2,0x0c,0x51,0x04,0x01,0x01,0x10,0x04,0x01,0x01,0x01,0xe6, - 0x91,0x08,0x10,0x04,0x01,0xe6,0x01,0x00,0x01,0x00,0xd4,0x30,0xd3,0x1c,0xd2,0x0c, - 0x91,0x08,0x10,0x04,0x01,0x00,0x01,0xe6,0x04,0x00,0xd1,0x08,0x10,0x04,0x06,0x00, - 0x06,0x01,0x10,0x04,0x06,0x01,0x06,0xe6,0x92,0x10,0xd1,0x08,0x10,0x04,0x06,0xdc, - 0x06,0xe6,0x10,0x04,0x06,0x01,0x08,0x01,0x09,0xdc,0x93,0x10,0x92,0x0c,0x91,0x08, - 0x10,0x04,0x0a,0xe6,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd1,0x81,0xd0,0x4f, - 0xcf,0x86,0x55,0x04,0x01,0x00,0xd4,0x29,0xd3,0x13,0x52,0x04,0x01,0x00,0x51,0x04, - 0x01,0x00,0x10,0x07,0x01,0xff,0xce,0xa9,0x00,0x01,0x00,0x92,0x12,0x51,0x04,0x01, - 0x00,0x10,0x06,0x01,0xff,0x4b,0x00,0x01,0xff,0x41,0xcc,0x8a,0x00,0x01,0x00,0x53, - 0x04,0x01,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04,0x01,0x00,0x04,0x00,0x10,0x04,0x04, - 0x00,0x07,0x00,0x91,0x08,0x10,0x04,0x08,0x00,0x06,0x00,0x06,0x00,0xcf,0x86,0x95, - 0x2c,0xd4,0x18,0x53,0x04,0x06,0x00,0x52,0x04,0x06,0x00,0xd1,0x08,0x10,0x04,0x08, - 0x00,0x09,0x00,0x10,0x04,0x09,0x00,0x0a,0x00,0x93,0x10,0x92,0x0c,0x51,0x04,0x0b, - 0x00,0x10,0x04,0x0b,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd0,0x68,0xcf, - 0x86,0xd5,0x48,0xd4,0x28,0xd3,0x18,0xd2,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01, - 0x00,0x04,0x00,0x91,0x08,0x10,0x04,0x09,0x00,0x0a,0x00,0x0a,0x00,0x92,0x0c,0x91, - 0x08,0x10,0x04,0x0a,0x00,0x0b,0x00,0x11,0x00,0x00,0x00,0x53,0x04,0x01,0x00,0x92, - 0x18,0x51,0x04,0x01,0x00,0x10,0x0a,0x01,0xff,0xe2,0x86,0x90,0xcc,0xb8,0x00,0x01, - 0xff,0xe2,0x86,0x92,0xcc,0xb8,0x00,0x01,0x00,0x94,0x1a,0x53,0x04,0x01,0x00,0x52, - 0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x0a,0x01,0xff,0xe2,0x86,0x94,0xcc,0xb8, - 0x00,0x01,0x00,0x01,0x00,0xcf,0x86,0xd5,0x2e,0x94,0x2a,0x53,0x04,0x01,0x00,0x52, - 0x04,0x01,0x00,0xd1,0x0e,0x10,0x04,0x01,0x00,0x01,0xff,0xe2,0x87,0x90,0xcc,0xb8, - 0x00,0x10,0x0a,0x01,0xff,0xe2,0x87,0x94,0xcc,0xb8,0x00,0x01,0xff,0xe2,0x87,0x92, - 0xcc,0xb8,0x00,0x01,0x00,0xd4,0x14,0x53,0x04,0x01,0x00,0x92,0x0c,0x51,0x04,0x01, - 0x00,0x10,0x04,0x01,0x00,0x04,0x00,0x04,0x00,0x93,0x08,0x12,0x04,0x04,0x00,0x06, - 0x00,0x06,0x00,0xe2,0x38,0x02,0xe1,0x3f,0x01,0xd0,0x68,0xcf,0x86,0xd5,0x3e,0x94, - 0x3a,0xd3,0x16,0x52,0x04,0x01,0x00,0x91,0x0e,0x10,0x0a,0x01,0xff,0xe2,0x88,0x83, - 0xcc,0xb8,0x00,0x01,0x00,0x01,0x00,0xd2,0x12,0x91,0x0e,0x10,0x04,0x01,0x00,0x01, - 0xff,0xe2,0x88,0x88,0xcc,0xb8,0x00,0x01,0x00,0x91,0x0e,0x10,0x0a,0x01,0xff,0xe2, - 0x88,0x8b,0xcc,0xb8,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x94,0x24,0x93,0x20,0x52, - 0x04,0x01,0x00,0xd1,0x0e,0x10,0x0a,0x01,0xff,0xe2,0x88,0xa3,0xcc,0xb8,0x00,0x01, - 0x00,0x10,0x0a,0x01,0xff,0xe2,0x88,0xa5,0xcc,0xb8,0x00,0x01,0x00,0x01,0x00,0x01, - 0x00,0xcf,0x86,0xd5,0x48,0x94,0x44,0xd3,0x2e,0xd2,0x12,0x91,0x0e,0x10,0x04,0x01, - 0x00,0x01,0xff,0xe2,0x88,0xbc,0xcc,0xb8,0x00,0x01,0x00,0xd1,0x0e,0x10,0x0a,0x01, - 0xff,0xe2,0x89,0x83,0xcc,0xb8,0x00,0x01,0x00,0x10,0x04,0x01,0x00,0x01,0xff,0xe2, - 0x89,0x85,0xcc,0xb8,0x00,0x92,0x12,0x91,0x0e,0x10,0x04,0x01,0x00,0x01,0xff,0xe2, - 0x89,0x88,0xcc,0xb8,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd4,0x40,0xd3,0x1e,0x92, - 0x1a,0xd1,0x0c,0x10,0x08,0x01,0xff,0x3d,0xcc,0xb8,0x00,0x01,0x00,0x10,0x0a,0x01, - 0xff,0xe2,0x89,0xa1,0xcc,0xb8,0x00,0x01,0x00,0x01,0x00,0x52,0x04,0x01,0x00,0xd1, - 0x0e,0x10,0x04,0x01,0x00,0x01,0xff,0xe2,0x89,0x8d,0xcc,0xb8,0x00,0x10,0x08,0x01, - 0xff,0x3c,0xcc,0xb8,0x00,0x01,0xff,0x3e,0xcc,0xb8,0x00,0xd3,0x30,0xd2,0x18,0x91, - 0x14,0x10,0x0a,0x01,0xff,0xe2,0x89,0xa4,0xcc,0xb8,0x00,0x01,0xff,0xe2,0x89,0xa5, - 0xcc,0xb8,0x00,0x01,0x00,0x91,0x14,0x10,0x0a,0x01,0xff,0xe2,0x89,0xb2,0xcc,0xb8, - 0x00,0x01,0xff,0xe2,0x89,0xb3,0xcc,0xb8,0x00,0x01,0x00,0x92,0x18,0x91,0x14,0x10, - 0x0a,0x01,0xff,0xe2,0x89,0xb6,0xcc,0xb8,0x00,0x01,0xff,0xe2,0x89,0xb7,0xcc,0xb8, - 0x00,0x01,0x00,0x01,0x00,0xd0,0x86,0xcf,0x86,0xd5,0x50,0x94,0x4c,0xd3,0x30,0xd2, - 0x18,0x91,0x14,0x10,0x0a,0x01,0xff,0xe2,0x89,0xba,0xcc,0xb8,0x00,0x01,0xff,0xe2, - 0x89,0xbb,0xcc,0xb8,0x00,0x01,0x00,0x91,0x14,0x10,0x0a,0x01,0xff,0xe2,0x8a,0x82, - 0xcc,0xb8,0x00,0x01,0xff,0xe2,0x8a,0x83,0xcc,0xb8,0x00,0x01,0x00,0x92,0x18,0x91, - 0x14,0x10,0x0a,0x01,0xff,0xe2,0x8a,0x86,0xcc,0xb8,0x00,0x01,0xff,0xe2,0x8a,0x87, - 0xcc,0xb8,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x94,0x30,0x53,0x04,0x01,0x00,0x52, - 0x04,0x01,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0xe2,0x8a,0xa2,0xcc,0xb8,0x00,0x01, - 0xff,0xe2,0x8a,0xa8,0xcc,0xb8,0x00,0x10,0x0a,0x01,0xff,0xe2,0x8a,0xa9,0xcc,0xb8, - 0x00,0x01,0xff,0xe2,0x8a,0xab,0xcc,0xb8,0x00,0x01,0x00,0xcf,0x86,0x55,0x04,0x01, - 0x00,0xd4,0x5c,0xd3,0x2c,0x92,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0xe2,0x89,0xbc, - 0xcc,0xb8,0x00,0x01,0xff,0xe2,0x89,0xbd,0xcc,0xb8,0x00,0x10,0x0a,0x01,0xff,0xe2, - 0x8a,0x91,0xcc,0xb8,0x00,0x01,0xff,0xe2,0x8a,0x92,0xcc,0xb8,0x00,0x01,0x00,0xd2, - 0x18,0x51,0x04,0x01,0x00,0x10,0x0a,0x01,0xff,0xe2,0x8a,0xb2,0xcc,0xb8,0x00,0x01, - 0xff,0xe2,0x8a,0xb3,0xcc,0xb8,0x00,0x91,0x14,0x10,0x0a,0x01,0xff,0xe2,0x8a,0xb4, - 0xcc,0xb8,0x00,0x01,0xff,0xe2,0x8a,0xb5,0xcc,0xb8,0x00,0x01,0x00,0x93,0x0c,0x92, - 0x08,0x11,0x04,0x01,0x00,0x06,0x00,0x06,0x00,0x06,0x00,0xd1,0x64,0xd0,0x3e,0xcf, - 0x86,0xd5,0x18,0x94,0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x01,0x00,0x04, - 0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x94,0x20,0x53,0x04,0x01,0x00,0x92, - 0x18,0xd1,0x0c,0x10,0x04,0x01,0x00,0x01,0xff,0xe3,0x80,0x88,0x00,0x10,0x08,0x01, - 0xff,0xe3,0x80,0x89,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xcf,0x86,0x55,0x04,0x01, - 0x00,0x54,0x04,0x01,0x00,0x53,0x04,0x01,0x00,0xd2,0x0c,0x51,0x04,0x01,0x00,0x10, - 0x04,0x01,0x00,0x04,0x00,0x91,0x08,0x10,0x04,0x06,0x00,0x04,0x00,0x04,0x00,0xd0, - 0x1e,0xcf,0x86,0x95,0x18,0x54,0x04,0x04,0x00,0x53,0x04,0x04,0x00,0x92,0x0c,0x51, - 0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x06,0x00,0x06,0x00,0x06,0x00,0xcf,0x86,0xd5, - 0x2c,0xd4,0x14,0x53,0x04,0x06,0x00,0x52,0x04,0x06,0x00,0x51,0x04,0x06,0x00,0x10, - 0x04,0x06,0x00,0x07,0x00,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x07,0x00,0x08, - 0x00,0x08,0x00,0x08,0x00,0x12,0x04,0x08,0x00,0x09,0x00,0xd4,0x14,0x53,0x04,0x09, - 0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x0b,0x00,0x0c,0x00,0x0c,0x00,0x0c,0x00,0xd3, - 0x08,0x12,0x04,0x0c,0x00,0x10,0x00,0xd2,0x0c,0x51,0x04,0x10,0x00,0x10,0x04,0x10, - 0x00,0x12,0x00,0x51,0x04,0x12,0x00,0x10,0x04,0x12,0x00,0x13,0x00,0xd3,0xa6,0xd2, - 0x74,0xd1,0x40,0xd0,0x22,0xcf,0x86,0x55,0x04,0x01,0x00,0x94,0x18,0x93,0x14,0x52, - 0x04,0x01,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x04,0x00,0x10,0x04,0x04,0x00,0x00, - 0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0x95,0x18,0x94,0x14,0x53,0x04,0x01,0x00,0x92, - 0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x01, - 0x00,0xd0,0x06,0xcf,0x06,0x01,0x00,0xcf,0x86,0x55,0x04,0x01,0x00,0xd4,0x14,0x53, - 0x04,0x01,0x00,0x92,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x06,0x00,0x06, - 0x00,0x53,0x04,0x06,0x00,0x52,0x04,0x06,0x00,0x51,0x04,0x06,0x00,0x10,0x04,0x06, - 0x00,0x07,0x00,0xd1,0x06,0xcf,0x06,0x01,0x00,0xd0,0x1a,0xcf,0x86,0x95,0x14,0x54, - 0x04,0x01,0x00,0x93,0x0c,0x52,0x04,0x01,0x00,0x11,0x04,0x01,0x00,0x06,0x00,0x06, - 0x00,0x01,0x00,0xcf,0x86,0x55,0x04,0x01,0x00,0x54,0x04,0x01,0x00,0x13,0x04,0x04, - 0x00,0x06,0x00,0xd2,0xdc,0xd1,0x48,0xd0,0x26,0xcf,0x86,0x95,0x20,0x54,0x04,0x01, - 0x00,0xd3,0x0c,0x52,0x04,0x01,0x00,0x11,0x04,0x07,0x00,0x06,0x00,0x92,0x0c,0x91, - 0x08,0x10,0x04,0x08,0x00,0x04,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xcf,0x86,0x55, - 0x04,0x01,0x00,0x54,0x04,0x01,0x00,0xd3,0x0c,0x92,0x08,0x11,0x04,0x04,0x00,0x06, - 0x00,0x06,0x00,0x52,0x04,0x06,0x00,0x11,0x04,0x06,0x00,0x08,0x00,0xd0,0x5e,0xcf, - 0x86,0xd5,0x2c,0xd4,0x10,0x53,0x04,0x06,0x00,0x92,0x08,0x11,0x04,0x06,0x00,0x07, - 0x00,0x07,0x00,0xd3,0x0c,0x92,0x08,0x11,0x04,0x07,0x00,0x08,0x00,0x08,0x00,0x52, - 0x04,0x08,0x00,0x91,0x08,0x10,0x04,0x08,0x00,0x0a,0x00,0x0b,0x00,0xd4,0x10,0x93, - 0x0c,0x92,0x08,0x11,0x04,0x07,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0xd3,0x10,0x92, - 0x0c,0x51,0x04,0x08,0x00,0x10,0x04,0x09,0x00,0x0a,0x00,0x0a,0x00,0x52,0x04,0x0a, - 0x00,0x91,0x08,0x10,0x04,0x0a,0x00,0x0b,0x00,0x0b,0x00,0xcf,0x86,0xd5,0x1c,0x94, - 0x18,0xd3,0x08,0x12,0x04,0x0a,0x00,0x0b,0x00,0x52,0x04,0x0b,0x00,0x51,0x04,0x0b, - 0x00,0x10,0x04,0x0c,0x00,0x0b,0x00,0x0b,0x00,0x94,0x14,0x93,0x10,0x92,0x0c,0x51, - 0x04,0x0b,0x00,0x10,0x04,0x0c,0x00,0x0b,0x00,0x0c,0x00,0x0b,0x00,0x0b,0x00,0xd1, - 0xa8,0xd0,0x42,0xcf,0x86,0xd5,0x28,0x94,0x24,0xd3,0x18,0xd2,0x0c,0x91,0x08,0x10, - 0x04,0x10,0x00,0x01,0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x01,0x00,0x0c,0x00,0x01, - 0x00,0x92,0x08,0x11,0x04,0x01,0x00,0x0c,0x00,0x01,0x00,0x01,0x00,0x94,0x14,0x53, - 0x04,0x01,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x0c,0x00,0x01,0x00,0x01,0x00,0x01, - 0x00,0x01,0x00,0xcf,0x86,0xd5,0x40,0xd4,0x18,0x53,0x04,0x01,0x00,0x52,0x04,0x01, - 0x00,0xd1,0x08,0x10,0x04,0x0c,0x00,0x01,0x00,0x10,0x04,0x0c,0x00,0x01,0x00,0xd3, - 0x18,0xd2,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x0c,0x00,0x51,0x04,0x0c, - 0x00,0x10,0x04,0x01,0x00,0x0b,0x00,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10, - 0x04,0x01,0x00,0x0c,0x00,0xd4,0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x0c, - 0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x06,0x00,0x93,0x0c,0x52,0x04,0x06,0x00,0x11, - 0x04,0x06,0x00,0x01,0x00,0x01,0x00,0xd0,0x3e,0xcf,0x86,0xd5,0x18,0x54,0x04,0x01, - 0x00,0x93,0x10,0x52,0x04,0x01,0x00,0x91,0x08,0x10,0x04,0x01,0x00,0x0c,0x00,0x0c, - 0x00,0x01,0x00,0x54,0x04,0x01,0x00,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x0c, - 0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10, - 0x04,0x01,0x00,0x0c,0x00,0xcf,0x86,0xd5,0x2c,0x94,0x28,0xd3,0x10,0x52,0x04,0x08, - 0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x09,0x00,0xd2,0x0c,0x51,0x04,0x09, - 0x00,0x10,0x04,0x09,0x00,0x0d,0x00,0x91,0x08,0x10,0x04,0x0a,0x00,0x0d,0x00,0x0c, - 0x00,0x06,0x00,0x94,0x0c,0x53,0x04,0x06,0x00,0x12,0x04,0x06,0x00,0x0a,0x00,0x06, - 0x00,0xe4,0x39,0x01,0xd3,0x0c,0xd2,0x06,0xcf,0x06,0x04,0x00,0xcf,0x06,0x06,0x00, - 0xd2,0x30,0xd1,0x06,0xcf,0x06,0x06,0x00,0xd0,0x06,0xcf,0x06,0x06,0x00,0xcf,0x86, - 0x95,0x1e,0x54,0x04,0x06,0x00,0x53,0x04,0x06,0x00,0x52,0x04,0x06,0x00,0x91,0x0e, - 0x10,0x0a,0x06,0xff,0xe2,0xab,0x9d,0xcc,0xb8,0x00,0x06,0x00,0x06,0x00,0x06,0x00, - 0xd1,0x80,0xd0,0x3a,0xcf,0x86,0xd5,0x28,0xd4,0x10,0x53,0x04,0x07,0x00,0x52,0x04, - 0x07,0x00,0x11,0x04,0x07,0x00,0x08,0x00,0xd3,0x08,0x12,0x04,0x08,0x00,0x09,0x00, - 0x92,0x0c,0x51,0x04,0x09,0x00,0x10,0x04,0x09,0x00,0x0a,0x00,0x0a,0x00,0x94,0x0c, - 0x93,0x08,0x12,0x04,0x09,0x00,0x0a,0x00,0x0a,0x00,0x0a,0x00,0xcf,0x86,0xd5,0x30, - 0xd4,0x14,0x53,0x04,0x0a,0x00,0x52,0x04,0x0a,0x00,0x91,0x08,0x10,0x04,0x0a,0x00, - 0x10,0x00,0x10,0x00,0xd3,0x10,0x52,0x04,0x0a,0x00,0x91,0x08,0x10,0x04,0x0a,0x00, - 0x0b,0x00,0x0b,0x00,0x92,0x08,0x11,0x04,0x0b,0x00,0x10,0x00,0x10,0x00,0x54,0x04, - 0x10,0x00,0x93,0x0c,0x52,0x04,0x10,0x00,0x11,0x04,0x00,0x00,0x10,0x00,0x10,0x00, - 0xd0,0x32,0xcf,0x86,0xd5,0x14,0x54,0x04,0x10,0x00,0x93,0x0c,0x52,0x04,0x10,0x00, - 0x11,0x04,0x10,0x00,0x00,0x00,0x10,0x00,0x54,0x04,0x10,0x00,0x53,0x04,0x10,0x00, - 0xd2,0x08,0x11,0x04,0x10,0x00,0x14,0x00,0x91,0x08,0x10,0x04,0x14,0x00,0x10,0x00, - 0x10,0x00,0xcf,0x86,0xd5,0x28,0xd4,0x14,0x53,0x04,0x10,0x00,0x92,0x0c,0x91,0x08, - 0x10,0x04,0x10,0x00,0x15,0x00,0x10,0x00,0x10,0x00,0x93,0x10,0x92,0x0c,0x51,0x04, - 0x10,0x00,0x10,0x04,0x13,0x00,0x14,0x00,0x14,0x00,0x14,0x00,0xd4,0x0c,0x53,0x04, - 0x14,0x00,0x12,0x04,0x14,0x00,0x11,0x00,0x53,0x04,0x14,0x00,0x52,0x04,0x14,0x00, - 0x51,0x04,0x14,0x00,0x10,0x04,0x14,0x00,0x15,0x00,0xe3,0xb9,0x01,0xd2,0xac,0xd1, - 0x68,0xd0,0x1e,0xcf,0x86,0x55,0x04,0x08,0x00,0x94,0x14,0x53,0x04,0x08,0x00,0x52, - 0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x00,0x00,0x08,0x00,0xcf, - 0x86,0xd5,0x18,0x54,0x04,0x08,0x00,0x53,0x04,0x08,0x00,0x52,0x04,0x08,0x00,0x51, - 0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x00,0x00,0xd4,0x14,0x53,0x04,0x09,0x00,0x52, - 0x04,0x09,0x00,0x91,0x08,0x10,0x04,0x09,0x00,0x0a,0x00,0x0a,0x00,0xd3,0x10,0x92, - 0x0c,0x91,0x08,0x10,0x04,0x0b,0x00,0x0a,0x00,0x0a,0x00,0x09,0x00,0x52,0x04,0x0a, - 0x00,0x11,0x04,0x0a,0x00,0x0b,0x00,0xd0,0x06,0xcf,0x06,0x08,0x00,0xcf,0x86,0x55, - 0x04,0x08,0x00,0xd4,0x1c,0x53,0x04,0x08,0x00,0xd2,0x0c,0x51,0x04,0x08,0x00,0x10, - 0x04,0x08,0x00,0x0b,0x00,0x51,0x04,0x0b,0x00,0x10,0x04,0x0b,0x00,0x0b,0xe6,0xd3, - 0x0c,0x92,0x08,0x11,0x04,0x0b,0xe6,0x0d,0x00,0x00,0x00,0x92,0x0c,0x91,0x08,0x10, - 0x04,0x00,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0xd1,0x6c,0xd0,0x2a,0xcf,0x86,0x55, - 0x04,0x08,0x00,0x94,0x20,0xd3,0x10,0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10, - 0x04,0x00,0x00,0x0d,0x00,0x52,0x04,0x00,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x0d, - 0x00,0x00,0x00,0x08,0x00,0xcf,0x86,0x55,0x04,0x08,0x00,0xd4,0x1c,0xd3,0x0c,0x52, - 0x04,0x08,0x00,0x11,0x04,0x08,0x00,0x0d,0x00,0x52,0x04,0x00,0x00,0x51,0x04,0x00, - 0x00,0x10,0x04,0x00,0x00,0x08,0x00,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x0c, - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x52,0x04,0x00,0x00,0x51,0x04,0x00,0x00,0x10, - 0x04,0x00,0x00,0x0c,0x09,0xd0,0x5a,0xcf,0x86,0xd5,0x18,0x54,0x04,0x08,0x00,0x93, - 0x10,0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x00,0x00,0x00, - 0x00,0xd4,0x20,0xd3,0x10,0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08, - 0x00,0x00,0x00,0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x00, - 0x00,0xd3,0x10,0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x00, - 0x00,0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x00,0x00,0xcf, - 0x86,0x95,0x40,0xd4,0x20,0xd3,0x10,0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10, - 0x04,0x08,0x00,0x00,0x00,0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08, - 0x00,0x00,0x00,0xd3,0x10,0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08, - 0x00,0x00,0x00,0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x00, - 0x00,0x0a,0xe6,0xd2,0x9c,0xd1,0x68,0xd0,0x32,0xcf,0x86,0xd5,0x14,0x54,0x04,0x08, - 0x00,0x53,0x04,0x08,0x00,0x52,0x04,0x0a,0x00,0x11,0x04,0x08,0x00,0x0a,0x00,0x54, - 0x04,0x0a,0x00,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x0a,0x00,0x0b,0x00,0x0d, - 0x00,0x0d,0x00,0x12,0x04,0x0d,0x00,0x10,0x00,0xcf,0x86,0x95,0x30,0x94,0x2c,0xd3, - 0x18,0xd2,0x0c,0x51,0x04,0x10,0x00,0x10,0x04,0x10,0x00,0x12,0x00,0x91,0x08,0x10, - 0x04,0x12,0x00,0x13,0x00,0x13,0x00,0xd2,0x08,0x11,0x04,0x13,0x00,0x14,0x00,0x51, - 0x04,0x14,0x00,0x10,0x04,0x14,0x00,0x15,0x00,0x00,0x00,0x00,0x00,0xd0,0x1e,0xcf, - 0x86,0x95,0x18,0x54,0x04,0x04,0x00,0x53,0x04,0x04,0x00,0x92,0x0c,0x51,0x04,0x04, - 0x00,0x10,0x04,0x00,0x00,0x04,0x00,0x04,0x00,0x04,0x00,0xcf,0x86,0x55,0x04,0x04, - 0x00,0x54,0x04,0x04,0x00,0x93,0x08,0x12,0x04,0x04,0x00,0x00,0x00,0x00,0x00,0xd1, - 0x06,0xcf,0x06,0x04,0x00,0xd0,0x06,0xcf,0x06,0x04,0x00,0xcf,0x86,0xd5,0x14,0x54, - 0x04,0x04,0x00,0x93,0x0c,0x52,0x04,0x04,0x00,0x11,0x04,0x04,0x00,0x00,0x00,0x00, - 0x00,0x54,0x04,0x00,0x00,0x53,0x04,0x04,0x00,0x12,0x04,0x04,0x00,0x00,0x00,0xcf, - 0x86,0xe5,0xa6,0x05,0xe4,0x9f,0x05,0xe3,0x96,0x04,0xe2,0xe4,0x03,0xe1,0xc0,0x01, - 0xd0,0x3e,0xcf,0x86,0x55,0x04,0x01,0x00,0xd4,0x1c,0x53,0x04,0x01,0x00,0xd2,0x0c, - 0x51,0x04,0x01,0x00,0x10,0x04,0x01,0xda,0x01,0xe4,0x91,0x08,0x10,0x04,0x01,0xe8, - 0x01,0xde,0x01,0xe0,0x53,0x04,0x01,0x00,0xd2,0x0c,0x51,0x04,0x04,0x00,0x10,0x04, - 0x04,0x00,0x06,0x00,0x51,0x04,0x06,0x00,0x10,0x04,0x04,0x00,0x01,0x00,0xcf,0x86, - 0xd5,0xaa,0xd4,0x32,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x01,0x00, - 0x01,0x00,0x01,0x00,0x52,0x04,0x01,0x00,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3,0x81, - 0x8b,0xe3,0x82,0x99,0x00,0x01,0x00,0x10,0x0b,0x01,0xff,0xe3,0x81,0x8d,0xe3,0x82, - 0x99,0x00,0x01,0x00,0xd3,0x3c,0xd2,0x1e,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3,0x81, - 0x8f,0xe3,0x82,0x99,0x00,0x01,0x00,0x10,0x0b,0x01,0xff,0xe3,0x81,0x91,0xe3,0x82, - 0x99,0x00,0x01,0x00,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3,0x81,0x93,0xe3,0x82,0x99, - 0x00,0x01,0x00,0x10,0x0b,0x01,0xff,0xe3,0x81,0x95,0xe3,0x82,0x99,0x00,0x01,0x00, - 0xd2,0x1e,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3,0x81,0x97,0xe3,0x82,0x99,0x00,0x01, - 0x00,0x10,0x0b,0x01,0xff,0xe3,0x81,0x99,0xe3,0x82,0x99,0x00,0x01,0x00,0xd1,0x0f, - 0x10,0x0b,0x01,0xff,0xe3,0x81,0x9b,0xe3,0x82,0x99,0x00,0x01,0x00,0x10,0x0b,0x01, - 0xff,0xe3,0x81,0x9d,0xe3,0x82,0x99,0x00,0x01,0x00,0xd4,0x53,0xd3,0x3c,0xd2,0x1e, - 0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3,0x81,0x9f,0xe3,0x82,0x99,0x00,0x01,0x00,0x10, - 0x0b,0x01,0xff,0xe3,0x81,0xa1,0xe3,0x82,0x99,0x00,0x01,0x00,0xd1,0x0f,0x10,0x04, - 0x01,0x00,0x01,0xff,0xe3,0x81,0xa4,0xe3,0x82,0x99,0x00,0x10,0x04,0x01,0x00,0x01, - 0xff,0xe3,0x81,0xa6,0xe3,0x82,0x99,0x00,0x92,0x13,0x91,0x0f,0x10,0x04,0x01,0x00, - 0x01,0xff,0xe3,0x81,0xa8,0xe3,0x82,0x99,0x00,0x01,0x00,0x01,0x00,0xd3,0x4a,0xd2, - 0x25,0xd1,0x16,0x10,0x0b,0x01,0xff,0xe3,0x81,0xaf,0xe3,0x82,0x99,0x00,0x01,0xff, - 0xe3,0x81,0xaf,0xe3,0x82,0x9a,0x00,0x10,0x04,0x01,0x00,0x01,0xff,0xe3,0x81,0xb2, - 0xe3,0x82,0x99,0x00,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3,0x81,0xb2,0xe3,0x82,0x9a, - 0x00,0x01,0x00,0x10,0x0b,0x01,0xff,0xe3,0x81,0xb5,0xe3,0x82,0x99,0x00,0x01,0xff, - 0xe3,0x81,0xb5,0xe3,0x82,0x9a,0x00,0xd2,0x1e,0xd1,0x0f,0x10,0x04,0x01,0x00,0x01, - 0xff,0xe3,0x81,0xb8,0xe3,0x82,0x99,0x00,0x10,0x0b,0x01,0xff,0xe3,0x81,0xb8,0xe3, - 0x82,0x9a,0x00,0x01,0x00,0x91,0x16,0x10,0x0b,0x01,0xff,0xe3,0x81,0xbb,0xe3,0x82, - 0x99,0x00,0x01,0xff,0xe3,0x81,0xbb,0xe3,0x82,0x9a,0x00,0x01,0x00,0xd0,0xee,0xcf, - 0x86,0xd5,0x42,0x54,0x04,0x01,0x00,0xd3,0x1b,0x52,0x04,0x01,0x00,0xd1,0x0f,0x10, - 0x0b,0x01,0xff,0xe3,0x81,0x86,0xe3,0x82,0x99,0x00,0x06,0x00,0x10,0x04,0x06,0x00, - 0x00,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04,0x00,0x00,0x01,0x08,0x10,0x04,0x01,0x08, - 0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x0b,0x01,0xff,0xe3,0x82,0x9d,0xe3,0x82,0x99, - 0x00,0x06,0x00,0xd4,0x32,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x06,0x00,0x01, - 0x00,0x01,0x00,0x01,0x00,0x52,0x04,0x01,0x00,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3, - 0x82,0xab,0xe3,0x82,0x99,0x00,0x01,0x00,0x10,0x0b,0x01,0xff,0xe3,0x82,0xad,0xe3, - 0x82,0x99,0x00,0x01,0x00,0xd3,0x3c,0xd2,0x1e,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3, - 0x82,0xaf,0xe3,0x82,0x99,0x00,0x01,0x00,0x10,0x0b,0x01,0xff,0xe3,0x82,0xb1,0xe3, - 0x82,0x99,0x00,0x01,0x00,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3,0x82,0xb3,0xe3,0x82, - 0x99,0x00,0x01,0x00,0x10,0x0b,0x01,0xff,0xe3,0x82,0xb5,0xe3,0x82,0x99,0x00,0x01, - 0x00,0xd2,0x1e,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3,0x82,0xb7,0xe3,0x82,0x99,0x00, - 0x01,0x00,0x10,0x0b,0x01,0xff,0xe3,0x82,0xb9,0xe3,0x82,0x99,0x00,0x01,0x00,0xd1, - 0x0f,0x10,0x0b,0x01,0xff,0xe3,0x82,0xbb,0xe3,0x82,0x99,0x00,0x01,0x00,0x10,0x0b, - 0x01,0xff,0xe3,0x82,0xbd,0xe3,0x82,0x99,0x00,0x01,0x00,0xcf,0x86,0xd5,0xd5,0xd4, - 0x53,0xd3,0x3c,0xd2,0x1e,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3,0x82,0xbf,0xe3,0x82, - 0x99,0x00,0x01,0x00,0x10,0x0b,0x01,0xff,0xe3,0x83,0x81,0xe3,0x82,0x99,0x00,0x01, - 0x00,0xd1,0x0f,0x10,0x04,0x01,0x00,0x01,0xff,0xe3,0x83,0x84,0xe3,0x82,0x99,0x00, - 0x10,0x04,0x01,0x00,0x01,0xff,0xe3,0x83,0x86,0xe3,0x82,0x99,0x00,0x92,0x13,0x91, - 0x0f,0x10,0x04,0x01,0x00,0x01,0xff,0xe3,0x83,0x88,0xe3,0x82,0x99,0x00,0x01,0x00, - 0x01,0x00,0xd3,0x4a,0xd2,0x25,0xd1,0x16,0x10,0x0b,0x01,0xff,0xe3,0x83,0x8f,0xe3, - 0x82,0x99,0x00,0x01,0xff,0xe3,0x83,0x8f,0xe3,0x82,0x9a,0x00,0x10,0x04,0x01,0x00, - 0x01,0xff,0xe3,0x83,0x92,0xe3,0x82,0x99,0x00,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3, - 0x83,0x92,0xe3,0x82,0x9a,0x00,0x01,0x00,0x10,0x0b,0x01,0xff,0xe3,0x83,0x95,0xe3, - 0x82,0x99,0x00,0x01,0xff,0xe3,0x83,0x95,0xe3,0x82,0x9a,0x00,0xd2,0x1e,0xd1,0x0f, - 0x10,0x04,0x01,0x00,0x01,0xff,0xe3,0x83,0x98,0xe3,0x82,0x99,0x00,0x10,0x0b,0x01, - 0xff,0xe3,0x83,0x98,0xe3,0x82,0x9a,0x00,0x01,0x00,0x91,0x16,0x10,0x0b,0x01,0xff, - 0xe3,0x83,0x9b,0xe3,0x82,0x99,0x00,0x01,0xff,0xe3,0x83,0x9b,0xe3,0x82,0x9a,0x00, - 0x01,0x00,0x54,0x04,0x01,0x00,0xd3,0x22,0x52,0x04,0x01,0x00,0xd1,0x0f,0x10,0x0b, - 0x01,0xff,0xe3,0x82,0xa6,0xe3,0x82,0x99,0x00,0x01,0x00,0x10,0x04,0x01,0x00,0x01, - 0xff,0xe3,0x83,0xaf,0xe3,0x82,0x99,0x00,0xd2,0x25,0xd1,0x16,0x10,0x0b,0x01,0xff, - 0xe3,0x83,0xb0,0xe3,0x82,0x99,0x00,0x01,0xff,0xe3,0x83,0xb1,0xe3,0x82,0x99,0x00, - 0x10,0x0b,0x01,0xff,0xe3,0x83,0xb2,0xe3,0x82,0x99,0x00,0x01,0x00,0x51,0x04,0x01, - 0x00,0x10,0x0b,0x01,0xff,0xe3,0x83,0xbd,0xe3,0x82,0x99,0x00,0x06,0x00,0xd1,0x65, - 0xd0,0x46,0xcf,0x86,0xd5,0x18,0x94,0x14,0x93,0x10,0x52,0x04,0x00,0x00,0x91,0x08, - 0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd4,0x18,0x53,0x04, - 0x01,0x00,0x52,0x04,0x01,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x0a,0x00,0x10,0x04, - 0x13,0x00,0x14,0x00,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x01,0x00, - 0x01,0x00,0x01,0x00,0x01,0x00,0xcf,0x86,0x55,0x04,0x01,0x00,0x94,0x15,0x93,0x11, - 0x52,0x04,0x01,0x00,0x91,0x09,0x10,0x05,0x01,0xff,0x00,0x01,0x00,0x01,0x00,0x01, - 0x00,0x01,0x00,0xd0,0x32,0xcf,0x86,0xd5,0x18,0x94,0x14,0x53,0x04,0x01,0x00,0x52, - 0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x54, - 0x04,0x04,0x00,0x53,0x04,0x04,0x00,0x92,0x0c,0x51,0x04,0x0c,0x00,0x10,0x04,0x0c, - 0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0xd5,0x08,0x14,0x04,0x08,0x00,0x0a,0x00,0x94, - 0x0c,0x93,0x08,0x12,0x04,0x0a,0x00,0x00,0x00,0x00,0x00,0x06,0x00,0xd2,0xa4,0xd1, - 0x5c,0xd0,0x22,0xcf,0x86,0x95,0x1c,0x54,0x04,0x01,0x00,0x53,0x04,0x01,0x00,0x52, - 0x04,0x01,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x07,0x00,0x10,0x04,0x07,0x00,0x00, - 0x00,0x01,0x00,0xcf,0x86,0xd5,0x20,0xd4,0x0c,0x93,0x08,0x12,0x04,0x01,0x00,0x0b, - 0x00,0x0b,0x00,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x07,0x00,0x06,0x00,0x06, - 0x00,0x06,0x00,0x06,0x00,0x54,0x04,0x01,0x00,0x53,0x04,0x01,0x00,0x52,0x04,0x01, - 0x00,0x51,0x04,0x07,0x00,0x10,0x04,0x08,0x00,0x01,0x00,0xd0,0x1e,0xcf,0x86,0x55, - 0x04,0x01,0x00,0x54,0x04,0x01,0x00,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x01, - 0x00,0x06,0x00,0x06,0x00,0x06,0x00,0x06,0x00,0xcf,0x86,0xd5,0x10,0x94,0x0c,0x53, - 0x04,0x01,0x00,0x12,0x04,0x01,0x00,0x07,0x00,0x01,0x00,0x54,0x04,0x01,0x00,0x53, - 0x04,0x01,0x00,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x16, - 0x00,0xd1,0x30,0xd0,0x06,0xcf,0x06,0x01,0x00,0xcf,0x86,0x55,0x04,0x01,0x00,0x54, - 0x04,0x01,0x00,0xd3,0x10,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01, - 0x00,0x07,0x00,0x92,0x0c,0x51,0x04,0x07,0x00,0x10,0x04,0x07,0x00,0x01,0x00,0x01, - 0x00,0xd0,0x06,0xcf,0x06,0x01,0x00,0xcf,0x86,0xd5,0x14,0x54,0x04,0x01,0x00,0x53, - 0x04,0x01,0x00,0x52,0x04,0x01,0x00,0x11,0x04,0x01,0x00,0x07,0x00,0x54,0x04,0x01, - 0x00,0x53,0x04,0x01,0x00,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01, - 0x00,0x07,0x00,0xcf,0x06,0x04,0x00,0xcf,0x06,0x04,0x00,0xd1,0x48,0xd0,0x40,0xcf, - 0x86,0xd5,0x06,0xcf,0x06,0x04,0x00,0xd4,0x06,0xcf,0x06,0x04,0x00,0xd3,0x2c,0xd2, - 0x06,0xcf,0x06,0x04,0x00,0xd1,0x06,0xcf,0x06,0x04,0x00,0xd0,0x1a,0xcf,0x86,0x55, - 0x04,0x04,0x00,0x54,0x04,0x04,0x00,0x93,0x0c,0x52,0x04,0x04,0x00,0x11,0x04,0x04, - 0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x07,0x00,0xcf,0x06,0x01,0x00,0xcf,0x86,0xcf, - 0x06,0x01,0x00,0xcf,0x86,0xcf,0x06,0x01,0x00,0xe2,0x71,0x05,0xd1,0x8c,0xd0,0x08, - 0xcf,0x86,0xcf,0x06,0x01,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x01,0x00,0xd4,0x06, - 0xcf,0x06,0x01,0x00,0xd3,0x06,0xcf,0x06,0x01,0x00,0xd2,0x06,0xcf,0x06,0x01,0x00, - 0xd1,0x06,0xcf,0x06,0x01,0x00,0xd0,0x22,0xcf,0x86,0x55,0x04,0x01,0x00,0xd4,0x10, - 0x93,0x0c,0x52,0x04,0x01,0x00,0x11,0x04,0x01,0x00,0x08,0x00,0x08,0x00,0x53,0x04, - 0x08,0x00,0x12,0x04,0x08,0x00,0x0a,0x00,0xcf,0x86,0xd5,0x28,0xd4,0x18,0xd3,0x08, - 0x12,0x04,0x0a,0x00,0x0b,0x00,0x52,0x04,0x0b,0x00,0x91,0x08,0x10,0x04,0x0d,0x00, - 0x11,0x00,0x11,0x00,0x93,0x0c,0x52,0x04,0x11,0x00,0x11,0x04,0x11,0x00,0x13,0x00, - 0x13,0x00,0x94,0x14,0x53,0x04,0x13,0x00,0x92,0x0c,0x51,0x04,0x13,0x00,0x10,0x04, - 0x13,0x00,0x14,0x00,0x14,0x00,0x00,0x00,0xe0,0xdb,0x04,0xcf,0x86,0xe5,0xdf,0x01, - 0xd4,0x06,0xcf,0x06,0x04,0x00,0xd3,0x74,0xd2,0x6e,0xd1,0x06,0xcf,0x06,0x04,0x00, - 0xd0,0x3e,0xcf,0x86,0xd5,0x18,0x94,0x14,0x53,0x04,0x04,0x00,0x52,0x04,0x04,0x00, - 0x91,0x08,0x10,0x04,0x04,0x00,0x00,0x00,0x00,0x00,0x04,0x00,0xd4,0x10,0x93,0x0c, - 0x92,0x08,0x11,0x04,0x04,0x00,0x06,0x00,0x04,0x00,0x04,0x00,0x93,0x10,0x52,0x04, - 0x04,0x00,0x91,0x08,0x10,0x04,0x06,0x00,0x04,0x00,0x04,0x00,0x04,0x00,0xcf,0x86, - 0x95,0x24,0x94,0x20,0x93,0x1c,0xd2,0x0c,0x91,0x08,0x10,0x04,0x04,0x00,0x06,0x00, - 0x04,0x00,0xd1,0x08,0x10,0x04,0x04,0x00,0x06,0x00,0x10,0x04,0x04,0x00,0x00,0x00, - 0x00,0x00,0x0b,0x00,0x0b,0x00,0xcf,0x06,0x0a,0x00,0xd2,0x84,0xd1,0x4c,0xd0,0x16, - 0xcf,0x86,0x55,0x04,0x0a,0x00,0x94,0x0c,0x53,0x04,0x0a,0x00,0x12,0x04,0x0a,0x00, - 0x00,0x00,0x00,0x00,0xcf,0x86,0x55,0x04,0x0a,0x00,0xd4,0x1c,0xd3,0x0c,0x92,0x08, - 0x11,0x04,0x0c,0x00,0x0a,0x00,0x0a,0x00,0x52,0x04,0x0a,0x00,0x51,0x04,0x0a,0x00, - 0x10,0x04,0x0a,0x00,0x0a,0xe6,0xd3,0x08,0x12,0x04,0x0a,0x00,0x0d,0xe6,0x52,0x04, - 0x0d,0xe6,0x11,0x04,0x0a,0xe6,0x0a,0x00,0xd0,0x1e,0xcf,0x86,0x95,0x18,0x54,0x04, - 0x0a,0x00,0x53,0x04,0x0a,0x00,0x52,0x04,0x10,0x00,0x51,0x04,0x10,0x00,0x10,0x04, - 0x11,0xe6,0x0d,0xe6,0x0b,0x00,0xcf,0x86,0x55,0x04,0x0b,0x00,0x54,0x04,0x0b,0x00, - 0x93,0x0c,0x92,0x08,0x11,0x04,0x0b,0xe6,0x0b,0x00,0x0b,0x00,0x00,0x00,0xd1,0x40, - 0xd0,0x3a,0xcf,0x86,0xd5,0x24,0x54,0x04,0x08,0x00,0xd3,0x10,0x52,0x04,0x08,0x00, - 0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x09,0x00,0x92,0x0c,0x51,0x04,0x09,0x00, - 0x10,0x04,0x09,0x00,0x0a,0x00,0x0a,0x00,0x94,0x10,0x93,0x0c,0x92,0x08,0x11,0x04, - 0x09,0x00,0x0a,0x00,0x0a,0x00,0x0a,0x00,0x0a,0x00,0xcf,0x06,0x0a,0x00,0xd0,0x5e, - 0xcf,0x86,0xd5,0x28,0xd4,0x18,0x53,0x04,0x0a,0x00,0x52,0x04,0x0a,0x00,0xd1,0x08, - 0x10,0x04,0x0a,0x00,0x0c,0x00,0x10,0x04,0x0c,0x00,0x11,0x00,0x93,0x0c,0x92,0x08, - 0x11,0x04,0x0c,0x00,0x0d,0x00,0x10,0x00,0x10,0x00,0xd4,0x1c,0x53,0x04,0x0c,0x00, - 0xd2,0x0c,0x51,0x04,0x0c,0x00,0x10,0x04,0x0d,0x00,0x10,0x00,0x51,0x04,0x10,0x00, - 0x10,0x04,0x12,0x00,0x14,0x00,0xd3,0x0c,0x92,0x08,0x11,0x04,0x10,0x00,0x11,0x00, - 0x11,0x00,0x92,0x08,0x11,0x04,0x14,0x00,0x15,0x00,0x15,0x00,0xcf,0x86,0xd5,0x1c, - 0x94,0x18,0x93,0x14,0xd2,0x08,0x11,0x04,0x00,0x00,0x15,0x00,0x51,0x04,0x15,0x00, - 0x10,0x04,0x15,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x54,0x04,0x00,0x00,0xd3,0x10, - 0x52,0x04,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x10,0x00,0x92,0x0c, - 0x51,0x04,0x0d,0x00,0x10,0x04,0x0c,0x00,0x0a,0x00,0x0a,0x00,0xe4,0xf2,0x02,0xe3, - 0x65,0x01,0xd2,0x98,0xd1,0x48,0xd0,0x36,0xcf,0x86,0xd5,0x18,0x94,0x14,0x93,0x10, - 0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x09,0x08,0x00,0x08,0x00, - 0x08,0x00,0xd4,0x0c,0x53,0x04,0x08,0x00,0x12,0x04,0x08,0x00,0x00,0x00,0x53,0x04, - 0x0b,0x00,0x92,0x08,0x11,0x04,0x0b,0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0x55,0x04, - 0x09,0x00,0x54,0x04,0x09,0x00,0x13,0x04,0x09,0x00,0x00,0x00,0xd0,0x06,0xcf,0x06, - 0x0a,0x00,0xcf,0x86,0xd5,0x2c,0xd4,0x1c,0xd3,0x10,0x52,0x04,0x0a,0x00,0x91,0x08, - 0x10,0x04,0x0a,0x09,0x12,0x00,0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00, - 0x0a,0x00,0x53,0x04,0x0a,0x00,0x92,0x08,0x11,0x04,0x0a,0x00,0x00,0x00,0x00,0x00, - 0x54,0x04,0x0b,0xe6,0xd3,0x0c,0x92,0x08,0x11,0x04,0x0b,0xe6,0x0b,0x00,0x0b,0x00, - 0x52,0x04,0x0b,0x00,0x11,0x04,0x11,0x00,0x14,0x00,0xd1,0x60,0xd0,0x22,0xcf,0x86, - 0x55,0x04,0x0a,0x00,0x94,0x18,0x53,0x04,0x0a,0x00,0xd2,0x0c,0x51,0x04,0x0a,0x00, - 0x10,0x04,0x0a,0x00,0x0a,0xdc,0x11,0x04,0x0a,0xdc,0x0a,0x00,0x0a,0x00,0xcf,0x86, - 0xd5,0x24,0x54,0x04,0x0a,0x00,0xd3,0x10,0x92,0x0c,0x51,0x04,0x0a,0x00,0x10,0x04, - 0x0a,0x00,0x0a,0x09,0x00,0x00,0x52,0x04,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04, - 0x00,0x00,0x0a,0x00,0x54,0x04,0x0b,0x00,0x53,0x04,0x0b,0x00,0x52,0x04,0x0b,0x00, - 0x91,0x08,0x10,0x04,0x0b,0x00,0x00,0x00,0x00,0x00,0xd0,0x1e,0xcf,0x86,0x55,0x04, - 0x0b,0x00,0x54,0x04,0x0b,0x00,0x93,0x10,0x92,0x0c,0x51,0x04,0x0b,0x00,0x10,0x04, - 0x0b,0x00,0x0b,0x07,0x0b,0x00,0x0b,0x00,0xcf,0x86,0xd5,0x34,0xd4,0x20,0xd3,0x10, - 0x92,0x0c,0x91,0x08,0x10,0x04,0x0b,0x09,0x0b,0x00,0x0b,0x00,0x0b,0x00,0x52,0x04, - 0x0b,0x00,0x51,0x04,0x0b,0x00,0x10,0x04,0x00,0x00,0x0b,0x00,0x53,0x04,0x0b,0x00, - 0xd2,0x08,0x11,0x04,0x0b,0x00,0x00,0x00,0x11,0x04,0x00,0x00,0x0b,0x00,0x54,0x04, - 0x10,0x00,0x53,0x04,0x10,0x00,0x52,0x04,0x10,0x00,0x51,0x04,0x10,0x00,0x10,0x04, - 0x10,0x00,0x00,0x00,0xd2,0xd0,0xd1,0x50,0xd0,0x1e,0xcf,0x86,0x55,0x04,0x0a,0x00, - 0x54,0x04,0x0a,0x00,0x93,0x10,0x52,0x04,0x0a,0x00,0x51,0x04,0x0a,0x00,0x10,0x04, - 0x0a,0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0xd5,0x20,0xd4,0x10,0x53,0x04,0x0a,0x00, - 0x52,0x04,0x0a,0x00,0x11,0x04,0x0a,0x00,0x00,0x00,0x53,0x04,0x0a,0x00,0x92,0x08, - 0x11,0x04,0x0a,0x00,0x00,0x00,0x0a,0x00,0x54,0x04,0x0b,0x00,0x53,0x04,0x0b,0x00, - 0x12,0x04,0x0b,0x00,0x10,0x00,0xd0,0x3a,0xcf,0x86,0x55,0x04,0x0b,0x00,0x54,0x04, - 0x0b,0x00,0xd3,0x1c,0xd2,0x0c,0x91,0x08,0x10,0x04,0x0b,0xe6,0x0b,0x00,0x0b,0xe6, - 0xd1,0x08,0x10,0x04,0x0b,0xdc,0x0b,0x00,0x10,0x04,0x0b,0x00,0x0b,0xe6,0xd2,0x0c, - 0x91,0x08,0x10,0x04,0x0b,0xe6,0x0b,0x00,0x0b,0x00,0x11,0x04,0x0b,0x00,0x0b,0xe6, - 0xcf,0x86,0xd5,0x2c,0xd4,0x18,0x93,0x14,0x92,0x10,0xd1,0x08,0x10,0x04,0x0b,0x00, - 0x0b,0xe6,0x10,0x04,0x0b,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x53,0x04,0x00,0x00, - 0x92,0x0c,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x0b,0x00,0x0b,0x00,0x54,0x04, - 0x0d,0x00,0x93,0x10,0x52,0x04,0x0d,0x00,0x51,0x04,0x0d,0x00,0x10,0x04,0x0d,0x09, - 0x00,0x00,0x00,0x00,0xd1,0x8c,0xd0,0x72,0xcf,0x86,0xd5,0x4c,0xd4,0x30,0xd3,0x18, - 0xd2,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x0c,0x00,0x0c,0x00,0x51,0x04,0x0c,0x00, - 0x10,0x04,0x0c,0x00,0x00,0x00,0xd2,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x0c,0x00, - 0x0c,0x00,0x51,0x04,0x0c,0x00,0x10,0x04,0x0c,0x00,0x00,0x00,0x93,0x18,0xd2,0x0c, - 0x91,0x08,0x10,0x04,0x00,0x00,0x0c,0x00,0x0c,0x00,0x51,0x04,0x0c,0x00,0x10,0x04, - 0x0c,0x00,0x00,0x00,0x00,0x00,0x94,0x20,0xd3,0x10,0x52,0x04,0x0c,0x00,0x51,0x04, - 0x0c,0x00,0x10,0x04,0x0c,0x00,0x00,0x00,0x52,0x04,0x0c,0x00,0x51,0x04,0x0c,0x00, - 0x10,0x04,0x0c,0x00,0x00,0x00,0x10,0x00,0xcf,0x86,0x55,0x04,0x10,0x00,0x94,0x10, - 0x93,0x0c,0x52,0x04,0x11,0x00,0x11,0x04,0x10,0x00,0x15,0x00,0x00,0x00,0x11,0x00, - 0xd0,0x06,0xcf,0x06,0x11,0x00,0xcf,0x86,0x55,0x04,0x0b,0x00,0xd4,0x14,0x53,0x04, - 0x0b,0x00,0x52,0x04,0x0b,0x00,0x91,0x08,0x10,0x04,0x0b,0x00,0x0b,0x09,0x00,0x00, - 0x53,0x04,0x0b,0x00,0x92,0x08,0x11,0x04,0x0b,0x00,0x00,0x00,0x00,0x00,0xcf,0x06, - 0x02,0xff,0xff,0xcf,0x86,0xcf,0x06,0x02,0xff,0xff,0xd1,0x76,0xd0,0x09,0xcf,0x86, - 0xcf,0x06,0x02,0xff,0xff,0xcf,0x86,0x85,0xd4,0x07,0xcf,0x06,0x02,0xff,0xff,0xd3, - 0x07,0xcf,0x06,0x02,0xff,0xff,0xd2,0x07,0xcf,0x06,0x02,0xff,0xff,0xd1,0x07,0xcf, - 0x06,0x02,0xff,0xff,0xd0,0x18,0xcf,0x86,0x55,0x05,0x02,0xff,0xff,0x94,0x0d,0x93, - 0x09,0x12,0x05,0x02,0xff,0xff,0x00,0x00,0x00,0x00,0x0b,0x00,0xcf,0x86,0xd5,0x24, - 0x94,0x20,0xd3,0x10,0x52,0x04,0x0b,0x00,0x51,0x04,0x0b,0x00,0x10,0x04,0x0b,0x00, - 0x00,0x00,0x92,0x0c,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x0b,0x00,0x0b,0x00, - 0x0b,0x00,0x54,0x04,0x0b,0x00,0x53,0x04,0x0b,0x00,0x12,0x04,0x0b,0x00,0x00,0x00, - 0xd0,0x08,0xcf,0x86,0xcf,0x06,0x01,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x01,0x00, - 0xe4,0x9c,0x10,0xe3,0x16,0x08,0xd2,0x06,0xcf,0x06,0x01,0x00,0xe1,0x08,0x04,0xe0, - 0x04,0x02,0xcf,0x86,0xe5,0x01,0x01,0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10, - 0x08,0x01,0xff,0xe8,0xb1,0x88,0x00,0x01,0xff,0xe6,0x9b,0xb4,0x00,0x10,0x08,0x01, - 0xff,0xe8,0xbb,0x8a,0x00,0x01,0xff,0xe8,0xb3,0x88,0x00,0xd1,0x10,0x10,0x08,0x01, - 0xff,0xe6,0xbb,0x91,0x00,0x01,0xff,0xe4,0xb8,0xb2,0x00,0x10,0x08,0x01,0xff,0xe5, - 0x8f,0xa5,0x00,0x01,0xff,0xe9,0xbe,0x9c,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01, - 0xff,0xe9,0xbe,0x9c,0x00,0x01,0xff,0xe5,0xa5,0x91,0x00,0x10,0x08,0x01,0xff,0xe9, - 0x87,0x91,0x00,0x01,0xff,0xe5,0x96,0x87,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe5, - 0xa5,0x88,0x00,0x01,0xff,0xe6,0x87,0xb6,0x00,0x10,0x08,0x01,0xff,0xe7,0x99,0xa9, - 0x00,0x01,0xff,0xe7,0xbe,0x85,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01, - 0xff,0xe8,0x98,0xbf,0x00,0x01,0xff,0xe8,0x9e,0xba,0x00,0x10,0x08,0x01,0xff,0xe8, - 0xa3,0xb8,0x00,0x01,0xff,0xe9,0x82,0x8f,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe6, - 0xa8,0x82,0x00,0x01,0xff,0xe6,0xb4,0x9b,0x00,0x10,0x08,0x01,0xff,0xe7,0x83,0x99, - 0x00,0x01,0xff,0xe7,0x8f,0x9e,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe8, - 0x90,0xbd,0x00,0x01,0xff,0xe9,0x85,0xaa,0x00,0x10,0x08,0x01,0xff,0xe9,0xa7,0xb1, - 0x00,0x01,0xff,0xe4,0xba,0x82,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe5,0x8d,0xb5, - 0x00,0x01,0xff,0xe6,0xac,0x84,0x00,0x10,0x08,0x01,0xff,0xe7,0x88,0x9b,0x00,0x01, - 0xff,0xe8,0x98,0xad,0x00,0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01, - 0xff,0xe9,0xb8,0x9e,0x00,0x01,0xff,0xe5,0xb5,0x90,0x00,0x10,0x08,0x01,0xff,0xe6, - 0xbf,0xab,0x00,0x01,0xff,0xe8,0x97,0x8d,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe8, - 0xa5,0xa4,0x00,0x01,0xff,0xe6,0x8b,0x89,0x00,0x10,0x08,0x01,0xff,0xe8,0x87,0x98, - 0x00,0x01,0xff,0xe8,0xa0,0x9f,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe5, - 0xbb,0x8a,0x00,0x01,0xff,0xe6,0x9c,0x97,0x00,0x10,0x08,0x01,0xff,0xe6,0xb5,0xaa, - 0x00,0x01,0xff,0xe7,0x8b,0xbc,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe9,0x83,0x8e, - 0x00,0x01,0xff,0xe4,0xbe,0x86,0x00,0x10,0x08,0x01,0xff,0xe5,0x86,0xb7,0x00,0x01, - 0xff,0xe5,0x8b,0x9e,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe6, - 0x93,0x84,0x00,0x01,0xff,0xe6,0xab,0x93,0x00,0x10,0x08,0x01,0xff,0xe7,0x88,0x90, - 0x00,0x01,0xff,0xe7,0x9b,0xa7,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe8,0x80,0x81, - 0x00,0x01,0xff,0xe8,0x98,0x86,0x00,0x10,0x08,0x01,0xff,0xe8,0x99,0x9c,0x00,0x01, - 0xff,0xe8,0xb7,0xaf,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe9,0x9c,0xb2, - 0x00,0x01,0xff,0xe9,0xad,0xaf,0x00,0x10,0x08,0x01,0xff,0xe9,0xb7,0xba,0x00,0x01, - 0xff,0xe7,0xa2,0x8c,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe7,0xa5,0xbf,0x00,0x01, - 0xff,0xe7,0xb6,0xa0,0x00,0x10,0x08,0x01,0xff,0xe8,0x8f,0x89,0x00,0x01,0xff,0xe9, - 0x8c,0x84,0x00,0xcf,0x86,0xe5,0x01,0x01,0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10, - 0x10,0x08,0x01,0xff,0xe9,0xb9,0xbf,0x00,0x01,0xff,0xe8,0xab,0x96,0x00,0x10,0x08, - 0x01,0xff,0xe5,0xa3,0x9f,0x00,0x01,0xff,0xe5,0xbc,0x84,0x00,0xd1,0x10,0x10,0x08, - 0x01,0xff,0xe7,0xb1,0xa0,0x00,0x01,0xff,0xe8,0x81,0xbe,0x00,0x10,0x08,0x01,0xff, - 0xe7,0x89,0xa2,0x00,0x01,0xff,0xe7,0xa3,0x8a,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08, - 0x01,0xff,0xe8,0xb3,0x82,0x00,0x01,0xff,0xe9,0x9b,0xb7,0x00,0x10,0x08,0x01,0xff, - 0xe5,0xa3,0x98,0x00,0x01,0xff,0xe5,0xb1,0xa2,0x00,0xd1,0x10,0x10,0x08,0x01,0xff, - 0xe6,0xa8,0x93,0x00,0x01,0xff,0xe6,0xb7,0x9a,0x00,0x10,0x08,0x01,0xff,0xe6,0xbc, - 0x8f,0x00,0x01,0xff,0xe7,0xb4,0xaf,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08, - 0x01,0xff,0xe7,0xb8,0xb7,0x00,0x01,0xff,0xe9,0x99,0x8b,0x00,0x10,0x08,0x01,0xff, - 0xe5,0x8b,0x92,0x00,0x01,0xff,0xe8,0x82,0x8b,0x00,0xd1,0x10,0x10,0x08,0x01,0xff, - 0xe5,0x87,0x9c,0x00,0x01,0xff,0xe5,0x87,0x8c,0x00,0x10,0x08,0x01,0xff,0xe7,0xa8, - 0x9c,0x00,0x01,0xff,0xe7,0xb6,0xbe,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff, - 0xe8,0x8f,0xb1,0x00,0x01,0xff,0xe9,0x99,0xb5,0x00,0x10,0x08,0x01,0xff,0xe8,0xae, - 0x80,0x00,0x01,0xff,0xe6,0x8b,0x8f,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe6,0xa8, - 0x82,0x00,0x01,0xff,0xe8,0xab,0xbe,0x00,0x10,0x08,0x01,0xff,0xe4,0xb8,0xb9,0x00, - 0x01,0xff,0xe5,0xaf,0xa7,0x00,0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08, - 0x01,0xff,0xe6,0x80,0x92,0x00,0x01,0xff,0xe7,0x8e,0x87,0x00,0x10,0x08,0x01,0xff, - 0xe7,0x95,0xb0,0x00,0x01,0xff,0xe5,0x8c,0x97,0x00,0xd1,0x10,0x10,0x08,0x01,0xff, - 0xe7,0xa3,0xbb,0x00,0x01,0xff,0xe4,0xbe,0xbf,0x00,0x10,0x08,0x01,0xff,0xe5,0xbe, - 0xa9,0x00,0x01,0xff,0xe4,0xb8,0x8d,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff, - 0xe6,0xb3,0x8c,0x00,0x01,0xff,0xe6,0x95,0xb8,0x00,0x10,0x08,0x01,0xff,0xe7,0xb4, - 0xa2,0x00,0x01,0xff,0xe5,0x8f,0x83,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe5,0xa1, - 0x9e,0x00,0x01,0xff,0xe7,0x9c,0x81,0x00,0x10,0x08,0x01,0xff,0xe8,0x91,0x89,0x00, - 0x01,0xff,0xe8,0xaa,0xaa,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff, - 0xe6,0xae,0xba,0x00,0x01,0xff,0xe8,0xbe,0xb0,0x00,0x10,0x08,0x01,0xff,0xe6,0xb2, - 0x88,0x00,0x01,0xff,0xe6,0x8b,0xbe,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe8,0x8b, - 0xa5,0x00,0x01,0xff,0xe6,0x8e,0xa0,0x00,0x10,0x08,0x01,0xff,0xe7,0x95,0xa5,0x00, - 0x01,0xff,0xe4,0xba,0xae,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe5,0x85, - 0xa9,0x00,0x01,0xff,0xe5,0x87,0x89,0x00,0x10,0x08,0x01,0xff,0xe6,0xa2,0x81,0x00, - 0x01,0xff,0xe7,0xb3,0xa7,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe8,0x89,0xaf,0x00, - 0x01,0xff,0xe8,0xab,0x92,0x00,0x10,0x08,0x01,0xff,0xe9,0x87,0x8f,0x00,0x01,0xff, - 0xe5,0x8b,0xb5,0x00,0xe0,0x04,0x02,0xcf,0x86,0xe5,0x01,0x01,0xd4,0x80,0xd3,0x40, - 0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe5,0x91,0x82,0x00,0x01,0xff,0xe5,0xa5, - 0xb3,0x00,0x10,0x08,0x01,0xff,0xe5,0xbb,0xac,0x00,0x01,0xff,0xe6,0x97,0x85,0x00, - 0xd1,0x10,0x10,0x08,0x01,0xff,0xe6,0xbf,0xbe,0x00,0x01,0xff,0xe7,0xa4,0xaa,0x00, - 0x10,0x08,0x01,0xff,0xe9,0x96,0xad,0x00,0x01,0xff,0xe9,0xa9,0xaa,0x00,0xd2,0x20, - 0xd1,0x10,0x10,0x08,0x01,0xff,0xe9,0xba,0x97,0x00,0x01,0xff,0xe9,0xbb,0x8e,0x00, - 0x10,0x08,0x01,0xff,0xe5,0x8a,0x9b,0x00,0x01,0xff,0xe6,0x9b,0x86,0x00,0xd1,0x10, - 0x10,0x08,0x01,0xff,0xe6,0xad,0xb7,0x00,0x01,0xff,0xe8,0xbd,0xa2,0x00,0x10,0x08, - 0x01,0xff,0xe5,0xb9,0xb4,0x00,0x01,0xff,0xe6,0x86,0x90,0x00,0xd3,0x40,0xd2,0x20, - 0xd1,0x10,0x10,0x08,0x01,0xff,0xe6,0x88,0x80,0x00,0x01,0xff,0xe6,0x92,0x9a,0x00, - 0x10,0x08,0x01,0xff,0xe6,0xbc,0xa3,0x00,0x01,0xff,0xe7,0x85,0x89,0x00,0xd1,0x10, - 0x10,0x08,0x01,0xff,0xe7,0x92,0x89,0x00,0x01,0xff,0xe7,0xa7,0x8a,0x00,0x10,0x08, - 0x01,0xff,0xe7,0xb7,0xb4,0x00,0x01,0xff,0xe8,0x81,0xaf,0x00,0xd2,0x20,0xd1,0x10, - 0x10,0x08,0x01,0xff,0xe8,0xbc,0xa6,0x00,0x01,0xff,0xe8,0x93,0xae,0x00,0x10,0x08, - 0x01,0xff,0xe9,0x80,0xa3,0x00,0x01,0xff,0xe9,0x8d,0x8a,0x00,0xd1,0x10,0x10,0x08, - 0x01,0xff,0xe5,0x88,0x97,0x00,0x01,0xff,0xe5,0x8a,0xa3,0x00,0x10,0x08,0x01,0xff, - 0xe5,0x92,0xbd,0x00,0x01,0xff,0xe7,0x83,0x88,0x00,0xd4,0x80,0xd3,0x40,0xd2,0x20, - 0xd1,0x10,0x10,0x08,0x01,0xff,0xe8,0xa3,0x82,0x00,0x01,0xff,0xe8,0xaa,0xaa,0x00, - 0x10,0x08,0x01,0xff,0xe5,0xbb,0x89,0x00,0x01,0xff,0xe5,0xbf,0xb5,0x00,0xd1,0x10, - 0x10,0x08,0x01,0xff,0xe6,0x8d,0xbb,0x00,0x01,0xff,0xe6,0xae,0xae,0x00,0x10,0x08, - 0x01,0xff,0xe7,0xb0,0xbe,0x00,0x01,0xff,0xe7,0x8d,0xb5,0x00,0xd2,0x20,0xd1,0x10, - 0x10,0x08,0x01,0xff,0xe4,0xbb,0xa4,0x00,0x01,0xff,0xe5,0x9b,0xb9,0x00,0x10,0x08, - 0x01,0xff,0xe5,0xaf,0xa7,0x00,0x01,0xff,0xe5,0xb6,0xba,0x00,0xd1,0x10,0x10,0x08, - 0x01,0xff,0xe6,0x80,0x9c,0x00,0x01,0xff,0xe7,0x8e,0xb2,0x00,0x10,0x08,0x01,0xff, - 0xe7,0x91,0xa9,0x00,0x01,0xff,0xe7,0xbe,0x9a,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10, - 0x10,0x08,0x01,0xff,0xe8,0x81,0x86,0x00,0x01,0xff,0xe9,0x88,0xb4,0x00,0x10,0x08, - 0x01,0xff,0xe9,0x9b,0xb6,0x00,0x01,0xff,0xe9,0x9d,0x88,0x00,0xd1,0x10,0x10,0x08, - 0x01,0xff,0xe9,0xa0,0x98,0x00,0x01,0xff,0xe4,0xbe,0x8b,0x00,0x10,0x08,0x01,0xff, - 0xe7,0xa6,0xae,0x00,0x01,0xff,0xe9,0x86,0xb4,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08, - 0x01,0xff,0xe9,0x9a,0xb8,0x00,0x01,0xff,0xe6,0x83,0xa1,0x00,0x10,0x08,0x01,0xff, - 0xe4,0xba,0x86,0x00,0x01,0xff,0xe5,0x83,0x9a,0x00,0xd1,0x10,0x10,0x08,0x01,0xff, - 0xe5,0xaf,0xae,0x00,0x01,0xff,0xe5,0xb0,0xbf,0x00,0x10,0x08,0x01,0xff,0xe6,0x96, - 0x99,0x00,0x01,0xff,0xe6,0xa8,0x82,0x00,0xcf,0x86,0xe5,0x01,0x01,0xd4,0x80,0xd3, - 0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe7,0x87,0x8e,0x00,0x01,0xff,0xe7, - 0x99,0x82,0x00,0x10,0x08,0x01,0xff,0xe8,0x93,0xbc,0x00,0x01,0xff,0xe9,0x81,0xbc, - 0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe9,0xbe,0x8d,0x00,0x01,0xff,0xe6,0x9a,0x88, - 0x00,0x10,0x08,0x01,0xff,0xe9,0x98,0xae,0x00,0x01,0xff,0xe5,0x8a,0x89,0x00,0xd2, - 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe6,0x9d,0xbb,0x00,0x01,0xff,0xe6,0x9f,0xb3, - 0x00,0x10,0x08,0x01,0xff,0xe6,0xb5,0x81,0x00,0x01,0xff,0xe6,0xba,0x9c,0x00,0xd1, - 0x10,0x10,0x08,0x01,0xff,0xe7,0x90,0x89,0x00,0x01,0xff,0xe7,0x95,0x99,0x00,0x10, - 0x08,0x01,0xff,0xe7,0xa1,0xab,0x00,0x01,0xff,0xe7,0xb4,0x90,0x00,0xd3,0x40,0xd2, - 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe9,0xa1,0x9e,0x00,0x01,0xff,0xe5,0x85,0xad, - 0x00,0x10,0x08,0x01,0xff,0xe6,0x88,0xae,0x00,0x01,0xff,0xe9,0x99,0xb8,0x00,0xd1, - 0x10,0x10,0x08,0x01,0xff,0xe5,0x80,0xab,0x00,0x01,0xff,0xe5,0xb4,0x99,0x00,0x10, - 0x08,0x01,0xff,0xe6,0xb7,0xaa,0x00,0x01,0xff,0xe8,0xbc,0xaa,0x00,0xd2,0x20,0xd1, - 0x10,0x10,0x08,0x01,0xff,0xe5,0xbe,0x8b,0x00,0x01,0xff,0xe6,0x85,0x84,0x00,0x10, - 0x08,0x01,0xff,0xe6,0xa0,0x97,0x00,0x01,0xff,0xe7,0x8e,0x87,0x00,0xd1,0x10,0x10, - 0x08,0x01,0xff,0xe9,0x9a,0x86,0x00,0x01,0xff,0xe5,0x88,0xa9,0x00,0x10,0x08,0x01, - 0xff,0xe5,0x90,0x8f,0x00,0x01,0xff,0xe5,0xb1,0xa5,0x00,0xd4,0x80,0xd3,0x40,0xd2, - 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe6,0x98,0x93,0x00,0x01,0xff,0xe6,0x9d,0x8e, - 0x00,0x10,0x08,0x01,0xff,0xe6,0xa2,0xa8,0x00,0x01,0xff,0xe6,0xb3,0xa5,0x00,0xd1, - 0x10,0x10,0x08,0x01,0xff,0xe7,0x90,0x86,0x00,0x01,0xff,0xe7,0x97,0xa2,0x00,0x10, - 0x08,0x01,0xff,0xe7,0xbd,0xb9,0x00,0x01,0xff,0xe8,0xa3,0x8f,0x00,0xd2,0x20,0xd1, - 0x10,0x10,0x08,0x01,0xff,0xe8,0xa3,0xa1,0x00,0x01,0xff,0xe9,0x87,0x8c,0x00,0x10, - 0x08,0x01,0xff,0xe9,0x9b,0xa2,0x00,0x01,0xff,0xe5,0x8c,0xbf,0x00,0xd1,0x10,0x10, - 0x08,0x01,0xff,0xe6,0xba,0xba,0x00,0x01,0xff,0xe5,0x90,0x9d,0x00,0x10,0x08,0x01, - 0xff,0xe7,0x87,0x90,0x00,0x01,0xff,0xe7,0x92,0x98,0x00,0xd3,0x40,0xd2,0x20,0xd1, - 0x10,0x10,0x08,0x01,0xff,0xe8,0x97,0xba,0x00,0x01,0xff,0xe9,0x9a,0xa3,0x00,0x10, - 0x08,0x01,0xff,0xe9,0xb1,0x97,0x00,0x01,0xff,0xe9,0xba,0x9f,0x00,0xd1,0x10,0x10, - 0x08,0x01,0xff,0xe6,0x9e,0x97,0x00,0x01,0xff,0xe6,0xb7,0x8b,0x00,0x10,0x08,0x01, - 0xff,0xe8,0x87,0xa8,0x00,0x01,0xff,0xe7,0xab,0x8b,0x00,0xd2,0x20,0xd1,0x10,0x10, - 0x08,0x01,0xff,0xe7,0xac,0xa0,0x00,0x01,0xff,0xe7,0xb2,0x92,0x00,0x10,0x08,0x01, - 0xff,0xe7,0x8b,0x80,0x00,0x01,0xff,0xe7,0x82,0x99,0x00,0xd1,0x10,0x10,0x08,0x01, - 0xff,0xe8,0xad,0x98,0x00,0x01,0xff,0xe4,0xbb,0x80,0x00,0x10,0x08,0x01,0xff,0xe8, - 0x8c,0xb6,0x00,0x01,0xff,0xe5,0x88,0xba,0x00,0xe2,0xad,0x06,0xe1,0xc4,0x03,0xe0, - 0xcb,0x01,0xcf,0x86,0xd5,0xe4,0xd4,0x74,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08, - 0x01,0xff,0xe5,0x88,0x87,0x00,0x01,0xff,0xe5,0xba,0xa6,0x00,0x10,0x08,0x01,0xff, - 0xe6,0x8b,0x93,0x00,0x01,0xff,0xe7,0xb3,0x96,0x00,0xd1,0x10,0x10,0x08,0x01,0xff, - 0xe5,0xae,0x85,0x00,0x01,0xff,0xe6,0xb4,0x9e,0x00,0x10,0x08,0x01,0xff,0xe6,0x9a, - 0xb4,0x00,0x01,0xff,0xe8,0xbc,0xbb,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff, - 0xe8,0xa1,0x8c,0x00,0x01,0xff,0xe9,0x99,0x8d,0x00,0x10,0x08,0x01,0xff,0xe8,0xa6, - 0x8b,0x00,0x01,0xff,0xe5,0xbb,0x93,0x00,0x91,0x10,0x10,0x08,0x01,0xff,0xe5,0x85, - 0x80,0x00,0x01,0xff,0xe5,0x97,0x80,0x00,0x01,0x00,0xd3,0x34,0xd2,0x18,0xd1,0x0c, - 0x10,0x08,0x01,0xff,0xe5,0xa1,0x9a,0x00,0x01,0x00,0x10,0x08,0x01,0xff,0xe6,0x99, - 0xb4,0x00,0x01,0x00,0xd1,0x0c,0x10,0x04,0x01,0x00,0x01,0xff,0xe5,0x87,0x9e,0x00, - 0x10,0x08,0x01,0xff,0xe7,0x8c,0xaa,0x00,0x01,0xff,0xe7,0x9b,0x8a,0x00,0xd2,0x20, - 0xd1,0x10,0x10,0x08,0x01,0xff,0xe7,0xa4,0xbc,0x00,0x01,0xff,0xe7,0xa5,0x9e,0x00, - 0x10,0x08,0x01,0xff,0xe7,0xa5,0xa5,0x00,0x01,0xff,0xe7,0xa6,0x8f,0x00,0xd1,0x10, - 0x10,0x08,0x01,0xff,0xe9,0x9d,0x96,0x00,0x01,0xff,0xe7,0xb2,0xbe,0x00,0x10,0x08, - 0x01,0xff,0xe7,0xbe,0xbd,0x00,0x01,0x00,0xd4,0x64,0xd3,0x30,0xd2,0x18,0xd1,0x0c, - 0x10,0x08,0x01,0xff,0xe8,0x98,0x92,0x00,0x01,0x00,0x10,0x08,0x01,0xff,0xe8,0xab, - 0xb8,0x00,0x01,0x00,0xd1,0x0c,0x10,0x04,0x01,0x00,0x01,0xff,0xe9,0x80,0xb8,0x00, - 0x10,0x08,0x01,0xff,0xe9,0x83,0xbd,0x00,0x01,0x00,0xd2,0x14,0x51,0x04,0x01,0x00, - 0x10,0x08,0x01,0xff,0xe9,0xa3,0xaf,0x00,0x01,0xff,0xe9,0xa3,0xbc,0x00,0xd1,0x10, - 0x10,0x08,0x01,0xff,0xe9,0xa4,0xa8,0x00,0x01,0xff,0xe9,0xb6,0xb4,0x00,0x10,0x08, - 0x0d,0xff,0xe9,0x83,0x9e,0x00,0x0d,0xff,0xe9,0x9a,0xb7,0x00,0xd3,0x40,0xd2,0x20, - 0xd1,0x10,0x10,0x08,0x06,0xff,0xe4,0xbe,0xae,0x00,0x06,0xff,0xe5,0x83,0xa7,0x00, - 0x10,0x08,0x06,0xff,0xe5,0x85,0x8d,0x00,0x06,0xff,0xe5,0x8b,0x89,0x00,0xd1,0x10, - 0x10,0x08,0x06,0xff,0xe5,0x8b,0xa4,0x00,0x06,0xff,0xe5,0x8d,0x91,0x00,0x10,0x08, - 0x06,0xff,0xe5,0x96,0x9d,0x00,0x06,0xff,0xe5,0x98,0x86,0x00,0xd2,0x20,0xd1,0x10, - 0x10,0x08,0x06,0xff,0xe5,0x99,0xa8,0x00,0x06,0xff,0xe5,0xa1,0x80,0x00,0x10,0x08, - 0x06,0xff,0xe5,0xa2,0xa8,0x00,0x06,0xff,0xe5,0xb1,0xa4,0x00,0xd1,0x10,0x10,0x08, - 0x06,0xff,0xe5,0xb1,0xae,0x00,0x06,0xff,0xe6,0x82,0x94,0x00,0x10,0x08,0x06,0xff, - 0xe6,0x85,0xa8,0x00,0x06,0xff,0xe6,0x86,0x8e,0x00,0xcf,0x86,0xe5,0x01,0x01,0xd4, - 0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x06,0xff,0xe6,0x87,0xb2,0x00,0x06, - 0xff,0xe6,0x95,0x8f,0x00,0x10,0x08,0x06,0xff,0xe6,0x97,0xa2,0x00,0x06,0xff,0xe6, - 0x9a,0x91,0x00,0xd1,0x10,0x10,0x08,0x06,0xff,0xe6,0xa2,0x85,0x00,0x06,0xff,0xe6, - 0xb5,0xb7,0x00,0x10,0x08,0x06,0xff,0xe6,0xb8,0x9a,0x00,0x06,0xff,0xe6,0xbc,0xa2, - 0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x06,0xff,0xe7,0x85,0xae,0x00,0x06,0xff,0xe7, - 0x88,0xab,0x00,0x10,0x08,0x06,0xff,0xe7,0x90,0xa2,0x00,0x06,0xff,0xe7,0xa2,0x91, - 0x00,0xd1,0x10,0x10,0x08,0x06,0xff,0xe7,0xa4,0xbe,0x00,0x06,0xff,0xe7,0xa5,0x89, - 0x00,0x10,0x08,0x06,0xff,0xe7,0xa5,0x88,0x00,0x06,0xff,0xe7,0xa5,0x90,0x00,0xd3, - 0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x06,0xff,0xe7,0xa5,0x96,0x00,0x06,0xff,0xe7, - 0xa5,0x9d,0x00,0x10,0x08,0x06,0xff,0xe7,0xa6,0x8d,0x00,0x06,0xff,0xe7,0xa6,0x8e, - 0x00,0xd1,0x10,0x10,0x08,0x06,0xff,0xe7,0xa9,0x80,0x00,0x06,0xff,0xe7,0xaa,0x81, - 0x00,0x10,0x08,0x06,0xff,0xe7,0xaf,0x80,0x00,0x06,0xff,0xe7,0xb7,0xb4,0x00,0xd2, - 0x20,0xd1,0x10,0x10,0x08,0x06,0xff,0xe7,0xb8,0x89,0x00,0x06,0xff,0xe7,0xb9,0x81, - 0x00,0x10,0x08,0x06,0xff,0xe7,0xbd,0xb2,0x00,0x06,0xff,0xe8,0x80,0x85,0x00,0xd1, - 0x10,0x10,0x08,0x06,0xff,0xe8,0x87,0xad,0x00,0x06,0xff,0xe8,0x89,0xb9,0x00,0x10, - 0x08,0x06,0xff,0xe8,0x89,0xb9,0x00,0x06,0xff,0xe8,0x91,0x97,0x00,0xd4,0x75,0xd3, - 0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x06,0xff,0xe8,0xa4,0x90,0x00,0x06,0xff,0xe8, - 0xa6,0x96,0x00,0x10,0x08,0x06,0xff,0xe8,0xac,0x81,0x00,0x06,0xff,0xe8,0xac,0xb9, - 0x00,0xd1,0x10,0x10,0x08,0x06,0xff,0xe8,0xb3,0x93,0x00,0x06,0xff,0xe8,0xb4,0x88, - 0x00,0x10,0x08,0x06,0xff,0xe8,0xbe,0xb6,0x00,0x06,0xff,0xe9,0x80,0xb8,0x00,0xd2, - 0x20,0xd1,0x10,0x10,0x08,0x06,0xff,0xe9,0x9b,0xa3,0x00,0x06,0xff,0xe9,0x9f,0xbf, - 0x00,0x10,0x08,0x06,0xff,0xe9,0xa0,0xbb,0x00,0x0b,0xff,0xe6,0x81,0xb5,0x00,0x91, - 0x11,0x10,0x09,0x0b,0xff,0xf0,0xa4,0x8b,0xae,0x00,0x0b,0xff,0xe8,0x88,0x98,0x00, - 0x00,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x08,0xff,0xe4,0xb8,0xa6,0x00, - 0x08,0xff,0xe5,0x86,0xb5,0x00,0x10,0x08,0x08,0xff,0xe5,0x85,0xa8,0x00,0x08,0xff, - 0xe4,0xbe,0x80,0x00,0xd1,0x10,0x10,0x08,0x08,0xff,0xe5,0x85,0x85,0x00,0x08,0xff, - 0xe5,0x86,0x80,0x00,0x10,0x08,0x08,0xff,0xe5,0x8b,0x87,0x00,0x08,0xff,0xe5,0x8b, - 0xba,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x08,0xff,0xe5,0x96,0x9d,0x00,0x08,0xff, - 0xe5,0x95,0x95,0x00,0x10,0x08,0x08,0xff,0xe5,0x96,0x99,0x00,0x08,0xff,0xe5,0x97, - 0xa2,0x00,0xd1,0x10,0x10,0x08,0x08,0xff,0xe5,0xa1,0x9a,0x00,0x08,0xff,0xe5,0xa2, - 0xb3,0x00,0x10,0x08,0x08,0xff,0xe5,0xa5,0x84,0x00,0x08,0xff,0xe5,0xa5,0x94,0x00, - 0xe0,0x04,0x02,0xcf,0x86,0xe5,0x01,0x01,0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10, - 0x10,0x08,0x08,0xff,0xe5,0xa9,0xa2,0x00,0x08,0xff,0xe5,0xac,0xa8,0x00,0x10,0x08, - 0x08,0xff,0xe5,0xbb,0x92,0x00,0x08,0xff,0xe5,0xbb,0x99,0x00,0xd1,0x10,0x10,0x08, - 0x08,0xff,0xe5,0xbd,0xa9,0x00,0x08,0xff,0xe5,0xbe,0xad,0x00,0x10,0x08,0x08,0xff, - 0xe6,0x83,0x98,0x00,0x08,0xff,0xe6,0x85,0x8e,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08, - 0x08,0xff,0xe6,0x84,0x88,0x00,0x08,0xff,0xe6,0x86,0x8e,0x00,0x10,0x08,0x08,0xff, - 0xe6,0x85,0xa0,0x00,0x08,0xff,0xe6,0x87,0xb2,0x00,0xd1,0x10,0x10,0x08,0x08,0xff, - 0xe6,0x88,0xb4,0x00,0x08,0xff,0xe6,0x8f,0x84,0x00,0x10,0x08,0x08,0xff,0xe6,0x90, - 0x9c,0x00,0x08,0xff,0xe6,0x91,0x92,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08, - 0x08,0xff,0xe6,0x95,0x96,0x00,0x08,0xff,0xe6,0x99,0xb4,0x00,0x10,0x08,0x08,0xff, - 0xe6,0x9c,0x97,0x00,0x08,0xff,0xe6,0x9c,0x9b,0x00,0xd1,0x10,0x10,0x08,0x08,0xff, - 0xe6,0x9d,0x96,0x00,0x08,0xff,0xe6,0xad,0xb9,0x00,0x10,0x08,0x08,0xff,0xe6,0xae, - 0xba,0x00,0x08,0xff,0xe6,0xb5,0x81,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x08,0xff, - 0xe6,0xbb,0x9b,0x00,0x08,0xff,0xe6,0xbb,0x8b,0x00,0x10,0x08,0x08,0xff,0xe6,0xbc, - 0xa2,0x00,0x08,0xff,0xe7,0x80,0x9e,0x00,0xd1,0x10,0x10,0x08,0x08,0xff,0xe7,0x85, - 0xae,0x00,0x08,0xff,0xe7,0x9e,0xa7,0x00,0x10,0x08,0x08,0xff,0xe7,0x88,0xb5,0x00, - 0x08,0xff,0xe7,0x8a,0xaf,0x00,0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08, - 0x08,0xff,0xe7,0x8c,0xaa,0x00,0x08,0xff,0xe7,0x91,0xb1,0x00,0x10,0x08,0x08,0xff, - 0xe7,0x94,0x86,0x00,0x08,0xff,0xe7,0x94,0xbb,0x00,0xd1,0x10,0x10,0x08,0x08,0xff, - 0xe7,0x98,0x9d,0x00,0x08,0xff,0xe7,0x98,0x9f,0x00,0x10,0x08,0x08,0xff,0xe7,0x9b, - 0x8a,0x00,0x08,0xff,0xe7,0x9b,0x9b,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x08,0xff, - 0xe7,0x9b,0xb4,0x00,0x08,0xff,0xe7,0x9d,0x8a,0x00,0x10,0x08,0x08,0xff,0xe7,0x9d, - 0x80,0x00,0x08,0xff,0xe7,0xa3,0x8c,0x00,0xd1,0x10,0x10,0x08,0x08,0xff,0xe7,0xaa, - 0xb1,0x00,0x08,0xff,0xe7,0xaf,0x80,0x00,0x10,0x08,0x08,0xff,0xe7,0xb1,0xbb,0x00, - 0x08,0xff,0xe7,0xb5,0x9b,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x08,0xff, - 0xe7,0xb7,0xb4,0x00,0x08,0xff,0xe7,0xbc,0xbe,0x00,0x10,0x08,0x08,0xff,0xe8,0x80, - 0x85,0x00,0x08,0xff,0xe8,0x8d,0x92,0x00,0xd1,0x10,0x10,0x08,0x08,0xff,0xe8,0x8f, - 0xaf,0x00,0x08,0xff,0xe8,0x9d,0xb9,0x00,0x10,0x08,0x08,0xff,0xe8,0xa5,0x81,0x00, - 0x08,0xff,0xe8,0xa6,0x86,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x08,0xff,0xe8,0xa6, - 0x96,0x00,0x08,0xff,0xe8,0xaa,0xbf,0x00,0x10,0x08,0x08,0xff,0xe8,0xab,0xb8,0x00, - 0x08,0xff,0xe8,0xab,0x8b,0x00,0xd1,0x10,0x10,0x08,0x08,0xff,0xe8,0xac,0x81,0x00, - 0x08,0xff,0xe8,0xab,0xbe,0x00,0x10,0x08,0x08,0xff,0xe8,0xab,0xad,0x00,0x08,0xff, - 0xe8,0xac,0xb9,0x00,0xcf,0x86,0x95,0xde,0xd4,0x81,0xd3,0x40,0xd2,0x20,0xd1,0x10, - 0x10,0x08,0x08,0xff,0xe8,0xae,0x8a,0x00,0x08,0xff,0xe8,0xb4,0x88,0x00,0x10,0x08, - 0x08,0xff,0xe8,0xbc,0xb8,0x00,0x08,0xff,0xe9,0x81,0xb2,0x00,0xd1,0x10,0x10,0x08, - 0x08,0xff,0xe9,0x86,0x99,0x00,0x08,0xff,0xe9,0x89,0xb6,0x00,0x10,0x08,0x08,0xff, - 0xe9,0x99,0xbc,0x00,0x08,0xff,0xe9,0x9b,0xa3,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08, - 0x08,0xff,0xe9,0x9d,0x96,0x00,0x08,0xff,0xe9,0x9f,0x9b,0x00,0x10,0x08,0x08,0xff, - 0xe9,0x9f,0xbf,0x00,0x08,0xff,0xe9,0xa0,0x8b,0x00,0xd1,0x10,0x10,0x08,0x08,0xff, - 0xe9,0xa0,0xbb,0x00,0x08,0xff,0xe9,0xac,0x92,0x00,0x10,0x08,0x08,0xff,0xe9,0xbe, - 0x9c,0x00,0x08,0xff,0xf0,0xa2,0xa1,0x8a,0x00,0xd3,0x45,0xd2,0x22,0xd1,0x12,0x10, - 0x09,0x08,0xff,0xf0,0xa2,0xa1,0x84,0x00,0x08,0xff,0xf0,0xa3,0x8f,0x95,0x00,0x10, - 0x08,0x08,0xff,0xe3,0xae,0x9d,0x00,0x08,0xff,0xe4,0x80,0x98,0x00,0xd1,0x11,0x10, - 0x08,0x08,0xff,0xe4,0x80,0xb9,0x00,0x08,0xff,0xf0,0xa5,0x89,0x89,0x00,0x10,0x09, - 0x08,0xff,0xf0,0xa5,0xb3,0x90,0x00,0x08,0xff,0xf0,0xa7,0xbb,0x93,0x00,0x92,0x14, - 0x91,0x10,0x10,0x08,0x08,0xff,0xe9,0xbd,0x83,0x00,0x08,0xff,0xe9,0xbe,0x8e,0x00, - 0x00,0x00,0x00,0x00,0x00,0x00,0xe1,0x94,0x01,0xe0,0x08,0x01,0xcf,0x86,0xd5,0x42, - 0xd4,0x14,0x93,0x10,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00, - 0x00,0x00,0x00,0x00,0xd3,0x10,0x92,0x0c,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00, - 0x01,0x00,0x01,0x00,0x52,0x04,0x00,0x00,0xd1,0x0d,0x10,0x04,0x00,0x00,0x04,0xff, - 0xd7,0x99,0xd6,0xb4,0x00,0x10,0x04,0x01,0x1a,0x01,0xff,0xd7,0xb2,0xd6,0xb7,0x00, - 0xd4,0x42,0x53,0x04,0x01,0x00,0xd2,0x16,0x51,0x04,0x01,0x00,0x10,0x09,0x01,0xff, - 0xd7,0xa9,0xd7,0x81,0x00,0x01,0xff,0xd7,0xa9,0xd7,0x82,0x00,0xd1,0x16,0x10,0x0b, - 0x01,0xff,0xd7,0xa9,0xd6,0xbc,0xd7,0x81,0x00,0x01,0xff,0xd7,0xa9,0xd6,0xbc,0xd7, - 0x82,0x00,0x10,0x09,0x01,0xff,0xd7,0x90,0xd6,0xb7,0x00,0x01,0xff,0xd7,0x90,0xd6, - 0xb8,0x00,0xd3,0x43,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff,0xd7,0x90,0xd6,0xbc, - 0x00,0x01,0xff,0xd7,0x91,0xd6,0xbc,0x00,0x10,0x09,0x01,0xff,0xd7,0x92,0xd6,0xbc, - 0x00,0x01,0xff,0xd7,0x93,0xd6,0xbc,0x00,0xd1,0x12,0x10,0x09,0x01,0xff,0xd7,0x94, - 0xd6,0xbc,0x00,0x01,0xff,0xd7,0x95,0xd6,0xbc,0x00,0x10,0x09,0x01,0xff,0xd7,0x96, - 0xd6,0xbc,0x00,0x00,0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff,0xd7,0x98,0xd6, - 0xbc,0x00,0x01,0xff,0xd7,0x99,0xd6,0xbc,0x00,0x10,0x09,0x01,0xff,0xd7,0x9a,0xd6, - 0xbc,0x00,0x01,0xff,0xd7,0x9b,0xd6,0xbc,0x00,0xd1,0x0d,0x10,0x09,0x01,0xff,0xd7, - 0x9c,0xd6,0xbc,0x00,0x00,0x00,0x10,0x09,0x01,0xff,0xd7,0x9e,0xd6,0xbc,0x00,0x00, - 0x00,0xcf,0x86,0x95,0x85,0x94,0x81,0xd3,0x3e,0xd2,0x1f,0xd1,0x12,0x10,0x09,0x01, - 0xff,0xd7,0xa0,0xd6,0xbc,0x00,0x01,0xff,0xd7,0xa1,0xd6,0xbc,0x00,0x10,0x04,0x00, - 0x00,0x01,0xff,0xd7,0xa3,0xd6,0xbc,0x00,0xd1,0x0d,0x10,0x09,0x01,0xff,0xd7,0xa4, - 0xd6,0xbc,0x00,0x00,0x00,0x10,0x09,0x01,0xff,0xd7,0xa6,0xd6,0xbc,0x00,0x01,0xff, - 0xd7,0xa7,0xd6,0xbc,0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff,0xd7,0xa8,0xd6, - 0xbc,0x00,0x01,0xff,0xd7,0xa9,0xd6,0xbc,0x00,0x10,0x09,0x01,0xff,0xd7,0xaa,0xd6, - 0xbc,0x00,0x01,0xff,0xd7,0x95,0xd6,0xb9,0x00,0xd1,0x12,0x10,0x09,0x01,0xff,0xd7, - 0x91,0xd6,0xbf,0x00,0x01,0xff,0xd7,0x9b,0xd6,0xbf,0x00,0x10,0x09,0x01,0xff,0xd7, - 0xa4,0xd6,0xbf,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd0,0x1a,0xcf,0x86,0x55,0x04, - 0x01,0x00,0x54,0x04,0x01,0x00,0x93,0x0c,0x92,0x08,0x11,0x04,0x01,0x00,0x0c,0x00, - 0x0c,0x00,0x0c,0x00,0xcf,0x86,0x95,0x24,0xd4,0x10,0x93,0x0c,0x92,0x08,0x11,0x04, - 0x0c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x93,0x10,0x92,0x0c,0x51,0x04,0x00,0x00, - 0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd3,0x5a,0xd2,0x06, - 0xcf,0x06,0x01,0x00,0xd1,0x14,0xd0,0x06,0xcf,0x06,0x01,0x00,0xcf,0x86,0x95,0x08, - 0x14,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0xd0,0x1a,0xcf,0x86,0x95,0x14,0x54,0x04, - 0x01,0x00,0x93,0x0c,0x92,0x08,0x11,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x01,0x00, - 0x01,0x00,0xcf,0x86,0xd5,0x0c,0x94,0x08,0x13,0x04,0x01,0x00,0x00,0x00,0x05,0x00, - 0x54,0x04,0x05,0x00,0x53,0x04,0x01,0x00,0x52,0x04,0x01,0x00,0x91,0x08,0x10,0x04, - 0x06,0x00,0x07,0x00,0x00,0x00,0xd2,0xce,0xd1,0xa5,0xd0,0x37,0xcf,0x86,0xd5,0x15, - 0x54,0x05,0x06,0xff,0x00,0x53,0x04,0x08,0x00,0x92,0x08,0x11,0x04,0x08,0x00,0x00, - 0x00,0x00,0x00,0x94,0x1c,0xd3,0x10,0x52,0x04,0x01,0xe6,0x51,0x04,0x0a,0xe6,0x10, - 0x04,0x0a,0xe6,0x10,0xdc,0x52,0x04,0x10,0xdc,0x11,0x04,0x10,0xdc,0x11,0xe6,0x01, - 0x00,0xcf,0x86,0xd5,0x38,0xd4,0x24,0xd3,0x14,0x52,0x04,0x01,0x00,0xd1,0x08,0x10, - 0x04,0x01,0x00,0x06,0x00,0x10,0x04,0x06,0x00,0x07,0x00,0x92,0x0c,0x91,0x08,0x10, - 0x04,0x07,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x93,0x10,0x92,0x0c,0x51,0x04,0x01, - 0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x01,0x00,0xd4,0x18,0xd3,0x10,0x52, - 0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x12,0x04,0x01, - 0x00,0x00,0x00,0x93,0x18,0xd2,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x06, - 0x00,0x91,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x01,0x00,0xd0,0x06,0xcf, - 0x06,0x01,0x00,0xcf,0x86,0x55,0x04,0x01,0x00,0x54,0x04,0x01,0x00,0x53,0x04,0x01, - 0x00,0x52,0x04,0x01,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x10,0x04,0x00, - 0x00,0x01,0xff,0x00,0xd1,0x50,0xd0,0x1e,0xcf,0x86,0x95,0x18,0x94,0x14,0x93,0x10, - 0x92,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00, - 0x01,0x00,0x01,0x00,0xcf,0x86,0xd5,0x18,0x54,0x04,0x01,0x00,0x53,0x04,0x01,0x00, - 0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x06,0x00,0x94,0x14, - 0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x06,0x00,0x01,0x00,0x01,0x00,0x01,0x00, - 0x01,0x00,0x01,0x00,0xd0,0x2f,0xcf,0x86,0x55,0x04,0x01,0x00,0xd4,0x15,0x93,0x11, - 0x92,0x0d,0x91,0x09,0x10,0x05,0x01,0xff,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01, - 0x00,0x53,0x04,0x01,0x00,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01, - 0x00,0x00,0x00,0xcf,0x86,0xd5,0x38,0xd4,0x18,0xd3,0x0c,0x92,0x08,0x11,0x04,0x00, - 0x00,0x01,0x00,0x01,0x00,0x92,0x08,0x11,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0xd3, - 0x0c,0x92,0x08,0x11,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0xd2,0x08,0x11,0x04,0x00, - 0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x00,0x00,0xd4,0x20,0xd3, - 0x10,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x52, - 0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x53,0x05,0x00, - 0xff,0x00,0xd2,0x0d,0x91,0x09,0x10,0x05,0x00,0xff,0x00,0x04,0x00,0x04,0x00,0x91, - 0x08,0x10,0x04,0x03,0x00,0x01,0x00,0x01,0x00,0x83,0xe2,0x46,0x3e,0xe1,0x1f,0x3b, - 0xe0,0x9c,0x39,0xcf,0x86,0xe5,0x40,0x26,0xc4,0xe3,0x16,0x14,0xe2,0xef,0x11,0xe1, - 0xd0,0x10,0xe0,0x60,0x07,0xcf,0x86,0xe5,0x53,0x03,0xe4,0x4c,0x02,0xe3,0x3d,0x01, - 0xd2,0x94,0xd1,0x70,0xd0,0x4a,0xcf,0x86,0xd5,0x18,0x94,0x14,0x53,0x04,0x07,0x00, - 0x52,0x04,0x07,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x07,0x00,0x07,0x00,0x07,0x00, - 0xd4,0x14,0x93,0x10,0x52,0x04,0x07,0x00,0x51,0x04,0x07,0x00,0x10,0x04,0x07,0x00, - 0x00,0x00,0x07,0x00,0x53,0x04,0x07,0x00,0xd2,0x0c,0x51,0x04,0x07,0x00,0x10,0x04, - 0x07,0x00,0x00,0x00,0x51,0x04,0x07,0x00,0x10,0x04,0x00,0x00,0x07,0x00,0xcf,0x86, - 0x95,0x20,0xd4,0x10,0x53,0x04,0x07,0x00,0x52,0x04,0x07,0x00,0x11,0x04,0x07,0x00, - 0x00,0x00,0x53,0x04,0x07,0x00,0x52,0x04,0x07,0x00,0x11,0x04,0x07,0x00,0x00,0x00, - 0x00,0x00,0xd0,0x06,0xcf,0x06,0x07,0x00,0xcf,0x86,0x55,0x04,0x07,0x00,0x54,0x04, - 0x07,0x00,0x53,0x04,0x07,0x00,0x92,0x0c,0x51,0x04,0x07,0x00,0x10,0x04,0x07,0x00, - 0x00,0x00,0x00,0x00,0xd1,0x40,0xd0,0x3a,0xcf,0x86,0xd5,0x20,0x94,0x1c,0x93,0x18, - 0xd2,0x0c,0x51,0x04,0x07,0x00,0x10,0x04,0x07,0x00,0x00,0x00,0x51,0x04,0x00,0x00, - 0x10,0x04,0x00,0x00,0x07,0x00,0x07,0x00,0x07,0x00,0x54,0x04,0x07,0x00,0x93,0x10, - 0x52,0x04,0x07,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x07,0x00,0x07,0x00, - 0xcf,0x06,0x08,0x00,0xd0,0x46,0xcf,0x86,0xd5,0x2c,0xd4,0x20,0x53,0x04,0x08,0x00, - 0xd2,0x0c,0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x10,0x00,0xd1,0x08,0x10,0x04, - 0x10,0x00,0x12,0x00,0x10,0x04,0x12,0x00,0x00,0x00,0x53,0x04,0x0a,0x00,0x12,0x04, - 0x0a,0x00,0x00,0x00,0x94,0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x10,0x00, - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0xd5,0x08,0x14,0x04, - 0x00,0x00,0x0a,0x00,0x54,0x04,0x0a,0x00,0x53,0x04,0x0a,0x00,0x52,0x04,0x0a,0x00, - 0x91,0x08,0x10,0x04,0x0a,0x00,0x0a,0xdc,0x00,0x00,0xd2,0x5e,0xd1,0x06,0xcf,0x06, - 0x00,0x00,0xd0,0x1e,0xcf,0x86,0x95,0x18,0x54,0x04,0x0a,0x00,0x53,0x04,0x0a,0x00, - 0x52,0x04,0x0a,0x00,0x91,0x08,0x10,0x04,0x0a,0x00,0x00,0x00,0x00,0x00,0x0a,0x00, - 0xcf,0x86,0xd5,0x18,0x54,0x04,0x0a,0x00,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04, - 0x0a,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd4,0x14,0x93,0x10,0x92,0x0c, - 0x91,0x08,0x10,0x04,0x10,0xdc,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x53,0x04, - 0x10,0x00,0x12,0x04,0x10,0x00,0x00,0x00,0xd1,0x70,0xd0,0x36,0xcf,0x86,0xd5,0x18, - 0x54,0x04,0x05,0x00,0x53,0x04,0x05,0x00,0x52,0x04,0x05,0x00,0x51,0x04,0x05,0x00, - 0x10,0x04,0x05,0x00,0x10,0x00,0x94,0x18,0xd3,0x08,0x12,0x04,0x05,0x00,0x00,0x00, - 0x52,0x04,0x00,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x13,0x00,0x13,0x00,0x05,0x00, - 0xcf,0x86,0xd5,0x18,0x94,0x14,0x53,0x04,0x05,0x00,0x92,0x0c,0x51,0x04,0x05,0x00, - 0x10,0x04,0x05,0x00,0x00,0x00,0x00,0x00,0x10,0x00,0x54,0x04,0x10,0x00,0xd3,0x0c, - 0x52,0x04,0x10,0x00,0x11,0x04,0x10,0x00,0x10,0xe6,0x92,0x0c,0x51,0x04,0x10,0xe6, - 0x10,0x04,0x10,0xe6,0x00,0x00,0x00,0x00,0xd0,0x1e,0xcf,0x86,0x95,0x18,0x54,0x04, - 0x07,0x00,0x53,0x04,0x07,0x00,0x52,0x04,0x07,0x00,0x51,0x04,0x07,0x00,0x10,0x04, - 0x00,0x00,0x07,0x00,0x08,0x00,0xcf,0x86,0x95,0x1c,0xd4,0x0c,0x93,0x08,0x12,0x04, - 0x08,0x00,0x00,0x00,0x08,0x00,0x93,0x0c,0x52,0x04,0x08,0x00,0x11,0x04,0x08,0x00, - 0x00,0x00,0x00,0x00,0x00,0x00,0xd3,0xba,0xd2,0x80,0xd1,0x34,0xd0,0x1a,0xcf,0x86, - 0x55,0x04,0x05,0x00,0x94,0x10,0x93,0x0c,0x52,0x04,0x05,0x00,0x11,0x04,0x05,0x00, - 0x07,0x00,0x05,0x00,0x05,0x00,0xcf,0x86,0x95,0x14,0x94,0x10,0x53,0x04,0x05,0x00, - 0x52,0x04,0x05,0x00,0x11,0x04,0x05,0x00,0x07,0x00,0x07,0x00,0x07,0x00,0xd0,0x2a, - 0xcf,0x86,0xd5,0x14,0x54,0x04,0x07,0x00,0x53,0x04,0x07,0x00,0x52,0x04,0x07,0x00, - 0x11,0x04,0x07,0x00,0x00,0x00,0x94,0x10,0x53,0x04,0x07,0x00,0x92,0x08,0x11,0x04, - 0x07,0x00,0x00,0x00,0x00,0x00,0x12,0x00,0xcf,0x86,0xd5,0x10,0x54,0x04,0x12,0x00, - 0x93,0x08,0x12,0x04,0x12,0x00,0x00,0x00,0x12,0x00,0x54,0x04,0x12,0x00,0x53,0x04, - 0x12,0x00,0x12,0x04,0x12,0x00,0x00,0x00,0xd1,0x34,0xd0,0x12,0xcf,0x86,0x55,0x04, - 0x10,0x00,0x94,0x08,0x13,0x04,0x10,0x00,0x00,0x00,0x10,0x00,0xcf,0x86,0x55,0x04, - 0x10,0x00,0x94,0x18,0xd3,0x08,0x12,0x04,0x10,0x00,0x00,0x00,0x52,0x04,0x00,0x00, - 0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x10,0x00,0x00,0x00,0xcf,0x06,0x00,0x00, - 0xd2,0x06,0xcf,0x06,0x10,0x00,0xd1,0x40,0xd0,0x1e,0xcf,0x86,0x55,0x04,0x10,0x00, - 0x54,0x04,0x10,0x00,0x93,0x10,0x52,0x04,0x10,0x00,0x51,0x04,0x10,0x00,0x10,0x04, - 0x10,0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0xd5,0x14,0x54,0x04,0x10,0x00,0x93,0x0c, - 0x52,0x04,0x10,0x00,0x11,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0x94,0x08,0x13,0x04, - 0x10,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xe4,0xce,0x02,0xe3,0x45,0x01, - 0xd2,0xd0,0xd1,0x70,0xd0,0x52,0xcf,0x86,0xd5,0x20,0x94,0x1c,0xd3,0x0c,0x52,0x04, - 0x07,0x00,0x11,0x04,0x07,0x00,0x00,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x07,0x00, - 0x00,0x00,0x07,0x00,0x07,0x00,0x07,0x00,0x54,0x04,0x07,0x00,0xd3,0x10,0x52,0x04, - 0x07,0x00,0x51,0x04,0x07,0x00,0x10,0x04,0x00,0x00,0x07,0x00,0xd2,0x0c,0x91,0x08, - 0x10,0x04,0x07,0x00,0x00,0x00,0x00,0x00,0xd1,0x08,0x10,0x04,0x07,0x00,0x00,0x00, - 0x10,0x04,0x00,0x00,0x07,0x00,0xcf,0x86,0x95,0x18,0x54,0x04,0x0b,0x00,0x93,0x10, - 0x52,0x04,0x0b,0x00,0x51,0x04,0x0b,0x00,0x10,0x04,0x00,0x00,0x0b,0x00,0x0b,0x00, - 0x10,0x00,0xd0,0x32,0xcf,0x86,0xd5,0x18,0x54,0x04,0x10,0x00,0x53,0x04,0x10,0x00, - 0x52,0x04,0x10,0x00,0x51,0x04,0x10,0x00,0x10,0x04,0x10,0x00,0x00,0x00,0x94,0x14, - 0x93,0x10,0x52,0x04,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x10,0x00, - 0x10,0x00,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x11,0x00,0xd3,0x14, - 0xd2,0x0c,0x51,0x04,0x11,0x00,0x10,0x04,0x11,0x00,0x00,0x00,0x11,0x04,0x11,0x00, - 0x00,0x00,0x92,0x0c,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x11,0x00,0x11,0x00, - 0xd1,0x40,0xd0,0x3a,0xcf,0x86,0xd5,0x1c,0x54,0x04,0x09,0x00,0x53,0x04,0x09,0x00, - 0xd2,0x08,0x11,0x04,0x09,0x00,0x0b,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00, - 0x09,0x00,0x54,0x04,0x0a,0x00,0x53,0x04,0x0a,0x00,0xd2,0x08,0x11,0x04,0x0a,0x00, - 0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x0a,0x00,0xcf,0x06,0x00,0x00, - 0xd0,0x1a,0xcf,0x86,0x55,0x04,0x0d,0x00,0x54,0x04,0x0d,0x00,0x53,0x04,0x0d,0x00, - 0x52,0x04,0x00,0x00,0x11,0x04,0x11,0x00,0x0d,0x00,0xcf,0x86,0x95,0x14,0x54,0x04, - 0x11,0x00,0x93,0x0c,0x92,0x08,0x11,0x04,0x00,0x00,0x11,0x00,0x11,0x00,0x11,0x00, - 0x11,0x00,0xd2,0xec,0xd1,0xa4,0xd0,0x76,0xcf,0x86,0xd5,0x48,0xd4,0x28,0xd3,0x14, - 0x52,0x04,0x08,0x00,0xd1,0x08,0x10,0x04,0x00,0x00,0x08,0x00,0x10,0x04,0x08,0x00, - 0x00,0x00,0x52,0x04,0x00,0x00,0xd1,0x08,0x10,0x04,0x08,0x00,0x08,0xdc,0x10,0x04, - 0x08,0x00,0x08,0xe6,0xd3,0x10,0x52,0x04,0x08,0x00,0x91,0x08,0x10,0x04,0x00,0x00, - 0x08,0x00,0x08,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x08,0x00,0x08,0x00, - 0x08,0x00,0x54,0x04,0x08,0x00,0xd3,0x0c,0x52,0x04,0x08,0x00,0x11,0x04,0x14,0x00, - 0x00,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04,0x08,0xe6,0x08,0x01,0x10,0x04,0x08,0xdc, - 0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x08,0x09,0xcf,0x86,0x95,0x28, - 0xd4,0x14,0x53,0x04,0x08,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x14,0x00,0x00,0x00, - 0x00,0x00,0x00,0x00,0x53,0x04,0x08,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x08,0x00, - 0x00,0x00,0x00,0x00,0x00,0x00,0x0b,0x00,0xd0,0x0a,0xcf,0x86,0x15,0x04,0x10,0x00, - 0x00,0x00,0xcf,0x86,0x55,0x04,0x10,0x00,0xd4,0x24,0xd3,0x14,0x52,0x04,0x10,0x00, - 0xd1,0x08,0x10,0x04,0x10,0x00,0x10,0xe6,0x10,0x04,0x10,0xdc,0x00,0x00,0x92,0x0c, - 0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x10,0x00,0x10,0x00,0x93,0x10,0x52,0x04, - 0x10,0x00,0x51,0x04,0x10,0x00,0x10,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0xd1,0x54, - 0xd0,0x26,0xcf,0x86,0x55,0x04,0x0b,0x00,0x54,0x04,0x0b,0x00,0xd3,0x0c,0x52,0x04, - 0x0b,0x00,0x11,0x04,0x0b,0x00,0x00,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x00,0x00, - 0x0b,0x00,0x0b,0x00,0x0b,0x00,0xcf,0x86,0xd5,0x14,0x54,0x04,0x0b,0x00,0x93,0x0c, - 0x52,0x04,0x0b,0x00,0x11,0x04,0x0b,0x00,0x00,0x00,0x0b,0x00,0x54,0x04,0x0b,0x00, - 0x93,0x10,0x92,0x0c,0x51,0x04,0x0b,0x00,0x10,0x04,0x0b,0x00,0x00,0x00,0x00,0x00, - 0x0b,0x00,0xd0,0x42,0xcf,0x86,0xd5,0x28,0x54,0x04,0x10,0x00,0xd3,0x0c,0x92,0x08, - 0x11,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0xd2,0x0c,0x91,0x08,0x10,0x04,0x00,0x00, - 0x10,0x00,0x10,0x00,0x91,0x08,0x10,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0x94,0x14, - 0x53,0x04,0x00,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x10,0x00,0x10,0x00, - 0x10,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xd3,0x96,0xd2,0x68,0xd1,0x24,0xd0,0x06, - 0xcf,0x06,0x0b,0x00,0xcf,0x86,0x95,0x18,0x94,0x14,0x53,0x04,0x0b,0x00,0x92,0x0c, - 0x91,0x08,0x10,0x04,0x0b,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - 0xd0,0x1e,0xcf,0x86,0x55,0x04,0x11,0x00,0x54,0x04,0x11,0x00,0x93,0x10,0x92,0x0c, - 0x51,0x04,0x11,0x00,0x10,0x04,0x11,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x86, - 0x55,0x04,0x11,0x00,0x54,0x04,0x11,0x00,0xd3,0x10,0x92,0x0c,0x51,0x04,0x11,0x00, - 0x10,0x04,0x11,0x00,0x00,0x00,0x00,0x00,0x92,0x08,0x11,0x04,0x00,0x00,0x11,0x00, - 0x11,0x00,0xd1,0x28,0xd0,0x22,0xcf,0x86,0x55,0x04,0x14,0x00,0xd4,0x0c,0x93,0x08, - 0x12,0x04,0x14,0x00,0x14,0xe6,0x00,0x00,0x53,0x04,0x14,0x00,0x92,0x08,0x11,0x04, - 0x14,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xd2,0x2a, - 0xd1,0x24,0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04, - 0x0b,0x00,0x53,0x04,0x0b,0x00,0x52,0x04,0x0b,0x00,0x51,0x04,0x0b,0x00,0x10,0x04, - 0x0b,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xd1,0x58,0xd0,0x12,0xcf,0x86,0x55,0x04, - 0x14,0x00,0x94,0x08,0x13,0x04,0x14,0x00,0x00,0x00,0x14,0x00,0xcf,0x86,0x95,0x40, - 0xd4,0x24,0xd3,0x0c,0x52,0x04,0x14,0x00,0x11,0x04,0x14,0x00,0x14,0xdc,0xd2,0x0c, - 0x51,0x04,0x14,0xe6,0x10,0x04,0x14,0xe6,0x14,0xdc,0x91,0x08,0x10,0x04,0x14,0xe6, - 0x14,0xdc,0x14,0xdc,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x14,0xdc,0x14,0x00, - 0x14,0x00,0x14,0x00,0x92,0x08,0x11,0x04,0x14,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - 0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x15,0x00, - 0x93,0x10,0x52,0x04,0x15,0x00,0x51,0x04,0x15,0x00,0x10,0x04,0x15,0x00,0x00,0x00, - 0x00,0x00,0xcf,0x86,0xe5,0x0f,0x06,0xe4,0xf8,0x03,0xe3,0x02,0x02,0xd2,0xfb,0xd1, - 0x4c,0xd0,0x06,0xcf,0x06,0x0c,0x00,0xcf,0x86,0xd5,0x2c,0xd4,0x1c,0xd3,0x10,0x52, - 0x04,0x0c,0x00,0x51,0x04,0x0c,0x00,0x10,0x04,0x0c,0x09,0x0c,0x00,0x52,0x04,0x0c, - 0x00,0x11,0x04,0x0c,0x00,0x00,0x00,0x93,0x0c,0x92,0x08,0x11,0x04,0x00,0x00,0x0c, - 0x00,0x0c,0x00,0x0c,0x00,0x54,0x04,0x0c,0x00,0x53,0x04,0x00,0x00,0x52,0x04,0x00, - 0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x10,0x09,0xd0,0x69,0xcf,0x86,0xd5, - 0x32,0x54,0x04,0x0b,0x00,0x53,0x04,0x0b,0x00,0xd2,0x15,0x51,0x04,0x0b,0x00,0x10, - 0x0d,0x0b,0xff,0xf0,0x91,0x82,0x99,0xf0,0x91,0x82,0xba,0x00,0x0b,0x00,0x91,0x11, - 0x10,0x0d,0x0b,0xff,0xf0,0x91,0x82,0x9b,0xf0,0x91,0x82,0xba,0x00,0x0b,0x00,0x0b, - 0x00,0xd4,0x1d,0x53,0x04,0x0b,0x00,0x92,0x15,0x51,0x04,0x0b,0x00,0x10,0x04,0x0b, - 0x00,0x0b,0xff,0xf0,0x91,0x82,0xa5,0xf0,0x91,0x82,0xba,0x00,0x0b,0x00,0x53,0x04, - 0x0b,0x00,0x92,0x10,0xd1,0x08,0x10,0x04,0x0b,0x00,0x0b,0x09,0x10,0x04,0x0b,0x07, - 0x0b,0x00,0x0b,0x00,0xcf,0x86,0xd5,0x20,0x94,0x1c,0xd3,0x0c,0x92,0x08,0x11,0x04, - 0x0b,0x00,0x00,0x00,0x00,0x00,0x52,0x04,0x00,0x00,0x91,0x08,0x10,0x04,0x00,0x00, - 0x14,0x00,0x00,0x00,0x0d,0x00,0xd4,0x14,0x53,0x04,0x0d,0x00,0x92,0x0c,0x91,0x08, - 0x10,0x04,0x0d,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x53,0x04,0x0d,0x00,0x92,0x08, - 0x11,0x04,0x0d,0x00,0x00,0x00,0x00,0x00,0xd1,0x96,0xd0,0x5c,0xcf,0x86,0xd5,0x18, - 0x94,0x14,0x93,0x10,0x92,0x0c,0x51,0x04,0x0d,0xe6,0x10,0x04,0x0d,0xe6,0x0d,0x00, - 0x0d,0x00,0x0d,0x00,0x0d,0x00,0xd4,0x26,0x53,0x04,0x0d,0x00,0x52,0x04,0x0d,0x00, - 0x51,0x04,0x0d,0x00,0x10,0x0d,0x0d,0xff,0xf0,0x91,0x84,0xb1,0xf0,0x91,0x84,0xa7, - 0x00,0x0d,0xff,0xf0,0x91,0x84,0xb2,0xf0,0x91,0x84,0xa7,0x00,0x93,0x18,0xd2,0x0c, - 0x51,0x04,0x0d,0x00,0x10,0x04,0x0d,0x00,0x0d,0x09,0x91,0x08,0x10,0x04,0x0d,0x09, - 0x00,0x00,0x0d,0x00,0x0d,0x00,0xcf,0x86,0xd5,0x18,0x94,0x14,0x93,0x10,0x52,0x04, - 0x0d,0x00,0x51,0x04,0x14,0x00,0x10,0x04,0x14,0x00,0x00,0x00,0x00,0x00,0x10,0x00, - 0x54,0x04,0x10,0x00,0x93,0x18,0xd2,0x0c,0x51,0x04,0x10,0x00,0x10,0x04,0x10,0x00, - 0x10,0x07,0x51,0x04,0x10,0x00,0x10,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0xd0,0x06, - 0xcf,0x06,0x0d,0x00,0xcf,0x86,0xd5,0x40,0xd4,0x2c,0xd3,0x10,0x92,0x0c,0x91,0x08, - 0x10,0x04,0x0d,0x09,0x0d,0x00,0x0d,0x00,0x0d,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04, - 0x0d,0x00,0x11,0x00,0x10,0x04,0x11,0x07,0x11,0x00,0x91,0x08,0x10,0x04,0x11,0x00, - 0x10,0x00,0x00,0x00,0x53,0x04,0x0d,0x00,0x92,0x0c,0x51,0x04,0x0d,0x00,0x10,0x04, - 0x10,0x00,0x11,0x00,0x11,0x00,0xd4,0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04, - 0x00,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x93,0x10,0x52,0x04,0x10,0x00, - 0x91,0x08,0x10,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd2,0xc8,0xd1,0x48, - 0xd0,0x42,0xcf,0x86,0xd5,0x18,0x54,0x04,0x10,0x00,0x93,0x10,0x92,0x0c,0x51,0x04, - 0x10,0x00,0x10,0x04,0x00,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x54,0x04,0x10,0x00, - 0xd3,0x14,0x52,0x04,0x10,0x00,0xd1,0x08,0x10,0x04,0x10,0x00,0x10,0x09,0x10,0x04, - 0x10,0x07,0x10,0x00,0x52,0x04,0x10,0x00,0x51,0x04,0x10,0x00,0x10,0x04,0x12,0x00, - 0x00,0x00,0xcf,0x06,0x00,0x00,0xd0,0x52,0xcf,0x86,0xd5,0x3c,0xd4,0x28,0xd3,0x10, - 0x52,0x04,0x11,0x00,0x51,0x04,0x11,0x00,0x10,0x04,0x11,0x00,0x00,0x00,0xd2,0x0c, - 0x91,0x08,0x10,0x04,0x11,0x00,0x00,0x00,0x11,0x00,0x51,0x04,0x11,0x00,0x10,0x04, - 0x00,0x00,0x11,0x00,0x53,0x04,0x11,0x00,0x52,0x04,0x11,0x00,0x51,0x04,0x11,0x00, - 0x10,0x04,0x00,0x00,0x11,0x00,0x94,0x10,0x53,0x04,0x11,0x00,0x92,0x08,0x11,0x04, - 0x11,0x00,0x00,0x00,0x00,0x00,0x10,0x00,0xcf,0x86,0x55,0x04,0x10,0x00,0xd4,0x18, - 0x53,0x04,0x10,0x00,0x92,0x10,0xd1,0x08,0x10,0x04,0x10,0x00,0x10,0x07,0x10,0x04, - 0x10,0x09,0x00,0x00,0x00,0x00,0x53,0x04,0x10,0x00,0x92,0x08,0x11,0x04,0x10,0x00, - 0x00,0x00,0x00,0x00,0xe1,0x27,0x01,0xd0,0x8a,0xcf,0x86,0xd5,0x44,0xd4,0x2c,0xd3, - 0x18,0xd2,0x0c,0x91,0x08,0x10,0x04,0x11,0x00,0x10,0x00,0x10,0x00,0x91,0x08,0x10, - 0x04,0x00,0x00,0x10,0x00,0x10,0x00,0x52,0x04,0x10,0x00,0xd1,0x08,0x10,0x04,0x10, - 0x00,0x00,0x00,0x10,0x04,0x00,0x00,0x10,0x00,0x93,0x14,0x92,0x10,0xd1,0x08,0x10, - 0x04,0x10,0x00,0x00,0x00,0x10,0x04,0x00,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0xd4, - 0x14,0x53,0x04,0x10,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x10,0x00,0x00,0x00,0x10, - 0x00,0x10,0x00,0xd3,0x18,0xd2,0x0c,0x91,0x08,0x10,0x04,0x10,0x00,0x00,0x00,0x10, - 0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x10,0x00,0x10,0x00,0xd2,0x0c,0x51,0x04,0x10, - 0x00,0x10,0x04,0x00,0x00,0x14,0x07,0x91,0x08,0x10,0x04,0x10,0x07,0x10,0x00,0x10, - 0x00,0xcf,0x86,0xd5,0x6a,0xd4,0x42,0xd3,0x14,0x52,0x04,0x10,0x00,0xd1,0x08,0x10, - 0x04,0x10,0x00,0x00,0x00,0x10,0x04,0x00,0x00,0x10,0x00,0xd2,0x19,0xd1,0x08,0x10, - 0x04,0x10,0x00,0x00,0x00,0x10,0x04,0x00,0x00,0x10,0xff,0xf0,0x91,0x8d,0x87,0xf0, - 0x91,0x8c,0xbe,0x00,0x91,0x11,0x10,0x0d,0x10,0xff,0xf0,0x91,0x8d,0x87,0xf0,0x91, - 0x8d,0x97,0x00,0x10,0x09,0x00,0x00,0xd3,0x18,0xd2,0x0c,0x91,0x08,0x10,0x04,0x11, - 0x00,0x00,0x00,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x10,0x00,0x52, - 0x04,0x00,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x10,0x00,0x10,0x00,0xd4,0x1c,0xd3, - 0x0c,0x52,0x04,0x10,0x00,0x11,0x04,0x00,0x00,0x10,0xe6,0x52,0x04,0x10,0xe6,0x91, - 0x08,0x10,0x04,0x10,0xe6,0x00,0x00,0x00,0x00,0x93,0x10,0x52,0x04,0x10,0xe6,0x91, - 0x08,0x10,0x04,0x10,0xe6,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xe3, - 0x30,0x01,0xd2,0xb7,0xd1,0x48,0xd0,0x06,0xcf,0x06,0x12,0x00,0xcf,0x86,0x95,0x3c, - 0xd4,0x1c,0x93,0x18,0xd2,0x0c,0x51,0x04,0x12,0x00,0x10,0x04,0x12,0x09,0x12,0x00, - 0x51,0x04,0x12,0x00,0x10,0x04,0x12,0x07,0x12,0x00,0x12,0x00,0x53,0x04,0x12,0x00, - 0xd2,0x0c,0x51,0x04,0x12,0x00,0x10,0x04,0x00,0x00,0x12,0x00,0xd1,0x08,0x10,0x04, - 0x00,0x00,0x12,0x00,0x10,0x04,0x14,0xe6,0x15,0x00,0x00,0x00,0xd0,0x45,0xcf,0x86, - 0x55,0x04,0x10,0x00,0x54,0x04,0x10,0x00,0x53,0x04,0x10,0x00,0xd2,0x15,0x51,0x04, - 0x10,0x00,0x10,0x04,0x10,0x00,0x10,0xff,0xf0,0x91,0x92,0xb9,0xf0,0x91,0x92,0xba, - 0x00,0xd1,0x11,0x10,0x0d,0x10,0xff,0xf0,0x91,0x92,0xb9,0xf0,0x91,0x92,0xb0,0x00, - 0x10,0x00,0x10,0x0d,0x10,0xff,0xf0,0x91,0x92,0xb9,0xf0,0x91,0x92,0xbd,0x00,0x10, - 0x00,0xcf,0x86,0x95,0x24,0xd4,0x14,0x93,0x10,0x92,0x0c,0x51,0x04,0x10,0x00,0x10, - 0x04,0x10,0x09,0x10,0x07,0x10,0x00,0x00,0x00,0x53,0x04,0x10,0x00,0x92,0x08,0x11, - 0x04,0x10,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd1,0x06,0xcf,0x06,0x00,0x00,0xd0, - 0x40,0xcf,0x86,0x55,0x04,0x10,0x00,0x54,0x04,0x10,0x00,0xd3,0x0c,0x52,0x04,0x10, - 0x00,0x11,0x04,0x10,0x00,0x00,0x00,0xd2,0x1e,0x51,0x04,0x10,0x00,0x10,0x0d,0x10, - 0xff,0xf0,0x91,0x96,0xb8,0xf0,0x91,0x96,0xaf,0x00,0x10,0xff,0xf0,0x91,0x96,0xb9, - 0xf0,0x91,0x96,0xaf,0x00,0x51,0x04,0x10,0x00,0x10,0x04,0x10,0x00,0x10,0x09,0xcf, - 0x86,0x95,0x2c,0xd4,0x1c,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x10,0x07,0x10, - 0x00,0x10,0x00,0x10,0x00,0x92,0x08,0x11,0x04,0x10,0x00,0x11,0x00,0x11,0x00,0x53, - 0x04,0x11,0x00,0x52,0x04,0x11,0x00,0x11,0x04,0x11,0x00,0x00,0x00,0x00,0x00,0xd2, - 0xa0,0xd1,0x5c,0xd0,0x1e,0xcf,0x86,0x55,0x04,0x10,0x00,0x54,0x04,0x10,0x00,0x53, - 0x04,0x10,0x00,0x52,0x04,0x10,0x00,0x51,0x04,0x10,0x00,0x10,0x04,0x10,0x00,0x10, - 0x09,0xcf,0x86,0xd5,0x24,0xd4,0x14,0x93,0x10,0x52,0x04,0x10,0x00,0x91,0x08,0x10, - 0x04,0x10,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x53,0x04,0x10,0x00,0x92,0x08,0x11, - 0x04,0x10,0x00,0x00,0x00,0x00,0x00,0x94,0x14,0x53,0x04,0x12,0x00,0x52,0x04,0x12, - 0x00,0x91,0x08,0x10,0x04,0x12,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd0,0x2a,0xcf, - 0x86,0x55,0x04,0x0d,0x00,0x54,0x04,0x0d,0x00,0xd3,0x10,0x52,0x04,0x0d,0x00,0x51, - 0x04,0x0d,0x00,0x10,0x04,0x0d,0x09,0x0d,0x07,0x92,0x0c,0x91,0x08,0x10,0x04,0x15, - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0x95,0x14,0x94,0x10,0x53,0x04,0x0d, - 0x00,0x92,0x08,0x11,0x04,0x0d,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd1, - 0x40,0xd0,0x3a,0xcf,0x86,0xd5,0x20,0x54,0x04,0x11,0x00,0x53,0x04,0x11,0x00,0xd2, - 0x0c,0x51,0x04,0x11,0x00,0x10,0x04,0x14,0x00,0x00,0x00,0x91,0x08,0x10,0x04,0x00, - 0x00,0x11,0x00,0x11,0x00,0x94,0x14,0x53,0x04,0x11,0x00,0x92,0x0c,0x51,0x04,0x11, - 0x00,0x10,0x04,0x11,0x00,0x11,0x09,0x00,0x00,0x11,0x00,0xcf,0x06,0x00,0x00,0xcf, - 0x06,0x00,0x00,0xe4,0x59,0x01,0xd3,0xb2,0xd2,0x5c,0xd1,0x28,0xd0,0x22,0xcf,0x86, - 0x55,0x04,0x14,0x00,0x54,0x04,0x14,0x00,0x53,0x04,0x14,0x00,0x92,0x10,0xd1,0x08, - 0x10,0x04,0x14,0x00,0x14,0x09,0x10,0x04,0x14,0x07,0x14,0x00,0x00,0x00,0xcf,0x06, - 0x00,0x00,0xd0,0x0a,0xcf,0x86,0x15,0x04,0x00,0x00,0x10,0x00,0xcf,0x86,0x55,0x04, - 0x10,0x00,0x54,0x04,0x10,0x00,0xd3,0x10,0x92,0x0c,0x51,0x04,0x10,0x00,0x10,0x04, - 0x10,0x00,0x00,0x00,0x00,0x00,0x52,0x04,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04, - 0x00,0x00,0x10,0x00,0xd1,0x06,0xcf,0x06,0x00,0x00,0xd0,0x1a,0xcf,0x86,0x55,0x04, - 0x00,0x00,0x94,0x10,0x53,0x04,0x15,0x00,0x92,0x08,0x11,0x04,0x00,0x00,0x15,0x00, - 0x15,0x00,0x15,0x00,0xcf,0x86,0xd5,0x14,0x54,0x04,0x15,0x00,0x53,0x04,0x15,0x00, - 0x92,0x08,0x11,0x04,0x00,0x00,0x15,0x00,0x15,0x00,0x94,0x1c,0x93,0x18,0xd2,0x0c, - 0x91,0x08,0x10,0x04,0x15,0x09,0x15,0x00,0x15,0x00,0x91,0x08,0x10,0x04,0x15,0x00, - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd2,0xa0,0xd1,0x3c,0xd0,0x1e,0xcf,0x86, - 0x55,0x04,0x13,0x00,0x54,0x04,0x13,0x00,0x93,0x10,0x52,0x04,0x13,0x00,0x91,0x08, - 0x10,0x04,0x13,0x09,0x13,0x00,0x13,0x00,0x13,0x00,0xcf,0x86,0x95,0x18,0x94,0x14, - 0x93,0x10,0x52,0x04,0x13,0x00,0x51,0x04,0x13,0x00,0x10,0x04,0x13,0x00,0x13,0x09, - 0x00,0x00,0x13,0x00,0x13,0x00,0xd0,0x46,0xcf,0x86,0xd5,0x2c,0xd4,0x10,0x93,0x0c, - 0x52,0x04,0x13,0x00,0x11,0x04,0x15,0x00,0x13,0x00,0x13,0x00,0x53,0x04,0x13,0x00, - 0xd2,0x0c,0x91,0x08,0x10,0x04,0x13,0x00,0x13,0x09,0x13,0x00,0x91,0x08,0x10,0x04, - 0x13,0x00,0x14,0x00,0x13,0x00,0x94,0x14,0x93,0x10,0x92,0x0c,0x51,0x04,0x13,0x00, - 0x10,0x04,0x13,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0x55,0x04, - 0x10,0x00,0x54,0x04,0x10,0x00,0x53,0x04,0x10,0x00,0x92,0x0c,0x91,0x08,0x10,0x04, - 0x10,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xe3,0xa9,0x01,0xd2, - 0xb0,0xd1,0x6c,0xd0,0x3e,0xcf,0x86,0xd5,0x18,0x94,0x14,0x53,0x04,0x12,0x00,0x92, - 0x0c,0x91,0x08,0x10,0x04,0x12,0x00,0x00,0x00,0x12,0x00,0x12,0x00,0x12,0x00,0x54, - 0x04,0x12,0x00,0xd3,0x10,0x52,0x04,0x12,0x00,0x51,0x04,0x12,0x00,0x10,0x04,0x12, - 0x00,0x00,0x00,0x52,0x04,0x12,0x00,0x51,0x04,0x12,0x00,0x10,0x04,0x12,0x00,0x12, - 0x09,0xcf,0x86,0xd5,0x14,0x94,0x10,0x93,0x0c,0x52,0x04,0x12,0x00,0x11,0x04,0x12, - 0x00,0x00,0x00,0x00,0x00,0x12,0x00,0x94,0x14,0x53,0x04,0x12,0x00,0x52,0x04,0x12, - 0x00,0x91,0x08,0x10,0x04,0x12,0x00,0x00,0x00,0x00,0x00,0x12,0x00,0xd0,0x3e,0xcf, - 0x86,0xd5,0x14,0x54,0x04,0x12,0x00,0x93,0x0c,0x92,0x08,0x11,0x04,0x00,0x00,0x12, - 0x00,0x12,0x00,0x12,0x00,0xd4,0x14,0x53,0x04,0x12,0x00,0x92,0x0c,0x91,0x08,0x10, - 0x04,0x00,0x00,0x12,0x00,0x12,0x00,0x12,0x00,0x93,0x10,0x52,0x04,0x12,0x00,0x51, - 0x04,0x12,0x00,0x10,0x04,0x12,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xd1, - 0xa0,0xd0,0x52,0xcf,0x86,0xd5,0x24,0x94,0x20,0xd3,0x10,0x52,0x04,0x13,0x00,0x51, - 0x04,0x13,0x00,0x10,0x04,0x13,0x00,0x00,0x00,0x92,0x0c,0x51,0x04,0x13,0x00,0x10, - 0x04,0x00,0x00,0x13,0x00,0x13,0x00,0x13,0x00,0x54,0x04,0x13,0x00,0xd3,0x10,0x52, - 0x04,0x13,0x00,0x51,0x04,0x13,0x00,0x10,0x04,0x13,0x00,0x00,0x00,0xd2,0x0c,0x51, - 0x04,0x00,0x00,0x10,0x04,0x13,0x00,0x00,0x00,0x51,0x04,0x13,0x00,0x10,0x04,0x00, - 0x00,0x13,0x00,0xcf,0x86,0xd5,0x28,0xd4,0x18,0x93,0x14,0xd2,0x0c,0x51,0x04,0x13, - 0x00,0x10,0x04,0x13,0x07,0x13,0x00,0x11,0x04,0x13,0x09,0x13,0x00,0x00,0x00,0x53, - 0x04,0x13,0x00,0x92,0x08,0x11,0x04,0x13,0x00,0x00,0x00,0x00,0x00,0x94,0x20,0xd3, - 0x10,0x52,0x04,0x14,0x00,0x51,0x04,0x14,0x00,0x10,0x04,0x00,0x00,0x14,0x00,0x92, - 0x0c,0x91,0x08,0x10,0x04,0x14,0x00,0x00,0x00,0x14,0x00,0x14,0x00,0x14,0x00,0xd0, - 0x52,0xcf,0x86,0xd5,0x3c,0xd4,0x14,0x53,0x04,0x14,0x00,0x52,0x04,0x14,0x00,0x51, - 0x04,0x14,0x00,0x10,0x04,0x14,0x00,0x00,0x00,0xd3,0x18,0xd2,0x0c,0x51,0x04,0x14, - 0x00,0x10,0x04,0x00,0x00,0x14,0x00,0x51,0x04,0x14,0x00,0x10,0x04,0x14,0x00,0x14, - 0x09,0x92,0x0c,0x91,0x08,0x10,0x04,0x14,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x94, - 0x10,0x53,0x04,0x14,0x00,0x92,0x08,0x11,0x04,0x14,0x00,0x00,0x00,0x00,0x00,0x00, - 0x00,0xcf,0x06,0x00,0x00,0xd2,0x2a,0xd1,0x06,0xcf,0x06,0x00,0x00,0xd0,0x06,0xcf, - 0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x14,0x00,0x53,0x04,0x14, - 0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x14,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd1, - 0x06,0xcf,0x06,0x00,0x00,0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x15, - 0x00,0x54,0x04,0x15,0x00,0xd3,0x0c,0x92,0x08,0x11,0x04,0x15,0x00,0x00,0x00,0x00, - 0x00,0x52,0x04,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x15,0x00,0xd0, - 0xca,0xcf,0x86,0xd5,0xc2,0xd4,0x54,0xd3,0x06,0xcf,0x06,0x09,0x00,0xd2,0x06,0xcf, - 0x06,0x09,0x00,0xd1,0x24,0xd0,0x06,0xcf,0x06,0x09,0x00,0xcf,0x86,0x55,0x04,0x09, - 0x00,0x94,0x14,0x53,0x04,0x09,0x00,0x52,0x04,0x09,0x00,0x51,0x04,0x09,0x00,0x10, - 0x04,0x09,0x00,0x10,0x00,0x10,0x00,0xd0,0x1e,0xcf,0x86,0x95,0x18,0x54,0x04,0x10, - 0x00,0x53,0x04,0x10,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x10,0x00,0x11,0x00,0x00, - 0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xd3,0x68,0xd2,0x46,0xd1,0x40,0xd0, - 0x06,0xcf,0x06,0x09,0x00,0xcf,0x86,0x55,0x04,0x09,0x00,0xd4,0x20,0xd3,0x10,0x92, - 0x0c,0x51,0x04,0x09,0x00,0x10,0x04,0x09,0x00,0x10,0x00,0x10,0x00,0x52,0x04,0x10, - 0x00,0x51,0x04,0x10,0x00,0x10,0x04,0x10,0x00,0x00,0x00,0x93,0x10,0x52,0x04,0x09, - 0x00,0x91,0x08,0x10,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x11, - 0x00,0xd1,0x1c,0xd0,0x06,0xcf,0x06,0x11,0x00,0xcf,0x86,0x95,0x10,0x94,0x0c,0x93, - 0x08,0x12,0x04,0x11,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00, - 0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x86,0xd5,0x4c,0xd4,0x06,0xcf, - 0x06,0x0b,0x00,0xd3,0x40,0xd2,0x3a,0xd1,0x34,0xd0,0x2e,0xcf,0x86,0x55,0x04,0x0b, - 0x00,0xd4,0x14,0x53,0x04,0x0b,0x00,0x52,0x04,0x0b,0x00,0x51,0x04,0x0b,0x00,0x10, - 0x04,0x0b,0x00,0x00,0x00,0x53,0x04,0x15,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x15, - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf, - 0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xd1,0x4c,0xd0,0x44,0xcf, - 0x86,0xd5,0x3c,0xd4,0x06,0xcf,0x06,0x00,0x00,0xd3,0x06,0xcf,0x06,0x11,0x00,0xd2, - 0x2a,0xd1,0x24,0xd0,0x06,0xcf,0x06,0x11,0x00,0xcf,0x86,0x95,0x18,0x94,0x14,0x93, - 0x10,0x52,0x04,0x11,0x00,0x51,0x04,0x11,0x00,0x10,0x04,0x11,0x00,0x00,0x00,0x00, - 0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00, - 0x00,0xcf,0x86,0xcf,0x06,0x00,0x00,0xe0,0xd2,0x01,0xcf,0x86,0xd5,0x06,0xcf,0x06, - 0x00,0x00,0xe4,0x0b,0x01,0xd3,0x06,0xcf,0x06,0x0c,0x00,0xd2,0x84,0xd1,0x50,0xd0, - 0x1e,0xcf,0x86,0x55,0x04,0x0c,0x00,0x54,0x04,0x0c,0x00,0x53,0x04,0x0c,0x00,0x92, - 0x0c,0x91,0x08,0x10,0x04,0x0c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0xd5, - 0x18,0x54,0x04,0x10,0x00,0x53,0x04,0x10,0x00,0x52,0x04,0x10,0x00,0x51,0x04,0x10, - 0x00,0x10,0x04,0x10,0x00,0x00,0x00,0x94,0x14,0x53,0x04,0x10,0x00,0xd2,0x08,0x11, - 0x04,0x10,0x00,0x00,0x00,0x11,0x04,0x00,0x00,0x10,0x00,0x00,0x00,0xd0,0x06,0xcf, - 0x06,0x00,0x00,0xcf,0x86,0xd5,0x08,0x14,0x04,0x00,0x00,0x10,0x00,0xd4,0x10,0x53, - 0x04,0x10,0x00,0x52,0x04,0x10,0x00,0x11,0x04,0x10,0x00,0x00,0x00,0x93,0x10,0x52, - 0x04,0x10,0x01,0x91,0x08,0x10,0x04,0x10,0x01,0x10,0x00,0x00,0x00,0x00,0x00,0xd1, - 0x6c,0xd0,0x1e,0xcf,0x86,0x55,0x04,0x10,0x00,0x54,0x04,0x10,0x00,0x93,0x10,0x52, - 0x04,0x10,0xe6,0x51,0x04,0x10,0xe6,0x10,0x04,0x10,0xe6,0x10,0x00,0x10,0x00,0xcf, - 0x86,0xd5,0x24,0xd4,0x10,0x93,0x0c,0x52,0x04,0x10,0x00,0x11,0x04,0x10,0x00,0x00, - 0x00,0x00,0x00,0x53,0x04,0x10,0x00,0x92,0x0c,0x51,0x04,0x10,0x00,0x10,0x04,0x00, - 0x00,0x10,0x00,0x10,0x00,0xd4,0x14,0x93,0x10,0x92,0x0c,0x51,0x04,0x10,0x00,0x10, - 0x04,0x00,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x53,0x04,0x10,0x00,0x52,0x04,0x00, - 0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x10,0x00,0x10,0x00,0xd0,0x0e,0xcf,0x86,0x95, - 0x08,0x14,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xd3,0x06,0xcf, - 0x06,0x00,0x00,0xd2,0x30,0xd1,0x0c,0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x06,0x14, - 0x00,0xd0,0x1e,0xcf,0x86,0x95,0x18,0x54,0x04,0x14,0x00,0x53,0x04,0x14,0x00,0x92, - 0x0c,0x51,0x04,0x14,0x00,0x10,0x04,0x14,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf, - 0x06,0x00,0x00,0xd1,0x4c,0xd0,0x06,0xcf,0x06,0x0d,0x00,0xcf,0x86,0xd5,0x2c,0x94, - 0x28,0xd3,0x10,0x52,0x04,0x0d,0x00,0x91,0x08,0x10,0x04,0x0d,0x00,0x15,0x00,0x15, - 0x00,0xd2,0x0c,0x51,0x04,0x15,0x00,0x10,0x04,0x15,0x00,0x00,0x00,0x51,0x04,0x00, - 0x00,0x10,0x04,0x00,0x00,0x15,0x00,0x0d,0x00,0x54,0x04,0x0d,0x00,0x53,0x04,0x0d, - 0x00,0x52,0x04,0x0d,0x00,0x51,0x04,0x0d,0x00,0x10,0x04,0x0d,0x00,0x15,0x00,0xd0, - 0x1e,0xcf,0x86,0x95,0x18,0x94,0x14,0x53,0x04,0x15,0x00,0x52,0x04,0x00,0x00,0x51, - 0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x0d,0x00,0x0d,0x00,0x00,0x00,0xcf,0x86,0x55, - 0x04,0x00,0x00,0x94,0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x12,0x00,0x13, - 0x00,0x15,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0xcf,0x06,0x12,0x00,0xe2, - 0xc6,0x01,0xd1,0x8e,0xd0,0x86,0xcf,0x86,0xd5,0x48,0xd4,0x06,0xcf,0x06,0x12,0x00, - 0xd3,0x06,0xcf,0x06,0x12,0x00,0xd2,0x06,0xcf,0x06,0x12,0x00,0xd1,0x06,0xcf,0x06, - 0x12,0x00,0xd0,0x06,0xcf,0x06,0x12,0x00,0xcf,0x86,0x55,0x04,0x12,0x00,0xd4,0x14, - 0x53,0x04,0x12,0x00,0x52,0x04,0x12,0x00,0x91,0x08,0x10,0x04,0x12,0x00,0x14,0x00, - 0x14,0x00,0x93,0x0c,0x92,0x08,0x11,0x04,0x14,0x00,0x15,0x00,0x15,0x00,0x00,0x00, - 0xd4,0x36,0xd3,0x06,0xcf,0x06,0x12,0x00,0xd2,0x2a,0xd1,0x06,0xcf,0x06,0x12,0x00, - 0xd0,0x06,0xcf,0x06,0x12,0x00,0xcf,0x86,0x55,0x04,0x12,0x00,0x54,0x04,0x12,0x00, - 0x93,0x10,0x92,0x0c,0x51,0x04,0x12,0x00,0x10,0x04,0x12,0x00,0x00,0x00,0x00,0x00, - 0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x86,0xcf,0x06,0x00,0x00, - 0xd0,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xcf,0x86,0xd5,0xa2,0xd4,0x9c,0xd3,0x74, - 0xd2,0x26,0xd1,0x20,0xd0,0x1a,0xcf,0x86,0x95,0x14,0x94,0x10,0x93,0x0c,0x92,0x08, - 0x11,0x04,0x0c,0x00,0x13,0x00,0x13,0x00,0x13,0x00,0x13,0x00,0x13,0x00,0xcf,0x06, - 0x13,0x00,0xcf,0x06,0x13,0x00,0xd1,0x48,0xd0,0x1e,0xcf,0x86,0x95,0x18,0x54,0x04, - 0x13,0x00,0x53,0x04,0x13,0x00,0x52,0x04,0x13,0x00,0x51,0x04,0x13,0x00,0x10,0x04, - 0x13,0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0xd5,0x18,0x54,0x04,0x00,0x00,0x93,0x10, - 0x92,0x0c,0x51,0x04,0x15,0x00,0x10,0x04,0x15,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - 0x94,0x0c,0x93,0x08,0x12,0x04,0x00,0x00,0x15,0x00,0x00,0x00,0x13,0x00,0xcf,0x06, - 0x13,0x00,0xd2,0x22,0xd1,0x06,0xcf,0x06,0x13,0x00,0xd0,0x06,0xcf,0x06,0x13,0x00, - 0xcf,0x86,0x55,0x04,0x13,0x00,0x54,0x04,0x13,0x00,0x53,0x04,0x13,0x00,0x12,0x04, - 0x13,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf,0x06, - 0x00,0x00,0xd3,0x7f,0xd2,0x79,0xd1,0x34,0xd0,0x06,0xcf,0x06,0x10,0x00,0xcf,0x86, - 0x55,0x04,0x10,0x00,0xd4,0x14,0x53,0x04,0x10,0x00,0x92,0x0c,0x51,0x04,0x10,0x00, - 0x10,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0x53,0x04,0x10,0x00,0x52,0x04,0x10,0x00, - 0x91,0x08,0x10,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0xd0,0x3f,0xcf,0x86,0xd5,0x2c, - 0xd4,0x14,0x53,0x04,0x10,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x10,0x00,0x00,0x00, - 0x00,0x00,0x00,0x00,0x53,0x04,0x10,0x00,0xd2,0x08,0x11,0x04,0x10,0x00,0x00,0x00, - 0x51,0x04,0x10,0x00,0x10,0x04,0x10,0x01,0x10,0x00,0x94,0x0d,0x93,0x09,0x12,0x05, - 0x10,0xff,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00, - 0x00,0xcf,0x06,0x00,0x00,0xe1,0x96,0x04,0xd0,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00, - 0xcf,0x86,0xe5,0x33,0x04,0xe4,0x83,0x02,0xe3,0xf8,0x01,0xd2,0x26,0xd1,0x06,0xcf, - 0x06,0x05,0x00,0xd0,0x06,0xcf,0x06,0x05,0x00,0xcf,0x86,0x55,0x04,0x05,0x00,0x54, - 0x04,0x05,0x00,0x93,0x0c,0x52,0x04,0x05,0x00,0x11,0x04,0x05,0x00,0x00,0x00,0x00, - 0x00,0xd1,0xef,0xd0,0x2a,0xcf,0x86,0x55,0x04,0x05,0x00,0x94,0x20,0xd3,0x10,0x52, - 0x04,0x05,0x00,0x51,0x04,0x05,0x00,0x10,0x04,0x05,0x00,0x00,0x00,0x92,0x0c,0x91, - 0x08,0x10,0x04,0x00,0x00,0x0a,0x00,0x05,0x00,0x05,0x00,0x05,0x00,0xcf,0x86,0xd5, - 0x2a,0x54,0x04,0x05,0x00,0x53,0x04,0x05,0x00,0x52,0x04,0x05,0x00,0x51,0x04,0x05, - 0x00,0x10,0x0d,0x05,0xff,0xf0,0x9d,0x85,0x97,0xf0,0x9d,0x85,0xa5,0x00,0x05,0xff, - 0xf0,0x9d,0x85,0x98,0xf0,0x9d,0x85,0xa5,0x00,0xd4,0x75,0xd3,0x61,0xd2,0x44,0xd1, - 0x22,0x10,0x11,0x05,0xff,0xf0,0x9d,0x85,0x98,0xf0,0x9d,0x85,0xa5,0xf0,0x9d,0x85, - 0xae,0x00,0x05,0xff,0xf0,0x9d,0x85,0x98,0xf0,0x9d,0x85,0xa5,0xf0,0x9d,0x85,0xaf, - 0x00,0x10,0x11,0x05,0xff,0xf0,0x9d,0x85,0x98,0xf0,0x9d,0x85,0xa5,0xf0,0x9d,0x85, - 0xb0,0x00,0x05,0xff,0xf0,0x9d,0x85,0x98,0xf0,0x9d,0x85,0xa5,0xf0,0x9d,0x85,0xb1, - 0x00,0xd1,0x15,0x10,0x11,0x05,0xff,0xf0,0x9d,0x85,0x98,0xf0,0x9d,0x85,0xa5,0xf0, - 0x9d,0x85,0xb2,0x00,0x05,0xd8,0x10,0x04,0x05,0xd8,0x05,0x01,0xd2,0x08,0x11,0x04, - 0x05,0x01,0x05,0x00,0x91,0x08,0x10,0x04,0x05,0x00,0x05,0xe2,0x05,0xd8,0xd3,0x12, - 0x92,0x0d,0x51,0x04,0x05,0xd8,0x10,0x04,0x05,0xd8,0x05,0xff,0x00,0x05,0xff,0x00, - 0x92,0x0e,0x51,0x05,0x05,0xff,0x00,0x10,0x05,0x05,0xff,0x00,0x05,0xdc,0x05,0xdc, - 0xd0,0x97,0xcf,0x86,0xd5,0x28,0x94,0x24,0xd3,0x18,0xd2,0x0c,0x51,0x04,0x05,0xdc, - 0x10,0x04,0x05,0xdc,0x05,0x00,0x91,0x08,0x10,0x04,0x05,0x00,0x05,0xe6,0x05,0xe6, - 0x92,0x08,0x11,0x04,0x05,0xe6,0x05,0xdc,0x05,0x00,0x05,0x00,0xd4,0x14,0x53,0x04, - 0x05,0x00,0xd2,0x08,0x11,0x04,0x05,0x00,0x05,0xe6,0x11,0x04,0x05,0xe6,0x05,0x00, - 0x53,0x04,0x05,0x00,0xd2,0x15,0x51,0x04,0x05,0x00,0x10,0x04,0x05,0x00,0x05,0xff, - 0xf0,0x9d,0x86,0xb9,0xf0,0x9d,0x85,0xa5,0x00,0xd1,0x1e,0x10,0x0d,0x05,0xff,0xf0, - 0x9d,0x86,0xba,0xf0,0x9d,0x85,0xa5,0x00,0x05,0xff,0xf0,0x9d,0x86,0xb9,0xf0,0x9d, - 0x85,0xa5,0xf0,0x9d,0x85,0xae,0x00,0x10,0x11,0x05,0xff,0xf0,0x9d,0x86,0xba,0xf0, - 0x9d,0x85,0xa5,0xf0,0x9d,0x85,0xae,0x00,0x05,0xff,0xf0,0x9d,0x86,0xb9,0xf0,0x9d, - 0x85,0xa5,0xf0,0x9d,0x85,0xaf,0x00,0xcf,0x86,0xd5,0x31,0xd4,0x21,0x93,0x1d,0x92, - 0x19,0x91,0x15,0x10,0x11,0x05,0xff,0xf0,0x9d,0x86,0xba,0xf0,0x9d,0x85,0xa5,0xf0, - 0x9d,0x85,0xaf,0x00,0x05,0x00,0x05,0x00,0x05,0x00,0x05,0x00,0x53,0x04,0x05,0x00, - 0x52,0x04,0x05,0x00,0x11,0x04,0x05,0x00,0x11,0x00,0x94,0x14,0x53,0x04,0x11,0x00, - 0x92,0x0c,0x91,0x08,0x10,0x04,0x11,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, - 0xd2,0x44,0xd1,0x28,0xd0,0x06,0xcf,0x06,0x08,0x00,0xcf,0x86,0x95,0x1c,0x94,0x18, - 0x93,0x14,0xd2,0x08,0x11,0x04,0x08,0x00,0x08,0xe6,0x91,0x08,0x10,0x04,0x08,0xe6, - 0x08,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd0,0x06,0xcf,0x06,0x00,0x00, - 0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x14,0x00,0x93,0x08,0x12,0x04,0x14,0x00, - 0x00,0x00,0x00,0x00,0xd1,0x40,0xd0,0x06,0xcf,0x06,0x07,0x00,0xcf,0x86,0xd5,0x18, - 0x54,0x04,0x07,0x00,0x93,0x10,0x52,0x04,0x07,0x00,0x51,0x04,0x07,0x00,0x10,0x04, - 0x07,0x00,0x00,0x00,0x00,0x00,0x54,0x04,0x09,0x00,0xd3,0x0c,0x92,0x08,0x11,0x04, - 0x09,0x00,0x14,0x00,0x14,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x14,0x00,0x00,0x00, - 0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xe3,0x5f,0x01,0xd2,0xb4,0xd1,0x24,0xd0, - 0x06,0xcf,0x06,0x05,0x00,0xcf,0x86,0x95,0x18,0x54,0x04,0x05,0x00,0x93,0x10,0x52, - 0x04,0x05,0x00,0x91,0x08,0x10,0x04,0x05,0x00,0x00,0x00,0x05,0x00,0x05,0x00,0x05, - 0x00,0xd0,0x6a,0xcf,0x86,0xd5,0x18,0x54,0x04,0x05,0x00,0x53,0x04,0x05,0x00,0x52, - 0x04,0x05,0x00,0x91,0x08,0x10,0x04,0x05,0x00,0x00,0x00,0x05,0x00,0xd4,0x34,0xd3, - 0x1c,0xd2,0x0c,0x51,0x04,0x00,0x00,0x10,0x04,0x05,0x00,0x00,0x00,0xd1,0x08,0x10, - 0x04,0x00,0x00,0x05,0x00,0x10,0x04,0x05,0x00,0x00,0x00,0xd2,0x0c,0x91,0x08,0x10, - 0x04,0x00,0x00,0x05,0x00,0x05,0x00,0x91,0x08,0x10,0x04,0x05,0x00,0x00,0x00,0x05, - 0x00,0x53,0x04,0x05,0x00,0xd2,0x0c,0x51,0x04,0x05,0x00,0x10,0x04,0x00,0x00,0x05, - 0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x05,0x00,0x05,0x00,0xcf,0x86,0x95,0x20,0x94, - 0x1c,0x93,0x18,0xd2,0x0c,0x91,0x08,0x10,0x04,0x05,0x00,0x07,0x00,0x05,0x00,0x91, - 0x08,0x10,0x04,0x00,0x00,0x05,0x00,0x05,0x00,0x05,0x00,0x05,0x00,0x05,0x00,0xd1, - 0xa4,0xd0,0x6a,0xcf,0x86,0xd5,0x48,0xd4,0x28,0xd3,0x10,0x52,0x04,0x05,0x00,0x51, - 0x04,0x05,0x00,0x10,0x04,0x00,0x00,0x05,0x00,0xd2,0x0c,0x51,0x04,0x05,0x00,0x10, - 0x04,0x05,0x00,0x00,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x05,0x00,0x05,0x00,0xd3, - 0x10,0x52,0x04,0x05,0x00,0x91,0x08,0x10,0x04,0x05,0x00,0x00,0x00,0x05,0x00,0x52, - 0x04,0x05,0x00,0x91,0x08,0x10,0x04,0x05,0x00,0x00,0x00,0x05,0x00,0x54,0x04,0x05, - 0x00,0x53,0x04,0x05,0x00,0xd2,0x0c,0x51,0x04,0x05,0x00,0x10,0x04,0x00,0x00,0x05, - 0x00,0x51,0x04,0x05,0x00,0x10,0x04,0x05,0x00,0x00,0x00,0xcf,0x86,0x95,0x34,0xd4, - 0x20,0xd3,0x14,0x52,0x04,0x05,0x00,0xd1,0x08,0x10,0x04,0x05,0x00,0x00,0x00,0x10, - 0x04,0x05,0x00,0x00,0x00,0x92,0x08,0x11,0x04,0x00,0x00,0x05,0x00,0x05,0x00,0x93, - 0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x05,0x00,0x00,0x00,0x05,0x00,0x05,0x00,0x05, - 0x00,0x05,0x00,0xcf,0x06,0x05,0x00,0xd2,0x26,0xd1,0x06,0xcf,0x06,0x05,0x00,0xd0, - 0x1a,0xcf,0x86,0x55,0x04,0x05,0x00,0x94,0x10,0x93,0x0c,0x52,0x04,0x05,0x00,0x11, - 0x04,0x08,0x00,0x00,0x00,0x05,0x00,0x05,0x00,0xcf,0x06,0x05,0x00,0xd1,0x06,0xcf, - 0x06,0x05,0x00,0xd0,0x06,0xcf,0x06,0x05,0x00,0xcf,0x86,0x95,0x18,0x94,0x14,0x53, - 0x04,0x05,0x00,0xd2,0x08,0x11,0x04,0x05,0x00,0x09,0x00,0x11,0x04,0x00,0x00,0x05, - 0x00,0x05,0x00,0x05,0x00,0xd4,0x52,0xd3,0x06,0xcf,0x06,0x11,0x00,0xd2,0x46,0xd1, - 0x06,0xcf,0x06,0x11,0x00,0xd0,0x3a,0xcf,0x86,0xd5,0x20,0xd4,0x0c,0x53,0x04,0x11, - 0x00,0x12,0x04,0x11,0x00,0x00,0x00,0x53,0x04,0x00,0x00,0x92,0x0c,0x51,0x04,0x00, - 0x00,0x10,0x04,0x00,0x00,0x11,0x00,0x11,0x00,0x94,0x14,0x93,0x10,0x92,0x0c,0x91, - 0x08,0x10,0x04,0x00,0x00,0x11,0x00,0x11,0x00,0x11,0x00,0x11,0x00,0x00,0x00,0xcf, - 0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xe0,0xc2,0x03,0xcf,0x86, - 0xe5,0x03,0x01,0xd4,0xfc,0xd3,0xc0,0xd2,0x66,0xd1,0x60,0xd0,0x5a,0xcf,0x86,0xd5, - 0x2c,0xd4,0x14,0x93,0x10,0x52,0x04,0x12,0xe6,0x51,0x04,0x12,0xe6,0x10,0x04,0x12, - 0xe6,0x00,0x00,0x12,0xe6,0x53,0x04,0x12,0xe6,0x92,0x10,0xd1,0x08,0x10,0x04,0x12, - 0xe6,0x00,0x00,0x10,0x04,0x00,0x00,0x12,0xe6,0x12,0xe6,0x94,0x28,0xd3,0x18,0xd2, - 0x0c,0x51,0x04,0x12,0xe6,0x10,0x04,0x00,0x00,0x12,0xe6,0x91,0x08,0x10,0x04,0x12, - 0xe6,0x00,0x00,0x12,0xe6,0x92,0x0c,0x51,0x04,0x12,0xe6,0x10,0x04,0x12,0xe6,0x00, - 0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xd1,0x54,0xd0, - 0x36,0xcf,0x86,0x55,0x04,0x15,0x00,0xd4,0x14,0x53,0x04,0x15,0x00,0x52,0x04,0x15, - 0x00,0x91,0x08,0x10,0x04,0x15,0x00,0x00,0x00,0x00,0x00,0xd3,0x10,0x52,0x04,0x15, - 0xe6,0x51,0x04,0x15,0xe6,0x10,0x04,0x15,0xe6,0x15,0x00,0x52,0x04,0x15,0x00,0x11, - 0x04,0x15,0x00,0x00,0x00,0xcf,0x86,0x95,0x18,0x94,0x14,0x53,0x04,0x15,0x00,0xd2, - 0x08,0x11,0x04,0x15,0x00,0x00,0x00,0x11,0x04,0x00,0x00,0x15,0x00,0x00,0x00,0x00, - 0x00,0xcf,0x06,0x00,0x00,0xd2,0x36,0xd1,0x06,0xcf,0x06,0x00,0x00,0xd0,0x06,0xcf, - 0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x15,0x00,0xd4,0x0c,0x53,0x04,0x15,0x00,0x12, - 0x04,0x15,0x00,0x15,0xe6,0x53,0x04,0x15,0x00,0xd2,0x08,0x11,0x04,0x15,0x00,0x00, - 0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x15,0x00,0xcf,0x06,0x00,0x00,0xcf, - 0x06,0x00,0x00,0xd4,0x82,0xd3,0x7c,0xd2,0x3e,0xd1,0x06,0xcf,0x06,0x10,0x00,0xd0, - 0x06,0xcf,0x06,0x10,0x00,0xcf,0x86,0x95,0x2c,0xd4,0x18,0x93,0x14,0x52,0x04,0x10, - 0x00,0xd1,0x08,0x10,0x04,0x10,0x00,0x00,0x00,0x10,0x04,0x00,0x00,0x10,0x00,0x10, - 0x00,0x93,0x10,0x52,0x04,0x10,0xdc,0x51,0x04,0x10,0xdc,0x10,0x04,0x10,0xdc,0x00, - 0x00,0x00,0x00,0x00,0x00,0xd1,0x38,0xd0,0x06,0xcf,0x06,0x12,0x00,0xcf,0x86,0x95, - 0x2c,0xd4,0x18,0xd3,0x08,0x12,0x04,0x12,0x00,0x12,0xe6,0x92,0x0c,0x51,0x04,0x12, - 0xe6,0x10,0x04,0x12,0x07,0x15,0x00,0x00,0x00,0x53,0x04,0x12,0x00,0xd2,0x08,0x11, - 0x04,0x12,0x00,0x00,0x00,0x11,0x04,0x00,0x00,0x12,0x00,0x00,0x00,0xcf,0x06,0x00, - 0x00,0xcf,0x06,0x00,0x00,0xd3,0x82,0xd2,0x48,0xd1,0x24,0xd0,0x06,0xcf,0x06,0x00, - 0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x00,0x00,0x93,0x10,0x92,0x0c,0x91, - 0x08,0x10,0x04,0x00,0x00,0x14,0x00,0x14,0x00,0x14,0x00,0x14,0x00,0xd0,0x1e,0xcf, - 0x86,0x55,0x04,0x14,0x00,0x54,0x04,0x14,0x00,0x93,0x10,0x52,0x04,0x14,0x00,0x91, - 0x08,0x10,0x04,0x14,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xd1, - 0x34,0xd0,0x2e,0xcf,0x86,0xd5,0x18,0x94,0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10, - 0x04,0x00,0x00,0x15,0x00,0x15,0x00,0x15,0x00,0x15,0x00,0x15,0x00,0x54,0x04,0x15, - 0x00,0x53,0x04,0x15,0x00,0x52,0x04,0x15,0x00,0x11,0x04,0x15,0x00,0x00,0x00,0xcf, - 0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xe2,0xb2,0x01,0xe1,0x41,0x01,0xd0,0x6e,0xcf, - 0x86,0xd5,0x18,0x94,0x14,0x93,0x10,0x52,0x04,0x0d,0x00,0x91,0x08,0x10,0x04,0x00, - 0x00,0x0d,0x00,0x0d,0x00,0x0d,0x00,0x0d,0x00,0xd4,0x30,0xd3,0x20,0xd2,0x10,0xd1, - 0x08,0x10,0x04,0x00,0x00,0x0d,0x00,0x10,0x04,0x0d,0x00,0x00,0x00,0xd1,0x08,0x10, - 0x04,0x0d,0x00,0x00,0x00,0x10,0x04,0x00,0x00,0x0d,0x00,0x92,0x0c,0x91,0x08,0x10, - 0x04,0x00,0x00,0x0d,0x00,0x0d,0x00,0x0d,0x00,0xd3,0x10,0x92,0x0c,0x51,0x04,0x0d, - 0x00,0x10,0x04,0x0d,0x00,0x00,0x00,0x0d,0x00,0x92,0x10,0xd1,0x08,0x10,0x04,0x00, - 0x00,0x0d,0x00,0x10,0x04,0x00,0x00,0x0d,0x00,0x00,0x00,0xcf,0x86,0xd5,0x74,0xd4, - 0x34,0xd3,0x18,0xd2,0x0c,0x51,0x04,0x00,0x00,0x10,0x04,0x0d,0x00,0x00,0x00,0x51, - 0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x0d,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04,0x00, - 0x00,0x0d,0x00,0x10,0x04,0x00,0x00,0x0d,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x0d, - 0x00,0x0d,0x00,0xd3,0x20,0xd2,0x10,0xd1,0x08,0x10,0x04,0x00,0x00,0x0d,0x00,0x10, - 0x04,0x0d,0x00,0x00,0x00,0xd1,0x08,0x10,0x04,0x0d,0x00,0x00,0x00,0x10,0x04,0x00, - 0x00,0x0d,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04,0x00,0x00,0x0d,0x00,0x10,0x04,0x00, - 0x00,0x0d,0x00,0xd1,0x08,0x10,0x04,0x00,0x00,0x0d,0x00,0x10,0x04,0x00,0x00,0x0d, - 0x00,0xd4,0x30,0xd3,0x20,0xd2,0x10,0xd1,0x08,0x10,0x04,0x00,0x00,0x0d,0x00,0x10, - 0x04,0x0d,0x00,0x00,0x00,0xd1,0x08,0x10,0x04,0x0d,0x00,0x00,0x00,0x10,0x04,0x00, - 0x00,0x0d,0x00,0x92,0x0c,0x51,0x04,0x0d,0x00,0x10,0x04,0x0d,0x00,0x00,0x00,0x0d, - 0x00,0xd3,0x10,0x92,0x0c,0x51,0x04,0x0d,0x00,0x10,0x04,0x0d,0x00,0x00,0x00,0x0d, - 0x00,0xd2,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x0d,0x00,0x0d,0x00,0xd1,0x08,0x10, - 0x04,0x0d,0x00,0x00,0x00,0x10,0x04,0x0d,0x00,0x00,0x00,0xd0,0x56,0xcf,0x86,0xd5, - 0x20,0xd4,0x14,0x53,0x04,0x0d,0x00,0x92,0x0c,0x51,0x04,0x0d,0x00,0x10,0x04,0x00, - 0x00,0x0d,0x00,0x0d,0x00,0x53,0x04,0x0d,0x00,0x12,0x04,0x0d,0x00,0x00,0x00,0xd4, - 0x28,0xd3,0x18,0xd2,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x0d,0x00,0x0d,0x00,0x91, - 0x08,0x10,0x04,0x00,0x00,0x0d,0x00,0x0d,0x00,0x92,0x0c,0x51,0x04,0x0d,0x00,0x10, - 0x04,0x00,0x00,0x0d,0x00,0x0d,0x00,0x53,0x04,0x0d,0x00,0x12,0x04,0x0d,0x00,0x00, - 0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x00,0x00,0x93,0x0c,0x92,0x08,0x11, - 0x04,0x0d,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x86,0xe5, - 0x96,0x05,0xe4,0x28,0x03,0xe3,0xed,0x01,0xd2,0xa0,0xd1,0x1c,0xd0,0x16,0xcf,0x86, - 0x55,0x04,0x0a,0x00,0x94,0x0c,0x53,0x04,0x0a,0x00,0x12,0x04,0x0a,0x00,0x00,0x00, - 0x0a,0x00,0xcf,0x06,0x0a,0x00,0xd0,0x46,0xcf,0x86,0xd5,0x10,0x54,0x04,0x0a,0x00, - 0x93,0x08,0x12,0x04,0x0a,0x00,0x00,0x00,0x00,0x00,0xd4,0x14,0x53,0x04,0x0c,0x00, - 0x52,0x04,0x0c,0x00,0x51,0x04,0x0c,0x00,0x10,0x04,0x0c,0x00,0x00,0x00,0xd3,0x10, - 0x92,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x0c,0x00,0x0c,0x00,0x0c,0x00,0x52,0x04, - 0x0c,0x00,0x51,0x04,0x0c,0x00,0x10,0x04,0x0c,0x00,0x10,0x00,0xcf,0x86,0xd5,0x28, - 0xd4,0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x0c,0x00,0x0c,0x00, - 0x0c,0x00,0x0c,0x00,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x0c,0x00, - 0x0c,0x00,0x0c,0x00,0x0c,0x00,0x54,0x04,0x10,0x00,0x93,0x0c,0x52,0x04,0x10,0x00, - 0x11,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0xd1,0xe4,0xd0,0x5a,0xcf,0x86,0xd5,0x20, - 0x94,0x1c,0x53,0x04,0x0b,0x00,0xd2,0x0c,0x51,0x04,0x0b,0x00,0x10,0x04,0x0b,0x00, - 0x10,0x00,0x91,0x08,0x10,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0x0b,0x00,0xd4,0x14, - 0x53,0x04,0x0b,0x00,0x52,0x04,0x0b,0x00,0x51,0x04,0x0b,0x00,0x10,0x04,0x0b,0x00, - 0x14,0x00,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x0c,0x00,0x0b,0x00,0x0c,0x00, - 0x0c,0x00,0x52,0x04,0x0c,0x00,0xd1,0x08,0x10,0x04,0x0c,0x00,0x0b,0x00,0x10,0x04, - 0x0c,0x00,0x0b,0x00,0xcf,0x86,0xd5,0x4c,0xd4,0x2c,0xd3,0x18,0xd2,0x0c,0x51,0x04, - 0x0c,0x00,0x10,0x04,0x0b,0x00,0x0c,0x00,0x51,0x04,0x0c,0x00,0x10,0x04,0x0b,0x00, - 0x0c,0x00,0xd2,0x08,0x11,0x04,0x0c,0x00,0x0b,0x00,0x51,0x04,0x0b,0x00,0x10,0x04, - 0x0b,0x00,0x0c,0x00,0xd3,0x10,0x52,0x04,0x0c,0x00,0x51,0x04,0x0c,0x00,0x10,0x04, - 0x0c,0x00,0x0b,0x00,0x52,0x04,0x0c,0x00,0x51,0x04,0x0c,0x00,0x10,0x04,0x0c,0x00, - 0x0b,0x00,0xd4,0x18,0x53,0x04,0x0c,0x00,0xd2,0x08,0x11,0x04,0x0c,0x00,0x0d,0x00, - 0x91,0x08,0x10,0x04,0x15,0x00,0x00,0x00,0x00,0x00,0x53,0x04,0x0c,0x00,0xd2,0x10, - 0xd1,0x08,0x10,0x04,0x0c,0x00,0x0b,0x00,0x10,0x04,0x0c,0x00,0x0b,0x00,0xd1,0x08, - 0x10,0x04,0x0b,0x00,0x0c,0x00,0x10,0x04,0x0c,0x00,0x0b,0x00,0xd0,0x4e,0xcf,0x86, - 0xd5,0x34,0xd4,0x14,0x53,0x04,0x0c,0x00,0xd2,0x08,0x11,0x04,0x0c,0x00,0x0b,0x00, - 0x11,0x04,0x0b,0x00,0x0c,0x00,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x0b,0x00, - 0x0c,0x00,0x0c,0x00,0x0c,0x00,0x92,0x0c,0x51,0x04,0x0c,0x00,0x10,0x04,0x0c,0x00, - 0x12,0x00,0x12,0x00,0x94,0x14,0x53,0x04,0x12,0x00,0x52,0x04,0x12,0x00,0x91,0x08, - 0x10,0x04,0x12,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00, - 0x94,0x10,0x93,0x0c,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x0c,0x00,0x0c,0x00, - 0x0c,0x00,0xd2,0x7e,0xd1,0x78,0xd0,0x3e,0xcf,0x86,0xd5,0x1c,0x94,0x18,0x93,0x14, - 0x92,0x10,0xd1,0x08,0x10,0x04,0x0b,0x00,0x0c,0x00,0x10,0x04,0x0c,0x00,0x00,0x00, - 0x00,0x00,0x00,0x00,0x0b,0x00,0x54,0x04,0x0b,0x00,0xd3,0x0c,0x92,0x08,0x11,0x04, - 0x0b,0x00,0x0c,0x00,0x0c,0x00,0x92,0x0c,0x51,0x04,0x0c,0x00,0x10,0x04,0x0c,0x00, - 0x12,0x00,0x00,0x00,0xcf,0x86,0xd5,0x24,0xd4,0x14,0x53,0x04,0x0b,0x00,0x92,0x0c, - 0x91,0x08,0x10,0x04,0x0b,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x93,0x0c,0x92,0x08, - 0x11,0x04,0x0c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x94,0x10,0x93,0x0c,0x52,0x04, - 0x13,0x00,0x11,0x04,0x13,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00, - 0xd1,0x58,0xd0,0x3a,0xcf,0x86,0x55,0x04,0x0c,0x00,0xd4,0x20,0xd3,0x10,0x92,0x0c, - 0x91,0x08,0x10,0x04,0x0c,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x52,0x04,0x10,0x00, - 0x91,0x08,0x10,0x04,0x10,0x00,0x11,0x00,0x11,0x00,0x93,0x10,0x52,0x04,0x0c,0x00, - 0x51,0x04,0x0c,0x00,0x10,0x04,0x10,0x00,0x0c,0x00,0x0c,0x00,0xcf,0x86,0x55,0x04, - 0x0c,0x00,0x54,0x04,0x0c,0x00,0x53,0x04,0x0c,0x00,0x52,0x04,0x0c,0x00,0x91,0x08, - 0x10,0x04,0x0c,0x00,0x10,0x00,0x11,0x00,0xd0,0x16,0xcf,0x86,0x95,0x10,0x54,0x04, - 0x0c,0x00,0x93,0x08,0x12,0x04,0x0c,0x00,0x10,0x00,0x10,0x00,0x0c,0x00,0xcf,0x86, - 0xd5,0x34,0xd4,0x28,0xd3,0x10,0x52,0x04,0x0c,0x00,0x91,0x08,0x10,0x04,0x0c,0x00, - 0x10,0x00,0x0c,0x00,0xd2,0x0c,0x51,0x04,0x0c,0x00,0x10,0x04,0x0c,0x00,0x10,0x00, - 0x51,0x04,0x10,0x00,0x10,0x04,0x10,0x00,0x11,0x00,0x93,0x08,0x12,0x04,0x11,0x00, - 0x10,0x00,0x10,0x00,0x54,0x04,0x0c,0x00,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04, - 0x0c,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x11,0x00,0xd3,0xfc,0xd2,0x6c,0xd1,0x3c, - 0xd0,0x1e,0xcf,0x86,0x55,0x04,0x0c,0x00,0x54,0x04,0x0c,0x00,0x53,0x04,0x0c,0x00, - 0x52,0x04,0x0c,0x00,0x51,0x04,0x0c,0x00,0x10,0x04,0x0c,0x00,0x10,0x00,0xcf,0x86, - 0x95,0x18,0x94,0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x0c,0x00,0x10,0x00, - 0x0c,0x00,0x0c,0x00,0x0c,0x00,0x0c,0x00,0x0c,0x00,0xd0,0x06,0xcf,0x06,0x0c,0x00, - 0xcf,0x86,0x55,0x04,0x0c,0x00,0x54,0x04,0x0c,0x00,0x53,0x04,0x0c,0x00,0xd2,0x0c, - 0x91,0x08,0x10,0x04,0x10,0x00,0x0c,0x00,0x0c,0x00,0xd1,0x08,0x10,0x04,0x0c,0x00, - 0x10,0x00,0x10,0x04,0x10,0x00,0x11,0x00,0xd1,0x54,0xd0,0x1a,0xcf,0x86,0x55,0x04, - 0x0c,0x00,0x54,0x04,0x0c,0x00,0x53,0x04,0x0c,0x00,0x52,0x04,0x0c,0x00,0x11,0x04, - 0x0c,0x00,0x10,0x00,0xcf,0x86,0xd5,0x1c,0x94,0x18,0xd3,0x08,0x12,0x04,0x0d,0x00, - 0x10,0x00,0x92,0x0c,0x51,0x04,0x10,0x00,0x10,0x04,0x10,0x00,0x11,0x00,0x11,0x00, - 0x0c,0x00,0xd4,0x08,0x13,0x04,0x0c,0x00,0x10,0x00,0x53,0x04,0x10,0x00,0x92,0x0c, - 0x51,0x04,0x10,0x00,0x10,0x04,0x12,0x00,0x10,0x00,0x10,0x00,0xd0,0x1e,0xcf,0x86, - 0x55,0x04,0x10,0x00,0x94,0x14,0x93,0x10,0x52,0x04,0x10,0x00,0x91,0x08,0x10,0x04, - 0x12,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0xcf,0x86,0x55,0x04,0x10,0x00, - 0x54,0x04,0x10,0x00,0x53,0x04,0x10,0x00,0x92,0x0c,0x51,0x04,0x10,0x00,0x10,0x04, - 0x10,0x00,0x0c,0x00,0x0c,0x00,0xe2,0x19,0x01,0xd1,0xa8,0xd0,0x7e,0xcf,0x86,0xd5, - 0x4c,0xd4,0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x0d,0x00,0x0c,0x00,0x0c, - 0x00,0x0c,0x00,0x0c,0x00,0xd3,0x1c,0xd2,0x0c,0x91,0x08,0x10,0x04,0x0c,0x00,0x0d, - 0x00,0x0c,0x00,0xd1,0x08,0x10,0x04,0x0c,0x00,0x0d,0x00,0x10,0x04,0x0c,0x00,0x0d, - 0x00,0xd2,0x10,0xd1,0x08,0x10,0x04,0x0c,0x00,0x0d,0x00,0x10,0x04,0x0c,0x00,0x0d, - 0x00,0x51,0x04,0x0c,0x00,0x10,0x04,0x0c,0x00,0x0d,0x00,0xd4,0x1c,0xd3,0x0c,0x52, - 0x04,0x0c,0x00,0x11,0x04,0x0c,0x00,0x0d,0x00,0x52,0x04,0x0c,0x00,0x91,0x08,0x10, - 0x04,0x0d,0x00,0x0c,0x00,0x0d,0x00,0x93,0x10,0x52,0x04,0x0c,0x00,0x91,0x08,0x10, - 0x04,0x0d,0x00,0x0c,0x00,0x0c,0x00,0x0c,0x00,0xcf,0x86,0x95,0x24,0x94,0x20,0x93, - 0x1c,0xd2,0x10,0xd1,0x08,0x10,0x04,0x0c,0x00,0x10,0x00,0x10,0x04,0x10,0x00,0x11, - 0x00,0x91,0x08,0x10,0x04,0x11,0x00,0x0c,0x00,0x0c,0x00,0x0c,0x00,0x10,0x00,0x10, - 0x00,0xd0,0x06,0xcf,0x06,0x0c,0x00,0xcf,0x86,0xd5,0x30,0xd4,0x10,0x93,0x0c,0x52, - 0x04,0x0c,0x00,0x11,0x04,0x0c,0x00,0x10,0x00,0x10,0x00,0x93,0x1c,0xd2,0x10,0xd1, - 0x08,0x10,0x04,0x11,0x00,0x12,0x00,0x10,0x04,0x12,0x00,0x13,0x00,0x91,0x08,0x10, - 0x04,0x13,0x00,0x15,0x00,0x00,0x00,0x00,0x00,0xd4,0x14,0x53,0x04,0x10,0x00,0x52, - 0x04,0x10,0x00,0x91,0x08,0x10,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0xd3,0x10,0x52, - 0x04,0x10,0x00,0x51,0x04,0x12,0x00,0x10,0x04,0x12,0x00,0x13,0x00,0x92,0x10,0xd1, - 0x08,0x10,0x04,0x13,0x00,0x14,0x00,0x10,0x04,0x15,0x00,0x00,0x00,0x00,0x00,0xd1, - 0x1c,0xd0,0x06,0xcf,0x06,0x0c,0x00,0xcf,0x86,0x55,0x04,0x0c,0x00,0x54,0x04,0x0c, - 0x00,0x93,0x08,0x12,0x04,0x0c,0x00,0x00,0x00,0x00,0x00,0xd0,0x06,0xcf,0x06,0x10, - 0x00,0xcf,0x86,0xd5,0x24,0x54,0x04,0x10,0x00,0xd3,0x10,0x52,0x04,0x10,0x00,0x91, - 0x08,0x10,0x04,0x10,0x00,0x14,0x00,0x14,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x14, - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x94,0x0c,0x53,0x04,0x15,0x00,0x12,0x04,0x15, - 0x00,0x00,0x00,0x00,0x00,0xe4,0x40,0x02,0xe3,0xc9,0x01,0xd2,0x5c,0xd1,0x34,0xd0, - 0x16,0xcf,0x86,0x95,0x10,0x94,0x0c,0x53,0x04,0x10,0x00,0x12,0x04,0x10,0x00,0x00, - 0x00,0x10,0x00,0x10,0x00,0xcf,0x86,0x95,0x18,0xd4,0x08,0x13,0x04,0x10,0x00,0x00, - 0x00,0x53,0x04,0x10,0x00,0x92,0x08,0x11,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0x10, - 0x00,0xd0,0x22,0xcf,0x86,0xd5,0x0c,0x94,0x08,0x13,0x04,0x10,0x00,0x00,0x00,0x10, - 0x00,0x94,0x10,0x53,0x04,0x10,0x00,0x52,0x04,0x10,0x00,0x11,0x04,0x10,0x00,0x00, - 0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xd1,0xc0,0xd0,0x5e,0xcf,0x86,0xd5,0x30,0xd4, - 0x14,0x53,0x04,0x13,0x00,0x52,0x04,0x13,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x15, - 0x00,0x15,0x00,0x53,0x04,0x11,0x00,0xd2,0x0c,0x91,0x08,0x10,0x04,0x11,0x00,0x12, - 0x00,0x12,0x00,0x51,0x04,0x12,0x00,0x10,0x04,0x12,0x00,0x13,0x00,0xd4,0x08,0x13, - 0x04,0x12,0x00,0x13,0x00,0xd3,0x14,0x92,0x10,0xd1,0x08,0x10,0x04,0x12,0x00,0x13, - 0x00,0x10,0x04,0x13,0x00,0x12,0x00,0x12,0x00,0x52,0x04,0x12,0x00,0x51,0x04,0x12, - 0x00,0x10,0x04,0x12,0x00,0x15,0x00,0xcf,0x86,0xd5,0x28,0xd4,0x14,0x53,0x04,0x12, - 0x00,0x52,0x04,0x12,0x00,0x91,0x08,0x10,0x04,0x13,0x00,0x14,0x00,0x14,0x00,0x53, - 0x04,0x12,0x00,0x52,0x04,0x12,0x00,0x51,0x04,0x12,0x00,0x10,0x04,0x12,0x00,0x13, - 0x00,0xd4,0x0c,0x53,0x04,0x13,0x00,0x12,0x04,0x13,0x00,0x14,0x00,0xd3,0x1c,0xd2, - 0x10,0xd1,0x08,0x10,0x04,0x14,0x00,0x15,0x00,0x10,0x04,0x00,0x00,0x14,0x00,0x51, - 0x04,0x14,0x00,0x10,0x04,0x14,0x00,0x00,0x00,0x92,0x0c,0x51,0x04,0x00,0x00,0x10, - 0x04,0x14,0x00,0x15,0x00,0x14,0x00,0xd0,0x62,0xcf,0x86,0xd5,0x24,0xd4,0x14,0x93, - 0x10,0x52,0x04,0x11,0x00,0x91,0x08,0x10,0x04,0x11,0x00,0x12,0x00,0x12,0x00,0x12, - 0x00,0x93,0x0c,0x92,0x08,0x11,0x04,0x12,0x00,0x13,0x00,0x13,0x00,0x14,0x00,0xd4, - 0x2c,0xd3,0x18,0xd2,0x0c,0x51,0x04,0x14,0x00,0x10,0x04,0x14,0x00,0x00,0x00,0x91, - 0x08,0x10,0x04,0x00,0x00,0x15,0x00,0x15,0x00,0xd2,0x0c,0x51,0x04,0x15,0x00,0x10, - 0x04,0x15,0x00,0x00,0x00,0x11,0x04,0x00,0x00,0x15,0x00,0x53,0x04,0x14,0x00,0x92, - 0x08,0x11,0x04,0x14,0x00,0x15,0x00,0x15,0x00,0xcf,0x86,0xd5,0x30,0x94,0x2c,0xd3, - 0x14,0x92,0x10,0xd1,0x08,0x10,0x04,0x11,0x00,0x14,0x00,0x10,0x04,0x14,0x00,0x15, - 0x00,0x15,0x00,0xd2,0x0c,0x51,0x04,0x15,0x00,0x10,0x04,0x15,0x00,0x00,0x00,0x91, - 0x08,0x10,0x04,0x00,0x00,0x15,0x00,0x15,0x00,0x13,0x00,0x94,0x14,0x93,0x10,0x52, - 0x04,0x13,0x00,0x51,0x04,0x13,0x00,0x10,0x04,0x13,0x00,0x14,0x00,0x14,0x00,0x14, - 0x00,0xd2,0x70,0xd1,0x40,0xd0,0x06,0xcf,0x06,0x15,0x00,0xcf,0x86,0xd5,0x10,0x54, - 0x04,0x15,0x00,0x93,0x08,0x12,0x04,0x15,0x00,0x00,0x00,0x00,0x00,0xd4,0x10,0x53, - 0x04,0x14,0x00,0x52,0x04,0x14,0x00,0x11,0x04,0x14,0x00,0x00,0x00,0xd3,0x08,0x12, - 0x04,0x15,0x00,0x00,0x00,0x92,0x0c,0x51,0x04,0x15,0x00,0x10,0x04,0x15,0x00,0x00, - 0x00,0x00,0x00,0xd0,0x2a,0xcf,0x86,0x95,0x24,0xd4,0x14,0x93,0x10,0x92,0x0c,0x51, - 0x04,0x15,0x00,0x10,0x04,0x15,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x93,0x0c,0x52, - 0x04,0x15,0x00,0x11,0x04,0x15,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00, - 0x00,0xcf,0x06,0x00,0x00,0xd3,0x06,0xcf,0x06,0x00,0x00,0xd2,0x06,0xcf,0x06,0x00, - 0x00,0xd1,0x06,0xcf,0x06,0x00,0x00,0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55, - 0x04,0x00,0x00,0x54,0x04,0x00,0x00,0x53,0x04,0x00,0x00,0x52,0x04,0x00,0x00,0x11, - 0x04,0x00,0x00,0x02,0x00,0xe4,0xf9,0x12,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x05,0x00, - 0xd2,0xc2,0xd1,0x08,0xcf,0x86,0xcf,0x06,0x05,0x00,0xd0,0x44,0xcf,0x86,0xd5,0x3c, - 0xd4,0x06,0xcf,0x06,0x05,0x00,0xd3,0x06,0xcf,0x06,0x05,0x00,0xd2,0x2a,0xd1,0x06, - 0xcf,0x06,0x05,0x00,0xd0,0x06,0xcf,0x06,0x05,0x00,0xcf,0x86,0x95,0x18,0x54,0x04, - 0x05,0x00,0x93,0x10,0x52,0x04,0x05,0x00,0x51,0x04,0x05,0x00,0x10,0x04,0x05,0x00, - 0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x0b,0x00,0xcf,0x06,0x0b,0x00,0xcf,0x86, - 0xd5,0x3c,0xd4,0x06,0xcf,0x06,0x0b,0x00,0xd3,0x06,0xcf,0x06,0x0b,0x00,0xd2,0x06, - 0xcf,0x06,0x0b,0x00,0xd1,0x24,0xd0,0x1e,0xcf,0x86,0x55,0x04,0x0b,0x00,0x54,0x04, - 0x0b,0x00,0x93,0x10,0x52,0x04,0x0b,0x00,0x91,0x08,0x10,0x04,0x0b,0x00,0x00,0x00, - 0x00,0x00,0x00,0x00,0xcf,0x06,0x0c,0x00,0xcf,0x06,0x0c,0x00,0xd4,0x32,0xd3,0x2c, - 0xd2,0x26,0xd1,0x20,0xd0,0x1a,0xcf,0x86,0x95,0x14,0x54,0x04,0x0c,0x00,0x53,0x04, - 0x0c,0x00,0x52,0x04,0x0c,0x00,0x11,0x04,0x0c,0x00,0x00,0x00,0x11,0x00,0xcf,0x06, - 0x11,0x00,0xcf,0x06,0x11,0x00,0xcf,0x06,0x11,0x00,0xcf,0x06,0x11,0x00,0xcf,0x06, - 0x11,0x00,0xd1,0x48,0xd0,0x40,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x11,0x00,0xd4,0x06, - 0xcf,0x06,0x11,0x00,0xd3,0x06,0xcf,0x06,0x11,0x00,0xd2,0x26,0xd1,0x06,0xcf,0x06, - 0x11,0x00,0xd0,0x1a,0xcf,0x86,0x55,0x04,0x11,0x00,0x94,0x10,0x93,0x0c,0x92,0x08, - 0x11,0x04,0x11,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x13,0x00,0xcf,0x06,0x13,0x00, - 0xcf,0x06,0x13,0x00,0xcf,0x86,0xcf,0x06,0x13,0x00,0xd0,0x44,0xcf,0x86,0xd5,0x06, - 0xcf,0x06,0x13,0x00,0xd4,0x36,0xd3,0x06,0xcf,0x06,0x13,0x00,0xd2,0x06,0xcf,0x06, - 0x13,0x00,0xd1,0x06,0xcf,0x06,0x13,0x00,0xd0,0x06,0xcf,0x06,0x13,0x00,0xcf,0x86, - 0x55,0x04,0x13,0x00,0x94,0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x13,0x00, - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x86, - 0xd5,0x06,0xcf,0x06,0x00,0x00,0xe4,0x68,0x11,0xe3,0x51,0x10,0xe2,0x17,0x08,0xe1, - 0x06,0x04,0xe0,0x03,0x02,0xcf,0x86,0xe5,0x06,0x01,0xd4,0x82,0xd3,0x41,0xd2,0x21, - 0xd1,0x10,0x10,0x08,0x05,0xff,0xe4,0xb8,0xbd,0x00,0x05,0xff,0xe4,0xb8,0xb8,0x00, - 0x10,0x08,0x05,0xff,0xe4,0xb9,0x81,0x00,0x05,0xff,0xf0,0xa0,0x84,0xa2,0x00,0xd1, - 0x10,0x10,0x08,0x05,0xff,0xe4,0xbd,0xa0,0x00,0x05,0xff,0xe4,0xbe,0xae,0x00,0x10, - 0x08,0x05,0xff,0xe4,0xbe,0xbb,0x00,0x05,0xff,0xe5,0x80,0x82,0x00,0xd2,0x20,0xd1, - 0x10,0x10,0x08,0x05,0xff,0xe5,0x81,0xba,0x00,0x05,0xff,0xe5,0x82,0x99,0x00,0x10, - 0x08,0x05,0xff,0xe5,0x83,0xa7,0x00,0x05,0xff,0xe5,0x83,0x8f,0x00,0xd1,0x11,0x10, - 0x08,0x05,0xff,0xe3,0x92,0x9e,0x00,0x05,0xff,0xf0,0xa0,0x98,0xba,0x00,0x10,0x08, - 0x05,0xff,0xe5,0x85,0x8d,0x00,0x05,0xff,0xe5,0x85,0x94,0x00,0xd3,0x42,0xd2,0x21, - 0xd1,0x10,0x10,0x08,0x05,0xff,0xe5,0x85,0xa4,0x00,0x05,0xff,0xe5,0x85,0xb7,0x00, - 0x10,0x09,0x05,0xff,0xf0,0xa0,0x94,0x9c,0x00,0x05,0xff,0xe3,0x92,0xb9,0x00,0xd1, - 0x10,0x10,0x08,0x05,0xff,0xe5,0x85,0xa7,0x00,0x05,0xff,0xe5,0x86,0x8d,0x00,0x10, - 0x09,0x05,0xff,0xf0,0xa0,0x95,0x8b,0x00,0x05,0xff,0xe5,0x86,0x97,0x00,0xd2,0x20, - 0xd1,0x10,0x10,0x08,0x05,0xff,0xe5,0x86,0xa4,0x00,0x05,0xff,0xe4,0xbb,0x8c,0x00, - 0x10,0x08,0x05,0xff,0xe5,0x86,0xac,0x00,0x05,0xff,0xe5,0x86,0xb5,0x00,0xd1,0x11, - 0x10,0x09,0x05,0xff,0xf0,0xa9,0x87,0x9f,0x00,0x05,0xff,0xe5,0x87,0xb5,0x00,0x10, - 0x08,0x05,0xff,0xe5,0x88,0x83,0x00,0x05,0xff,0xe3,0x93,0x9f,0x00,0xd4,0x80,0xd3, - 0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe5,0x88,0xbb,0x00,0x05,0xff,0xe5, - 0x89,0x86,0x00,0x10,0x08,0x05,0xff,0xe5,0x89,0xb2,0x00,0x05,0xff,0xe5,0x89,0xb7, - 0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe3,0x94,0x95,0x00,0x05,0xff,0xe5,0x8b,0x87, - 0x00,0x10,0x08,0x05,0xff,0xe5,0x8b,0x89,0x00,0x05,0xff,0xe5,0x8b,0xa4,0x00,0xd2, - 0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe5,0x8b,0xba,0x00,0x05,0xff,0xe5,0x8c,0x85, - 0x00,0x10,0x08,0x05,0xff,0xe5,0x8c,0x86,0x00,0x05,0xff,0xe5,0x8c,0x97,0x00,0xd1, - 0x10,0x10,0x08,0x05,0xff,0xe5,0x8d,0x89,0x00,0x05,0xff,0xe5,0x8d,0x91,0x00,0x10, - 0x08,0x05,0xff,0xe5,0x8d,0x9a,0x00,0x05,0xff,0xe5,0x8d,0xb3,0x00,0xd3,0x39,0xd2, - 0x18,0x91,0x10,0x10,0x08,0x05,0xff,0xe5,0x8d,0xbd,0x00,0x05,0xff,0xe5,0x8d,0xbf, - 0x00,0x05,0xff,0xe5,0x8d,0xbf,0x00,0xd1,0x11,0x10,0x09,0x05,0xff,0xf0,0xa0,0xa8, - 0xac,0x00,0x05,0xff,0xe7,0x81,0xb0,0x00,0x10,0x08,0x05,0xff,0xe5,0x8f,0x8a,0x00, - 0x05,0xff,0xe5,0x8f,0x9f,0x00,0xd2,0x21,0xd1,0x11,0x10,0x09,0x05,0xff,0xf0,0xa0, - 0xad,0xa3,0x00,0x05,0xff,0xe5,0x8f,0xab,0x00,0x10,0x08,0x05,0xff,0xe5,0x8f,0xb1, - 0x00,0x05,0xff,0xe5,0x90,0x86,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe5,0x92,0x9e, - 0x00,0x05,0xff,0xe5,0x90,0xb8,0x00,0x10,0x08,0x05,0xff,0xe5,0x91,0x88,0x00,0x05, - 0xff,0xe5,0x91,0xa8,0x00,0xcf,0x86,0xe5,0x02,0x01,0xd4,0x80,0xd3,0x40,0xd2,0x20, - 0xd1,0x10,0x10,0x08,0x05,0xff,0xe5,0x92,0xa2,0x00,0x05,0xff,0xe5,0x93,0xb6,0x00, - 0x10,0x08,0x05,0xff,0xe5,0x94,0x90,0x00,0x05,0xff,0xe5,0x95,0x93,0x00,0xd1,0x10, - 0x10,0x08,0x05,0xff,0xe5,0x95,0xa3,0x00,0x05,0xff,0xe5,0x96,0x84,0x00,0x10,0x08, - 0x05,0xff,0xe5,0x96,0x84,0x00,0x05,0xff,0xe5,0x96,0x99,0x00,0xd2,0x20,0xd1,0x10, - 0x10,0x08,0x05,0xff,0xe5,0x96,0xab,0x00,0x05,0xff,0xe5,0x96,0xb3,0x00,0x10,0x08, - 0x05,0xff,0xe5,0x97,0x82,0x00,0x05,0xff,0xe5,0x9c,0x96,0x00,0xd1,0x10,0x10,0x08, - 0x05,0xff,0xe5,0x98,0x86,0x00,0x05,0xff,0xe5,0x9c,0x97,0x00,0x10,0x08,0x05,0xff, - 0xe5,0x99,0x91,0x00,0x05,0xff,0xe5,0x99,0xb4,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10, - 0x10,0x08,0x05,0xff,0xe5,0x88,0x87,0x00,0x05,0xff,0xe5,0xa3,0xae,0x00,0x10,0x08, - 0x05,0xff,0xe5,0x9f,0x8e,0x00,0x05,0xff,0xe5,0x9f,0xb4,0x00,0xd1,0x10,0x10,0x08, - 0x05,0xff,0xe5,0xa0,0x8d,0x00,0x05,0xff,0xe5,0x9e,0x8b,0x00,0x10,0x08,0x05,0xff, - 0xe5,0xa0,0xb2,0x00,0x05,0xff,0xe5,0xa0,0xb1,0x00,0xd2,0x21,0xd1,0x11,0x10,0x08, - 0x05,0xff,0xe5,0xa2,0xac,0x00,0x05,0xff,0xf0,0xa1,0x93,0xa4,0x00,0x10,0x08,0x05, - 0xff,0xe5,0xa3,0xb2,0x00,0x05,0xff,0xe5,0xa3,0xb7,0x00,0xd1,0x10,0x10,0x08,0x05, - 0xff,0xe5,0xa4,0x86,0x00,0x05,0xff,0xe5,0xa4,0x9a,0x00,0x10,0x08,0x05,0xff,0xe5, - 0xa4,0xa2,0x00,0x05,0xff,0xe5,0xa5,0xa2,0x00,0xd4,0x7b,0xd3,0x42,0xd2,0x22,0xd1, - 0x12,0x10,0x09,0x05,0xff,0xf0,0xa1,0x9a,0xa8,0x00,0x05,0xff,0xf0,0xa1,0x9b,0xaa, - 0x00,0x10,0x08,0x05,0xff,0xe5,0xa7,0xac,0x00,0x05,0xff,0xe5,0xa8,0x9b,0x00,0xd1, - 0x10,0x10,0x08,0x05,0xff,0xe5,0xa8,0xa7,0x00,0x05,0xff,0xe5,0xa7,0x98,0x00,0x10, - 0x08,0x05,0xff,0xe5,0xa9,0xa6,0x00,0x05,0xff,0xe3,0x9b,0xae,0x00,0xd2,0x18,0x91, - 0x10,0x10,0x08,0x05,0xff,0xe3,0x9b,0xbc,0x00,0x05,0xff,0xe5,0xac,0x88,0x00,0x05, - 0xff,0xe5,0xac,0xbe,0x00,0xd1,0x11,0x10,0x09,0x05,0xff,0xf0,0xa1,0xa7,0x88,0x00, - 0x05,0xff,0xe5,0xaf,0x83,0x00,0x10,0x08,0x05,0xff,0xe5,0xaf,0x98,0x00,0x05,0xff, - 0xe5,0xaf,0xa7,0x00,0xd3,0x41,0xd2,0x21,0xd1,0x11,0x10,0x08,0x05,0xff,0xe5,0xaf, - 0xb3,0x00,0x05,0xff,0xf0,0xa1,0xac,0x98,0x00,0x10,0x08,0x05,0xff,0xe5,0xaf,0xbf, - 0x00,0x05,0xff,0xe5,0xb0,0x86,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe5,0xbd,0x93, - 0x00,0x05,0xff,0xe5,0xb0,0xa2,0x00,0x10,0x08,0x05,0xff,0xe3,0x9e,0x81,0x00,0x05, - 0xff,0xe5,0xb1,0xa0,0x00,0xd2,0x21,0xd1,0x10,0x10,0x08,0x05,0xff,0xe5,0xb1,0xae, - 0x00,0x05,0xff,0xe5,0xb3,0x80,0x00,0x10,0x08,0x05,0xff,0xe5,0xb2,0x8d,0x00,0x05, - 0xff,0xf0,0xa1,0xb7,0xa4,0x00,0xd1,0x11,0x10,0x08,0x05,0xff,0xe5,0xb5,0x83,0x00, - 0x05,0xff,0xf0,0xa1,0xb7,0xa6,0x00,0x10,0x08,0x05,0xff,0xe5,0xb5,0xae,0x00,0x05, - 0xff,0xe5,0xb5,0xab,0x00,0xe0,0x04,0x02,0xcf,0x86,0xd5,0xfe,0xd4,0x82,0xd3,0x40, - 0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe5,0xb5,0xbc,0x00,0x05,0xff,0xe5,0xb7, - 0xa1,0x00,0x10,0x08,0x05,0xff,0xe5,0xb7,0xa2,0x00,0x05,0xff,0xe3,0xa0,0xaf,0x00, - 0xd1,0x10,0x10,0x08,0x05,0xff,0xe5,0xb7,0xbd,0x00,0x05,0xff,0xe5,0xb8,0xa8,0x00, - 0x10,0x08,0x05,0xff,0xe5,0xb8,0xbd,0x00,0x05,0xff,0xe5,0xb9,0xa9,0x00,0xd2,0x21, - 0xd1,0x11,0x10,0x08,0x05,0xff,0xe3,0xa1,0xa2,0x00,0x05,0xff,0xf0,0xa2,0x86,0x83, - 0x00,0x10,0x08,0x05,0xff,0xe3,0xa1,0xbc,0x00,0x05,0xff,0xe5,0xba,0xb0,0x00,0xd1, - 0x10,0x10,0x08,0x05,0xff,0xe5,0xba,0xb3,0x00,0x05,0xff,0xe5,0xba,0xb6,0x00,0x10, - 0x08,0x05,0xff,0xe5,0xbb,0x8a,0x00,0x05,0xff,0xf0,0xaa,0x8e,0x92,0x00,0xd3,0x3b, - 0xd2,0x22,0xd1,0x11,0x10,0x08,0x05,0xff,0xe5,0xbb,0xbe,0x00,0x05,0xff,0xf0,0xa2, - 0x8c,0xb1,0x00,0x10,0x09,0x05,0xff,0xf0,0xa2,0x8c,0xb1,0x00,0x05,0xff,0xe8,0x88, - 0x81,0x00,0x51,0x08,0x05,0xff,0xe5,0xbc,0xa2,0x00,0x10,0x08,0x05,0xff,0xe3,0xa3, - 0x87,0x00,0x05,0xff,0xf0,0xa3,0x8a,0xb8,0x00,0xd2,0x21,0xd1,0x11,0x10,0x09,0x05, - 0xff,0xf0,0xa6,0x87,0x9a,0x00,0x05,0xff,0xe5,0xbd,0xa2,0x00,0x10,0x08,0x05,0xff, - 0xe5,0xbd,0xab,0x00,0x05,0xff,0xe3,0xa3,0xa3,0x00,0xd1,0x10,0x10,0x08,0x05,0xff, - 0xe5,0xbe,0x9a,0x00,0x05,0xff,0xe5,0xbf,0x8d,0x00,0x10,0x08,0x05,0xff,0xe5,0xbf, - 0x97,0x00,0x05,0xff,0xe5,0xbf,0xb9,0x00,0xd4,0x81,0xd3,0x41,0xd2,0x20,0xd1,0x10, - 0x10,0x08,0x05,0xff,0xe6,0x82,0x81,0x00,0x05,0xff,0xe3,0xa4,0xba,0x00,0x10,0x08, - 0x05,0xff,0xe3,0xa4,0x9c,0x00,0x05,0xff,0xe6,0x82,0x94,0x00,0xd1,0x11,0x10,0x09, - 0x05,0xff,0xf0,0xa2,0x9b,0x94,0x00,0x05,0xff,0xe6,0x83,0x87,0x00,0x10,0x08,0x05, - 0xff,0xe6,0x85,0x88,0x00,0x05,0xff,0xe6,0x85,0x8c,0x00,0xd2,0x20,0xd1,0x10,0x10, - 0x08,0x05,0xff,0xe6,0x85,0x8e,0x00,0x05,0xff,0xe6,0x85,0x8c,0x00,0x10,0x08,0x05, - 0xff,0xe6,0x85,0xba,0x00,0x05,0xff,0xe6,0x86,0x8e,0x00,0xd1,0x10,0x10,0x08,0x05, - 0xff,0xe6,0x86,0xb2,0x00,0x05,0xff,0xe6,0x86,0xa4,0x00,0x10,0x08,0x05,0xff,0xe6, - 0x86,0xaf,0x00,0x05,0xff,0xe6,0x87,0x9e,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10, - 0x08,0x05,0xff,0xe6,0x87,0xb2,0x00,0x05,0xff,0xe6,0x87,0xb6,0x00,0x10,0x08,0x05, - 0xff,0xe6,0x88,0x90,0x00,0x05,0xff,0xe6,0x88,0x9b,0x00,0xd1,0x10,0x10,0x08,0x05, - 0xff,0xe6,0x89,0x9d,0x00,0x05,0xff,0xe6,0x8a,0xb1,0x00,0x10,0x08,0x05,0xff,0xe6, - 0x8b,0x94,0x00,0x05,0xff,0xe6,0x8d,0x90,0x00,0xd2,0x21,0xd1,0x11,0x10,0x09,0x05, - 0xff,0xf0,0xa2,0xac,0x8c,0x00,0x05,0xff,0xe6,0x8c,0xbd,0x00,0x10,0x08,0x05,0xff, - 0xe6,0x8b,0xbc,0x00,0x05,0xff,0xe6,0x8d,0xa8,0x00,0xd1,0x10,0x10,0x08,0x05,0xff, - 0xe6,0x8e,0x83,0x00,0x05,0xff,0xe6,0x8f,0xa4,0x00,0x10,0x09,0x05,0xff,0xf0,0xa2, - 0xaf,0xb1,0x00,0x05,0xff,0xe6,0x90,0xa2,0x00,0xcf,0x86,0xe5,0x03,0x01,0xd4,0x81, - 0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0x8f,0x85,0x00,0x05,0xff, - 0xe6,0x8e,0xa9,0x00,0x10,0x08,0x05,0xff,0xe3,0xa8,0xae,0x00,0x05,0xff,0xe6,0x91, - 0xa9,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0x91,0xbe,0x00,0x05,0xff,0xe6,0x92, - 0x9d,0x00,0x10,0x08,0x05,0xff,0xe6,0x91,0xb7,0x00,0x05,0xff,0xe3,0xa9,0xac,0x00, - 0xd2,0x21,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0x95,0x8f,0x00,0x05,0xff,0xe6,0x95, - 0xac,0x00,0x10,0x09,0x05,0xff,0xf0,0xa3,0x80,0x8a,0x00,0x05,0xff,0xe6,0x97,0xa3, - 0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0x9b,0xb8,0x00,0x05,0xff,0xe6,0x99,0x89, - 0x00,0x10,0x08,0x05,0xff,0xe3,0xac,0x99,0x00,0x05,0xff,0xe6,0x9a,0x91,0x00,0xd3, - 0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe3,0xac,0x88,0x00,0x05,0xff,0xe3, - 0xab,0xa4,0x00,0x10,0x08,0x05,0xff,0xe5,0x86,0x92,0x00,0x05,0xff,0xe5,0x86,0x95, - 0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0x9c,0x80,0x00,0x05,0xff,0xe6,0x9a,0x9c, - 0x00,0x10,0x08,0x05,0xff,0xe8,0x82,0xad,0x00,0x05,0xff,0xe4,0x8f,0x99,0x00,0xd2, - 0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0x9c,0x97,0x00,0x05,0xff,0xe6,0x9c,0x9b, - 0x00,0x10,0x08,0x05,0xff,0xe6,0x9c,0xa1,0x00,0x05,0xff,0xe6,0x9d,0x9e,0x00,0xd1, - 0x11,0x10,0x08,0x05,0xff,0xe6,0x9d,0x93,0x00,0x05,0xff,0xf0,0xa3,0x8f,0x83,0x00, - 0x10,0x08,0x05,0xff,0xe3,0xad,0x89,0x00,0x05,0xff,0xe6,0x9f,0xba,0x00,0xd4,0x82, - 0xd3,0x41,0xd2,0x21,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0x9e,0x85,0x00,0x05,0xff, - 0xe6,0xa1,0x92,0x00,0x10,0x08,0x05,0xff,0xe6,0xa2,0x85,0x00,0x05,0xff,0xf0,0xa3, - 0x91,0xad,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0xa2,0x8e,0x00,0x05,0xff,0xe6, - 0xa0,0x9f,0x00,0x10,0x08,0x05,0xff,0xe6,0xa4,0x94,0x00,0x05,0xff,0xe3,0xae,0x9d, - 0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0xa5,0x82,0x00,0x05,0xff,0xe6, - 0xa6,0xa3,0x00,0x10,0x08,0x05,0xff,0xe6,0xa7,0xaa,0x00,0x05,0xff,0xe6,0xaa,0xa8, - 0x00,0xd1,0x11,0x10,0x09,0x05,0xff,0xf0,0xa3,0x9a,0xa3,0x00,0x05,0xff,0xe6,0xab, - 0x9b,0x00,0x10,0x08,0x05,0xff,0xe3,0xb0,0x98,0x00,0x05,0xff,0xe6,0xac,0xa1,0x00, - 0xd3,0x42,0xd2,0x21,0xd1,0x11,0x10,0x09,0x05,0xff,0xf0,0xa3,0xa2,0xa7,0x00,0x05, - 0xff,0xe6,0xad,0x94,0x00,0x10,0x08,0x05,0xff,0xe3,0xb1,0x8e,0x00,0x05,0xff,0xe6, - 0xad,0xb2,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0xae,0x9f,0x00,0x05,0xff,0xe6, - 0xae,0xba,0x00,0x10,0x08,0x05,0xff,0xe6,0xae,0xbb,0x00,0x05,0xff,0xf0,0xa3,0xaa, - 0x8d,0x00,0xd2,0x23,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa1,0xb4,0x8b,0x00,0x05, - 0xff,0xf0,0xa3,0xab,0xba,0x00,0x10,0x08,0x05,0xff,0xe6,0xb1,0x8e,0x00,0x05,0xff, - 0xf0,0xa3,0xb2,0xbc,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0xb2,0xbf,0x00,0x05, - 0xff,0xe6,0xb3,0x8d,0x00,0x10,0x08,0x05,0xff,0xe6,0xb1,0xa7,0x00,0x05,0xff,0xe6, - 0xb4,0x96,0x00,0xe1,0x1d,0x04,0xe0,0x0c,0x02,0xcf,0x86,0xe5,0x08,0x01,0xd4,0x82, - 0xd3,0x41,0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0xb4,0xbe,0x00,0x05,0xff, - 0xe6,0xb5,0xb7,0x00,0x10,0x08,0x05,0xff,0xe6,0xb5,0x81,0x00,0x05,0xff,0xe6,0xb5, - 0xa9,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0xb5,0xb8,0x00,0x05,0xff,0xe6,0xb6, - 0x85,0x00,0x10,0x09,0x05,0xff,0xf0,0xa3,0xb4,0x9e,0x00,0x05,0xff,0xe6,0xb4,0xb4, - 0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0xb8,0xaf,0x00,0x05,0xff,0xe6, - 0xb9,0xae,0x00,0x10,0x08,0x05,0xff,0xe3,0xb4,0xb3,0x00,0x05,0xff,0xe6,0xbb,0x8b, - 0x00,0xd1,0x11,0x10,0x08,0x05,0xff,0xe6,0xbb,0x87,0x00,0x05,0xff,0xf0,0xa3,0xbb, - 0x91,0x00,0x10,0x08,0x05,0xff,0xe6,0xb7,0xb9,0x00,0x05,0xff,0xe6,0xbd,0xae,0x00, - 0xd3,0x42,0xd2,0x22,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa3,0xbd,0x9e,0x00,0x05, - 0xff,0xf0,0xa3,0xbe,0x8e,0x00,0x10,0x08,0x05,0xff,0xe6,0xbf,0x86,0x00,0x05,0xff, - 0xe7,0x80,0xb9,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe7,0x80,0x9e,0x00,0x05,0xff, - 0xe7,0x80,0x9b,0x00,0x10,0x08,0x05,0xff,0xe3,0xb6,0x96,0x00,0x05,0xff,0xe7,0x81, - 0x8a,0x00,0xd2,0x21,0xd1,0x10,0x10,0x08,0x05,0xff,0xe7,0x81,0xbd,0x00,0x05,0xff, - 0xe7,0x81,0xb7,0x00,0x10,0x08,0x05,0xff,0xe7,0x82,0xad,0x00,0x05,0xff,0xf0,0xa0, - 0x94,0xa5,0x00,0xd1,0x11,0x10,0x08,0x05,0xff,0xe7,0x85,0x85,0x00,0x05,0xff,0xf0, - 0xa4,0x89,0xa3,0x00,0x10,0x08,0x05,0xff,0xe7,0x86,0x9c,0x00,0x05,0xff,0xf0,0xa4, - 0x8e,0xab,0x00,0xd4,0x7b,0xd3,0x43,0xd2,0x21,0xd1,0x10,0x10,0x08,0x05,0xff,0xe7, - 0x88,0xa8,0x00,0x05,0xff,0xe7,0x88,0xb5,0x00,0x10,0x08,0x05,0xff,0xe7,0x89,0x90, - 0x00,0x05,0xff,0xf0,0xa4,0x98,0x88,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe7,0x8a, - 0x80,0x00,0x05,0xff,0xe7,0x8a,0x95,0x00,0x10,0x09,0x05,0xff,0xf0,0xa4,0x9c,0xb5, - 0x00,0x05,0xff,0xf0,0xa4,0xa0,0x94,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff, - 0xe7,0x8d,0xba,0x00,0x05,0xff,0xe7,0x8e,0x8b,0x00,0x10,0x08,0x05,0xff,0xe3,0xba, - 0xac,0x00,0x05,0xff,0xe7,0x8e,0xa5,0x00,0x51,0x08,0x05,0xff,0xe3,0xba,0xb8,0x00, - 0x10,0x08,0x05,0xff,0xe7,0x91,0x87,0x00,0x05,0xff,0xe7,0x91,0x9c,0x00,0xd3,0x42, - 0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe7,0x91,0xb1,0x00,0x05,0xff,0xe7,0x92, - 0x85,0x00,0x10,0x08,0x05,0xff,0xe7,0x93,0x8a,0x00,0x05,0xff,0xe3,0xbc,0x9b,0x00, - 0xd1,0x11,0x10,0x08,0x05,0xff,0xe7,0x94,0xa4,0x00,0x05,0xff,0xf0,0xa4,0xb0,0xb6, - 0x00,0x10,0x08,0x05,0xff,0xe7,0x94,0xbe,0x00,0x05,0xff,0xf0,0xa4,0xb2,0x92,0x00, - 0xd2,0x22,0xd1,0x11,0x10,0x08,0x05,0xff,0xe7,0x95,0xb0,0x00,0x05,0xff,0xf0,0xa2, - 0x86,0x9f,0x00,0x10,0x08,0x05,0xff,0xe7,0x98,0x90,0x00,0x05,0xff,0xf0,0xa4,0xbe, - 0xa1,0x00,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa4,0xbe,0xb8,0x00,0x05,0xff,0xf0, - 0xa5,0x81,0x84,0x00,0x10,0x08,0x05,0xff,0xe3,0xbf,0xbc,0x00,0x05,0xff,0xe4,0x80, - 0x88,0x00,0xcf,0x86,0xe5,0x04,0x01,0xd4,0x7d,0xd3,0x3c,0xd2,0x23,0xd1,0x11,0x10, - 0x08,0x05,0xff,0xe7,0x9b,0xb4,0x00,0x05,0xff,0xf0,0xa5,0x83,0xb3,0x00,0x10,0x09, - 0x05,0xff,0xf0,0xa5,0x83,0xb2,0x00,0x05,0xff,0xf0,0xa5,0x84,0x99,0x00,0x91,0x11, - 0x10,0x09,0x05,0xff,0xf0,0xa5,0x84,0xb3,0x00,0x05,0xff,0xe7,0x9c,0x9e,0x00,0x05, - 0xff,0xe7,0x9c,0x9f,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe7,0x9d,0x8a, - 0x00,0x05,0xff,0xe4,0x80,0xb9,0x00,0x10,0x08,0x05,0xff,0xe7,0x9e,0x8b,0x00,0x05, - 0xff,0xe4,0x81,0x86,0x00,0xd1,0x11,0x10,0x08,0x05,0xff,0xe4,0x82,0x96,0x00,0x05, - 0xff,0xf0,0xa5,0x90,0x9d,0x00,0x10,0x08,0x05,0xff,0xe7,0xa1,0x8e,0x00,0x05,0xff, - 0xe7,0xa2,0x8c,0x00,0xd3,0x43,0xd2,0x21,0xd1,0x10,0x10,0x08,0x05,0xff,0xe7,0xa3, - 0x8c,0x00,0x05,0xff,0xe4,0x83,0xa3,0x00,0x10,0x09,0x05,0xff,0xf0,0xa5,0x98,0xa6, - 0x00,0x05,0xff,0xe7,0xa5,0x96,0x00,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa5,0x9a, - 0x9a,0x00,0x05,0xff,0xf0,0xa5,0x9b,0x85,0x00,0x10,0x08,0x05,0xff,0xe7,0xa6,0x8f, - 0x00,0x05,0xff,0xe7,0xa7,0xab,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe4, - 0x84,0xaf,0x00,0x05,0xff,0xe7,0xa9,0x80,0x00,0x10,0x08,0x05,0xff,0xe7,0xa9,0x8a, - 0x00,0x05,0xff,0xe7,0xa9,0x8f,0x00,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa5,0xa5, - 0xbc,0x00,0x05,0xff,0xf0,0xa5,0xaa,0xa7,0x00,0x10,0x09,0x05,0xff,0xf0,0xa5,0xaa, - 0xa7,0x00,0x05,0xff,0xe7,0xab,0xae,0x00,0xd4,0x83,0xd3,0x42,0xd2,0x21,0xd1,0x11, - 0x10,0x08,0x05,0xff,0xe4,0x88,0x82,0x00,0x05,0xff,0xf0,0xa5,0xae,0xab,0x00,0x10, - 0x08,0x05,0xff,0xe7,0xaf,0x86,0x00,0x05,0xff,0xe7,0xaf,0x89,0x00,0xd1,0x11,0x10, - 0x08,0x05,0xff,0xe4,0x88,0xa7,0x00,0x05,0xff,0xf0,0xa5,0xb2,0x80,0x00,0x10,0x08, - 0x05,0xff,0xe7,0xb3,0x92,0x00,0x05,0xff,0xe4,0x8a,0xa0,0x00,0xd2,0x21,0xd1,0x10, - 0x10,0x08,0x05,0xff,0xe7,0xb3,0xa8,0x00,0x05,0xff,0xe7,0xb3,0xa3,0x00,0x10,0x08, - 0x05,0xff,0xe7,0xb4,0x80,0x00,0x05,0xff,0xf0,0xa5,0xbe,0x86,0x00,0xd1,0x10,0x10, - 0x08,0x05,0xff,0xe7,0xb5,0xa3,0x00,0x05,0xff,0xe4,0x8c,0x81,0x00,0x10,0x08,0x05, - 0xff,0xe7,0xb7,0x87,0x00,0x05,0xff,0xe7,0xb8,0x82,0x00,0xd3,0x44,0xd2,0x22,0xd1, - 0x10,0x10,0x08,0x05,0xff,0xe7,0xb9,0x85,0x00,0x05,0xff,0xe4,0x8c,0xb4,0x00,0x10, - 0x09,0x05,0xff,0xf0,0xa6,0x88,0xa8,0x00,0x05,0xff,0xf0,0xa6,0x89,0x87,0x00,0xd1, - 0x11,0x10,0x08,0x05,0xff,0xe4,0x8d,0x99,0x00,0x05,0xff,0xf0,0xa6,0x8b,0x99,0x00, - 0x10,0x08,0x05,0xff,0xe7,0xbd,0xba,0x00,0x05,0xff,0xf0,0xa6,0x8c,0xbe,0x00,0xd2, - 0x21,0xd1,0x10,0x10,0x08,0x05,0xff,0xe7,0xbe,0x95,0x00,0x05,0xff,0xe7,0xbf,0xba, - 0x00,0x10,0x08,0x05,0xff,0xe8,0x80,0x85,0x00,0x05,0xff,0xf0,0xa6,0x93,0x9a,0x00, - 0xd1,0x11,0x10,0x09,0x05,0xff,0xf0,0xa6,0x94,0xa3,0x00,0x05,0xff,0xe8,0x81,0xa0, - 0x00,0x10,0x09,0x05,0xff,0xf0,0xa6,0x96,0xa8,0x00,0x05,0xff,0xe8,0x81,0xb0,0x00, - 0xe0,0x11,0x02,0xcf,0x86,0xe5,0x07,0x01,0xd4,0x85,0xd3,0x42,0xd2,0x21,0xd1,0x11, - 0x10,0x09,0x05,0xff,0xf0,0xa3,0x8d,0x9f,0x00,0x05,0xff,0xe4,0x8f,0x95,0x00,0x10, - 0x08,0x05,0xff,0xe8,0x82,0xb2,0x00,0x05,0xff,0xe8,0x84,0x83,0x00,0xd1,0x10,0x10, - 0x08,0x05,0xff,0xe4,0x90,0x8b,0x00,0x05,0xff,0xe8,0x84,0xbe,0x00,0x10,0x08,0x05, - 0xff,0xe5,0xaa,0xb5,0x00,0x05,0xff,0xf0,0xa6,0x9e,0xa7,0x00,0xd2,0x23,0xd1,0x12, - 0x10,0x09,0x05,0xff,0xf0,0xa6,0x9e,0xb5,0x00,0x05,0xff,0xf0,0xa3,0x8e,0x93,0x00, - 0x10,0x09,0x05,0xff,0xf0,0xa3,0x8e,0x9c,0x00,0x05,0xff,0xe8,0x88,0x81,0x00,0xd1, - 0x10,0x10,0x08,0x05,0xff,0xe8,0x88,0x84,0x00,0x05,0xff,0xe8,0xbe,0x9e,0x00,0x10, - 0x08,0x05,0xff,0xe4,0x91,0xab,0x00,0x05,0xff,0xe8,0x8a,0x91,0x00,0xd3,0x41,0xd2, - 0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe8,0x8a,0x8b,0x00,0x05,0xff,0xe8,0x8a,0x9d, - 0x00,0x10,0x08,0x05,0xff,0xe5,0x8a,0xb3,0x00,0x05,0xff,0xe8,0x8a,0xb1,0x00,0xd1, - 0x10,0x10,0x08,0x05,0xff,0xe8,0x8a,0xb3,0x00,0x05,0xff,0xe8,0x8a,0xbd,0x00,0x10, - 0x08,0x05,0xff,0xe8,0x8b,0xa6,0x00,0x05,0xff,0xf0,0xa6,0xac,0xbc,0x00,0xd2,0x20, - 0xd1,0x10,0x10,0x08,0x05,0xff,0xe8,0x8b,0xa5,0x00,0x05,0xff,0xe8,0x8c,0x9d,0x00, - 0x10,0x08,0x05,0xff,0xe8,0x8d,0xa3,0x00,0x05,0xff,0xe8,0x8e,0xad,0x00,0xd1,0x10, - 0x10,0x08,0x05,0xff,0xe8,0x8c,0xa3,0x00,0x05,0xff,0xe8,0x8e,0xbd,0x00,0x10,0x08, - 0x05,0xff,0xe8,0x8f,0xa7,0x00,0x05,0xff,0xe8,0x91,0x97,0x00,0xd4,0x85,0xd3,0x43, - 0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe8,0x8d,0x93,0x00,0x05,0xff,0xe8,0x8f, - 0x8a,0x00,0x10,0x08,0x05,0xff,0xe8,0x8f,0x8c,0x00,0x05,0xff,0xe8,0x8f,0x9c,0x00, - 0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa6,0xb0,0xb6,0x00,0x05,0xff,0xf0,0xa6,0xb5, - 0xab,0x00,0x10,0x09,0x05,0xff,0xf0,0xa6,0xb3,0x95,0x00,0x05,0xff,0xe4,0x94,0xab, - 0x00,0xd2,0x21,0xd1,0x10,0x10,0x08,0x05,0xff,0xe8,0x93,0xb1,0x00,0x05,0xff,0xe8, - 0x93,0xb3,0x00,0x10,0x08,0x05,0xff,0xe8,0x94,0x96,0x00,0x05,0xff,0xf0,0xa7,0x8f, - 0x8a,0x00,0xd1,0x11,0x10,0x08,0x05,0xff,0xe8,0x95,0xa4,0x00,0x05,0xff,0xf0,0xa6, - 0xbc,0xac,0x00,0x10,0x08,0x05,0xff,0xe4,0x95,0x9d,0x00,0x05,0xff,0xe4,0x95,0xa1, - 0x00,0xd3,0x42,0xd2,0x22,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa6,0xbe,0xb1,0x00, - 0x05,0xff,0xf0,0xa7,0x83,0x92,0x00,0x10,0x08,0x05,0xff,0xe4,0x95,0xab,0x00,0x05, - 0xff,0xe8,0x99,0x90,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe8,0x99,0x9c,0x00,0x05, - 0xff,0xe8,0x99,0xa7,0x00,0x10,0x08,0x05,0xff,0xe8,0x99,0xa9,0x00,0x05,0xff,0xe8, - 0x9a,0xa9,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe8,0x9a,0x88,0x00,0x05, - 0xff,0xe8,0x9c,0x8e,0x00,0x10,0x08,0x05,0xff,0xe8,0x9b,0xa2,0x00,0x05,0xff,0xe8, - 0x9d,0xb9,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe8,0x9c,0xa8,0x00,0x05,0xff,0xe8, - 0x9d,0xab,0x00,0x10,0x08,0x05,0xff,0xe8,0x9e,0x86,0x00,0x05,0xff,0xe4,0x97,0x97, - 0x00,0xcf,0x86,0xe5,0x08,0x01,0xd4,0x83,0xd3,0x41,0xd2,0x20,0xd1,0x10,0x10,0x08, - 0x05,0xff,0xe8,0x9f,0xa1,0x00,0x05,0xff,0xe8,0xa0,0x81,0x00,0x10,0x08,0x05,0xff, - 0xe4,0x97,0xb9,0x00,0x05,0xff,0xe8,0xa1,0xa0,0x00,0xd1,0x11,0x10,0x08,0x05,0xff, - 0xe8,0xa1,0xa3,0x00,0x05,0xff,0xf0,0xa7,0x99,0xa7,0x00,0x10,0x08,0x05,0xff,0xe8, - 0xa3,0x97,0x00,0x05,0xff,0xe8,0xa3,0x9e,0x00,0xd2,0x21,0xd1,0x10,0x10,0x08,0x05, - 0xff,0xe4,0x98,0xb5,0x00,0x05,0xff,0xe8,0xa3,0xba,0x00,0x10,0x08,0x05,0xff,0xe3, - 0x92,0xbb,0x00,0x05,0xff,0xf0,0xa7,0xa2,0xae,0x00,0xd1,0x11,0x10,0x09,0x05,0xff, - 0xf0,0xa7,0xa5,0xa6,0x00,0x05,0xff,0xe4,0x9a,0xbe,0x00,0x10,0x08,0x05,0xff,0xe4, - 0x9b,0x87,0x00,0x05,0xff,0xe8,0xaa,0xa0,0x00,0xd3,0x41,0xd2,0x21,0xd1,0x10,0x10, - 0x08,0x05,0xff,0xe8,0xab,0xad,0x00,0x05,0xff,0xe8,0xae,0x8a,0x00,0x10,0x08,0x05, - 0xff,0xe8,0xb1,0x95,0x00,0x05,0xff,0xf0,0xa7,0xb2,0xa8,0x00,0xd1,0x10,0x10,0x08, - 0x05,0xff,0xe8,0xb2,0xab,0x00,0x05,0xff,0xe8,0xb3,0x81,0x00,0x10,0x08,0x05,0xff, - 0xe8,0xb4,0x9b,0x00,0x05,0xff,0xe8,0xb5,0xb7,0x00,0xd2,0x22,0xd1,0x12,0x10,0x09, - 0x05,0xff,0xf0,0xa7,0xbc,0xaf,0x00,0x05,0xff,0xf0,0xa0,0xa0,0x84,0x00,0x10,0x08, - 0x05,0xff,0xe8,0xb7,0x8b,0x00,0x05,0xff,0xe8,0xb6,0xbc,0x00,0xd1,0x11,0x10,0x08, - 0x05,0xff,0xe8,0xb7,0xb0,0x00,0x05,0xff,0xf0,0xa0,0xa3,0x9e,0x00,0x10,0x08,0x05, - 0xff,0xe8,0xbb,0x94,0x00,0x05,0xff,0xe8,0xbc,0xb8,0x00,0xd4,0x84,0xd3,0x43,0xd2, - 0x22,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa8,0x97,0x92,0x00,0x05,0xff,0xf0,0xa8, - 0x97,0xad,0x00,0x10,0x08,0x05,0xff,0xe9,0x82,0x94,0x00,0x05,0xff,0xe9,0x83,0xb1, - 0x00,0xd1,0x11,0x10,0x08,0x05,0xff,0xe9,0x84,0x91,0x00,0x05,0xff,0xf0,0xa8,0x9c, - 0xae,0x00,0x10,0x08,0x05,0xff,0xe9,0x84,0x9b,0x00,0x05,0xff,0xe9,0x88,0xb8,0x00, - 0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe9,0x8b,0x97,0x00,0x05,0xff,0xe9,0x8b, - 0x98,0x00,0x10,0x08,0x05,0xff,0xe9,0x89,0xbc,0x00,0x05,0xff,0xe9,0x8f,0xb9,0x00, - 0xd1,0x11,0x10,0x08,0x05,0xff,0xe9,0x90,0x95,0x00,0x05,0xff,0xf0,0xa8,0xaf,0xba, - 0x00,0x10,0x08,0x05,0xff,0xe9,0x96,0x8b,0x00,0x05,0xff,0xe4,0xa6,0x95,0x00,0xd3, - 0x43,0xd2,0x21,0xd1,0x11,0x10,0x08,0x05,0xff,0xe9,0x96,0xb7,0x00,0x05,0xff,0xf0, - 0xa8,0xb5,0xb7,0x00,0x10,0x08,0x05,0xff,0xe4,0xa7,0xa6,0x00,0x05,0xff,0xe9,0x9b, - 0x83,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe5,0xb6,0xb2,0x00,0x05,0xff,0xe9,0x9c, - 0xa3,0x00,0x10,0x09,0x05,0xff,0xf0,0xa9,0x85,0x85,0x00,0x05,0xff,0xf0,0xa9,0x88, - 0x9a,0x00,0xd2,0x21,0xd1,0x10,0x10,0x08,0x05,0xff,0xe4,0xa9,0xae,0x00,0x05,0xff, - 0xe4,0xa9,0xb6,0x00,0x10,0x08,0x05,0xff,0xe9,0x9f,0xa0,0x00,0x05,0xff,0xf0,0xa9, - 0x90,0x8a,0x00,0x91,0x11,0x10,0x08,0x05,0xff,0xe4,0xaa,0xb2,0x00,0x05,0xff,0xf0, - 0xa9,0x92,0x96,0x00,0x05,0xff,0xe9,0xa0,0x8b,0x00,0xe2,0x10,0x01,0xe1,0x09,0x01, - 0xe0,0x02,0x01,0xcf,0x86,0x95,0xfb,0xd4,0x82,0xd3,0x41,0xd2,0x21,0xd1,0x11,0x10, - 0x08,0x05,0xff,0xe9,0xa0,0xa9,0x00,0x05,0xff,0xf0,0xa9,0x96,0xb6,0x00,0x10,0x08, - 0x05,0xff,0xe9,0xa3,0xa2,0x00,0x05,0xff,0xe4,0xac,0xb3,0x00,0xd1,0x10,0x10,0x08, - 0x05,0xff,0xe9,0xa4,0xa9,0x00,0x05,0xff,0xe9,0xa6,0xa7,0x00,0x10,0x08,0x05,0xff, - 0xe9,0xa7,0x82,0x00,0x05,0xff,0xe9,0xa7,0xbe,0x00,0xd2,0x21,0xd1,0x11,0x10,0x08, - 0x05,0xff,0xe4,0xaf,0x8e,0x00,0x05,0xff,0xf0,0xa9,0xac,0xb0,0x00,0x10,0x08,0x05, - 0xff,0xe9,0xac,0x92,0x00,0x05,0xff,0xe9,0xb1,0x80,0x00,0xd1,0x10,0x10,0x08,0x05, - 0xff,0xe9,0xb3,0xbd,0x00,0x05,0xff,0xe4,0xb3,0x8e,0x00,0x10,0x08,0x05,0xff,0xe4, - 0xb3,0xad,0x00,0x05,0xff,0xe9,0xb5,0xa7,0x00,0xd3,0x44,0xd2,0x23,0xd1,0x11,0x10, - 0x09,0x05,0xff,0xf0,0xaa,0x83,0x8e,0x00,0x05,0xff,0xe4,0xb3,0xb8,0x00,0x10,0x09, - 0x05,0xff,0xf0,0xaa,0x84,0x85,0x00,0x05,0xff,0xf0,0xaa,0x88,0x8e,0x00,0xd1,0x11, - 0x10,0x09,0x05,0xff,0xf0,0xaa,0x8a,0x91,0x00,0x05,0xff,0xe9,0xba,0xbb,0x00,0x10, - 0x08,0x05,0xff,0xe4,0xb5,0x96,0x00,0x05,0xff,0xe9,0xbb,0xb9,0x00,0xd2,0x20,0xd1, - 0x10,0x10,0x08,0x05,0xff,0xe9,0xbb,0xbe,0x00,0x05,0xff,0xe9,0xbc,0x85,0x00,0x10, - 0x08,0x05,0xff,0xe9,0xbc,0x8f,0x00,0x05,0xff,0xe9,0xbc,0x96,0x00,0x91,0x11,0x10, - 0x08,0x05,0xff,0xe9,0xbc,0xbb,0x00,0x05,0xff,0xf0,0xaa,0x98,0x80,0x00,0x00,0x00, - 0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xd3,0x06, - 0xcf,0x06,0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1,0x06,0xcf,0x06,0x00,0x00, - 0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x00,0x00, - 0x53,0x04,0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x02,0x00,0xd3,0x08, - 0xcf,0x86,0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd1,0x08, - 0xcf,0x86,0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xcf,0x86, - 0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf,0x06,0x00,0x00,0xd3,0x06,0xcf,0x06, - 0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1,0x06,0xcf,0x06,0x00,0x00,0xd0,0x06, - 0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x00,0x00,0x53,0x04, - 0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x02,0x00,0xcf,0x86,0xd5,0xc0, - 0xd4,0x60,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf,0x86,0xcf,0x06, - 0x00,0x00,0xd1,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf,0x86,0xcf,0x06, - 0x00,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf,0x06,0x00,0x00, - 0xd3,0x06,0xcf,0x06,0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1,0x06,0xcf,0x06, - 0x00,0x00,0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04, - 0x00,0x00,0x53,0x04,0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x02,0x00, - 0xd3,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00, - 0xd1,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00, - 0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf,0x06,0x00,0x00,0xd3,0x06, - 0xcf,0x06,0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1,0x06,0xcf,0x06,0x00,0x00, - 0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x00,0x00, - 0x53,0x04,0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x02,0x00,0xd4,0x60, - 0xd3,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00, - 0xd1,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00, - 0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf,0x06,0x00,0x00,0xd3,0x06, - 0xcf,0x06,0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1,0x06,0xcf,0x06,0x00,0x00, - 0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x00,0x00, - 0x53,0x04,0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x02,0x00,0xd3,0x08, - 0xcf,0x86,0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd1,0x08, - 0xcf,0x86,0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xcf,0x86, - 0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf,0x06,0x00,0x00,0xd3,0x06,0xcf,0x06, - 0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1,0x06,0xcf,0x06,0x00,0x00,0xd0,0x06, - 0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x00,0x00,0x53,0x04, - 0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x02,0x00,0xe0,0x83,0x01,0xcf, - 0x86,0xd5,0xc0,0xd4,0x60,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf, - 0x86,0xcf,0x06,0x00,0x00,0xd1,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf, - 0x86,0xcf,0x06,0x00,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf, - 0x06,0x00,0x00,0xd3,0x06,0xcf,0x06,0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1, - 0x06,0xcf,0x06,0x00,0x00,0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00, - 0x00,0x54,0x04,0x00,0x00,0x53,0x04,0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00, - 0x00,0x02,0x00,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf,0x86,0xcf, - 0x06,0x00,0x00,0xd1,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf,0x86,0xcf, - 0x06,0x00,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf,0x06,0x00, - 0x00,0xd3,0x06,0xcf,0x06,0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1,0x06,0xcf, - 0x06,0x00,0x00,0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54, - 0x04,0x00,0x00,0x53,0x04,0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x02, - 0x00,0xd4,0x60,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf,0x86,0xcf, - 0x06,0x00,0x00,0xd1,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf,0x86,0xcf, - 0x06,0x00,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf,0x06,0x00, - 0x00,0xd3,0x06,0xcf,0x06,0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1,0x06,0xcf, - 0x06,0x00,0x00,0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54, - 0x04,0x00,0x00,0x53,0x04,0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x02, - 0x00,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf,0x86,0xcf,0x06,0x00, - 0x00,0xd1,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf,0x86,0xcf,0x06,0x00, - 0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf,0x06,0x00,0x00,0xd3, - 0x06,0xcf,0x06,0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1,0x06,0xcf,0x06,0x00, - 0x00,0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x00, - 0x00,0x53,0x04,0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x02,0x00,0xcf, - 0x86,0xd5,0xc0,0xd4,0x60,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf, - 0x86,0xcf,0x06,0x00,0x00,0xd1,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf, - 0x86,0xcf,0x06,0x00,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf, - 0x06,0x00,0x00,0xd3,0x06,0xcf,0x06,0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1, - 0x06,0xcf,0x06,0x00,0x00,0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00, - 0x00,0x54,0x04,0x00,0x00,0x53,0x04,0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00, - 0x00,0x02,0x00,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf,0x86,0xcf, - 0x06,0x00,0x00,0xd1,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf,0x86,0xcf, - 0x06,0x00,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf,0x06,0x00, - 0x00,0xd3,0x06,0xcf,0x06,0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1,0x06,0xcf, - 0x06,0x00,0x00,0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54, - 0x04,0x00,0x00,0x53,0x04,0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x02, - 0x00,0xd4,0xd9,0xd3,0x81,0xd2,0x79,0xd1,0x71,0xd0,0x69,0xcf,0x86,0xd5,0x60,0xd4, - 0x59,0xd3,0x52,0xd2,0x33,0xd1,0x2c,0xd0,0x25,0xcf,0x86,0x95,0x1e,0x94,0x19,0x93, - 0x14,0x92,0x0f,0x91,0x0a,0x10,0x05,0x00,0xff,0x00,0x05,0xff,0x00,0x00,0xff,0x00, - 0x00,0xff,0x00,0x00,0xff,0x00,0x00,0xff,0x00,0x05,0xff,0x00,0xcf,0x06,0x05,0xff, - 0x00,0xcf,0x06,0x00,0xff,0x00,0xd1,0x07,0xcf,0x06,0x07,0xff,0x00,0xd0,0x07,0xcf, - 0x06,0x07,0xff,0x00,0xcf,0x86,0x55,0x05,0x07,0xff,0x00,0x14,0x05,0x07,0xff,0x00, - 0x00,0xff,0x00,0xcf,0x06,0x00,0xff,0x00,0xcf,0x06,0x00,0xff,0x00,0xcf,0x06,0x00, - 0xff,0x00,0xcf,0x86,0xcf,0x06,0x00,0x00,0xcf,0x86,0xcf,0x06,0x00,0x00,0xcf,0x86, - 0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd1,0x08,0xcf,0x86, - 0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xcf,0x86,0xd5,0x06, - 0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf,0x06,0x00,0x00,0xd3,0x06,0xcf,0x06,0x00,0x00, - 0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1,0x06,0xcf,0x06,0x00,0x00,0xd0,0x06,0xcf,0x06, - 0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x00,0x00,0x53,0x04,0x00,0x00, - 0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x02,0x00,0xcf,0x86,0xcf,0x06,0x02,0x00, - 0x81,0x80,0xcf,0x86,0x85,0x84,0xcf,0x86,0xcf,0x06,0x02,0x00,0x00,0x00,0x00,0x00 -}; diff --git a/fs/unicode/utf8data.h_shipped b/fs/unicode/utf8data.h_shipped new file mode 100644 index 000000000000..76e4f0e1b089 --- /dev/null +++ b/fs/unicode/utf8data.h_shipped @@ -0,0 +1,4109 @@ +/* This file is generated code, do not edit. */ +#ifndef __INCLUDED_FROM_UTF8NORM_C__ +#error Only nls_utf8-norm.c should include this file. +#endif + +static const unsigned int utf8vers = 0xc0100; + +static const unsigned int utf8agetab[] = { + 0, + 0x10100, + 0x20000, + 0x20100, + 0x30000, + 0x30100, + 0x30200, + 0x40000, + 0x40100, + 0x50000, + 0x50100, + 0x50200, + 0x60000, + 0x60100, + 0x60200, + 0x60300, + 0x70000, + 0x80000, + 0x90000, + 0xa0000, + 0xb0000, + 0xc0000, + 0xc0100 +}; + +static const struct utf8data utf8nfdicfdata[] = { + { 0, 0 }, + { 0x10100, 0 }, + { 0x20000, 0 }, + { 0x20100, 0 }, + { 0x30000, 0 }, + { 0x30100, 0 }, + { 0x30200, 1792 }, + { 0x40000, 3200 }, + { 0x40100, 3200 }, + { 0x50000, 3200 }, + { 0x50100, 3200 }, + { 0x50200, 3200 }, + { 0x60000, 3200 }, + { 0x60100, 3200 }, + { 0x60200, 3200 }, + { 0x60300, 3200 }, + { 0x70000, 3200 }, + { 0x80000, 3200 }, + { 0x90000, 3200 }, + { 0xa0000, 3200 }, + { 0xb0000, 3200 }, + { 0xc0000, 3200 }, + { 0xc0100, 3200 } +}; + +static const struct utf8data utf8nfdidata[] = { + { 0, 896 }, + { 0x10100, 896 }, + { 0x20000, 896 }, + { 0x20100, 896 }, + { 0x30000, 896 }, + { 0x30100, 896 }, + { 0x30200, 2496 }, + { 0x40000, 20736 }, + { 0x40100, 20736 }, + { 0x50000, 20736 }, + { 0x50100, 20736 }, + { 0x50200, 20736 }, + { 0x60000, 20736 }, + { 0x60100, 20736 }, + { 0x60200, 20736 }, + { 0x60300, 20736 }, + { 0x70000, 20736 }, + { 0x80000, 20736 }, + { 0x90000, 20736 }, + { 0xa0000, 20736 }, + { 0xb0000, 20736 }, + { 0xc0000, 20736 }, + { 0xc0100, 20736 } +}; + +static const unsigned char utf8data[64256] = { + /* nfdicf_30100 */ + 0xd7,0x07,0x66,0x84,0x0c,0x01,0x00,0xc6,0xd5,0x16,0xe4,0x99,0x1a,0xe3,0x63,0x15, + 0xe2,0x4c,0x0e,0xc1,0xe0,0x4e,0x0d,0xcf,0x86,0x65,0x2d,0x0d,0x01,0x00,0xd4,0xb8, + 0xd3,0x27,0xe2,0x89,0xa3,0xe1,0xce,0x35,0xe0,0x2c,0x22,0xcf,0x86,0xc5,0xe4,0x15, + 0x6d,0xe3,0x60,0x68,0xe2,0xf6,0x65,0xe1,0x29,0x65,0xe0,0xee,0x64,0xcf,0x86,0xe5, + 0xb3,0x64,0x64,0x96,0x64,0x0b,0x00,0xd2,0x0e,0xe1,0xb5,0x3c,0xe0,0xba,0xa3,0xcf, + 0x86,0xcf,0x06,0x01,0x00,0xd1,0x0c,0xe0,0x1e,0xa9,0xcf,0x86,0xcf,0x06,0x02,0xff, + 0xff,0xd0,0x08,0xcf,0x86,0xcf,0x06,0x01,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x01, + 0x00,0xe4,0xe1,0x45,0xe3,0x3b,0x45,0xd2,0x06,0xcf,0x06,0x01,0x00,0xe1,0x87,0xad, + 0xd0,0x21,0xcf,0x86,0xe5,0x81,0xaa,0xe4,0x00,0xaa,0xe3,0xbf,0xa9,0xe2,0x9e,0xa9, + 0xe1,0x8d,0xa9,0x10,0x08,0x01,0xff,0xe8,0xb1,0x88,0x00,0x01,0xff,0xe6,0x9b,0xb4, + 0x00,0xcf,0x86,0xe5,0x63,0xac,0xd4,0x19,0xe3,0xa2,0xab,0xe2,0x81,0xab,0xe1,0x70, + 0xab,0x10,0x08,0x01,0xff,0xe9,0xb9,0xbf,0x00,0x01,0xff,0xe8,0xab,0x96,0x00,0xe3, + 0x09,0xac,0xe2,0xe8,0xab,0xe1,0xd7,0xab,0x10,0x08,0x01,0xff,0xe7,0xb8,0xb7,0x00, + 0x01,0xff,0xe9,0x9b,0xbb,0x00,0x83,0xe2,0x19,0xfa,0xe1,0xf2,0xf6,0xe0,0x6f,0xf5, + 0xcf,0x86,0xd5,0x31,0xc4,0xe3,0x54,0x4e,0xe2,0xf5,0x4c,0xe1,0xa4,0xcc,0xe0,0x9c, + 0x4b,0xcf,0x86,0xe5,0x8e,0x49,0xe4,0xaf,0x46,0xe3,0x11,0xbd,0xe2,0x68,0xbc,0xe1, + 0x43,0xbc,0xe0,0x1c,0xbc,0xcf,0x86,0xe5,0xe9,0xbb,0x94,0x07,0x63,0xd4,0xbb,0x07, + 0x00,0x07,0x00,0xe4,0xdb,0xf4,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x05,0x00,0xd2,0x0b, + 0xe1,0xea,0xe1,0xcf,0x86,0xcf,0x06,0x05,0x00,0xd1,0x0e,0xe0,0xd9,0xe2,0xcf,0x86, + 0xe5,0x9e,0xe2,0xcf,0x06,0x11,0x00,0xd0,0x0b,0xcf,0x86,0xe5,0xd9,0xe2,0xcf,0x06, + 0x13,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xe4,0x74,0xf4,0xe3,0x5d,0xf3, + 0xd2,0xa0,0xe1,0x13,0xe7,0xd0,0x21,0xcf,0x86,0xe5,0x14,0xe4,0xe4,0x90,0xe3,0xe3, + 0x4e,0xe3,0xe2,0x2d,0xe3,0xe1,0x1b,0xe3,0x10,0x08,0x05,0xff,0xe4,0xb8,0xbd,0x00, + 0x05,0xff,0xe4,0xb8,0xb8,0x00,0xcf,0x86,0xd5,0x1c,0xe4,0x70,0xe5,0xe3,0x2f,0xe5, + 0xe2,0x0e,0xe5,0xe1,0xfd,0xe4,0x10,0x08,0x05,0xff,0xe5,0x92,0xa2,0x00,0x05,0xff, + 0xe5,0x93,0xb6,0x00,0xd4,0x34,0xd3,0x18,0xe2,0xf7,0xe5,0xe1,0xe6,0xe5,0x10,0x09, + 0x05,0xff,0xf0,0xa1,0x9a,0xa8,0x00,0x05,0xff,0xf0,0xa1,0x9b,0xaa,0x00,0xe2,0x17, + 0xe6,0x91,0x11,0x10,0x09,0x05,0xff,0xf0,0xa1,0x8d,0xaa,0x00,0x05,0xff,0xe5,0xac, + 0x88,0x00,0x05,0xff,0xe5,0xac,0xbe,0x00,0xe3,0x5d,0xe6,0xd2,0x14,0xe1,0x2c,0xe6, + 0x10,0x08,0x05,0xff,0xe5,0xaf,0xb3,0x00,0x05,0xff,0xf0,0xa1,0xac,0x98,0x00,0xe1, + 0x38,0xe6,0x10,0x08,0x05,0xff,0xe5,0xbc,0xb3,0x00,0x05,0xff,0xe5,0xb0,0xa2,0x00, + 0xd1,0xd5,0xd0,0x6a,0xcf,0x86,0xe5,0x8d,0xeb,0xd4,0x19,0xe3,0xc6,0xea,0xe2,0xa4, + 0xea,0xe1,0x93,0xea,0x10,0x08,0x05,0xff,0xe6,0xb4,0xbe,0x00,0x05,0xff,0xe6,0xb5, + 0xb7,0x00,0xd3,0x18,0xe2,0x10,0xeb,0xe1,0xff,0xea,0x10,0x09,0x05,0xff,0xf0,0xa3, + 0xbd,0x9e,0x00,0x05,0xff,0xf0,0xa3,0xbe,0x8e,0x00,0xd2,0x13,0xe1,0x28,0xeb,0x10, + 0x08,0x05,0xff,0xe7,0x81,0xbd,0x00,0x05,0xff,0xe7,0x81,0xb7,0x00,0xd1,0x11,0x10, + 0x08,0x05,0xff,0xe7,0x85,0x85,0x00,0x05,0xff,0xf0,0xa4,0x89,0xa3,0x00,0x10,0x08, + 0x05,0xff,0xe7,0x86,0x9c,0x00,0x05,0xff,0xe4,0x8e,0xab,0x00,0xcf,0x86,0xe5,0x2a, + 0xed,0xd4,0x1a,0xe3,0x62,0xec,0xe2,0x48,0xec,0xe1,0x35,0xec,0x10,0x08,0x05,0xff, + 0xe7,0x9b,0xb4,0x00,0x05,0xff,0xf0,0xa5,0x83,0xb3,0x00,0xd3,0x16,0xe2,0xaa,0xec, + 0xe1,0x98,0xec,0x10,0x08,0x05,0xff,0xe7,0xa3,0x8c,0x00,0x05,0xff,0xe4,0x83,0xa3, + 0x00,0xd2,0x13,0xe1,0xc6,0xec,0x10,0x08,0x05,0xff,0xe4,0x84,0xaf,0x00,0x05,0xff, + 0xe7,0xa9,0x80,0x00,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa5,0xa5,0xbc,0x00,0x05, + 0xff,0xf0,0xa5,0xaa,0xa7,0x00,0x10,0x09,0x05,0xff,0xf0,0xa5,0xaa,0xa7,0x00,0x05, + 0xff,0xe7,0xaa,0xae,0x00,0xe0,0xdc,0xef,0xcf,0x86,0xd5,0x1d,0xe4,0x51,0xee,0xe3, + 0x0d,0xee,0xe2,0xeb,0xed,0xe1,0xda,0xed,0x10,0x09,0x05,0xff,0xf0,0xa3,0x8d,0x9f, + 0x00,0x05,0xff,0xe4,0x8f,0x95,0x00,0xd4,0x19,0xe3,0xf8,0xee,0xe2,0xd4,0xee,0xe1, + 0xc3,0xee,0x10,0x08,0x05,0xff,0xe8,0x8d,0x93,0x00,0x05,0xff,0xe8,0x8f,0x8a,0x00, + 0xd3,0x18,0xe2,0x43,0xef,0xe1,0x32,0xef,0x10,0x09,0x05,0xff,0xf0,0xa6,0xbe,0xb1, + 0x00,0x05,0xff,0xf0,0xa7,0x83,0x92,0x00,0xd2,0x13,0xe1,0x5b,0xef,0x10,0x08,0x05, + 0xff,0xe8,0x9a,0x88,0x00,0x05,0xff,0xe8,0x9c,0x8e,0x00,0xd1,0x10,0x10,0x08,0x05, + 0xff,0xe8,0x9c,0xa8,0x00,0x05,0xff,0xe8,0x9d,0xab,0x00,0x10,0x08,0x05,0xff,0xe8, + 0x9e,0x86,0x00,0x05,0xff,0xe4,0xb5,0x97,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, + 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, + 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, + 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, + /* nfdi_30100 */ + 0x57,0x04,0x01,0x00,0xc6,0xd5,0x16,0xe4,0xc2,0x59,0xe3,0xfb,0x54,0xe2,0x74,0x4f, + 0xc1,0xe0,0xa0,0x4d,0xcf,0x86,0x65,0x84,0x4d,0x01,0x00,0xd4,0xb8,0xd3,0x27,0xe2, + 0x0c,0xa0,0xe1,0xdf,0x8d,0xe0,0x39,0x71,0xcf,0x86,0xc5,0xe4,0x98,0x69,0xe3,0xe3, + 0x64,0xe2,0x79,0x62,0xe1,0xac,0x61,0xe0,0x71,0x61,0xcf,0x86,0xe5,0x36,0x61,0x64, + 0x19,0x61,0x0b,0x00,0xd2,0x0e,0xe1,0xc2,0xa0,0xe0,0x3d,0xa0,0xcf,0x86,0xcf,0x06, + 0x01,0x00,0xd1,0x0c,0xe0,0xa1,0xa5,0xcf,0x86,0xcf,0x06,0x02,0xff,0xff,0xd0,0x08, + 0xcf,0x86,0xcf,0x06,0x01,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x01,0x00,0xe4,0x9e, + 0xb6,0xe3,0x18,0xae,0xd2,0x06,0xcf,0x06,0x01,0x00,0xe1,0x0a,0xaa,0xd0,0x21,0xcf, + 0x86,0xe5,0x04,0xa7,0xe4,0x83,0xa6,0xe3,0x42,0xa6,0xe2,0x21,0xa6,0xe1,0x10,0xa6, + 0x10,0x08,0x01,0xff,0xe8,0xb1,0x88,0x00,0x01,0xff,0xe6,0x9b,0xb4,0x00,0xcf,0x86, + 0xe5,0xe6,0xa8,0xd4,0x19,0xe3,0x25,0xa8,0xe2,0x04,0xa8,0xe1,0xf3,0xa7,0x10,0x08, + 0x01,0xff,0xe9,0xb9,0xbf,0x00,0x01,0xff,0xe8,0xab,0x96,0x00,0xe3,0x8c,0xa8,0xe2, + 0x6b,0xa8,0xe1,0x5a,0xa8,0x10,0x08,0x01,0xff,0xe7,0xb8,0xb7,0x00,0x01,0xff,0xe9, + 0x9b,0xbb,0x00,0x83,0xe2,0x9c,0xf6,0xe1,0x75,0xf3,0xe0,0xf2,0xf1,0xcf,0x86,0xd5, + 0x31,0xc4,0xe3,0x6d,0xcc,0xe2,0x46,0xca,0xe1,0x27,0xc9,0xe0,0xb7,0xbf,0xcf,0x86, + 0xe5,0xaa,0xbb,0xe4,0xa3,0xba,0xe3,0x94,0xb9,0xe2,0xeb,0xb8,0xe1,0xc6,0xb8,0xe0, + 0x9f,0xb8,0xcf,0x86,0xe5,0x6c,0xb8,0x94,0x07,0x63,0x57,0xb8,0x07,0x00,0x07,0x00, + 0xe4,0x5e,0xf1,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x05,0x00,0xd2,0x0b,0xe1,0x6d,0xde, + 0xcf,0x86,0xcf,0x06,0x05,0x00,0xd1,0x0e,0xe0,0x5c,0xdf,0xcf,0x86,0xe5,0x21,0xdf, + 0xcf,0x06,0x11,0x00,0xd0,0x0b,0xcf,0x86,0xe5,0x5c,0xdf,0xcf,0x06,0x13,0x00,0xcf, + 0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xe4,0xf7,0xf0,0xe3,0xe0,0xef,0xd2,0xa0,0xe1, + 0x96,0xe3,0xd0,0x21,0xcf,0x86,0xe5,0x97,0xe0,0xe4,0x13,0xe0,0xe3,0xd1,0xdf,0xe2, + 0xb0,0xdf,0xe1,0x9e,0xdf,0x10,0x08,0x05,0xff,0xe4,0xb8,0xbd,0x00,0x05,0xff,0xe4, + 0xb8,0xb8,0x00,0xcf,0x86,0xd5,0x1c,0xe4,0xf3,0xe1,0xe3,0xb2,0xe1,0xe2,0x91,0xe1, + 0xe1,0x80,0xe1,0x10,0x08,0x05,0xff,0xe5,0x92,0xa2,0x00,0x05,0xff,0xe5,0x93,0xb6, + 0x00,0xd4,0x34,0xd3,0x18,0xe2,0x7a,0xe2,0xe1,0x69,0xe2,0x10,0x09,0x05,0xff,0xf0, + 0xa1,0x9a,0xa8,0x00,0x05,0xff,0xf0,0xa1,0x9b,0xaa,0x00,0xe2,0x9a,0xe2,0x91,0x11, + 0x10,0x09,0x05,0xff,0xf0,0xa1,0x8d,0xaa,0x00,0x05,0xff,0xe5,0xac,0x88,0x00,0x05, + 0xff,0xe5,0xac,0xbe,0x00,0xe3,0xe0,0xe2,0xd2,0x14,0xe1,0xaf,0xe2,0x10,0x08,0x05, + 0xff,0xe5,0xaf,0xb3,0x00,0x05,0xff,0xf0,0xa1,0xac,0x98,0x00,0xe1,0xbb,0xe2,0x10, + 0x08,0x05,0xff,0xe5,0xbc,0xb3,0x00,0x05,0xff,0xe5,0xb0,0xa2,0x00,0xd1,0xd5,0xd0, + 0x6a,0xcf,0x86,0xe5,0x10,0xe8,0xd4,0x19,0xe3,0x49,0xe7,0xe2,0x27,0xe7,0xe1,0x16, + 0xe7,0x10,0x08,0x05,0xff,0xe6,0xb4,0xbe,0x00,0x05,0xff,0xe6,0xb5,0xb7,0x00,0xd3, + 0x18,0xe2,0x93,0xe7,0xe1,0x82,0xe7,0x10,0x09,0x05,0xff,0xf0,0xa3,0xbd,0x9e,0x00, + 0x05,0xff,0xf0,0xa3,0xbe,0x8e,0x00,0xd2,0x13,0xe1,0xab,0xe7,0x10,0x08,0x05,0xff, + 0xe7,0x81,0xbd,0x00,0x05,0xff,0xe7,0x81,0xb7,0x00,0xd1,0x11,0x10,0x08,0x05,0xff, + 0xe7,0x85,0x85,0x00,0x05,0xff,0xf0,0xa4,0x89,0xa3,0x00,0x10,0x08,0x05,0xff,0xe7, + 0x86,0x9c,0x00,0x05,0xff,0xe4,0x8e,0xab,0x00,0xcf,0x86,0xe5,0xad,0xe9,0xd4,0x1a, + 0xe3,0xe5,0xe8,0xe2,0xcb,0xe8,0xe1,0xb8,0xe8,0x10,0x08,0x05,0xff,0xe7,0x9b,0xb4, + 0x00,0x05,0xff,0xf0,0xa5,0x83,0xb3,0x00,0xd3,0x16,0xe2,0x2d,0xe9,0xe1,0x1b,0xe9, + 0x10,0x08,0x05,0xff,0xe7,0xa3,0x8c,0x00,0x05,0xff,0xe4,0x83,0xa3,0x00,0xd2,0x13, + 0xe1,0x49,0xe9,0x10,0x08,0x05,0xff,0xe4,0x84,0xaf,0x00,0x05,0xff,0xe7,0xa9,0x80, + 0x00,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa5,0xa5,0xbc,0x00,0x05,0xff,0xf0,0xa5, + 0xaa,0xa7,0x00,0x10,0x09,0x05,0xff,0xf0,0xa5,0xaa,0xa7,0x00,0x05,0xff,0xe7,0xaa, + 0xae,0x00,0xe0,0x5f,0xec,0xcf,0x86,0xd5,0x1d,0xe4,0xd4,0xea,0xe3,0x90,0xea,0xe2, + 0x6e,0xea,0xe1,0x5d,0xea,0x10,0x09,0x05,0xff,0xf0,0xa3,0x8d,0x9f,0x00,0x05,0xff, + 0xe4,0x8f,0x95,0x00,0xd4,0x19,0xe3,0x7b,0xeb,0xe2,0x57,0xeb,0xe1,0x46,0xeb,0x10, + 0x08,0x05,0xff,0xe8,0x8d,0x93,0x00,0x05,0xff,0xe8,0x8f,0x8a,0x00,0xd3,0x18,0xe2, + 0xc6,0xeb,0xe1,0xb5,0xeb,0x10,0x09,0x05,0xff,0xf0,0xa6,0xbe,0xb1,0x00,0x05,0xff, + 0xf0,0xa7,0x83,0x92,0x00,0xd2,0x13,0xe1,0xde,0xeb,0x10,0x08,0x05,0xff,0xe8,0x9a, + 0x88,0x00,0x05,0xff,0xe8,0x9c,0x8e,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe8,0x9c, + 0xa8,0x00,0x05,0xff,0xe8,0x9d,0xab,0x00,0x10,0x08,0x05,0xff,0xe8,0x9e,0x86,0x00, + 0x05,0xff,0xe4,0xb5,0x97,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, + 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, + 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, + 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, + /* nfdicf_30200 */ + 0xd7,0x07,0x66,0x84,0x05,0x01,0x00,0xc6,0xd5,0x16,0xe4,0x99,0x13,0xe3,0x63,0x0e, + 0xe2,0x4c,0x07,0xc1,0xe0,0x4e,0x06,0xcf,0x86,0x65,0x2d,0x06,0x01,0x00,0xd4,0x2a, + 0xe3,0xd0,0x35,0xe2,0x88,0x9c,0xe1,0xcd,0x2e,0xe0,0x2b,0x1b,0xcf,0x86,0xc5,0xe4, + 0x14,0x66,0xe3,0x5f,0x61,0xe2,0xf5,0x5e,0xe1,0x28,0x5e,0xe0,0xed,0x5d,0xcf,0x86, + 0xe5,0xb2,0x5d,0x64,0x95,0x5d,0x0b,0x00,0x83,0xe2,0xa7,0xf3,0xe1,0x80,0xf0,0xe0, + 0xfd,0xee,0xcf,0x86,0xd5,0x31,0xc4,0xe3,0xe2,0x47,0xe2,0x83,0x46,0xe1,0x32,0xc6, + 0xe0,0x2a,0x45,0xcf,0x86,0xe5,0x1c,0x43,0xe4,0x3d,0x40,0xe3,0x9f,0xb6,0xe2,0xf6, + 0xb5,0xe1,0xd1,0xb5,0xe0,0xaa,0xb5,0xcf,0x86,0xe5,0x77,0xb5,0x94,0x07,0x63,0x62, + 0xb5,0x07,0x00,0x07,0x00,0xe4,0x69,0xee,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x05,0x00, + 0xd2,0x0b,0xe1,0x78,0xdb,0xcf,0x86,0xcf,0x06,0x05,0x00,0xd1,0x0e,0xe0,0x67,0xdc, + 0xcf,0x86,0xe5,0x2c,0xdc,0xcf,0x06,0x11,0x00,0xd0,0x0b,0xcf,0x86,0xe5,0x67,0xdc, + 0xcf,0x06,0x13,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xe4,0x02,0xee,0xe3, + 0xeb,0xec,0xd2,0xa0,0xe1,0xa1,0xe0,0xd0,0x21,0xcf,0x86,0xe5,0xa2,0xdd,0xe4,0x1e, + 0xdd,0xe3,0xdc,0xdc,0xe2,0xbb,0xdc,0xe1,0xa9,0xdc,0x10,0x08,0x05,0xff,0xe4,0xb8, + 0xbd,0x00,0x05,0xff,0xe4,0xb8,0xb8,0x00,0xcf,0x86,0xd5,0x1c,0xe4,0xfe,0xde,0xe3, + 0xbd,0xde,0xe2,0x9c,0xde,0xe1,0x8b,0xde,0x10,0x08,0x05,0xff,0xe5,0x92,0xa2,0x00, + 0x05,0xff,0xe5,0x93,0xb6,0x00,0xd4,0x34,0xd3,0x18,0xe2,0x85,0xdf,0xe1,0x74,0xdf, + 0x10,0x09,0x05,0xff,0xf0,0xa1,0x9a,0xa8,0x00,0x05,0xff,0xf0,0xa1,0x9b,0xaa,0x00, + 0xe2,0xa5,0xdf,0x91,0x11,0x10,0x09,0x05,0xff,0xf0,0xa1,0x8d,0xaa,0x00,0x05,0xff, + 0xe5,0xac,0x88,0x00,0x05,0xff,0xe5,0xac,0xbe,0x00,0xe3,0xeb,0xdf,0xd2,0x14,0xe1, + 0xba,0xdf,0x10,0x08,0x05,0xff,0xe5,0xaf,0xb3,0x00,0x05,0xff,0xf0,0xa1,0xac,0x98, + 0x00,0xe1,0xc6,0xdf,0x10,0x08,0x05,0xff,0xe5,0xbc,0xb3,0x00,0x05,0xff,0xe5,0xb0, + 0xa2,0x00,0xd1,0xd5,0xd0,0x6a,0xcf,0x86,0xe5,0x1b,0xe5,0xd4,0x19,0xe3,0x54,0xe4, + 0xe2,0x32,0xe4,0xe1,0x21,0xe4,0x10,0x08,0x05,0xff,0xe6,0xb4,0xbe,0x00,0x05,0xff, + 0xe6,0xb5,0xb7,0x00,0xd3,0x18,0xe2,0x9e,0xe4,0xe1,0x8d,0xe4,0x10,0x09,0x05,0xff, + 0xf0,0xa3,0xbd,0x9e,0x00,0x05,0xff,0xf0,0xa3,0xbe,0x8e,0x00,0xd2,0x13,0xe1,0xb6, + 0xe4,0x10,0x08,0x05,0xff,0xe7,0x81,0xbd,0x00,0x05,0xff,0xe7,0x81,0xb7,0x00,0xd1, + 0x11,0x10,0x08,0x05,0xff,0xe7,0x85,0x85,0x00,0x05,0xff,0xf0,0xa4,0x89,0xa3,0x00, + 0x10,0x08,0x05,0xff,0xe7,0x86,0x9c,0x00,0x05,0xff,0xe4,0x8e,0xab,0x00,0xcf,0x86, + 0xe5,0xb8,0xe6,0xd4,0x1a,0xe3,0xf0,0xe5,0xe2,0xd6,0xe5,0xe1,0xc3,0xe5,0x10,0x08, + 0x05,0xff,0xe7,0x9b,0xb4,0x00,0x05,0xff,0xf0,0xa5,0x83,0xb3,0x00,0xd3,0x16,0xe2, + 0x38,0xe6,0xe1,0x26,0xe6,0x10,0x08,0x05,0xff,0xe7,0xa3,0x8c,0x00,0x05,0xff,0xe4, + 0x83,0xa3,0x00,0xd2,0x13,0xe1,0x54,0xe6,0x10,0x08,0x05,0xff,0xe4,0x84,0xaf,0x00, + 0x05,0xff,0xe7,0xa9,0x80,0x00,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa5,0xa5,0xbc, + 0x00,0x05,0xff,0xf0,0xa5,0xaa,0xa7,0x00,0x10,0x09,0x05,0xff,0xf0,0xa5,0xaa,0xa7, + 0x00,0x05,0xff,0xe7,0xaa,0xae,0x00,0xe0,0x6a,0xe9,0xcf,0x86,0xd5,0x1d,0xe4,0xdf, + 0xe7,0xe3,0x9b,0xe7,0xe2,0x79,0xe7,0xe1,0x68,0xe7,0x10,0x09,0x05,0xff,0xf0,0xa3, + 0x8d,0x9f,0x00,0x05,0xff,0xe4,0x8f,0x95,0x00,0xd4,0x19,0xe3,0x86,0xe8,0xe2,0x62, + 0xe8,0xe1,0x51,0xe8,0x10,0x08,0x05,0xff,0xe8,0x8d,0x93,0x00,0x05,0xff,0xe8,0x8f, + 0x8a,0x00,0xd3,0x18,0xe2,0xd1,0xe8,0xe1,0xc0,0xe8,0x10,0x09,0x05,0xff,0xf0,0xa6, + 0xbe,0xb1,0x00,0x05,0xff,0xf0,0xa7,0x83,0x92,0x00,0xd2,0x13,0xe1,0xe9,0xe8,0x10, + 0x08,0x05,0xff,0xe8,0x9a,0x88,0x00,0x05,0xff,0xe8,0x9c,0x8e,0x00,0xd1,0x10,0x10, + 0x08,0x05,0xff,0xe8,0x9c,0xa8,0x00,0x05,0xff,0xe8,0x9d,0xab,0x00,0x10,0x08,0x05, + 0xff,0xe8,0x9e,0x86,0x00,0x05,0xff,0xe4,0xb5,0x97,0x00,0x00,0x00,0x00,0x00,0x00, + /* nfdi_30200 */ + 0x57,0x04,0x01,0x00,0xc6,0xd5,0x16,0xe4,0x82,0x53,0xe3,0xbb,0x4e,0xe2,0x34,0x49, + 0xc1,0xe0,0x60,0x47,0xcf,0x86,0x65,0x44,0x47,0x01,0x00,0xd4,0x2a,0xe3,0x1c,0x9a, + 0xe2,0xcb,0x99,0xe1,0x9e,0x87,0xe0,0xf8,0x6a,0xcf,0x86,0xc5,0xe4,0x57,0x63,0xe3, + 0xa2,0x5e,0xe2,0x38,0x5c,0xe1,0x6b,0x5b,0xe0,0x30,0x5b,0xcf,0x86,0xe5,0xf5,0x5a, + 0x64,0xd8,0x5a,0x0b,0x00,0x83,0xe2,0xea,0xf0,0xe1,0xc3,0xed,0xe0,0x40,0xec,0xcf, + 0x86,0xd5,0x31,0xc4,0xe3,0xbb,0xc6,0xe2,0x94,0xc4,0xe1,0x75,0xc3,0xe0,0x05,0xba, + 0xcf,0x86,0xe5,0xf8,0xb5,0xe4,0xf1,0xb4,0xe3,0xe2,0xb3,0xe2,0x39,0xb3,0xe1,0x14, + 0xb3,0xe0,0xed,0xb2,0xcf,0x86,0xe5,0xba,0xb2,0x94,0x07,0x63,0xa5,0xb2,0x07,0x00, + 0x07,0x00,0xe4,0xac,0xeb,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x05,0x00,0xd2,0x0b,0xe1, + 0xbb,0xd8,0xcf,0x86,0xcf,0x06,0x05,0x00,0xd1,0x0e,0xe0,0xaa,0xd9,0xcf,0x86,0xe5, + 0x6f,0xd9,0xcf,0x06,0x11,0x00,0xd0,0x0b,0xcf,0x86,0xe5,0xaa,0xd9,0xcf,0x06,0x13, + 0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xe4,0x45,0xeb,0xe3,0x2e,0xea,0xd2, + 0xa0,0xe1,0xe4,0xdd,0xd0,0x21,0xcf,0x86,0xe5,0xe5,0xda,0xe4,0x61,0xda,0xe3,0x1f, + 0xda,0xe2,0xfe,0xd9,0xe1,0xec,0xd9,0x10,0x08,0x05,0xff,0xe4,0xb8,0xbd,0x00,0x05, + 0xff,0xe4,0xb8,0xb8,0x00,0xcf,0x86,0xd5,0x1c,0xe4,0x41,0xdc,0xe3,0x00,0xdc,0xe2, + 0xdf,0xdb,0xe1,0xce,0xdb,0x10,0x08,0x05,0xff,0xe5,0x92,0xa2,0x00,0x05,0xff,0xe5, + 0x93,0xb6,0x00,0xd4,0x34,0xd3,0x18,0xe2,0xc8,0xdc,0xe1,0xb7,0xdc,0x10,0x09,0x05, + 0xff,0xf0,0xa1,0x9a,0xa8,0x00,0x05,0xff,0xf0,0xa1,0x9b,0xaa,0x00,0xe2,0xe8,0xdc, + 0x91,0x11,0x10,0x09,0x05,0xff,0xf0,0xa1,0x8d,0xaa,0x00,0x05,0xff,0xe5,0xac,0x88, + 0x00,0x05,0xff,0xe5,0xac,0xbe,0x00,0xe3,0x2e,0xdd,0xd2,0x14,0xe1,0xfd,0xdc,0x10, + 0x08,0x05,0xff,0xe5,0xaf,0xb3,0x00,0x05,0xff,0xf0,0xa1,0xac,0x98,0x00,0xe1,0x09, + 0xdd,0x10,0x08,0x05,0xff,0xe5,0xbc,0xb3,0x00,0x05,0xff,0xe5,0xb0,0xa2,0x00,0xd1, + 0xd5,0xd0,0x6a,0xcf,0x86,0xe5,0x5e,0xe2,0xd4,0x19,0xe3,0x97,0xe1,0xe2,0x75,0xe1, + 0xe1,0x64,0xe1,0x10,0x08,0x05,0xff,0xe6,0xb4,0xbe,0x00,0x05,0xff,0xe6,0xb5,0xb7, + 0x00,0xd3,0x18,0xe2,0xe1,0xe1,0xe1,0xd0,0xe1,0x10,0x09,0x05,0xff,0xf0,0xa3,0xbd, + 0x9e,0x00,0x05,0xff,0xf0,0xa3,0xbe,0x8e,0x00,0xd2,0x13,0xe1,0xf9,0xe1,0x10,0x08, + 0x05,0xff,0xe7,0x81,0xbd,0x00,0x05,0xff,0xe7,0x81,0xb7,0x00,0xd1,0x11,0x10,0x08, + 0x05,0xff,0xe7,0x85,0x85,0x00,0x05,0xff,0xf0,0xa4,0x89,0xa3,0x00,0x10,0x08,0x05, + 0xff,0xe7,0x86,0x9c,0x00,0x05,0xff,0xe4,0x8e,0xab,0x00,0xcf,0x86,0xe5,0xfb,0xe3, + 0xd4,0x1a,0xe3,0x33,0xe3,0xe2,0x19,0xe3,0xe1,0x06,0xe3,0x10,0x08,0x05,0xff,0xe7, + 0x9b,0xb4,0x00,0x05,0xff,0xf0,0xa5,0x83,0xb3,0x00,0xd3,0x16,0xe2,0x7b,0xe3,0xe1, + 0x69,0xe3,0x10,0x08,0x05,0xff,0xe7,0xa3,0x8c,0x00,0x05,0xff,0xe4,0x83,0xa3,0x00, + 0xd2,0x13,0xe1,0x97,0xe3,0x10,0x08,0x05,0xff,0xe4,0x84,0xaf,0x00,0x05,0xff,0xe7, + 0xa9,0x80,0x00,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa5,0xa5,0xbc,0x00,0x05,0xff, + 0xf0,0xa5,0xaa,0xa7,0x00,0x10,0x09,0x05,0xff,0xf0,0xa5,0xaa,0xa7,0x00,0x05,0xff, + 0xe7,0xaa,0xae,0x00,0xe0,0xad,0xe6,0xcf,0x86,0xd5,0x1d,0xe4,0x22,0xe5,0xe3,0xde, + 0xe4,0xe2,0xbc,0xe4,0xe1,0xab,0xe4,0x10,0x09,0x05,0xff,0xf0,0xa3,0x8d,0x9f,0x00, + 0x05,0xff,0xe4,0x8f,0x95,0x00,0xd4,0x19,0xe3,0xc9,0xe5,0xe2,0xa5,0xe5,0xe1,0x94, + 0xe5,0x10,0x08,0x05,0xff,0xe8,0x8d,0x93,0x00,0x05,0xff,0xe8,0x8f,0x8a,0x00,0xd3, + 0x18,0xe2,0x14,0xe6,0xe1,0x03,0xe6,0x10,0x09,0x05,0xff,0xf0,0xa6,0xbe,0xb1,0x00, + 0x05,0xff,0xf0,0xa7,0x83,0x92,0x00,0xd2,0x13,0xe1,0x2c,0xe6,0x10,0x08,0x05,0xff, + 0xe8,0x9a,0x88,0x00,0x05,0xff,0xe8,0x9c,0x8e,0x00,0xd1,0x10,0x10,0x08,0x05,0xff, + 0xe8,0x9c,0xa8,0x00,0x05,0xff,0xe8,0x9d,0xab,0x00,0x10,0x08,0x05,0xff,0xe8,0x9e, + 0x86,0x00,0x05,0xff,0xe4,0xb5,0x97,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, + /* nfdicf_c0100 */ + 0xd7,0xb0,0x56,0x04,0x01,0x00,0x95,0xa8,0xd4,0x5e,0xd3,0x2e,0xd2,0x16,0xd1,0x0a, + 0x10,0x04,0x01,0x00,0x01,0xff,0x61,0x00,0x10,0x06,0x01,0xff,0x62,0x00,0x01,0xff, + 0x63,0x00,0xd1,0x0c,0x10,0x06,0x01,0xff,0x64,0x00,0x01,0xff,0x65,0x00,0x10,0x06, + 0x01,0xff,0x66,0x00,0x01,0xff,0x67,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x06,0x01,0xff, + 0x68,0x00,0x01,0xff,0x69,0x00,0x10,0x06,0x01,0xff,0x6a,0x00,0x01,0xff,0x6b,0x00, + 0xd1,0x0c,0x10,0x06,0x01,0xff,0x6c,0x00,0x01,0xff,0x6d,0x00,0x10,0x06,0x01,0xff, + 0x6e,0x00,0x01,0xff,0x6f,0x00,0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x06,0x01,0xff, + 0x70,0x00,0x01,0xff,0x71,0x00,0x10,0x06,0x01,0xff,0x72,0x00,0x01,0xff,0x73,0x00, + 0xd1,0x0c,0x10,0x06,0x01,0xff,0x74,0x00,0x01,0xff,0x75,0x00,0x10,0x06,0x01,0xff, + 0x76,0x00,0x01,0xff,0x77,0x00,0x92,0x16,0xd1,0x0c,0x10,0x06,0x01,0xff,0x78,0x00, + 0x01,0xff,0x79,0x00,0x10,0x06,0x01,0xff,0x7a,0x00,0x01,0x00,0x01,0x00,0x01,0x00, + 0xc6,0xe5,0xf9,0x14,0xe4,0x6f,0x0d,0xe3,0x39,0x08,0xe2,0x22,0x01,0xc1,0xd0,0x24, + 0xcf,0x86,0x55,0x04,0x01,0x00,0xd4,0x07,0x63,0xd8,0x43,0x01,0x00,0x93,0x13,0x52, + 0x04,0x01,0x00,0x91,0x0b,0x10,0x04,0x01,0x00,0x01,0xff,0xce,0xbc,0x00,0x01,0x00, + 0x01,0x00,0xcf,0x86,0xe5,0xb3,0x44,0xd4,0x7f,0xd3,0x3f,0xd2,0x20,0xd1,0x10,0x10, + 0x08,0x01,0xff,0x61,0xcc,0x80,0x00,0x01,0xff,0x61,0xcc,0x81,0x00,0x10,0x08,0x01, + 0xff,0x61,0xcc,0x82,0x00,0x01,0xff,0x61,0xcc,0x83,0x00,0xd1,0x10,0x10,0x08,0x01, + 0xff,0x61,0xcc,0x88,0x00,0x01,0xff,0x61,0xcc,0x8a,0x00,0x10,0x07,0x01,0xff,0xc3, + 0xa6,0x00,0x01,0xff,0x63,0xcc,0xa7,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff, + 0x65,0xcc,0x80,0x00,0x01,0xff,0x65,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x65,0xcc, + 0x82,0x00,0x01,0xff,0x65,0xcc,0x88,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x69,0xcc, + 0x80,0x00,0x01,0xff,0x69,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x69,0xcc,0x82,0x00, + 0x01,0xff,0x69,0xcc,0x88,0x00,0xd3,0x3b,0xd2,0x1f,0xd1,0x0f,0x10,0x07,0x01,0xff, + 0xc3,0xb0,0x00,0x01,0xff,0x6e,0xcc,0x83,0x00,0x10,0x08,0x01,0xff,0x6f,0xcc,0x80, + 0x00,0x01,0xff,0x6f,0xcc,0x81,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x6f,0xcc,0x82, + 0x00,0x01,0xff,0x6f,0xcc,0x83,0x00,0x10,0x08,0x01,0xff,0x6f,0xcc,0x88,0x00,0x01, + 0x00,0xd2,0x1f,0xd1,0x0f,0x10,0x07,0x01,0xff,0xc3,0xb8,0x00,0x01,0xff,0x75,0xcc, + 0x80,0x00,0x10,0x08,0x01,0xff,0x75,0xcc,0x81,0x00,0x01,0xff,0x75,0xcc,0x82,0x00, + 0xd1,0x10,0x10,0x08,0x01,0xff,0x75,0xcc,0x88,0x00,0x01,0xff,0x79,0xcc,0x81,0x00, + 0x10,0x07,0x01,0xff,0xc3,0xbe,0x00,0x01,0xff,0x73,0x73,0x00,0xe1,0xd4,0x03,0xe0, + 0xeb,0x01,0xcf,0x86,0xd5,0xfb,0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08, + 0x01,0xff,0x61,0xcc,0x84,0x00,0x01,0xff,0x61,0xcc,0x84,0x00,0x10,0x08,0x01,0xff, + 0x61,0xcc,0x86,0x00,0x01,0xff,0x61,0xcc,0x86,0x00,0xd1,0x10,0x10,0x08,0x01,0xff, + 0x61,0xcc,0xa8,0x00,0x01,0xff,0x61,0xcc,0xa8,0x00,0x10,0x08,0x01,0xff,0x63,0xcc, + 0x81,0x00,0x01,0xff,0x63,0xcc,0x81,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff, + 0x63,0xcc,0x82,0x00,0x01,0xff,0x63,0xcc,0x82,0x00,0x10,0x08,0x01,0xff,0x63,0xcc, + 0x87,0x00,0x01,0xff,0x63,0xcc,0x87,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x63,0xcc, + 0x8c,0x00,0x01,0xff,0x63,0xcc,0x8c,0x00,0x10,0x08,0x01,0xff,0x64,0xcc,0x8c,0x00, + 0x01,0xff,0x64,0xcc,0x8c,0x00,0xd3,0x3b,0xd2,0x1b,0xd1,0x0b,0x10,0x07,0x01,0xff, + 0xc4,0x91,0x00,0x01,0x00,0x10,0x08,0x01,0xff,0x65,0xcc,0x84,0x00,0x01,0xff,0x65, + 0xcc,0x84,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x65,0xcc,0x86,0x00,0x01,0xff,0x65, + 0xcc,0x86,0x00,0x10,0x08,0x01,0xff,0x65,0xcc,0x87,0x00,0x01,0xff,0x65,0xcc,0x87, + 0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x65,0xcc,0xa8,0x00,0x01,0xff,0x65, + 0xcc,0xa8,0x00,0x10,0x08,0x01,0xff,0x65,0xcc,0x8c,0x00,0x01,0xff,0x65,0xcc,0x8c, + 0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x67,0xcc,0x82,0x00,0x01,0xff,0x67,0xcc,0x82, + 0x00,0x10,0x08,0x01,0xff,0x67,0xcc,0x86,0x00,0x01,0xff,0x67,0xcc,0x86,0x00,0xd4, + 0x7b,0xd3,0x3b,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x67,0xcc,0x87,0x00,0x01, + 0xff,0x67,0xcc,0x87,0x00,0x10,0x08,0x01,0xff,0x67,0xcc,0xa7,0x00,0x01,0xff,0x67, + 0xcc,0xa7,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x68,0xcc,0x82,0x00,0x01,0xff,0x68, + 0xcc,0x82,0x00,0x10,0x07,0x01,0xff,0xc4,0xa7,0x00,0x01,0x00,0xd2,0x20,0xd1,0x10, + 0x10,0x08,0x01,0xff,0x69,0xcc,0x83,0x00,0x01,0xff,0x69,0xcc,0x83,0x00,0x10,0x08, + 0x01,0xff,0x69,0xcc,0x84,0x00,0x01,0xff,0x69,0xcc,0x84,0x00,0xd1,0x10,0x10,0x08, + 0x01,0xff,0x69,0xcc,0x86,0x00,0x01,0xff,0x69,0xcc,0x86,0x00,0x10,0x08,0x01,0xff, + 0x69,0xcc,0xa8,0x00,0x01,0xff,0x69,0xcc,0xa8,0x00,0xd3,0x37,0xd2,0x17,0xd1,0x0c, + 0x10,0x08,0x01,0xff,0x69,0xcc,0x87,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xc4,0xb3, + 0x00,0x01,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x6a,0xcc,0x82,0x00,0x01,0xff,0x6a, + 0xcc,0x82,0x00,0x10,0x08,0x01,0xff,0x6b,0xcc,0xa7,0x00,0x01,0xff,0x6b,0xcc,0xa7, + 0x00,0xd2,0x1c,0xd1,0x0c,0x10,0x04,0x01,0x00,0x01,0xff,0x6c,0xcc,0x81,0x00,0x10, + 0x08,0x01,0xff,0x6c,0xcc,0x81,0x00,0x01,0xff,0x6c,0xcc,0xa7,0x00,0xd1,0x10,0x10, + 0x08,0x01,0xff,0x6c,0xcc,0xa7,0x00,0x01,0xff,0x6c,0xcc,0x8c,0x00,0x10,0x08,0x01, + 0xff,0x6c,0xcc,0x8c,0x00,0x01,0xff,0xc5,0x80,0x00,0xcf,0x86,0xd5,0xed,0xd4,0x72, + 0xd3,0x37,0xd2,0x17,0xd1,0x0b,0x10,0x04,0x01,0x00,0x01,0xff,0xc5,0x82,0x00,0x10, + 0x04,0x01,0x00,0x01,0xff,0x6e,0xcc,0x81,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x6e, + 0xcc,0x81,0x00,0x01,0xff,0x6e,0xcc,0xa7,0x00,0x10,0x08,0x01,0xff,0x6e,0xcc,0xa7, + 0x00,0x01,0xff,0x6e,0xcc,0x8c,0x00,0xd2,0x1b,0xd1,0x10,0x10,0x08,0x01,0xff,0x6e, + 0xcc,0x8c,0x00,0x01,0xff,0xca,0xbc,0x6e,0x00,0x10,0x07,0x01,0xff,0xc5,0x8b,0x00, + 0x01,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x6f,0xcc,0x84,0x00,0x01,0xff,0x6f,0xcc, + 0x84,0x00,0x10,0x08,0x01,0xff,0x6f,0xcc,0x86,0x00,0x01,0xff,0x6f,0xcc,0x86,0x00, + 0xd3,0x3b,0xd2,0x1b,0xd1,0x10,0x10,0x08,0x01,0xff,0x6f,0xcc,0x8b,0x00,0x01,0xff, + 0x6f,0xcc,0x8b,0x00,0x10,0x07,0x01,0xff,0xc5,0x93,0x00,0x01,0x00,0xd1,0x10,0x10, + 0x08,0x01,0xff,0x72,0xcc,0x81,0x00,0x01,0xff,0x72,0xcc,0x81,0x00,0x10,0x08,0x01, + 0xff,0x72,0xcc,0xa7,0x00,0x01,0xff,0x72,0xcc,0xa7,0x00,0xd2,0x20,0xd1,0x10,0x10, + 0x08,0x01,0xff,0x72,0xcc,0x8c,0x00,0x01,0xff,0x72,0xcc,0x8c,0x00,0x10,0x08,0x01, + 0xff,0x73,0xcc,0x81,0x00,0x01,0xff,0x73,0xcc,0x81,0x00,0xd1,0x10,0x10,0x08,0x01, + 0xff,0x73,0xcc,0x82,0x00,0x01,0xff,0x73,0xcc,0x82,0x00,0x10,0x08,0x01,0xff,0x73, + 0xcc,0xa7,0x00,0x01,0xff,0x73,0xcc,0xa7,0x00,0xd4,0x7b,0xd3,0x3b,0xd2,0x20,0xd1, + 0x10,0x10,0x08,0x01,0xff,0x73,0xcc,0x8c,0x00,0x01,0xff,0x73,0xcc,0x8c,0x00,0x10, + 0x08,0x01,0xff,0x74,0xcc,0xa7,0x00,0x01,0xff,0x74,0xcc,0xa7,0x00,0xd1,0x10,0x10, + 0x08,0x01,0xff,0x74,0xcc,0x8c,0x00,0x01,0xff,0x74,0xcc,0x8c,0x00,0x10,0x07,0x01, + 0xff,0xc5,0xa7,0x00,0x01,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x75,0xcc, + 0x83,0x00,0x01,0xff,0x75,0xcc,0x83,0x00,0x10,0x08,0x01,0xff,0x75,0xcc,0x84,0x00, + 0x01,0xff,0x75,0xcc,0x84,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x75,0xcc,0x86,0x00, + 0x01,0xff,0x75,0xcc,0x86,0x00,0x10,0x08,0x01,0xff,0x75,0xcc,0x8a,0x00,0x01,0xff, + 0x75,0xcc,0x8a,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x75,0xcc, + 0x8b,0x00,0x01,0xff,0x75,0xcc,0x8b,0x00,0x10,0x08,0x01,0xff,0x75,0xcc,0xa8,0x00, + 0x01,0xff,0x75,0xcc,0xa8,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x77,0xcc,0x82,0x00, + 0x01,0xff,0x77,0xcc,0x82,0x00,0x10,0x08,0x01,0xff,0x79,0xcc,0x82,0x00,0x01,0xff, + 0x79,0xcc,0x82,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x79,0xcc,0x88,0x00, + 0x01,0xff,0x7a,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x7a,0xcc,0x81,0x00,0x01,0xff, + 0x7a,0xcc,0x87,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x7a,0xcc,0x87,0x00,0x01,0xff, + 0x7a,0xcc,0x8c,0x00,0x10,0x08,0x01,0xff,0x7a,0xcc,0x8c,0x00,0x01,0xff,0x73,0x00, + 0xe0,0x65,0x01,0xcf,0x86,0xd5,0xb4,0xd4,0x5a,0xd3,0x2f,0xd2,0x16,0xd1,0x0b,0x10, + 0x04,0x01,0x00,0x01,0xff,0xc9,0x93,0x00,0x10,0x07,0x01,0xff,0xc6,0x83,0x00,0x01, + 0x00,0xd1,0x0b,0x10,0x07,0x01,0xff,0xc6,0x85,0x00,0x01,0x00,0x10,0x07,0x01,0xff, + 0xc9,0x94,0x00,0x01,0xff,0xc6,0x88,0x00,0xd2,0x19,0xd1,0x0b,0x10,0x04,0x01,0x00, + 0x01,0xff,0xc9,0x96,0x00,0x10,0x07,0x01,0xff,0xc9,0x97,0x00,0x01,0xff,0xc6,0x8c, + 0x00,0x51,0x04,0x01,0x00,0x10,0x07,0x01,0xff,0xc7,0x9d,0x00,0x01,0xff,0xc9,0x99, + 0x00,0xd3,0x32,0xd2,0x19,0xd1,0x0e,0x10,0x07,0x01,0xff,0xc9,0x9b,0x00,0x01,0xff, + 0xc6,0x92,0x00,0x10,0x04,0x01,0x00,0x01,0xff,0xc9,0xa0,0x00,0xd1,0x0b,0x10,0x07, + 0x01,0xff,0xc9,0xa3,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xc9,0xa9,0x00,0x01,0xff, + 0xc9,0xa8,0x00,0xd2,0x0f,0x91,0x0b,0x10,0x07,0x01,0xff,0xc6,0x99,0x00,0x01,0x00, + 0x01,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff,0xc9,0xaf,0x00,0x01,0xff,0xc9,0xb2,0x00, + 0x10,0x04,0x01,0x00,0x01,0xff,0xc9,0xb5,0x00,0xd4,0x5d,0xd3,0x34,0xd2,0x1b,0xd1, + 0x10,0x10,0x08,0x01,0xff,0x6f,0xcc,0x9b,0x00,0x01,0xff,0x6f,0xcc,0x9b,0x00,0x10, + 0x07,0x01,0xff,0xc6,0xa3,0x00,0x01,0x00,0xd1,0x0b,0x10,0x07,0x01,0xff,0xc6,0xa5, + 0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xca,0x80,0x00,0x01,0xff,0xc6,0xa8,0x00,0xd2, + 0x0f,0x91,0x0b,0x10,0x04,0x01,0x00,0x01,0xff,0xca,0x83,0x00,0x01,0x00,0xd1,0x0b, + 0x10,0x07,0x01,0xff,0xc6,0xad,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xca,0x88,0x00, + 0x01,0xff,0x75,0xcc,0x9b,0x00,0xd3,0x33,0xd2,0x1d,0xd1,0x0f,0x10,0x08,0x01,0xff, + 0x75,0xcc,0x9b,0x00,0x01,0xff,0xca,0x8a,0x00,0x10,0x07,0x01,0xff,0xca,0x8b,0x00, + 0x01,0xff,0xc6,0xb4,0x00,0xd1,0x0b,0x10,0x04,0x01,0x00,0x01,0xff,0xc6,0xb6,0x00, + 0x10,0x04,0x01,0x00,0x01,0xff,0xca,0x92,0x00,0xd2,0x0f,0x91,0x0b,0x10,0x07,0x01, + 0xff,0xc6,0xb9,0x00,0x01,0x00,0x01,0x00,0x91,0x0b,0x10,0x07,0x01,0xff,0xc6,0xbd, + 0x00,0x01,0x00,0x01,0x00,0xcf,0x86,0xd5,0xd4,0xd4,0x44,0xd3,0x16,0x52,0x04,0x01, + 0x00,0x51,0x07,0x01,0xff,0xc7,0x86,0x00,0x10,0x04,0x01,0x00,0x01,0xff,0xc7,0x89, + 0x00,0xd2,0x12,0x91,0x0b,0x10,0x07,0x01,0xff,0xc7,0x89,0x00,0x01,0x00,0x01,0xff, + 0xc7,0x8c,0x00,0xd1,0x0c,0x10,0x04,0x01,0x00,0x01,0xff,0x61,0xcc,0x8c,0x00,0x10, + 0x08,0x01,0xff,0x61,0xcc,0x8c,0x00,0x01,0xff,0x69,0xcc,0x8c,0x00,0xd3,0x46,0xd2, + 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x69,0xcc,0x8c,0x00,0x01,0xff,0x6f,0xcc,0x8c, + 0x00,0x10,0x08,0x01,0xff,0x6f,0xcc,0x8c,0x00,0x01,0xff,0x75,0xcc,0x8c,0x00,0xd1, + 0x12,0x10,0x08,0x01,0xff,0x75,0xcc,0x8c,0x00,0x01,0xff,0x75,0xcc,0x88,0xcc,0x84, + 0x00,0x10,0x0a,0x01,0xff,0x75,0xcc,0x88,0xcc,0x84,0x00,0x01,0xff,0x75,0xcc,0x88, + 0xcc,0x81,0x00,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x75,0xcc,0x88,0xcc,0x81, + 0x00,0x01,0xff,0x75,0xcc,0x88,0xcc,0x8c,0x00,0x10,0x0a,0x01,0xff,0x75,0xcc,0x88, + 0xcc,0x8c,0x00,0x01,0xff,0x75,0xcc,0x88,0xcc,0x80,0x00,0xd1,0x0e,0x10,0x0a,0x01, + 0xff,0x75,0xcc,0x88,0xcc,0x80,0x00,0x01,0x00,0x10,0x0a,0x01,0xff,0x61,0xcc,0x88, + 0xcc,0x84,0x00,0x01,0xff,0x61,0xcc,0x88,0xcc,0x84,0x00,0xd4,0x87,0xd3,0x41,0xd2, + 0x26,0xd1,0x14,0x10,0x0a,0x01,0xff,0x61,0xcc,0x87,0xcc,0x84,0x00,0x01,0xff,0x61, + 0xcc,0x87,0xcc,0x84,0x00,0x10,0x09,0x01,0xff,0xc3,0xa6,0xcc,0x84,0x00,0x01,0xff, + 0xc3,0xa6,0xcc,0x84,0x00,0xd1,0x0b,0x10,0x07,0x01,0xff,0xc7,0xa5,0x00,0x01,0x00, + 0x10,0x08,0x01,0xff,0x67,0xcc,0x8c,0x00,0x01,0xff,0x67,0xcc,0x8c,0x00,0xd2,0x20, + 0xd1,0x10,0x10,0x08,0x01,0xff,0x6b,0xcc,0x8c,0x00,0x01,0xff,0x6b,0xcc,0x8c,0x00, + 0x10,0x08,0x01,0xff,0x6f,0xcc,0xa8,0x00,0x01,0xff,0x6f,0xcc,0xa8,0x00,0xd1,0x14, + 0x10,0x0a,0x01,0xff,0x6f,0xcc,0xa8,0xcc,0x84,0x00,0x01,0xff,0x6f,0xcc,0xa8,0xcc, + 0x84,0x00,0x10,0x09,0x01,0xff,0xca,0x92,0xcc,0x8c,0x00,0x01,0xff,0xca,0x92,0xcc, + 0x8c,0x00,0xd3,0x38,0xd2,0x1a,0xd1,0x0f,0x10,0x08,0x01,0xff,0x6a,0xcc,0x8c,0x00, + 0x01,0xff,0xc7,0xb3,0x00,0x10,0x07,0x01,0xff,0xc7,0xb3,0x00,0x01,0x00,0xd1,0x10, + 0x10,0x08,0x01,0xff,0x67,0xcc,0x81,0x00,0x01,0xff,0x67,0xcc,0x81,0x00,0x10,0x07, + 0x04,0xff,0xc6,0x95,0x00,0x04,0xff,0xc6,0xbf,0x00,0xd2,0x24,0xd1,0x10,0x10,0x08, + 0x04,0xff,0x6e,0xcc,0x80,0x00,0x04,0xff,0x6e,0xcc,0x80,0x00,0x10,0x0a,0x01,0xff, + 0x61,0xcc,0x8a,0xcc,0x81,0x00,0x01,0xff,0x61,0xcc,0x8a,0xcc,0x81,0x00,0xd1,0x12, + 0x10,0x09,0x01,0xff,0xc3,0xa6,0xcc,0x81,0x00,0x01,0xff,0xc3,0xa6,0xcc,0x81,0x00, + 0x10,0x09,0x01,0xff,0xc3,0xb8,0xcc,0x81,0x00,0x01,0xff,0xc3,0xb8,0xcc,0x81,0x00, + 0xe2,0x31,0x02,0xe1,0xc3,0x44,0xe0,0xc8,0x01,0xcf,0x86,0xd5,0xfb,0xd4,0x80,0xd3, + 0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x61,0xcc,0x8f,0x00,0x01,0xff,0x61, + 0xcc,0x8f,0x00,0x10,0x08,0x01,0xff,0x61,0xcc,0x91,0x00,0x01,0xff,0x61,0xcc,0x91, + 0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x65,0xcc,0x8f,0x00,0x01,0xff,0x65,0xcc,0x8f, + 0x00,0x10,0x08,0x01,0xff,0x65,0xcc,0x91,0x00,0x01,0xff,0x65,0xcc,0x91,0x00,0xd2, + 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x69,0xcc,0x8f,0x00,0x01,0xff,0x69,0xcc,0x8f, + 0x00,0x10,0x08,0x01,0xff,0x69,0xcc,0x91,0x00,0x01,0xff,0x69,0xcc,0x91,0x00,0xd1, + 0x10,0x10,0x08,0x01,0xff,0x6f,0xcc,0x8f,0x00,0x01,0xff,0x6f,0xcc,0x8f,0x00,0x10, + 0x08,0x01,0xff,0x6f,0xcc,0x91,0x00,0x01,0xff,0x6f,0xcc,0x91,0x00,0xd3,0x40,0xd2, + 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x72,0xcc,0x8f,0x00,0x01,0xff,0x72,0xcc,0x8f, + 0x00,0x10,0x08,0x01,0xff,0x72,0xcc,0x91,0x00,0x01,0xff,0x72,0xcc,0x91,0x00,0xd1, + 0x10,0x10,0x08,0x01,0xff,0x75,0xcc,0x8f,0x00,0x01,0xff,0x75,0xcc,0x8f,0x00,0x10, + 0x08,0x01,0xff,0x75,0xcc,0x91,0x00,0x01,0xff,0x75,0xcc,0x91,0x00,0xd2,0x20,0xd1, + 0x10,0x10,0x08,0x04,0xff,0x73,0xcc,0xa6,0x00,0x04,0xff,0x73,0xcc,0xa6,0x00,0x10, + 0x08,0x04,0xff,0x74,0xcc,0xa6,0x00,0x04,0xff,0x74,0xcc,0xa6,0x00,0xd1,0x0b,0x10, + 0x07,0x04,0xff,0xc8,0x9d,0x00,0x04,0x00,0x10,0x08,0x04,0xff,0x68,0xcc,0x8c,0x00, + 0x04,0xff,0x68,0xcc,0x8c,0x00,0xd4,0x79,0xd3,0x31,0xd2,0x16,0xd1,0x0b,0x10,0x07, + 0x06,0xff,0xc6,0x9e,0x00,0x07,0x00,0x10,0x07,0x04,0xff,0xc8,0xa3,0x00,0x04,0x00, + 0xd1,0x0b,0x10,0x07,0x04,0xff,0xc8,0xa5,0x00,0x04,0x00,0x10,0x08,0x04,0xff,0x61, + 0xcc,0x87,0x00,0x04,0xff,0x61,0xcc,0x87,0x00,0xd2,0x24,0xd1,0x10,0x10,0x08,0x04, + 0xff,0x65,0xcc,0xa7,0x00,0x04,0xff,0x65,0xcc,0xa7,0x00,0x10,0x0a,0x04,0xff,0x6f, + 0xcc,0x88,0xcc,0x84,0x00,0x04,0xff,0x6f,0xcc,0x88,0xcc,0x84,0x00,0xd1,0x14,0x10, + 0x0a,0x04,0xff,0x6f,0xcc,0x83,0xcc,0x84,0x00,0x04,0xff,0x6f,0xcc,0x83,0xcc,0x84, + 0x00,0x10,0x08,0x04,0xff,0x6f,0xcc,0x87,0x00,0x04,0xff,0x6f,0xcc,0x87,0x00,0xd3, + 0x27,0xe2,0x21,0x43,0xd1,0x14,0x10,0x0a,0x04,0xff,0x6f,0xcc,0x87,0xcc,0x84,0x00, + 0x04,0xff,0x6f,0xcc,0x87,0xcc,0x84,0x00,0x10,0x08,0x04,0xff,0x79,0xcc,0x84,0x00, + 0x04,0xff,0x79,0xcc,0x84,0x00,0xd2,0x13,0x51,0x04,0x08,0x00,0x10,0x08,0x08,0xff, + 0xe2,0xb1,0xa5,0x00,0x08,0xff,0xc8,0xbc,0x00,0xd1,0x0b,0x10,0x04,0x08,0x00,0x08, + 0xff,0xc6,0x9a,0x00,0x10,0x08,0x08,0xff,0xe2,0xb1,0xa6,0x00,0x08,0x00,0xcf,0x86, + 0x95,0x5f,0x94,0x5b,0xd3,0x2f,0xd2,0x16,0xd1,0x0b,0x10,0x04,0x08,0x00,0x08,0xff, + 0xc9,0x82,0x00,0x10,0x04,0x09,0x00,0x09,0xff,0xc6,0x80,0x00,0xd1,0x0e,0x10,0x07, + 0x09,0xff,0xca,0x89,0x00,0x09,0xff,0xca,0x8c,0x00,0x10,0x07,0x09,0xff,0xc9,0x87, + 0x00,0x09,0x00,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x09,0xff,0xc9,0x89,0x00,0x09,0x00, + 0x10,0x07,0x09,0xff,0xc9,0x8b,0x00,0x09,0x00,0xd1,0x0b,0x10,0x07,0x09,0xff,0xc9, + 0x8d,0x00,0x09,0x00,0x10,0x07,0x09,0xff,0xc9,0x8f,0x00,0x09,0x00,0x01,0x00,0x01, + 0x00,0xd1,0x8b,0xd0,0x0c,0xcf,0x86,0xe5,0x10,0x43,0x64,0xef,0x42,0x01,0xe6,0xcf, + 0x86,0xd5,0x2a,0xe4,0x99,0x43,0xe3,0x7f,0x43,0xd2,0x11,0xe1,0x5e,0x43,0x10,0x07, + 0x01,0xff,0xcc,0x80,0x00,0x01,0xff,0xcc,0x81,0x00,0xe1,0x65,0x43,0x10,0x09,0x01, + 0xff,0xcc,0x88,0xcc,0x81,0x00,0x01,0xff,0xce,0xb9,0x00,0xd4,0x0f,0x93,0x0b,0x92, + 0x07,0x61,0xab,0x43,0x01,0xea,0x06,0xe6,0x06,0xe6,0xd3,0x2c,0xd2,0x16,0xd1,0x0b, + 0x10,0x07,0x0a,0xff,0xcd,0xb1,0x00,0x0a,0x00,0x10,0x07,0x0a,0xff,0xcd,0xb3,0x00, + 0x0a,0x00,0xd1,0x0b,0x10,0x07,0x01,0xff,0xca,0xb9,0x00,0x01,0x00,0x10,0x07,0x0a, + 0xff,0xcd,0xb7,0x00,0x0a,0x00,0xd2,0x07,0x61,0x97,0x43,0x00,0x00,0x51,0x04,0x09, + 0x00,0x10,0x06,0x01,0xff,0x3b,0x00,0x10,0xff,0xcf,0xb3,0x00,0xe0,0x31,0x01,0xcf, + 0x86,0xd5,0xd3,0xd4,0x5f,0xd3,0x21,0x52,0x04,0x00,0x00,0xd1,0x0d,0x10,0x04,0x01, + 0x00,0x01,0xff,0xc2,0xa8,0xcc,0x81,0x00,0x10,0x09,0x01,0xff,0xce,0xb1,0xcc,0x81, + 0x00,0x01,0xff,0xc2,0xb7,0x00,0xd2,0x1f,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb5, + 0xcc,0x81,0x00,0x01,0xff,0xce,0xb7,0xcc,0x81,0x00,0x10,0x09,0x01,0xff,0xce,0xb9, + 0xcc,0x81,0x00,0x00,0x00,0xd1,0x0d,0x10,0x09,0x01,0xff,0xce,0xbf,0xcc,0x81,0x00, + 0x00,0x00,0x10,0x09,0x01,0xff,0xcf,0x85,0xcc,0x81,0x00,0x01,0xff,0xcf,0x89,0xcc, + 0x81,0x00,0xd3,0x3c,0xd2,0x20,0xd1,0x12,0x10,0x0b,0x01,0xff,0xce,0xb9,0xcc,0x88, + 0xcc,0x81,0x00,0x01,0xff,0xce,0xb1,0x00,0x10,0x07,0x01,0xff,0xce,0xb2,0x00,0x01, + 0xff,0xce,0xb3,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff,0xce,0xb4,0x00,0x01,0xff,0xce, + 0xb5,0x00,0x10,0x07,0x01,0xff,0xce,0xb6,0x00,0x01,0xff,0xce,0xb7,0x00,0xd2,0x1c, + 0xd1,0x0e,0x10,0x07,0x01,0xff,0xce,0xb8,0x00,0x01,0xff,0xce,0xb9,0x00,0x10,0x07, + 0x01,0xff,0xce,0xba,0x00,0x01,0xff,0xce,0xbb,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff, + 0xce,0xbc,0x00,0x01,0xff,0xce,0xbd,0x00,0x10,0x07,0x01,0xff,0xce,0xbe,0x00,0x01, + 0xff,0xce,0xbf,0x00,0xe4,0x85,0x43,0xd3,0x35,0xd2,0x19,0xd1,0x0e,0x10,0x07,0x01, + 0xff,0xcf,0x80,0x00,0x01,0xff,0xcf,0x81,0x00,0x10,0x04,0x00,0x00,0x01,0xff,0xcf, + 0x83,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff,0xcf,0x84,0x00,0x01,0xff,0xcf,0x85,0x00, + 0x10,0x07,0x01,0xff,0xcf,0x86,0x00,0x01,0xff,0xcf,0x87,0x00,0xe2,0x2b,0x43,0xd1, + 0x0e,0x10,0x07,0x01,0xff,0xcf,0x88,0x00,0x01,0xff,0xcf,0x89,0x00,0x10,0x09,0x01, + 0xff,0xce,0xb9,0xcc,0x88,0x00,0x01,0xff,0xcf,0x85,0xcc,0x88,0x00,0xcf,0x86,0xd5, + 0x94,0xd4,0x3c,0xd3,0x13,0x92,0x0f,0x51,0x04,0x01,0x00,0x10,0x07,0x01,0xff,0xcf, + 0x83,0x00,0x01,0x00,0x01,0x00,0xd2,0x07,0x61,0x3a,0x43,0x01,0x00,0xd1,0x12,0x10, + 0x09,0x01,0xff,0xce,0xbf,0xcc,0x81,0x00,0x01,0xff,0xcf,0x85,0xcc,0x81,0x00,0x10, + 0x09,0x01,0xff,0xcf,0x89,0xcc,0x81,0x00,0x0a,0xff,0xcf,0x97,0x00,0xd3,0x2c,0xd2, + 0x11,0xe1,0x46,0x43,0x10,0x07,0x01,0xff,0xce,0xb2,0x00,0x01,0xff,0xce,0xb8,0x00, + 0xd1,0x10,0x10,0x09,0x01,0xff,0xcf,0x92,0xcc,0x88,0x00,0x01,0xff,0xcf,0x86,0x00, + 0x10,0x07,0x01,0xff,0xcf,0x80,0x00,0x04,0x00,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x06, + 0xff,0xcf,0x99,0x00,0x06,0x00,0x10,0x07,0x01,0xff,0xcf,0x9b,0x00,0x04,0x00,0xd1, + 0x0b,0x10,0x07,0x01,0xff,0xcf,0x9d,0x00,0x04,0x00,0x10,0x07,0x01,0xff,0xcf,0x9f, + 0x00,0x04,0x00,0xd4,0x58,0xd3,0x2c,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x01,0xff,0xcf, + 0xa1,0x00,0x04,0x00,0x10,0x07,0x01,0xff,0xcf,0xa3,0x00,0x01,0x00,0xd1,0x0b,0x10, + 0x07,0x01,0xff,0xcf,0xa5,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xcf,0xa7,0x00,0x01, + 0x00,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x01,0xff,0xcf,0xa9,0x00,0x01,0x00,0x10,0x07, + 0x01,0xff,0xcf,0xab,0x00,0x01,0x00,0xd1,0x0b,0x10,0x07,0x01,0xff,0xcf,0xad,0x00, + 0x01,0x00,0x10,0x07,0x01,0xff,0xcf,0xaf,0x00,0x01,0x00,0xd3,0x2b,0xd2,0x12,0x91, + 0x0e,0x10,0x07,0x01,0xff,0xce,0xba,0x00,0x01,0xff,0xcf,0x81,0x00,0x01,0x00,0xd1, + 0x0e,0x10,0x07,0x05,0xff,0xce,0xb8,0x00,0x05,0xff,0xce,0xb5,0x00,0x10,0x04,0x06, + 0x00,0x07,0xff,0xcf,0xb8,0x00,0xd2,0x16,0xd1,0x0b,0x10,0x04,0x07,0x00,0x07,0xff, + 0xcf,0xb2,0x00,0x10,0x07,0x07,0xff,0xcf,0xbb,0x00,0x07,0x00,0xd1,0x0b,0x10,0x04, + 0x08,0x00,0x08,0xff,0xcd,0xbb,0x00,0x10,0x07,0x08,0xff,0xcd,0xbc,0x00,0x08,0xff, + 0xcd,0xbd,0x00,0xe3,0xed,0x46,0xe2,0x3d,0x05,0xe1,0x27,0x02,0xe0,0x66,0x01,0xcf, + 0x86,0xd5,0xf0,0xd4,0x7e,0xd3,0x40,0xd2,0x22,0xd1,0x12,0x10,0x09,0x04,0xff,0xd0, + 0xb5,0xcc,0x80,0x00,0x01,0xff,0xd0,0xb5,0xcc,0x88,0x00,0x10,0x07,0x01,0xff,0xd1, + 0x92,0x00,0x01,0xff,0xd0,0xb3,0xcc,0x81,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd1, + 0x94,0x00,0x01,0xff,0xd1,0x95,0x00,0x10,0x07,0x01,0xff,0xd1,0x96,0x00,0x01,0xff, + 0xd1,0x96,0xcc,0x88,0x00,0xd2,0x1c,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd1,0x98,0x00, + 0x01,0xff,0xd1,0x99,0x00,0x10,0x07,0x01,0xff,0xd1,0x9a,0x00,0x01,0xff,0xd1,0x9b, + 0x00,0xd1,0x12,0x10,0x09,0x01,0xff,0xd0,0xba,0xcc,0x81,0x00,0x04,0xff,0xd0,0xb8, + 0xcc,0x80,0x00,0x10,0x09,0x01,0xff,0xd1,0x83,0xcc,0x86,0x00,0x01,0xff,0xd1,0x9f, + 0x00,0xd3,0x38,0xd2,0x1c,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd0,0xb0,0x00,0x01,0xff, + 0xd0,0xb1,0x00,0x10,0x07,0x01,0xff,0xd0,0xb2,0x00,0x01,0xff,0xd0,0xb3,0x00,0xd1, + 0x0e,0x10,0x07,0x01,0xff,0xd0,0xb4,0x00,0x01,0xff,0xd0,0xb5,0x00,0x10,0x07,0x01, + 0xff,0xd0,0xb6,0x00,0x01,0xff,0xd0,0xb7,0x00,0xd2,0x1e,0xd1,0x10,0x10,0x07,0x01, + 0xff,0xd0,0xb8,0x00,0x01,0xff,0xd0,0xb8,0xcc,0x86,0x00,0x10,0x07,0x01,0xff,0xd0, + 0xba,0x00,0x01,0xff,0xd0,0xbb,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd0,0xbc,0x00, + 0x01,0xff,0xd0,0xbd,0x00,0x10,0x07,0x01,0xff,0xd0,0xbe,0x00,0x01,0xff,0xd0,0xbf, + 0x00,0xe4,0x25,0x42,0xd3,0x38,0xd2,0x1c,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd1,0x80, + 0x00,0x01,0xff,0xd1,0x81,0x00,0x10,0x07,0x01,0xff,0xd1,0x82,0x00,0x01,0xff,0xd1, + 0x83,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd1,0x84,0x00,0x01,0xff,0xd1,0x85,0x00, + 0x10,0x07,0x01,0xff,0xd1,0x86,0x00,0x01,0xff,0xd1,0x87,0x00,0xd2,0x1c,0xd1,0x0e, + 0x10,0x07,0x01,0xff,0xd1,0x88,0x00,0x01,0xff,0xd1,0x89,0x00,0x10,0x07,0x01,0xff, + 0xd1,0x8a,0x00,0x01,0xff,0xd1,0x8b,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd1,0x8c, + 0x00,0x01,0xff,0xd1,0x8d,0x00,0x10,0x07,0x01,0xff,0xd1,0x8e,0x00,0x01,0xff,0xd1, + 0x8f,0x00,0xcf,0x86,0xd5,0x07,0x64,0xcf,0x41,0x01,0x00,0xd4,0x58,0xd3,0x2c,0xd2, + 0x16,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd1,0xa1,0x00,0x01,0x00,0x10,0x07,0x01,0xff, + 0xd1,0xa3,0x00,0x01,0x00,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd1,0xa5,0x00,0x01,0x00, + 0x10,0x07,0x01,0xff,0xd1,0xa7,0x00,0x01,0x00,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x01, + 0xff,0xd1,0xa9,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xd1,0xab,0x00,0x01,0x00,0xd1, + 0x0b,0x10,0x07,0x01,0xff,0xd1,0xad,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xd1,0xaf, + 0x00,0x01,0x00,0xd3,0x33,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd1,0xb1,0x00, + 0x01,0x00,0x10,0x07,0x01,0xff,0xd1,0xb3,0x00,0x01,0x00,0xd1,0x0b,0x10,0x07,0x01, + 0xff,0xd1,0xb5,0x00,0x01,0x00,0x10,0x09,0x01,0xff,0xd1,0xb5,0xcc,0x8f,0x00,0x01, + 0xff,0xd1,0xb5,0xcc,0x8f,0x00,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd1,0xb9, + 0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xd1,0xbb,0x00,0x01,0x00,0xd1,0x0b,0x10,0x07, + 0x01,0xff,0xd1,0xbd,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xd1,0xbf,0x00,0x01,0x00, + 0xe0,0x41,0x01,0xcf,0x86,0xd5,0x8e,0xd4,0x36,0xd3,0x11,0xe2,0x91,0x41,0xe1,0x88, + 0x41,0x10,0x07,0x01,0xff,0xd2,0x81,0x00,0x01,0x00,0xd2,0x0f,0x51,0x04,0x04,0x00, + 0x10,0x07,0x06,0xff,0xd2,0x8b,0x00,0x06,0x00,0xd1,0x0b,0x10,0x07,0x04,0xff,0xd2, + 0x8d,0x00,0x04,0x00,0x10,0x07,0x04,0xff,0xd2,0x8f,0x00,0x04,0x00,0xd3,0x2c,0xd2, + 0x16,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd2,0x91,0x00,0x01,0x00,0x10,0x07,0x01,0xff, + 0xd2,0x93,0x00,0x01,0x00,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd2,0x95,0x00,0x01,0x00, + 0x10,0x07,0x01,0xff,0xd2,0x97,0x00,0x01,0x00,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x01, + 0xff,0xd2,0x99,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xd2,0x9b,0x00,0x01,0x00,0xd1, + 0x0b,0x10,0x07,0x01,0xff,0xd2,0x9d,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xd2,0x9f, + 0x00,0x01,0x00,0xd4,0x58,0xd3,0x2c,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd2, + 0xa1,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xd2,0xa3,0x00,0x01,0x00,0xd1,0x0b,0x10, + 0x07,0x01,0xff,0xd2,0xa5,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xd2,0xa7,0x00,0x01, + 0x00,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd2,0xa9,0x00,0x01,0x00,0x10,0x07, + 0x01,0xff,0xd2,0xab,0x00,0x01,0x00,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd2,0xad,0x00, + 0x01,0x00,0x10,0x07,0x01,0xff,0xd2,0xaf,0x00,0x01,0x00,0xd3,0x2c,0xd2,0x16,0xd1, + 0x0b,0x10,0x07,0x01,0xff,0xd2,0xb1,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xd2,0xb3, + 0x00,0x01,0x00,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd2,0xb5,0x00,0x01,0x00,0x10,0x07, + 0x01,0xff,0xd2,0xb7,0x00,0x01,0x00,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd2, + 0xb9,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xd2,0xbb,0x00,0x01,0x00,0xd1,0x0b,0x10, + 0x07,0x01,0xff,0xd2,0xbd,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xd2,0xbf,0x00,0x01, + 0x00,0xcf,0x86,0xd5,0xdc,0xd4,0x5a,0xd3,0x36,0xd2,0x20,0xd1,0x10,0x10,0x07,0x01, + 0xff,0xd3,0x8f,0x00,0x01,0xff,0xd0,0xb6,0xcc,0x86,0x00,0x10,0x09,0x01,0xff,0xd0, + 0xb6,0xcc,0x86,0x00,0x01,0xff,0xd3,0x84,0x00,0xd1,0x0b,0x10,0x04,0x01,0x00,0x06, + 0xff,0xd3,0x86,0x00,0x10,0x04,0x06,0x00,0x01,0xff,0xd3,0x88,0x00,0xd2,0x16,0xd1, + 0x0b,0x10,0x04,0x01,0x00,0x06,0xff,0xd3,0x8a,0x00,0x10,0x04,0x06,0x00,0x01,0xff, + 0xd3,0x8c,0x00,0xe1,0x69,0x40,0x10,0x04,0x01,0x00,0x06,0xff,0xd3,0x8e,0x00,0xd3, + 0x41,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff,0xd0,0xb0,0xcc,0x86,0x00,0x01,0xff, + 0xd0,0xb0,0xcc,0x86,0x00,0x10,0x09,0x01,0xff,0xd0,0xb0,0xcc,0x88,0x00,0x01,0xff, + 0xd0,0xb0,0xcc,0x88,0x00,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd3,0x95,0x00,0x01,0x00, + 0x10,0x09,0x01,0xff,0xd0,0xb5,0xcc,0x86,0x00,0x01,0xff,0xd0,0xb5,0xcc,0x86,0x00, + 0xd2,0x1d,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd3,0x99,0x00,0x01,0x00,0x10,0x09,0x01, + 0xff,0xd3,0x99,0xcc,0x88,0x00,0x01,0xff,0xd3,0x99,0xcc,0x88,0x00,0xd1,0x12,0x10, + 0x09,0x01,0xff,0xd0,0xb6,0xcc,0x88,0x00,0x01,0xff,0xd0,0xb6,0xcc,0x88,0x00,0x10, + 0x09,0x01,0xff,0xd0,0xb7,0xcc,0x88,0x00,0x01,0xff,0xd0,0xb7,0xcc,0x88,0x00,0xd4, + 0x82,0xd3,0x41,0xd2,0x1d,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd3,0xa1,0x00,0x01,0x00, + 0x10,0x09,0x01,0xff,0xd0,0xb8,0xcc,0x84,0x00,0x01,0xff,0xd0,0xb8,0xcc,0x84,0x00, + 0xd1,0x12,0x10,0x09,0x01,0xff,0xd0,0xb8,0xcc,0x88,0x00,0x01,0xff,0xd0,0xb8,0xcc, + 0x88,0x00,0x10,0x09,0x01,0xff,0xd0,0xbe,0xcc,0x88,0x00,0x01,0xff,0xd0,0xbe,0xcc, + 0x88,0x00,0xd2,0x1d,0xd1,0x0b,0x10,0x07,0x01,0xff,0xd3,0xa9,0x00,0x01,0x00,0x10, + 0x09,0x01,0xff,0xd3,0xa9,0xcc,0x88,0x00,0x01,0xff,0xd3,0xa9,0xcc,0x88,0x00,0xd1, + 0x12,0x10,0x09,0x04,0xff,0xd1,0x8d,0xcc,0x88,0x00,0x04,0xff,0xd1,0x8d,0xcc,0x88, + 0x00,0x10,0x09,0x01,0xff,0xd1,0x83,0xcc,0x84,0x00,0x01,0xff,0xd1,0x83,0xcc,0x84, + 0x00,0xd3,0x41,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff,0xd1,0x83,0xcc,0x88,0x00, + 0x01,0xff,0xd1,0x83,0xcc,0x88,0x00,0x10,0x09,0x01,0xff,0xd1,0x83,0xcc,0x8b,0x00, + 0x01,0xff,0xd1,0x83,0xcc,0x8b,0x00,0xd1,0x12,0x10,0x09,0x01,0xff,0xd1,0x87,0xcc, + 0x88,0x00,0x01,0xff,0xd1,0x87,0xcc,0x88,0x00,0x10,0x07,0x08,0xff,0xd3,0xb7,0x00, + 0x08,0x00,0xd2,0x1d,0xd1,0x12,0x10,0x09,0x01,0xff,0xd1,0x8b,0xcc,0x88,0x00,0x01, + 0xff,0xd1,0x8b,0xcc,0x88,0x00,0x10,0x07,0x09,0xff,0xd3,0xbb,0x00,0x09,0x00,0xd1, + 0x0b,0x10,0x07,0x09,0xff,0xd3,0xbd,0x00,0x09,0x00,0x10,0x07,0x09,0xff,0xd3,0xbf, + 0x00,0x09,0x00,0xe1,0x26,0x02,0xe0,0x78,0x01,0xcf,0x86,0xd5,0xb0,0xd4,0x58,0xd3, + 0x2c,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x06,0xff,0xd4,0x81,0x00,0x06,0x00,0x10,0x07, + 0x06,0xff,0xd4,0x83,0x00,0x06,0x00,0xd1,0x0b,0x10,0x07,0x06,0xff,0xd4,0x85,0x00, + 0x06,0x00,0x10,0x07,0x06,0xff,0xd4,0x87,0x00,0x06,0x00,0xd2,0x16,0xd1,0x0b,0x10, + 0x07,0x06,0xff,0xd4,0x89,0x00,0x06,0x00,0x10,0x07,0x06,0xff,0xd4,0x8b,0x00,0x06, + 0x00,0xd1,0x0b,0x10,0x07,0x06,0xff,0xd4,0x8d,0x00,0x06,0x00,0x10,0x07,0x06,0xff, + 0xd4,0x8f,0x00,0x06,0x00,0xd3,0x2c,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x09,0xff,0xd4, + 0x91,0x00,0x09,0x00,0x10,0x07,0x09,0xff,0xd4,0x93,0x00,0x09,0x00,0xd1,0x0b,0x10, + 0x07,0x0a,0xff,0xd4,0x95,0x00,0x0a,0x00,0x10,0x07,0x0a,0xff,0xd4,0x97,0x00,0x0a, + 0x00,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x0a,0xff,0xd4,0x99,0x00,0x0a,0x00,0x10,0x07, + 0x0a,0xff,0xd4,0x9b,0x00,0x0a,0x00,0xd1,0x0b,0x10,0x07,0x0a,0xff,0xd4,0x9d,0x00, + 0x0a,0x00,0x10,0x07,0x0a,0xff,0xd4,0x9f,0x00,0x0a,0x00,0xd4,0x58,0xd3,0x2c,0xd2, + 0x16,0xd1,0x0b,0x10,0x07,0x0a,0xff,0xd4,0xa1,0x00,0x0a,0x00,0x10,0x07,0x0a,0xff, + 0xd4,0xa3,0x00,0x0a,0x00,0xd1,0x0b,0x10,0x07,0x0b,0xff,0xd4,0xa5,0x00,0x0b,0x00, + 0x10,0x07,0x0c,0xff,0xd4,0xa7,0x00,0x0c,0x00,0xd2,0x16,0xd1,0x0b,0x10,0x07,0x10, + 0xff,0xd4,0xa9,0x00,0x10,0x00,0x10,0x07,0x10,0xff,0xd4,0xab,0x00,0x10,0x00,0xd1, + 0x0b,0x10,0x07,0x10,0xff,0xd4,0xad,0x00,0x10,0x00,0x10,0x07,0x10,0xff,0xd4,0xaf, + 0x00,0x10,0x00,0xd3,0x35,0xd2,0x19,0xd1,0x0b,0x10,0x04,0x00,0x00,0x01,0xff,0xd5, + 0xa1,0x00,0x10,0x07,0x01,0xff,0xd5,0xa2,0x00,0x01,0xff,0xd5,0xa3,0x00,0xd1,0x0e, + 0x10,0x07,0x01,0xff,0xd5,0xa4,0x00,0x01,0xff,0xd5,0xa5,0x00,0x10,0x07,0x01,0xff, + 0xd5,0xa6,0x00,0x01,0xff,0xd5,0xa7,0x00,0xd2,0x1c,0xd1,0x0e,0x10,0x07,0x01,0xff, + 0xd5,0xa8,0x00,0x01,0xff,0xd5,0xa9,0x00,0x10,0x07,0x01,0xff,0xd5,0xaa,0x00,0x01, + 0xff,0xd5,0xab,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd5,0xac,0x00,0x01,0xff,0xd5, + 0xad,0x00,0x10,0x07,0x01,0xff,0xd5,0xae,0x00,0x01,0xff,0xd5,0xaf,0x00,0xcf,0x86, + 0xe5,0x08,0x3f,0xd4,0x70,0xd3,0x38,0xd2,0x1c,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd5, + 0xb0,0x00,0x01,0xff,0xd5,0xb1,0x00,0x10,0x07,0x01,0xff,0xd5,0xb2,0x00,0x01,0xff, + 0xd5,0xb3,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd5,0xb4,0x00,0x01,0xff,0xd5,0xb5, + 0x00,0x10,0x07,0x01,0xff,0xd5,0xb6,0x00,0x01,0xff,0xd5,0xb7,0x00,0xd2,0x1c,0xd1, + 0x0e,0x10,0x07,0x01,0xff,0xd5,0xb8,0x00,0x01,0xff,0xd5,0xb9,0x00,0x10,0x07,0x01, + 0xff,0xd5,0xba,0x00,0x01,0xff,0xd5,0xbb,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd5, + 0xbc,0x00,0x01,0xff,0xd5,0xbd,0x00,0x10,0x07,0x01,0xff,0xd5,0xbe,0x00,0x01,0xff, + 0xd5,0xbf,0x00,0xe3,0x87,0x3e,0xd2,0x1c,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd6,0x80, + 0x00,0x01,0xff,0xd6,0x81,0x00,0x10,0x07,0x01,0xff,0xd6,0x82,0x00,0x01,0xff,0xd6, + 0x83,0x00,0xd1,0x0e,0x10,0x07,0x01,0xff,0xd6,0x84,0x00,0x01,0xff,0xd6,0x85,0x00, + 0x10,0x07,0x01,0xff,0xd6,0x86,0x00,0x00,0x00,0xe0,0x2f,0x3f,0xcf,0x86,0xe5,0xc0, + 0x3e,0xe4,0x97,0x3e,0xe3,0x76,0x3e,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10, + 0x04,0x01,0x00,0x01,0xff,0xd5,0xa5,0xd6,0x82,0x00,0xe4,0x3e,0x25,0xe3,0xc3,0x1a, + 0xe2,0x7b,0x81,0xe1,0xc0,0x13,0xd0,0x1e,0xcf,0x86,0xc5,0xe4,0x08,0x4b,0xe3,0x53, + 0x46,0xe2,0xe9,0x43,0xe1,0x1c,0x43,0xe0,0xe1,0x42,0xcf,0x86,0xe5,0xa6,0x42,0x64, + 0x89,0x42,0x0b,0x00,0xcf,0x86,0xe5,0xfa,0x01,0xe4,0x03,0x56,0xe3,0x76,0x01,0xe2, + 0x8e,0x53,0xd1,0x0c,0xe0,0xef,0x52,0xcf,0x86,0x65,0x8d,0x52,0x04,0x00,0xe0,0x0d, + 0x01,0xcf,0x86,0xd5,0x0a,0xe4,0x10,0x53,0x63,0xff,0x52,0x0a,0x00,0xd4,0x80,0xd3, + 0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0xb4,0x80,0x00,0x01,0xff,0xe2, + 0xb4,0x81,0x00,0x10,0x08,0x01,0xff,0xe2,0xb4,0x82,0x00,0x01,0xff,0xe2,0xb4,0x83, + 0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0xb4,0x84,0x00,0x01,0xff,0xe2,0xb4,0x85, + 0x00,0x10,0x08,0x01,0xff,0xe2,0xb4,0x86,0x00,0x01,0xff,0xe2,0xb4,0x87,0x00,0xd2, + 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0xb4,0x88,0x00,0x01,0xff,0xe2,0xb4,0x89, + 0x00,0x10,0x08,0x01,0xff,0xe2,0xb4,0x8a,0x00,0x01,0xff,0xe2,0xb4,0x8b,0x00,0xd1, + 0x10,0x10,0x08,0x01,0xff,0xe2,0xb4,0x8c,0x00,0x01,0xff,0xe2,0xb4,0x8d,0x00,0x10, + 0x08,0x01,0xff,0xe2,0xb4,0x8e,0x00,0x01,0xff,0xe2,0xb4,0x8f,0x00,0xd3,0x40,0xd2, + 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0xb4,0x90,0x00,0x01,0xff,0xe2,0xb4,0x91, + 0x00,0x10,0x08,0x01,0xff,0xe2,0xb4,0x92,0x00,0x01,0xff,0xe2,0xb4,0x93,0x00,0xd1, + 0x10,0x10,0x08,0x01,0xff,0xe2,0xb4,0x94,0x00,0x01,0xff,0xe2,0xb4,0x95,0x00,0x10, + 0x08,0x01,0xff,0xe2,0xb4,0x96,0x00,0x01,0xff,0xe2,0xb4,0x97,0x00,0xd2,0x20,0xd1, + 0x10,0x10,0x08,0x01,0xff,0xe2,0xb4,0x98,0x00,0x01,0xff,0xe2,0xb4,0x99,0x00,0x10, + 0x08,0x01,0xff,0xe2,0xb4,0x9a,0x00,0x01,0xff,0xe2,0xb4,0x9b,0x00,0xd1,0x10,0x10, + 0x08,0x01,0xff,0xe2,0xb4,0x9c,0x00,0x01,0xff,0xe2,0xb4,0x9d,0x00,0x10,0x08,0x01, + 0xff,0xe2,0xb4,0x9e,0x00,0x01,0xff,0xe2,0xb4,0x9f,0x00,0xcf,0x86,0xe5,0x42,0x52, + 0x94,0x50,0xd3,0x3c,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0xb4,0xa0,0x00, + 0x01,0xff,0xe2,0xb4,0xa1,0x00,0x10,0x08,0x01,0xff,0xe2,0xb4,0xa2,0x00,0x01,0xff, + 0xe2,0xb4,0xa3,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0xb4,0xa4,0x00,0x01,0xff, + 0xe2,0xb4,0xa5,0x00,0x10,0x04,0x00,0x00,0x0d,0xff,0xe2,0xb4,0xa7,0x00,0x52,0x04, + 0x00,0x00,0x91,0x0c,0x10,0x04,0x00,0x00,0x0d,0xff,0xe2,0xb4,0xad,0x00,0x00,0x00, + 0x01,0x00,0xd2,0x1b,0xe1,0xfc,0x52,0xe0,0xad,0x52,0xcf,0x86,0x95,0x0f,0x94,0x0b, + 0x93,0x07,0x62,0x92,0x52,0x04,0x00,0x04,0x00,0x04,0x00,0x04,0x00,0xd1,0x13,0xe0, + 0xd3,0x53,0xcf,0x86,0x95,0x0a,0xe4,0xa8,0x53,0x63,0x97,0x53,0x04,0x00,0x04,0x00, + 0xd0,0x0d,0xcf,0x86,0x95,0x07,0x64,0x22,0x54,0x08,0x00,0x04,0x00,0xcf,0x86,0x55, + 0x04,0x04,0x00,0x54,0x04,0x04,0x00,0xd3,0x07,0x62,0x2f,0x54,0x04,0x00,0xd2,0x20, + 0xd1,0x10,0x10,0x08,0x11,0xff,0xe1,0x8f,0xb0,0x00,0x11,0xff,0xe1,0x8f,0xb1,0x00, + 0x10,0x08,0x11,0xff,0xe1,0x8f,0xb2,0x00,0x11,0xff,0xe1,0x8f,0xb3,0x00,0x91,0x10, + 0x10,0x08,0x11,0xff,0xe1,0x8f,0xb4,0x00,0x11,0xff,0xe1,0x8f,0xb5,0x00,0x00,0x00, + 0xd4,0x1c,0xe3,0xe0,0x56,0xe2,0x17,0x56,0xe1,0xda,0x55,0xe0,0xbb,0x55,0xcf,0x86, + 0x95,0x0a,0xe4,0xa4,0x55,0x63,0x88,0x55,0x04,0x00,0x04,0x00,0xe3,0xd2,0x01,0xe2, + 0x2b,0x5a,0xd1,0x0c,0xe0,0x4c,0x59,0xcf,0x86,0x65,0x25,0x59,0x0a,0x00,0xe0,0x9c, + 0x59,0xcf,0x86,0xd5,0xc5,0xd4,0x45,0xd3,0x31,0xd2,0x1c,0xd1,0x0e,0x10,0x07,0x12, + 0xff,0xd0,0xb2,0x00,0x12,0xff,0xd0,0xb4,0x00,0x10,0x07,0x12,0xff,0xd0,0xbe,0x00, + 0x12,0xff,0xd1,0x81,0x00,0x51,0x07,0x12,0xff,0xd1,0x82,0x00,0x10,0x07,0x12,0xff, + 0xd1,0x8a,0x00,0x12,0xff,0xd1,0xa3,0x00,0x92,0x10,0x91,0x0c,0x10,0x08,0x12,0xff, + 0xea,0x99,0x8b,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10, + 0x10,0x08,0x14,0xff,0xe1,0x83,0x90,0x00,0x14,0xff,0xe1,0x83,0x91,0x00,0x10,0x08, + 0x14,0xff,0xe1,0x83,0x92,0x00,0x14,0xff,0xe1,0x83,0x93,0x00,0xd1,0x10,0x10,0x08, + 0x14,0xff,0xe1,0x83,0x94,0x00,0x14,0xff,0xe1,0x83,0x95,0x00,0x10,0x08,0x14,0xff, + 0xe1,0x83,0x96,0x00,0x14,0xff,0xe1,0x83,0x97,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08, + 0x14,0xff,0xe1,0x83,0x98,0x00,0x14,0xff,0xe1,0x83,0x99,0x00,0x10,0x08,0x14,0xff, + 0xe1,0x83,0x9a,0x00,0x14,0xff,0xe1,0x83,0x9b,0x00,0xd1,0x10,0x10,0x08,0x14,0xff, + 0xe1,0x83,0x9c,0x00,0x14,0xff,0xe1,0x83,0x9d,0x00,0x10,0x08,0x14,0xff,0xe1,0x83, + 0x9e,0x00,0x14,0xff,0xe1,0x83,0x9f,0x00,0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10, + 0x10,0x08,0x14,0xff,0xe1,0x83,0xa0,0x00,0x14,0xff,0xe1,0x83,0xa1,0x00,0x10,0x08, + 0x14,0xff,0xe1,0x83,0xa2,0x00,0x14,0xff,0xe1,0x83,0xa3,0x00,0xd1,0x10,0x10,0x08, + 0x14,0xff,0xe1,0x83,0xa4,0x00,0x14,0xff,0xe1,0x83,0xa5,0x00,0x10,0x08,0x14,0xff, + 0xe1,0x83,0xa6,0x00,0x14,0xff,0xe1,0x83,0xa7,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08, + 0x14,0xff,0xe1,0x83,0xa8,0x00,0x14,0xff,0xe1,0x83,0xa9,0x00,0x10,0x08,0x14,0xff, + 0xe1,0x83,0xaa,0x00,0x14,0xff,0xe1,0x83,0xab,0x00,0xd1,0x10,0x10,0x08,0x14,0xff, + 0xe1,0x83,0xac,0x00,0x14,0xff,0xe1,0x83,0xad,0x00,0x10,0x08,0x14,0xff,0xe1,0x83, + 0xae,0x00,0x14,0xff,0xe1,0x83,0xaf,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08, + 0x14,0xff,0xe1,0x83,0xb0,0x00,0x14,0xff,0xe1,0x83,0xb1,0x00,0x10,0x08,0x14,0xff, + 0xe1,0x83,0xb2,0x00,0x14,0xff,0xe1,0x83,0xb3,0x00,0xd1,0x10,0x10,0x08,0x14,0xff, + 0xe1,0x83,0xb4,0x00,0x14,0xff,0xe1,0x83,0xb5,0x00,0x10,0x08,0x14,0xff,0xe1,0x83, + 0xb6,0x00,0x14,0xff,0xe1,0x83,0xb7,0x00,0xd2,0x1c,0xd1,0x10,0x10,0x08,0x14,0xff, + 0xe1,0x83,0xb8,0x00,0x14,0xff,0xe1,0x83,0xb9,0x00,0x10,0x08,0x14,0xff,0xe1,0x83, + 0xba,0x00,0x00,0x00,0xd1,0x0c,0x10,0x04,0x00,0x00,0x14,0xff,0xe1,0x83,0xbd,0x00, + 0x10,0x08,0x14,0xff,0xe1,0x83,0xbe,0x00,0x14,0xff,0xe1,0x83,0xbf,0x00,0xe2,0x9d, + 0x08,0xe1,0x48,0x04,0xe0,0x1c,0x02,0xcf,0x86,0xe5,0x11,0x01,0xd4,0x84,0xd3,0x40, + 0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x61,0xcc,0xa5,0x00,0x01,0xff,0x61,0xcc, + 0xa5,0x00,0x10,0x08,0x01,0xff,0x62,0xcc,0x87,0x00,0x01,0xff,0x62,0xcc,0x87,0x00, + 0xd1,0x10,0x10,0x08,0x01,0xff,0x62,0xcc,0xa3,0x00,0x01,0xff,0x62,0xcc,0xa3,0x00, + 0x10,0x08,0x01,0xff,0x62,0xcc,0xb1,0x00,0x01,0xff,0x62,0xcc,0xb1,0x00,0xd2,0x24, + 0xd1,0x14,0x10,0x0a,0x01,0xff,0x63,0xcc,0xa7,0xcc,0x81,0x00,0x01,0xff,0x63,0xcc, + 0xa7,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x64,0xcc,0x87,0x00,0x01,0xff,0x64,0xcc, + 0x87,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x64,0xcc,0xa3,0x00,0x01,0xff,0x64,0xcc, + 0xa3,0x00,0x10,0x08,0x01,0xff,0x64,0xcc,0xb1,0x00,0x01,0xff,0x64,0xcc,0xb1,0x00, + 0xd3,0x48,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x64,0xcc,0xa7,0x00,0x01,0xff, + 0x64,0xcc,0xa7,0x00,0x10,0x08,0x01,0xff,0x64,0xcc,0xad,0x00,0x01,0xff,0x64,0xcc, + 0xad,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x65,0xcc,0x84,0xcc,0x80,0x00,0x01,0xff, + 0x65,0xcc,0x84,0xcc,0x80,0x00,0x10,0x0a,0x01,0xff,0x65,0xcc,0x84,0xcc,0x81,0x00, + 0x01,0xff,0x65,0xcc,0x84,0xcc,0x81,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff, + 0x65,0xcc,0xad,0x00,0x01,0xff,0x65,0xcc,0xad,0x00,0x10,0x08,0x01,0xff,0x65,0xcc, + 0xb0,0x00,0x01,0xff,0x65,0xcc,0xb0,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x65,0xcc, + 0xa7,0xcc,0x86,0x00,0x01,0xff,0x65,0xcc,0xa7,0xcc,0x86,0x00,0x10,0x08,0x01,0xff, + 0x66,0xcc,0x87,0x00,0x01,0xff,0x66,0xcc,0x87,0x00,0xd4,0x84,0xd3,0x40,0xd2,0x20, + 0xd1,0x10,0x10,0x08,0x01,0xff,0x67,0xcc,0x84,0x00,0x01,0xff,0x67,0xcc,0x84,0x00, + 0x10,0x08,0x01,0xff,0x68,0xcc,0x87,0x00,0x01,0xff,0x68,0xcc,0x87,0x00,0xd1,0x10, + 0x10,0x08,0x01,0xff,0x68,0xcc,0xa3,0x00,0x01,0xff,0x68,0xcc,0xa3,0x00,0x10,0x08, + 0x01,0xff,0x68,0xcc,0x88,0x00,0x01,0xff,0x68,0xcc,0x88,0x00,0xd2,0x20,0xd1,0x10, + 0x10,0x08,0x01,0xff,0x68,0xcc,0xa7,0x00,0x01,0xff,0x68,0xcc,0xa7,0x00,0x10,0x08, + 0x01,0xff,0x68,0xcc,0xae,0x00,0x01,0xff,0x68,0xcc,0xae,0x00,0xd1,0x10,0x10,0x08, + 0x01,0xff,0x69,0xcc,0xb0,0x00,0x01,0xff,0x69,0xcc,0xb0,0x00,0x10,0x0a,0x01,0xff, + 0x69,0xcc,0x88,0xcc,0x81,0x00,0x01,0xff,0x69,0xcc,0x88,0xcc,0x81,0x00,0xd3,0x40, + 0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x6b,0xcc,0x81,0x00,0x01,0xff,0x6b,0xcc, + 0x81,0x00,0x10,0x08,0x01,0xff,0x6b,0xcc,0xa3,0x00,0x01,0xff,0x6b,0xcc,0xa3,0x00, + 0xd1,0x10,0x10,0x08,0x01,0xff,0x6b,0xcc,0xb1,0x00,0x01,0xff,0x6b,0xcc,0xb1,0x00, + 0x10,0x08,0x01,0xff,0x6c,0xcc,0xa3,0x00,0x01,0xff,0x6c,0xcc,0xa3,0x00,0xd2,0x24, + 0xd1,0x14,0x10,0x0a,0x01,0xff,0x6c,0xcc,0xa3,0xcc,0x84,0x00,0x01,0xff,0x6c,0xcc, + 0xa3,0xcc,0x84,0x00,0x10,0x08,0x01,0xff,0x6c,0xcc,0xb1,0x00,0x01,0xff,0x6c,0xcc, + 0xb1,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x6c,0xcc,0xad,0x00,0x01,0xff,0x6c,0xcc, + 0xad,0x00,0x10,0x08,0x01,0xff,0x6d,0xcc,0x81,0x00,0x01,0xff,0x6d,0xcc,0x81,0x00, + 0xcf,0x86,0xe5,0x15,0x01,0xd4,0x88,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01, + 0xff,0x6d,0xcc,0x87,0x00,0x01,0xff,0x6d,0xcc,0x87,0x00,0x10,0x08,0x01,0xff,0x6d, + 0xcc,0xa3,0x00,0x01,0xff,0x6d,0xcc,0xa3,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x6e, + 0xcc,0x87,0x00,0x01,0xff,0x6e,0xcc,0x87,0x00,0x10,0x08,0x01,0xff,0x6e,0xcc,0xa3, + 0x00,0x01,0xff,0x6e,0xcc,0xa3,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x6e, + 0xcc,0xb1,0x00,0x01,0xff,0x6e,0xcc,0xb1,0x00,0x10,0x08,0x01,0xff,0x6e,0xcc,0xad, + 0x00,0x01,0xff,0x6e,0xcc,0xad,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x6f,0xcc,0x83, + 0xcc,0x81,0x00,0x01,0xff,0x6f,0xcc,0x83,0xcc,0x81,0x00,0x10,0x0a,0x01,0xff,0x6f, + 0xcc,0x83,0xcc,0x88,0x00,0x01,0xff,0x6f,0xcc,0x83,0xcc,0x88,0x00,0xd3,0x48,0xd2, + 0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x6f,0xcc,0x84,0xcc,0x80,0x00,0x01,0xff,0x6f, + 0xcc,0x84,0xcc,0x80,0x00,0x10,0x0a,0x01,0xff,0x6f,0xcc,0x84,0xcc,0x81,0x00,0x01, + 0xff,0x6f,0xcc,0x84,0xcc,0x81,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x70,0xcc,0x81, + 0x00,0x01,0xff,0x70,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x70,0xcc,0x87,0x00,0x01, + 0xff,0x70,0xcc,0x87,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x72,0xcc,0x87, + 0x00,0x01,0xff,0x72,0xcc,0x87,0x00,0x10,0x08,0x01,0xff,0x72,0xcc,0xa3,0x00,0x01, + 0xff,0x72,0xcc,0xa3,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x72,0xcc,0xa3,0xcc,0x84, + 0x00,0x01,0xff,0x72,0xcc,0xa3,0xcc,0x84,0x00,0x10,0x08,0x01,0xff,0x72,0xcc,0xb1, + 0x00,0x01,0xff,0x72,0xcc,0xb1,0x00,0xd4,0x8c,0xd3,0x48,0xd2,0x20,0xd1,0x10,0x10, + 0x08,0x01,0xff,0x73,0xcc,0x87,0x00,0x01,0xff,0x73,0xcc,0x87,0x00,0x10,0x08,0x01, + 0xff,0x73,0xcc,0xa3,0x00,0x01,0xff,0x73,0xcc,0xa3,0x00,0xd1,0x14,0x10,0x0a,0x01, + 0xff,0x73,0xcc,0x81,0xcc,0x87,0x00,0x01,0xff,0x73,0xcc,0x81,0xcc,0x87,0x00,0x10, + 0x0a,0x01,0xff,0x73,0xcc,0x8c,0xcc,0x87,0x00,0x01,0xff,0x73,0xcc,0x8c,0xcc,0x87, + 0x00,0xd2,0x24,0xd1,0x14,0x10,0x0a,0x01,0xff,0x73,0xcc,0xa3,0xcc,0x87,0x00,0x01, + 0xff,0x73,0xcc,0xa3,0xcc,0x87,0x00,0x10,0x08,0x01,0xff,0x74,0xcc,0x87,0x00,0x01, + 0xff,0x74,0xcc,0x87,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x74,0xcc,0xa3,0x00,0x01, + 0xff,0x74,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x74,0xcc,0xb1,0x00,0x01,0xff,0x74, + 0xcc,0xb1,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x74,0xcc,0xad, + 0x00,0x01,0xff,0x74,0xcc,0xad,0x00,0x10,0x08,0x01,0xff,0x75,0xcc,0xa4,0x00,0x01, + 0xff,0x75,0xcc,0xa4,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x75,0xcc,0xb0,0x00,0x01, + 0xff,0x75,0xcc,0xb0,0x00,0x10,0x08,0x01,0xff,0x75,0xcc,0xad,0x00,0x01,0xff,0x75, + 0xcc,0xad,0x00,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x75,0xcc,0x83,0xcc,0x81, + 0x00,0x01,0xff,0x75,0xcc,0x83,0xcc,0x81,0x00,0x10,0x0a,0x01,0xff,0x75,0xcc,0x84, + 0xcc,0x88,0x00,0x01,0xff,0x75,0xcc,0x84,0xcc,0x88,0x00,0xd1,0x10,0x10,0x08,0x01, + 0xff,0x76,0xcc,0x83,0x00,0x01,0xff,0x76,0xcc,0x83,0x00,0x10,0x08,0x01,0xff,0x76, + 0xcc,0xa3,0x00,0x01,0xff,0x76,0xcc,0xa3,0x00,0xe0,0x11,0x02,0xcf,0x86,0xd5,0xe2, + 0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x77,0xcc,0x80,0x00, + 0x01,0xff,0x77,0xcc,0x80,0x00,0x10,0x08,0x01,0xff,0x77,0xcc,0x81,0x00,0x01,0xff, + 0x77,0xcc,0x81,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x77,0xcc,0x88,0x00,0x01,0xff, + 0x77,0xcc,0x88,0x00,0x10,0x08,0x01,0xff,0x77,0xcc,0x87,0x00,0x01,0xff,0x77,0xcc, + 0x87,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x77,0xcc,0xa3,0x00,0x01,0xff, + 0x77,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x78,0xcc,0x87,0x00,0x01,0xff,0x78,0xcc, + 0x87,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x78,0xcc,0x88,0x00,0x01,0xff,0x78,0xcc, + 0x88,0x00,0x10,0x08,0x01,0xff,0x79,0xcc,0x87,0x00,0x01,0xff,0x79,0xcc,0x87,0x00, + 0xd3,0x33,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x7a,0xcc,0x82,0x00,0x01,0xff, + 0x7a,0xcc,0x82,0x00,0x10,0x08,0x01,0xff,0x7a,0xcc,0xa3,0x00,0x01,0xff,0x7a,0xcc, + 0xa3,0x00,0xe1,0x12,0x59,0x10,0x08,0x01,0xff,0x7a,0xcc,0xb1,0x00,0x01,0xff,0x7a, + 0xcc,0xb1,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x77,0xcc,0x8a,0x00,0x01, + 0xff,0x79,0xcc,0x8a,0x00,0x10,0x08,0x01,0xff,0x61,0xca,0xbe,0x00,0x02,0xff,0x73, + 0xcc,0x87,0x00,0x51,0x04,0x0a,0x00,0x10,0x07,0x0a,0xff,0x73,0x73,0x00,0x0a,0x00, + 0xd4,0x98,0xd3,0x48,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x61,0xcc,0xa3,0x00, + 0x01,0xff,0x61,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x61,0xcc,0x89,0x00,0x01,0xff, + 0x61,0xcc,0x89,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x61,0xcc,0x82,0xcc,0x81,0x00, + 0x01,0xff,0x61,0xcc,0x82,0xcc,0x81,0x00,0x10,0x0a,0x01,0xff,0x61,0xcc,0x82,0xcc, + 0x80,0x00,0x01,0xff,0x61,0xcc,0x82,0xcc,0x80,0x00,0xd2,0x28,0xd1,0x14,0x10,0x0a, + 0x01,0xff,0x61,0xcc,0x82,0xcc,0x89,0x00,0x01,0xff,0x61,0xcc,0x82,0xcc,0x89,0x00, + 0x10,0x0a,0x01,0xff,0x61,0xcc,0x82,0xcc,0x83,0x00,0x01,0xff,0x61,0xcc,0x82,0xcc, + 0x83,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x61,0xcc,0xa3,0xcc,0x82,0x00,0x01,0xff, + 0x61,0xcc,0xa3,0xcc,0x82,0x00,0x10,0x0a,0x01,0xff,0x61,0xcc,0x86,0xcc,0x81,0x00, + 0x01,0xff,0x61,0xcc,0x86,0xcc,0x81,0x00,0xd3,0x50,0xd2,0x28,0xd1,0x14,0x10,0x0a, + 0x01,0xff,0x61,0xcc,0x86,0xcc,0x80,0x00,0x01,0xff,0x61,0xcc,0x86,0xcc,0x80,0x00, + 0x10,0x0a,0x01,0xff,0x61,0xcc,0x86,0xcc,0x89,0x00,0x01,0xff,0x61,0xcc,0x86,0xcc, + 0x89,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x61,0xcc,0x86,0xcc,0x83,0x00,0x01,0xff, + 0x61,0xcc,0x86,0xcc,0x83,0x00,0x10,0x0a,0x01,0xff,0x61,0xcc,0xa3,0xcc,0x86,0x00, + 0x01,0xff,0x61,0xcc,0xa3,0xcc,0x86,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff, + 0x65,0xcc,0xa3,0x00,0x01,0xff,0x65,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x65,0xcc, + 0x89,0x00,0x01,0xff,0x65,0xcc,0x89,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x65,0xcc, + 0x83,0x00,0x01,0xff,0x65,0xcc,0x83,0x00,0x10,0x0a,0x01,0xff,0x65,0xcc,0x82,0xcc, + 0x81,0x00,0x01,0xff,0x65,0xcc,0x82,0xcc,0x81,0x00,0xcf,0x86,0xe5,0x31,0x01,0xd4, + 0x90,0xd3,0x50,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x65,0xcc,0x82,0xcc,0x80, + 0x00,0x01,0xff,0x65,0xcc,0x82,0xcc,0x80,0x00,0x10,0x0a,0x01,0xff,0x65,0xcc,0x82, + 0xcc,0x89,0x00,0x01,0xff,0x65,0xcc,0x82,0xcc,0x89,0x00,0xd1,0x14,0x10,0x0a,0x01, + 0xff,0x65,0xcc,0x82,0xcc,0x83,0x00,0x01,0xff,0x65,0xcc,0x82,0xcc,0x83,0x00,0x10, + 0x0a,0x01,0xff,0x65,0xcc,0xa3,0xcc,0x82,0x00,0x01,0xff,0x65,0xcc,0xa3,0xcc,0x82, + 0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x69,0xcc,0x89,0x00,0x01,0xff,0x69, + 0xcc,0x89,0x00,0x10,0x08,0x01,0xff,0x69,0xcc,0xa3,0x00,0x01,0xff,0x69,0xcc,0xa3, + 0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x6f,0xcc,0xa3,0x00,0x01,0xff,0x6f,0xcc,0xa3, + 0x00,0x10,0x08,0x01,0xff,0x6f,0xcc,0x89,0x00,0x01,0xff,0x6f,0xcc,0x89,0x00,0xd3, + 0x50,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x6f,0xcc,0x82,0xcc,0x81,0x00,0x01, + 0xff,0x6f,0xcc,0x82,0xcc,0x81,0x00,0x10,0x0a,0x01,0xff,0x6f,0xcc,0x82,0xcc,0x80, + 0x00,0x01,0xff,0x6f,0xcc,0x82,0xcc,0x80,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x6f, + 0xcc,0x82,0xcc,0x89,0x00,0x01,0xff,0x6f,0xcc,0x82,0xcc,0x89,0x00,0x10,0x0a,0x01, + 0xff,0x6f,0xcc,0x82,0xcc,0x83,0x00,0x01,0xff,0x6f,0xcc,0x82,0xcc,0x83,0x00,0xd2, + 0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x6f,0xcc,0xa3,0xcc,0x82,0x00,0x01,0xff,0x6f, + 0xcc,0xa3,0xcc,0x82,0x00,0x10,0x0a,0x01,0xff,0x6f,0xcc,0x9b,0xcc,0x81,0x00,0x01, + 0xff,0x6f,0xcc,0x9b,0xcc,0x81,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x6f,0xcc,0x9b, + 0xcc,0x80,0x00,0x01,0xff,0x6f,0xcc,0x9b,0xcc,0x80,0x00,0x10,0x0a,0x01,0xff,0x6f, + 0xcc,0x9b,0xcc,0x89,0x00,0x01,0xff,0x6f,0xcc,0x9b,0xcc,0x89,0x00,0xd4,0x98,0xd3, + 0x48,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x6f,0xcc,0x9b,0xcc,0x83,0x00,0x01, + 0xff,0x6f,0xcc,0x9b,0xcc,0x83,0x00,0x10,0x0a,0x01,0xff,0x6f,0xcc,0x9b,0xcc,0xa3, + 0x00,0x01,0xff,0x6f,0xcc,0x9b,0xcc,0xa3,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x75, + 0xcc,0xa3,0x00,0x01,0xff,0x75,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x75,0xcc,0x89, + 0x00,0x01,0xff,0x75,0xcc,0x89,0x00,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x75, + 0xcc,0x9b,0xcc,0x81,0x00,0x01,0xff,0x75,0xcc,0x9b,0xcc,0x81,0x00,0x10,0x0a,0x01, + 0xff,0x75,0xcc,0x9b,0xcc,0x80,0x00,0x01,0xff,0x75,0xcc,0x9b,0xcc,0x80,0x00,0xd1, + 0x14,0x10,0x0a,0x01,0xff,0x75,0xcc,0x9b,0xcc,0x89,0x00,0x01,0xff,0x75,0xcc,0x9b, + 0xcc,0x89,0x00,0x10,0x0a,0x01,0xff,0x75,0xcc,0x9b,0xcc,0x83,0x00,0x01,0xff,0x75, + 0xcc,0x9b,0xcc,0x83,0x00,0xd3,0x44,0xd2,0x24,0xd1,0x14,0x10,0x0a,0x01,0xff,0x75, + 0xcc,0x9b,0xcc,0xa3,0x00,0x01,0xff,0x75,0xcc,0x9b,0xcc,0xa3,0x00,0x10,0x08,0x01, + 0xff,0x79,0xcc,0x80,0x00,0x01,0xff,0x79,0xcc,0x80,0x00,0xd1,0x10,0x10,0x08,0x01, + 0xff,0x79,0xcc,0xa3,0x00,0x01,0xff,0x79,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x79, + 0xcc,0x89,0x00,0x01,0xff,0x79,0xcc,0x89,0x00,0xd2,0x1c,0xd1,0x10,0x10,0x08,0x01, + 0xff,0x79,0xcc,0x83,0x00,0x01,0xff,0x79,0xcc,0x83,0x00,0x10,0x08,0x0a,0xff,0xe1, + 0xbb,0xbb,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xe1,0xbb,0xbd,0x00,0x0a, + 0x00,0x10,0x08,0x0a,0xff,0xe1,0xbb,0xbf,0x00,0x0a,0x00,0xe1,0xbf,0x02,0xe0,0xa1, + 0x01,0xcf,0x86,0xd5,0xc6,0xd4,0x6c,0xd3,0x18,0xe2,0x0e,0x59,0xe1,0xf7,0x58,0x10, + 0x09,0x01,0xff,0xce,0xb1,0xcc,0x93,0x00,0x01,0xff,0xce,0xb1,0xcc,0x94,0x00,0xd2, + 0x28,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb1,0xcc,0x93,0x00,0x01,0xff,0xce,0xb1, + 0xcc,0x94,0x00,0x10,0x0b,0x01,0xff,0xce,0xb1,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff, + 0xce,0xb1,0xcc,0x94,0xcc,0x80,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0xb1,0xcc, + 0x93,0xcc,0x81,0x00,0x01,0xff,0xce,0xb1,0xcc,0x94,0xcc,0x81,0x00,0x10,0x0b,0x01, + 0xff,0xce,0xb1,0xcc,0x93,0xcd,0x82,0x00,0x01,0xff,0xce,0xb1,0xcc,0x94,0xcd,0x82, + 0x00,0xd3,0x18,0xe2,0x4a,0x59,0xe1,0x33,0x59,0x10,0x09,0x01,0xff,0xce,0xb5,0xcc, + 0x93,0x00,0x01,0xff,0xce,0xb5,0xcc,0x94,0x00,0xd2,0x28,0xd1,0x12,0x10,0x09,0x01, + 0xff,0xce,0xb5,0xcc,0x93,0x00,0x01,0xff,0xce,0xb5,0xcc,0x94,0x00,0x10,0x0b,0x01, + 0xff,0xce,0xb5,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff,0xce,0xb5,0xcc,0x94,0xcc,0x80, + 0x00,0x91,0x16,0x10,0x0b,0x01,0xff,0xce,0xb5,0xcc,0x93,0xcc,0x81,0x00,0x01,0xff, + 0xce,0xb5,0xcc,0x94,0xcc,0x81,0x00,0x00,0x00,0xd4,0x6c,0xd3,0x18,0xe2,0x74,0x59, + 0xe1,0x5d,0x59,0x10,0x09,0x01,0xff,0xce,0xb7,0xcc,0x93,0x00,0x01,0xff,0xce,0xb7, + 0xcc,0x94,0x00,0xd2,0x28,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb7,0xcc,0x93,0x00, + 0x01,0xff,0xce,0xb7,0xcc,0x94,0x00,0x10,0x0b,0x01,0xff,0xce,0xb7,0xcc,0x93,0xcc, + 0x80,0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcc,0x80,0x00,0xd1,0x16,0x10,0x0b,0x01, + 0xff,0xce,0xb7,0xcc,0x93,0xcc,0x81,0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcc,0x81, + 0x00,0x10,0x0b,0x01,0xff,0xce,0xb7,0xcc,0x93,0xcd,0x82,0x00,0x01,0xff,0xce,0xb7, + 0xcc,0x94,0xcd,0x82,0x00,0xd3,0x18,0xe2,0xb0,0x59,0xe1,0x99,0x59,0x10,0x09,0x01, + 0xff,0xce,0xb9,0xcc,0x93,0x00,0x01,0xff,0xce,0xb9,0xcc,0x94,0x00,0xd2,0x28,0xd1, + 0x12,0x10,0x09,0x01,0xff,0xce,0xb9,0xcc,0x93,0x00,0x01,0xff,0xce,0xb9,0xcc,0x94, + 0x00,0x10,0x0b,0x01,0xff,0xce,0xb9,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff,0xce,0xb9, + 0xcc,0x94,0xcc,0x80,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0xb9,0xcc,0x93,0xcc, + 0x81,0x00,0x01,0xff,0xce,0xb9,0xcc,0x94,0xcc,0x81,0x00,0x10,0x0b,0x01,0xff,0xce, + 0xb9,0xcc,0x93,0xcd,0x82,0x00,0x01,0xff,0xce,0xb9,0xcc,0x94,0xcd,0x82,0x00,0xcf, + 0x86,0xd5,0xac,0xd4,0x5a,0xd3,0x18,0xe2,0xed,0x59,0xe1,0xd6,0x59,0x10,0x09,0x01, + 0xff,0xce,0xbf,0xcc,0x93,0x00,0x01,0xff,0xce,0xbf,0xcc,0x94,0x00,0xd2,0x28,0xd1, + 0x12,0x10,0x09,0x01,0xff,0xce,0xbf,0xcc,0x93,0x00,0x01,0xff,0xce,0xbf,0xcc,0x94, + 0x00,0x10,0x0b,0x01,0xff,0xce,0xbf,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff,0xce,0xbf, + 0xcc,0x94,0xcc,0x80,0x00,0x91,0x16,0x10,0x0b,0x01,0xff,0xce,0xbf,0xcc,0x93,0xcc, + 0x81,0x00,0x01,0xff,0xce,0xbf,0xcc,0x94,0xcc,0x81,0x00,0x00,0x00,0xd3,0x18,0xe2, + 0x17,0x5a,0xe1,0x00,0x5a,0x10,0x09,0x01,0xff,0xcf,0x85,0xcc,0x93,0x00,0x01,0xff, + 0xcf,0x85,0xcc,0x94,0x00,0xd2,0x1c,0xd1,0x0d,0x10,0x04,0x00,0x00,0x01,0xff,0xcf, + 0x85,0xcc,0x94,0x00,0x10,0x04,0x00,0x00,0x01,0xff,0xcf,0x85,0xcc,0x94,0xcc,0x80, + 0x00,0xd1,0x0f,0x10,0x04,0x00,0x00,0x01,0xff,0xcf,0x85,0xcc,0x94,0xcc,0x81,0x00, + 0x10,0x04,0x00,0x00,0x01,0xff,0xcf,0x85,0xcc,0x94,0xcd,0x82,0x00,0xe4,0xd3,0x5a, + 0xd3,0x18,0xe2,0x52,0x5a,0xe1,0x3b,0x5a,0x10,0x09,0x01,0xff,0xcf,0x89,0xcc,0x93, + 0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0x00,0xd2,0x28,0xd1,0x12,0x10,0x09,0x01,0xff, + 0xcf,0x89,0xcc,0x93,0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0x00,0x10,0x0b,0x01,0xff, + 0xcf,0x89,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xcc,0x80,0x00, + 0xd1,0x16,0x10,0x0b,0x01,0xff,0xcf,0x89,0xcc,0x93,0xcc,0x81,0x00,0x01,0xff,0xcf, + 0x89,0xcc,0x94,0xcc,0x81,0x00,0x10,0x0b,0x01,0xff,0xcf,0x89,0xcc,0x93,0xcd,0x82, + 0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xcd,0x82,0x00,0xe0,0xd9,0x02,0xcf,0x86,0xe5, + 0x91,0x01,0xd4,0xc8,0xd3,0x64,0xd2,0x30,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0xb1, + 0xcc,0x93,0xce,0xb9,0x00,0x01,0xff,0xce,0xb1,0xcc,0x94,0xce,0xb9,0x00,0x10,0x0d, + 0x01,0xff,0xce,0xb1,0xcc,0x93,0xcc,0x80,0xce,0xb9,0x00,0x01,0xff,0xce,0xb1,0xcc, + 0x94,0xcc,0x80,0xce,0xb9,0x00,0xd1,0x1a,0x10,0x0d,0x01,0xff,0xce,0xb1,0xcc,0x93, + 0xcc,0x81,0xce,0xb9,0x00,0x01,0xff,0xce,0xb1,0xcc,0x94,0xcc,0x81,0xce,0xb9,0x00, + 0x10,0x0d,0x01,0xff,0xce,0xb1,0xcc,0x93,0xcd,0x82,0xce,0xb9,0x00,0x01,0xff,0xce, + 0xb1,0xcc,0x94,0xcd,0x82,0xce,0xb9,0x00,0xd2,0x30,0xd1,0x16,0x10,0x0b,0x01,0xff, + 0xce,0xb1,0xcc,0x93,0xce,0xb9,0x00,0x01,0xff,0xce,0xb1,0xcc,0x94,0xce,0xb9,0x00, + 0x10,0x0d,0x01,0xff,0xce,0xb1,0xcc,0x93,0xcc,0x80,0xce,0xb9,0x00,0x01,0xff,0xce, + 0xb1,0xcc,0x94,0xcc,0x80,0xce,0xb9,0x00,0xd1,0x1a,0x10,0x0d,0x01,0xff,0xce,0xb1, + 0xcc,0x93,0xcc,0x81,0xce,0xb9,0x00,0x01,0xff,0xce,0xb1,0xcc,0x94,0xcc,0x81,0xce, + 0xb9,0x00,0x10,0x0d,0x01,0xff,0xce,0xb1,0xcc,0x93,0xcd,0x82,0xce,0xb9,0x00,0x01, + 0xff,0xce,0xb1,0xcc,0x94,0xcd,0x82,0xce,0xb9,0x00,0xd3,0x64,0xd2,0x30,0xd1,0x16, + 0x10,0x0b,0x01,0xff,0xce,0xb7,0xcc,0x93,0xce,0xb9,0x00,0x01,0xff,0xce,0xb7,0xcc, + 0x94,0xce,0xb9,0x00,0x10,0x0d,0x01,0xff,0xce,0xb7,0xcc,0x93,0xcc,0x80,0xce,0xb9, + 0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcc,0x80,0xce,0xb9,0x00,0xd1,0x1a,0x10,0x0d, + 0x01,0xff,0xce,0xb7,0xcc,0x93,0xcc,0x81,0xce,0xb9,0x00,0x01,0xff,0xce,0xb7,0xcc, + 0x94,0xcc,0x81,0xce,0xb9,0x00,0x10,0x0d,0x01,0xff,0xce,0xb7,0xcc,0x93,0xcd,0x82, + 0xce,0xb9,0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcd,0x82,0xce,0xb9,0x00,0xd2,0x30, + 0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0xb7,0xcc,0x93,0xce,0xb9,0x00,0x01,0xff,0xce, + 0xb7,0xcc,0x94,0xce,0xb9,0x00,0x10,0x0d,0x01,0xff,0xce,0xb7,0xcc,0x93,0xcc,0x80, + 0xce,0xb9,0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcc,0x80,0xce,0xb9,0x00,0xd1,0x1a, + 0x10,0x0d,0x01,0xff,0xce,0xb7,0xcc,0x93,0xcc,0x81,0xce,0xb9,0x00,0x01,0xff,0xce, + 0xb7,0xcc,0x94,0xcc,0x81,0xce,0xb9,0x00,0x10,0x0d,0x01,0xff,0xce,0xb7,0xcc,0x93, + 0xcd,0x82,0xce,0xb9,0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcd,0x82,0xce,0xb9,0x00, + 0xd4,0xc8,0xd3,0x64,0xd2,0x30,0xd1,0x16,0x10,0x0b,0x01,0xff,0xcf,0x89,0xcc,0x93, + 0xce,0xb9,0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xce,0xb9,0x00,0x10,0x0d,0x01,0xff, + 0xcf,0x89,0xcc,0x93,0xcc,0x80,0xce,0xb9,0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xcc, + 0x80,0xce,0xb9,0x00,0xd1,0x1a,0x10,0x0d,0x01,0xff,0xcf,0x89,0xcc,0x93,0xcc,0x81, + 0xce,0xb9,0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xcc,0x81,0xce,0xb9,0x00,0x10,0x0d, + 0x01,0xff,0xcf,0x89,0xcc,0x93,0xcd,0x82,0xce,0xb9,0x00,0x01,0xff,0xcf,0x89,0xcc, + 0x94,0xcd,0x82,0xce,0xb9,0x00,0xd2,0x30,0xd1,0x16,0x10,0x0b,0x01,0xff,0xcf,0x89, + 0xcc,0x93,0xce,0xb9,0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xce,0xb9,0x00,0x10,0x0d, + 0x01,0xff,0xcf,0x89,0xcc,0x93,0xcc,0x80,0xce,0xb9,0x00,0x01,0xff,0xcf,0x89,0xcc, + 0x94,0xcc,0x80,0xce,0xb9,0x00,0xd1,0x1a,0x10,0x0d,0x01,0xff,0xcf,0x89,0xcc,0x93, + 0xcc,0x81,0xce,0xb9,0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xcc,0x81,0xce,0xb9,0x00, + 0x10,0x0d,0x01,0xff,0xcf,0x89,0xcc,0x93,0xcd,0x82,0xce,0xb9,0x00,0x01,0xff,0xcf, + 0x89,0xcc,0x94,0xcd,0x82,0xce,0xb9,0x00,0xd3,0x49,0xd2,0x26,0xd1,0x12,0x10,0x09, + 0x01,0xff,0xce,0xb1,0xcc,0x86,0x00,0x01,0xff,0xce,0xb1,0xcc,0x84,0x00,0x10,0x0b, + 0x01,0xff,0xce,0xb1,0xcc,0x80,0xce,0xb9,0x00,0x01,0xff,0xce,0xb1,0xce,0xb9,0x00, + 0xd1,0x0f,0x10,0x0b,0x01,0xff,0xce,0xb1,0xcc,0x81,0xce,0xb9,0x00,0x00,0x00,0x10, + 0x09,0x01,0xff,0xce,0xb1,0xcd,0x82,0x00,0x01,0xff,0xce,0xb1,0xcd,0x82,0xce,0xb9, + 0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb1,0xcc,0x86,0x00,0x01,0xff, + 0xce,0xb1,0xcc,0x84,0x00,0x10,0x09,0x01,0xff,0xce,0xb1,0xcc,0x80,0x00,0x01,0xff, + 0xce,0xb1,0xcc,0x81,0x00,0xe1,0xf3,0x5a,0x10,0x09,0x01,0xff,0xce,0xb1,0xce,0xb9, + 0x00,0x01,0x00,0xcf,0x86,0xd5,0xbd,0xd4,0x7e,0xd3,0x44,0xd2,0x21,0xd1,0x0d,0x10, + 0x04,0x01,0x00,0x01,0xff,0xc2,0xa8,0xcd,0x82,0x00,0x10,0x0b,0x01,0xff,0xce,0xb7, + 0xcc,0x80,0xce,0xb9,0x00,0x01,0xff,0xce,0xb7,0xce,0xb9,0x00,0xd1,0x0f,0x10,0x0b, + 0x01,0xff,0xce,0xb7,0xcc,0x81,0xce,0xb9,0x00,0x00,0x00,0x10,0x09,0x01,0xff,0xce, + 0xb7,0xcd,0x82,0x00,0x01,0xff,0xce,0xb7,0xcd,0x82,0xce,0xb9,0x00,0xd2,0x24,0xd1, + 0x12,0x10,0x09,0x01,0xff,0xce,0xb5,0xcc,0x80,0x00,0x01,0xff,0xce,0xb5,0xcc,0x81, + 0x00,0x10,0x09,0x01,0xff,0xce,0xb7,0xcc,0x80,0x00,0x01,0xff,0xce,0xb7,0xcc,0x81, + 0x00,0xe1,0x02,0x5b,0x10,0x09,0x01,0xff,0xce,0xb7,0xce,0xb9,0x00,0x01,0xff,0xe1, + 0xbe,0xbf,0xcc,0x80,0x00,0xd3,0x18,0xe2,0x28,0x5b,0xe1,0x11,0x5b,0x10,0x09,0x01, + 0xff,0xce,0xb9,0xcc,0x86,0x00,0x01,0xff,0xce,0xb9,0xcc,0x84,0x00,0xe2,0x4c,0x5b, + 0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb9,0xcc,0x86,0x00,0x01,0xff,0xce,0xb9,0xcc, + 0x84,0x00,0x10,0x09,0x01,0xff,0xce,0xb9,0xcc,0x80,0x00,0x01,0xff,0xce,0xb9,0xcc, + 0x81,0x00,0xd4,0x51,0xd3,0x18,0xe2,0x6f,0x5b,0xe1,0x58,0x5b,0x10,0x09,0x01,0xff, + 0xcf,0x85,0xcc,0x86,0x00,0x01,0xff,0xcf,0x85,0xcc,0x84,0x00,0xd2,0x24,0xd1,0x12, + 0x10,0x09,0x01,0xff,0xcf,0x85,0xcc,0x86,0x00,0x01,0xff,0xcf,0x85,0xcc,0x84,0x00, + 0x10,0x09,0x01,0xff,0xcf,0x85,0xcc,0x80,0x00,0x01,0xff,0xcf,0x85,0xcc,0x81,0x00, + 0xe1,0x8f,0x5b,0x10,0x09,0x01,0xff,0xcf,0x81,0xcc,0x94,0x00,0x01,0xff,0xc2,0xa8, + 0xcc,0x80,0x00,0xd3,0x3b,0xd2,0x18,0x51,0x04,0x00,0x00,0x10,0x0b,0x01,0xff,0xcf, + 0x89,0xcc,0x80,0xce,0xb9,0x00,0x01,0xff,0xcf,0x89,0xce,0xb9,0x00,0xd1,0x0f,0x10, + 0x0b,0x01,0xff,0xcf,0x89,0xcc,0x81,0xce,0xb9,0x00,0x00,0x00,0x10,0x09,0x01,0xff, + 0xcf,0x89,0xcd,0x82,0x00,0x01,0xff,0xcf,0x89,0xcd,0x82,0xce,0xb9,0x00,0xd2,0x24, + 0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xbf,0xcc,0x80,0x00,0x01,0xff,0xce,0xbf,0xcc, + 0x81,0x00,0x10,0x09,0x01,0xff,0xcf,0x89,0xcc,0x80,0x00,0x01,0xff,0xcf,0x89,0xcc, + 0x81,0x00,0xe1,0x99,0x5b,0x10,0x09,0x01,0xff,0xcf,0x89,0xce,0xb9,0x00,0x01,0xff, + 0xc2,0xb4,0x00,0xe0,0x0c,0x68,0xcf,0x86,0xe5,0x23,0x02,0xe4,0x25,0x01,0xe3,0x85, + 0x5e,0xd2,0x2a,0xe1,0x5f,0x5c,0xe0,0xdd,0x5b,0xcf,0x86,0xe5,0xbb,0x5b,0x94,0x1b, + 0xe3,0xa4,0x5b,0x92,0x14,0x91,0x10,0x10,0x08,0x01,0xff,0xe2,0x80,0x82,0x00,0x01, + 0xff,0xe2,0x80,0x83,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd1,0xd6,0xd0,0x46,0xcf, + 0x86,0x55,0x04,0x01,0x00,0xd4,0x29,0xd3,0x13,0x52,0x04,0x01,0x00,0x51,0x04,0x01, + 0x00,0x10,0x07,0x01,0xff,0xcf,0x89,0x00,0x01,0x00,0x92,0x12,0x51,0x04,0x01,0x00, + 0x10,0x06,0x01,0xff,0x6b,0x00,0x01,0xff,0x61,0xcc,0x8a,0x00,0x01,0x00,0xe3,0x25, + 0x5d,0x92,0x10,0x51,0x04,0x01,0x00,0x10,0x08,0x01,0xff,0xe2,0x85,0x8e,0x00,0x01, + 0x00,0x01,0x00,0xcf,0x86,0xd5,0x0a,0xe4,0x42,0x5d,0x63,0x2d,0x5d,0x06,0x00,0x94, + 0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0x85,0xb0,0x00,0x01, + 0xff,0xe2,0x85,0xb1,0x00,0x10,0x08,0x01,0xff,0xe2,0x85,0xb2,0x00,0x01,0xff,0xe2, + 0x85,0xb3,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0x85,0xb4,0x00,0x01,0xff,0xe2, + 0x85,0xb5,0x00,0x10,0x08,0x01,0xff,0xe2,0x85,0xb6,0x00,0x01,0xff,0xe2,0x85,0xb7, + 0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0x85,0xb8,0x00,0x01,0xff,0xe2, + 0x85,0xb9,0x00,0x10,0x08,0x01,0xff,0xe2,0x85,0xba,0x00,0x01,0xff,0xe2,0x85,0xbb, + 0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0x85,0xbc,0x00,0x01,0xff,0xe2,0x85,0xbd, + 0x00,0x10,0x08,0x01,0xff,0xe2,0x85,0xbe,0x00,0x01,0xff,0xe2,0x85,0xbf,0x00,0x01, + 0x00,0xe0,0x34,0x5d,0xcf,0x86,0xe5,0x13,0x5d,0xe4,0xf2,0x5c,0xe3,0xe1,0x5c,0xe2, + 0xd4,0x5c,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x04,0xff,0xe2,0x86,0x84,0x00, + 0xe3,0x23,0x61,0xe2,0xf0,0x60,0xd1,0x0c,0xe0,0x9d,0x60,0xcf,0x86,0x65,0x7e,0x60, + 0x01,0x00,0xd0,0x62,0xcf,0x86,0x55,0x04,0x01,0x00,0x54,0x04,0x01,0x00,0xd3,0x18, + 0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x08,0x01,0xff,0xe2,0x93,0x90,0x00, + 0x01,0xff,0xe2,0x93,0x91,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0x93, + 0x92,0x00,0x01,0xff,0xe2,0x93,0x93,0x00,0x10,0x08,0x01,0xff,0xe2,0x93,0x94,0x00, + 0x01,0xff,0xe2,0x93,0x95,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe2,0x93,0x96,0x00, + 0x01,0xff,0xe2,0x93,0x97,0x00,0x10,0x08,0x01,0xff,0xe2,0x93,0x98,0x00,0x01,0xff, + 0xe2,0x93,0x99,0x00,0xcf,0x86,0xe5,0x57,0x60,0x94,0x80,0xd3,0x40,0xd2,0x20,0xd1, + 0x10,0x10,0x08,0x01,0xff,0xe2,0x93,0x9a,0x00,0x01,0xff,0xe2,0x93,0x9b,0x00,0x10, + 0x08,0x01,0xff,0xe2,0x93,0x9c,0x00,0x01,0xff,0xe2,0x93,0x9d,0x00,0xd1,0x10,0x10, + 0x08,0x01,0xff,0xe2,0x93,0x9e,0x00,0x01,0xff,0xe2,0x93,0x9f,0x00,0x10,0x08,0x01, + 0xff,0xe2,0x93,0xa0,0x00,0x01,0xff,0xe2,0x93,0xa1,0x00,0xd2,0x20,0xd1,0x10,0x10, + 0x08,0x01,0xff,0xe2,0x93,0xa2,0x00,0x01,0xff,0xe2,0x93,0xa3,0x00,0x10,0x08,0x01, + 0xff,0xe2,0x93,0xa4,0x00,0x01,0xff,0xe2,0x93,0xa5,0x00,0xd1,0x10,0x10,0x08,0x01, + 0xff,0xe2,0x93,0xa6,0x00,0x01,0xff,0xe2,0x93,0xa7,0x00,0x10,0x08,0x01,0xff,0xe2, + 0x93,0xa8,0x00,0x01,0xff,0xe2,0x93,0xa9,0x00,0x01,0x00,0xd4,0x0c,0xe3,0x33,0x62, + 0xe2,0x2c,0x62,0xcf,0x06,0x04,0x00,0xe3,0x0c,0x65,0xe2,0xff,0x63,0xe1,0x2e,0x02, + 0xe0,0x84,0x01,0xcf,0x86,0xe5,0x01,0x01,0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10, + 0x10,0x08,0x08,0xff,0xe2,0xb0,0xb0,0x00,0x08,0xff,0xe2,0xb0,0xb1,0x00,0x10,0x08, + 0x08,0xff,0xe2,0xb0,0xb2,0x00,0x08,0xff,0xe2,0xb0,0xb3,0x00,0xd1,0x10,0x10,0x08, + 0x08,0xff,0xe2,0xb0,0xb4,0x00,0x08,0xff,0xe2,0xb0,0xb5,0x00,0x10,0x08,0x08,0xff, + 0xe2,0xb0,0xb6,0x00,0x08,0xff,0xe2,0xb0,0xb7,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08, + 0x08,0xff,0xe2,0xb0,0xb8,0x00,0x08,0xff,0xe2,0xb0,0xb9,0x00,0x10,0x08,0x08,0xff, + 0xe2,0xb0,0xba,0x00,0x08,0xff,0xe2,0xb0,0xbb,0x00,0xd1,0x10,0x10,0x08,0x08,0xff, + 0xe2,0xb0,0xbc,0x00,0x08,0xff,0xe2,0xb0,0xbd,0x00,0x10,0x08,0x08,0xff,0xe2,0xb0, + 0xbe,0x00,0x08,0xff,0xe2,0xb0,0xbf,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08, + 0x08,0xff,0xe2,0xb1,0x80,0x00,0x08,0xff,0xe2,0xb1,0x81,0x00,0x10,0x08,0x08,0xff, + 0xe2,0xb1,0x82,0x00,0x08,0xff,0xe2,0xb1,0x83,0x00,0xd1,0x10,0x10,0x08,0x08,0xff, + 0xe2,0xb1,0x84,0x00,0x08,0xff,0xe2,0xb1,0x85,0x00,0x10,0x08,0x08,0xff,0xe2,0xb1, + 0x86,0x00,0x08,0xff,0xe2,0xb1,0x87,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x08,0xff, + 0xe2,0xb1,0x88,0x00,0x08,0xff,0xe2,0xb1,0x89,0x00,0x10,0x08,0x08,0xff,0xe2,0xb1, + 0x8a,0x00,0x08,0xff,0xe2,0xb1,0x8b,0x00,0xd1,0x10,0x10,0x08,0x08,0xff,0xe2,0xb1, + 0x8c,0x00,0x08,0xff,0xe2,0xb1,0x8d,0x00,0x10,0x08,0x08,0xff,0xe2,0xb1,0x8e,0x00, + 0x08,0xff,0xe2,0xb1,0x8f,0x00,0x94,0x7c,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08, + 0x08,0xff,0xe2,0xb1,0x90,0x00,0x08,0xff,0xe2,0xb1,0x91,0x00,0x10,0x08,0x08,0xff, + 0xe2,0xb1,0x92,0x00,0x08,0xff,0xe2,0xb1,0x93,0x00,0xd1,0x10,0x10,0x08,0x08,0xff, + 0xe2,0xb1,0x94,0x00,0x08,0xff,0xe2,0xb1,0x95,0x00,0x10,0x08,0x08,0xff,0xe2,0xb1, + 0x96,0x00,0x08,0xff,0xe2,0xb1,0x97,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x08,0xff, + 0xe2,0xb1,0x98,0x00,0x08,0xff,0xe2,0xb1,0x99,0x00,0x10,0x08,0x08,0xff,0xe2,0xb1, + 0x9a,0x00,0x08,0xff,0xe2,0xb1,0x9b,0x00,0xd1,0x10,0x10,0x08,0x08,0xff,0xe2,0xb1, + 0x9c,0x00,0x08,0xff,0xe2,0xb1,0x9d,0x00,0x10,0x08,0x08,0xff,0xe2,0xb1,0x9e,0x00, + 0x00,0x00,0x08,0x00,0xcf,0x86,0xd5,0x07,0x64,0xef,0x61,0x08,0x00,0xd4,0x63,0xd3, + 0x32,0xd2,0x1b,0xd1,0x0c,0x10,0x08,0x09,0xff,0xe2,0xb1,0xa1,0x00,0x09,0x00,0x10, + 0x07,0x09,0xff,0xc9,0xab,0x00,0x09,0xff,0xe1,0xb5,0xbd,0x00,0xd1,0x0b,0x10,0x07, + 0x09,0xff,0xc9,0xbd,0x00,0x09,0x00,0x10,0x04,0x09,0x00,0x09,0xff,0xe2,0xb1,0xa8, + 0x00,0xd2,0x18,0xd1,0x0c,0x10,0x04,0x09,0x00,0x09,0xff,0xe2,0xb1,0xaa,0x00,0x10, + 0x04,0x09,0x00,0x09,0xff,0xe2,0xb1,0xac,0x00,0xd1,0x0b,0x10,0x04,0x09,0x00,0x0a, + 0xff,0xc9,0x91,0x00,0x10,0x07,0x0a,0xff,0xc9,0xb1,0x00,0x0a,0xff,0xc9,0x90,0x00, + 0xd3,0x27,0xd2,0x17,0xd1,0x0b,0x10,0x07,0x0b,0xff,0xc9,0x92,0x00,0x0a,0x00,0x10, + 0x08,0x0a,0xff,0xe2,0xb1,0xb3,0x00,0x0a,0x00,0x91,0x0c,0x10,0x04,0x09,0x00,0x09, + 0xff,0xe2,0xb1,0xb6,0x00,0x09,0x00,0x52,0x04,0x0a,0x00,0x51,0x04,0x0a,0x00,0x10, + 0x07,0x0b,0xff,0xc8,0xbf,0x00,0x0b,0xff,0xc9,0x80,0x00,0xe0,0x83,0x01,0xcf,0x86, + 0xd5,0xc0,0xd4,0x60,0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb2, + 0x81,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2,0x83,0x00,0x08,0x00,0xd1,0x0c, + 0x10,0x08,0x08,0xff,0xe2,0xb2,0x85,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2, + 0x87,0x00,0x08,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb2,0x89,0x00, + 0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2,0x8b,0x00,0x08,0x00,0xd1,0x0c,0x10,0x08, + 0x08,0xff,0xe2,0xb2,0x8d,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2,0x8f,0x00, + 0x08,0x00,0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb2,0x91,0x00, + 0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2,0x93,0x00,0x08,0x00,0xd1,0x0c,0x10,0x08, + 0x08,0xff,0xe2,0xb2,0x95,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2,0x97,0x00, + 0x08,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb2,0x99,0x00,0x08,0x00, + 0x10,0x08,0x08,0xff,0xe2,0xb2,0x9b,0x00,0x08,0x00,0xd1,0x0c,0x10,0x08,0x08,0xff, + 0xe2,0xb2,0x9d,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2,0x9f,0x00,0x08,0x00, + 0xd4,0x60,0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb2,0xa1,0x00, + 0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2,0xa3,0x00,0x08,0x00,0xd1,0x0c,0x10,0x08, + 0x08,0xff,0xe2,0xb2,0xa5,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2,0xa7,0x00, + 0x08,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb2,0xa9,0x00,0x08,0x00, + 0x10,0x08,0x08,0xff,0xe2,0xb2,0xab,0x00,0x08,0x00,0xd1,0x0c,0x10,0x08,0x08,0xff, + 0xe2,0xb2,0xad,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2,0xaf,0x00,0x08,0x00, + 0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb2,0xb1,0x00,0x08,0x00, + 0x10,0x08,0x08,0xff,0xe2,0xb2,0xb3,0x00,0x08,0x00,0xd1,0x0c,0x10,0x08,0x08,0xff, + 0xe2,0xb2,0xb5,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2,0xb7,0x00,0x08,0x00, + 0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb2,0xb9,0x00,0x08,0x00,0x10,0x08, + 0x08,0xff,0xe2,0xb2,0xbb,0x00,0x08,0x00,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb2, + 0xbd,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb2,0xbf,0x00,0x08,0x00,0xcf,0x86, + 0xd5,0xc0,0xd4,0x60,0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb3, + 0x81,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb3,0x83,0x00,0x08,0x00,0xd1,0x0c, + 0x10,0x08,0x08,0xff,0xe2,0xb3,0x85,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb3, + 0x87,0x00,0x08,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb3,0x89,0x00, + 0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb3,0x8b,0x00,0x08,0x00,0xd1,0x0c,0x10,0x08, + 0x08,0xff,0xe2,0xb3,0x8d,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb3,0x8f,0x00, + 0x08,0x00,0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb3,0x91,0x00, + 0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb3,0x93,0x00,0x08,0x00,0xd1,0x0c,0x10,0x08, + 0x08,0xff,0xe2,0xb3,0x95,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb3,0x97,0x00, + 0x08,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb3,0x99,0x00,0x08,0x00, + 0x10,0x08,0x08,0xff,0xe2,0xb3,0x9b,0x00,0x08,0x00,0xd1,0x0c,0x10,0x08,0x08,0xff, + 0xe2,0xb3,0x9d,0x00,0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb3,0x9f,0x00,0x08,0x00, + 0xd4,0x3b,0xd3,0x1c,0x92,0x18,0xd1,0x0c,0x10,0x08,0x08,0xff,0xe2,0xb3,0xa1,0x00, + 0x08,0x00,0x10,0x08,0x08,0xff,0xe2,0xb3,0xa3,0x00,0x08,0x00,0x08,0x00,0xd2,0x10, + 0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x0b,0xff,0xe2,0xb3,0xac,0x00,0xe1,0x3b, + 0x5f,0x10,0x04,0x0b,0x00,0x0b,0xff,0xe2,0xb3,0xae,0x00,0xe3,0x40,0x5f,0x92,0x10, + 0x51,0x04,0x0b,0xe6,0x10,0x08,0x0d,0xff,0xe2,0xb3,0xb3,0x00,0x0d,0x00,0x00,0x00, + 0xe2,0x98,0x08,0xd1,0x0b,0xe0,0x11,0x67,0xcf,0x86,0xcf,0x06,0x01,0x00,0xe0,0x65, + 0x6c,0xcf,0x86,0xe5,0xa7,0x05,0xd4,0x06,0xcf,0x06,0x04,0x00,0xd3,0x0c,0xe2,0xf8, + 0x67,0xe1,0x8f,0x67,0xcf,0x06,0x04,0x00,0xe2,0xdb,0x01,0xe1,0x26,0x01,0xd0,0x09, + 0xcf,0x86,0x65,0xf4,0x67,0x0a,0x00,0xcf,0x86,0xd5,0xc0,0xd4,0x60,0xd3,0x30,0xd2, + 0x18,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x99,0x81,0x00,0x0a,0x00,0x10,0x08,0x0a, + 0xff,0xea,0x99,0x83,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x99,0x85, + 0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x99,0x87,0x00,0x0a,0x00,0xd2,0x18,0xd1, + 0x0c,0x10,0x08,0x0a,0xff,0xea,0x99,0x89,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea, + 0x99,0x8b,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x99,0x8d,0x00,0x0a, + 0x00,0x10,0x08,0x0a,0xff,0xea,0x99,0x8f,0x00,0x0a,0x00,0xd3,0x30,0xd2,0x18,0xd1, + 0x0c,0x10,0x08,0x0a,0xff,0xea,0x99,0x91,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea, + 0x99,0x93,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x99,0x95,0x00,0x0a, + 0x00,0x10,0x08,0x0a,0xff,0xea,0x99,0x97,0x00,0x0a,0x00,0xd2,0x18,0xd1,0x0c,0x10, + 0x08,0x0a,0xff,0xea,0x99,0x99,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x99,0x9b, + 0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x99,0x9d,0x00,0x0a,0x00,0x10, + 0x08,0x0a,0xff,0xea,0x99,0x9f,0x00,0x0a,0x00,0xe4,0x5d,0x67,0xd3,0x30,0xd2,0x18, + 0xd1,0x0c,0x10,0x08,0x0c,0xff,0xea,0x99,0xa1,0x00,0x0c,0x00,0x10,0x08,0x0a,0xff, + 0xea,0x99,0xa3,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x99,0xa5,0x00, + 0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x99,0xa7,0x00,0x0a,0x00,0xd2,0x18,0xd1,0x0c, + 0x10,0x08,0x0a,0xff,0xea,0x99,0xa9,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x99, + 0xab,0x00,0x0a,0x00,0xe1,0x0c,0x67,0x10,0x08,0x0a,0xff,0xea,0x99,0xad,0x00,0x0a, + 0x00,0xe0,0x35,0x67,0xcf,0x86,0x95,0xab,0xd4,0x60,0xd3,0x30,0xd2,0x18,0xd1,0x0c, + 0x10,0x08,0x0a,0xff,0xea,0x9a,0x81,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9a, + 0x83,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9a,0x85,0x00,0x0a,0x00, + 0x10,0x08,0x0a,0xff,0xea,0x9a,0x87,0x00,0x0a,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x08, + 0x0a,0xff,0xea,0x9a,0x89,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9a,0x8b,0x00, + 0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9a,0x8d,0x00,0x0a,0x00,0x10,0x08, + 0x0a,0xff,0xea,0x9a,0x8f,0x00,0x0a,0x00,0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x08, + 0x0a,0xff,0xea,0x9a,0x91,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9a,0x93,0x00, + 0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9a,0x95,0x00,0x0a,0x00,0x10,0x08, + 0x0a,0xff,0xea,0x9a,0x97,0x00,0x0a,0x00,0xe2,0x92,0x66,0xd1,0x0c,0x10,0x08,0x10, + 0xff,0xea,0x9a,0x99,0x00,0x10,0x00,0x10,0x08,0x10,0xff,0xea,0x9a,0x9b,0x00,0x10, + 0x00,0x0b,0x00,0xe1,0x10,0x02,0xd0,0xb9,0xcf,0x86,0xd5,0x07,0x64,0x9e,0x66,0x08, + 0x00,0xd4,0x58,0xd3,0x28,0xd2,0x10,0x51,0x04,0x09,0x00,0x10,0x08,0x0a,0xff,0xea, + 0x9c,0xa3,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9c,0xa5,0x00,0x0a, + 0x00,0x10,0x08,0x0a,0xff,0xea,0x9c,0xa7,0x00,0x0a,0x00,0xd2,0x18,0xd1,0x0c,0x10, + 0x08,0x0a,0xff,0xea,0x9c,0xa9,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9c,0xab, + 0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9c,0xad,0x00,0x0a,0x00,0x10, + 0x08,0x0a,0xff,0xea,0x9c,0xaf,0x00,0x0a,0x00,0xd3,0x28,0xd2,0x10,0x51,0x04,0x0a, + 0x00,0x10,0x08,0x0a,0xff,0xea,0x9c,0xb3,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a, + 0xff,0xea,0x9c,0xb5,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9c,0xb7,0x00,0x0a, + 0x00,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9c,0xb9,0x00,0x0a,0x00,0x10, + 0x08,0x0a,0xff,0xea,0x9c,0xbb,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea, + 0x9c,0xbd,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9c,0xbf,0x00,0x0a,0x00,0xcf, + 0x86,0xd5,0xc0,0xd4,0x60,0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea, + 0x9d,0x81,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0x83,0x00,0x0a,0x00,0xd1, + 0x0c,0x10,0x08,0x0a,0xff,0xea,0x9d,0x85,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea, + 0x9d,0x87,0x00,0x0a,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9d,0x89, + 0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0x8b,0x00,0x0a,0x00,0xd1,0x0c,0x10, + 0x08,0x0a,0xff,0xea,0x9d,0x8d,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0x8f, + 0x00,0x0a,0x00,0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9d,0x91, + 0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0x93,0x00,0x0a,0x00,0xd1,0x0c,0x10, + 0x08,0x0a,0xff,0xea,0x9d,0x95,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0x97, + 0x00,0x0a,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9d,0x99,0x00,0x0a, + 0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0x9b,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a, + 0xff,0xea,0x9d,0x9d,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0x9f,0x00,0x0a, + 0x00,0xd4,0x60,0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9d,0xa1, + 0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0xa3,0x00,0x0a,0x00,0xd1,0x0c,0x10, + 0x08,0x0a,0xff,0xea,0x9d,0xa5,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0xa7, + 0x00,0x0a,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9d,0xa9,0x00,0x0a, + 0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0xab,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a, + 0xff,0xea,0x9d,0xad,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0xaf,0x00,0x0a, + 0x00,0x53,0x04,0x0a,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x04,0x0a,0x00,0x0a,0xff,0xea, + 0x9d,0xba,0x00,0x10,0x04,0x0a,0x00,0x0a,0xff,0xea,0x9d,0xbc,0x00,0xd1,0x0c,0x10, + 0x04,0x0a,0x00,0x0a,0xff,0xe1,0xb5,0xb9,0x00,0x10,0x08,0x0a,0xff,0xea,0x9d,0xbf, + 0x00,0x0a,0x00,0xe0,0x71,0x01,0xcf,0x86,0xd5,0xa6,0xd4,0x4e,0xd3,0x30,0xd2,0x18, + 0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9e,0x81,0x00,0x0a,0x00,0x10,0x08,0x0a,0xff, + 0xea,0x9e,0x83,0x00,0x0a,0x00,0xd1,0x0c,0x10,0x08,0x0a,0xff,0xea,0x9e,0x85,0x00, + 0x0a,0x00,0x10,0x08,0x0a,0xff,0xea,0x9e,0x87,0x00,0x0a,0x00,0xd2,0x10,0x51,0x04, + 0x0a,0x00,0x10,0x04,0x0a,0x00,0x0a,0xff,0xea,0x9e,0x8c,0x00,0xe1,0x9a,0x64,0x10, + 0x04,0x0a,0x00,0x0c,0xff,0xc9,0xa5,0x00,0xd3,0x28,0xd2,0x18,0xd1,0x0c,0x10,0x08, + 0x0c,0xff,0xea,0x9e,0x91,0x00,0x0c,0x00,0x10,0x08,0x0d,0xff,0xea,0x9e,0x93,0x00, + 0x0d,0x00,0x51,0x04,0x10,0x00,0x10,0x08,0x10,0xff,0xea,0x9e,0x97,0x00,0x10,0x00, + 0xd2,0x18,0xd1,0x0c,0x10,0x08,0x10,0xff,0xea,0x9e,0x99,0x00,0x10,0x00,0x10,0x08, + 0x10,0xff,0xea,0x9e,0x9b,0x00,0x10,0x00,0xd1,0x0c,0x10,0x08,0x10,0xff,0xea,0x9e, + 0x9d,0x00,0x10,0x00,0x10,0x08,0x10,0xff,0xea,0x9e,0x9f,0x00,0x10,0x00,0xd4,0x63, + 0xd3,0x30,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x0c,0xff,0xea,0x9e,0xa1,0x00,0x0c,0x00, + 0x10,0x08,0x0c,0xff,0xea,0x9e,0xa3,0x00,0x0c,0x00,0xd1,0x0c,0x10,0x08,0x0c,0xff, + 0xea,0x9e,0xa5,0x00,0x0c,0x00,0x10,0x08,0x0c,0xff,0xea,0x9e,0xa7,0x00,0x0c,0x00, + 0xd2,0x1a,0xd1,0x0c,0x10,0x08,0x0c,0xff,0xea,0x9e,0xa9,0x00,0x0c,0x00,0x10,0x07, + 0x0d,0xff,0xc9,0xa6,0x00,0x10,0xff,0xc9,0x9c,0x00,0xd1,0x0e,0x10,0x07,0x10,0xff, + 0xc9,0xa1,0x00,0x10,0xff,0xc9,0xac,0x00,0x10,0x07,0x12,0xff,0xc9,0xaa,0x00,0x14, + 0x00,0xd3,0x35,0xd2,0x1d,0xd1,0x0e,0x10,0x07,0x10,0xff,0xca,0x9e,0x00,0x10,0xff, + 0xca,0x87,0x00,0x10,0x07,0x11,0xff,0xca,0x9d,0x00,0x11,0xff,0xea,0xad,0x93,0x00, + 0xd1,0x0c,0x10,0x08,0x11,0xff,0xea,0x9e,0xb5,0x00,0x11,0x00,0x10,0x08,0x11,0xff, + 0xea,0x9e,0xb7,0x00,0x11,0x00,0xd2,0x18,0xd1,0x0c,0x10,0x08,0x14,0xff,0xea,0x9e, + 0xb9,0x00,0x14,0x00,0x10,0x08,0x15,0xff,0xea,0x9e,0xbb,0x00,0x15,0x00,0xd1,0x0c, + 0x10,0x08,0x15,0xff,0xea,0x9e,0xbd,0x00,0x15,0x00,0x10,0x08,0x15,0xff,0xea,0x9e, + 0xbf,0x00,0x15,0x00,0xcf,0x86,0xe5,0xd4,0x63,0x94,0x2f,0x93,0x2b,0xd2,0x10,0x51, + 0x04,0x00,0x00,0x10,0x08,0x15,0xff,0xea,0x9f,0x83,0x00,0x15,0x00,0xd1,0x0f,0x10, + 0x08,0x15,0xff,0xea,0x9e,0x94,0x00,0x15,0xff,0xca,0x82,0x00,0x10,0x08,0x15,0xff, + 0xe1,0xb6,0x8e,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xe4,0xb4,0x66,0xd3,0x1d,0xe2, + 0x5b,0x64,0xe1,0x0a,0x64,0xe0,0xf7,0x63,0xcf,0x86,0xe5,0xd8,0x63,0x94,0x0b,0x93, + 0x07,0x62,0xc3,0x63,0x08,0x00,0x08,0x00,0x08,0x00,0xd2,0x0f,0xe1,0x5a,0x65,0xe0, + 0x27,0x65,0xcf,0x86,0x65,0x0c,0x65,0x0a,0x00,0xd1,0xab,0xd0,0x1a,0xcf,0x86,0xe5, + 0x17,0x66,0xe4,0xfa,0x65,0xe3,0xe1,0x65,0xe2,0xd4,0x65,0x91,0x08,0x10,0x04,0x00, + 0x00,0x0c,0x00,0x0c,0x00,0xcf,0x86,0x55,0x04,0x10,0x00,0xd4,0x0b,0x93,0x07,0x62, + 0x27,0x66,0x11,0x00,0x00,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x11,0xff, + 0xe1,0x8e,0xa0,0x00,0x11,0xff,0xe1,0x8e,0xa1,0x00,0x10,0x08,0x11,0xff,0xe1,0x8e, + 0xa2,0x00,0x11,0xff,0xe1,0x8e,0xa3,0x00,0xd1,0x10,0x10,0x08,0x11,0xff,0xe1,0x8e, + 0xa4,0x00,0x11,0xff,0xe1,0x8e,0xa5,0x00,0x10,0x08,0x11,0xff,0xe1,0x8e,0xa6,0x00, + 0x11,0xff,0xe1,0x8e,0xa7,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x11,0xff,0xe1,0x8e, + 0xa8,0x00,0x11,0xff,0xe1,0x8e,0xa9,0x00,0x10,0x08,0x11,0xff,0xe1,0x8e,0xaa,0x00, + 0x11,0xff,0xe1,0x8e,0xab,0x00,0xd1,0x10,0x10,0x08,0x11,0xff,0xe1,0x8e,0xac,0x00, + 0x11,0xff,0xe1,0x8e,0xad,0x00,0x10,0x08,0x11,0xff,0xe1,0x8e,0xae,0x00,0x11,0xff, + 0xe1,0x8e,0xaf,0x00,0xe0,0xb2,0x65,0xcf,0x86,0xe5,0x01,0x01,0xd4,0x80,0xd3,0x40, + 0xd2,0x20,0xd1,0x10,0x10,0x08,0x11,0xff,0xe1,0x8e,0xb0,0x00,0x11,0xff,0xe1,0x8e, + 0xb1,0x00,0x10,0x08,0x11,0xff,0xe1,0x8e,0xb2,0x00,0x11,0xff,0xe1,0x8e,0xb3,0x00, + 0xd1,0x10,0x10,0x08,0x11,0xff,0xe1,0x8e,0xb4,0x00,0x11,0xff,0xe1,0x8e,0xb5,0x00, + 0x10,0x08,0x11,0xff,0xe1,0x8e,0xb6,0x00,0x11,0xff,0xe1,0x8e,0xb7,0x00,0xd2,0x20, + 0xd1,0x10,0x10,0x08,0x11,0xff,0xe1,0x8e,0xb8,0x00,0x11,0xff,0xe1,0x8e,0xb9,0x00, + 0x10,0x08,0x11,0xff,0xe1,0x8e,0xba,0x00,0x11,0xff,0xe1,0x8e,0xbb,0x00,0xd1,0x10, + 0x10,0x08,0x11,0xff,0xe1,0x8e,0xbc,0x00,0x11,0xff,0xe1,0x8e,0xbd,0x00,0x10,0x08, + 0x11,0xff,0xe1,0x8e,0xbe,0x00,0x11,0xff,0xe1,0x8e,0xbf,0x00,0xd3,0x40,0xd2,0x20, + 0xd1,0x10,0x10,0x08,0x11,0xff,0xe1,0x8f,0x80,0x00,0x11,0xff,0xe1,0x8f,0x81,0x00, + 0x10,0x08,0x11,0xff,0xe1,0x8f,0x82,0x00,0x11,0xff,0xe1,0x8f,0x83,0x00,0xd1,0x10, + 0x10,0x08,0x11,0xff,0xe1,0x8f,0x84,0x00,0x11,0xff,0xe1,0x8f,0x85,0x00,0x10,0x08, + 0x11,0xff,0xe1,0x8f,0x86,0x00,0x11,0xff,0xe1,0x8f,0x87,0x00,0xd2,0x20,0xd1,0x10, + 0x10,0x08,0x11,0xff,0xe1,0x8f,0x88,0x00,0x11,0xff,0xe1,0x8f,0x89,0x00,0x10,0x08, + 0x11,0xff,0xe1,0x8f,0x8a,0x00,0x11,0xff,0xe1,0x8f,0x8b,0x00,0xd1,0x10,0x10,0x08, + 0x11,0xff,0xe1,0x8f,0x8c,0x00,0x11,0xff,0xe1,0x8f,0x8d,0x00,0x10,0x08,0x11,0xff, + 0xe1,0x8f,0x8e,0x00,0x11,0xff,0xe1,0x8f,0x8f,0x00,0xd4,0x80,0xd3,0x40,0xd2,0x20, + 0xd1,0x10,0x10,0x08,0x11,0xff,0xe1,0x8f,0x90,0x00,0x11,0xff,0xe1,0x8f,0x91,0x00, + 0x10,0x08,0x11,0xff,0xe1,0x8f,0x92,0x00,0x11,0xff,0xe1,0x8f,0x93,0x00,0xd1,0x10, + 0x10,0x08,0x11,0xff,0xe1,0x8f,0x94,0x00,0x11,0xff,0xe1,0x8f,0x95,0x00,0x10,0x08, + 0x11,0xff,0xe1,0x8f,0x96,0x00,0x11,0xff,0xe1,0x8f,0x97,0x00,0xd2,0x20,0xd1,0x10, + 0x10,0x08,0x11,0xff,0xe1,0x8f,0x98,0x00,0x11,0xff,0xe1,0x8f,0x99,0x00,0x10,0x08, + 0x11,0xff,0xe1,0x8f,0x9a,0x00,0x11,0xff,0xe1,0x8f,0x9b,0x00,0xd1,0x10,0x10,0x08, + 0x11,0xff,0xe1,0x8f,0x9c,0x00,0x11,0xff,0xe1,0x8f,0x9d,0x00,0x10,0x08,0x11,0xff, + 0xe1,0x8f,0x9e,0x00,0x11,0xff,0xe1,0x8f,0x9f,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10, + 0x10,0x08,0x11,0xff,0xe1,0x8f,0xa0,0x00,0x11,0xff,0xe1,0x8f,0xa1,0x00,0x10,0x08, + 0x11,0xff,0xe1,0x8f,0xa2,0x00,0x11,0xff,0xe1,0x8f,0xa3,0x00,0xd1,0x10,0x10,0x08, + 0x11,0xff,0xe1,0x8f,0xa4,0x00,0x11,0xff,0xe1,0x8f,0xa5,0x00,0x10,0x08,0x11,0xff, + 0xe1,0x8f,0xa6,0x00,0x11,0xff,0xe1,0x8f,0xa7,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08, + 0x11,0xff,0xe1,0x8f,0xa8,0x00,0x11,0xff,0xe1,0x8f,0xa9,0x00,0x10,0x08,0x11,0xff, + 0xe1,0x8f,0xaa,0x00,0x11,0xff,0xe1,0x8f,0xab,0x00,0xd1,0x10,0x10,0x08,0x11,0xff, + 0xe1,0x8f,0xac,0x00,0x11,0xff,0xe1,0x8f,0xad,0x00,0x10,0x08,0x11,0xff,0xe1,0x8f, + 0xae,0x00,0x11,0xff,0xe1,0x8f,0xaf,0x00,0xd1,0x0c,0xe0,0xeb,0x63,0xcf,0x86,0xcf, + 0x06,0x02,0xff,0xff,0xd0,0x08,0xcf,0x86,0xcf,0x06,0x01,0x00,0xcf,0x86,0xd5,0x06, + 0xcf,0x06,0x01,0x00,0xd4,0xae,0xd3,0x09,0xe2,0x54,0x64,0xcf,0x06,0x01,0x00,0xd2, + 0x27,0xe1,0x1f,0x70,0xe0,0x26,0x6e,0xcf,0x86,0xe5,0x3f,0x6d,0xe4,0xce,0x6c,0xe3, + 0x99,0x6c,0xe2,0x78,0x6c,0xe1,0x67,0x6c,0x10,0x08,0x01,0xff,0xe5,0x88,0x87,0x00, + 0x01,0xff,0xe5,0xba,0xa6,0x00,0xe1,0x74,0x74,0xe0,0xe8,0x73,0xcf,0x86,0xe5,0x22, + 0x73,0xd4,0x3b,0x93,0x37,0xd2,0x1d,0xd1,0x0e,0x10,0x07,0x01,0xff,0x66,0x66,0x00, + 0x01,0xff,0x66,0x69,0x00,0x10,0x07,0x01,0xff,0x66,0x6c,0x00,0x01,0xff,0x66,0x66, + 0x69,0x00,0xd1,0x0f,0x10,0x08,0x01,0xff,0x66,0x66,0x6c,0x00,0x01,0xff,0x73,0x74, + 0x00,0x10,0x07,0x01,0xff,0x73,0x74,0x00,0x00,0x00,0x00,0x00,0xe3,0xc8,0x72,0xd2, + 0x11,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x01,0xff,0xd5,0xb4,0xd5,0xb6,0x00, + 0xd1,0x12,0x10,0x09,0x01,0xff,0xd5,0xb4,0xd5,0xa5,0x00,0x01,0xff,0xd5,0xb4,0xd5, + 0xab,0x00,0x10,0x09,0x01,0xff,0xd5,0xbe,0xd5,0xb6,0x00,0x01,0xff,0xd5,0xb4,0xd5, + 0xad,0x00,0xd3,0x09,0xe2,0x40,0x74,0xcf,0x06,0x01,0x00,0xd2,0x13,0xe1,0x30,0x75, + 0xe0,0xc1,0x74,0xcf,0x86,0xe5,0x9e,0x74,0x64,0x8d,0x74,0x06,0xff,0x00,0xe1,0x96, + 0x75,0xe0,0x63,0x75,0xcf,0x86,0xd5,0x18,0x94,0x14,0x93,0x10,0x92,0x0c,0x91,0x08, + 0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd4,0x7c, + 0xd3,0x3c,0xd2,0x1c,0xd1,0x0c,0x10,0x04,0x01,0x00,0x01,0xff,0xef,0xbd,0x81,0x00, + 0x10,0x08,0x01,0xff,0xef,0xbd,0x82,0x00,0x01,0xff,0xef,0xbd,0x83,0x00,0xd1,0x10, + 0x10,0x08,0x01,0xff,0xef,0xbd,0x84,0x00,0x01,0xff,0xef,0xbd,0x85,0x00,0x10,0x08, + 0x01,0xff,0xef,0xbd,0x86,0x00,0x01,0xff,0xef,0xbd,0x87,0x00,0xd2,0x20,0xd1,0x10, + 0x10,0x08,0x01,0xff,0xef,0xbd,0x88,0x00,0x01,0xff,0xef,0xbd,0x89,0x00,0x10,0x08, + 0x01,0xff,0xef,0xbd,0x8a,0x00,0x01,0xff,0xef,0xbd,0x8b,0x00,0xd1,0x10,0x10,0x08, + 0x01,0xff,0xef,0xbd,0x8c,0x00,0x01,0xff,0xef,0xbd,0x8d,0x00,0x10,0x08,0x01,0xff, + 0xef,0xbd,0x8e,0x00,0x01,0xff,0xef,0xbd,0x8f,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10, + 0x10,0x08,0x01,0xff,0xef,0xbd,0x90,0x00,0x01,0xff,0xef,0xbd,0x91,0x00,0x10,0x08, + 0x01,0xff,0xef,0xbd,0x92,0x00,0x01,0xff,0xef,0xbd,0x93,0x00,0xd1,0x10,0x10,0x08, + 0x01,0xff,0xef,0xbd,0x94,0x00,0x01,0xff,0xef,0xbd,0x95,0x00,0x10,0x08,0x01,0xff, + 0xef,0xbd,0x96,0x00,0x01,0xff,0xef,0xbd,0x97,0x00,0x92,0x1c,0xd1,0x10,0x10,0x08, + 0x01,0xff,0xef,0xbd,0x98,0x00,0x01,0xff,0xef,0xbd,0x99,0x00,0x10,0x08,0x01,0xff, + 0xef,0xbd,0x9a,0x00,0x01,0x00,0x01,0x00,0x83,0xe2,0x87,0xb3,0xe1,0x60,0xb0,0xe0, + 0xdd,0xae,0xcf,0x86,0xe5,0x81,0x9b,0xc4,0xe3,0xc1,0x07,0xe2,0x62,0x06,0xe1,0x11, + 0x86,0xe0,0x09,0x05,0xcf,0x86,0xe5,0xfb,0x02,0xd4,0x1c,0xe3,0x7f,0x76,0xe2,0xd6, + 0x75,0xe1,0xb1,0x75,0xe0,0x8a,0x75,0xcf,0x86,0xe5,0x57,0x75,0x94,0x07,0x63,0x42, + 0x75,0x07,0x00,0x07,0x00,0xe3,0x2b,0x78,0xe2,0xf0,0x77,0xe1,0x77,0x01,0xe0,0x88, + 0x77,0xcf,0x86,0xe5,0x21,0x01,0xd4,0x90,0xd3,0x48,0xd2,0x24,0xd1,0x12,0x10,0x09, + 0x05,0xff,0xf0,0x90,0x90,0xa8,0x00,0x05,0xff,0xf0,0x90,0x90,0xa9,0x00,0x10,0x09, + 0x05,0xff,0xf0,0x90,0x90,0xaa,0x00,0x05,0xff,0xf0,0x90,0x90,0xab,0x00,0xd1,0x12, + 0x10,0x09,0x05,0xff,0xf0,0x90,0x90,0xac,0x00,0x05,0xff,0xf0,0x90,0x90,0xad,0x00, + 0x10,0x09,0x05,0xff,0xf0,0x90,0x90,0xae,0x00,0x05,0xff,0xf0,0x90,0x90,0xaf,0x00, + 0xd2,0x24,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0x90,0x90,0xb0,0x00,0x05,0xff,0xf0, + 0x90,0x90,0xb1,0x00,0x10,0x09,0x05,0xff,0xf0,0x90,0x90,0xb2,0x00,0x05,0xff,0xf0, + 0x90,0x90,0xb3,0x00,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0x90,0x90,0xb4,0x00,0x05, + 0xff,0xf0,0x90,0x90,0xb5,0x00,0x10,0x09,0x05,0xff,0xf0,0x90,0x90,0xb6,0x00,0x05, + 0xff,0xf0,0x90,0x90,0xb7,0x00,0xd3,0x48,0xd2,0x24,0xd1,0x12,0x10,0x09,0x05,0xff, + 0xf0,0x90,0x90,0xb8,0x00,0x05,0xff,0xf0,0x90,0x90,0xb9,0x00,0x10,0x09,0x05,0xff, + 0xf0,0x90,0x90,0xba,0x00,0x05,0xff,0xf0,0x90,0x90,0xbb,0x00,0xd1,0x12,0x10,0x09, + 0x05,0xff,0xf0,0x90,0x90,0xbc,0x00,0x05,0xff,0xf0,0x90,0x90,0xbd,0x00,0x10,0x09, + 0x05,0xff,0xf0,0x90,0x90,0xbe,0x00,0x05,0xff,0xf0,0x90,0x90,0xbf,0x00,0xd2,0x24, + 0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0x90,0x91,0x80,0x00,0x05,0xff,0xf0,0x90,0x91, + 0x81,0x00,0x10,0x09,0x05,0xff,0xf0,0x90,0x91,0x82,0x00,0x05,0xff,0xf0,0x90,0x91, + 0x83,0x00,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0x90,0x91,0x84,0x00,0x05,0xff,0xf0, + 0x90,0x91,0x85,0x00,0x10,0x09,0x05,0xff,0xf0,0x90,0x91,0x86,0x00,0x05,0xff,0xf0, + 0x90,0x91,0x87,0x00,0x94,0x4c,0x93,0x48,0xd2,0x24,0xd1,0x12,0x10,0x09,0x05,0xff, + 0xf0,0x90,0x91,0x88,0x00,0x05,0xff,0xf0,0x90,0x91,0x89,0x00,0x10,0x09,0x05,0xff, + 0xf0,0x90,0x91,0x8a,0x00,0x05,0xff,0xf0,0x90,0x91,0x8b,0x00,0xd1,0x12,0x10,0x09, + 0x05,0xff,0xf0,0x90,0x91,0x8c,0x00,0x05,0xff,0xf0,0x90,0x91,0x8d,0x00,0x10,0x09, + 0x07,0xff,0xf0,0x90,0x91,0x8e,0x00,0x07,0xff,0xf0,0x90,0x91,0x8f,0x00,0x05,0x00, + 0x05,0x00,0xd0,0xa0,0xcf,0x86,0xd5,0x07,0x64,0x30,0x76,0x07,0x00,0xd4,0x07,0x63, + 0x3d,0x76,0x07,0x00,0xd3,0x48,0xd2,0x24,0xd1,0x12,0x10,0x09,0x12,0xff,0xf0,0x90, + 0x93,0x98,0x00,0x12,0xff,0xf0,0x90,0x93,0x99,0x00,0x10,0x09,0x12,0xff,0xf0,0x90, + 0x93,0x9a,0x00,0x12,0xff,0xf0,0x90,0x93,0x9b,0x00,0xd1,0x12,0x10,0x09,0x12,0xff, + 0xf0,0x90,0x93,0x9c,0x00,0x12,0xff,0xf0,0x90,0x93,0x9d,0x00,0x10,0x09,0x12,0xff, + 0xf0,0x90,0x93,0x9e,0x00,0x12,0xff,0xf0,0x90,0x93,0x9f,0x00,0xd2,0x24,0xd1,0x12, + 0x10,0x09,0x12,0xff,0xf0,0x90,0x93,0xa0,0x00,0x12,0xff,0xf0,0x90,0x93,0xa1,0x00, + 0x10,0x09,0x12,0xff,0xf0,0x90,0x93,0xa2,0x00,0x12,0xff,0xf0,0x90,0x93,0xa3,0x00, + 0xd1,0x12,0x10,0x09,0x12,0xff,0xf0,0x90,0x93,0xa4,0x00,0x12,0xff,0xf0,0x90,0x93, + 0xa5,0x00,0x10,0x09,0x12,0xff,0xf0,0x90,0x93,0xa6,0x00,0x12,0xff,0xf0,0x90,0x93, + 0xa7,0x00,0xcf,0x86,0xe5,0xc6,0x75,0xd4,0x90,0xd3,0x48,0xd2,0x24,0xd1,0x12,0x10, + 0x09,0x12,0xff,0xf0,0x90,0x93,0xa8,0x00,0x12,0xff,0xf0,0x90,0x93,0xa9,0x00,0x10, + 0x09,0x12,0xff,0xf0,0x90,0x93,0xaa,0x00,0x12,0xff,0xf0,0x90,0x93,0xab,0x00,0xd1, + 0x12,0x10,0x09,0x12,0xff,0xf0,0x90,0x93,0xac,0x00,0x12,0xff,0xf0,0x90,0x93,0xad, + 0x00,0x10,0x09,0x12,0xff,0xf0,0x90,0x93,0xae,0x00,0x12,0xff,0xf0,0x90,0x93,0xaf, + 0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x12,0xff,0xf0,0x90,0x93,0xb0,0x00,0x12,0xff, + 0xf0,0x90,0x93,0xb1,0x00,0x10,0x09,0x12,0xff,0xf0,0x90,0x93,0xb2,0x00,0x12,0xff, + 0xf0,0x90,0x93,0xb3,0x00,0xd1,0x12,0x10,0x09,0x12,0xff,0xf0,0x90,0x93,0xb4,0x00, + 0x12,0xff,0xf0,0x90,0x93,0xb5,0x00,0x10,0x09,0x12,0xff,0xf0,0x90,0x93,0xb6,0x00, + 0x12,0xff,0xf0,0x90,0x93,0xb7,0x00,0x93,0x28,0x92,0x24,0xd1,0x12,0x10,0x09,0x12, + 0xff,0xf0,0x90,0x93,0xb8,0x00,0x12,0xff,0xf0,0x90,0x93,0xb9,0x00,0x10,0x09,0x12, + 0xff,0xf0,0x90,0x93,0xba,0x00,0x12,0xff,0xf0,0x90,0x93,0xbb,0x00,0x00,0x00,0x12, + 0x00,0xd4,0x1f,0xe3,0xdf,0x76,0xe2,0x6a,0x76,0xe1,0x09,0x76,0xe0,0xea,0x75,0xcf, + 0x86,0xe5,0xb7,0x75,0x94,0x0a,0xe3,0xa2,0x75,0x62,0x99,0x75,0x07,0x00,0x07,0x00, + 0xe3,0xde,0x78,0xe2,0xaf,0x78,0xd1,0x09,0xe0,0x4c,0x78,0xcf,0x06,0x0b,0x00,0xe0, + 0x7f,0x78,0xcf,0x86,0xe5,0x21,0x01,0xd4,0x90,0xd3,0x48,0xd2,0x24,0xd1,0x12,0x10, + 0x09,0x11,0xff,0xf0,0x90,0xb3,0x80,0x00,0x11,0xff,0xf0,0x90,0xb3,0x81,0x00,0x10, + 0x09,0x11,0xff,0xf0,0x90,0xb3,0x82,0x00,0x11,0xff,0xf0,0x90,0xb3,0x83,0x00,0xd1, + 0x12,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0x84,0x00,0x11,0xff,0xf0,0x90,0xb3,0x85, + 0x00,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0x86,0x00,0x11,0xff,0xf0,0x90,0xb3,0x87, + 0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0x88,0x00,0x11,0xff, + 0xf0,0x90,0xb3,0x89,0x00,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0x8a,0x00,0x11,0xff, + 0xf0,0x90,0xb3,0x8b,0x00,0xd1,0x12,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0x8c,0x00, + 0x11,0xff,0xf0,0x90,0xb3,0x8d,0x00,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0x8e,0x00, + 0x11,0xff,0xf0,0x90,0xb3,0x8f,0x00,0xd3,0x48,0xd2,0x24,0xd1,0x12,0x10,0x09,0x11, + 0xff,0xf0,0x90,0xb3,0x90,0x00,0x11,0xff,0xf0,0x90,0xb3,0x91,0x00,0x10,0x09,0x11, + 0xff,0xf0,0x90,0xb3,0x92,0x00,0x11,0xff,0xf0,0x90,0xb3,0x93,0x00,0xd1,0x12,0x10, + 0x09,0x11,0xff,0xf0,0x90,0xb3,0x94,0x00,0x11,0xff,0xf0,0x90,0xb3,0x95,0x00,0x10, + 0x09,0x11,0xff,0xf0,0x90,0xb3,0x96,0x00,0x11,0xff,0xf0,0x90,0xb3,0x97,0x00,0xd2, + 0x24,0xd1,0x12,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0x98,0x00,0x11,0xff,0xf0,0x90, + 0xb3,0x99,0x00,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0x9a,0x00,0x11,0xff,0xf0,0x90, + 0xb3,0x9b,0x00,0xd1,0x12,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0x9c,0x00,0x11,0xff, + 0xf0,0x90,0xb3,0x9d,0x00,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0x9e,0x00,0x11,0xff, + 0xf0,0x90,0xb3,0x9f,0x00,0xd4,0x90,0xd3,0x48,0xd2,0x24,0xd1,0x12,0x10,0x09,0x11, + 0xff,0xf0,0x90,0xb3,0xa0,0x00,0x11,0xff,0xf0,0x90,0xb3,0xa1,0x00,0x10,0x09,0x11, + 0xff,0xf0,0x90,0xb3,0xa2,0x00,0x11,0xff,0xf0,0x90,0xb3,0xa3,0x00,0xd1,0x12,0x10, + 0x09,0x11,0xff,0xf0,0x90,0xb3,0xa4,0x00,0x11,0xff,0xf0,0x90,0xb3,0xa5,0x00,0x10, + 0x09,0x11,0xff,0xf0,0x90,0xb3,0xa6,0x00,0x11,0xff,0xf0,0x90,0xb3,0xa7,0x00,0xd2, + 0x24,0xd1,0x12,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0xa8,0x00,0x11,0xff,0xf0,0x90, + 0xb3,0xa9,0x00,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0xaa,0x00,0x11,0xff,0xf0,0x90, + 0xb3,0xab,0x00,0xd1,0x12,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0xac,0x00,0x11,0xff, + 0xf0,0x90,0xb3,0xad,0x00,0x10,0x09,0x11,0xff,0xf0,0x90,0xb3,0xae,0x00,0x11,0xff, + 0xf0,0x90,0xb3,0xaf,0x00,0x93,0x23,0x92,0x1f,0xd1,0x12,0x10,0x09,0x11,0xff,0xf0, + 0x90,0xb3,0xb0,0x00,0x11,0xff,0xf0,0x90,0xb3,0xb1,0x00,0x10,0x09,0x11,0xff,0xf0, + 0x90,0xb3,0xb2,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0xd5,0x15,0xe4,0x91, + 0x7b,0xe3,0x9b,0x79,0xe2,0x94,0x78,0xe1,0xe4,0x77,0xe0,0x9d,0x77,0xcf,0x06,0x0c, + 0x00,0xe4,0xeb,0x7e,0xe3,0x44,0x7e,0xe2,0xed,0x7d,0xd1,0x0c,0xe0,0xb2,0x7d,0xcf, + 0x86,0x65,0x93,0x7d,0x14,0x00,0xe0,0xb6,0x7d,0xcf,0x86,0x55,0x04,0x00,0x00,0xd4, + 0x90,0xd3,0x48,0xd2,0x24,0xd1,0x12,0x10,0x09,0x10,0xff,0xf0,0x91,0xa3,0x80,0x00, + 0x10,0xff,0xf0,0x91,0xa3,0x81,0x00,0x10,0x09,0x10,0xff,0xf0,0x91,0xa3,0x82,0x00, + 0x10,0xff,0xf0,0x91,0xa3,0x83,0x00,0xd1,0x12,0x10,0x09,0x10,0xff,0xf0,0x91,0xa3, + 0x84,0x00,0x10,0xff,0xf0,0x91,0xa3,0x85,0x00,0x10,0x09,0x10,0xff,0xf0,0x91,0xa3, + 0x86,0x00,0x10,0xff,0xf0,0x91,0xa3,0x87,0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x10, + 0xff,0xf0,0x91,0xa3,0x88,0x00,0x10,0xff,0xf0,0x91,0xa3,0x89,0x00,0x10,0x09,0x10, + 0xff,0xf0,0x91,0xa3,0x8a,0x00,0x10,0xff,0xf0,0x91,0xa3,0x8b,0x00,0xd1,0x12,0x10, + 0x09,0x10,0xff,0xf0,0x91,0xa3,0x8c,0x00,0x10,0xff,0xf0,0x91,0xa3,0x8d,0x00,0x10, + 0x09,0x10,0xff,0xf0,0x91,0xa3,0x8e,0x00,0x10,0xff,0xf0,0x91,0xa3,0x8f,0x00,0xd3, + 0x48,0xd2,0x24,0xd1,0x12,0x10,0x09,0x10,0xff,0xf0,0x91,0xa3,0x90,0x00,0x10,0xff, + 0xf0,0x91,0xa3,0x91,0x00,0x10,0x09,0x10,0xff,0xf0,0x91,0xa3,0x92,0x00,0x10,0xff, + 0xf0,0x91,0xa3,0x93,0x00,0xd1,0x12,0x10,0x09,0x10,0xff,0xf0,0x91,0xa3,0x94,0x00, + 0x10,0xff,0xf0,0x91,0xa3,0x95,0x00,0x10,0x09,0x10,0xff,0xf0,0x91,0xa3,0x96,0x00, + 0x10,0xff,0xf0,0x91,0xa3,0x97,0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x10,0xff,0xf0, + 0x91,0xa3,0x98,0x00,0x10,0xff,0xf0,0x91,0xa3,0x99,0x00,0x10,0x09,0x10,0xff,0xf0, + 0x91,0xa3,0x9a,0x00,0x10,0xff,0xf0,0x91,0xa3,0x9b,0x00,0xd1,0x12,0x10,0x09,0x10, + 0xff,0xf0,0x91,0xa3,0x9c,0x00,0x10,0xff,0xf0,0x91,0xa3,0x9d,0x00,0x10,0x09,0x10, + 0xff,0xf0,0x91,0xa3,0x9e,0x00,0x10,0xff,0xf0,0x91,0xa3,0x9f,0x00,0xd1,0x11,0xe0, + 0x12,0x81,0xcf,0x86,0xe5,0x09,0x81,0xe4,0xd2,0x80,0xcf,0x06,0x00,0x00,0xe0,0xdb, + 0x82,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x09,0xe3,0x10,0x81,0xcf,0x06, + 0x0c,0x00,0xd3,0x06,0xcf,0x06,0x00,0x00,0xe2,0x3b,0x82,0xe1,0x16,0x82,0xd0,0x06, + 0xcf,0x06,0x00,0x00,0xcf,0x86,0xa5,0x21,0x01,0xd4,0x90,0xd3,0x48,0xd2,0x24,0xd1, + 0x12,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xa0,0x00,0x14,0xff,0xf0,0x96,0xb9,0xa1, + 0x00,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xa2,0x00,0x14,0xff,0xf0,0x96,0xb9,0xa3, + 0x00,0xd1,0x12,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xa4,0x00,0x14,0xff,0xf0,0x96, + 0xb9,0xa5,0x00,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xa6,0x00,0x14,0xff,0xf0,0x96, + 0xb9,0xa7,0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xa8,0x00, + 0x14,0xff,0xf0,0x96,0xb9,0xa9,0x00,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xaa,0x00, + 0x14,0xff,0xf0,0x96,0xb9,0xab,0x00,0xd1,0x12,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9, + 0xac,0x00,0x14,0xff,0xf0,0x96,0xb9,0xad,0x00,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9, + 0xae,0x00,0x14,0xff,0xf0,0x96,0xb9,0xaf,0x00,0xd3,0x48,0xd2,0x24,0xd1,0x12,0x10, + 0x09,0x14,0xff,0xf0,0x96,0xb9,0xb0,0x00,0x14,0xff,0xf0,0x96,0xb9,0xb1,0x00,0x10, + 0x09,0x14,0xff,0xf0,0x96,0xb9,0xb2,0x00,0x14,0xff,0xf0,0x96,0xb9,0xb3,0x00,0xd1, + 0x12,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xb4,0x00,0x14,0xff,0xf0,0x96,0xb9,0xb5, + 0x00,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xb6,0x00,0x14,0xff,0xf0,0x96,0xb9,0xb7, + 0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xb8,0x00,0x14,0xff, + 0xf0,0x96,0xb9,0xb9,0x00,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xba,0x00,0x14,0xff, + 0xf0,0x96,0xb9,0xbb,0x00,0xd1,0x12,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xbc,0x00, + 0x14,0xff,0xf0,0x96,0xb9,0xbd,0x00,0x10,0x09,0x14,0xff,0xf0,0x96,0xb9,0xbe,0x00, + 0x14,0xff,0xf0,0x96,0xb9,0xbf,0x00,0x14,0x00,0xd2,0x14,0xe1,0x25,0x82,0xe0,0x1c, + 0x82,0xcf,0x86,0xe5,0xdd,0x81,0xe4,0x9a,0x81,0xcf,0x06,0x12,0x00,0xd1,0x0b,0xe0, + 0x51,0x83,0xcf,0x86,0xcf,0x06,0x00,0x00,0xe0,0x95,0x8b,0xcf,0x86,0xd5,0x22,0xe4, + 0xd0,0x88,0xe3,0x93,0x88,0xe2,0x38,0x88,0xe1,0x31,0x88,0xe0,0x2a,0x88,0xcf,0x86, + 0xe5,0xfb,0x87,0xe4,0xe2,0x87,0x93,0x07,0x62,0xd1,0x87,0x12,0xe6,0x12,0xe6,0xe4, + 0x36,0x89,0xe3,0x2f,0x89,0xd2,0x09,0xe1,0xb8,0x88,0xcf,0x06,0x10,0x00,0xe1,0x1f, + 0x89,0xe0,0xec,0x88,0xcf,0x86,0xe5,0x21,0x01,0xd4,0x90,0xd3,0x48,0xd2,0x24,0xd1, + 0x12,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4,0xa2,0x00,0x12,0xff,0xf0,0x9e,0xa4,0xa3, + 0x00,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4,0xa4,0x00,0x12,0xff,0xf0,0x9e,0xa4,0xa5, + 0x00,0xd1,0x12,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4,0xa6,0x00,0x12,0xff,0xf0,0x9e, + 0xa4,0xa7,0x00,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4,0xa8,0x00,0x12,0xff,0xf0,0x9e, + 0xa4,0xa9,0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4,0xaa,0x00, + 0x12,0xff,0xf0,0x9e,0xa4,0xab,0x00,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4,0xac,0x00, + 0x12,0xff,0xf0,0x9e,0xa4,0xad,0x00,0xd1,0x12,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4, + 0xae,0x00,0x12,0xff,0xf0,0x9e,0xa4,0xaf,0x00,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4, + 0xb0,0x00,0x12,0xff,0xf0,0x9e,0xa4,0xb1,0x00,0xd3,0x48,0xd2,0x24,0xd1,0x12,0x10, + 0x09,0x12,0xff,0xf0,0x9e,0xa4,0xb2,0x00,0x12,0xff,0xf0,0x9e,0xa4,0xb3,0x00,0x10, + 0x09,0x12,0xff,0xf0,0x9e,0xa4,0xb4,0x00,0x12,0xff,0xf0,0x9e,0xa4,0xb5,0x00,0xd1, + 0x12,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4,0xb6,0x00,0x12,0xff,0xf0,0x9e,0xa4,0xb7, + 0x00,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4,0xb8,0x00,0x12,0xff,0xf0,0x9e,0xa4,0xb9, + 0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4,0xba,0x00,0x12,0xff, + 0xf0,0x9e,0xa4,0xbb,0x00,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4,0xbc,0x00,0x12,0xff, + 0xf0,0x9e,0xa4,0xbd,0x00,0xd1,0x12,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa4,0xbe,0x00, + 0x12,0xff,0xf0,0x9e,0xa4,0xbf,0x00,0x10,0x09,0x12,0xff,0xf0,0x9e,0xa5,0x80,0x00, + 0x12,0xff,0xf0,0x9e,0xa5,0x81,0x00,0x94,0x1e,0x93,0x1a,0x92,0x16,0x91,0x12,0x10, + 0x09,0x12,0xff,0xf0,0x9e,0xa5,0x82,0x00,0x12,0xff,0xf0,0x9e,0xa5,0x83,0x00,0x12, + 0x00,0x12,0x00,0x12,0x00,0x12,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, + 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, + 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, + /* nfdi_c0100 */ + 0x57,0x04,0x01,0x00,0xc6,0xe5,0xac,0x13,0xe4,0x41,0x0c,0xe3,0x7a,0x07,0xe2,0xf3, + 0x01,0xc1,0xd0,0x1f,0xcf,0x86,0x55,0x04,0x01,0x00,0x94,0x15,0x53,0x04,0x01,0x00, + 0x52,0x04,0x01,0x00,0x91,0x09,0x10,0x04,0x01,0x00,0x01,0xff,0x00,0x01,0x00,0x01, + 0x00,0xcf,0x86,0xd5,0xe4,0xd4,0x7c,0xd3,0x3c,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01, + 0xff,0x41,0xcc,0x80,0x00,0x01,0xff,0x41,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x41, + 0xcc,0x82,0x00,0x01,0xff,0x41,0xcc,0x83,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x41, + 0xcc,0x88,0x00,0x01,0xff,0x41,0xcc,0x8a,0x00,0x10,0x04,0x01,0x00,0x01,0xff,0x43, + 0xcc,0xa7,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x45,0xcc,0x80,0x00,0x01, + 0xff,0x45,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x45,0xcc,0x82,0x00,0x01,0xff,0x45, + 0xcc,0x88,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x49,0xcc,0x80,0x00,0x01,0xff,0x49, + 0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x49,0xcc,0x82,0x00,0x01,0xff,0x49,0xcc,0x88, + 0x00,0xd3,0x38,0xd2,0x1c,0xd1,0x0c,0x10,0x04,0x01,0x00,0x01,0xff,0x4e,0xcc,0x83, + 0x00,0x10,0x08,0x01,0xff,0x4f,0xcc,0x80,0x00,0x01,0xff,0x4f,0xcc,0x81,0x00,0xd1, + 0x10,0x10,0x08,0x01,0xff,0x4f,0xcc,0x82,0x00,0x01,0xff,0x4f,0xcc,0x83,0x00,0x10, + 0x08,0x01,0xff,0x4f,0xcc,0x88,0x00,0x01,0x00,0xd2,0x1c,0xd1,0x0c,0x10,0x04,0x01, + 0x00,0x01,0xff,0x55,0xcc,0x80,0x00,0x10,0x08,0x01,0xff,0x55,0xcc,0x81,0x00,0x01, + 0xff,0x55,0xcc,0x82,0x00,0x91,0x10,0x10,0x08,0x01,0xff,0x55,0xcc,0x88,0x00,0x01, + 0xff,0x59,0xcc,0x81,0x00,0x01,0x00,0xd4,0x7c,0xd3,0x3c,0xd2,0x20,0xd1,0x10,0x10, + 0x08,0x01,0xff,0x61,0xcc,0x80,0x00,0x01,0xff,0x61,0xcc,0x81,0x00,0x10,0x08,0x01, + 0xff,0x61,0xcc,0x82,0x00,0x01,0xff,0x61,0xcc,0x83,0x00,0xd1,0x10,0x10,0x08,0x01, + 0xff,0x61,0xcc,0x88,0x00,0x01,0xff,0x61,0xcc,0x8a,0x00,0x10,0x04,0x01,0x00,0x01, + 0xff,0x63,0xcc,0xa7,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x65,0xcc,0x80, + 0x00,0x01,0xff,0x65,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x65,0xcc,0x82,0x00,0x01, + 0xff,0x65,0xcc,0x88,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x69,0xcc,0x80,0x00,0x01, + 0xff,0x69,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x69,0xcc,0x82,0x00,0x01,0xff,0x69, + 0xcc,0x88,0x00,0xd3,0x38,0xd2,0x1c,0xd1,0x0c,0x10,0x04,0x01,0x00,0x01,0xff,0x6e, + 0xcc,0x83,0x00,0x10,0x08,0x01,0xff,0x6f,0xcc,0x80,0x00,0x01,0xff,0x6f,0xcc,0x81, + 0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x6f,0xcc,0x82,0x00,0x01,0xff,0x6f,0xcc,0x83, + 0x00,0x10,0x08,0x01,0xff,0x6f,0xcc,0x88,0x00,0x01,0x00,0xd2,0x1c,0xd1,0x0c,0x10, + 0x04,0x01,0x00,0x01,0xff,0x75,0xcc,0x80,0x00,0x10,0x08,0x01,0xff,0x75,0xcc,0x81, + 0x00,0x01,0xff,0x75,0xcc,0x82,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x75,0xcc,0x88, + 0x00,0x01,0xff,0x79,0xcc,0x81,0x00,0x10,0x04,0x01,0x00,0x01,0xff,0x79,0xcc,0x88, + 0x00,0xe1,0x9a,0x03,0xe0,0xd3,0x01,0xcf,0x86,0xd5,0xf4,0xd4,0x80,0xd3,0x40,0xd2, + 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x41,0xcc,0x84,0x00,0x01,0xff,0x61,0xcc,0x84, + 0x00,0x10,0x08,0x01,0xff,0x41,0xcc,0x86,0x00,0x01,0xff,0x61,0xcc,0x86,0x00,0xd1, + 0x10,0x10,0x08,0x01,0xff,0x41,0xcc,0xa8,0x00,0x01,0xff,0x61,0xcc,0xa8,0x00,0x10, + 0x08,0x01,0xff,0x43,0xcc,0x81,0x00,0x01,0xff,0x63,0xcc,0x81,0x00,0xd2,0x20,0xd1, + 0x10,0x10,0x08,0x01,0xff,0x43,0xcc,0x82,0x00,0x01,0xff,0x63,0xcc,0x82,0x00,0x10, + 0x08,0x01,0xff,0x43,0xcc,0x87,0x00,0x01,0xff,0x63,0xcc,0x87,0x00,0xd1,0x10,0x10, + 0x08,0x01,0xff,0x43,0xcc,0x8c,0x00,0x01,0xff,0x63,0xcc,0x8c,0x00,0x10,0x08,0x01, + 0xff,0x44,0xcc,0x8c,0x00,0x01,0xff,0x64,0xcc,0x8c,0x00,0xd3,0x34,0xd2,0x14,0x51, + 0x04,0x01,0x00,0x10,0x08,0x01,0xff,0x45,0xcc,0x84,0x00,0x01,0xff,0x65,0xcc,0x84, + 0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x45,0xcc,0x86,0x00,0x01,0xff,0x65,0xcc,0x86, + 0x00,0x10,0x08,0x01,0xff,0x45,0xcc,0x87,0x00,0x01,0xff,0x65,0xcc,0x87,0x00,0xd2, + 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x45,0xcc,0xa8,0x00,0x01,0xff,0x65,0xcc,0xa8, + 0x00,0x10,0x08,0x01,0xff,0x45,0xcc,0x8c,0x00,0x01,0xff,0x65,0xcc,0x8c,0x00,0xd1, + 0x10,0x10,0x08,0x01,0xff,0x47,0xcc,0x82,0x00,0x01,0xff,0x67,0xcc,0x82,0x00,0x10, + 0x08,0x01,0xff,0x47,0xcc,0x86,0x00,0x01,0xff,0x67,0xcc,0x86,0x00,0xd4,0x74,0xd3, + 0x34,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x47,0xcc,0x87,0x00,0x01,0xff,0x67, + 0xcc,0x87,0x00,0x10,0x08,0x01,0xff,0x47,0xcc,0xa7,0x00,0x01,0xff,0x67,0xcc,0xa7, + 0x00,0x91,0x10,0x10,0x08,0x01,0xff,0x48,0xcc,0x82,0x00,0x01,0xff,0x68,0xcc,0x82, + 0x00,0x01,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x49,0xcc,0x83,0x00,0x01, + 0xff,0x69,0xcc,0x83,0x00,0x10,0x08,0x01,0xff,0x49,0xcc,0x84,0x00,0x01,0xff,0x69, + 0xcc,0x84,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x49,0xcc,0x86,0x00,0x01,0xff,0x69, + 0xcc,0x86,0x00,0x10,0x08,0x01,0xff,0x49,0xcc,0xa8,0x00,0x01,0xff,0x69,0xcc,0xa8, + 0x00,0xd3,0x30,0xd2,0x10,0x91,0x0c,0x10,0x08,0x01,0xff,0x49,0xcc,0x87,0x00,0x01, + 0x00,0x01,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x4a,0xcc,0x82,0x00,0x01,0xff,0x6a, + 0xcc,0x82,0x00,0x10,0x08,0x01,0xff,0x4b,0xcc,0xa7,0x00,0x01,0xff,0x6b,0xcc,0xa7, + 0x00,0xd2,0x1c,0xd1,0x0c,0x10,0x04,0x01,0x00,0x01,0xff,0x4c,0xcc,0x81,0x00,0x10, + 0x08,0x01,0xff,0x6c,0xcc,0x81,0x00,0x01,0xff,0x4c,0xcc,0xa7,0x00,0xd1,0x10,0x10, + 0x08,0x01,0xff,0x6c,0xcc,0xa7,0x00,0x01,0xff,0x4c,0xcc,0x8c,0x00,0x10,0x08,0x01, + 0xff,0x6c,0xcc,0x8c,0x00,0x01,0x00,0xcf,0x86,0xd5,0xd4,0xd4,0x60,0xd3,0x30,0xd2, + 0x10,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x01,0xff,0x4e,0xcc,0x81,0x00,0xd1, + 0x10,0x10,0x08,0x01,0xff,0x6e,0xcc,0x81,0x00,0x01,0xff,0x4e,0xcc,0xa7,0x00,0x10, + 0x08,0x01,0xff,0x6e,0xcc,0xa7,0x00,0x01,0xff,0x4e,0xcc,0x8c,0x00,0xd2,0x10,0x91, + 0x0c,0x10,0x08,0x01,0xff,0x6e,0xcc,0x8c,0x00,0x01,0x00,0x01,0x00,0xd1,0x10,0x10, + 0x08,0x01,0xff,0x4f,0xcc,0x84,0x00,0x01,0xff,0x6f,0xcc,0x84,0x00,0x10,0x08,0x01, + 0xff,0x4f,0xcc,0x86,0x00,0x01,0xff,0x6f,0xcc,0x86,0x00,0xd3,0x34,0xd2,0x14,0x91, + 0x10,0x10,0x08,0x01,0xff,0x4f,0xcc,0x8b,0x00,0x01,0xff,0x6f,0xcc,0x8b,0x00,0x01, + 0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x52,0xcc,0x81,0x00,0x01,0xff,0x72,0xcc,0x81, + 0x00,0x10,0x08,0x01,0xff,0x52,0xcc,0xa7,0x00,0x01,0xff,0x72,0xcc,0xa7,0x00,0xd2, + 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x52,0xcc,0x8c,0x00,0x01,0xff,0x72,0xcc,0x8c, + 0x00,0x10,0x08,0x01,0xff,0x53,0xcc,0x81,0x00,0x01,0xff,0x73,0xcc,0x81,0x00,0xd1, + 0x10,0x10,0x08,0x01,0xff,0x53,0xcc,0x82,0x00,0x01,0xff,0x73,0xcc,0x82,0x00,0x10, + 0x08,0x01,0xff,0x53,0xcc,0xa7,0x00,0x01,0xff,0x73,0xcc,0xa7,0x00,0xd4,0x74,0xd3, + 0x34,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x53,0xcc,0x8c,0x00,0x01,0xff,0x73, + 0xcc,0x8c,0x00,0x10,0x08,0x01,0xff,0x54,0xcc,0xa7,0x00,0x01,0xff,0x74,0xcc,0xa7, + 0x00,0x91,0x10,0x10,0x08,0x01,0xff,0x54,0xcc,0x8c,0x00,0x01,0xff,0x74,0xcc,0x8c, + 0x00,0x01,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x55,0xcc,0x83,0x00,0x01, + 0xff,0x75,0xcc,0x83,0x00,0x10,0x08,0x01,0xff,0x55,0xcc,0x84,0x00,0x01,0xff,0x75, + 0xcc,0x84,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x55,0xcc,0x86,0x00,0x01,0xff,0x75, + 0xcc,0x86,0x00,0x10,0x08,0x01,0xff,0x55,0xcc,0x8a,0x00,0x01,0xff,0x75,0xcc,0x8a, + 0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x55,0xcc,0x8b,0x00,0x01, + 0xff,0x75,0xcc,0x8b,0x00,0x10,0x08,0x01,0xff,0x55,0xcc,0xa8,0x00,0x01,0xff,0x75, + 0xcc,0xa8,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x57,0xcc,0x82,0x00,0x01,0xff,0x77, + 0xcc,0x82,0x00,0x10,0x08,0x01,0xff,0x59,0xcc,0x82,0x00,0x01,0xff,0x79,0xcc,0x82, + 0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x59,0xcc,0x88,0x00,0x01,0xff,0x5a, + 0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x7a,0xcc,0x81,0x00,0x01,0xff,0x5a,0xcc,0x87, + 0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x7a,0xcc,0x87,0x00,0x01,0xff,0x5a,0xcc,0x8c, + 0x00,0x10,0x08,0x01,0xff,0x7a,0xcc,0x8c,0x00,0x01,0x00,0xd0,0x4a,0xcf,0x86,0x55, + 0x04,0x01,0x00,0xd4,0x2c,0xd3,0x18,0x92,0x14,0x91,0x10,0x10,0x08,0x01,0xff,0x4f, + 0xcc,0x9b,0x00,0x01,0xff,0x6f,0xcc,0x9b,0x00,0x01,0x00,0x01,0x00,0x52,0x04,0x01, + 0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x01,0xff,0x55,0xcc,0x9b,0x00,0x93, + 0x14,0x92,0x10,0x91,0x0c,0x10,0x08,0x01,0xff,0x75,0xcc,0x9b,0x00,0x01,0x00,0x01, + 0x00,0x01,0x00,0x01,0x00,0xcf,0x86,0xd5,0xb4,0xd4,0x24,0x53,0x04,0x01,0x00,0x52, + 0x04,0x01,0x00,0xd1,0x0c,0x10,0x04,0x01,0x00,0x01,0xff,0x41,0xcc,0x8c,0x00,0x10, + 0x08,0x01,0xff,0x61,0xcc,0x8c,0x00,0x01,0xff,0x49,0xcc,0x8c,0x00,0xd3,0x46,0xd2, + 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x69,0xcc,0x8c,0x00,0x01,0xff,0x4f,0xcc,0x8c, + 0x00,0x10,0x08,0x01,0xff,0x6f,0xcc,0x8c,0x00,0x01,0xff,0x55,0xcc,0x8c,0x00,0xd1, + 0x12,0x10,0x08,0x01,0xff,0x75,0xcc,0x8c,0x00,0x01,0xff,0x55,0xcc,0x88,0xcc,0x84, + 0x00,0x10,0x0a,0x01,0xff,0x75,0xcc,0x88,0xcc,0x84,0x00,0x01,0xff,0x55,0xcc,0x88, + 0xcc,0x81,0x00,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x75,0xcc,0x88,0xcc,0x81, + 0x00,0x01,0xff,0x55,0xcc,0x88,0xcc,0x8c,0x00,0x10,0x0a,0x01,0xff,0x75,0xcc,0x88, + 0xcc,0x8c,0x00,0x01,0xff,0x55,0xcc,0x88,0xcc,0x80,0x00,0xd1,0x0e,0x10,0x0a,0x01, + 0xff,0x75,0xcc,0x88,0xcc,0x80,0x00,0x01,0x00,0x10,0x0a,0x01,0xff,0x41,0xcc,0x88, + 0xcc,0x84,0x00,0x01,0xff,0x61,0xcc,0x88,0xcc,0x84,0x00,0xd4,0x80,0xd3,0x3a,0xd2, + 0x26,0xd1,0x14,0x10,0x0a,0x01,0xff,0x41,0xcc,0x87,0xcc,0x84,0x00,0x01,0xff,0x61, + 0xcc,0x87,0xcc,0x84,0x00,0x10,0x09,0x01,0xff,0xc3,0x86,0xcc,0x84,0x00,0x01,0xff, + 0xc3,0xa6,0xcc,0x84,0x00,0x51,0x04,0x01,0x00,0x10,0x08,0x01,0xff,0x47,0xcc,0x8c, + 0x00,0x01,0xff,0x67,0xcc,0x8c,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x4b, + 0xcc,0x8c,0x00,0x01,0xff,0x6b,0xcc,0x8c,0x00,0x10,0x08,0x01,0xff,0x4f,0xcc,0xa8, + 0x00,0x01,0xff,0x6f,0xcc,0xa8,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x4f,0xcc,0xa8, + 0xcc,0x84,0x00,0x01,0xff,0x6f,0xcc,0xa8,0xcc,0x84,0x00,0x10,0x09,0x01,0xff,0xc6, + 0xb7,0xcc,0x8c,0x00,0x01,0xff,0xca,0x92,0xcc,0x8c,0x00,0xd3,0x24,0xd2,0x10,0x91, + 0x0c,0x10,0x08,0x01,0xff,0x6a,0xcc,0x8c,0x00,0x01,0x00,0x01,0x00,0x91,0x10,0x10, + 0x08,0x01,0xff,0x47,0xcc,0x81,0x00,0x01,0xff,0x67,0xcc,0x81,0x00,0x04,0x00,0xd2, + 0x24,0xd1,0x10,0x10,0x08,0x04,0xff,0x4e,0xcc,0x80,0x00,0x04,0xff,0x6e,0xcc,0x80, + 0x00,0x10,0x0a,0x01,0xff,0x41,0xcc,0x8a,0xcc,0x81,0x00,0x01,0xff,0x61,0xcc,0x8a, + 0xcc,0x81,0x00,0xd1,0x12,0x10,0x09,0x01,0xff,0xc3,0x86,0xcc,0x81,0x00,0x01,0xff, + 0xc3,0xa6,0xcc,0x81,0x00,0x10,0x09,0x01,0xff,0xc3,0x98,0xcc,0x81,0x00,0x01,0xff, + 0xc3,0xb8,0xcc,0x81,0x00,0xe2,0x07,0x02,0xe1,0xae,0x01,0xe0,0x93,0x01,0xcf,0x86, + 0xd5,0xf4,0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x41,0xcc, + 0x8f,0x00,0x01,0xff,0x61,0xcc,0x8f,0x00,0x10,0x08,0x01,0xff,0x41,0xcc,0x91,0x00, + 0x01,0xff,0x61,0xcc,0x91,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x45,0xcc,0x8f,0x00, + 0x01,0xff,0x65,0xcc,0x8f,0x00,0x10,0x08,0x01,0xff,0x45,0xcc,0x91,0x00,0x01,0xff, + 0x65,0xcc,0x91,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x49,0xcc,0x8f,0x00, + 0x01,0xff,0x69,0xcc,0x8f,0x00,0x10,0x08,0x01,0xff,0x49,0xcc,0x91,0x00,0x01,0xff, + 0x69,0xcc,0x91,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x4f,0xcc,0x8f,0x00,0x01,0xff, + 0x6f,0xcc,0x8f,0x00,0x10,0x08,0x01,0xff,0x4f,0xcc,0x91,0x00,0x01,0xff,0x6f,0xcc, + 0x91,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x52,0xcc,0x8f,0x00, + 0x01,0xff,0x72,0xcc,0x8f,0x00,0x10,0x08,0x01,0xff,0x52,0xcc,0x91,0x00,0x01,0xff, + 0x72,0xcc,0x91,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x55,0xcc,0x8f,0x00,0x01,0xff, + 0x75,0xcc,0x8f,0x00,0x10,0x08,0x01,0xff,0x55,0xcc,0x91,0x00,0x01,0xff,0x75,0xcc, + 0x91,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x04,0xff,0x53,0xcc,0xa6,0x00,0x04,0xff, + 0x73,0xcc,0xa6,0x00,0x10,0x08,0x04,0xff,0x54,0xcc,0xa6,0x00,0x04,0xff,0x74,0xcc, + 0xa6,0x00,0x51,0x04,0x04,0x00,0x10,0x08,0x04,0xff,0x48,0xcc,0x8c,0x00,0x04,0xff, + 0x68,0xcc,0x8c,0x00,0xd4,0x68,0xd3,0x20,0xd2,0x0c,0x91,0x08,0x10,0x04,0x06,0x00, + 0x07,0x00,0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x08,0x04,0xff,0x41,0xcc,0x87,0x00, + 0x04,0xff,0x61,0xcc,0x87,0x00,0xd2,0x24,0xd1,0x10,0x10,0x08,0x04,0xff,0x45,0xcc, + 0xa7,0x00,0x04,0xff,0x65,0xcc,0xa7,0x00,0x10,0x0a,0x04,0xff,0x4f,0xcc,0x88,0xcc, + 0x84,0x00,0x04,0xff,0x6f,0xcc,0x88,0xcc,0x84,0x00,0xd1,0x14,0x10,0x0a,0x04,0xff, + 0x4f,0xcc,0x83,0xcc,0x84,0x00,0x04,0xff,0x6f,0xcc,0x83,0xcc,0x84,0x00,0x10,0x08, + 0x04,0xff,0x4f,0xcc,0x87,0x00,0x04,0xff,0x6f,0xcc,0x87,0x00,0x93,0x30,0xd2,0x24, + 0xd1,0x14,0x10,0x0a,0x04,0xff,0x4f,0xcc,0x87,0xcc,0x84,0x00,0x04,0xff,0x6f,0xcc, + 0x87,0xcc,0x84,0x00,0x10,0x08,0x04,0xff,0x59,0xcc,0x84,0x00,0x04,0xff,0x79,0xcc, + 0x84,0x00,0x51,0x04,0x07,0x00,0x10,0x04,0x07,0x00,0x08,0x00,0x08,0x00,0xcf,0x86, + 0x95,0x14,0x94,0x10,0x93,0x0c,0x92,0x08,0x11,0x04,0x08,0x00,0x09,0x00,0x09,0x00, + 0x09,0x00,0x01,0x00,0x01,0x00,0xd0,0x22,0xcf,0x86,0x55,0x04,0x01,0x00,0x94,0x18, + 0x53,0x04,0x01,0x00,0xd2,0x0c,0x91,0x08,0x10,0x04,0x01,0x00,0x04,0x00,0x04,0x00, + 0x11,0x04,0x04,0x00,0x07,0x00,0x01,0x00,0xcf,0x86,0xd5,0x18,0x54,0x04,0x01,0x00, + 0x53,0x04,0x01,0x00,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00, + 0x04,0x00,0x94,0x18,0x53,0x04,0x01,0x00,0xd2,0x08,0x11,0x04,0x01,0x00,0x04,0x00, + 0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x07,0x00,0x07,0x00,0xe1,0x35,0x01,0xd0, + 0x72,0xcf,0x86,0xd5,0x24,0x54,0x04,0x01,0xe6,0xd3,0x10,0x52,0x04,0x01,0xe6,0x91, + 0x08,0x10,0x04,0x01,0xe6,0x01,0xe8,0x01,0xdc,0x92,0x0c,0x51,0x04,0x01,0xdc,0x10, + 0x04,0x01,0xe8,0x01,0xd8,0x01,0xdc,0xd4,0x2c,0xd3,0x1c,0xd2,0x10,0xd1,0x08,0x10, + 0x04,0x01,0xdc,0x01,0xca,0x10,0x04,0x01,0xca,0x01,0xdc,0x51,0x04,0x01,0xdc,0x10, + 0x04,0x01,0xdc,0x01,0xca,0x92,0x0c,0x91,0x08,0x10,0x04,0x01,0xca,0x01,0xdc,0x01, + 0xdc,0x01,0xdc,0xd3,0x08,0x12,0x04,0x01,0xdc,0x01,0x01,0xd2,0x0c,0x91,0x08,0x10, + 0x04,0x01,0x01,0x01,0xdc,0x01,0xdc,0x91,0x08,0x10,0x04,0x01,0xdc,0x01,0xe6,0x01, + 0xe6,0xcf,0x86,0xd5,0x7f,0xd4,0x47,0xd3,0x2e,0xd2,0x19,0xd1,0x0e,0x10,0x07,0x01, + 0xff,0xcc,0x80,0x00,0x01,0xff,0xcc,0x81,0x00,0x10,0x04,0x01,0xe6,0x01,0xff,0xcc, + 0x93,0x00,0xd1,0x0d,0x10,0x09,0x01,0xff,0xcc,0x88,0xcc,0x81,0x00,0x01,0xf0,0x10, + 0x04,0x04,0xe6,0x04,0xdc,0xd2,0x08,0x11,0x04,0x04,0xdc,0x04,0xe6,0xd1,0x08,0x10, + 0x04,0x04,0xe6,0x04,0xdc,0x10,0x04,0x04,0xdc,0x06,0xff,0x00,0xd3,0x18,0xd2,0x0c, + 0x51,0x04,0x07,0xe6,0x10,0x04,0x07,0xe6,0x07,0xdc,0x51,0x04,0x07,0xdc,0x10,0x04, + 0x07,0xdc,0x07,0xe6,0xd2,0x10,0xd1,0x08,0x10,0x04,0x08,0xe8,0x08,0xdc,0x10,0x04, + 0x08,0xdc,0x08,0xe6,0xd1,0x08,0x10,0x04,0x08,0xe9,0x07,0xea,0x10,0x04,0x07,0xea, + 0x07,0xe9,0xd4,0x14,0x93,0x10,0x92,0x0c,0x51,0x04,0x01,0xea,0x10,0x04,0x04,0xe9, + 0x06,0xe6,0x06,0xe6,0x06,0xe6,0xd3,0x13,0x52,0x04,0x0a,0x00,0x91,0x0b,0x10,0x07, + 0x01,0xff,0xca,0xb9,0x00,0x01,0x00,0x0a,0x00,0xd2,0x0c,0x51,0x04,0x00,0x00,0x10, + 0x04,0x01,0x00,0x09,0x00,0x51,0x04,0x09,0x00,0x10,0x06,0x01,0xff,0x3b,0x00,0x10, + 0x00,0xd0,0xe1,0xcf,0x86,0xd5,0x7a,0xd4,0x5f,0xd3,0x21,0x52,0x04,0x00,0x00,0xd1, + 0x0d,0x10,0x04,0x01,0x00,0x01,0xff,0xc2,0xa8,0xcc,0x81,0x00,0x10,0x09,0x01,0xff, + 0xce,0x91,0xcc,0x81,0x00,0x01,0xff,0xc2,0xb7,0x00,0xd2,0x1f,0xd1,0x12,0x10,0x09, + 0x01,0xff,0xce,0x95,0xcc,0x81,0x00,0x01,0xff,0xce,0x97,0xcc,0x81,0x00,0x10,0x09, + 0x01,0xff,0xce,0x99,0xcc,0x81,0x00,0x00,0x00,0xd1,0x0d,0x10,0x09,0x01,0xff,0xce, + 0x9f,0xcc,0x81,0x00,0x00,0x00,0x10,0x09,0x01,0xff,0xce,0xa5,0xcc,0x81,0x00,0x01, + 0xff,0xce,0xa9,0xcc,0x81,0x00,0x93,0x17,0x92,0x13,0x91,0x0f,0x10,0x0b,0x01,0xff, + 0xce,0xb9,0xcc,0x88,0xcc,0x81,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd4, + 0x4a,0xd3,0x10,0x92,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x00,0x00,0x01,0x00,0x01, + 0x00,0xd2,0x16,0x51,0x04,0x01,0x00,0x10,0x09,0x01,0xff,0xce,0x99,0xcc,0x88,0x00, + 0x01,0xff,0xce,0xa5,0xcc,0x88,0x00,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb1,0xcc, + 0x81,0x00,0x01,0xff,0xce,0xb5,0xcc,0x81,0x00,0x10,0x09,0x01,0xff,0xce,0xb7,0xcc, + 0x81,0x00,0x01,0xff,0xce,0xb9,0xcc,0x81,0x00,0x93,0x17,0x92,0x13,0x91,0x0f,0x10, + 0x0b,0x01,0xff,0xcf,0x85,0xcc,0x88,0xcc,0x81,0x00,0x01,0x00,0x01,0x00,0x01,0x00, + 0x01,0x00,0xcf,0x86,0xd5,0x7b,0xd4,0x39,0x53,0x04,0x01,0x00,0xd2,0x16,0x51,0x04, + 0x01,0x00,0x10,0x09,0x01,0xff,0xce,0xb9,0xcc,0x88,0x00,0x01,0xff,0xcf,0x85,0xcc, + 0x88,0x00,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xbf,0xcc,0x81,0x00,0x01,0xff,0xcf, + 0x85,0xcc,0x81,0x00,0x10,0x09,0x01,0xff,0xcf,0x89,0xcc,0x81,0x00,0x0a,0x00,0xd3, + 0x26,0xd2,0x11,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x01,0xff,0xcf,0x92,0xcc, + 0x81,0x00,0xd1,0x0d,0x10,0x09,0x01,0xff,0xcf,0x92,0xcc,0x88,0x00,0x01,0x00,0x10, + 0x04,0x01,0x00,0x04,0x00,0xd2,0x0c,0x51,0x04,0x06,0x00,0x10,0x04,0x01,0x00,0x04, + 0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x04,0x00,0x10,0x04,0x01,0x00,0x04,0x00,0xd4, + 0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x01,0x00,0x04,0x00,0x01,0x00,0x01, + 0x00,0x01,0x00,0xd3,0x10,0x52,0x04,0x01,0x00,0x51,0x04,0x05,0x00,0x10,0x04,0x06, + 0x00,0x07,0x00,0x12,0x04,0x07,0x00,0x08,0x00,0xe3,0x47,0x04,0xe2,0xbe,0x02,0xe1, + 0x07,0x01,0xd0,0x8b,0xcf,0x86,0xd5,0x6c,0xd4,0x53,0xd3,0x30,0xd2,0x1f,0xd1,0x12, + 0x10,0x09,0x04,0xff,0xd0,0x95,0xcc,0x80,0x00,0x01,0xff,0xd0,0x95,0xcc,0x88,0x00, + 0x10,0x04,0x01,0x00,0x01,0xff,0xd0,0x93,0xcc,0x81,0x00,0x51,0x04,0x01,0x00,0x10, + 0x04,0x01,0x00,0x01,0xff,0xd0,0x86,0xcc,0x88,0x00,0x52,0x04,0x01,0x00,0xd1,0x12, + 0x10,0x09,0x01,0xff,0xd0,0x9a,0xcc,0x81,0x00,0x04,0xff,0xd0,0x98,0xcc,0x80,0x00, + 0x10,0x09,0x01,0xff,0xd0,0xa3,0xcc,0x86,0x00,0x01,0x00,0x53,0x04,0x01,0x00,0x92, + 0x11,0x91,0x0d,0x10,0x04,0x01,0x00,0x01,0xff,0xd0,0x98,0xcc,0x86,0x00,0x01,0x00, + 0x01,0x00,0x54,0x04,0x01,0x00,0x53,0x04,0x01,0x00,0x92,0x11,0x91,0x0d,0x10,0x04, + 0x01,0x00,0x01,0xff,0xd0,0xb8,0xcc,0x86,0x00,0x01,0x00,0x01,0x00,0xcf,0x86,0xd5, + 0x57,0x54,0x04,0x01,0x00,0xd3,0x30,0xd2,0x1f,0xd1,0x12,0x10,0x09,0x04,0xff,0xd0, + 0xb5,0xcc,0x80,0x00,0x01,0xff,0xd0,0xb5,0xcc,0x88,0x00,0x10,0x04,0x01,0x00,0x01, + 0xff,0xd0,0xb3,0xcc,0x81,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x01,0xff, + 0xd1,0x96,0xcc,0x88,0x00,0x52,0x04,0x01,0x00,0xd1,0x12,0x10,0x09,0x01,0xff,0xd0, + 0xba,0xcc,0x81,0x00,0x04,0xff,0xd0,0xb8,0xcc,0x80,0x00,0x10,0x09,0x01,0xff,0xd1, + 0x83,0xcc,0x86,0x00,0x01,0x00,0x54,0x04,0x01,0x00,0x93,0x1a,0x52,0x04,0x01,0x00, + 0x51,0x04,0x01,0x00,0x10,0x09,0x01,0xff,0xd1,0xb4,0xcc,0x8f,0x00,0x01,0xff,0xd1, + 0xb5,0xcc,0x8f,0x00,0x01,0x00,0xd0,0x2e,0xcf,0x86,0x95,0x28,0x94,0x24,0xd3,0x18, + 0xd2,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x01,0xe6,0x51,0x04,0x01,0xe6, + 0x10,0x04,0x01,0xe6,0x0a,0xe6,0x92,0x08,0x11,0x04,0x04,0x00,0x06,0x00,0x04,0x00, + 0x01,0x00,0x01,0x00,0xcf,0x86,0xd5,0xbe,0xd4,0x4a,0xd3,0x2a,0xd2,0x1a,0xd1,0x0d, + 0x10,0x04,0x01,0x00,0x01,0xff,0xd0,0x96,0xcc,0x86,0x00,0x10,0x09,0x01,0xff,0xd0, + 0xb6,0xcc,0x86,0x00,0x01,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x06,0x00,0x10,0x04, + 0x06,0x00,0x01,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04,0x01,0x00,0x06,0x00,0x10,0x04, + 0x06,0x00,0x01,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x06,0x00,0x10,0x04,0x06,0x00, + 0x09,0x00,0xd3,0x3a,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff,0xd0,0x90,0xcc,0x86, + 0x00,0x01,0xff,0xd0,0xb0,0xcc,0x86,0x00,0x10,0x09,0x01,0xff,0xd0,0x90,0xcc,0x88, + 0x00,0x01,0xff,0xd0,0xb0,0xcc,0x88,0x00,0x51,0x04,0x01,0x00,0x10,0x09,0x01,0xff, + 0xd0,0x95,0xcc,0x86,0x00,0x01,0xff,0xd0,0xb5,0xcc,0x86,0x00,0xd2,0x16,0x51,0x04, + 0x01,0x00,0x10,0x09,0x01,0xff,0xd3,0x98,0xcc,0x88,0x00,0x01,0xff,0xd3,0x99,0xcc, + 0x88,0x00,0xd1,0x12,0x10,0x09,0x01,0xff,0xd0,0x96,0xcc,0x88,0x00,0x01,0xff,0xd0, + 0xb6,0xcc,0x88,0x00,0x10,0x09,0x01,0xff,0xd0,0x97,0xcc,0x88,0x00,0x01,0xff,0xd0, + 0xb7,0xcc,0x88,0x00,0xd4,0x74,0xd3,0x3a,0xd2,0x16,0x51,0x04,0x01,0x00,0x10,0x09, + 0x01,0xff,0xd0,0x98,0xcc,0x84,0x00,0x01,0xff,0xd0,0xb8,0xcc,0x84,0x00,0xd1,0x12, + 0x10,0x09,0x01,0xff,0xd0,0x98,0xcc,0x88,0x00,0x01,0xff,0xd0,0xb8,0xcc,0x88,0x00, + 0x10,0x09,0x01,0xff,0xd0,0x9e,0xcc,0x88,0x00,0x01,0xff,0xd0,0xbe,0xcc,0x88,0x00, + 0xd2,0x16,0x51,0x04,0x01,0x00,0x10,0x09,0x01,0xff,0xd3,0xa8,0xcc,0x88,0x00,0x01, + 0xff,0xd3,0xa9,0xcc,0x88,0x00,0xd1,0x12,0x10,0x09,0x04,0xff,0xd0,0xad,0xcc,0x88, + 0x00,0x04,0xff,0xd1,0x8d,0xcc,0x88,0x00,0x10,0x09,0x01,0xff,0xd0,0xa3,0xcc,0x84, + 0x00,0x01,0xff,0xd1,0x83,0xcc,0x84,0x00,0xd3,0x3a,0xd2,0x24,0xd1,0x12,0x10,0x09, + 0x01,0xff,0xd0,0xa3,0xcc,0x88,0x00,0x01,0xff,0xd1,0x83,0xcc,0x88,0x00,0x10,0x09, + 0x01,0xff,0xd0,0xa3,0xcc,0x8b,0x00,0x01,0xff,0xd1,0x83,0xcc,0x8b,0x00,0x91,0x12, + 0x10,0x09,0x01,0xff,0xd0,0xa7,0xcc,0x88,0x00,0x01,0xff,0xd1,0x87,0xcc,0x88,0x00, + 0x08,0x00,0x92,0x16,0x91,0x12,0x10,0x09,0x01,0xff,0xd0,0xab,0xcc,0x88,0x00,0x01, + 0xff,0xd1,0x8b,0xcc,0x88,0x00,0x09,0x00,0x09,0x00,0xd1,0x74,0xd0,0x36,0xcf,0x86, + 0xd5,0x10,0x54,0x04,0x06,0x00,0x93,0x08,0x12,0x04,0x09,0x00,0x0a,0x00,0x0a,0x00, + 0xd4,0x10,0x93,0x0c,0x52,0x04,0x0a,0x00,0x11,0x04,0x0b,0x00,0x0c,0x00,0x10,0x00, + 0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x01,0x00, + 0x01,0x00,0xcf,0x86,0xd5,0x24,0x54,0x04,0x01,0x00,0xd3,0x10,0x52,0x04,0x01,0x00, + 0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x92,0x0c,0x91,0x08,0x10,0x04, + 0x00,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x94,0x14,0x93,0x10,0x92,0x0c,0x91,0x08, + 0x10,0x04,0x14,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd0,0xba, + 0xcf,0x86,0xd5,0x4c,0xd4,0x24,0x53,0x04,0x01,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04, + 0x14,0x00,0x01,0x00,0x10,0x04,0x04,0x00,0x00,0x00,0xd1,0x08,0x10,0x04,0x00,0x00, + 0x10,0x00,0x10,0x04,0x10,0x00,0x0d,0x00,0xd3,0x18,0xd2,0x0c,0x91,0x08,0x10,0x04, + 0x00,0x00,0x02,0xdc,0x02,0xe6,0x51,0x04,0x02,0xe6,0x10,0x04,0x02,0xdc,0x02,0xe6, + 0x92,0x0c,0x51,0x04,0x02,0xe6,0x10,0x04,0x02,0xde,0x02,0xdc,0x02,0xe6,0xd4,0x2c, + 0xd3,0x10,0x92,0x0c,0x51,0x04,0x02,0xe6,0x10,0x04,0x08,0xdc,0x02,0xdc,0x02,0xdc, + 0xd2,0x0c,0x51,0x04,0x02,0xe6,0x10,0x04,0x02,0xdc,0x02,0xe6,0xd1,0x08,0x10,0x04, + 0x02,0xe6,0x02,0xde,0x10,0x04,0x02,0xe4,0x02,0xe6,0xd3,0x20,0xd2,0x10,0xd1,0x08, + 0x10,0x04,0x01,0x0a,0x01,0x0b,0x10,0x04,0x01,0x0c,0x01,0x0d,0xd1,0x08,0x10,0x04, + 0x01,0x0e,0x01,0x0f,0x10,0x04,0x01,0x10,0x01,0x11,0xd2,0x10,0xd1,0x08,0x10,0x04, + 0x01,0x12,0x01,0x13,0x10,0x04,0x09,0x13,0x01,0x14,0xd1,0x08,0x10,0x04,0x01,0x15, + 0x01,0x16,0x10,0x04,0x01,0x00,0x01,0x17,0xcf,0x86,0xd5,0x28,0x94,0x24,0x93,0x20, + 0xd2,0x10,0xd1,0x08,0x10,0x04,0x01,0x00,0x01,0x18,0x10,0x04,0x01,0x19,0x01,0x00, + 0xd1,0x08,0x10,0x04,0x02,0xe6,0x08,0xdc,0x10,0x04,0x08,0x00,0x08,0x12,0x00,0x00, + 0x01,0x00,0xd4,0x1c,0x53,0x04,0x01,0x00,0xd2,0x0c,0x51,0x04,0x01,0x00,0x10,0x04, + 0x01,0x00,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x14,0x00,0x93,0x10, + 0x52,0x04,0x01,0x00,0x91,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00, + 0xe2,0xfb,0x01,0xe1,0x2b,0x01,0xd0,0xa8,0xcf,0x86,0xd5,0x55,0xd4,0x28,0xd3,0x10, + 0x52,0x04,0x07,0x00,0x91,0x08,0x10,0x04,0x0d,0x00,0x10,0x00,0x0a,0x00,0xd2,0x0c, + 0x51,0x04,0x0a,0x00,0x10,0x04,0x0a,0x00,0x08,0x00,0x91,0x08,0x10,0x04,0x01,0x00, + 0x07,0x00,0x07,0x00,0xd3,0x0c,0x52,0x04,0x07,0xe6,0x11,0x04,0x07,0xe6,0x0a,0xe6, + 0xd2,0x10,0xd1,0x08,0x10,0x04,0x0a,0x1e,0x0a,0x1f,0x10,0x04,0x0a,0x20,0x01,0x00, + 0xd1,0x09,0x10,0x05,0x0f,0xff,0x00,0x00,0x00,0x10,0x04,0x08,0x00,0x01,0x00,0xd4, + 0x3d,0x93,0x39,0xd2,0x1a,0xd1,0x08,0x10,0x04,0x0c,0x00,0x01,0x00,0x10,0x09,0x01, + 0xff,0xd8,0xa7,0xd9,0x93,0x00,0x01,0xff,0xd8,0xa7,0xd9,0x94,0x00,0xd1,0x12,0x10, + 0x09,0x01,0xff,0xd9,0x88,0xd9,0x94,0x00,0x01,0xff,0xd8,0xa7,0xd9,0x95,0x00,0x10, + 0x09,0x01,0xff,0xd9,0x8a,0xd9,0x94,0x00,0x01,0x00,0x01,0x00,0x53,0x04,0x01,0x00, + 0x92,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x0a,0x00,0x0a,0x00,0xcf,0x86, + 0xd5,0x5c,0xd4,0x20,0x53,0x04,0x01,0x00,0xd2,0x0c,0x51,0x04,0x01,0x00,0x10,0x04, + 0x01,0x00,0x01,0x1b,0xd1,0x08,0x10,0x04,0x01,0x1c,0x01,0x1d,0x10,0x04,0x01,0x1e, + 0x01,0x1f,0xd3,0x20,0xd2,0x10,0xd1,0x08,0x10,0x04,0x01,0x20,0x01,0x21,0x10,0x04, + 0x01,0x22,0x04,0xe6,0xd1,0x08,0x10,0x04,0x04,0xe6,0x04,0xdc,0x10,0x04,0x07,0xdc, + 0x07,0xe6,0xd2,0x0c,0x91,0x08,0x10,0x04,0x07,0xe6,0x08,0xe6,0x08,0xe6,0xd1,0x08, + 0x10,0x04,0x08,0xdc,0x08,0xe6,0x10,0x04,0x08,0xe6,0x0c,0xdc,0xd4,0x10,0x53,0x04, + 0x01,0x00,0x52,0x04,0x01,0x00,0x11,0x04,0x01,0x00,0x06,0x00,0x93,0x10,0x92,0x0c, + 0x91,0x08,0x10,0x04,0x01,0x23,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd0,0x22, + 0xcf,0x86,0x55,0x04,0x01,0x00,0x54,0x04,0x01,0x00,0x53,0x04,0x01,0x00,0xd2,0x08, + 0x11,0x04,0x04,0x00,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x04,0x00, + 0xcf,0x86,0xd5,0x5b,0xd4,0x2e,0xd3,0x1e,0x92,0x1a,0xd1,0x0d,0x10,0x09,0x01,0xff, + 0xdb,0x95,0xd9,0x94,0x00,0x01,0x00,0x10,0x09,0x01,0xff,0xdb,0x81,0xd9,0x94,0x00, + 0x01,0x00,0x01,0x00,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00, + 0x04,0x00,0xd3,0x19,0xd2,0x11,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x01,0xff, + 0xdb,0x92,0xd9,0x94,0x00,0x11,0x04,0x01,0x00,0x01,0xe6,0x52,0x04,0x01,0xe6,0xd1, + 0x08,0x10,0x04,0x01,0xe6,0x01,0x00,0x10,0x04,0x01,0x00,0x01,0xe6,0xd4,0x38,0xd3, + 0x1c,0xd2,0x0c,0x51,0x04,0x01,0xe6,0x10,0x04,0x01,0xe6,0x01,0xdc,0xd1,0x08,0x10, + 0x04,0x01,0xe6,0x01,0x00,0x10,0x04,0x01,0x00,0x01,0xe6,0xd2,0x10,0xd1,0x08,0x10, + 0x04,0x01,0xe6,0x01,0x00,0x10,0x04,0x01,0xdc,0x01,0xe6,0x91,0x08,0x10,0x04,0x01, + 0xe6,0x01,0xdc,0x07,0x00,0x53,0x04,0x01,0x00,0xd2,0x08,0x11,0x04,0x01,0x00,0x04, + 0x00,0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x07,0x00,0xd1,0xc8,0xd0,0x76,0xcf, + 0x86,0xd5,0x28,0xd4,0x14,0x53,0x04,0x04,0x00,0x52,0x04,0x04,0x00,0x51,0x04,0x04, + 0x00,0x10,0x04,0x00,0x00,0x04,0x00,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x04, + 0x00,0x04,0x24,0x04,0x00,0x04,0x00,0x04,0x00,0xd4,0x14,0x53,0x04,0x04,0x00,0x52, + 0x04,0x04,0x00,0x91,0x08,0x10,0x04,0x04,0x00,0x07,0x00,0x07,0x00,0xd3,0x1c,0xd2, + 0x0c,0x91,0x08,0x10,0x04,0x04,0xe6,0x04,0xdc,0x04,0xe6,0xd1,0x08,0x10,0x04,0x04, + 0xdc,0x04,0xe6,0x10,0x04,0x04,0xe6,0x04,0xdc,0xd2,0x0c,0x51,0x04,0x04,0xdc,0x10, + 0x04,0x04,0xe6,0x04,0xdc,0xd1,0x08,0x10,0x04,0x04,0xdc,0x04,0xe6,0x10,0x04,0x04, + 0xdc,0x04,0xe6,0xcf,0x86,0xd5,0x3c,0x94,0x38,0xd3,0x1c,0xd2,0x0c,0x51,0x04,0x04, + 0xe6,0x10,0x04,0x04,0xdc,0x04,0xe6,0xd1,0x08,0x10,0x04,0x04,0xdc,0x04,0xe6,0x10, + 0x04,0x04,0xdc,0x04,0xe6,0xd2,0x10,0xd1,0x08,0x10,0x04,0x04,0xdc,0x04,0xe6,0x10, + 0x04,0x04,0xe6,0x00,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x07,0x00,0x07,0x00,0x08, + 0x00,0x94,0x10,0x53,0x04,0x08,0x00,0x52,0x04,0x08,0x00,0x11,0x04,0x08,0x00,0x0a, + 0x00,0x0a,0x00,0xd0,0x1e,0xcf,0x86,0x55,0x04,0x04,0x00,0x54,0x04,0x04,0x00,0x93, + 0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x04,0x00,0x06,0x00,0x00,0x00,0x00,0x00,0x00, + 0x00,0xcf,0x86,0x55,0x04,0x09,0x00,0xd4,0x14,0x53,0x04,0x09,0x00,0x92,0x0c,0x51, + 0x04,0x09,0x00,0x10,0x04,0x09,0x00,0x09,0xe6,0x09,0xe6,0xd3,0x10,0x92,0x0c,0x51, + 0x04,0x09,0xe6,0x10,0x04,0x09,0xdc,0x09,0xe6,0x09,0x00,0xd2,0x0c,0x51,0x04,0x09, + 0x00,0x10,0x04,0x09,0x00,0x00,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x14,0xdc,0x14, + 0x00,0xe4,0xf8,0x57,0xe3,0x45,0x3f,0xe2,0xf4,0x3e,0xe1,0xc7,0x2c,0xe0,0x21,0x10, + 0xcf,0x86,0xc5,0xe4,0x80,0x08,0xe3,0xcb,0x03,0xe2,0x61,0x01,0xd1,0x94,0xd0,0x5a, + 0xcf,0x86,0xd5,0x20,0x54,0x04,0x0b,0x00,0xd3,0x0c,0x52,0x04,0x0b,0x00,0x11,0x04, + 0x0b,0x00,0x0b,0xe6,0x92,0x0c,0x51,0x04,0x0b,0xe6,0x10,0x04,0x0b,0x00,0x0b,0xe6, + 0x0b,0xe6,0xd4,0x24,0xd3,0x10,0x52,0x04,0x0b,0xe6,0x91,0x08,0x10,0x04,0x0b,0x00, + 0x0b,0xe6,0x0b,0xe6,0xd2,0x0c,0x91,0x08,0x10,0x04,0x0b,0x00,0x0b,0xe6,0x0b,0xe6, + 0x11,0x04,0x0b,0xe6,0x00,0x00,0x53,0x04,0x0b,0x00,0x52,0x04,0x0b,0x00,0x51,0x04, + 0x0b,0x00,0x10,0x04,0x0b,0x00,0x00,0x00,0xcf,0x86,0xd5,0x20,0x54,0x04,0x0c,0x00, + 0x53,0x04,0x0c,0x00,0xd2,0x0c,0x91,0x08,0x10,0x04,0x0c,0x00,0x0c,0xdc,0x0c,0xdc, + 0x51,0x04,0x00,0x00,0x10,0x04,0x0c,0x00,0x00,0x00,0x94,0x14,0x53,0x04,0x13,0x00, + 0x92,0x0c,0x51,0x04,0x13,0x00,0x10,0x04,0x13,0x00,0x00,0x00,0x00,0x00,0x00,0x00, + 0xd0,0x4a,0xcf,0x86,0x55,0x04,0x00,0x00,0xd4,0x20,0xd3,0x10,0x92,0x0c,0x91,0x08, + 0x10,0x04,0x0d,0x00,0x10,0x00,0x0d,0x00,0x0d,0x00,0x52,0x04,0x0d,0x00,0x91,0x08, + 0x10,0x04,0x0d,0x00,0x10,0x00,0x10,0x00,0xd3,0x18,0xd2,0x0c,0x51,0x04,0x10,0x00, + 0x10,0x04,0x10,0x00,0x11,0x00,0x91,0x08,0x10,0x04,0x11,0x00,0x00,0x00,0x12,0x00, + 0x52,0x04,0x12,0x00,0x11,0x04,0x12,0x00,0x00,0x00,0xcf,0x86,0xd5,0x18,0x54,0x04, + 0x00,0x00,0x93,0x10,0x92,0x0c,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x14,0xdc, + 0x12,0xe6,0x12,0xe6,0xd4,0x30,0xd3,0x18,0xd2,0x0c,0x51,0x04,0x12,0xe6,0x10,0x04, + 0x12,0x00,0x11,0xdc,0x51,0x04,0x0d,0xe6,0x10,0x04,0x0d,0xdc,0x0d,0xe6,0xd2,0x0c, + 0x91,0x08,0x10,0x04,0x0d,0xe6,0x0d,0xdc,0x0d,0xe6,0x91,0x08,0x10,0x04,0x0d,0xe6, + 0x0d,0xdc,0x0d,0xdc,0xd3,0x1c,0xd2,0x10,0xd1,0x08,0x10,0x04,0x0d,0x1b,0x0d,0x1c, + 0x10,0x04,0x0d,0x1d,0x0d,0xe6,0x51,0x04,0x0d,0xe6,0x10,0x04,0x0d,0xdc,0x0d,0xe6, + 0xd2,0x10,0xd1,0x08,0x10,0x04,0x0d,0xe6,0x0d,0xdc,0x10,0x04,0x0d,0xdc,0x0d,0xe6, + 0x51,0x04,0x0d,0xe6,0x10,0x04,0x0d,0xe6,0x10,0xe6,0xe1,0x3a,0x01,0xd0,0x77,0xcf, + 0x86,0xd5,0x20,0x94,0x1c,0x93,0x18,0xd2,0x0c,0x91,0x08,0x10,0x04,0x0b,0x00,0x01, + 0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x07,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01, + 0x00,0xd4,0x1b,0x53,0x04,0x01,0x00,0x92,0x13,0x91,0x0f,0x10,0x04,0x01,0x00,0x01, + 0xff,0xe0,0xa4,0xa8,0xe0,0xa4,0xbc,0x00,0x01,0x00,0x01,0x00,0xd3,0x26,0xd2,0x13, + 0x91,0x0f,0x10,0x04,0x01,0x00,0x01,0xff,0xe0,0xa4,0xb0,0xe0,0xa4,0xbc,0x00,0x01, + 0x00,0x91,0x0f,0x10,0x0b,0x01,0xff,0xe0,0xa4,0xb3,0xe0,0xa4,0xbc,0x00,0x01,0x00, + 0x01,0x00,0xd2,0x08,0x11,0x04,0x01,0x00,0x0c,0x00,0x91,0x08,0x10,0x04,0x01,0x07, + 0x01,0x00,0x01,0x00,0xcf,0x86,0xd5,0x8c,0xd4,0x18,0x53,0x04,0x01,0x00,0x52,0x04, + 0x01,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x01,0x09,0x10,0x04,0x0b,0x00,0x0c,0x00, + 0xd3,0x1c,0xd2,0x10,0xd1,0x08,0x10,0x04,0x01,0x00,0x01,0xe6,0x10,0x04,0x01,0xdc, + 0x01,0xe6,0x91,0x08,0x10,0x04,0x01,0xe6,0x0b,0x00,0x0c,0x00,0xd2,0x2c,0xd1,0x16, + 0x10,0x0b,0x01,0xff,0xe0,0xa4,0x95,0xe0,0xa4,0xbc,0x00,0x01,0xff,0xe0,0xa4,0x96, + 0xe0,0xa4,0xbc,0x00,0x10,0x0b,0x01,0xff,0xe0,0xa4,0x97,0xe0,0xa4,0xbc,0x00,0x01, + 0xff,0xe0,0xa4,0x9c,0xe0,0xa4,0xbc,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xe0,0xa4, + 0xa1,0xe0,0xa4,0xbc,0x00,0x01,0xff,0xe0,0xa4,0xa2,0xe0,0xa4,0xbc,0x00,0x10,0x0b, + 0x01,0xff,0xe0,0xa4,0xab,0xe0,0xa4,0xbc,0x00,0x01,0xff,0xe0,0xa4,0xaf,0xe0,0xa4, + 0xbc,0x00,0x54,0x04,0x01,0x00,0xd3,0x14,0x92,0x10,0xd1,0x08,0x10,0x04,0x01,0x00, + 0x0a,0x00,0x10,0x04,0x0a,0x00,0x0c,0x00,0x0c,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04, + 0x10,0x00,0x0b,0x00,0x10,0x04,0x0b,0x00,0x09,0x00,0x91,0x08,0x10,0x04,0x09,0x00, + 0x08,0x00,0x09,0x00,0xd0,0x86,0xcf,0x86,0xd5,0x44,0xd4,0x2c,0xd3,0x18,0xd2,0x0c, + 0x91,0x08,0x10,0x04,0x10,0x00,0x01,0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x00,0x00, + 0x01,0x00,0x01,0x00,0x52,0x04,0x01,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x00,0x00, + 0x10,0x04,0x00,0x00,0x01,0x00,0x93,0x14,0x92,0x10,0xd1,0x08,0x10,0x04,0x01,0x00, + 0x00,0x00,0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd4,0x14,0x53,0x04, + 0x01,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x01,0x00, + 0xd3,0x18,0xd2,0x10,0xd1,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x10,0x04,0x01,0x00, + 0x00,0x00,0x11,0x04,0x00,0x00,0x01,0x00,0xd2,0x08,0x11,0x04,0x01,0x00,0x00,0x00, + 0x91,0x08,0x10,0x04,0x01,0x07,0x07,0x00,0x01,0x00,0xcf,0x86,0xd5,0x7b,0xd4,0x42, + 0xd3,0x14,0x52,0x04,0x01,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x10,0x04, + 0x00,0x00,0x01,0x00,0xd2,0x17,0xd1,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x10,0x04, + 0x00,0x00,0x01,0xff,0xe0,0xa7,0x87,0xe0,0xa6,0xbe,0x00,0xd1,0x0f,0x10,0x0b,0x01, + 0xff,0xe0,0xa7,0x87,0xe0,0xa7,0x97,0x00,0x01,0x09,0x10,0x04,0x08,0x00,0x00,0x00, + 0xd3,0x10,0x52,0x04,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x01,0x00, + 0x52,0x04,0x00,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xe0,0xa6,0xa1,0xe0,0xa6,0xbc, + 0x00,0x01,0xff,0xe0,0xa6,0xa2,0xe0,0xa6,0xbc,0x00,0x10,0x04,0x00,0x00,0x01,0xff, + 0xe0,0xa6,0xaf,0xe0,0xa6,0xbc,0x00,0xd4,0x10,0x93,0x0c,0x52,0x04,0x01,0x00,0x11, + 0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x53,0x04,0x01,0x00,0xd2,0x0c,0x51,0x04,0x01, + 0x00,0x10,0x04,0x01,0x00,0x0b,0x00,0x51,0x04,0x13,0x00,0x10,0x04,0x14,0xe6,0x00, + 0x00,0xe2,0x48,0x02,0xe1,0x4f,0x01,0xd0,0xa4,0xcf,0x86,0xd5,0x4c,0xd4,0x34,0xd3, + 0x1c,0xd2,0x10,0xd1,0x08,0x10,0x04,0x00,0x00,0x07,0x00,0x10,0x04,0x01,0x00,0x07, + 0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0xd2,0x0c,0x51,0x04,0x01, + 0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x01, + 0x00,0x93,0x14,0x92,0x10,0xd1,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x10,0x04,0x00, + 0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd4,0x14,0x53,0x04,0x01,0x00,0x92,0x0c,0x91, + 0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x01,0x00,0xd3,0x2e,0xd2,0x17,0xd1, + 0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x10,0x04,0x01,0x00,0x01,0xff,0xe0,0xa8,0xb2, + 0xe0,0xa8,0xbc,0x00,0xd1,0x08,0x10,0x04,0x00,0x00,0x01,0x00,0x10,0x0b,0x01,0xff, + 0xe0,0xa8,0xb8,0xe0,0xa8,0xbc,0x00,0x00,0x00,0xd2,0x08,0x11,0x04,0x01,0x00,0x00, + 0x00,0x91,0x08,0x10,0x04,0x01,0x07,0x00,0x00,0x01,0x00,0xcf,0x86,0xd5,0x80,0xd4, + 0x34,0xd3,0x18,0xd2,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x51, + 0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x01,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04,0x01, + 0x00,0x00,0x00,0x10,0x04,0x00,0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x01,0x00,0x01, + 0x09,0x00,0x00,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x0a,0x00,0x00, + 0x00,0x00,0x00,0xd2,0x25,0xd1,0x0f,0x10,0x04,0x00,0x00,0x01,0xff,0xe0,0xa8,0x96, + 0xe0,0xa8,0xbc,0x00,0x10,0x0b,0x01,0xff,0xe0,0xa8,0x97,0xe0,0xa8,0xbc,0x00,0x01, + 0xff,0xe0,0xa8,0x9c,0xe0,0xa8,0xbc,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x00,0x00, + 0x10,0x0b,0x01,0xff,0xe0,0xa8,0xab,0xe0,0xa8,0xbc,0x00,0x00,0x00,0xd4,0x10,0x93, + 0x0c,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x93,0x14,0x52, + 0x04,0x01,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x0a,0x00,0x10,0x04,0x14,0x00,0x00, + 0x00,0x00,0x00,0xd0,0x82,0xcf,0x86,0xd5,0x40,0xd4,0x2c,0xd3,0x18,0xd2,0x0c,0x91, + 0x08,0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x01, + 0x00,0x01,0x00,0x52,0x04,0x01,0x00,0xd1,0x08,0x10,0x04,0x07,0x00,0x01,0x00,0x10, + 0x04,0x00,0x00,0x01,0x00,0x93,0x10,0x92,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x00, + 0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd4,0x14,0x53,0x04,0x01,0x00,0x92,0x0c,0x91, + 0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x01,0x00,0xd3,0x18,0xd2,0x0c,0x91, + 0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x01, + 0x00,0x01,0x00,0xd2,0x08,0x11,0x04,0x01,0x00,0x00,0x00,0x91,0x08,0x10,0x04,0x01, + 0x07,0x01,0x00,0x01,0x00,0xcf,0x86,0xd5,0x3c,0xd4,0x28,0xd3,0x10,0x52,0x04,0x01, + 0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x00,0x00,0x01,0x00,0xd2,0x0c,0x51,0x04,0x01, + 0x00,0x10,0x04,0x00,0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x01,0x00,0x01,0x09,0x00, + 0x00,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x00,0x00,0x00, + 0x00,0x00,0x00,0xd4,0x18,0x93,0x14,0xd2,0x0c,0x91,0x08,0x10,0x04,0x01,0x00,0x07, + 0x00,0x07,0x00,0x11,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0xd3,0x10,0x92,0x0c,0x91, + 0x08,0x10,0x04,0x0d,0x00,0x07,0x00,0x00,0x00,0x00,0x00,0x92,0x0c,0x91,0x08,0x10, + 0x04,0x00,0x00,0x11,0x00,0x13,0x00,0x13,0x00,0xe1,0x24,0x01,0xd0,0x86,0xcf,0x86, + 0xd5,0x44,0xd4,0x2c,0xd3,0x18,0xd2,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x01,0x00, + 0x01,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x52,0x04,0x01,0x00, + 0xd1,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x10,0x04,0x00,0x00,0x01,0x00,0x93,0x14, + 0x92,0x10,0xd1,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x10,0x04,0x00,0x00,0x01,0x00, + 0x01,0x00,0x01,0x00,0xd4,0x14,0x53,0x04,0x01,0x00,0x92,0x0c,0x91,0x08,0x10,0x04, + 0x01,0x00,0x00,0x00,0x01,0x00,0x01,0x00,0xd3,0x18,0xd2,0x0c,0x91,0x08,0x10,0x04, + 0x01,0x00,0x00,0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x07,0x00,0x01,0x00, + 0xd2,0x08,0x11,0x04,0x01,0x00,0x00,0x00,0x91,0x08,0x10,0x04,0x01,0x07,0x01,0x00, + 0x01,0x00,0xcf,0x86,0xd5,0x73,0xd4,0x45,0xd3,0x14,0x52,0x04,0x01,0x00,0xd1,0x08, + 0x10,0x04,0x0a,0x00,0x00,0x00,0x10,0x04,0x00,0x00,0x01,0x00,0xd2,0x1e,0xd1,0x0f, + 0x10,0x0b,0x01,0xff,0xe0,0xad,0x87,0xe0,0xad,0x96,0x00,0x00,0x00,0x10,0x04,0x00, + 0x00,0x01,0xff,0xe0,0xad,0x87,0xe0,0xac,0xbe,0x00,0x91,0x0f,0x10,0x0b,0x01,0xff, + 0xe0,0xad,0x87,0xe0,0xad,0x97,0x00,0x01,0x09,0x00,0x00,0xd3,0x0c,0x52,0x04,0x00, + 0x00,0x11,0x04,0x00,0x00,0x01,0x00,0x52,0x04,0x00,0x00,0xd1,0x16,0x10,0x0b,0x01, + 0xff,0xe0,0xac,0xa1,0xe0,0xac,0xbc,0x00,0x01,0xff,0xe0,0xac,0xa2,0xe0,0xac,0xbc, + 0x00,0x10,0x04,0x00,0x00,0x01,0x00,0xd4,0x14,0x93,0x10,0xd2,0x08,0x11,0x04,0x01, + 0x00,0x0a,0x00,0x11,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x93,0x10,0x92,0x0c,0x91, + 0x08,0x10,0x04,0x01,0x00,0x07,0x00,0x0c,0x00,0x0c,0x00,0x00,0x00,0xd0,0xb1,0xcf, + 0x86,0xd5,0x63,0xd4,0x28,0xd3,0x14,0xd2,0x08,0x11,0x04,0x00,0x00,0x01,0x00,0x91, + 0x08,0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0xd2,0x0c,0x51,0x04,0x01,0x00,0x10, + 0x04,0x01,0x00,0x00,0x00,0x11,0x04,0x00,0x00,0x01,0x00,0xd3,0x1f,0xd2,0x0c,0x91, + 0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x91,0x0f,0x10,0x0b,0x01,0xff,0xe0, + 0xae,0x92,0xe0,0xaf,0x97,0x00,0x01,0x00,0x00,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04, + 0x00,0x00,0x01,0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x91,0x08,0x10,0x04,0x01,0x00, + 0x00,0x00,0x01,0x00,0xd4,0x2c,0xd3,0x18,0xd2,0x0c,0x51,0x04,0x00,0x00,0x10,0x04, + 0x00,0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x00,0x00,0xd2,0x0c, + 0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x11,0x04,0x00,0x00,0x01,0x00, + 0xd3,0x10,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x08,0x00,0x01,0x00, + 0xd2,0x08,0x11,0x04,0x01,0x00,0x00,0x00,0x11,0x04,0x00,0x00,0x01,0x00,0xcf,0x86, + 0xd5,0x61,0xd4,0x45,0xd3,0x14,0xd2,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00, + 0x00,0x00,0x11,0x04,0x00,0x00,0x01,0x00,0xd2,0x1e,0xd1,0x08,0x10,0x04,0x01,0x00, + 0x00,0x00,0x10,0x0b,0x01,0xff,0xe0,0xaf,0x86,0xe0,0xae,0xbe,0x00,0x01,0xff,0xe0, + 0xaf,0x87,0xe0,0xae,0xbe,0x00,0x91,0x0f,0x10,0x0b,0x01,0xff,0xe0,0xaf,0x86,0xe0, + 0xaf,0x97,0x00,0x01,0x09,0x00,0x00,0x93,0x18,0xd2,0x0c,0x91,0x08,0x10,0x04,0x0a, + 0x00,0x00,0x00,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x01,0x00,0x00, + 0x00,0xd4,0x14,0x93,0x10,0x52,0x04,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x08, + 0x00,0x01,0x00,0x01,0x00,0xd3,0x10,0x92,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01, + 0x00,0x07,0x00,0x07,0x00,0x92,0x0c,0x51,0x04,0x07,0x00,0x10,0x04,0x07,0x00,0x00, + 0x00,0x00,0x00,0xe3,0x1c,0x04,0xe2,0x1a,0x02,0xd1,0xf3,0xd0,0x76,0xcf,0x86,0xd5, + 0x3c,0xd4,0x28,0xd3,0x18,0xd2,0x0c,0x91,0x08,0x10,0x04,0x10,0x00,0x01,0x00,0x01, + 0x00,0x91,0x08,0x10,0x04,0x14,0x00,0x01,0x00,0x01,0x00,0x52,0x04,0x01,0x00,0x91, + 0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x93,0x10,0x92,0x0c,0x91,0x08,0x10, + 0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd4,0x14,0x53,0x04,0x01, + 0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x01,0x00,0xd3, + 0x10,0x52,0x04,0x01,0x00,0x91,0x08,0x10,0x04,0x10,0x00,0x01,0x00,0x01,0x00,0xd2, + 0x08,0x11,0x04,0x01,0x00,0x00,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x0a,0x00,0x01, + 0x00,0xcf,0x86,0xd5,0x53,0xd4,0x2f,0xd3,0x10,0x52,0x04,0x01,0x00,0x91,0x08,0x10, + 0x04,0x01,0x00,0x00,0x00,0x01,0x00,0xd2,0x13,0x91,0x0f,0x10,0x0b,0x01,0xff,0xe0, + 0xb1,0x86,0xe0,0xb1,0x96,0x00,0x00,0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x01,0x00, + 0x01,0x09,0x00,0x00,0xd3,0x14,0x52,0x04,0x00,0x00,0xd1,0x08,0x10,0x04,0x00,0x00, + 0x01,0x54,0x10,0x04,0x01,0x5b,0x00,0x00,0x92,0x0c,0x51,0x04,0x0a,0x00,0x10,0x04, + 0x11,0x00,0x00,0x00,0x00,0x00,0xd4,0x14,0x93,0x10,0xd2,0x08,0x11,0x04,0x01,0x00, + 0x0a,0x00,0x11,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x93,0x10,0x52,0x04,0x00,0x00, + 0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x15,0x00,0x0a,0x00,0xd0,0x76,0xcf,0x86, + 0xd5,0x3c,0xd4,0x28,0xd3,0x18,0xd2,0x0c,0x91,0x08,0x10,0x04,0x12,0x00,0x10,0x00, + 0x01,0x00,0x91,0x08,0x10,0x04,0x14,0x00,0x01,0x00,0x01,0x00,0x52,0x04,0x01,0x00, + 0x91,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x93,0x10,0x92,0x0c,0x91,0x08, + 0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd4,0x14,0x53,0x04, + 0x01,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x01,0x00, + 0xd3,0x10,0x52,0x04,0x01,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00, + 0xd2,0x08,0x11,0x04,0x01,0x00,0x00,0x00,0x91,0x08,0x10,0x04,0x07,0x07,0x07,0x00, + 0x01,0x00,0xcf,0x86,0xd5,0x82,0xd4,0x5e,0xd3,0x2a,0xd2,0x13,0x91,0x0f,0x10,0x0b, + 0x01,0xff,0xe0,0xb2,0xbf,0xe0,0xb3,0x95,0x00,0x01,0x00,0x01,0x00,0xd1,0x08,0x10, + 0x04,0x01,0x00,0x00,0x00,0x10,0x04,0x01,0x00,0x01,0xff,0xe0,0xb3,0x86,0xe0,0xb3, + 0x95,0x00,0xd2,0x28,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe0,0xb3,0x86,0xe0,0xb3,0x96, + 0x00,0x00,0x00,0x10,0x0b,0x01,0xff,0xe0,0xb3,0x86,0xe0,0xb3,0x82,0x00,0x01,0xff, + 0xe0,0xb3,0x86,0xe0,0xb3,0x82,0xe0,0xb3,0x95,0x00,0x91,0x08,0x10,0x04,0x01,0x00, + 0x01,0x09,0x00,0x00,0xd3,0x14,0x52,0x04,0x00,0x00,0xd1,0x08,0x10,0x04,0x00,0x00, + 0x01,0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x52,0x04,0x00,0x00,0x51,0x04,0x00,0x00, + 0x10,0x04,0x01,0x00,0x00,0x00,0xd4,0x14,0x93,0x10,0xd2,0x08,0x11,0x04,0x01,0x00, + 0x09,0x00,0x11,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x93,0x14,0x92,0x10,0xd1,0x08, + 0x10,0x04,0x00,0x00,0x09,0x00,0x10,0x04,0x09,0x00,0x00,0x00,0x00,0x00,0x00,0x00, + 0xe1,0x06,0x01,0xd0,0x6e,0xcf,0x86,0xd5,0x3c,0xd4,0x28,0xd3,0x18,0xd2,0x0c,0x91, + 0x08,0x10,0x04,0x13,0x00,0x10,0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x01, + 0x00,0x01,0x00,0x52,0x04,0x01,0x00,0x91,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01, + 0x00,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x01, + 0x00,0x01,0x00,0xd4,0x14,0x53,0x04,0x01,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x01, + 0x00,0x0c,0x00,0x01,0x00,0x01,0x00,0x53,0x04,0x01,0x00,0xd2,0x0c,0x51,0x04,0x01, + 0x00,0x10,0x04,0x0c,0x00,0x13,0x09,0x91,0x08,0x10,0x04,0x13,0x09,0x0a,0x00,0x01, + 0x00,0xcf,0x86,0xd5,0x65,0xd4,0x45,0xd3,0x10,0x52,0x04,0x01,0x00,0x91,0x08,0x10, + 0x04,0x0a,0x00,0x00,0x00,0x01,0x00,0xd2,0x1e,0xd1,0x08,0x10,0x04,0x01,0x00,0x00, + 0x00,0x10,0x0b,0x01,0xff,0xe0,0xb5,0x86,0xe0,0xb4,0xbe,0x00,0x01,0xff,0xe0,0xb5, + 0x87,0xe0,0xb4,0xbe,0x00,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe0,0xb5,0x86,0xe0,0xb5, + 0x97,0x00,0x01,0x09,0x10,0x04,0x0c,0x00,0x12,0x00,0xd3,0x10,0x52,0x04,0x00,0x00, + 0x51,0x04,0x12,0x00,0x10,0x04,0x12,0x00,0x01,0x00,0x52,0x04,0x12,0x00,0x51,0x04, + 0x12,0x00,0x10,0x04,0x12,0x00,0x11,0x00,0xd4,0x14,0x93,0x10,0xd2,0x08,0x11,0x04, + 0x01,0x00,0x0a,0x00,0x11,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0xd3,0x0c,0x52,0x04, + 0x0a,0x00,0x11,0x04,0x0a,0x00,0x12,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x12,0x00, + 0x0a,0x00,0x0a,0x00,0x0a,0x00,0xd0,0x5a,0xcf,0x86,0xd5,0x34,0xd4,0x18,0x93,0x14, + 0xd2,0x08,0x11,0x04,0x00,0x00,0x04,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x04,0x00, + 0x04,0x00,0x04,0x00,0xd3,0x10,0x52,0x04,0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x04, + 0x04,0x00,0x00,0x00,0x92,0x08,0x11,0x04,0x00,0x00,0x04,0x00,0x04,0x00,0x54,0x04, + 0x04,0x00,0xd3,0x10,0x92,0x0c,0x51,0x04,0x04,0x00,0x10,0x04,0x00,0x00,0x04,0x00, + 0x04,0x00,0x52,0x04,0x04,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x04,0x00,0x00,0x00, + 0xcf,0x86,0xd5,0x77,0xd4,0x28,0xd3,0x10,0x52,0x04,0x04,0x00,0x51,0x04,0x04,0x00, + 0x10,0x04,0x04,0x00,0x00,0x00,0xd2,0x0c,0x51,0x04,0x00,0x00,0x10,0x04,0x04,0x09, + 0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x04,0x00,0xd3,0x14,0x52,0x04, + 0x04,0x00,0xd1,0x08,0x10,0x04,0x04,0x00,0x00,0x00,0x10,0x04,0x04,0x00,0x00,0x00, + 0xd2,0x13,0x51,0x04,0x04,0x00,0x10,0x0b,0x04,0xff,0xe0,0xb7,0x99,0xe0,0xb7,0x8a, + 0x00,0x04,0x00,0xd1,0x19,0x10,0x0b,0x04,0xff,0xe0,0xb7,0x99,0xe0,0xb7,0x8f,0x00, + 0x04,0xff,0xe0,0xb7,0x99,0xe0,0xb7,0x8f,0xe0,0xb7,0x8a,0x00,0x10,0x0b,0x04,0xff, + 0xe0,0xb7,0x99,0xe0,0xb7,0x9f,0x00,0x04,0x00,0xd4,0x10,0x93,0x0c,0x52,0x04,0x00, + 0x00,0x11,0x04,0x00,0x00,0x10,0x00,0x10,0x00,0x93,0x14,0xd2,0x08,0x11,0x04,0x00, + 0x00,0x04,0x00,0x91,0x08,0x10,0x04,0x04,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xe2, + 0x31,0x01,0xd1,0x58,0xd0,0x3a,0xcf,0x86,0xd5,0x18,0x94,0x14,0x93,0x10,0x92,0x0c, + 0x91,0x08,0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00, + 0x54,0x04,0x01,0x00,0x53,0x04,0x01,0x00,0xd2,0x0c,0x51,0x04,0x01,0x67,0x10,0x04, + 0x01,0x09,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x01,0x00,0xcf,0x86, + 0x95,0x18,0xd4,0x0c,0x53,0x04,0x01,0x00,0x12,0x04,0x01,0x6b,0x01,0x00,0x53,0x04, + 0x01,0x00,0x12,0x04,0x01,0x00,0x00,0x00,0x00,0x00,0xd0,0x9e,0xcf,0x86,0xd5,0x54, + 0xd4,0x3c,0xd3,0x20,0xd2,0x10,0xd1,0x08,0x10,0x04,0x00,0x00,0x01,0x00,0x10,0x04, + 0x01,0x00,0x00,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x10,0x04,0x15,0x00, + 0x01,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04,0x01,0x00,0x15,0x00,0x10,0x04,0x01,0x00, + 0x00,0x00,0x91,0x08,0x10,0x04,0x15,0x00,0x01,0x00,0x15,0x00,0xd3,0x08,0x12,0x04, + 0x15,0x00,0x01,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x15,0x00,0x01,0x00,0x01,0x00, + 0x01,0x00,0xd4,0x30,0xd3,0x1c,0xd2,0x0c,0x91,0x08,0x10,0x04,0x15,0x00,0x01,0x00, + 0x01,0x00,0xd1,0x08,0x10,0x04,0x00,0x00,0x01,0x00,0x10,0x04,0x00,0x00,0x01,0x00, + 0xd2,0x08,0x11,0x04,0x15,0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x15,0x00,0x01,0x00, + 0x01,0x00,0x53,0x04,0x01,0x00,0xd2,0x0c,0x51,0x04,0x01,0x76,0x10,0x04,0x15,0x09, + 0x01,0x00,0x11,0x04,0x01,0x00,0x00,0x00,0xcf,0x86,0x95,0x34,0xd4,0x20,0xd3,0x14, + 0x52,0x04,0x01,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x10,0x04,0x01,0x00, + 0x00,0x00,0x52,0x04,0x01,0x7a,0x11,0x04,0x01,0x00,0x00,0x00,0x53,0x04,0x01,0x00, + 0xd2,0x08,0x11,0x04,0x01,0x00,0x00,0x00,0x11,0x04,0x01,0x00,0x0d,0x00,0x00,0x00, + 0xe1,0x2b,0x01,0xd0,0x3e,0xcf,0x86,0xd5,0x14,0x54,0x04,0x02,0x00,0x53,0x04,0x02, + 0x00,0x92,0x08,0x11,0x04,0x02,0xdc,0x02,0x00,0x02,0x00,0x54,0x04,0x02,0x00,0xd3, + 0x14,0x52,0x04,0x02,0x00,0xd1,0x08,0x10,0x04,0x02,0x00,0x02,0xdc,0x10,0x04,0x02, + 0x00,0x02,0xdc,0x92,0x0c,0x91,0x08,0x10,0x04,0x02,0x00,0x02,0xd8,0x02,0x00,0x02, + 0x00,0xcf,0x86,0xd5,0x73,0xd4,0x36,0xd3,0x17,0x92,0x13,0x51,0x04,0x02,0x00,0x10, + 0x04,0x02,0x00,0x02,0xff,0xe0,0xbd,0x82,0xe0,0xbe,0xb7,0x00,0x02,0x00,0xd2,0x0c, + 0x91,0x08,0x10,0x04,0x00,0x00,0x02,0x00,0x02,0x00,0x91,0x0f,0x10,0x04,0x02,0x00, + 0x02,0xff,0xe0,0xbd,0x8c,0xe0,0xbe,0xb7,0x00,0x02,0x00,0xd3,0x26,0xd2,0x13,0x51, + 0x04,0x02,0x00,0x10,0x0b,0x02,0xff,0xe0,0xbd,0x91,0xe0,0xbe,0xb7,0x00,0x02,0x00, + 0x51,0x04,0x02,0x00,0x10,0x04,0x02,0x00,0x02,0xff,0xe0,0xbd,0x96,0xe0,0xbe,0xb7, + 0x00,0x52,0x04,0x02,0x00,0x91,0x0f,0x10,0x0b,0x02,0xff,0xe0,0xbd,0x9b,0xe0,0xbe, + 0xb7,0x00,0x02,0x00,0x02,0x00,0xd4,0x27,0x53,0x04,0x02,0x00,0xd2,0x17,0xd1,0x0f, + 0x10,0x04,0x02,0x00,0x02,0xff,0xe0,0xbd,0x80,0xe0,0xbe,0xb5,0x00,0x10,0x04,0x04, + 0x00,0x0a,0x00,0x91,0x08,0x10,0x04,0x0a,0x00,0x00,0x00,0x00,0x00,0xd3,0x35,0xd2, + 0x17,0xd1,0x08,0x10,0x04,0x00,0x00,0x02,0x81,0x10,0x04,0x02,0x82,0x02,0xff,0xe0, + 0xbd,0xb1,0xe0,0xbd,0xb2,0x00,0xd1,0x0f,0x10,0x04,0x02,0x84,0x02,0xff,0xe0,0xbd, + 0xb1,0xe0,0xbd,0xb4,0x00,0x10,0x0b,0x02,0xff,0xe0,0xbe,0xb2,0xe0,0xbe,0x80,0x00, + 0x02,0x00,0xd2,0x13,0x91,0x0f,0x10,0x0b,0x02,0xff,0xe0,0xbe,0xb3,0xe0,0xbe,0x80, + 0x00,0x02,0x00,0x02,0x82,0x11,0x04,0x02,0x82,0x02,0x00,0xd0,0xd3,0xcf,0x86,0xd5, + 0x65,0xd4,0x27,0xd3,0x1f,0xd2,0x13,0x91,0x0f,0x10,0x04,0x02,0x82,0x02,0xff,0xe0, + 0xbd,0xb1,0xe0,0xbe,0x80,0x00,0x02,0xe6,0x91,0x08,0x10,0x04,0x02,0x09,0x02,0x00, + 0x02,0xe6,0x12,0x04,0x02,0x00,0x0c,0x00,0xd3,0x1f,0xd2,0x13,0x51,0x04,0x02,0x00, + 0x10,0x04,0x02,0x00,0x02,0xff,0xe0,0xbe,0x92,0xe0,0xbe,0xb7,0x00,0x51,0x04,0x02, + 0x00,0x10,0x04,0x04,0x00,0x02,0x00,0xd2,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x02, + 0x00,0x02,0x00,0x91,0x0f,0x10,0x04,0x02,0x00,0x02,0xff,0xe0,0xbe,0x9c,0xe0,0xbe, + 0xb7,0x00,0x02,0x00,0xd4,0x3d,0xd3,0x26,0xd2,0x13,0x51,0x04,0x02,0x00,0x10,0x0b, + 0x02,0xff,0xe0,0xbe,0xa1,0xe0,0xbe,0xb7,0x00,0x02,0x00,0x51,0x04,0x02,0x00,0x10, + 0x04,0x02,0x00,0x02,0xff,0xe0,0xbe,0xa6,0xe0,0xbe,0xb7,0x00,0x52,0x04,0x02,0x00, + 0x91,0x0f,0x10,0x0b,0x02,0xff,0xe0,0xbe,0xab,0xe0,0xbe,0xb7,0x00,0x02,0x00,0x04, + 0x00,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x04,0x00,0x02,0x00,0x02,0x00,0x02, + 0x00,0xd2,0x13,0x91,0x0f,0x10,0x04,0x04,0x00,0x02,0xff,0xe0,0xbe,0x90,0xe0,0xbe, + 0xb5,0x00,0x04,0x00,0x91,0x08,0x10,0x04,0x04,0x00,0x00,0x00,0x04,0x00,0xcf,0x86, + 0x95,0x4c,0xd4,0x24,0xd3,0x10,0x52,0x04,0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x04, + 0x04,0xdc,0x04,0x00,0x52,0x04,0x04,0x00,0xd1,0x08,0x10,0x04,0x04,0x00,0x00,0x00, + 0x10,0x04,0x0a,0x00,0x04,0x00,0xd3,0x14,0xd2,0x08,0x11,0x04,0x08,0x00,0x0a,0x00, + 0x91,0x08,0x10,0x04,0x0a,0x00,0x0b,0x00,0x0b,0x00,0x92,0x10,0xd1,0x08,0x10,0x04, + 0x0b,0x00,0x0c,0x00,0x10,0x04,0x0c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x86, + 0xe5,0xf7,0x04,0xe4,0x79,0x03,0xe3,0x7b,0x01,0xe2,0x04,0x01,0xd1,0x7f,0xd0,0x65, + 0xcf,0x86,0x55,0x04,0x04,0x00,0xd4,0x33,0xd3,0x1f,0xd2,0x0c,0x51,0x04,0x04,0x00, + 0x10,0x04,0x0a,0x00,0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x0b,0x04,0xff,0xe1,0x80, + 0xa5,0xe1,0x80,0xae,0x00,0x04,0x00,0x92,0x10,0xd1,0x08,0x10,0x04,0x0a,0x00,0x04, + 0x00,0x10,0x04,0x04,0x00,0x0a,0x00,0x04,0x00,0xd3,0x18,0xd2,0x0c,0x51,0x04,0x04, + 0x00,0x10,0x04,0x04,0x00,0x0a,0x00,0x51,0x04,0x0a,0x00,0x10,0x04,0x04,0x00,0x04, + 0x07,0x92,0x10,0xd1,0x08,0x10,0x04,0x04,0x00,0x04,0x09,0x10,0x04,0x0a,0x09,0x0a, + 0x00,0x0a,0x00,0xcf,0x86,0x95,0x14,0x54,0x04,0x04,0x00,0x53,0x04,0x04,0x00,0x92, + 0x08,0x11,0x04,0x04,0x00,0x0a,0x00,0x0a,0x00,0x0a,0x00,0xd0,0x2e,0xcf,0x86,0x95, + 0x28,0xd4,0x14,0x53,0x04,0x0a,0x00,0x52,0x04,0x0a,0x00,0x91,0x08,0x10,0x04,0x0a, + 0x00,0x0a,0xdc,0x0a,0x00,0x53,0x04,0x0a,0x00,0xd2,0x08,0x11,0x04,0x0a,0x00,0x0b, + 0x00,0x11,0x04,0x0b,0x00,0x0a,0x00,0x01,0x00,0xcf,0x86,0xd5,0x24,0x94,0x20,0xd3, + 0x10,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x00,0x00,0x0d,0x00,0x52, + 0x04,0x00,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x0d,0x00,0x00,0x00,0x01,0x00,0x54, + 0x04,0x01,0x00,0xd3,0x10,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01, + 0x00,0x06,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04,0x06,0x00,0x08,0x00,0x10,0x04,0x08, + 0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x08,0x00,0x0d,0x00,0x0d,0x00,0xd1,0x3e,0xd0, + 0x06,0xcf,0x06,0x01,0x00,0xcf,0x86,0xd5,0x1d,0x54,0x04,0x01,0x00,0x53,0x04,0x01, + 0x00,0xd2,0x08,0x11,0x04,0x01,0x00,0x0b,0x00,0x51,0x04,0x0b,0x00,0x10,0x04,0x0b, + 0x00,0x01,0xff,0x00,0x94,0x15,0x93,0x11,0x92,0x0d,0x91,0x09,0x10,0x05,0x01,0xff, + 0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd0,0x1e,0xcf,0x86,0x55, + 0x04,0x01,0x00,0x94,0x14,0x93,0x10,0x92,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01, + 0x00,0x0b,0x00,0x0b,0x00,0x01,0x00,0x01,0x00,0xcf,0x86,0x55,0x04,0x01,0x00,0x54, + 0x04,0x01,0x00,0x53,0x04,0x01,0x00,0x92,0x08,0x11,0x04,0x01,0x00,0x0b,0x00,0x0b, + 0x00,0xe2,0x21,0x01,0xd1,0x6c,0xd0,0x1e,0xcf,0x86,0x95,0x18,0x94,0x14,0x93,0x10, + 0x52,0x04,0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x08,0x00,0x04,0x00, + 0x04,0x00,0x04,0x00,0xcf,0x86,0x95,0x48,0xd4,0x24,0xd3,0x10,0x52,0x04,0x04,0x00, + 0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x08,0x00,0xd2,0x0c,0x91,0x08,0x10,0x04, + 0x04,0x00,0x00,0x00,0x04,0x00,0x11,0x04,0x04,0x00,0x00,0x00,0xd3,0x10,0x52,0x04, + 0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x00,0x00,0xd2,0x0c,0x91,0x08, + 0x10,0x04,0x04,0x00,0x00,0x00,0x04,0x00,0x11,0x04,0x04,0x00,0x00,0x00,0x04,0x00, + 0xd0,0x62,0xcf,0x86,0xd5,0x28,0x94,0x24,0xd3,0x10,0x52,0x04,0x04,0x00,0x51,0x04, + 0x04,0x00,0x10,0x04,0x04,0x00,0x08,0x00,0xd2,0x0c,0x91,0x08,0x10,0x04,0x04,0x00, + 0x00,0x00,0x04,0x00,0x11,0x04,0x04,0x00,0x00,0x00,0x04,0x00,0xd4,0x14,0x53,0x04, + 0x04,0x00,0x52,0x04,0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x08,0x00, + 0xd3,0x14,0xd2,0x0c,0x91,0x08,0x10,0x04,0x04,0x00,0x00,0x00,0x04,0x00,0x11,0x04, + 0x04,0x00,0x00,0x00,0x52,0x04,0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00, + 0x00,0x00,0xcf,0x86,0xd5,0x38,0xd4,0x24,0xd3,0x14,0xd2,0x0c,0x91,0x08,0x10,0x04, + 0x04,0x00,0x00,0x00,0x04,0x00,0x11,0x04,0x04,0x00,0x00,0x00,0x52,0x04,0x04,0x00, + 0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x08,0x00,0x93,0x10,0x52,0x04,0x04,0x00, + 0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x00,0x00,0x04,0x00,0x94,0x14,0x53,0x04, + 0x04,0x00,0x52,0x04,0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x08,0x00, + 0x04,0x00,0xd1,0x9c,0xd0,0x3e,0xcf,0x86,0x95,0x38,0xd4,0x14,0x53,0x04,0x04,0x00, + 0x52,0x04,0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x08,0x00,0xd3,0x14, + 0xd2,0x0c,0x91,0x08,0x10,0x04,0x04,0x00,0x00,0x00,0x04,0x00,0x11,0x04,0x04,0x00, + 0x00,0x00,0x52,0x04,0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x08,0x00, + 0x04,0x00,0xcf,0x86,0xd5,0x34,0xd4,0x14,0x93,0x10,0x52,0x04,0x04,0x00,0x51,0x04, + 0x04,0x00,0x10,0x04,0x04,0x00,0x08,0x00,0x04,0x00,0x53,0x04,0x04,0x00,0xd2,0x0c, + 0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x00,0x00,0xd1,0x08,0x10,0x04,0x00,0x00, + 0x0c,0xe6,0x10,0x04,0x0c,0xe6,0x08,0xe6,0xd4,0x14,0x93,0x10,0x92,0x0c,0x91,0x08, + 0x10,0x04,0x08,0x00,0x04,0x00,0x04,0x00,0x04,0x00,0x04,0x00,0x53,0x04,0x04,0x00, + 0x52,0x04,0x04,0x00,0x91,0x08,0x10,0x04,0x04,0x00,0x00,0x00,0x00,0x00,0xd0,0x1a, + 0xcf,0x86,0x95,0x14,0x54,0x04,0x08,0x00,0x53,0x04,0x08,0x00,0x92,0x08,0x11,0x04, + 0x08,0x00,0x00,0x00,0x00,0x00,0x04,0x00,0xcf,0x86,0x55,0x04,0x04,0x00,0x54,0x04, + 0x04,0x00,0xd3,0x10,0x52,0x04,0x04,0x00,0x91,0x08,0x10,0x04,0x04,0x00,0x11,0x00, + 0x00,0x00,0x52,0x04,0x11,0x00,0x11,0x04,0x11,0x00,0x00,0x00,0xd3,0x30,0xd2,0x2a, + 0xd1,0x24,0xd0,0x1e,0xcf,0x86,0x95,0x18,0x94,0x14,0x93,0x10,0x92,0x0c,0x91,0x08, + 0x10,0x04,0x0b,0x00,0x04,0x00,0x04,0x00,0x04,0x00,0x04,0x00,0x04,0x00,0x04,0x00, + 0xcf,0x06,0x04,0x00,0xcf,0x06,0x04,0x00,0xcf,0x06,0x04,0x00,0xd2,0x6c,0xd1,0x24, + 0xd0,0x06,0xcf,0x06,0x04,0x00,0xcf,0x86,0x55,0x04,0x04,0x00,0x54,0x04,0x04,0x00, + 0x93,0x10,0x52,0x04,0x04,0x00,0x51,0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x0b,0x00, + 0x0b,0x00,0xd0,0x1e,0xcf,0x86,0x95,0x18,0x54,0x04,0x04,0x00,0x53,0x04,0x04,0x00, + 0x52,0x04,0x04,0x00,0x91,0x08,0x10,0x04,0x04,0x00,0x00,0x00,0x00,0x00,0x04,0x00, + 0xcf,0x86,0x55,0x04,0x04,0x00,0x54,0x04,0x04,0x00,0xd3,0x10,0x92,0x0c,0x91,0x08, + 0x10,0x04,0x04,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x92,0x0c,0x91,0x08,0x10,0x04, + 0x10,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd1,0x80,0xd0,0x46,0xcf,0x86,0xd5,0x28, + 0xd4,0x14,0x53,0x04,0x06,0x00,0x52,0x04,0x06,0x00,0x91,0x08,0x10,0x04,0x06,0x00, + 0x00,0x00,0x06,0x00,0x93,0x10,0x52,0x04,0x06,0x00,0x91,0x08,0x10,0x04,0x06,0x09, + 0x00,0x00,0x00,0x00,0x00,0x00,0x54,0x04,0x06,0x00,0x93,0x14,0x52,0x04,0x06,0x00, + 0xd1,0x08,0x10,0x04,0x06,0x09,0x06,0x00,0x10,0x04,0x06,0x00,0x00,0x00,0x00,0x00, + 0xcf,0x86,0xd5,0x10,0x54,0x04,0x06,0x00,0x93,0x08,0x12,0x04,0x06,0x00,0x00,0x00, + 0x00,0x00,0xd4,0x14,0x53,0x04,0x06,0x00,0x52,0x04,0x06,0x00,0x91,0x08,0x10,0x04, + 0x06,0x00,0x00,0x00,0x06,0x00,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x06,0x00, + 0x00,0x00,0x06,0x00,0x00,0x00,0x00,0x00,0xd0,0x1b,0xcf,0x86,0x55,0x04,0x04,0x00, + 0x54,0x04,0x04,0x00,0x93,0x0d,0x52,0x04,0x04,0x00,0x11,0x05,0x04,0xff,0x00,0x04, + 0x00,0x04,0x00,0xcf,0x86,0xd5,0x24,0x54,0x04,0x04,0x00,0xd3,0x10,0x92,0x0c,0x51, + 0x04,0x04,0x00,0x10,0x04,0x04,0x09,0x04,0x00,0x04,0x00,0x52,0x04,0x04,0x00,0x91, + 0x08,0x10,0x04,0x04,0x00,0x07,0xe6,0x00,0x00,0xd4,0x10,0x53,0x04,0x04,0x00,0x92, + 0x08,0x11,0x04,0x04,0x00,0x00,0x00,0x00,0x00,0x53,0x04,0x07,0x00,0x92,0x08,0x11, + 0x04,0x07,0x00,0x00,0x00,0x00,0x00,0xe4,0xb7,0x03,0xe3,0x58,0x01,0xd2,0x8f,0xd1, + 0x53,0xd0,0x35,0xcf,0x86,0x95,0x2f,0xd4,0x1f,0x53,0x04,0x04,0x00,0xd2,0x0d,0x51, + 0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x04,0xff,0x00,0x51,0x05,0x04,0xff,0x00,0x10, + 0x05,0x04,0xff,0x00,0x00,0x00,0x53,0x04,0x04,0x00,0x92,0x08,0x11,0x04,0x04,0x00, + 0x00,0x00,0x00,0x00,0x04,0x00,0xcf,0x86,0x55,0x04,0x04,0x00,0x54,0x04,0x04,0x00, + 0x53,0x04,0x04,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x14,0x00,0x00,0x00,0x00,0x00, + 0x00,0x00,0xd0,0x22,0xcf,0x86,0x55,0x04,0x04,0x00,0x94,0x18,0x53,0x04,0x04,0x00, + 0x92,0x10,0xd1,0x08,0x10,0x04,0x04,0x00,0x04,0xe4,0x10,0x04,0x0a,0x00,0x00,0x00, + 0x00,0x00,0x0b,0x00,0xcf,0x86,0x55,0x04,0x0b,0x00,0x54,0x04,0x0b,0x00,0x93,0x0c, + 0x52,0x04,0x0b,0x00,0x11,0x04,0x0b,0x00,0x00,0x00,0x00,0x00,0xd1,0x80,0xd0,0x42, + 0xcf,0x86,0xd5,0x1c,0x54,0x04,0x07,0x00,0x53,0x04,0x07,0x00,0x52,0x04,0x07,0x00, + 0xd1,0x08,0x10,0x04,0x07,0x00,0x10,0x00,0x10,0x04,0x10,0x00,0x00,0x00,0xd4,0x0c, + 0x53,0x04,0x07,0x00,0x12,0x04,0x07,0x00,0x00,0x00,0x53,0x04,0x07,0x00,0x92,0x10, + 0xd1,0x08,0x10,0x04,0x07,0x00,0x07,0xde,0x10,0x04,0x07,0xe6,0x07,0xdc,0x00,0x00, + 0xcf,0x86,0xd5,0x18,0x94,0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x07,0x00, + 0x00,0x00,0x00,0x00,0x07,0x00,0x07,0x00,0x07,0x00,0xd4,0x10,0x53,0x04,0x07,0x00, + 0x52,0x04,0x07,0x00,0x11,0x04,0x07,0x00,0x00,0x00,0x93,0x10,0x52,0x04,0x07,0x00, + 0x91,0x08,0x10,0x04,0x07,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd0,0x1a,0xcf,0x86, + 0x55,0x04,0x08,0x00,0x94,0x10,0x53,0x04,0x08,0x00,0x92,0x08,0x11,0x04,0x08,0x00, + 0x0b,0x00,0x00,0x00,0x08,0x00,0xcf,0x86,0x95,0x28,0xd4,0x10,0x53,0x04,0x08,0x00, + 0x92,0x08,0x11,0x04,0x08,0x00,0x00,0x00,0x00,0x00,0x53,0x04,0x08,0x00,0xd2,0x0c, + 0x51,0x04,0x08,0x00,0x10,0x04,0x0b,0x00,0x00,0x00,0x11,0x04,0x00,0x00,0x08,0x00, + 0x07,0x00,0xd2,0xe4,0xd1,0x80,0xd0,0x2e,0xcf,0x86,0x95,0x28,0x54,0x04,0x08,0x00, + 0xd3,0x10,0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x08,0xe6, + 0xd2,0x0c,0x91,0x08,0x10,0x04,0x08,0xdc,0x08,0x00,0x08,0x00,0x11,0x04,0x00,0x00, + 0x08,0x00,0x0b,0x00,0xcf,0x86,0xd5,0x18,0x54,0x04,0x0b,0x00,0x53,0x04,0x0b,0x00, + 0x52,0x04,0x0b,0x00,0x51,0x04,0x0b,0x00,0x10,0x04,0x0b,0x00,0x00,0x00,0xd4,0x14, + 0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x0b,0x09,0x0b,0x00,0x0b,0x00,0x0b,0x00, + 0x0b,0x00,0xd3,0x10,0x52,0x04,0x0b,0x00,0x91,0x08,0x10,0x04,0x0b,0x00,0x0b,0xe6, + 0x0b,0xe6,0x52,0x04,0x0b,0xe6,0xd1,0x08,0x10,0x04,0x0b,0xe6,0x00,0x00,0x10,0x04, + 0x00,0x00,0x0b,0xdc,0xd0,0x5e,0xcf,0x86,0xd5,0x20,0xd4,0x10,0x53,0x04,0x0b,0x00, + 0x92,0x08,0x11,0x04,0x0b,0x00,0x00,0x00,0x00,0x00,0x53,0x04,0x0b,0x00,0x92,0x08, + 0x11,0x04,0x0b,0x00,0x00,0x00,0x00,0x00,0xd4,0x10,0x53,0x04,0x0b,0x00,0x52,0x04, + 0x0b,0x00,0x11,0x04,0x0b,0x00,0x00,0x00,0xd3,0x10,0x52,0x04,0x10,0xe6,0x91,0x08, + 0x10,0x04,0x10,0xe6,0x10,0xdc,0x10,0xdc,0xd2,0x0c,0x51,0x04,0x10,0xdc,0x10,0x04, + 0x10,0xdc,0x10,0xe6,0xd1,0x08,0x10,0x04,0x10,0xe6,0x10,0xdc,0x10,0x04,0x10,0x00, + 0x00,0x00,0xcf,0x06,0x00,0x00,0xe1,0x1e,0x01,0xd0,0xaa,0xcf,0x86,0xd5,0x6e,0xd4, + 0x53,0xd3,0x17,0x52,0x04,0x09,0x00,0x51,0x04,0x09,0x00,0x10,0x0b,0x09,0xff,0xe1, + 0xac,0x85,0xe1,0xac,0xb5,0x00,0x09,0x00,0xd2,0x1e,0xd1,0x0f,0x10,0x0b,0x09,0xff, + 0xe1,0xac,0x87,0xe1,0xac,0xb5,0x00,0x09,0x00,0x10,0x0b,0x09,0xff,0xe1,0xac,0x89, + 0xe1,0xac,0xb5,0x00,0x09,0x00,0xd1,0x0f,0x10,0x0b,0x09,0xff,0xe1,0xac,0x8b,0xe1, + 0xac,0xb5,0x00,0x09,0x00,0x10,0x0b,0x09,0xff,0xe1,0xac,0x8d,0xe1,0xac,0xb5,0x00, + 0x09,0x00,0x93,0x17,0x92,0x13,0x51,0x04,0x09,0x00,0x10,0x0b,0x09,0xff,0xe1,0xac, + 0x91,0xe1,0xac,0xb5,0x00,0x09,0x00,0x09,0x00,0x09,0x00,0x54,0x04,0x09,0x00,0xd3, + 0x10,0x52,0x04,0x09,0x00,0x91,0x08,0x10,0x04,0x09,0x07,0x09,0x00,0x09,0x00,0xd2, + 0x13,0x51,0x04,0x09,0x00,0x10,0x04,0x09,0x00,0x09,0xff,0xe1,0xac,0xba,0xe1,0xac, + 0xb5,0x00,0x91,0x0f,0x10,0x04,0x09,0x00,0x09,0xff,0xe1,0xac,0xbc,0xe1,0xac,0xb5, + 0x00,0x09,0x00,0xcf,0x86,0xd5,0x3d,0x94,0x39,0xd3,0x31,0xd2,0x25,0xd1,0x16,0x10, + 0x0b,0x09,0xff,0xe1,0xac,0xbe,0xe1,0xac,0xb5,0x00,0x09,0xff,0xe1,0xac,0xbf,0xe1, + 0xac,0xb5,0x00,0x10,0x04,0x09,0x00,0x09,0xff,0xe1,0xad,0x82,0xe1,0xac,0xb5,0x00, + 0x91,0x08,0x10,0x04,0x09,0x09,0x09,0x00,0x09,0x00,0x12,0x04,0x09,0x00,0x00,0x00, + 0x09,0x00,0xd4,0x1c,0x53,0x04,0x09,0x00,0xd2,0x0c,0x51,0x04,0x09,0x00,0x10,0x04, + 0x09,0x00,0x09,0xe6,0x91,0x08,0x10,0x04,0x09,0xdc,0x09,0xe6,0x09,0xe6,0xd3,0x08, + 0x12,0x04,0x09,0xe6,0x09,0x00,0x52,0x04,0x09,0x00,0x91,0x08,0x10,0x04,0x09,0x00, + 0x00,0x00,0x00,0x00,0xd0,0x2e,0xcf,0x86,0x55,0x04,0x0a,0x00,0xd4,0x18,0x53,0x04, + 0x0a,0x00,0xd2,0x0c,0x51,0x04,0x0a,0x00,0x10,0x04,0x0a,0x09,0x0d,0x09,0x11,0x04, + 0x0d,0x00,0x0a,0x00,0x53,0x04,0x0a,0x00,0x92,0x08,0x11,0x04,0x0a,0x00,0x0d,0x00, + 0x0d,0x00,0xcf,0x86,0x55,0x04,0x0c,0x00,0xd4,0x14,0x93,0x10,0x52,0x04,0x0c,0x00, + 0x51,0x04,0x0c,0x00,0x10,0x04,0x0c,0x07,0x0c,0x00,0x0c,0x00,0xd3,0x0c,0x92,0x08, + 0x11,0x04,0x0c,0x00,0x0c,0x09,0x00,0x00,0x12,0x04,0x00,0x00,0x0c,0x00,0xe3,0xb2, + 0x01,0xe2,0x09,0x01,0xd1,0x4c,0xd0,0x2a,0xcf,0x86,0x55,0x04,0x0a,0x00,0x54,0x04, + 0x0a,0x00,0xd3,0x10,0x52,0x04,0x0a,0x00,0x51,0x04,0x0a,0x00,0x10,0x04,0x0a,0x00, + 0x0a,0x07,0x92,0x0c,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x0a,0x00,0x0a,0x00, + 0xcf,0x86,0x95,0x1c,0x94,0x18,0x53,0x04,0x0a,0x00,0xd2,0x08,0x11,0x04,0x0a,0x00, + 0x00,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x0a,0x00,0x0a,0x00,0x0a,0x00,0x0a,0x00, + 0xd0,0x3a,0xcf,0x86,0xd5,0x18,0x94,0x14,0x53,0x04,0x12,0x00,0x92,0x0c,0x91,0x08, + 0x10,0x04,0x12,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x14,0x00,0x54,0x04,0x14,0x00, + 0x53,0x04,0x14,0x00,0xd2,0x0c,0x51,0x04,0x14,0x00,0x10,0x04,0x14,0x00,0x00,0x00, + 0x91,0x08,0x10,0x04,0x00,0x00,0x14,0x00,0x14,0x00,0xcf,0x86,0xd5,0x2c,0xd4,0x08, + 0x13,0x04,0x0d,0x00,0x00,0x00,0xd3,0x18,0xd2,0x0c,0x51,0x04,0x0b,0xe6,0x10,0x04, + 0x0b,0xe6,0x0b,0x00,0x91,0x08,0x10,0x04,0x0b,0x01,0x0b,0xdc,0x0b,0xdc,0x92,0x08, + 0x11,0x04,0x0b,0xdc,0x0b,0xe6,0x0b,0xdc,0xd4,0x28,0xd3,0x10,0x92,0x0c,0x91,0x08, + 0x10,0x04,0x0b,0xe6,0x0b,0x00,0x0b,0x01,0x0b,0x01,0xd2,0x0c,0x91,0x08,0x10,0x04, + 0x0b,0x01,0x0b,0x00,0x0b,0x00,0x91,0x08,0x10,0x04,0x0b,0x00,0x0b,0xdc,0x0b,0x00, + 0xd3,0x1c,0xd2,0x0c,0x51,0x04,0x0b,0x00,0x10,0x04,0x0b,0x00,0x0d,0x00,0xd1,0x08, + 0x10,0x04,0x0d,0xe6,0x0d,0x00,0x10,0x04,0x0d,0x00,0x13,0x00,0x92,0x0c,0x51,0x04, + 0x10,0xe6,0x10,0x04,0x15,0x00,0x00,0x00,0x00,0x00,0xd1,0x1c,0xd0,0x06,0xcf,0x06, + 0x07,0x00,0xcf,0x86,0x55,0x04,0x07,0x00,0x94,0x0c,0x53,0x04,0x07,0x00,0x12,0x04, + 0x07,0x00,0x08,0x00,0x08,0x00,0xd0,0x06,0xcf,0x06,0x08,0x00,0xcf,0x86,0xd5,0x40, + 0xd4,0x2c,0xd3,0x10,0x92,0x0c,0x51,0x04,0x08,0xe6,0x10,0x04,0x08,0xdc,0x08,0xe6, + 0x09,0xe6,0xd2,0x0c,0x51,0x04,0x09,0xe6,0x10,0x04,0x09,0xdc,0x0a,0xe6,0xd1,0x08, + 0x10,0x04,0x0a,0xe6,0x0a,0xea,0x10,0x04,0x0a,0xd6,0x0a,0xdc,0x93,0x10,0x92,0x0c, + 0x91,0x08,0x10,0x04,0x0a,0xca,0x0a,0xe6,0x0a,0xe6,0x0a,0xe6,0x0a,0xe6,0xd4,0x14, + 0x93,0x10,0x52,0x04,0x0a,0xe6,0x51,0x04,0x0a,0xe6,0x10,0x04,0x0a,0xe6,0x10,0xe6, + 0x10,0xe6,0xd3,0x10,0x52,0x04,0x10,0xe6,0x51,0x04,0x10,0xe6,0x10,0x04,0x13,0xe8, + 0x13,0xe4,0xd2,0x10,0xd1,0x08,0x10,0x04,0x13,0xe4,0x13,0xdc,0x10,0x04,0x00,0x00, + 0x12,0xe6,0xd1,0x08,0x10,0x04,0x0c,0xe9,0x0b,0xdc,0x10,0x04,0x09,0xe6,0x09,0xdc, + 0xe2,0x80,0x08,0xe1,0x48,0x04,0xe0,0x1c,0x02,0xcf,0x86,0xe5,0x11,0x01,0xd4,0x84, + 0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x41,0xcc,0xa5,0x00,0x01,0xff, + 0x61,0xcc,0xa5,0x00,0x10,0x08,0x01,0xff,0x42,0xcc,0x87,0x00,0x01,0xff,0x62,0xcc, + 0x87,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x42,0xcc,0xa3,0x00,0x01,0xff,0x62,0xcc, + 0xa3,0x00,0x10,0x08,0x01,0xff,0x42,0xcc,0xb1,0x00,0x01,0xff,0x62,0xcc,0xb1,0x00, + 0xd2,0x24,0xd1,0x14,0x10,0x0a,0x01,0xff,0x43,0xcc,0xa7,0xcc,0x81,0x00,0x01,0xff, + 0x63,0xcc,0xa7,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x44,0xcc,0x87,0x00,0x01,0xff, + 0x64,0xcc,0x87,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x44,0xcc,0xa3,0x00,0x01,0xff, + 0x64,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x44,0xcc,0xb1,0x00,0x01,0xff,0x64,0xcc, + 0xb1,0x00,0xd3,0x48,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x44,0xcc,0xa7,0x00, + 0x01,0xff,0x64,0xcc,0xa7,0x00,0x10,0x08,0x01,0xff,0x44,0xcc,0xad,0x00,0x01,0xff, + 0x64,0xcc,0xad,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x45,0xcc,0x84,0xcc,0x80,0x00, + 0x01,0xff,0x65,0xcc,0x84,0xcc,0x80,0x00,0x10,0x0a,0x01,0xff,0x45,0xcc,0x84,0xcc, + 0x81,0x00,0x01,0xff,0x65,0xcc,0x84,0xcc,0x81,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08, + 0x01,0xff,0x45,0xcc,0xad,0x00,0x01,0xff,0x65,0xcc,0xad,0x00,0x10,0x08,0x01,0xff, + 0x45,0xcc,0xb0,0x00,0x01,0xff,0x65,0xcc,0xb0,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff, + 0x45,0xcc,0xa7,0xcc,0x86,0x00,0x01,0xff,0x65,0xcc,0xa7,0xcc,0x86,0x00,0x10,0x08, + 0x01,0xff,0x46,0xcc,0x87,0x00,0x01,0xff,0x66,0xcc,0x87,0x00,0xd4,0x84,0xd3,0x40, + 0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x47,0xcc,0x84,0x00,0x01,0xff,0x67,0xcc, + 0x84,0x00,0x10,0x08,0x01,0xff,0x48,0xcc,0x87,0x00,0x01,0xff,0x68,0xcc,0x87,0x00, + 0xd1,0x10,0x10,0x08,0x01,0xff,0x48,0xcc,0xa3,0x00,0x01,0xff,0x68,0xcc,0xa3,0x00, + 0x10,0x08,0x01,0xff,0x48,0xcc,0x88,0x00,0x01,0xff,0x68,0xcc,0x88,0x00,0xd2,0x20, + 0xd1,0x10,0x10,0x08,0x01,0xff,0x48,0xcc,0xa7,0x00,0x01,0xff,0x68,0xcc,0xa7,0x00, + 0x10,0x08,0x01,0xff,0x48,0xcc,0xae,0x00,0x01,0xff,0x68,0xcc,0xae,0x00,0xd1,0x10, + 0x10,0x08,0x01,0xff,0x49,0xcc,0xb0,0x00,0x01,0xff,0x69,0xcc,0xb0,0x00,0x10,0x0a, + 0x01,0xff,0x49,0xcc,0x88,0xcc,0x81,0x00,0x01,0xff,0x69,0xcc,0x88,0xcc,0x81,0x00, + 0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x4b,0xcc,0x81,0x00,0x01,0xff, + 0x6b,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x4b,0xcc,0xa3,0x00,0x01,0xff,0x6b,0xcc, + 0xa3,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x4b,0xcc,0xb1,0x00,0x01,0xff,0x6b,0xcc, + 0xb1,0x00,0x10,0x08,0x01,0xff,0x4c,0xcc,0xa3,0x00,0x01,0xff,0x6c,0xcc,0xa3,0x00, + 0xd2,0x24,0xd1,0x14,0x10,0x0a,0x01,0xff,0x4c,0xcc,0xa3,0xcc,0x84,0x00,0x01,0xff, + 0x6c,0xcc,0xa3,0xcc,0x84,0x00,0x10,0x08,0x01,0xff,0x4c,0xcc,0xb1,0x00,0x01,0xff, + 0x6c,0xcc,0xb1,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x4c,0xcc,0xad,0x00,0x01,0xff, + 0x6c,0xcc,0xad,0x00,0x10,0x08,0x01,0xff,0x4d,0xcc,0x81,0x00,0x01,0xff,0x6d,0xcc, + 0x81,0x00,0xcf,0x86,0xe5,0x15,0x01,0xd4,0x88,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10, + 0x08,0x01,0xff,0x4d,0xcc,0x87,0x00,0x01,0xff,0x6d,0xcc,0x87,0x00,0x10,0x08,0x01, + 0xff,0x4d,0xcc,0xa3,0x00,0x01,0xff,0x6d,0xcc,0xa3,0x00,0xd1,0x10,0x10,0x08,0x01, + 0xff,0x4e,0xcc,0x87,0x00,0x01,0xff,0x6e,0xcc,0x87,0x00,0x10,0x08,0x01,0xff,0x4e, + 0xcc,0xa3,0x00,0x01,0xff,0x6e,0xcc,0xa3,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01, + 0xff,0x4e,0xcc,0xb1,0x00,0x01,0xff,0x6e,0xcc,0xb1,0x00,0x10,0x08,0x01,0xff,0x4e, + 0xcc,0xad,0x00,0x01,0xff,0x6e,0xcc,0xad,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x4f, + 0xcc,0x83,0xcc,0x81,0x00,0x01,0xff,0x6f,0xcc,0x83,0xcc,0x81,0x00,0x10,0x0a,0x01, + 0xff,0x4f,0xcc,0x83,0xcc,0x88,0x00,0x01,0xff,0x6f,0xcc,0x83,0xcc,0x88,0x00,0xd3, + 0x48,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x4f,0xcc,0x84,0xcc,0x80,0x00,0x01, + 0xff,0x6f,0xcc,0x84,0xcc,0x80,0x00,0x10,0x0a,0x01,0xff,0x4f,0xcc,0x84,0xcc,0x81, + 0x00,0x01,0xff,0x6f,0xcc,0x84,0xcc,0x81,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x50, + 0xcc,0x81,0x00,0x01,0xff,0x70,0xcc,0x81,0x00,0x10,0x08,0x01,0xff,0x50,0xcc,0x87, + 0x00,0x01,0xff,0x70,0xcc,0x87,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x52, + 0xcc,0x87,0x00,0x01,0xff,0x72,0xcc,0x87,0x00,0x10,0x08,0x01,0xff,0x52,0xcc,0xa3, + 0x00,0x01,0xff,0x72,0xcc,0xa3,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x52,0xcc,0xa3, + 0xcc,0x84,0x00,0x01,0xff,0x72,0xcc,0xa3,0xcc,0x84,0x00,0x10,0x08,0x01,0xff,0x52, + 0xcc,0xb1,0x00,0x01,0xff,0x72,0xcc,0xb1,0x00,0xd4,0x8c,0xd3,0x48,0xd2,0x20,0xd1, + 0x10,0x10,0x08,0x01,0xff,0x53,0xcc,0x87,0x00,0x01,0xff,0x73,0xcc,0x87,0x00,0x10, + 0x08,0x01,0xff,0x53,0xcc,0xa3,0x00,0x01,0xff,0x73,0xcc,0xa3,0x00,0xd1,0x14,0x10, + 0x0a,0x01,0xff,0x53,0xcc,0x81,0xcc,0x87,0x00,0x01,0xff,0x73,0xcc,0x81,0xcc,0x87, + 0x00,0x10,0x0a,0x01,0xff,0x53,0xcc,0x8c,0xcc,0x87,0x00,0x01,0xff,0x73,0xcc,0x8c, + 0xcc,0x87,0x00,0xd2,0x24,0xd1,0x14,0x10,0x0a,0x01,0xff,0x53,0xcc,0xa3,0xcc,0x87, + 0x00,0x01,0xff,0x73,0xcc,0xa3,0xcc,0x87,0x00,0x10,0x08,0x01,0xff,0x54,0xcc,0x87, + 0x00,0x01,0xff,0x74,0xcc,0x87,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x54,0xcc,0xa3, + 0x00,0x01,0xff,0x74,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x54,0xcc,0xb1,0x00,0x01, + 0xff,0x74,0xcc,0xb1,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x54, + 0xcc,0xad,0x00,0x01,0xff,0x74,0xcc,0xad,0x00,0x10,0x08,0x01,0xff,0x55,0xcc,0xa4, + 0x00,0x01,0xff,0x75,0xcc,0xa4,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x55,0xcc,0xb0, + 0x00,0x01,0xff,0x75,0xcc,0xb0,0x00,0x10,0x08,0x01,0xff,0x55,0xcc,0xad,0x00,0x01, + 0xff,0x75,0xcc,0xad,0x00,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x55,0xcc,0x83, + 0xcc,0x81,0x00,0x01,0xff,0x75,0xcc,0x83,0xcc,0x81,0x00,0x10,0x0a,0x01,0xff,0x55, + 0xcc,0x84,0xcc,0x88,0x00,0x01,0xff,0x75,0xcc,0x84,0xcc,0x88,0x00,0xd1,0x10,0x10, + 0x08,0x01,0xff,0x56,0xcc,0x83,0x00,0x01,0xff,0x76,0xcc,0x83,0x00,0x10,0x08,0x01, + 0xff,0x56,0xcc,0xa3,0x00,0x01,0xff,0x76,0xcc,0xa3,0x00,0xe0,0x10,0x02,0xcf,0x86, + 0xd5,0xe1,0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x57,0xcc, + 0x80,0x00,0x01,0xff,0x77,0xcc,0x80,0x00,0x10,0x08,0x01,0xff,0x57,0xcc,0x81,0x00, + 0x01,0xff,0x77,0xcc,0x81,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x57,0xcc,0x88,0x00, + 0x01,0xff,0x77,0xcc,0x88,0x00,0x10,0x08,0x01,0xff,0x57,0xcc,0x87,0x00,0x01,0xff, + 0x77,0xcc,0x87,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x57,0xcc,0xa3,0x00, + 0x01,0xff,0x77,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x58,0xcc,0x87,0x00,0x01,0xff, + 0x78,0xcc,0x87,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x58,0xcc,0x88,0x00,0x01,0xff, + 0x78,0xcc,0x88,0x00,0x10,0x08,0x01,0xff,0x59,0xcc,0x87,0x00,0x01,0xff,0x79,0xcc, + 0x87,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x5a,0xcc,0x82,0x00, + 0x01,0xff,0x7a,0xcc,0x82,0x00,0x10,0x08,0x01,0xff,0x5a,0xcc,0xa3,0x00,0x01,0xff, + 0x7a,0xcc,0xa3,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x5a,0xcc,0xb1,0x00,0x01,0xff, + 0x7a,0xcc,0xb1,0x00,0x10,0x08,0x01,0xff,0x68,0xcc,0xb1,0x00,0x01,0xff,0x74,0xcc, + 0x88,0x00,0x92,0x1d,0xd1,0x10,0x10,0x08,0x01,0xff,0x77,0xcc,0x8a,0x00,0x01,0xff, + 0x79,0xcc,0x8a,0x00,0x10,0x04,0x01,0x00,0x02,0xff,0xc5,0xbf,0xcc,0x87,0x00,0x0a, + 0x00,0xd4,0x98,0xd3,0x48,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x41,0xcc,0xa3, + 0x00,0x01,0xff,0x61,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x41,0xcc,0x89,0x00,0x01, + 0xff,0x61,0xcc,0x89,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x41,0xcc,0x82,0xcc,0x81, + 0x00,0x01,0xff,0x61,0xcc,0x82,0xcc,0x81,0x00,0x10,0x0a,0x01,0xff,0x41,0xcc,0x82, + 0xcc,0x80,0x00,0x01,0xff,0x61,0xcc,0x82,0xcc,0x80,0x00,0xd2,0x28,0xd1,0x14,0x10, + 0x0a,0x01,0xff,0x41,0xcc,0x82,0xcc,0x89,0x00,0x01,0xff,0x61,0xcc,0x82,0xcc,0x89, + 0x00,0x10,0x0a,0x01,0xff,0x41,0xcc,0x82,0xcc,0x83,0x00,0x01,0xff,0x61,0xcc,0x82, + 0xcc,0x83,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x41,0xcc,0xa3,0xcc,0x82,0x00,0x01, + 0xff,0x61,0xcc,0xa3,0xcc,0x82,0x00,0x10,0x0a,0x01,0xff,0x41,0xcc,0x86,0xcc,0x81, + 0x00,0x01,0xff,0x61,0xcc,0x86,0xcc,0x81,0x00,0xd3,0x50,0xd2,0x28,0xd1,0x14,0x10, + 0x0a,0x01,0xff,0x41,0xcc,0x86,0xcc,0x80,0x00,0x01,0xff,0x61,0xcc,0x86,0xcc,0x80, + 0x00,0x10,0x0a,0x01,0xff,0x41,0xcc,0x86,0xcc,0x89,0x00,0x01,0xff,0x61,0xcc,0x86, + 0xcc,0x89,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x41,0xcc,0x86,0xcc,0x83,0x00,0x01, + 0xff,0x61,0xcc,0x86,0xcc,0x83,0x00,0x10,0x0a,0x01,0xff,0x41,0xcc,0xa3,0xcc,0x86, + 0x00,0x01,0xff,0x61,0xcc,0xa3,0xcc,0x86,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01, + 0xff,0x45,0xcc,0xa3,0x00,0x01,0xff,0x65,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x45, + 0xcc,0x89,0x00,0x01,0xff,0x65,0xcc,0x89,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x45, + 0xcc,0x83,0x00,0x01,0xff,0x65,0xcc,0x83,0x00,0x10,0x0a,0x01,0xff,0x45,0xcc,0x82, + 0xcc,0x81,0x00,0x01,0xff,0x65,0xcc,0x82,0xcc,0x81,0x00,0xcf,0x86,0xe5,0x31,0x01, + 0xd4,0x90,0xd3,0x50,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x45,0xcc,0x82,0xcc, + 0x80,0x00,0x01,0xff,0x65,0xcc,0x82,0xcc,0x80,0x00,0x10,0x0a,0x01,0xff,0x45,0xcc, + 0x82,0xcc,0x89,0x00,0x01,0xff,0x65,0xcc,0x82,0xcc,0x89,0x00,0xd1,0x14,0x10,0x0a, + 0x01,0xff,0x45,0xcc,0x82,0xcc,0x83,0x00,0x01,0xff,0x65,0xcc,0x82,0xcc,0x83,0x00, + 0x10,0x0a,0x01,0xff,0x45,0xcc,0xa3,0xcc,0x82,0x00,0x01,0xff,0x65,0xcc,0xa3,0xcc, + 0x82,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0x49,0xcc,0x89,0x00,0x01,0xff, + 0x69,0xcc,0x89,0x00,0x10,0x08,0x01,0xff,0x49,0xcc,0xa3,0x00,0x01,0xff,0x69,0xcc, + 0xa3,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0x4f,0xcc,0xa3,0x00,0x01,0xff,0x6f,0xcc, + 0xa3,0x00,0x10,0x08,0x01,0xff,0x4f,0xcc,0x89,0x00,0x01,0xff,0x6f,0xcc,0x89,0x00, + 0xd3,0x50,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x4f,0xcc,0x82,0xcc,0x81,0x00, + 0x01,0xff,0x6f,0xcc,0x82,0xcc,0x81,0x00,0x10,0x0a,0x01,0xff,0x4f,0xcc,0x82,0xcc, + 0x80,0x00,0x01,0xff,0x6f,0xcc,0x82,0xcc,0x80,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff, + 0x4f,0xcc,0x82,0xcc,0x89,0x00,0x01,0xff,0x6f,0xcc,0x82,0xcc,0x89,0x00,0x10,0x0a, + 0x01,0xff,0x4f,0xcc,0x82,0xcc,0x83,0x00,0x01,0xff,0x6f,0xcc,0x82,0xcc,0x83,0x00, + 0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x4f,0xcc,0xa3,0xcc,0x82,0x00,0x01,0xff, + 0x6f,0xcc,0xa3,0xcc,0x82,0x00,0x10,0x0a,0x01,0xff,0x4f,0xcc,0x9b,0xcc,0x81,0x00, + 0x01,0xff,0x6f,0xcc,0x9b,0xcc,0x81,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0x4f,0xcc, + 0x9b,0xcc,0x80,0x00,0x01,0xff,0x6f,0xcc,0x9b,0xcc,0x80,0x00,0x10,0x0a,0x01,0xff, + 0x4f,0xcc,0x9b,0xcc,0x89,0x00,0x01,0xff,0x6f,0xcc,0x9b,0xcc,0x89,0x00,0xd4,0x98, + 0xd3,0x48,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0x4f,0xcc,0x9b,0xcc,0x83,0x00, + 0x01,0xff,0x6f,0xcc,0x9b,0xcc,0x83,0x00,0x10,0x0a,0x01,0xff,0x4f,0xcc,0x9b,0xcc, + 0xa3,0x00,0x01,0xff,0x6f,0xcc,0x9b,0xcc,0xa3,0x00,0xd1,0x10,0x10,0x08,0x01,0xff, + 0x55,0xcc,0xa3,0x00,0x01,0xff,0x75,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff,0x55,0xcc, + 0x89,0x00,0x01,0xff,0x75,0xcc,0x89,0x00,0xd2,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff, + 0x55,0xcc,0x9b,0xcc,0x81,0x00,0x01,0xff,0x75,0xcc,0x9b,0xcc,0x81,0x00,0x10,0x0a, + 0x01,0xff,0x55,0xcc,0x9b,0xcc,0x80,0x00,0x01,0xff,0x75,0xcc,0x9b,0xcc,0x80,0x00, + 0xd1,0x14,0x10,0x0a,0x01,0xff,0x55,0xcc,0x9b,0xcc,0x89,0x00,0x01,0xff,0x75,0xcc, + 0x9b,0xcc,0x89,0x00,0x10,0x0a,0x01,0xff,0x55,0xcc,0x9b,0xcc,0x83,0x00,0x01,0xff, + 0x75,0xcc,0x9b,0xcc,0x83,0x00,0xd3,0x44,0xd2,0x24,0xd1,0x14,0x10,0x0a,0x01,0xff, + 0x55,0xcc,0x9b,0xcc,0xa3,0x00,0x01,0xff,0x75,0xcc,0x9b,0xcc,0xa3,0x00,0x10,0x08, + 0x01,0xff,0x59,0xcc,0x80,0x00,0x01,0xff,0x79,0xcc,0x80,0x00,0xd1,0x10,0x10,0x08, + 0x01,0xff,0x59,0xcc,0xa3,0x00,0x01,0xff,0x79,0xcc,0xa3,0x00,0x10,0x08,0x01,0xff, + 0x59,0xcc,0x89,0x00,0x01,0xff,0x79,0xcc,0x89,0x00,0x92,0x14,0x91,0x10,0x10,0x08, + 0x01,0xff,0x59,0xcc,0x83,0x00,0x01,0xff,0x79,0xcc,0x83,0x00,0x0a,0x00,0x0a,0x00, + 0xe1,0xc0,0x04,0xe0,0x80,0x02,0xcf,0x86,0xe5,0x2d,0x01,0xd4,0xa8,0xd3,0x54,0xd2, + 0x28,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb1,0xcc,0x93,0x00,0x01,0xff,0xce,0xb1, + 0xcc,0x94,0x00,0x10,0x0b,0x01,0xff,0xce,0xb1,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff, + 0xce,0xb1,0xcc,0x94,0xcc,0x80,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0xb1,0xcc, + 0x93,0xcc,0x81,0x00,0x01,0xff,0xce,0xb1,0xcc,0x94,0xcc,0x81,0x00,0x10,0x0b,0x01, + 0xff,0xce,0xb1,0xcc,0x93,0xcd,0x82,0x00,0x01,0xff,0xce,0xb1,0xcc,0x94,0xcd,0x82, + 0x00,0xd2,0x28,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0x91,0xcc,0x93,0x00,0x01,0xff, + 0xce,0x91,0xcc,0x94,0x00,0x10,0x0b,0x01,0xff,0xce,0x91,0xcc,0x93,0xcc,0x80,0x00, + 0x01,0xff,0xce,0x91,0xcc,0x94,0xcc,0x80,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce, + 0x91,0xcc,0x93,0xcc,0x81,0x00,0x01,0xff,0xce,0x91,0xcc,0x94,0xcc,0x81,0x00,0x10, + 0x0b,0x01,0xff,0xce,0x91,0xcc,0x93,0xcd,0x82,0x00,0x01,0xff,0xce,0x91,0xcc,0x94, + 0xcd,0x82,0x00,0xd3,0x42,0xd2,0x28,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb5,0xcc, + 0x93,0x00,0x01,0xff,0xce,0xb5,0xcc,0x94,0x00,0x10,0x0b,0x01,0xff,0xce,0xb5,0xcc, + 0x93,0xcc,0x80,0x00,0x01,0xff,0xce,0xb5,0xcc,0x94,0xcc,0x80,0x00,0x91,0x16,0x10, + 0x0b,0x01,0xff,0xce,0xb5,0xcc,0x93,0xcc,0x81,0x00,0x01,0xff,0xce,0xb5,0xcc,0x94, + 0xcc,0x81,0x00,0x00,0x00,0xd2,0x28,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0x95,0xcc, + 0x93,0x00,0x01,0xff,0xce,0x95,0xcc,0x94,0x00,0x10,0x0b,0x01,0xff,0xce,0x95,0xcc, + 0x93,0xcc,0x80,0x00,0x01,0xff,0xce,0x95,0xcc,0x94,0xcc,0x80,0x00,0x91,0x16,0x10, + 0x0b,0x01,0xff,0xce,0x95,0xcc,0x93,0xcc,0x81,0x00,0x01,0xff,0xce,0x95,0xcc,0x94, + 0xcc,0x81,0x00,0x00,0x00,0xd4,0xa8,0xd3,0x54,0xd2,0x28,0xd1,0x12,0x10,0x09,0x01, + 0xff,0xce,0xb7,0xcc,0x93,0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0x00,0x10,0x0b,0x01, + 0xff,0xce,0xb7,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcc,0x80, + 0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0xb7,0xcc,0x93,0xcc,0x81,0x00,0x01,0xff, + 0xce,0xb7,0xcc,0x94,0xcc,0x81,0x00,0x10,0x0b,0x01,0xff,0xce,0xb7,0xcc,0x93,0xcd, + 0x82,0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcd,0x82,0x00,0xd2,0x28,0xd1,0x12,0x10, + 0x09,0x01,0xff,0xce,0x97,0xcc,0x93,0x00,0x01,0xff,0xce,0x97,0xcc,0x94,0x00,0x10, + 0x0b,0x01,0xff,0xce,0x97,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff,0xce,0x97,0xcc,0x94, + 0xcc,0x80,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0x97,0xcc,0x93,0xcc,0x81,0x00, + 0x01,0xff,0xce,0x97,0xcc,0x94,0xcc,0x81,0x00,0x10,0x0b,0x01,0xff,0xce,0x97,0xcc, + 0x93,0xcd,0x82,0x00,0x01,0xff,0xce,0x97,0xcc,0x94,0xcd,0x82,0x00,0xd3,0x54,0xd2, + 0x28,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb9,0xcc,0x93,0x00,0x01,0xff,0xce,0xb9, + 0xcc,0x94,0x00,0x10,0x0b,0x01,0xff,0xce,0xb9,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff, + 0xce,0xb9,0xcc,0x94,0xcc,0x80,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0xb9,0xcc, + 0x93,0xcc,0x81,0x00,0x01,0xff,0xce,0xb9,0xcc,0x94,0xcc,0x81,0x00,0x10,0x0b,0x01, + 0xff,0xce,0xb9,0xcc,0x93,0xcd,0x82,0x00,0x01,0xff,0xce,0xb9,0xcc,0x94,0xcd,0x82, + 0x00,0xd2,0x28,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0x99,0xcc,0x93,0x00,0x01,0xff, + 0xce,0x99,0xcc,0x94,0x00,0x10,0x0b,0x01,0xff,0xce,0x99,0xcc,0x93,0xcc,0x80,0x00, + 0x01,0xff,0xce,0x99,0xcc,0x94,0xcc,0x80,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce, + 0x99,0xcc,0x93,0xcc,0x81,0x00,0x01,0xff,0xce,0x99,0xcc,0x94,0xcc,0x81,0x00,0x10, + 0x0b,0x01,0xff,0xce,0x99,0xcc,0x93,0xcd,0x82,0x00,0x01,0xff,0xce,0x99,0xcc,0x94, + 0xcd,0x82,0x00,0xcf,0x86,0xe5,0x13,0x01,0xd4,0x84,0xd3,0x42,0xd2,0x28,0xd1,0x12, + 0x10,0x09,0x01,0xff,0xce,0xbf,0xcc,0x93,0x00,0x01,0xff,0xce,0xbf,0xcc,0x94,0x00, + 0x10,0x0b,0x01,0xff,0xce,0xbf,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff,0xce,0xbf,0xcc, + 0x94,0xcc,0x80,0x00,0x91,0x16,0x10,0x0b,0x01,0xff,0xce,0xbf,0xcc,0x93,0xcc,0x81, + 0x00,0x01,0xff,0xce,0xbf,0xcc,0x94,0xcc,0x81,0x00,0x00,0x00,0xd2,0x28,0xd1,0x12, + 0x10,0x09,0x01,0xff,0xce,0x9f,0xcc,0x93,0x00,0x01,0xff,0xce,0x9f,0xcc,0x94,0x00, + 0x10,0x0b,0x01,0xff,0xce,0x9f,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff,0xce,0x9f,0xcc, + 0x94,0xcc,0x80,0x00,0x91,0x16,0x10,0x0b,0x01,0xff,0xce,0x9f,0xcc,0x93,0xcc,0x81, + 0x00,0x01,0xff,0xce,0x9f,0xcc,0x94,0xcc,0x81,0x00,0x00,0x00,0xd3,0x54,0xd2,0x28, + 0xd1,0x12,0x10,0x09,0x01,0xff,0xcf,0x85,0xcc,0x93,0x00,0x01,0xff,0xcf,0x85,0xcc, + 0x94,0x00,0x10,0x0b,0x01,0xff,0xcf,0x85,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff,0xcf, + 0x85,0xcc,0x94,0xcc,0x80,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xcf,0x85,0xcc,0x93, + 0xcc,0x81,0x00,0x01,0xff,0xcf,0x85,0xcc,0x94,0xcc,0x81,0x00,0x10,0x0b,0x01,0xff, + 0xcf,0x85,0xcc,0x93,0xcd,0x82,0x00,0x01,0xff,0xcf,0x85,0xcc,0x94,0xcd,0x82,0x00, + 0xd2,0x1c,0xd1,0x0d,0x10,0x04,0x00,0x00,0x01,0xff,0xce,0xa5,0xcc,0x94,0x00,0x10, + 0x04,0x00,0x00,0x01,0xff,0xce,0xa5,0xcc,0x94,0xcc,0x80,0x00,0xd1,0x0f,0x10,0x04, + 0x00,0x00,0x01,0xff,0xce,0xa5,0xcc,0x94,0xcc,0x81,0x00,0x10,0x04,0x00,0x00,0x01, + 0xff,0xce,0xa5,0xcc,0x94,0xcd,0x82,0x00,0xd4,0xa8,0xd3,0x54,0xd2,0x28,0xd1,0x12, + 0x10,0x09,0x01,0xff,0xcf,0x89,0xcc,0x93,0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0x00, + 0x10,0x0b,0x01,0xff,0xcf,0x89,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff,0xcf,0x89,0xcc, + 0x94,0xcc,0x80,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xcf,0x89,0xcc,0x93,0xcc,0x81, + 0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xcc,0x81,0x00,0x10,0x0b,0x01,0xff,0xcf,0x89, + 0xcc,0x93,0xcd,0x82,0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xcd,0x82,0x00,0xd2,0x28, + 0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xa9,0xcc,0x93,0x00,0x01,0xff,0xce,0xa9,0xcc, + 0x94,0x00,0x10,0x0b,0x01,0xff,0xce,0xa9,0xcc,0x93,0xcc,0x80,0x00,0x01,0xff,0xce, + 0xa9,0xcc,0x94,0xcc,0x80,0x00,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0xa9,0xcc,0x93, + 0xcc,0x81,0x00,0x01,0xff,0xce,0xa9,0xcc,0x94,0xcc,0x81,0x00,0x10,0x0b,0x01,0xff, + 0xce,0xa9,0xcc,0x93,0xcd,0x82,0x00,0x01,0xff,0xce,0xa9,0xcc,0x94,0xcd,0x82,0x00, + 0xd3,0x48,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb1,0xcc,0x80,0x00,0x01, + 0xff,0xce,0xb1,0xcc,0x81,0x00,0x10,0x09,0x01,0xff,0xce,0xb5,0xcc,0x80,0x00,0x01, + 0xff,0xce,0xb5,0xcc,0x81,0x00,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb7,0xcc,0x80, + 0x00,0x01,0xff,0xce,0xb7,0xcc,0x81,0x00,0x10,0x09,0x01,0xff,0xce,0xb9,0xcc,0x80, + 0x00,0x01,0xff,0xce,0xb9,0xcc,0x81,0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff, + 0xce,0xbf,0xcc,0x80,0x00,0x01,0xff,0xce,0xbf,0xcc,0x81,0x00,0x10,0x09,0x01,0xff, + 0xcf,0x85,0xcc,0x80,0x00,0x01,0xff,0xcf,0x85,0xcc,0x81,0x00,0x91,0x12,0x10,0x09, + 0x01,0xff,0xcf,0x89,0xcc,0x80,0x00,0x01,0xff,0xcf,0x89,0xcc,0x81,0x00,0x00,0x00, + 0xe0,0xe1,0x02,0xcf,0x86,0xe5,0x91,0x01,0xd4,0xc8,0xd3,0x64,0xd2,0x30,0xd1,0x16, + 0x10,0x0b,0x01,0xff,0xce,0xb1,0xcc,0x93,0xcd,0x85,0x00,0x01,0xff,0xce,0xb1,0xcc, + 0x94,0xcd,0x85,0x00,0x10,0x0d,0x01,0xff,0xce,0xb1,0xcc,0x93,0xcc,0x80,0xcd,0x85, + 0x00,0x01,0xff,0xce,0xb1,0xcc,0x94,0xcc,0x80,0xcd,0x85,0x00,0xd1,0x1a,0x10,0x0d, + 0x01,0xff,0xce,0xb1,0xcc,0x93,0xcc,0x81,0xcd,0x85,0x00,0x01,0xff,0xce,0xb1,0xcc, + 0x94,0xcc,0x81,0xcd,0x85,0x00,0x10,0x0d,0x01,0xff,0xce,0xb1,0xcc,0x93,0xcd,0x82, + 0xcd,0x85,0x00,0x01,0xff,0xce,0xb1,0xcc,0x94,0xcd,0x82,0xcd,0x85,0x00,0xd2,0x30, + 0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0x91,0xcc,0x93,0xcd,0x85,0x00,0x01,0xff,0xce, + 0x91,0xcc,0x94,0xcd,0x85,0x00,0x10,0x0d,0x01,0xff,0xce,0x91,0xcc,0x93,0xcc,0x80, + 0xcd,0x85,0x00,0x01,0xff,0xce,0x91,0xcc,0x94,0xcc,0x80,0xcd,0x85,0x00,0xd1,0x1a, + 0x10,0x0d,0x01,0xff,0xce,0x91,0xcc,0x93,0xcc,0x81,0xcd,0x85,0x00,0x01,0xff,0xce, + 0x91,0xcc,0x94,0xcc,0x81,0xcd,0x85,0x00,0x10,0x0d,0x01,0xff,0xce,0x91,0xcc,0x93, + 0xcd,0x82,0xcd,0x85,0x00,0x01,0xff,0xce,0x91,0xcc,0x94,0xcd,0x82,0xcd,0x85,0x00, + 0xd3,0x64,0xd2,0x30,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0xb7,0xcc,0x93,0xcd,0x85, + 0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcd,0x85,0x00,0x10,0x0d,0x01,0xff,0xce,0xb7, + 0xcc,0x93,0xcc,0x80,0xcd,0x85,0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcc,0x80,0xcd, + 0x85,0x00,0xd1,0x1a,0x10,0x0d,0x01,0xff,0xce,0xb7,0xcc,0x93,0xcc,0x81,0xcd,0x85, + 0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcc,0x81,0xcd,0x85,0x00,0x10,0x0d,0x01,0xff, + 0xce,0xb7,0xcc,0x93,0xcd,0x82,0xcd,0x85,0x00,0x01,0xff,0xce,0xb7,0xcc,0x94,0xcd, + 0x82,0xcd,0x85,0x00,0xd2,0x30,0xd1,0x16,0x10,0x0b,0x01,0xff,0xce,0x97,0xcc,0x93, + 0xcd,0x85,0x00,0x01,0xff,0xce,0x97,0xcc,0x94,0xcd,0x85,0x00,0x10,0x0d,0x01,0xff, + 0xce,0x97,0xcc,0x93,0xcc,0x80,0xcd,0x85,0x00,0x01,0xff,0xce,0x97,0xcc,0x94,0xcc, + 0x80,0xcd,0x85,0x00,0xd1,0x1a,0x10,0x0d,0x01,0xff,0xce,0x97,0xcc,0x93,0xcc,0x81, + 0xcd,0x85,0x00,0x01,0xff,0xce,0x97,0xcc,0x94,0xcc,0x81,0xcd,0x85,0x00,0x10,0x0d, + 0x01,0xff,0xce,0x97,0xcc,0x93,0xcd,0x82,0xcd,0x85,0x00,0x01,0xff,0xce,0x97,0xcc, + 0x94,0xcd,0x82,0xcd,0x85,0x00,0xd4,0xc8,0xd3,0x64,0xd2,0x30,0xd1,0x16,0x10,0x0b, + 0x01,0xff,0xcf,0x89,0xcc,0x93,0xcd,0x85,0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xcd, + 0x85,0x00,0x10,0x0d,0x01,0xff,0xcf,0x89,0xcc,0x93,0xcc,0x80,0xcd,0x85,0x00,0x01, + 0xff,0xcf,0x89,0xcc,0x94,0xcc,0x80,0xcd,0x85,0x00,0xd1,0x1a,0x10,0x0d,0x01,0xff, + 0xcf,0x89,0xcc,0x93,0xcc,0x81,0xcd,0x85,0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xcc, + 0x81,0xcd,0x85,0x00,0x10,0x0d,0x01,0xff,0xcf,0x89,0xcc,0x93,0xcd,0x82,0xcd,0x85, + 0x00,0x01,0xff,0xcf,0x89,0xcc,0x94,0xcd,0x82,0xcd,0x85,0x00,0xd2,0x30,0xd1,0x16, + 0x10,0x0b,0x01,0xff,0xce,0xa9,0xcc,0x93,0xcd,0x85,0x00,0x01,0xff,0xce,0xa9,0xcc, + 0x94,0xcd,0x85,0x00,0x10,0x0d,0x01,0xff,0xce,0xa9,0xcc,0x93,0xcc,0x80,0xcd,0x85, + 0x00,0x01,0xff,0xce,0xa9,0xcc,0x94,0xcc,0x80,0xcd,0x85,0x00,0xd1,0x1a,0x10,0x0d, + 0x01,0xff,0xce,0xa9,0xcc,0x93,0xcc,0x81,0xcd,0x85,0x00,0x01,0xff,0xce,0xa9,0xcc, + 0x94,0xcc,0x81,0xcd,0x85,0x00,0x10,0x0d,0x01,0xff,0xce,0xa9,0xcc,0x93,0xcd,0x82, + 0xcd,0x85,0x00,0x01,0xff,0xce,0xa9,0xcc,0x94,0xcd,0x82,0xcd,0x85,0x00,0xd3,0x49, + 0xd2,0x26,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0xb1,0xcc,0x86,0x00,0x01,0xff,0xce, + 0xb1,0xcc,0x84,0x00,0x10,0x0b,0x01,0xff,0xce,0xb1,0xcc,0x80,0xcd,0x85,0x00,0x01, + 0xff,0xce,0xb1,0xcd,0x85,0x00,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xce,0xb1,0xcc,0x81, + 0xcd,0x85,0x00,0x00,0x00,0x10,0x09,0x01,0xff,0xce,0xb1,0xcd,0x82,0x00,0x01,0xff, + 0xce,0xb1,0xcd,0x82,0xcd,0x85,0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff,0xce, + 0x91,0xcc,0x86,0x00,0x01,0xff,0xce,0x91,0xcc,0x84,0x00,0x10,0x09,0x01,0xff,0xce, + 0x91,0xcc,0x80,0x00,0x01,0xff,0xce,0x91,0xcc,0x81,0x00,0xd1,0x0d,0x10,0x09,0x01, + 0xff,0xce,0x91,0xcd,0x85,0x00,0x01,0x00,0x10,0x07,0x01,0xff,0xce,0xb9,0x00,0x01, + 0x00,0xcf,0x86,0xe5,0x16,0x01,0xd4,0x8f,0xd3,0x44,0xd2,0x21,0xd1,0x0d,0x10,0x04, + 0x01,0x00,0x01,0xff,0xc2,0xa8,0xcd,0x82,0x00,0x10,0x0b,0x01,0xff,0xce,0xb7,0xcc, + 0x80,0xcd,0x85,0x00,0x01,0xff,0xce,0xb7,0xcd,0x85,0x00,0xd1,0x0f,0x10,0x0b,0x01, + 0xff,0xce,0xb7,0xcc,0x81,0xcd,0x85,0x00,0x00,0x00,0x10,0x09,0x01,0xff,0xce,0xb7, + 0xcd,0x82,0x00,0x01,0xff,0xce,0xb7,0xcd,0x82,0xcd,0x85,0x00,0xd2,0x24,0xd1,0x12, + 0x10,0x09,0x01,0xff,0xce,0x95,0xcc,0x80,0x00,0x01,0xff,0xce,0x95,0xcc,0x81,0x00, + 0x10,0x09,0x01,0xff,0xce,0x97,0xcc,0x80,0x00,0x01,0xff,0xce,0x97,0xcc,0x81,0x00, + 0xd1,0x13,0x10,0x09,0x01,0xff,0xce,0x97,0xcd,0x85,0x00,0x01,0xff,0xe1,0xbe,0xbf, + 0xcc,0x80,0x00,0x10,0x0a,0x01,0xff,0xe1,0xbe,0xbf,0xcc,0x81,0x00,0x01,0xff,0xe1, + 0xbe,0xbf,0xcd,0x82,0x00,0xd3,0x40,0xd2,0x28,0xd1,0x12,0x10,0x09,0x01,0xff,0xce, + 0xb9,0xcc,0x86,0x00,0x01,0xff,0xce,0xb9,0xcc,0x84,0x00,0x10,0x0b,0x01,0xff,0xce, + 0xb9,0xcc,0x88,0xcc,0x80,0x00,0x01,0xff,0xce,0xb9,0xcc,0x88,0xcc,0x81,0x00,0x51, + 0x04,0x00,0x00,0x10,0x09,0x01,0xff,0xce,0xb9,0xcd,0x82,0x00,0x01,0xff,0xce,0xb9, + 0xcc,0x88,0xcd,0x82,0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff,0xce,0x99,0xcc, + 0x86,0x00,0x01,0xff,0xce,0x99,0xcc,0x84,0x00,0x10,0x09,0x01,0xff,0xce,0x99,0xcc, + 0x80,0x00,0x01,0xff,0xce,0x99,0xcc,0x81,0x00,0xd1,0x0e,0x10,0x04,0x00,0x00,0x01, + 0xff,0xe1,0xbf,0xbe,0xcc,0x80,0x00,0x10,0x0a,0x01,0xff,0xe1,0xbf,0xbe,0xcc,0x81, + 0x00,0x01,0xff,0xe1,0xbf,0xbe,0xcd,0x82,0x00,0xd4,0x93,0xd3,0x4e,0xd2,0x28,0xd1, + 0x12,0x10,0x09,0x01,0xff,0xcf,0x85,0xcc,0x86,0x00,0x01,0xff,0xcf,0x85,0xcc,0x84, + 0x00,0x10,0x0b,0x01,0xff,0xcf,0x85,0xcc,0x88,0xcc,0x80,0x00,0x01,0xff,0xcf,0x85, + 0xcc,0x88,0xcc,0x81,0x00,0xd1,0x12,0x10,0x09,0x01,0xff,0xcf,0x81,0xcc,0x93,0x00, + 0x01,0xff,0xcf,0x81,0xcc,0x94,0x00,0x10,0x09,0x01,0xff,0xcf,0x85,0xcd,0x82,0x00, + 0x01,0xff,0xcf,0x85,0xcc,0x88,0xcd,0x82,0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01, + 0xff,0xce,0xa5,0xcc,0x86,0x00,0x01,0xff,0xce,0xa5,0xcc,0x84,0x00,0x10,0x09,0x01, + 0xff,0xce,0xa5,0xcc,0x80,0x00,0x01,0xff,0xce,0xa5,0xcc,0x81,0x00,0xd1,0x12,0x10, + 0x09,0x01,0xff,0xce,0xa1,0xcc,0x94,0x00,0x01,0xff,0xc2,0xa8,0xcc,0x80,0x00,0x10, + 0x09,0x01,0xff,0xc2,0xa8,0xcc,0x81,0x00,0x01,0xff,0x60,0x00,0xd3,0x3b,0xd2,0x18, + 0x51,0x04,0x00,0x00,0x10,0x0b,0x01,0xff,0xcf,0x89,0xcc,0x80,0xcd,0x85,0x00,0x01, + 0xff,0xcf,0x89,0xcd,0x85,0x00,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xcf,0x89,0xcc,0x81, + 0xcd,0x85,0x00,0x00,0x00,0x10,0x09,0x01,0xff,0xcf,0x89,0xcd,0x82,0x00,0x01,0xff, + 0xcf,0x89,0xcd,0x82,0xcd,0x85,0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff,0xce, + 0x9f,0xcc,0x80,0x00,0x01,0xff,0xce,0x9f,0xcc,0x81,0x00,0x10,0x09,0x01,0xff,0xce, + 0xa9,0xcc,0x80,0x00,0x01,0xff,0xce,0xa9,0xcc,0x81,0x00,0xd1,0x10,0x10,0x09,0x01, + 0xff,0xce,0xa9,0xcd,0x85,0x00,0x01,0xff,0xc2,0xb4,0x00,0x10,0x04,0x01,0x00,0x00, + 0x00,0xe0,0x7e,0x0c,0xcf,0x86,0xe5,0xbb,0x08,0xe4,0x14,0x06,0xe3,0xf7,0x02,0xe2, + 0xbd,0x01,0xd1,0xd0,0xd0,0x4f,0xcf,0x86,0xd5,0x2e,0x94,0x2a,0xd3,0x18,0x92,0x14, + 0x91,0x10,0x10,0x08,0x01,0xff,0xe2,0x80,0x82,0x00,0x01,0xff,0xe2,0x80,0x83,0x00, + 0x01,0x00,0x01,0x00,0x92,0x0d,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x01,0xff, + 0x00,0x01,0xff,0x00,0x01,0x00,0x94,0x1b,0x53,0x04,0x01,0x00,0xd2,0x09,0x11,0x04, + 0x01,0x00,0x01,0xff,0x00,0x51,0x05,0x01,0xff,0x00,0x10,0x05,0x01,0xff,0x00,0x04, + 0x00,0x01,0x00,0xcf,0x86,0xd5,0x48,0xd4,0x1c,0xd3,0x10,0x52,0x04,0x01,0x00,0x51, + 0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x06,0x00,0x52,0x04,0x04,0x00,0x11,0x04,0x04, + 0x00,0x06,0x00,0xd3,0x1c,0xd2,0x0c,0x51,0x04,0x06,0x00,0x10,0x04,0x06,0x00,0x07, + 0x00,0xd1,0x08,0x10,0x04,0x07,0x00,0x08,0x00,0x10,0x04,0x08,0x00,0x06,0x00,0x52, + 0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x06,0x00,0xd4,0x23,0xd3, + 0x14,0x52,0x05,0x06,0xff,0x00,0x91,0x0a,0x10,0x05,0x0a,0xff,0x00,0x00,0xff,0x00, + 0x0f,0xff,0x00,0x92,0x0a,0x11,0x05,0x0f,0xff,0x00,0x01,0xff,0x00,0x01,0xff,0x00, + 0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x01,0x00,0x06,0x00,0x00,0x00,0x01,0x00, + 0x01,0x00,0xd0,0x7e,0xcf,0x86,0xd5,0x34,0xd4,0x14,0x53,0x04,0x01,0x00,0x52,0x04, + 0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x00,0x00,0xd3,0x10,0x52,0x04, + 0x08,0x00,0x91,0x08,0x10,0x04,0x08,0x00,0x0c,0x00,0x0c,0x00,0x52,0x04,0x0c,0x00, + 0x91,0x08,0x10,0x04,0x0c,0x00,0x00,0x00,0x00,0x00,0xd4,0x1c,0x53,0x04,0x01,0x00, + 0xd2,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x02,0x00,0x91,0x08,0x10,0x04, + 0x03,0x00,0x04,0x00,0x04,0x00,0xd3,0x10,0xd2,0x08,0x11,0x04,0x06,0x00,0x08,0x00, + 0x11,0x04,0x08,0x00,0x0b,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04,0x0b,0x00,0x0c,0x00, + 0x10,0x04,0x0e,0x00,0x10,0x00,0x51,0x04,0x10,0x00,0x10,0x04,0x11,0x00,0x13,0x00, + 0xcf,0x86,0xd5,0x28,0x54,0x04,0x00,0x00,0xd3,0x0c,0x92,0x08,0x11,0x04,0x01,0xe6, + 0x01,0x01,0x01,0xe6,0xd2,0x0c,0x51,0x04,0x01,0x01,0x10,0x04,0x01,0x01,0x01,0xe6, + 0x91,0x08,0x10,0x04,0x01,0xe6,0x01,0x00,0x01,0x00,0xd4,0x30,0xd3,0x1c,0xd2,0x0c, + 0x91,0x08,0x10,0x04,0x01,0x00,0x01,0xe6,0x04,0x00,0xd1,0x08,0x10,0x04,0x06,0x00, + 0x06,0x01,0x10,0x04,0x06,0x01,0x06,0xe6,0x92,0x10,0xd1,0x08,0x10,0x04,0x06,0xdc, + 0x06,0xe6,0x10,0x04,0x06,0x01,0x08,0x01,0x09,0xdc,0x93,0x10,0x92,0x0c,0x91,0x08, + 0x10,0x04,0x0a,0xe6,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd1,0x81,0xd0,0x4f, + 0xcf,0x86,0x55,0x04,0x01,0x00,0xd4,0x29,0xd3,0x13,0x52,0x04,0x01,0x00,0x51,0x04, + 0x01,0x00,0x10,0x07,0x01,0xff,0xce,0xa9,0x00,0x01,0x00,0x92,0x12,0x51,0x04,0x01, + 0x00,0x10,0x06,0x01,0xff,0x4b,0x00,0x01,0xff,0x41,0xcc,0x8a,0x00,0x01,0x00,0x53, + 0x04,0x01,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04,0x01,0x00,0x04,0x00,0x10,0x04,0x04, + 0x00,0x07,0x00,0x91,0x08,0x10,0x04,0x08,0x00,0x06,0x00,0x06,0x00,0xcf,0x86,0x95, + 0x2c,0xd4,0x18,0x53,0x04,0x06,0x00,0x52,0x04,0x06,0x00,0xd1,0x08,0x10,0x04,0x08, + 0x00,0x09,0x00,0x10,0x04,0x09,0x00,0x0a,0x00,0x93,0x10,0x92,0x0c,0x51,0x04,0x0b, + 0x00,0x10,0x04,0x0b,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd0,0x68,0xcf, + 0x86,0xd5,0x48,0xd4,0x28,0xd3,0x18,0xd2,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01, + 0x00,0x04,0x00,0x91,0x08,0x10,0x04,0x09,0x00,0x0a,0x00,0x0a,0x00,0x92,0x0c,0x91, + 0x08,0x10,0x04,0x0a,0x00,0x0b,0x00,0x11,0x00,0x00,0x00,0x53,0x04,0x01,0x00,0x92, + 0x18,0x51,0x04,0x01,0x00,0x10,0x0a,0x01,0xff,0xe2,0x86,0x90,0xcc,0xb8,0x00,0x01, + 0xff,0xe2,0x86,0x92,0xcc,0xb8,0x00,0x01,0x00,0x94,0x1a,0x53,0x04,0x01,0x00,0x52, + 0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x0a,0x01,0xff,0xe2,0x86,0x94,0xcc,0xb8, + 0x00,0x01,0x00,0x01,0x00,0xcf,0x86,0xd5,0x2e,0x94,0x2a,0x53,0x04,0x01,0x00,0x52, + 0x04,0x01,0x00,0xd1,0x0e,0x10,0x04,0x01,0x00,0x01,0xff,0xe2,0x87,0x90,0xcc,0xb8, + 0x00,0x10,0x0a,0x01,0xff,0xe2,0x87,0x94,0xcc,0xb8,0x00,0x01,0xff,0xe2,0x87,0x92, + 0xcc,0xb8,0x00,0x01,0x00,0xd4,0x14,0x53,0x04,0x01,0x00,0x92,0x0c,0x51,0x04,0x01, + 0x00,0x10,0x04,0x01,0x00,0x04,0x00,0x04,0x00,0x93,0x08,0x12,0x04,0x04,0x00,0x06, + 0x00,0x06,0x00,0xe2,0x38,0x02,0xe1,0x3f,0x01,0xd0,0x68,0xcf,0x86,0xd5,0x3e,0x94, + 0x3a,0xd3,0x16,0x52,0x04,0x01,0x00,0x91,0x0e,0x10,0x0a,0x01,0xff,0xe2,0x88,0x83, + 0xcc,0xb8,0x00,0x01,0x00,0x01,0x00,0xd2,0x12,0x91,0x0e,0x10,0x04,0x01,0x00,0x01, + 0xff,0xe2,0x88,0x88,0xcc,0xb8,0x00,0x01,0x00,0x91,0x0e,0x10,0x0a,0x01,0xff,0xe2, + 0x88,0x8b,0xcc,0xb8,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x94,0x24,0x93,0x20,0x52, + 0x04,0x01,0x00,0xd1,0x0e,0x10,0x0a,0x01,0xff,0xe2,0x88,0xa3,0xcc,0xb8,0x00,0x01, + 0x00,0x10,0x0a,0x01,0xff,0xe2,0x88,0xa5,0xcc,0xb8,0x00,0x01,0x00,0x01,0x00,0x01, + 0x00,0xcf,0x86,0xd5,0x48,0x94,0x44,0xd3,0x2e,0xd2,0x12,0x91,0x0e,0x10,0x04,0x01, + 0x00,0x01,0xff,0xe2,0x88,0xbc,0xcc,0xb8,0x00,0x01,0x00,0xd1,0x0e,0x10,0x0a,0x01, + 0xff,0xe2,0x89,0x83,0xcc,0xb8,0x00,0x01,0x00,0x10,0x04,0x01,0x00,0x01,0xff,0xe2, + 0x89,0x85,0xcc,0xb8,0x00,0x92,0x12,0x91,0x0e,0x10,0x04,0x01,0x00,0x01,0xff,0xe2, + 0x89,0x88,0xcc,0xb8,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd4,0x40,0xd3,0x1e,0x92, + 0x1a,0xd1,0x0c,0x10,0x08,0x01,0xff,0x3d,0xcc,0xb8,0x00,0x01,0x00,0x10,0x0a,0x01, + 0xff,0xe2,0x89,0xa1,0xcc,0xb8,0x00,0x01,0x00,0x01,0x00,0x52,0x04,0x01,0x00,0xd1, + 0x0e,0x10,0x04,0x01,0x00,0x01,0xff,0xe2,0x89,0x8d,0xcc,0xb8,0x00,0x10,0x08,0x01, + 0xff,0x3c,0xcc,0xb8,0x00,0x01,0xff,0x3e,0xcc,0xb8,0x00,0xd3,0x30,0xd2,0x18,0x91, + 0x14,0x10,0x0a,0x01,0xff,0xe2,0x89,0xa4,0xcc,0xb8,0x00,0x01,0xff,0xe2,0x89,0xa5, + 0xcc,0xb8,0x00,0x01,0x00,0x91,0x14,0x10,0x0a,0x01,0xff,0xe2,0x89,0xb2,0xcc,0xb8, + 0x00,0x01,0xff,0xe2,0x89,0xb3,0xcc,0xb8,0x00,0x01,0x00,0x92,0x18,0x91,0x14,0x10, + 0x0a,0x01,0xff,0xe2,0x89,0xb6,0xcc,0xb8,0x00,0x01,0xff,0xe2,0x89,0xb7,0xcc,0xb8, + 0x00,0x01,0x00,0x01,0x00,0xd0,0x86,0xcf,0x86,0xd5,0x50,0x94,0x4c,0xd3,0x30,0xd2, + 0x18,0x91,0x14,0x10,0x0a,0x01,0xff,0xe2,0x89,0xba,0xcc,0xb8,0x00,0x01,0xff,0xe2, + 0x89,0xbb,0xcc,0xb8,0x00,0x01,0x00,0x91,0x14,0x10,0x0a,0x01,0xff,0xe2,0x8a,0x82, + 0xcc,0xb8,0x00,0x01,0xff,0xe2,0x8a,0x83,0xcc,0xb8,0x00,0x01,0x00,0x92,0x18,0x91, + 0x14,0x10,0x0a,0x01,0xff,0xe2,0x8a,0x86,0xcc,0xb8,0x00,0x01,0xff,0xe2,0x8a,0x87, + 0xcc,0xb8,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x94,0x30,0x53,0x04,0x01,0x00,0x52, + 0x04,0x01,0x00,0xd1,0x14,0x10,0x0a,0x01,0xff,0xe2,0x8a,0xa2,0xcc,0xb8,0x00,0x01, + 0xff,0xe2,0x8a,0xa8,0xcc,0xb8,0x00,0x10,0x0a,0x01,0xff,0xe2,0x8a,0xa9,0xcc,0xb8, + 0x00,0x01,0xff,0xe2,0x8a,0xab,0xcc,0xb8,0x00,0x01,0x00,0xcf,0x86,0x55,0x04,0x01, + 0x00,0xd4,0x5c,0xd3,0x2c,0x92,0x28,0xd1,0x14,0x10,0x0a,0x01,0xff,0xe2,0x89,0xbc, + 0xcc,0xb8,0x00,0x01,0xff,0xe2,0x89,0xbd,0xcc,0xb8,0x00,0x10,0x0a,0x01,0xff,0xe2, + 0x8a,0x91,0xcc,0xb8,0x00,0x01,0xff,0xe2,0x8a,0x92,0xcc,0xb8,0x00,0x01,0x00,0xd2, + 0x18,0x51,0x04,0x01,0x00,0x10,0x0a,0x01,0xff,0xe2,0x8a,0xb2,0xcc,0xb8,0x00,0x01, + 0xff,0xe2,0x8a,0xb3,0xcc,0xb8,0x00,0x91,0x14,0x10,0x0a,0x01,0xff,0xe2,0x8a,0xb4, + 0xcc,0xb8,0x00,0x01,0xff,0xe2,0x8a,0xb5,0xcc,0xb8,0x00,0x01,0x00,0x93,0x0c,0x92, + 0x08,0x11,0x04,0x01,0x00,0x06,0x00,0x06,0x00,0x06,0x00,0xd1,0x64,0xd0,0x3e,0xcf, + 0x86,0xd5,0x18,0x94,0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x01,0x00,0x04, + 0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x94,0x20,0x53,0x04,0x01,0x00,0x92, + 0x18,0xd1,0x0c,0x10,0x04,0x01,0x00,0x01,0xff,0xe3,0x80,0x88,0x00,0x10,0x08,0x01, + 0xff,0xe3,0x80,0x89,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xcf,0x86,0x55,0x04,0x01, + 0x00,0x54,0x04,0x01,0x00,0x53,0x04,0x01,0x00,0xd2,0x0c,0x51,0x04,0x01,0x00,0x10, + 0x04,0x01,0x00,0x04,0x00,0x91,0x08,0x10,0x04,0x06,0x00,0x04,0x00,0x04,0x00,0xd0, + 0x1e,0xcf,0x86,0x95,0x18,0x54,0x04,0x04,0x00,0x53,0x04,0x04,0x00,0x92,0x0c,0x51, + 0x04,0x04,0x00,0x10,0x04,0x04,0x00,0x06,0x00,0x06,0x00,0x06,0x00,0xcf,0x86,0xd5, + 0x2c,0xd4,0x14,0x53,0x04,0x06,0x00,0x52,0x04,0x06,0x00,0x51,0x04,0x06,0x00,0x10, + 0x04,0x06,0x00,0x07,0x00,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x07,0x00,0x08, + 0x00,0x08,0x00,0x08,0x00,0x12,0x04,0x08,0x00,0x09,0x00,0xd4,0x14,0x53,0x04,0x09, + 0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x0b,0x00,0x0c,0x00,0x0c,0x00,0x0c,0x00,0xd3, + 0x08,0x12,0x04,0x0c,0x00,0x10,0x00,0xd2,0x0c,0x51,0x04,0x10,0x00,0x10,0x04,0x10, + 0x00,0x12,0x00,0x51,0x04,0x12,0x00,0x10,0x04,0x12,0x00,0x13,0x00,0xd3,0xa6,0xd2, + 0x74,0xd1,0x40,0xd0,0x22,0xcf,0x86,0x55,0x04,0x01,0x00,0x94,0x18,0x93,0x14,0x52, + 0x04,0x01,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x04,0x00,0x10,0x04,0x04,0x00,0x00, + 0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0x95,0x18,0x94,0x14,0x53,0x04,0x01,0x00,0x92, + 0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x01, + 0x00,0xd0,0x06,0xcf,0x06,0x01,0x00,0xcf,0x86,0x55,0x04,0x01,0x00,0xd4,0x14,0x53, + 0x04,0x01,0x00,0x92,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x06,0x00,0x06, + 0x00,0x53,0x04,0x06,0x00,0x52,0x04,0x06,0x00,0x51,0x04,0x06,0x00,0x10,0x04,0x06, + 0x00,0x07,0x00,0xd1,0x06,0xcf,0x06,0x01,0x00,0xd0,0x1a,0xcf,0x86,0x95,0x14,0x54, + 0x04,0x01,0x00,0x93,0x0c,0x52,0x04,0x01,0x00,0x11,0x04,0x01,0x00,0x06,0x00,0x06, + 0x00,0x01,0x00,0xcf,0x86,0x55,0x04,0x01,0x00,0x54,0x04,0x01,0x00,0x13,0x04,0x04, + 0x00,0x06,0x00,0xd2,0xdc,0xd1,0x48,0xd0,0x26,0xcf,0x86,0x95,0x20,0x54,0x04,0x01, + 0x00,0xd3,0x0c,0x52,0x04,0x01,0x00,0x11,0x04,0x07,0x00,0x06,0x00,0x92,0x0c,0x91, + 0x08,0x10,0x04,0x08,0x00,0x04,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xcf,0x86,0x55, + 0x04,0x01,0x00,0x54,0x04,0x01,0x00,0xd3,0x0c,0x92,0x08,0x11,0x04,0x04,0x00,0x06, + 0x00,0x06,0x00,0x52,0x04,0x06,0x00,0x11,0x04,0x06,0x00,0x08,0x00,0xd0,0x5e,0xcf, + 0x86,0xd5,0x2c,0xd4,0x10,0x53,0x04,0x06,0x00,0x92,0x08,0x11,0x04,0x06,0x00,0x07, + 0x00,0x07,0x00,0xd3,0x0c,0x92,0x08,0x11,0x04,0x07,0x00,0x08,0x00,0x08,0x00,0x52, + 0x04,0x08,0x00,0x91,0x08,0x10,0x04,0x08,0x00,0x0a,0x00,0x0b,0x00,0xd4,0x10,0x93, + 0x0c,0x92,0x08,0x11,0x04,0x07,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0xd3,0x10,0x92, + 0x0c,0x51,0x04,0x08,0x00,0x10,0x04,0x09,0x00,0x0a,0x00,0x0a,0x00,0x52,0x04,0x0a, + 0x00,0x91,0x08,0x10,0x04,0x0a,0x00,0x0b,0x00,0x0b,0x00,0xcf,0x86,0xd5,0x1c,0x94, + 0x18,0xd3,0x08,0x12,0x04,0x0a,0x00,0x0b,0x00,0x52,0x04,0x0b,0x00,0x51,0x04,0x0b, + 0x00,0x10,0x04,0x0c,0x00,0x0b,0x00,0x0b,0x00,0x94,0x14,0x93,0x10,0x92,0x0c,0x51, + 0x04,0x0b,0x00,0x10,0x04,0x0c,0x00,0x0b,0x00,0x0c,0x00,0x0b,0x00,0x0b,0x00,0xd1, + 0xa8,0xd0,0x42,0xcf,0x86,0xd5,0x28,0x94,0x24,0xd3,0x18,0xd2,0x0c,0x91,0x08,0x10, + 0x04,0x10,0x00,0x01,0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x01,0x00,0x0c,0x00,0x01, + 0x00,0x92,0x08,0x11,0x04,0x01,0x00,0x0c,0x00,0x01,0x00,0x01,0x00,0x94,0x14,0x53, + 0x04,0x01,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x0c,0x00,0x01,0x00,0x01,0x00,0x01, + 0x00,0x01,0x00,0xcf,0x86,0xd5,0x40,0xd4,0x18,0x53,0x04,0x01,0x00,0x52,0x04,0x01, + 0x00,0xd1,0x08,0x10,0x04,0x0c,0x00,0x01,0x00,0x10,0x04,0x0c,0x00,0x01,0x00,0xd3, + 0x18,0xd2,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x0c,0x00,0x51,0x04,0x0c, + 0x00,0x10,0x04,0x01,0x00,0x0b,0x00,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10, + 0x04,0x01,0x00,0x0c,0x00,0xd4,0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x0c, + 0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x06,0x00,0x93,0x0c,0x52,0x04,0x06,0x00,0x11, + 0x04,0x06,0x00,0x01,0x00,0x01,0x00,0xd0,0x3e,0xcf,0x86,0xd5,0x18,0x54,0x04,0x01, + 0x00,0x93,0x10,0x52,0x04,0x01,0x00,0x91,0x08,0x10,0x04,0x01,0x00,0x0c,0x00,0x0c, + 0x00,0x01,0x00,0x54,0x04,0x01,0x00,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x0c, + 0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10, + 0x04,0x01,0x00,0x0c,0x00,0xcf,0x86,0xd5,0x2c,0x94,0x28,0xd3,0x10,0x52,0x04,0x08, + 0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x09,0x00,0xd2,0x0c,0x51,0x04,0x09, + 0x00,0x10,0x04,0x09,0x00,0x0d,0x00,0x91,0x08,0x10,0x04,0x0a,0x00,0x0d,0x00,0x0c, + 0x00,0x06,0x00,0x94,0x0c,0x53,0x04,0x06,0x00,0x12,0x04,0x06,0x00,0x0a,0x00,0x06, + 0x00,0xe4,0x39,0x01,0xd3,0x0c,0xd2,0x06,0xcf,0x06,0x04,0x00,0xcf,0x06,0x06,0x00, + 0xd2,0x30,0xd1,0x06,0xcf,0x06,0x06,0x00,0xd0,0x06,0xcf,0x06,0x06,0x00,0xcf,0x86, + 0x95,0x1e,0x54,0x04,0x06,0x00,0x53,0x04,0x06,0x00,0x52,0x04,0x06,0x00,0x91,0x0e, + 0x10,0x0a,0x06,0xff,0xe2,0xab,0x9d,0xcc,0xb8,0x00,0x06,0x00,0x06,0x00,0x06,0x00, + 0xd1,0x80,0xd0,0x3a,0xcf,0x86,0xd5,0x28,0xd4,0x10,0x53,0x04,0x07,0x00,0x52,0x04, + 0x07,0x00,0x11,0x04,0x07,0x00,0x08,0x00,0xd3,0x08,0x12,0x04,0x08,0x00,0x09,0x00, + 0x92,0x0c,0x51,0x04,0x09,0x00,0x10,0x04,0x09,0x00,0x0a,0x00,0x0a,0x00,0x94,0x0c, + 0x93,0x08,0x12,0x04,0x09,0x00,0x0a,0x00,0x0a,0x00,0x0a,0x00,0xcf,0x86,0xd5,0x30, + 0xd4,0x14,0x53,0x04,0x0a,0x00,0x52,0x04,0x0a,0x00,0x91,0x08,0x10,0x04,0x0a,0x00, + 0x10,0x00,0x10,0x00,0xd3,0x10,0x52,0x04,0x0a,0x00,0x91,0x08,0x10,0x04,0x0a,0x00, + 0x0b,0x00,0x0b,0x00,0x92,0x08,0x11,0x04,0x0b,0x00,0x10,0x00,0x10,0x00,0x54,0x04, + 0x10,0x00,0x93,0x0c,0x52,0x04,0x10,0x00,0x11,0x04,0x00,0x00,0x10,0x00,0x10,0x00, + 0xd0,0x32,0xcf,0x86,0xd5,0x14,0x54,0x04,0x10,0x00,0x93,0x0c,0x52,0x04,0x10,0x00, + 0x11,0x04,0x10,0x00,0x00,0x00,0x10,0x00,0x54,0x04,0x10,0x00,0x53,0x04,0x10,0x00, + 0xd2,0x08,0x11,0x04,0x10,0x00,0x14,0x00,0x91,0x08,0x10,0x04,0x14,0x00,0x10,0x00, + 0x10,0x00,0xcf,0x86,0xd5,0x28,0xd4,0x14,0x53,0x04,0x10,0x00,0x92,0x0c,0x91,0x08, + 0x10,0x04,0x10,0x00,0x15,0x00,0x10,0x00,0x10,0x00,0x93,0x10,0x92,0x0c,0x51,0x04, + 0x10,0x00,0x10,0x04,0x13,0x00,0x14,0x00,0x14,0x00,0x14,0x00,0xd4,0x0c,0x53,0x04, + 0x14,0x00,0x12,0x04,0x14,0x00,0x11,0x00,0x53,0x04,0x14,0x00,0x52,0x04,0x14,0x00, + 0x51,0x04,0x14,0x00,0x10,0x04,0x14,0x00,0x15,0x00,0xe3,0xb9,0x01,0xd2,0xac,0xd1, + 0x68,0xd0,0x1e,0xcf,0x86,0x55,0x04,0x08,0x00,0x94,0x14,0x53,0x04,0x08,0x00,0x52, + 0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x00,0x00,0x08,0x00,0xcf, + 0x86,0xd5,0x18,0x54,0x04,0x08,0x00,0x53,0x04,0x08,0x00,0x52,0x04,0x08,0x00,0x51, + 0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x00,0x00,0xd4,0x14,0x53,0x04,0x09,0x00,0x52, + 0x04,0x09,0x00,0x91,0x08,0x10,0x04,0x09,0x00,0x0a,0x00,0x0a,0x00,0xd3,0x10,0x92, + 0x0c,0x91,0x08,0x10,0x04,0x0b,0x00,0x0a,0x00,0x0a,0x00,0x09,0x00,0x52,0x04,0x0a, + 0x00,0x11,0x04,0x0a,0x00,0x0b,0x00,0xd0,0x06,0xcf,0x06,0x08,0x00,0xcf,0x86,0x55, + 0x04,0x08,0x00,0xd4,0x1c,0x53,0x04,0x08,0x00,0xd2,0x0c,0x51,0x04,0x08,0x00,0x10, + 0x04,0x08,0x00,0x0b,0x00,0x51,0x04,0x0b,0x00,0x10,0x04,0x0b,0x00,0x0b,0xe6,0xd3, + 0x0c,0x92,0x08,0x11,0x04,0x0b,0xe6,0x0d,0x00,0x00,0x00,0x92,0x0c,0x91,0x08,0x10, + 0x04,0x00,0x00,0x08,0x00,0x08,0x00,0x08,0x00,0xd1,0x6c,0xd0,0x2a,0xcf,0x86,0x55, + 0x04,0x08,0x00,0x94,0x20,0xd3,0x10,0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10, + 0x04,0x00,0x00,0x0d,0x00,0x52,0x04,0x00,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x0d, + 0x00,0x00,0x00,0x08,0x00,0xcf,0x86,0x55,0x04,0x08,0x00,0xd4,0x1c,0xd3,0x0c,0x52, + 0x04,0x08,0x00,0x11,0x04,0x08,0x00,0x0d,0x00,0x52,0x04,0x00,0x00,0x51,0x04,0x00, + 0x00,0x10,0x04,0x00,0x00,0x08,0x00,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x0c, + 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x52,0x04,0x00,0x00,0x51,0x04,0x00,0x00,0x10, + 0x04,0x00,0x00,0x0c,0x09,0xd0,0x5a,0xcf,0x86,0xd5,0x18,0x54,0x04,0x08,0x00,0x93, + 0x10,0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x00,0x00,0x00, + 0x00,0xd4,0x20,0xd3,0x10,0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08, + 0x00,0x00,0x00,0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x00, + 0x00,0xd3,0x10,0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x00, + 0x00,0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x00,0x00,0xcf, + 0x86,0x95,0x40,0xd4,0x20,0xd3,0x10,0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10, + 0x04,0x08,0x00,0x00,0x00,0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08, + 0x00,0x00,0x00,0xd3,0x10,0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08, + 0x00,0x00,0x00,0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x00, + 0x00,0x0a,0xe6,0xd2,0x9c,0xd1,0x68,0xd0,0x32,0xcf,0x86,0xd5,0x14,0x54,0x04,0x08, + 0x00,0x53,0x04,0x08,0x00,0x52,0x04,0x0a,0x00,0x11,0x04,0x08,0x00,0x0a,0x00,0x54, + 0x04,0x0a,0x00,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x0a,0x00,0x0b,0x00,0x0d, + 0x00,0x0d,0x00,0x12,0x04,0x0d,0x00,0x10,0x00,0xcf,0x86,0x95,0x30,0x94,0x2c,0xd3, + 0x18,0xd2,0x0c,0x51,0x04,0x10,0x00,0x10,0x04,0x10,0x00,0x12,0x00,0x91,0x08,0x10, + 0x04,0x12,0x00,0x13,0x00,0x13,0x00,0xd2,0x08,0x11,0x04,0x13,0x00,0x14,0x00,0x51, + 0x04,0x14,0x00,0x10,0x04,0x14,0x00,0x15,0x00,0x00,0x00,0x00,0x00,0xd0,0x1e,0xcf, + 0x86,0x95,0x18,0x54,0x04,0x04,0x00,0x53,0x04,0x04,0x00,0x92,0x0c,0x51,0x04,0x04, + 0x00,0x10,0x04,0x00,0x00,0x04,0x00,0x04,0x00,0x04,0x00,0xcf,0x86,0x55,0x04,0x04, + 0x00,0x54,0x04,0x04,0x00,0x93,0x08,0x12,0x04,0x04,0x00,0x00,0x00,0x00,0x00,0xd1, + 0x06,0xcf,0x06,0x04,0x00,0xd0,0x06,0xcf,0x06,0x04,0x00,0xcf,0x86,0xd5,0x14,0x54, + 0x04,0x04,0x00,0x93,0x0c,0x52,0x04,0x04,0x00,0x11,0x04,0x04,0x00,0x00,0x00,0x00, + 0x00,0x54,0x04,0x00,0x00,0x53,0x04,0x04,0x00,0x12,0x04,0x04,0x00,0x00,0x00,0xcf, + 0x86,0xe5,0xa6,0x05,0xe4,0x9f,0x05,0xe3,0x96,0x04,0xe2,0xe4,0x03,0xe1,0xc0,0x01, + 0xd0,0x3e,0xcf,0x86,0x55,0x04,0x01,0x00,0xd4,0x1c,0x53,0x04,0x01,0x00,0xd2,0x0c, + 0x51,0x04,0x01,0x00,0x10,0x04,0x01,0xda,0x01,0xe4,0x91,0x08,0x10,0x04,0x01,0xe8, + 0x01,0xde,0x01,0xe0,0x53,0x04,0x01,0x00,0xd2,0x0c,0x51,0x04,0x04,0x00,0x10,0x04, + 0x04,0x00,0x06,0x00,0x51,0x04,0x06,0x00,0x10,0x04,0x04,0x00,0x01,0x00,0xcf,0x86, + 0xd5,0xaa,0xd4,0x32,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x01,0x00, + 0x01,0x00,0x01,0x00,0x52,0x04,0x01,0x00,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3,0x81, + 0x8b,0xe3,0x82,0x99,0x00,0x01,0x00,0x10,0x0b,0x01,0xff,0xe3,0x81,0x8d,0xe3,0x82, + 0x99,0x00,0x01,0x00,0xd3,0x3c,0xd2,0x1e,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3,0x81, + 0x8f,0xe3,0x82,0x99,0x00,0x01,0x00,0x10,0x0b,0x01,0xff,0xe3,0x81,0x91,0xe3,0x82, + 0x99,0x00,0x01,0x00,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3,0x81,0x93,0xe3,0x82,0x99, + 0x00,0x01,0x00,0x10,0x0b,0x01,0xff,0xe3,0x81,0x95,0xe3,0x82,0x99,0x00,0x01,0x00, + 0xd2,0x1e,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3,0x81,0x97,0xe3,0x82,0x99,0x00,0x01, + 0x00,0x10,0x0b,0x01,0xff,0xe3,0x81,0x99,0xe3,0x82,0x99,0x00,0x01,0x00,0xd1,0x0f, + 0x10,0x0b,0x01,0xff,0xe3,0x81,0x9b,0xe3,0x82,0x99,0x00,0x01,0x00,0x10,0x0b,0x01, + 0xff,0xe3,0x81,0x9d,0xe3,0x82,0x99,0x00,0x01,0x00,0xd4,0x53,0xd3,0x3c,0xd2,0x1e, + 0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3,0x81,0x9f,0xe3,0x82,0x99,0x00,0x01,0x00,0x10, + 0x0b,0x01,0xff,0xe3,0x81,0xa1,0xe3,0x82,0x99,0x00,0x01,0x00,0xd1,0x0f,0x10,0x04, + 0x01,0x00,0x01,0xff,0xe3,0x81,0xa4,0xe3,0x82,0x99,0x00,0x10,0x04,0x01,0x00,0x01, + 0xff,0xe3,0x81,0xa6,0xe3,0x82,0x99,0x00,0x92,0x13,0x91,0x0f,0x10,0x04,0x01,0x00, + 0x01,0xff,0xe3,0x81,0xa8,0xe3,0x82,0x99,0x00,0x01,0x00,0x01,0x00,0xd3,0x4a,0xd2, + 0x25,0xd1,0x16,0x10,0x0b,0x01,0xff,0xe3,0x81,0xaf,0xe3,0x82,0x99,0x00,0x01,0xff, + 0xe3,0x81,0xaf,0xe3,0x82,0x9a,0x00,0x10,0x04,0x01,0x00,0x01,0xff,0xe3,0x81,0xb2, + 0xe3,0x82,0x99,0x00,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3,0x81,0xb2,0xe3,0x82,0x9a, + 0x00,0x01,0x00,0x10,0x0b,0x01,0xff,0xe3,0x81,0xb5,0xe3,0x82,0x99,0x00,0x01,0xff, + 0xe3,0x81,0xb5,0xe3,0x82,0x9a,0x00,0xd2,0x1e,0xd1,0x0f,0x10,0x04,0x01,0x00,0x01, + 0xff,0xe3,0x81,0xb8,0xe3,0x82,0x99,0x00,0x10,0x0b,0x01,0xff,0xe3,0x81,0xb8,0xe3, + 0x82,0x9a,0x00,0x01,0x00,0x91,0x16,0x10,0x0b,0x01,0xff,0xe3,0x81,0xbb,0xe3,0x82, + 0x99,0x00,0x01,0xff,0xe3,0x81,0xbb,0xe3,0x82,0x9a,0x00,0x01,0x00,0xd0,0xee,0xcf, + 0x86,0xd5,0x42,0x54,0x04,0x01,0x00,0xd3,0x1b,0x52,0x04,0x01,0x00,0xd1,0x0f,0x10, + 0x0b,0x01,0xff,0xe3,0x81,0x86,0xe3,0x82,0x99,0x00,0x06,0x00,0x10,0x04,0x06,0x00, + 0x00,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04,0x00,0x00,0x01,0x08,0x10,0x04,0x01,0x08, + 0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x0b,0x01,0xff,0xe3,0x82,0x9d,0xe3,0x82,0x99, + 0x00,0x06,0x00,0xd4,0x32,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x06,0x00,0x01, + 0x00,0x01,0x00,0x01,0x00,0x52,0x04,0x01,0x00,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3, + 0x82,0xab,0xe3,0x82,0x99,0x00,0x01,0x00,0x10,0x0b,0x01,0xff,0xe3,0x82,0xad,0xe3, + 0x82,0x99,0x00,0x01,0x00,0xd3,0x3c,0xd2,0x1e,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3, + 0x82,0xaf,0xe3,0x82,0x99,0x00,0x01,0x00,0x10,0x0b,0x01,0xff,0xe3,0x82,0xb1,0xe3, + 0x82,0x99,0x00,0x01,0x00,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3,0x82,0xb3,0xe3,0x82, + 0x99,0x00,0x01,0x00,0x10,0x0b,0x01,0xff,0xe3,0x82,0xb5,0xe3,0x82,0x99,0x00,0x01, + 0x00,0xd2,0x1e,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3,0x82,0xb7,0xe3,0x82,0x99,0x00, + 0x01,0x00,0x10,0x0b,0x01,0xff,0xe3,0x82,0xb9,0xe3,0x82,0x99,0x00,0x01,0x00,0xd1, + 0x0f,0x10,0x0b,0x01,0xff,0xe3,0x82,0xbb,0xe3,0x82,0x99,0x00,0x01,0x00,0x10,0x0b, + 0x01,0xff,0xe3,0x82,0xbd,0xe3,0x82,0x99,0x00,0x01,0x00,0xcf,0x86,0xd5,0xd5,0xd4, + 0x53,0xd3,0x3c,0xd2,0x1e,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3,0x82,0xbf,0xe3,0x82, + 0x99,0x00,0x01,0x00,0x10,0x0b,0x01,0xff,0xe3,0x83,0x81,0xe3,0x82,0x99,0x00,0x01, + 0x00,0xd1,0x0f,0x10,0x04,0x01,0x00,0x01,0xff,0xe3,0x83,0x84,0xe3,0x82,0x99,0x00, + 0x10,0x04,0x01,0x00,0x01,0xff,0xe3,0x83,0x86,0xe3,0x82,0x99,0x00,0x92,0x13,0x91, + 0x0f,0x10,0x04,0x01,0x00,0x01,0xff,0xe3,0x83,0x88,0xe3,0x82,0x99,0x00,0x01,0x00, + 0x01,0x00,0xd3,0x4a,0xd2,0x25,0xd1,0x16,0x10,0x0b,0x01,0xff,0xe3,0x83,0x8f,0xe3, + 0x82,0x99,0x00,0x01,0xff,0xe3,0x83,0x8f,0xe3,0x82,0x9a,0x00,0x10,0x04,0x01,0x00, + 0x01,0xff,0xe3,0x83,0x92,0xe3,0x82,0x99,0x00,0xd1,0x0f,0x10,0x0b,0x01,0xff,0xe3, + 0x83,0x92,0xe3,0x82,0x9a,0x00,0x01,0x00,0x10,0x0b,0x01,0xff,0xe3,0x83,0x95,0xe3, + 0x82,0x99,0x00,0x01,0xff,0xe3,0x83,0x95,0xe3,0x82,0x9a,0x00,0xd2,0x1e,0xd1,0x0f, + 0x10,0x04,0x01,0x00,0x01,0xff,0xe3,0x83,0x98,0xe3,0x82,0x99,0x00,0x10,0x0b,0x01, + 0xff,0xe3,0x83,0x98,0xe3,0x82,0x9a,0x00,0x01,0x00,0x91,0x16,0x10,0x0b,0x01,0xff, + 0xe3,0x83,0x9b,0xe3,0x82,0x99,0x00,0x01,0xff,0xe3,0x83,0x9b,0xe3,0x82,0x9a,0x00, + 0x01,0x00,0x54,0x04,0x01,0x00,0xd3,0x22,0x52,0x04,0x01,0x00,0xd1,0x0f,0x10,0x0b, + 0x01,0xff,0xe3,0x82,0xa6,0xe3,0x82,0x99,0x00,0x01,0x00,0x10,0x04,0x01,0x00,0x01, + 0xff,0xe3,0x83,0xaf,0xe3,0x82,0x99,0x00,0xd2,0x25,0xd1,0x16,0x10,0x0b,0x01,0xff, + 0xe3,0x83,0xb0,0xe3,0x82,0x99,0x00,0x01,0xff,0xe3,0x83,0xb1,0xe3,0x82,0x99,0x00, + 0x10,0x0b,0x01,0xff,0xe3,0x83,0xb2,0xe3,0x82,0x99,0x00,0x01,0x00,0x51,0x04,0x01, + 0x00,0x10,0x0b,0x01,0xff,0xe3,0x83,0xbd,0xe3,0x82,0x99,0x00,0x06,0x00,0xd1,0x65, + 0xd0,0x46,0xcf,0x86,0xd5,0x18,0x94,0x14,0x93,0x10,0x52,0x04,0x00,0x00,0x91,0x08, + 0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd4,0x18,0x53,0x04, + 0x01,0x00,0x52,0x04,0x01,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x0a,0x00,0x10,0x04, + 0x13,0x00,0x14,0x00,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x01,0x00, + 0x01,0x00,0x01,0x00,0x01,0x00,0xcf,0x86,0x55,0x04,0x01,0x00,0x94,0x15,0x93,0x11, + 0x52,0x04,0x01,0x00,0x91,0x09,0x10,0x05,0x01,0xff,0x00,0x01,0x00,0x01,0x00,0x01, + 0x00,0x01,0x00,0xd0,0x32,0xcf,0x86,0xd5,0x18,0x94,0x14,0x53,0x04,0x01,0x00,0x52, + 0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x54, + 0x04,0x04,0x00,0x53,0x04,0x04,0x00,0x92,0x0c,0x51,0x04,0x0c,0x00,0x10,0x04,0x0c, + 0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0xd5,0x08,0x14,0x04,0x08,0x00,0x0a,0x00,0x94, + 0x0c,0x93,0x08,0x12,0x04,0x0a,0x00,0x00,0x00,0x00,0x00,0x06,0x00,0xd2,0xa4,0xd1, + 0x5c,0xd0,0x22,0xcf,0x86,0x95,0x1c,0x54,0x04,0x01,0x00,0x53,0x04,0x01,0x00,0x52, + 0x04,0x01,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x07,0x00,0x10,0x04,0x07,0x00,0x00, + 0x00,0x01,0x00,0xcf,0x86,0xd5,0x20,0xd4,0x0c,0x93,0x08,0x12,0x04,0x01,0x00,0x0b, + 0x00,0x0b,0x00,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x07,0x00,0x06,0x00,0x06, + 0x00,0x06,0x00,0x06,0x00,0x54,0x04,0x01,0x00,0x53,0x04,0x01,0x00,0x52,0x04,0x01, + 0x00,0x51,0x04,0x07,0x00,0x10,0x04,0x08,0x00,0x01,0x00,0xd0,0x1e,0xcf,0x86,0x55, + 0x04,0x01,0x00,0x54,0x04,0x01,0x00,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x01, + 0x00,0x06,0x00,0x06,0x00,0x06,0x00,0x06,0x00,0xcf,0x86,0xd5,0x10,0x94,0x0c,0x53, + 0x04,0x01,0x00,0x12,0x04,0x01,0x00,0x07,0x00,0x01,0x00,0x54,0x04,0x01,0x00,0x53, + 0x04,0x01,0x00,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x16, + 0x00,0xd1,0x30,0xd0,0x06,0xcf,0x06,0x01,0x00,0xcf,0x86,0x55,0x04,0x01,0x00,0x54, + 0x04,0x01,0x00,0xd3,0x10,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01, + 0x00,0x07,0x00,0x92,0x0c,0x51,0x04,0x07,0x00,0x10,0x04,0x07,0x00,0x01,0x00,0x01, + 0x00,0xd0,0x06,0xcf,0x06,0x01,0x00,0xcf,0x86,0xd5,0x14,0x54,0x04,0x01,0x00,0x53, + 0x04,0x01,0x00,0x52,0x04,0x01,0x00,0x11,0x04,0x01,0x00,0x07,0x00,0x54,0x04,0x01, + 0x00,0x53,0x04,0x01,0x00,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01, + 0x00,0x07,0x00,0xcf,0x06,0x04,0x00,0xcf,0x06,0x04,0x00,0xd1,0x48,0xd0,0x40,0xcf, + 0x86,0xd5,0x06,0xcf,0x06,0x04,0x00,0xd4,0x06,0xcf,0x06,0x04,0x00,0xd3,0x2c,0xd2, + 0x06,0xcf,0x06,0x04,0x00,0xd1,0x06,0xcf,0x06,0x04,0x00,0xd0,0x1a,0xcf,0x86,0x55, + 0x04,0x04,0x00,0x54,0x04,0x04,0x00,0x93,0x0c,0x52,0x04,0x04,0x00,0x11,0x04,0x04, + 0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x07,0x00,0xcf,0x06,0x01,0x00,0xcf,0x86,0xcf, + 0x06,0x01,0x00,0xcf,0x86,0xcf,0x06,0x01,0x00,0xe2,0x71,0x05,0xd1,0x8c,0xd0,0x08, + 0xcf,0x86,0xcf,0x06,0x01,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x01,0x00,0xd4,0x06, + 0xcf,0x06,0x01,0x00,0xd3,0x06,0xcf,0x06,0x01,0x00,0xd2,0x06,0xcf,0x06,0x01,0x00, + 0xd1,0x06,0xcf,0x06,0x01,0x00,0xd0,0x22,0xcf,0x86,0x55,0x04,0x01,0x00,0xd4,0x10, + 0x93,0x0c,0x52,0x04,0x01,0x00,0x11,0x04,0x01,0x00,0x08,0x00,0x08,0x00,0x53,0x04, + 0x08,0x00,0x12,0x04,0x08,0x00,0x0a,0x00,0xcf,0x86,0xd5,0x28,0xd4,0x18,0xd3,0x08, + 0x12,0x04,0x0a,0x00,0x0b,0x00,0x52,0x04,0x0b,0x00,0x91,0x08,0x10,0x04,0x0d,0x00, + 0x11,0x00,0x11,0x00,0x93,0x0c,0x52,0x04,0x11,0x00,0x11,0x04,0x11,0x00,0x13,0x00, + 0x13,0x00,0x94,0x14,0x53,0x04,0x13,0x00,0x92,0x0c,0x51,0x04,0x13,0x00,0x10,0x04, + 0x13,0x00,0x14,0x00,0x14,0x00,0x00,0x00,0xe0,0xdb,0x04,0xcf,0x86,0xe5,0xdf,0x01, + 0xd4,0x06,0xcf,0x06,0x04,0x00,0xd3,0x74,0xd2,0x6e,0xd1,0x06,0xcf,0x06,0x04,0x00, + 0xd0,0x3e,0xcf,0x86,0xd5,0x18,0x94,0x14,0x53,0x04,0x04,0x00,0x52,0x04,0x04,0x00, + 0x91,0x08,0x10,0x04,0x04,0x00,0x00,0x00,0x00,0x00,0x04,0x00,0xd4,0x10,0x93,0x0c, + 0x92,0x08,0x11,0x04,0x04,0x00,0x06,0x00,0x04,0x00,0x04,0x00,0x93,0x10,0x52,0x04, + 0x04,0x00,0x91,0x08,0x10,0x04,0x06,0x00,0x04,0x00,0x04,0x00,0x04,0x00,0xcf,0x86, + 0x95,0x24,0x94,0x20,0x93,0x1c,0xd2,0x0c,0x91,0x08,0x10,0x04,0x04,0x00,0x06,0x00, + 0x04,0x00,0xd1,0x08,0x10,0x04,0x04,0x00,0x06,0x00,0x10,0x04,0x04,0x00,0x00,0x00, + 0x00,0x00,0x0b,0x00,0x0b,0x00,0xcf,0x06,0x0a,0x00,0xd2,0x84,0xd1,0x4c,0xd0,0x16, + 0xcf,0x86,0x55,0x04,0x0a,0x00,0x94,0x0c,0x53,0x04,0x0a,0x00,0x12,0x04,0x0a,0x00, + 0x00,0x00,0x00,0x00,0xcf,0x86,0x55,0x04,0x0a,0x00,0xd4,0x1c,0xd3,0x0c,0x92,0x08, + 0x11,0x04,0x0c,0x00,0x0a,0x00,0x0a,0x00,0x52,0x04,0x0a,0x00,0x51,0x04,0x0a,0x00, + 0x10,0x04,0x0a,0x00,0x0a,0xe6,0xd3,0x08,0x12,0x04,0x0a,0x00,0x0d,0xe6,0x52,0x04, + 0x0d,0xe6,0x11,0x04,0x0a,0xe6,0x0a,0x00,0xd0,0x1e,0xcf,0x86,0x95,0x18,0x54,0x04, + 0x0a,0x00,0x53,0x04,0x0a,0x00,0x52,0x04,0x10,0x00,0x51,0x04,0x10,0x00,0x10,0x04, + 0x11,0xe6,0x0d,0xe6,0x0b,0x00,0xcf,0x86,0x55,0x04,0x0b,0x00,0x54,0x04,0x0b,0x00, + 0x93,0x0c,0x92,0x08,0x11,0x04,0x0b,0xe6,0x0b,0x00,0x0b,0x00,0x00,0x00,0xd1,0x40, + 0xd0,0x3a,0xcf,0x86,0xd5,0x24,0x54,0x04,0x08,0x00,0xd3,0x10,0x52,0x04,0x08,0x00, + 0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x09,0x00,0x92,0x0c,0x51,0x04,0x09,0x00, + 0x10,0x04,0x09,0x00,0x0a,0x00,0x0a,0x00,0x94,0x10,0x93,0x0c,0x92,0x08,0x11,0x04, + 0x09,0x00,0x0a,0x00,0x0a,0x00,0x0a,0x00,0x0a,0x00,0xcf,0x06,0x0a,0x00,0xd0,0x5e, + 0xcf,0x86,0xd5,0x28,0xd4,0x18,0x53,0x04,0x0a,0x00,0x52,0x04,0x0a,0x00,0xd1,0x08, + 0x10,0x04,0x0a,0x00,0x0c,0x00,0x10,0x04,0x0c,0x00,0x11,0x00,0x93,0x0c,0x92,0x08, + 0x11,0x04,0x0c,0x00,0x0d,0x00,0x10,0x00,0x10,0x00,0xd4,0x1c,0x53,0x04,0x0c,0x00, + 0xd2,0x0c,0x51,0x04,0x0c,0x00,0x10,0x04,0x0d,0x00,0x10,0x00,0x51,0x04,0x10,0x00, + 0x10,0x04,0x12,0x00,0x14,0x00,0xd3,0x0c,0x92,0x08,0x11,0x04,0x10,0x00,0x11,0x00, + 0x11,0x00,0x92,0x08,0x11,0x04,0x14,0x00,0x15,0x00,0x15,0x00,0xcf,0x86,0xd5,0x1c, + 0x94,0x18,0x93,0x14,0xd2,0x08,0x11,0x04,0x00,0x00,0x15,0x00,0x51,0x04,0x15,0x00, + 0x10,0x04,0x15,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x54,0x04,0x00,0x00,0xd3,0x10, + 0x52,0x04,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x10,0x00,0x92,0x0c, + 0x51,0x04,0x0d,0x00,0x10,0x04,0x0c,0x00,0x0a,0x00,0x0a,0x00,0xe4,0xf2,0x02,0xe3, + 0x65,0x01,0xd2,0x98,0xd1,0x48,0xd0,0x36,0xcf,0x86,0xd5,0x18,0x94,0x14,0x93,0x10, + 0x52,0x04,0x08,0x00,0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x09,0x08,0x00,0x08,0x00, + 0x08,0x00,0xd4,0x0c,0x53,0x04,0x08,0x00,0x12,0x04,0x08,0x00,0x00,0x00,0x53,0x04, + 0x0b,0x00,0x92,0x08,0x11,0x04,0x0b,0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0x55,0x04, + 0x09,0x00,0x54,0x04,0x09,0x00,0x13,0x04,0x09,0x00,0x00,0x00,0xd0,0x06,0xcf,0x06, + 0x0a,0x00,0xcf,0x86,0xd5,0x2c,0xd4,0x1c,0xd3,0x10,0x52,0x04,0x0a,0x00,0x91,0x08, + 0x10,0x04,0x0a,0x09,0x12,0x00,0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00, + 0x0a,0x00,0x53,0x04,0x0a,0x00,0x92,0x08,0x11,0x04,0x0a,0x00,0x00,0x00,0x00,0x00, + 0x54,0x04,0x0b,0xe6,0xd3,0x0c,0x92,0x08,0x11,0x04,0x0b,0xe6,0x0b,0x00,0x0b,0x00, + 0x52,0x04,0x0b,0x00,0x11,0x04,0x11,0x00,0x14,0x00,0xd1,0x60,0xd0,0x22,0xcf,0x86, + 0x55,0x04,0x0a,0x00,0x94,0x18,0x53,0x04,0x0a,0x00,0xd2,0x0c,0x51,0x04,0x0a,0x00, + 0x10,0x04,0x0a,0x00,0x0a,0xdc,0x11,0x04,0x0a,0xdc,0x0a,0x00,0x0a,0x00,0xcf,0x86, + 0xd5,0x24,0x54,0x04,0x0a,0x00,0xd3,0x10,0x92,0x0c,0x51,0x04,0x0a,0x00,0x10,0x04, + 0x0a,0x00,0x0a,0x09,0x00,0x00,0x52,0x04,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04, + 0x00,0x00,0x0a,0x00,0x54,0x04,0x0b,0x00,0x53,0x04,0x0b,0x00,0x52,0x04,0x0b,0x00, + 0x91,0x08,0x10,0x04,0x0b,0x00,0x00,0x00,0x00,0x00,0xd0,0x1e,0xcf,0x86,0x55,0x04, + 0x0b,0x00,0x54,0x04,0x0b,0x00,0x93,0x10,0x92,0x0c,0x51,0x04,0x0b,0x00,0x10,0x04, + 0x0b,0x00,0x0b,0x07,0x0b,0x00,0x0b,0x00,0xcf,0x86,0xd5,0x34,0xd4,0x20,0xd3,0x10, + 0x92,0x0c,0x91,0x08,0x10,0x04,0x0b,0x09,0x0b,0x00,0x0b,0x00,0x0b,0x00,0x52,0x04, + 0x0b,0x00,0x51,0x04,0x0b,0x00,0x10,0x04,0x00,0x00,0x0b,0x00,0x53,0x04,0x0b,0x00, + 0xd2,0x08,0x11,0x04,0x0b,0x00,0x00,0x00,0x11,0x04,0x00,0x00,0x0b,0x00,0x54,0x04, + 0x10,0x00,0x53,0x04,0x10,0x00,0x52,0x04,0x10,0x00,0x51,0x04,0x10,0x00,0x10,0x04, + 0x10,0x00,0x00,0x00,0xd2,0xd0,0xd1,0x50,0xd0,0x1e,0xcf,0x86,0x55,0x04,0x0a,0x00, + 0x54,0x04,0x0a,0x00,0x93,0x10,0x52,0x04,0x0a,0x00,0x51,0x04,0x0a,0x00,0x10,0x04, + 0x0a,0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0xd5,0x20,0xd4,0x10,0x53,0x04,0x0a,0x00, + 0x52,0x04,0x0a,0x00,0x11,0x04,0x0a,0x00,0x00,0x00,0x53,0x04,0x0a,0x00,0x92,0x08, + 0x11,0x04,0x0a,0x00,0x00,0x00,0x0a,0x00,0x54,0x04,0x0b,0x00,0x53,0x04,0x0b,0x00, + 0x12,0x04,0x0b,0x00,0x10,0x00,0xd0,0x3a,0xcf,0x86,0x55,0x04,0x0b,0x00,0x54,0x04, + 0x0b,0x00,0xd3,0x1c,0xd2,0x0c,0x91,0x08,0x10,0x04,0x0b,0xe6,0x0b,0x00,0x0b,0xe6, + 0xd1,0x08,0x10,0x04,0x0b,0xdc,0x0b,0x00,0x10,0x04,0x0b,0x00,0x0b,0xe6,0xd2,0x0c, + 0x91,0x08,0x10,0x04,0x0b,0xe6,0x0b,0x00,0x0b,0x00,0x11,0x04,0x0b,0x00,0x0b,0xe6, + 0xcf,0x86,0xd5,0x2c,0xd4,0x18,0x93,0x14,0x92,0x10,0xd1,0x08,0x10,0x04,0x0b,0x00, + 0x0b,0xe6,0x10,0x04,0x0b,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x53,0x04,0x00,0x00, + 0x92,0x0c,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x0b,0x00,0x0b,0x00,0x54,0x04, + 0x0d,0x00,0x93,0x10,0x52,0x04,0x0d,0x00,0x51,0x04,0x0d,0x00,0x10,0x04,0x0d,0x09, + 0x00,0x00,0x00,0x00,0xd1,0x8c,0xd0,0x72,0xcf,0x86,0xd5,0x4c,0xd4,0x30,0xd3,0x18, + 0xd2,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x0c,0x00,0x0c,0x00,0x51,0x04,0x0c,0x00, + 0x10,0x04,0x0c,0x00,0x00,0x00,0xd2,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x0c,0x00, + 0x0c,0x00,0x51,0x04,0x0c,0x00,0x10,0x04,0x0c,0x00,0x00,0x00,0x93,0x18,0xd2,0x0c, + 0x91,0x08,0x10,0x04,0x00,0x00,0x0c,0x00,0x0c,0x00,0x51,0x04,0x0c,0x00,0x10,0x04, + 0x0c,0x00,0x00,0x00,0x00,0x00,0x94,0x20,0xd3,0x10,0x52,0x04,0x0c,0x00,0x51,0x04, + 0x0c,0x00,0x10,0x04,0x0c,0x00,0x00,0x00,0x52,0x04,0x0c,0x00,0x51,0x04,0x0c,0x00, + 0x10,0x04,0x0c,0x00,0x00,0x00,0x10,0x00,0xcf,0x86,0x55,0x04,0x10,0x00,0x94,0x10, + 0x93,0x0c,0x52,0x04,0x11,0x00,0x11,0x04,0x10,0x00,0x15,0x00,0x00,0x00,0x11,0x00, + 0xd0,0x06,0xcf,0x06,0x11,0x00,0xcf,0x86,0x55,0x04,0x0b,0x00,0xd4,0x14,0x53,0x04, + 0x0b,0x00,0x52,0x04,0x0b,0x00,0x91,0x08,0x10,0x04,0x0b,0x00,0x0b,0x09,0x00,0x00, + 0x53,0x04,0x0b,0x00,0x92,0x08,0x11,0x04,0x0b,0x00,0x00,0x00,0x00,0x00,0xcf,0x06, + 0x02,0xff,0xff,0xcf,0x86,0xcf,0x06,0x02,0xff,0xff,0xd1,0x76,0xd0,0x09,0xcf,0x86, + 0xcf,0x06,0x02,0xff,0xff,0xcf,0x86,0x85,0xd4,0x07,0xcf,0x06,0x02,0xff,0xff,0xd3, + 0x07,0xcf,0x06,0x02,0xff,0xff,0xd2,0x07,0xcf,0x06,0x02,0xff,0xff,0xd1,0x07,0xcf, + 0x06,0x02,0xff,0xff,0xd0,0x18,0xcf,0x86,0x55,0x05,0x02,0xff,0xff,0x94,0x0d,0x93, + 0x09,0x12,0x05,0x02,0xff,0xff,0x00,0x00,0x00,0x00,0x0b,0x00,0xcf,0x86,0xd5,0x24, + 0x94,0x20,0xd3,0x10,0x52,0x04,0x0b,0x00,0x51,0x04,0x0b,0x00,0x10,0x04,0x0b,0x00, + 0x00,0x00,0x92,0x0c,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x0b,0x00,0x0b,0x00, + 0x0b,0x00,0x54,0x04,0x0b,0x00,0x53,0x04,0x0b,0x00,0x12,0x04,0x0b,0x00,0x00,0x00, + 0xd0,0x08,0xcf,0x86,0xcf,0x06,0x01,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x01,0x00, + 0xe4,0x9c,0x10,0xe3,0x16,0x08,0xd2,0x06,0xcf,0x06,0x01,0x00,0xe1,0x08,0x04,0xe0, + 0x04,0x02,0xcf,0x86,0xe5,0x01,0x01,0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10, + 0x08,0x01,0xff,0xe8,0xb1,0x88,0x00,0x01,0xff,0xe6,0x9b,0xb4,0x00,0x10,0x08,0x01, + 0xff,0xe8,0xbb,0x8a,0x00,0x01,0xff,0xe8,0xb3,0x88,0x00,0xd1,0x10,0x10,0x08,0x01, + 0xff,0xe6,0xbb,0x91,0x00,0x01,0xff,0xe4,0xb8,0xb2,0x00,0x10,0x08,0x01,0xff,0xe5, + 0x8f,0xa5,0x00,0x01,0xff,0xe9,0xbe,0x9c,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01, + 0xff,0xe9,0xbe,0x9c,0x00,0x01,0xff,0xe5,0xa5,0x91,0x00,0x10,0x08,0x01,0xff,0xe9, + 0x87,0x91,0x00,0x01,0xff,0xe5,0x96,0x87,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe5, + 0xa5,0x88,0x00,0x01,0xff,0xe6,0x87,0xb6,0x00,0x10,0x08,0x01,0xff,0xe7,0x99,0xa9, + 0x00,0x01,0xff,0xe7,0xbe,0x85,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01, + 0xff,0xe8,0x98,0xbf,0x00,0x01,0xff,0xe8,0x9e,0xba,0x00,0x10,0x08,0x01,0xff,0xe8, + 0xa3,0xb8,0x00,0x01,0xff,0xe9,0x82,0x8f,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe6, + 0xa8,0x82,0x00,0x01,0xff,0xe6,0xb4,0x9b,0x00,0x10,0x08,0x01,0xff,0xe7,0x83,0x99, + 0x00,0x01,0xff,0xe7,0x8f,0x9e,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe8, + 0x90,0xbd,0x00,0x01,0xff,0xe9,0x85,0xaa,0x00,0x10,0x08,0x01,0xff,0xe9,0xa7,0xb1, + 0x00,0x01,0xff,0xe4,0xba,0x82,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe5,0x8d,0xb5, + 0x00,0x01,0xff,0xe6,0xac,0x84,0x00,0x10,0x08,0x01,0xff,0xe7,0x88,0x9b,0x00,0x01, + 0xff,0xe8,0x98,0xad,0x00,0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01, + 0xff,0xe9,0xb8,0x9e,0x00,0x01,0xff,0xe5,0xb5,0x90,0x00,0x10,0x08,0x01,0xff,0xe6, + 0xbf,0xab,0x00,0x01,0xff,0xe8,0x97,0x8d,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe8, + 0xa5,0xa4,0x00,0x01,0xff,0xe6,0x8b,0x89,0x00,0x10,0x08,0x01,0xff,0xe8,0x87,0x98, + 0x00,0x01,0xff,0xe8,0xa0,0x9f,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe5, + 0xbb,0x8a,0x00,0x01,0xff,0xe6,0x9c,0x97,0x00,0x10,0x08,0x01,0xff,0xe6,0xb5,0xaa, + 0x00,0x01,0xff,0xe7,0x8b,0xbc,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe9,0x83,0x8e, + 0x00,0x01,0xff,0xe4,0xbe,0x86,0x00,0x10,0x08,0x01,0xff,0xe5,0x86,0xb7,0x00,0x01, + 0xff,0xe5,0x8b,0x9e,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe6, + 0x93,0x84,0x00,0x01,0xff,0xe6,0xab,0x93,0x00,0x10,0x08,0x01,0xff,0xe7,0x88,0x90, + 0x00,0x01,0xff,0xe7,0x9b,0xa7,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe8,0x80,0x81, + 0x00,0x01,0xff,0xe8,0x98,0x86,0x00,0x10,0x08,0x01,0xff,0xe8,0x99,0x9c,0x00,0x01, + 0xff,0xe8,0xb7,0xaf,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe9,0x9c,0xb2, + 0x00,0x01,0xff,0xe9,0xad,0xaf,0x00,0x10,0x08,0x01,0xff,0xe9,0xb7,0xba,0x00,0x01, + 0xff,0xe7,0xa2,0x8c,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe7,0xa5,0xbf,0x00,0x01, + 0xff,0xe7,0xb6,0xa0,0x00,0x10,0x08,0x01,0xff,0xe8,0x8f,0x89,0x00,0x01,0xff,0xe9, + 0x8c,0x84,0x00,0xcf,0x86,0xe5,0x01,0x01,0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10, + 0x10,0x08,0x01,0xff,0xe9,0xb9,0xbf,0x00,0x01,0xff,0xe8,0xab,0x96,0x00,0x10,0x08, + 0x01,0xff,0xe5,0xa3,0x9f,0x00,0x01,0xff,0xe5,0xbc,0x84,0x00,0xd1,0x10,0x10,0x08, + 0x01,0xff,0xe7,0xb1,0xa0,0x00,0x01,0xff,0xe8,0x81,0xbe,0x00,0x10,0x08,0x01,0xff, + 0xe7,0x89,0xa2,0x00,0x01,0xff,0xe7,0xa3,0x8a,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08, + 0x01,0xff,0xe8,0xb3,0x82,0x00,0x01,0xff,0xe9,0x9b,0xb7,0x00,0x10,0x08,0x01,0xff, + 0xe5,0xa3,0x98,0x00,0x01,0xff,0xe5,0xb1,0xa2,0x00,0xd1,0x10,0x10,0x08,0x01,0xff, + 0xe6,0xa8,0x93,0x00,0x01,0xff,0xe6,0xb7,0x9a,0x00,0x10,0x08,0x01,0xff,0xe6,0xbc, + 0x8f,0x00,0x01,0xff,0xe7,0xb4,0xaf,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08, + 0x01,0xff,0xe7,0xb8,0xb7,0x00,0x01,0xff,0xe9,0x99,0x8b,0x00,0x10,0x08,0x01,0xff, + 0xe5,0x8b,0x92,0x00,0x01,0xff,0xe8,0x82,0x8b,0x00,0xd1,0x10,0x10,0x08,0x01,0xff, + 0xe5,0x87,0x9c,0x00,0x01,0xff,0xe5,0x87,0x8c,0x00,0x10,0x08,0x01,0xff,0xe7,0xa8, + 0x9c,0x00,0x01,0xff,0xe7,0xb6,0xbe,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff, + 0xe8,0x8f,0xb1,0x00,0x01,0xff,0xe9,0x99,0xb5,0x00,0x10,0x08,0x01,0xff,0xe8,0xae, + 0x80,0x00,0x01,0xff,0xe6,0x8b,0x8f,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe6,0xa8, + 0x82,0x00,0x01,0xff,0xe8,0xab,0xbe,0x00,0x10,0x08,0x01,0xff,0xe4,0xb8,0xb9,0x00, + 0x01,0xff,0xe5,0xaf,0xa7,0x00,0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08, + 0x01,0xff,0xe6,0x80,0x92,0x00,0x01,0xff,0xe7,0x8e,0x87,0x00,0x10,0x08,0x01,0xff, + 0xe7,0x95,0xb0,0x00,0x01,0xff,0xe5,0x8c,0x97,0x00,0xd1,0x10,0x10,0x08,0x01,0xff, + 0xe7,0xa3,0xbb,0x00,0x01,0xff,0xe4,0xbe,0xbf,0x00,0x10,0x08,0x01,0xff,0xe5,0xbe, + 0xa9,0x00,0x01,0xff,0xe4,0xb8,0x8d,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff, + 0xe6,0xb3,0x8c,0x00,0x01,0xff,0xe6,0x95,0xb8,0x00,0x10,0x08,0x01,0xff,0xe7,0xb4, + 0xa2,0x00,0x01,0xff,0xe5,0x8f,0x83,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe5,0xa1, + 0x9e,0x00,0x01,0xff,0xe7,0x9c,0x81,0x00,0x10,0x08,0x01,0xff,0xe8,0x91,0x89,0x00, + 0x01,0xff,0xe8,0xaa,0xaa,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff, + 0xe6,0xae,0xba,0x00,0x01,0xff,0xe8,0xbe,0xb0,0x00,0x10,0x08,0x01,0xff,0xe6,0xb2, + 0x88,0x00,0x01,0xff,0xe6,0x8b,0xbe,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe8,0x8b, + 0xa5,0x00,0x01,0xff,0xe6,0x8e,0xa0,0x00,0x10,0x08,0x01,0xff,0xe7,0x95,0xa5,0x00, + 0x01,0xff,0xe4,0xba,0xae,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe5,0x85, + 0xa9,0x00,0x01,0xff,0xe5,0x87,0x89,0x00,0x10,0x08,0x01,0xff,0xe6,0xa2,0x81,0x00, + 0x01,0xff,0xe7,0xb3,0xa7,0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe8,0x89,0xaf,0x00, + 0x01,0xff,0xe8,0xab,0x92,0x00,0x10,0x08,0x01,0xff,0xe9,0x87,0x8f,0x00,0x01,0xff, + 0xe5,0x8b,0xb5,0x00,0xe0,0x04,0x02,0xcf,0x86,0xe5,0x01,0x01,0xd4,0x80,0xd3,0x40, + 0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe5,0x91,0x82,0x00,0x01,0xff,0xe5,0xa5, + 0xb3,0x00,0x10,0x08,0x01,0xff,0xe5,0xbb,0xac,0x00,0x01,0xff,0xe6,0x97,0x85,0x00, + 0xd1,0x10,0x10,0x08,0x01,0xff,0xe6,0xbf,0xbe,0x00,0x01,0xff,0xe7,0xa4,0xaa,0x00, + 0x10,0x08,0x01,0xff,0xe9,0x96,0xad,0x00,0x01,0xff,0xe9,0xa9,0xaa,0x00,0xd2,0x20, + 0xd1,0x10,0x10,0x08,0x01,0xff,0xe9,0xba,0x97,0x00,0x01,0xff,0xe9,0xbb,0x8e,0x00, + 0x10,0x08,0x01,0xff,0xe5,0x8a,0x9b,0x00,0x01,0xff,0xe6,0x9b,0x86,0x00,0xd1,0x10, + 0x10,0x08,0x01,0xff,0xe6,0xad,0xb7,0x00,0x01,0xff,0xe8,0xbd,0xa2,0x00,0x10,0x08, + 0x01,0xff,0xe5,0xb9,0xb4,0x00,0x01,0xff,0xe6,0x86,0x90,0x00,0xd3,0x40,0xd2,0x20, + 0xd1,0x10,0x10,0x08,0x01,0xff,0xe6,0x88,0x80,0x00,0x01,0xff,0xe6,0x92,0x9a,0x00, + 0x10,0x08,0x01,0xff,0xe6,0xbc,0xa3,0x00,0x01,0xff,0xe7,0x85,0x89,0x00,0xd1,0x10, + 0x10,0x08,0x01,0xff,0xe7,0x92,0x89,0x00,0x01,0xff,0xe7,0xa7,0x8a,0x00,0x10,0x08, + 0x01,0xff,0xe7,0xb7,0xb4,0x00,0x01,0xff,0xe8,0x81,0xaf,0x00,0xd2,0x20,0xd1,0x10, + 0x10,0x08,0x01,0xff,0xe8,0xbc,0xa6,0x00,0x01,0xff,0xe8,0x93,0xae,0x00,0x10,0x08, + 0x01,0xff,0xe9,0x80,0xa3,0x00,0x01,0xff,0xe9,0x8d,0x8a,0x00,0xd1,0x10,0x10,0x08, + 0x01,0xff,0xe5,0x88,0x97,0x00,0x01,0xff,0xe5,0x8a,0xa3,0x00,0x10,0x08,0x01,0xff, + 0xe5,0x92,0xbd,0x00,0x01,0xff,0xe7,0x83,0x88,0x00,0xd4,0x80,0xd3,0x40,0xd2,0x20, + 0xd1,0x10,0x10,0x08,0x01,0xff,0xe8,0xa3,0x82,0x00,0x01,0xff,0xe8,0xaa,0xaa,0x00, + 0x10,0x08,0x01,0xff,0xe5,0xbb,0x89,0x00,0x01,0xff,0xe5,0xbf,0xb5,0x00,0xd1,0x10, + 0x10,0x08,0x01,0xff,0xe6,0x8d,0xbb,0x00,0x01,0xff,0xe6,0xae,0xae,0x00,0x10,0x08, + 0x01,0xff,0xe7,0xb0,0xbe,0x00,0x01,0xff,0xe7,0x8d,0xb5,0x00,0xd2,0x20,0xd1,0x10, + 0x10,0x08,0x01,0xff,0xe4,0xbb,0xa4,0x00,0x01,0xff,0xe5,0x9b,0xb9,0x00,0x10,0x08, + 0x01,0xff,0xe5,0xaf,0xa7,0x00,0x01,0xff,0xe5,0xb6,0xba,0x00,0xd1,0x10,0x10,0x08, + 0x01,0xff,0xe6,0x80,0x9c,0x00,0x01,0xff,0xe7,0x8e,0xb2,0x00,0x10,0x08,0x01,0xff, + 0xe7,0x91,0xa9,0x00,0x01,0xff,0xe7,0xbe,0x9a,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10, + 0x10,0x08,0x01,0xff,0xe8,0x81,0x86,0x00,0x01,0xff,0xe9,0x88,0xb4,0x00,0x10,0x08, + 0x01,0xff,0xe9,0x9b,0xb6,0x00,0x01,0xff,0xe9,0x9d,0x88,0x00,0xd1,0x10,0x10,0x08, + 0x01,0xff,0xe9,0xa0,0x98,0x00,0x01,0xff,0xe4,0xbe,0x8b,0x00,0x10,0x08,0x01,0xff, + 0xe7,0xa6,0xae,0x00,0x01,0xff,0xe9,0x86,0xb4,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08, + 0x01,0xff,0xe9,0x9a,0xb8,0x00,0x01,0xff,0xe6,0x83,0xa1,0x00,0x10,0x08,0x01,0xff, + 0xe4,0xba,0x86,0x00,0x01,0xff,0xe5,0x83,0x9a,0x00,0xd1,0x10,0x10,0x08,0x01,0xff, + 0xe5,0xaf,0xae,0x00,0x01,0xff,0xe5,0xb0,0xbf,0x00,0x10,0x08,0x01,0xff,0xe6,0x96, + 0x99,0x00,0x01,0xff,0xe6,0xa8,0x82,0x00,0xcf,0x86,0xe5,0x01,0x01,0xd4,0x80,0xd3, + 0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe7,0x87,0x8e,0x00,0x01,0xff,0xe7, + 0x99,0x82,0x00,0x10,0x08,0x01,0xff,0xe8,0x93,0xbc,0x00,0x01,0xff,0xe9,0x81,0xbc, + 0x00,0xd1,0x10,0x10,0x08,0x01,0xff,0xe9,0xbe,0x8d,0x00,0x01,0xff,0xe6,0x9a,0x88, + 0x00,0x10,0x08,0x01,0xff,0xe9,0x98,0xae,0x00,0x01,0xff,0xe5,0x8a,0x89,0x00,0xd2, + 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe6,0x9d,0xbb,0x00,0x01,0xff,0xe6,0x9f,0xb3, + 0x00,0x10,0x08,0x01,0xff,0xe6,0xb5,0x81,0x00,0x01,0xff,0xe6,0xba,0x9c,0x00,0xd1, + 0x10,0x10,0x08,0x01,0xff,0xe7,0x90,0x89,0x00,0x01,0xff,0xe7,0x95,0x99,0x00,0x10, + 0x08,0x01,0xff,0xe7,0xa1,0xab,0x00,0x01,0xff,0xe7,0xb4,0x90,0x00,0xd3,0x40,0xd2, + 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe9,0xa1,0x9e,0x00,0x01,0xff,0xe5,0x85,0xad, + 0x00,0x10,0x08,0x01,0xff,0xe6,0x88,0xae,0x00,0x01,0xff,0xe9,0x99,0xb8,0x00,0xd1, + 0x10,0x10,0x08,0x01,0xff,0xe5,0x80,0xab,0x00,0x01,0xff,0xe5,0xb4,0x99,0x00,0x10, + 0x08,0x01,0xff,0xe6,0xb7,0xaa,0x00,0x01,0xff,0xe8,0xbc,0xaa,0x00,0xd2,0x20,0xd1, + 0x10,0x10,0x08,0x01,0xff,0xe5,0xbe,0x8b,0x00,0x01,0xff,0xe6,0x85,0x84,0x00,0x10, + 0x08,0x01,0xff,0xe6,0xa0,0x97,0x00,0x01,0xff,0xe7,0x8e,0x87,0x00,0xd1,0x10,0x10, + 0x08,0x01,0xff,0xe9,0x9a,0x86,0x00,0x01,0xff,0xe5,0x88,0xa9,0x00,0x10,0x08,0x01, + 0xff,0xe5,0x90,0x8f,0x00,0x01,0xff,0xe5,0xb1,0xa5,0x00,0xd4,0x80,0xd3,0x40,0xd2, + 0x20,0xd1,0x10,0x10,0x08,0x01,0xff,0xe6,0x98,0x93,0x00,0x01,0xff,0xe6,0x9d,0x8e, + 0x00,0x10,0x08,0x01,0xff,0xe6,0xa2,0xa8,0x00,0x01,0xff,0xe6,0xb3,0xa5,0x00,0xd1, + 0x10,0x10,0x08,0x01,0xff,0xe7,0x90,0x86,0x00,0x01,0xff,0xe7,0x97,0xa2,0x00,0x10, + 0x08,0x01,0xff,0xe7,0xbd,0xb9,0x00,0x01,0xff,0xe8,0xa3,0x8f,0x00,0xd2,0x20,0xd1, + 0x10,0x10,0x08,0x01,0xff,0xe8,0xa3,0xa1,0x00,0x01,0xff,0xe9,0x87,0x8c,0x00,0x10, + 0x08,0x01,0xff,0xe9,0x9b,0xa2,0x00,0x01,0xff,0xe5,0x8c,0xbf,0x00,0xd1,0x10,0x10, + 0x08,0x01,0xff,0xe6,0xba,0xba,0x00,0x01,0xff,0xe5,0x90,0x9d,0x00,0x10,0x08,0x01, + 0xff,0xe7,0x87,0x90,0x00,0x01,0xff,0xe7,0x92,0x98,0x00,0xd3,0x40,0xd2,0x20,0xd1, + 0x10,0x10,0x08,0x01,0xff,0xe8,0x97,0xba,0x00,0x01,0xff,0xe9,0x9a,0xa3,0x00,0x10, + 0x08,0x01,0xff,0xe9,0xb1,0x97,0x00,0x01,0xff,0xe9,0xba,0x9f,0x00,0xd1,0x10,0x10, + 0x08,0x01,0xff,0xe6,0x9e,0x97,0x00,0x01,0xff,0xe6,0xb7,0x8b,0x00,0x10,0x08,0x01, + 0xff,0xe8,0x87,0xa8,0x00,0x01,0xff,0xe7,0xab,0x8b,0x00,0xd2,0x20,0xd1,0x10,0x10, + 0x08,0x01,0xff,0xe7,0xac,0xa0,0x00,0x01,0xff,0xe7,0xb2,0x92,0x00,0x10,0x08,0x01, + 0xff,0xe7,0x8b,0x80,0x00,0x01,0xff,0xe7,0x82,0x99,0x00,0xd1,0x10,0x10,0x08,0x01, + 0xff,0xe8,0xad,0x98,0x00,0x01,0xff,0xe4,0xbb,0x80,0x00,0x10,0x08,0x01,0xff,0xe8, + 0x8c,0xb6,0x00,0x01,0xff,0xe5,0x88,0xba,0x00,0xe2,0xad,0x06,0xe1,0xc4,0x03,0xe0, + 0xcb,0x01,0xcf,0x86,0xd5,0xe4,0xd4,0x74,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08, + 0x01,0xff,0xe5,0x88,0x87,0x00,0x01,0xff,0xe5,0xba,0xa6,0x00,0x10,0x08,0x01,0xff, + 0xe6,0x8b,0x93,0x00,0x01,0xff,0xe7,0xb3,0x96,0x00,0xd1,0x10,0x10,0x08,0x01,0xff, + 0xe5,0xae,0x85,0x00,0x01,0xff,0xe6,0xb4,0x9e,0x00,0x10,0x08,0x01,0xff,0xe6,0x9a, + 0xb4,0x00,0x01,0xff,0xe8,0xbc,0xbb,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x01,0xff, + 0xe8,0xa1,0x8c,0x00,0x01,0xff,0xe9,0x99,0x8d,0x00,0x10,0x08,0x01,0xff,0xe8,0xa6, + 0x8b,0x00,0x01,0xff,0xe5,0xbb,0x93,0x00,0x91,0x10,0x10,0x08,0x01,0xff,0xe5,0x85, + 0x80,0x00,0x01,0xff,0xe5,0x97,0x80,0x00,0x01,0x00,0xd3,0x34,0xd2,0x18,0xd1,0x0c, + 0x10,0x08,0x01,0xff,0xe5,0xa1,0x9a,0x00,0x01,0x00,0x10,0x08,0x01,0xff,0xe6,0x99, + 0xb4,0x00,0x01,0x00,0xd1,0x0c,0x10,0x04,0x01,0x00,0x01,0xff,0xe5,0x87,0x9e,0x00, + 0x10,0x08,0x01,0xff,0xe7,0x8c,0xaa,0x00,0x01,0xff,0xe7,0x9b,0x8a,0x00,0xd2,0x20, + 0xd1,0x10,0x10,0x08,0x01,0xff,0xe7,0xa4,0xbc,0x00,0x01,0xff,0xe7,0xa5,0x9e,0x00, + 0x10,0x08,0x01,0xff,0xe7,0xa5,0xa5,0x00,0x01,0xff,0xe7,0xa6,0x8f,0x00,0xd1,0x10, + 0x10,0x08,0x01,0xff,0xe9,0x9d,0x96,0x00,0x01,0xff,0xe7,0xb2,0xbe,0x00,0x10,0x08, + 0x01,0xff,0xe7,0xbe,0xbd,0x00,0x01,0x00,0xd4,0x64,0xd3,0x30,0xd2,0x18,0xd1,0x0c, + 0x10,0x08,0x01,0xff,0xe8,0x98,0x92,0x00,0x01,0x00,0x10,0x08,0x01,0xff,0xe8,0xab, + 0xb8,0x00,0x01,0x00,0xd1,0x0c,0x10,0x04,0x01,0x00,0x01,0xff,0xe9,0x80,0xb8,0x00, + 0x10,0x08,0x01,0xff,0xe9,0x83,0xbd,0x00,0x01,0x00,0xd2,0x14,0x51,0x04,0x01,0x00, + 0x10,0x08,0x01,0xff,0xe9,0xa3,0xaf,0x00,0x01,0xff,0xe9,0xa3,0xbc,0x00,0xd1,0x10, + 0x10,0x08,0x01,0xff,0xe9,0xa4,0xa8,0x00,0x01,0xff,0xe9,0xb6,0xb4,0x00,0x10,0x08, + 0x0d,0xff,0xe9,0x83,0x9e,0x00,0x0d,0xff,0xe9,0x9a,0xb7,0x00,0xd3,0x40,0xd2,0x20, + 0xd1,0x10,0x10,0x08,0x06,0xff,0xe4,0xbe,0xae,0x00,0x06,0xff,0xe5,0x83,0xa7,0x00, + 0x10,0x08,0x06,0xff,0xe5,0x85,0x8d,0x00,0x06,0xff,0xe5,0x8b,0x89,0x00,0xd1,0x10, + 0x10,0x08,0x06,0xff,0xe5,0x8b,0xa4,0x00,0x06,0xff,0xe5,0x8d,0x91,0x00,0x10,0x08, + 0x06,0xff,0xe5,0x96,0x9d,0x00,0x06,0xff,0xe5,0x98,0x86,0x00,0xd2,0x20,0xd1,0x10, + 0x10,0x08,0x06,0xff,0xe5,0x99,0xa8,0x00,0x06,0xff,0xe5,0xa1,0x80,0x00,0x10,0x08, + 0x06,0xff,0xe5,0xa2,0xa8,0x00,0x06,0xff,0xe5,0xb1,0xa4,0x00,0xd1,0x10,0x10,0x08, + 0x06,0xff,0xe5,0xb1,0xae,0x00,0x06,0xff,0xe6,0x82,0x94,0x00,0x10,0x08,0x06,0xff, + 0xe6,0x85,0xa8,0x00,0x06,0xff,0xe6,0x86,0x8e,0x00,0xcf,0x86,0xe5,0x01,0x01,0xd4, + 0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x06,0xff,0xe6,0x87,0xb2,0x00,0x06, + 0xff,0xe6,0x95,0x8f,0x00,0x10,0x08,0x06,0xff,0xe6,0x97,0xa2,0x00,0x06,0xff,0xe6, + 0x9a,0x91,0x00,0xd1,0x10,0x10,0x08,0x06,0xff,0xe6,0xa2,0x85,0x00,0x06,0xff,0xe6, + 0xb5,0xb7,0x00,0x10,0x08,0x06,0xff,0xe6,0xb8,0x9a,0x00,0x06,0xff,0xe6,0xbc,0xa2, + 0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x06,0xff,0xe7,0x85,0xae,0x00,0x06,0xff,0xe7, + 0x88,0xab,0x00,0x10,0x08,0x06,0xff,0xe7,0x90,0xa2,0x00,0x06,0xff,0xe7,0xa2,0x91, + 0x00,0xd1,0x10,0x10,0x08,0x06,0xff,0xe7,0xa4,0xbe,0x00,0x06,0xff,0xe7,0xa5,0x89, + 0x00,0x10,0x08,0x06,0xff,0xe7,0xa5,0x88,0x00,0x06,0xff,0xe7,0xa5,0x90,0x00,0xd3, + 0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x06,0xff,0xe7,0xa5,0x96,0x00,0x06,0xff,0xe7, + 0xa5,0x9d,0x00,0x10,0x08,0x06,0xff,0xe7,0xa6,0x8d,0x00,0x06,0xff,0xe7,0xa6,0x8e, + 0x00,0xd1,0x10,0x10,0x08,0x06,0xff,0xe7,0xa9,0x80,0x00,0x06,0xff,0xe7,0xaa,0x81, + 0x00,0x10,0x08,0x06,0xff,0xe7,0xaf,0x80,0x00,0x06,0xff,0xe7,0xb7,0xb4,0x00,0xd2, + 0x20,0xd1,0x10,0x10,0x08,0x06,0xff,0xe7,0xb8,0x89,0x00,0x06,0xff,0xe7,0xb9,0x81, + 0x00,0x10,0x08,0x06,0xff,0xe7,0xbd,0xb2,0x00,0x06,0xff,0xe8,0x80,0x85,0x00,0xd1, + 0x10,0x10,0x08,0x06,0xff,0xe8,0x87,0xad,0x00,0x06,0xff,0xe8,0x89,0xb9,0x00,0x10, + 0x08,0x06,0xff,0xe8,0x89,0xb9,0x00,0x06,0xff,0xe8,0x91,0x97,0x00,0xd4,0x75,0xd3, + 0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x06,0xff,0xe8,0xa4,0x90,0x00,0x06,0xff,0xe8, + 0xa6,0x96,0x00,0x10,0x08,0x06,0xff,0xe8,0xac,0x81,0x00,0x06,0xff,0xe8,0xac,0xb9, + 0x00,0xd1,0x10,0x10,0x08,0x06,0xff,0xe8,0xb3,0x93,0x00,0x06,0xff,0xe8,0xb4,0x88, + 0x00,0x10,0x08,0x06,0xff,0xe8,0xbe,0xb6,0x00,0x06,0xff,0xe9,0x80,0xb8,0x00,0xd2, + 0x20,0xd1,0x10,0x10,0x08,0x06,0xff,0xe9,0x9b,0xa3,0x00,0x06,0xff,0xe9,0x9f,0xbf, + 0x00,0x10,0x08,0x06,0xff,0xe9,0xa0,0xbb,0x00,0x0b,0xff,0xe6,0x81,0xb5,0x00,0x91, + 0x11,0x10,0x09,0x0b,0xff,0xf0,0xa4,0x8b,0xae,0x00,0x0b,0xff,0xe8,0x88,0x98,0x00, + 0x00,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x08,0xff,0xe4,0xb8,0xa6,0x00, + 0x08,0xff,0xe5,0x86,0xb5,0x00,0x10,0x08,0x08,0xff,0xe5,0x85,0xa8,0x00,0x08,0xff, + 0xe4,0xbe,0x80,0x00,0xd1,0x10,0x10,0x08,0x08,0xff,0xe5,0x85,0x85,0x00,0x08,0xff, + 0xe5,0x86,0x80,0x00,0x10,0x08,0x08,0xff,0xe5,0x8b,0x87,0x00,0x08,0xff,0xe5,0x8b, + 0xba,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x08,0xff,0xe5,0x96,0x9d,0x00,0x08,0xff, + 0xe5,0x95,0x95,0x00,0x10,0x08,0x08,0xff,0xe5,0x96,0x99,0x00,0x08,0xff,0xe5,0x97, + 0xa2,0x00,0xd1,0x10,0x10,0x08,0x08,0xff,0xe5,0xa1,0x9a,0x00,0x08,0xff,0xe5,0xa2, + 0xb3,0x00,0x10,0x08,0x08,0xff,0xe5,0xa5,0x84,0x00,0x08,0xff,0xe5,0xa5,0x94,0x00, + 0xe0,0x04,0x02,0xcf,0x86,0xe5,0x01,0x01,0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10, + 0x10,0x08,0x08,0xff,0xe5,0xa9,0xa2,0x00,0x08,0xff,0xe5,0xac,0xa8,0x00,0x10,0x08, + 0x08,0xff,0xe5,0xbb,0x92,0x00,0x08,0xff,0xe5,0xbb,0x99,0x00,0xd1,0x10,0x10,0x08, + 0x08,0xff,0xe5,0xbd,0xa9,0x00,0x08,0xff,0xe5,0xbe,0xad,0x00,0x10,0x08,0x08,0xff, + 0xe6,0x83,0x98,0x00,0x08,0xff,0xe6,0x85,0x8e,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08, + 0x08,0xff,0xe6,0x84,0x88,0x00,0x08,0xff,0xe6,0x86,0x8e,0x00,0x10,0x08,0x08,0xff, + 0xe6,0x85,0xa0,0x00,0x08,0xff,0xe6,0x87,0xb2,0x00,0xd1,0x10,0x10,0x08,0x08,0xff, + 0xe6,0x88,0xb4,0x00,0x08,0xff,0xe6,0x8f,0x84,0x00,0x10,0x08,0x08,0xff,0xe6,0x90, + 0x9c,0x00,0x08,0xff,0xe6,0x91,0x92,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08, + 0x08,0xff,0xe6,0x95,0x96,0x00,0x08,0xff,0xe6,0x99,0xb4,0x00,0x10,0x08,0x08,0xff, + 0xe6,0x9c,0x97,0x00,0x08,0xff,0xe6,0x9c,0x9b,0x00,0xd1,0x10,0x10,0x08,0x08,0xff, + 0xe6,0x9d,0x96,0x00,0x08,0xff,0xe6,0xad,0xb9,0x00,0x10,0x08,0x08,0xff,0xe6,0xae, + 0xba,0x00,0x08,0xff,0xe6,0xb5,0x81,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x08,0xff, + 0xe6,0xbb,0x9b,0x00,0x08,0xff,0xe6,0xbb,0x8b,0x00,0x10,0x08,0x08,0xff,0xe6,0xbc, + 0xa2,0x00,0x08,0xff,0xe7,0x80,0x9e,0x00,0xd1,0x10,0x10,0x08,0x08,0xff,0xe7,0x85, + 0xae,0x00,0x08,0xff,0xe7,0x9e,0xa7,0x00,0x10,0x08,0x08,0xff,0xe7,0x88,0xb5,0x00, + 0x08,0xff,0xe7,0x8a,0xaf,0x00,0xd4,0x80,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08, + 0x08,0xff,0xe7,0x8c,0xaa,0x00,0x08,0xff,0xe7,0x91,0xb1,0x00,0x10,0x08,0x08,0xff, + 0xe7,0x94,0x86,0x00,0x08,0xff,0xe7,0x94,0xbb,0x00,0xd1,0x10,0x10,0x08,0x08,0xff, + 0xe7,0x98,0x9d,0x00,0x08,0xff,0xe7,0x98,0x9f,0x00,0x10,0x08,0x08,0xff,0xe7,0x9b, + 0x8a,0x00,0x08,0xff,0xe7,0x9b,0x9b,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x08,0xff, + 0xe7,0x9b,0xb4,0x00,0x08,0xff,0xe7,0x9d,0x8a,0x00,0x10,0x08,0x08,0xff,0xe7,0x9d, + 0x80,0x00,0x08,0xff,0xe7,0xa3,0x8c,0x00,0xd1,0x10,0x10,0x08,0x08,0xff,0xe7,0xaa, + 0xb1,0x00,0x08,0xff,0xe7,0xaf,0x80,0x00,0x10,0x08,0x08,0xff,0xe7,0xb1,0xbb,0x00, + 0x08,0xff,0xe7,0xb5,0x9b,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x08,0xff, + 0xe7,0xb7,0xb4,0x00,0x08,0xff,0xe7,0xbc,0xbe,0x00,0x10,0x08,0x08,0xff,0xe8,0x80, + 0x85,0x00,0x08,0xff,0xe8,0x8d,0x92,0x00,0xd1,0x10,0x10,0x08,0x08,0xff,0xe8,0x8f, + 0xaf,0x00,0x08,0xff,0xe8,0x9d,0xb9,0x00,0x10,0x08,0x08,0xff,0xe8,0xa5,0x81,0x00, + 0x08,0xff,0xe8,0xa6,0x86,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x08,0xff,0xe8,0xa6, + 0x96,0x00,0x08,0xff,0xe8,0xaa,0xbf,0x00,0x10,0x08,0x08,0xff,0xe8,0xab,0xb8,0x00, + 0x08,0xff,0xe8,0xab,0x8b,0x00,0xd1,0x10,0x10,0x08,0x08,0xff,0xe8,0xac,0x81,0x00, + 0x08,0xff,0xe8,0xab,0xbe,0x00,0x10,0x08,0x08,0xff,0xe8,0xab,0xad,0x00,0x08,0xff, + 0xe8,0xac,0xb9,0x00,0xcf,0x86,0x95,0xde,0xd4,0x81,0xd3,0x40,0xd2,0x20,0xd1,0x10, + 0x10,0x08,0x08,0xff,0xe8,0xae,0x8a,0x00,0x08,0xff,0xe8,0xb4,0x88,0x00,0x10,0x08, + 0x08,0xff,0xe8,0xbc,0xb8,0x00,0x08,0xff,0xe9,0x81,0xb2,0x00,0xd1,0x10,0x10,0x08, + 0x08,0xff,0xe9,0x86,0x99,0x00,0x08,0xff,0xe9,0x89,0xb6,0x00,0x10,0x08,0x08,0xff, + 0xe9,0x99,0xbc,0x00,0x08,0xff,0xe9,0x9b,0xa3,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08, + 0x08,0xff,0xe9,0x9d,0x96,0x00,0x08,0xff,0xe9,0x9f,0x9b,0x00,0x10,0x08,0x08,0xff, + 0xe9,0x9f,0xbf,0x00,0x08,0xff,0xe9,0xa0,0x8b,0x00,0xd1,0x10,0x10,0x08,0x08,0xff, + 0xe9,0xa0,0xbb,0x00,0x08,0xff,0xe9,0xac,0x92,0x00,0x10,0x08,0x08,0xff,0xe9,0xbe, + 0x9c,0x00,0x08,0xff,0xf0,0xa2,0xa1,0x8a,0x00,0xd3,0x45,0xd2,0x22,0xd1,0x12,0x10, + 0x09,0x08,0xff,0xf0,0xa2,0xa1,0x84,0x00,0x08,0xff,0xf0,0xa3,0x8f,0x95,0x00,0x10, + 0x08,0x08,0xff,0xe3,0xae,0x9d,0x00,0x08,0xff,0xe4,0x80,0x98,0x00,0xd1,0x11,0x10, + 0x08,0x08,0xff,0xe4,0x80,0xb9,0x00,0x08,0xff,0xf0,0xa5,0x89,0x89,0x00,0x10,0x09, + 0x08,0xff,0xf0,0xa5,0xb3,0x90,0x00,0x08,0xff,0xf0,0xa7,0xbb,0x93,0x00,0x92,0x14, + 0x91,0x10,0x10,0x08,0x08,0xff,0xe9,0xbd,0x83,0x00,0x08,0xff,0xe9,0xbe,0x8e,0x00, + 0x00,0x00,0x00,0x00,0x00,0x00,0xe1,0x94,0x01,0xe0,0x08,0x01,0xcf,0x86,0xd5,0x42, + 0xd4,0x14,0x93,0x10,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00, + 0x00,0x00,0x00,0x00,0xd3,0x10,0x92,0x0c,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00, + 0x01,0x00,0x01,0x00,0x52,0x04,0x00,0x00,0xd1,0x0d,0x10,0x04,0x00,0x00,0x04,0xff, + 0xd7,0x99,0xd6,0xb4,0x00,0x10,0x04,0x01,0x1a,0x01,0xff,0xd7,0xb2,0xd6,0xb7,0x00, + 0xd4,0x42,0x53,0x04,0x01,0x00,0xd2,0x16,0x51,0x04,0x01,0x00,0x10,0x09,0x01,0xff, + 0xd7,0xa9,0xd7,0x81,0x00,0x01,0xff,0xd7,0xa9,0xd7,0x82,0x00,0xd1,0x16,0x10,0x0b, + 0x01,0xff,0xd7,0xa9,0xd6,0xbc,0xd7,0x81,0x00,0x01,0xff,0xd7,0xa9,0xd6,0xbc,0xd7, + 0x82,0x00,0x10,0x09,0x01,0xff,0xd7,0x90,0xd6,0xb7,0x00,0x01,0xff,0xd7,0x90,0xd6, + 0xb8,0x00,0xd3,0x43,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff,0xd7,0x90,0xd6,0xbc, + 0x00,0x01,0xff,0xd7,0x91,0xd6,0xbc,0x00,0x10,0x09,0x01,0xff,0xd7,0x92,0xd6,0xbc, + 0x00,0x01,0xff,0xd7,0x93,0xd6,0xbc,0x00,0xd1,0x12,0x10,0x09,0x01,0xff,0xd7,0x94, + 0xd6,0xbc,0x00,0x01,0xff,0xd7,0x95,0xd6,0xbc,0x00,0x10,0x09,0x01,0xff,0xd7,0x96, + 0xd6,0xbc,0x00,0x00,0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff,0xd7,0x98,0xd6, + 0xbc,0x00,0x01,0xff,0xd7,0x99,0xd6,0xbc,0x00,0x10,0x09,0x01,0xff,0xd7,0x9a,0xd6, + 0xbc,0x00,0x01,0xff,0xd7,0x9b,0xd6,0xbc,0x00,0xd1,0x0d,0x10,0x09,0x01,0xff,0xd7, + 0x9c,0xd6,0xbc,0x00,0x00,0x00,0x10,0x09,0x01,0xff,0xd7,0x9e,0xd6,0xbc,0x00,0x00, + 0x00,0xcf,0x86,0x95,0x85,0x94,0x81,0xd3,0x3e,0xd2,0x1f,0xd1,0x12,0x10,0x09,0x01, + 0xff,0xd7,0xa0,0xd6,0xbc,0x00,0x01,0xff,0xd7,0xa1,0xd6,0xbc,0x00,0x10,0x04,0x00, + 0x00,0x01,0xff,0xd7,0xa3,0xd6,0xbc,0x00,0xd1,0x0d,0x10,0x09,0x01,0xff,0xd7,0xa4, + 0xd6,0xbc,0x00,0x00,0x00,0x10,0x09,0x01,0xff,0xd7,0xa6,0xd6,0xbc,0x00,0x01,0xff, + 0xd7,0xa7,0xd6,0xbc,0x00,0xd2,0x24,0xd1,0x12,0x10,0x09,0x01,0xff,0xd7,0xa8,0xd6, + 0xbc,0x00,0x01,0xff,0xd7,0xa9,0xd6,0xbc,0x00,0x10,0x09,0x01,0xff,0xd7,0xaa,0xd6, + 0xbc,0x00,0x01,0xff,0xd7,0x95,0xd6,0xb9,0x00,0xd1,0x12,0x10,0x09,0x01,0xff,0xd7, + 0x91,0xd6,0xbf,0x00,0x01,0xff,0xd7,0x9b,0xd6,0xbf,0x00,0x10,0x09,0x01,0xff,0xd7, + 0xa4,0xd6,0xbf,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd0,0x1a,0xcf,0x86,0x55,0x04, + 0x01,0x00,0x54,0x04,0x01,0x00,0x93,0x0c,0x92,0x08,0x11,0x04,0x01,0x00,0x0c,0x00, + 0x0c,0x00,0x0c,0x00,0xcf,0x86,0x95,0x24,0xd4,0x10,0x93,0x0c,0x92,0x08,0x11,0x04, + 0x0c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x93,0x10,0x92,0x0c,0x51,0x04,0x00,0x00, + 0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0xd3,0x5a,0xd2,0x06, + 0xcf,0x06,0x01,0x00,0xd1,0x14,0xd0,0x06,0xcf,0x06,0x01,0x00,0xcf,0x86,0x95,0x08, + 0x14,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0xd0,0x1a,0xcf,0x86,0x95,0x14,0x54,0x04, + 0x01,0x00,0x93,0x0c,0x92,0x08,0x11,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x01,0x00, + 0x01,0x00,0xcf,0x86,0xd5,0x0c,0x94,0x08,0x13,0x04,0x01,0x00,0x00,0x00,0x05,0x00, + 0x54,0x04,0x05,0x00,0x53,0x04,0x01,0x00,0x52,0x04,0x01,0x00,0x91,0x08,0x10,0x04, + 0x06,0x00,0x07,0x00,0x00,0x00,0xd2,0xce,0xd1,0xa5,0xd0,0x37,0xcf,0x86,0xd5,0x15, + 0x54,0x05,0x06,0xff,0x00,0x53,0x04,0x08,0x00,0x92,0x08,0x11,0x04,0x08,0x00,0x00, + 0x00,0x00,0x00,0x94,0x1c,0xd3,0x10,0x52,0x04,0x01,0xe6,0x51,0x04,0x0a,0xe6,0x10, + 0x04,0x0a,0xe6,0x10,0xdc,0x52,0x04,0x10,0xdc,0x11,0x04,0x10,0xdc,0x11,0xe6,0x01, + 0x00,0xcf,0x86,0xd5,0x38,0xd4,0x24,0xd3,0x14,0x52,0x04,0x01,0x00,0xd1,0x08,0x10, + 0x04,0x01,0x00,0x06,0x00,0x10,0x04,0x06,0x00,0x07,0x00,0x92,0x0c,0x91,0x08,0x10, + 0x04,0x07,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x93,0x10,0x92,0x0c,0x51,0x04,0x01, + 0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x01,0x00,0xd4,0x18,0xd3,0x10,0x52, + 0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x12,0x04,0x01, + 0x00,0x00,0x00,0x93,0x18,0xd2,0x0c,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x06, + 0x00,0x91,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x01,0x00,0x01,0x00,0xd0,0x06,0xcf, + 0x06,0x01,0x00,0xcf,0x86,0x55,0x04,0x01,0x00,0x54,0x04,0x01,0x00,0x53,0x04,0x01, + 0x00,0x52,0x04,0x01,0x00,0xd1,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x10,0x04,0x00, + 0x00,0x01,0xff,0x00,0xd1,0x50,0xd0,0x1e,0xcf,0x86,0x95,0x18,0x94,0x14,0x93,0x10, + 0x92,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00, + 0x01,0x00,0x01,0x00,0xcf,0x86,0xd5,0x18,0x54,0x04,0x01,0x00,0x53,0x04,0x01,0x00, + 0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x06,0x00,0x94,0x14, + 0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x06,0x00,0x01,0x00,0x01,0x00,0x01,0x00, + 0x01,0x00,0x01,0x00,0xd0,0x2f,0xcf,0x86,0x55,0x04,0x01,0x00,0xd4,0x15,0x93,0x11, + 0x92,0x0d,0x91,0x09,0x10,0x05,0x01,0xff,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01, + 0x00,0x53,0x04,0x01,0x00,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01, + 0x00,0x00,0x00,0xcf,0x86,0xd5,0x38,0xd4,0x18,0xd3,0x0c,0x92,0x08,0x11,0x04,0x00, + 0x00,0x01,0x00,0x01,0x00,0x92,0x08,0x11,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0xd3, + 0x0c,0x92,0x08,0x11,0x04,0x00,0x00,0x01,0x00,0x01,0x00,0xd2,0x08,0x11,0x04,0x00, + 0x00,0x01,0x00,0x91,0x08,0x10,0x04,0x01,0x00,0x00,0x00,0x00,0x00,0xd4,0x20,0xd3, + 0x10,0x52,0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x52, + 0x04,0x01,0x00,0x51,0x04,0x01,0x00,0x10,0x04,0x01,0x00,0x00,0x00,0x53,0x05,0x00, + 0xff,0x00,0xd2,0x0d,0x91,0x09,0x10,0x05,0x00,0xff,0x00,0x04,0x00,0x04,0x00,0x91, + 0x08,0x10,0x04,0x03,0x00,0x01,0x00,0x01,0x00,0x83,0xe2,0x46,0x3e,0xe1,0x1f,0x3b, + 0xe0,0x9c,0x39,0xcf,0x86,0xe5,0x40,0x26,0xc4,0xe3,0x16,0x14,0xe2,0xef,0x11,0xe1, + 0xd0,0x10,0xe0,0x60,0x07,0xcf,0x86,0xe5,0x53,0x03,0xe4,0x4c,0x02,0xe3,0x3d,0x01, + 0xd2,0x94,0xd1,0x70,0xd0,0x4a,0xcf,0x86,0xd5,0x18,0x94,0x14,0x53,0x04,0x07,0x00, + 0x52,0x04,0x07,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x07,0x00,0x07,0x00,0x07,0x00, + 0xd4,0x14,0x93,0x10,0x52,0x04,0x07,0x00,0x51,0x04,0x07,0x00,0x10,0x04,0x07,0x00, + 0x00,0x00,0x07,0x00,0x53,0x04,0x07,0x00,0xd2,0x0c,0x51,0x04,0x07,0x00,0x10,0x04, + 0x07,0x00,0x00,0x00,0x51,0x04,0x07,0x00,0x10,0x04,0x00,0x00,0x07,0x00,0xcf,0x86, + 0x95,0x20,0xd4,0x10,0x53,0x04,0x07,0x00,0x52,0x04,0x07,0x00,0x11,0x04,0x07,0x00, + 0x00,0x00,0x53,0x04,0x07,0x00,0x52,0x04,0x07,0x00,0x11,0x04,0x07,0x00,0x00,0x00, + 0x00,0x00,0xd0,0x06,0xcf,0x06,0x07,0x00,0xcf,0x86,0x55,0x04,0x07,0x00,0x54,0x04, + 0x07,0x00,0x53,0x04,0x07,0x00,0x92,0x0c,0x51,0x04,0x07,0x00,0x10,0x04,0x07,0x00, + 0x00,0x00,0x00,0x00,0xd1,0x40,0xd0,0x3a,0xcf,0x86,0xd5,0x20,0x94,0x1c,0x93,0x18, + 0xd2,0x0c,0x51,0x04,0x07,0x00,0x10,0x04,0x07,0x00,0x00,0x00,0x51,0x04,0x00,0x00, + 0x10,0x04,0x00,0x00,0x07,0x00,0x07,0x00,0x07,0x00,0x54,0x04,0x07,0x00,0x93,0x10, + 0x52,0x04,0x07,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x07,0x00,0x07,0x00, + 0xcf,0x06,0x08,0x00,0xd0,0x46,0xcf,0x86,0xd5,0x2c,0xd4,0x20,0x53,0x04,0x08,0x00, + 0xd2,0x0c,0x51,0x04,0x08,0x00,0x10,0x04,0x08,0x00,0x10,0x00,0xd1,0x08,0x10,0x04, + 0x10,0x00,0x12,0x00,0x10,0x04,0x12,0x00,0x00,0x00,0x53,0x04,0x0a,0x00,0x12,0x04, + 0x0a,0x00,0x00,0x00,0x94,0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x10,0x00, + 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0xd5,0x08,0x14,0x04, + 0x00,0x00,0x0a,0x00,0x54,0x04,0x0a,0x00,0x53,0x04,0x0a,0x00,0x52,0x04,0x0a,0x00, + 0x91,0x08,0x10,0x04,0x0a,0x00,0x0a,0xdc,0x00,0x00,0xd2,0x5e,0xd1,0x06,0xcf,0x06, + 0x00,0x00,0xd0,0x1e,0xcf,0x86,0x95,0x18,0x54,0x04,0x0a,0x00,0x53,0x04,0x0a,0x00, + 0x52,0x04,0x0a,0x00,0x91,0x08,0x10,0x04,0x0a,0x00,0x00,0x00,0x00,0x00,0x0a,0x00, + 0xcf,0x86,0xd5,0x18,0x54,0x04,0x0a,0x00,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04, + 0x0a,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd4,0x14,0x93,0x10,0x92,0x0c, + 0x91,0x08,0x10,0x04,0x10,0xdc,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x53,0x04, + 0x10,0x00,0x12,0x04,0x10,0x00,0x00,0x00,0xd1,0x70,0xd0,0x36,0xcf,0x86,0xd5,0x18, + 0x54,0x04,0x05,0x00,0x53,0x04,0x05,0x00,0x52,0x04,0x05,0x00,0x51,0x04,0x05,0x00, + 0x10,0x04,0x05,0x00,0x10,0x00,0x94,0x18,0xd3,0x08,0x12,0x04,0x05,0x00,0x00,0x00, + 0x52,0x04,0x00,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x13,0x00,0x13,0x00,0x05,0x00, + 0xcf,0x86,0xd5,0x18,0x94,0x14,0x53,0x04,0x05,0x00,0x92,0x0c,0x51,0x04,0x05,0x00, + 0x10,0x04,0x05,0x00,0x00,0x00,0x00,0x00,0x10,0x00,0x54,0x04,0x10,0x00,0xd3,0x0c, + 0x52,0x04,0x10,0x00,0x11,0x04,0x10,0x00,0x10,0xe6,0x92,0x0c,0x51,0x04,0x10,0xe6, + 0x10,0x04,0x10,0xe6,0x00,0x00,0x00,0x00,0xd0,0x1e,0xcf,0x86,0x95,0x18,0x54,0x04, + 0x07,0x00,0x53,0x04,0x07,0x00,0x52,0x04,0x07,0x00,0x51,0x04,0x07,0x00,0x10,0x04, + 0x00,0x00,0x07,0x00,0x08,0x00,0xcf,0x86,0x95,0x1c,0xd4,0x0c,0x93,0x08,0x12,0x04, + 0x08,0x00,0x00,0x00,0x08,0x00,0x93,0x0c,0x52,0x04,0x08,0x00,0x11,0x04,0x08,0x00, + 0x00,0x00,0x00,0x00,0x00,0x00,0xd3,0xba,0xd2,0x80,0xd1,0x34,0xd0,0x1a,0xcf,0x86, + 0x55,0x04,0x05,0x00,0x94,0x10,0x93,0x0c,0x52,0x04,0x05,0x00,0x11,0x04,0x05,0x00, + 0x07,0x00,0x05,0x00,0x05,0x00,0xcf,0x86,0x95,0x14,0x94,0x10,0x53,0x04,0x05,0x00, + 0x52,0x04,0x05,0x00,0x11,0x04,0x05,0x00,0x07,0x00,0x07,0x00,0x07,0x00,0xd0,0x2a, + 0xcf,0x86,0xd5,0x14,0x54,0x04,0x07,0x00,0x53,0x04,0x07,0x00,0x52,0x04,0x07,0x00, + 0x11,0x04,0x07,0x00,0x00,0x00,0x94,0x10,0x53,0x04,0x07,0x00,0x92,0x08,0x11,0x04, + 0x07,0x00,0x00,0x00,0x00,0x00,0x12,0x00,0xcf,0x86,0xd5,0x10,0x54,0x04,0x12,0x00, + 0x93,0x08,0x12,0x04,0x12,0x00,0x00,0x00,0x12,0x00,0x54,0x04,0x12,0x00,0x53,0x04, + 0x12,0x00,0x12,0x04,0x12,0x00,0x00,0x00,0xd1,0x34,0xd0,0x12,0xcf,0x86,0x55,0x04, + 0x10,0x00,0x94,0x08,0x13,0x04,0x10,0x00,0x00,0x00,0x10,0x00,0xcf,0x86,0x55,0x04, + 0x10,0x00,0x94,0x18,0xd3,0x08,0x12,0x04,0x10,0x00,0x00,0x00,0x52,0x04,0x00,0x00, + 0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x10,0x00,0x00,0x00,0xcf,0x06,0x00,0x00, + 0xd2,0x06,0xcf,0x06,0x10,0x00,0xd1,0x40,0xd0,0x1e,0xcf,0x86,0x55,0x04,0x10,0x00, + 0x54,0x04,0x10,0x00,0x93,0x10,0x52,0x04,0x10,0x00,0x51,0x04,0x10,0x00,0x10,0x04, + 0x10,0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0xd5,0x14,0x54,0x04,0x10,0x00,0x93,0x0c, + 0x52,0x04,0x10,0x00,0x11,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0x94,0x08,0x13,0x04, + 0x10,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xe4,0xce,0x02,0xe3,0x45,0x01, + 0xd2,0xd0,0xd1,0x70,0xd0,0x52,0xcf,0x86,0xd5,0x20,0x94,0x1c,0xd3,0x0c,0x52,0x04, + 0x07,0x00,0x11,0x04,0x07,0x00,0x00,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x07,0x00, + 0x00,0x00,0x07,0x00,0x07,0x00,0x07,0x00,0x54,0x04,0x07,0x00,0xd3,0x10,0x52,0x04, + 0x07,0x00,0x51,0x04,0x07,0x00,0x10,0x04,0x00,0x00,0x07,0x00,0xd2,0x0c,0x91,0x08, + 0x10,0x04,0x07,0x00,0x00,0x00,0x00,0x00,0xd1,0x08,0x10,0x04,0x07,0x00,0x00,0x00, + 0x10,0x04,0x00,0x00,0x07,0x00,0xcf,0x86,0x95,0x18,0x54,0x04,0x0b,0x00,0x93,0x10, + 0x52,0x04,0x0b,0x00,0x51,0x04,0x0b,0x00,0x10,0x04,0x00,0x00,0x0b,0x00,0x0b,0x00, + 0x10,0x00,0xd0,0x32,0xcf,0x86,0xd5,0x18,0x54,0x04,0x10,0x00,0x53,0x04,0x10,0x00, + 0x52,0x04,0x10,0x00,0x51,0x04,0x10,0x00,0x10,0x04,0x10,0x00,0x00,0x00,0x94,0x14, + 0x93,0x10,0x52,0x04,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x10,0x00, + 0x10,0x00,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x11,0x00,0xd3,0x14, + 0xd2,0x0c,0x51,0x04,0x11,0x00,0x10,0x04,0x11,0x00,0x00,0x00,0x11,0x04,0x11,0x00, + 0x00,0x00,0x92,0x0c,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x11,0x00,0x11,0x00, + 0xd1,0x40,0xd0,0x3a,0xcf,0x86,0xd5,0x1c,0x54,0x04,0x09,0x00,0x53,0x04,0x09,0x00, + 0xd2,0x08,0x11,0x04,0x09,0x00,0x0b,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00, + 0x09,0x00,0x54,0x04,0x0a,0x00,0x53,0x04,0x0a,0x00,0xd2,0x08,0x11,0x04,0x0a,0x00, + 0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x0a,0x00,0xcf,0x06,0x00,0x00, + 0xd0,0x1a,0xcf,0x86,0x55,0x04,0x0d,0x00,0x54,0x04,0x0d,0x00,0x53,0x04,0x0d,0x00, + 0x52,0x04,0x00,0x00,0x11,0x04,0x11,0x00,0x0d,0x00,0xcf,0x86,0x95,0x14,0x54,0x04, + 0x11,0x00,0x93,0x0c,0x92,0x08,0x11,0x04,0x00,0x00,0x11,0x00,0x11,0x00,0x11,0x00, + 0x11,0x00,0xd2,0xec,0xd1,0xa4,0xd0,0x76,0xcf,0x86,0xd5,0x48,0xd4,0x28,0xd3,0x14, + 0x52,0x04,0x08,0x00,0xd1,0x08,0x10,0x04,0x00,0x00,0x08,0x00,0x10,0x04,0x08,0x00, + 0x00,0x00,0x52,0x04,0x00,0x00,0xd1,0x08,0x10,0x04,0x08,0x00,0x08,0xdc,0x10,0x04, + 0x08,0x00,0x08,0xe6,0xd3,0x10,0x52,0x04,0x08,0x00,0x91,0x08,0x10,0x04,0x00,0x00, + 0x08,0x00,0x08,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x08,0x00,0x08,0x00, + 0x08,0x00,0x54,0x04,0x08,0x00,0xd3,0x0c,0x52,0x04,0x08,0x00,0x11,0x04,0x14,0x00, + 0x00,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04,0x08,0xe6,0x08,0x01,0x10,0x04,0x08,0xdc, + 0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x08,0x09,0xcf,0x86,0x95,0x28, + 0xd4,0x14,0x53,0x04,0x08,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x14,0x00,0x00,0x00, + 0x00,0x00,0x00,0x00,0x53,0x04,0x08,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x08,0x00, + 0x00,0x00,0x00,0x00,0x00,0x00,0x0b,0x00,0xd0,0x0a,0xcf,0x86,0x15,0x04,0x10,0x00, + 0x00,0x00,0xcf,0x86,0x55,0x04,0x10,0x00,0xd4,0x24,0xd3,0x14,0x52,0x04,0x10,0x00, + 0xd1,0x08,0x10,0x04,0x10,0x00,0x10,0xe6,0x10,0x04,0x10,0xdc,0x00,0x00,0x92,0x0c, + 0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x10,0x00,0x10,0x00,0x93,0x10,0x52,0x04, + 0x10,0x00,0x51,0x04,0x10,0x00,0x10,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0xd1,0x54, + 0xd0,0x26,0xcf,0x86,0x55,0x04,0x0b,0x00,0x54,0x04,0x0b,0x00,0xd3,0x0c,0x52,0x04, + 0x0b,0x00,0x11,0x04,0x0b,0x00,0x00,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x00,0x00, + 0x0b,0x00,0x0b,0x00,0x0b,0x00,0xcf,0x86,0xd5,0x14,0x54,0x04,0x0b,0x00,0x93,0x0c, + 0x52,0x04,0x0b,0x00,0x11,0x04,0x0b,0x00,0x00,0x00,0x0b,0x00,0x54,0x04,0x0b,0x00, + 0x93,0x10,0x92,0x0c,0x51,0x04,0x0b,0x00,0x10,0x04,0x0b,0x00,0x00,0x00,0x00,0x00, + 0x0b,0x00,0xd0,0x42,0xcf,0x86,0xd5,0x28,0x54,0x04,0x10,0x00,0xd3,0x0c,0x92,0x08, + 0x11,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0xd2,0x0c,0x91,0x08,0x10,0x04,0x00,0x00, + 0x10,0x00,0x10,0x00,0x91,0x08,0x10,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0x94,0x14, + 0x53,0x04,0x00,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x10,0x00,0x10,0x00, + 0x10,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xd3,0x96,0xd2,0x68,0xd1,0x24,0xd0,0x06, + 0xcf,0x06,0x0b,0x00,0xcf,0x86,0x95,0x18,0x94,0x14,0x53,0x04,0x0b,0x00,0x92,0x0c, + 0x91,0x08,0x10,0x04,0x0b,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, + 0xd0,0x1e,0xcf,0x86,0x55,0x04,0x11,0x00,0x54,0x04,0x11,0x00,0x93,0x10,0x92,0x0c, + 0x51,0x04,0x11,0x00,0x10,0x04,0x11,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x86, + 0x55,0x04,0x11,0x00,0x54,0x04,0x11,0x00,0xd3,0x10,0x92,0x0c,0x51,0x04,0x11,0x00, + 0x10,0x04,0x11,0x00,0x00,0x00,0x00,0x00,0x92,0x08,0x11,0x04,0x00,0x00,0x11,0x00, + 0x11,0x00,0xd1,0x28,0xd0,0x22,0xcf,0x86,0x55,0x04,0x14,0x00,0xd4,0x0c,0x93,0x08, + 0x12,0x04,0x14,0x00,0x14,0xe6,0x00,0x00,0x53,0x04,0x14,0x00,0x92,0x08,0x11,0x04, + 0x14,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xd2,0x2a, + 0xd1,0x24,0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04, + 0x0b,0x00,0x53,0x04,0x0b,0x00,0x52,0x04,0x0b,0x00,0x51,0x04,0x0b,0x00,0x10,0x04, + 0x0b,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xd1,0x58,0xd0,0x12,0xcf,0x86,0x55,0x04, + 0x14,0x00,0x94,0x08,0x13,0x04,0x14,0x00,0x00,0x00,0x14,0x00,0xcf,0x86,0x95,0x40, + 0xd4,0x24,0xd3,0x0c,0x52,0x04,0x14,0x00,0x11,0x04,0x14,0x00,0x14,0xdc,0xd2,0x0c, + 0x51,0x04,0x14,0xe6,0x10,0x04,0x14,0xe6,0x14,0xdc,0x91,0x08,0x10,0x04,0x14,0xe6, + 0x14,0xdc,0x14,0xdc,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x14,0xdc,0x14,0x00, + 0x14,0x00,0x14,0x00,0x92,0x08,0x11,0x04,0x14,0x00,0x00,0x00,0x00,0x00,0x00,0x00, + 0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x15,0x00, + 0x93,0x10,0x52,0x04,0x15,0x00,0x51,0x04,0x15,0x00,0x10,0x04,0x15,0x00,0x00,0x00, + 0x00,0x00,0xcf,0x86,0xe5,0x0f,0x06,0xe4,0xf8,0x03,0xe3,0x02,0x02,0xd2,0xfb,0xd1, + 0x4c,0xd0,0x06,0xcf,0x06,0x0c,0x00,0xcf,0x86,0xd5,0x2c,0xd4,0x1c,0xd3,0x10,0x52, + 0x04,0x0c,0x00,0x51,0x04,0x0c,0x00,0x10,0x04,0x0c,0x09,0x0c,0x00,0x52,0x04,0x0c, + 0x00,0x11,0x04,0x0c,0x00,0x00,0x00,0x93,0x0c,0x92,0x08,0x11,0x04,0x00,0x00,0x0c, + 0x00,0x0c,0x00,0x0c,0x00,0x54,0x04,0x0c,0x00,0x53,0x04,0x00,0x00,0x52,0x04,0x00, + 0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x10,0x09,0xd0,0x69,0xcf,0x86,0xd5, + 0x32,0x54,0x04,0x0b,0x00,0x53,0x04,0x0b,0x00,0xd2,0x15,0x51,0x04,0x0b,0x00,0x10, + 0x0d,0x0b,0xff,0xf0,0x91,0x82,0x99,0xf0,0x91,0x82,0xba,0x00,0x0b,0x00,0x91,0x11, + 0x10,0x0d,0x0b,0xff,0xf0,0x91,0x82,0x9b,0xf0,0x91,0x82,0xba,0x00,0x0b,0x00,0x0b, + 0x00,0xd4,0x1d,0x53,0x04,0x0b,0x00,0x92,0x15,0x51,0x04,0x0b,0x00,0x10,0x04,0x0b, + 0x00,0x0b,0xff,0xf0,0x91,0x82,0xa5,0xf0,0x91,0x82,0xba,0x00,0x0b,0x00,0x53,0x04, + 0x0b,0x00,0x92,0x10,0xd1,0x08,0x10,0x04,0x0b,0x00,0x0b,0x09,0x10,0x04,0x0b,0x07, + 0x0b,0x00,0x0b,0x00,0xcf,0x86,0xd5,0x20,0x94,0x1c,0xd3,0x0c,0x92,0x08,0x11,0x04, + 0x0b,0x00,0x00,0x00,0x00,0x00,0x52,0x04,0x00,0x00,0x91,0x08,0x10,0x04,0x00,0x00, + 0x14,0x00,0x00,0x00,0x0d,0x00,0xd4,0x14,0x53,0x04,0x0d,0x00,0x92,0x0c,0x91,0x08, + 0x10,0x04,0x0d,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x53,0x04,0x0d,0x00,0x92,0x08, + 0x11,0x04,0x0d,0x00,0x00,0x00,0x00,0x00,0xd1,0x96,0xd0,0x5c,0xcf,0x86,0xd5,0x18, + 0x94,0x14,0x93,0x10,0x92,0x0c,0x51,0x04,0x0d,0xe6,0x10,0x04,0x0d,0xe6,0x0d,0x00, + 0x0d,0x00,0x0d,0x00,0x0d,0x00,0xd4,0x26,0x53,0x04,0x0d,0x00,0x52,0x04,0x0d,0x00, + 0x51,0x04,0x0d,0x00,0x10,0x0d,0x0d,0xff,0xf0,0x91,0x84,0xb1,0xf0,0x91,0x84,0xa7, + 0x00,0x0d,0xff,0xf0,0x91,0x84,0xb2,0xf0,0x91,0x84,0xa7,0x00,0x93,0x18,0xd2,0x0c, + 0x51,0x04,0x0d,0x00,0x10,0x04,0x0d,0x00,0x0d,0x09,0x91,0x08,0x10,0x04,0x0d,0x09, + 0x00,0x00,0x0d,0x00,0x0d,0x00,0xcf,0x86,0xd5,0x18,0x94,0x14,0x93,0x10,0x52,0x04, + 0x0d,0x00,0x51,0x04,0x14,0x00,0x10,0x04,0x14,0x00,0x00,0x00,0x00,0x00,0x10,0x00, + 0x54,0x04,0x10,0x00,0x93,0x18,0xd2,0x0c,0x51,0x04,0x10,0x00,0x10,0x04,0x10,0x00, + 0x10,0x07,0x51,0x04,0x10,0x00,0x10,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0xd0,0x06, + 0xcf,0x06,0x0d,0x00,0xcf,0x86,0xd5,0x40,0xd4,0x2c,0xd3,0x10,0x92,0x0c,0x91,0x08, + 0x10,0x04,0x0d,0x09,0x0d,0x00,0x0d,0x00,0x0d,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04, + 0x0d,0x00,0x11,0x00,0x10,0x04,0x11,0x07,0x11,0x00,0x91,0x08,0x10,0x04,0x11,0x00, + 0x10,0x00,0x00,0x00,0x53,0x04,0x0d,0x00,0x92,0x0c,0x51,0x04,0x0d,0x00,0x10,0x04, + 0x10,0x00,0x11,0x00,0x11,0x00,0xd4,0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04, + 0x00,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x93,0x10,0x52,0x04,0x10,0x00, + 0x91,0x08,0x10,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd2,0xc8,0xd1,0x48, + 0xd0,0x42,0xcf,0x86,0xd5,0x18,0x54,0x04,0x10,0x00,0x93,0x10,0x92,0x0c,0x51,0x04, + 0x10,0x00,0x10,0x04,0x00,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x54,0x04,0x10,0x00, + 0xd3,0x14,0x52,0x04,0x10,0x00,0xd1,0x08,0x10,0x04,0x10,0x00,0x10,0x09,0x10,0x04, + 0x10,0x07,0x10,0x00,0x52,0x04,0x10,0x00,0x51,0x04,0x10,0x00,0x10,0x04,0x12,0x00, + 0x00,0x00,0xcf,0x06,0x00,0x00,0xd0,0x52,0xcf,0x86,0xd5,0x3c,0xd4,0x28,0xd3,0x10, + 0x52,0x04,0x11,0x00,0x51,0x04,0x11,0x00,0x10,0x04,0x11,0x00,0x00,0x00,0xd2,0x0c, + 0x91,0x08,0x10,0x04,0x11,0x00,0x00,0x00,0x11,0x00,0x51,0x04,0x11,0x00,0x10,0x04, + 0x00,0x00,0x11,0x00,0x53,0x04,0x11,0x00,0x52,0x04,0x11,0x00,0x51,0x04,0x11,0x00, + 0x10,0x04,0x00,0x00,0x11,0x00,0x94,0x10,0x53,0x04,0x11,0x00,0x92,0x08,0x11,0x04, + 0x11,0x00,0x00,0x00,0x00,0x00,0x10,0x00,0xcf,0x86,0x55,0x04,0x10,0x00,0xd4,0x18, + 0x53,0x04,0x10,0x00,0x92,0x10,0xd1,0x08,0x10,0x04,0x10,0x00,0x10,0x07,0x10,0x04, + 0x10,0x09,0x00,0x00,0x00,0x00,0x53,0x04,0x10,0x00,0x92,0x08,0x11,0x04,0x10,0x00, + 0x00,0x00,0x00,0x00,0xe1,0x27,0x01,0xd0,0x8a,0xcf,0x86,0xd5,0x44,0xd4,0x2c,0xd3, + 0x18,0xd2,0x0c,0x91,0x08,0x10,0x04,0x11,0x00,0x10,0x00,0x10,0x00,0x91,0x08,0x10, + 0x04,0x00,0x00,0x10,0x00,0x10,0x00,0x52,0x04,0x10,0x00,0xd1,0x08,0x10,0x04,0x10, + 0x00,0x00,0x00,0x10,0x04,0x00,0x00,0x10,0x00,0x93,0x14,0x92,0x10,0xd1,0x08,0x10, + 0x04,0x10,0x00,0x00,0x00,0x10,0x04,0x00,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0xd4, + 0x14,0x53,0x04,0x10,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x10,0x00,0x00,0x00,0x10, + 0x00,0x10,0x00,0xd3,0x18,0xd2,0x0c,0x91,0x08,0x10,0x04,0x10,0x00,0x00,0x00,0x10, + 0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x10,0x00,0x10,0x00,0xd2,0x0c,0x51,0x04,0x10, + 0x00,0x10,0x04,0x00,0x00,0x14,0x07,0x91,0x08,0x10,0x04,0x10,0x07,0x10,0x00,0x10, + 0x00,0xcf,0x86,0xd5,0x6a,0xd4,0x42,0xd3,0x14,0x52,0x04,0x10,0x00,0xd1,0x08,0x10, + 0x04,0x10,0x00,0x00,0x00,0x10,0x04,0x00,0x00,0x10,0x00,0xd2,0x19,0xd1,0x08,0x10, + 0x04,0x10,0x00,0x00,0x00,0x10,0x04,0x00,0x00,0x10,0xff,0xf0,0x91,0x8d,0x87,0xf0, + 0x91,0x8c,0xbe,0x00,0x91,0x11,0x10,0x0d,0x10,0xff,0xf0,0x91,0x8d,0x87,0xf0,0x91, + 0x8d,0x97,0x00,0x10,0x09,0x00,0x00,0xd3,0x18,0xd2,0x0c,0x91,0x08,0x10,0x04,0x11, + 0x00,0x00,0x00,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x10,0x00,0x52, + 0x04,0x00,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x10,0x00,0x10,0x00,0xd4,0x1c,0xd3, + 0x0c,0x52,0x04,0x10,0x00,0x11,0x04,0x00,0x00,0x10,0xe6,0x52,0x04,0x10,0xe6,0x91, + 0x08,0x10,0x04,0x10,0xe6,0x00,0x00,0x00,0x00,0x93,0x10,0x52,0x04,0x10,0xe6,0x91, + 0x08,0x10,0x04,0x10,0xe6,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xe3, + 0x30,0x01,0xd2,0xb7,0xd1,0x48,0xd0,0x06,0xcf,0x06,0x12,0x00,0xcf,0x86,0x95,0x3c, + 0xd4,0x1c,0x93,0x18,0xd2,0x0c,0x51,0x04,0x12,0x00,0x10,0x04,0x12,0x09,0x12,0x00, + 0x51,0x04,0x12,0x00,0x10,0x04,0x12,0x07,0x12,0x00,0x12,0x00,0x53,0x04,0x12,0x00, + 0xd2,0x0c,0x51,0x04,0x12,0x00,0x10,0x04,0x00,0x00,0x12,0x00,0xd1,0x08,0x10,0x04, + 0x00,0x00,0x12,0x00,0x10,0x04,0x14,0xe6,0x15,0x00,0x00,0x00,0xd0,0x45,0xcf,0x86, + 0x55,0x04,0x10,0x00,0x54,0x04,0x10,0x00,0x53,0x04,0x10,0x00,0xd2,0x15,0x51,0x04, + 0x10,0x00,0x10,0x04,0x10,0x00,0x10,0xff,0xf0,0x91,0x92,0xb9,0xf0,0x91,0x92,0xba, + 0x00,0xd1,0x11,0x10,0x0d,0x10,0xff,0xf0,0x91,0x92,0xb9,0xf0,0x91,0x92,0xb0,0x00, + 0x10,0x00,0x10,0x0d,0x10,0xff,0xf0,0x91,0x92,0xb9,0xf0,0x91,0x92,0xbd,0x00,0x10, + 0x00,0xcf,0x86,0x95,0x24,0xd4,0x14,0x93,0x10,0x92,0x0c,0x51,0x04,0x10,0x00,0x10, + 0x04,0x10,0x09,0x10,0x07,0x10,0x00,0x00,0x00,0x53,0x04,0x10,0x00,0x92,0x08,0x11, + 0x04,0x10,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd1,0x06,0xcf,0x06,0x00,0x00,0xd0, + 0x40,0xcf,0x86,0x55,0x04,0x10,0x00,0x54,0x04,0x10,0x00,0xd3,0x0c,0x52,0x04,0x10, + 0x00,0x11,0x04,0x10,0x00,0x00,0x00,0xd2,0x1e,0x51,0x04,0x10,0x00,0x10,0x0d,0x10, + 0xff,0xf0,0x91,0x96,0xb8,0xf0,0x91,0x96,0xaf,0x00,0x10,0xff,0xf0,0x91,0x96,0xb9, + 0xf0,0x91,0x96,0xaf,0x00,0x51,0x04,0x10,0x00,0x10,0x04,0x10,0x00,0x10,0x09,0xcf, + 0x86,0x95,0x2c,0xd4,0x1c,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x10,0x07,0x10, + 0x00,0x10,0x00,0x10,0x00,0x92,0x08,0x11,0x04,0x10,0x00,0x11,0x00,0x11,0x00,0x53, + 0x04,0x11,0x00,0x52,0x04,0x11,0x00,0x11,0x04,0x11,0x00,0x00,0x00,0x00,0x00,0xd2, + 0xa0,0xd1,0x5c,0xd0,0x1e,0xcf,0x86,0x55,0x04,0x10,0x00,0x54,0x04,0x10,0x00,0x53, + 0x04,0x10,0x00,0x52,0x04,0x10,0x00,0x51,0x04,0x10,0x00,0x10,0x04,0x10,0x00,0x10, + 0x09,0xcf,0x86,0xd5,0x24,0xd4,0x14,0x93,0x10,0x52,0x04,0x10,0x00,0x91,0x08,0x10, + 0x04,0x10,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x53,0x04,0x10,0x00,0x92,0x08,0x11, + 0x04,0x10,0x00,0x00,0x00,0x00,0x00,0x94,0x14,0x53,0x04,0x12,0x00,0x52,0x04,0x12, + 0x00,0x91,0x08,0x10,0x04,0x12,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd0,0x2a,0xcf, + 0x86,0x55,0x04,0x0d,0x00,0x54,0x04,0x0d,0x00,0xd3,0x10,0x52,0x04,0x0d,0x00,0x51, + 0x04,0x0d,0x00,0x10,0x04,0x0d,0x09,0x0d,0x07,0x92,0x0c,0x91,0x08,0x10,0x04,0x15, + 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0x95,0x14,0x94,0x10,0x53,0x04,0x0d, + 0x00,0x92,0x08,0x11,0x04,0x0d,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd1, + 0x40,0xd0,0x3a,0xcf,0x86,0xd5,0x20,0x54,0x04,0x11,0x00,0x53,0x04,0x11,0x00,0xd2, + 0x0c,0x51,0x04,0x11,0x00,0x10,0x04,0x14,0x00,0x00,0x00,0x91,0x08,0x10,0x04,0x00, + 0x00,0x11,0x00,0x11,0x00,0x94,0x14,0x53,0x04,0x11,0x00,0x92,0x0c,0x51,0x04,0x11, + 0x00,0x10,0x04,0x11,0x00,0x11,0x09,0x00,0x00,0x11,0x00,0xcf,0x06,0x00,0x00,0xcf, + 0x06,0x00,0x00,0xe4,0x59,0x01,0xd3,0xb2,0xd2,0x5c,0xd1,0x28,0xd0,0x22,0xcf,0x86, + 0x55,0x04,0x14,0x00,0x54,0x04,0x14,0x00,0x53,0x04,0x14,0x00,0x92,0x10,0xd1,0x08, + 0x10,0x04,0x14,0x00,0x14,0x09,0x10,0x04,0x14,0x07,0x14,0x00,0x00,0x00,0xcf,0x06, + 0x00,0x00,0xd0,0x0a,0xcf,0x86,0x15,0x04,0x00,0x00,0x10,0x00,0xcf,0x86,0x55,0x04, + 0x10,0x00,0x54,0x04,0x10,0x00,0xd3,0x10,0x92,0x0c,0x51,0x04,0x10,0x00,0x10,0x04, + 0x10,0x00,0x00,0x00,0x00,0x00,0x52,0x04,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04, + 0x00,0x00,0x10,0x00,0xd1,0x06,0xcf,0x06,0x00,0x00,0xd0,0x1a,0xcf,0x86,0x55,0x04, + 0x00,0x00,0x94,0x10,0x53,0x04,0x15,0x00,0x92,0x08,0x11,0x04,0x00,0x00,0x15,0x00, + 0x15,0x00,0x15,0x00,0xcf,0x86,0xd5,0x14,0x54,0x04,0x15,0x00,0x53,0x04,0x15,0x00, + 0x92,0x08,0x11,0x04,0x00,0x00,0x15,0x00,0x15,0x00,0x94,0x1c,0x93,0x18,0xd2,0x0c, + 0x91,0x08,0x10,0x04,0x15,0x09,0x15,0x00,0x15,0x00,0x91,0x08,0x10,0x04,0x15,0x00, + 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd2,0xa0,0xd1,0x3c,0xd0,0x1e,0xcf,0x86, + 0x55,0x04,0x13,0x00,0x54,0x04,0x13,0x00,0x93,0x10,0x52,0x04,0x13,0x00,0x91,0x08, + 0x10,0x04,0x13,0x09,0x13,0x00,0x13,0x00,0x13,0x00,0xcf,0x86,0x95,0x18,0x94,0x14, + 0x93,0x10,0x52,0x04,0x13,0x00,0x51,0x04,0x13,0x00,0x10,0x04,0x13,0x00,0x13,0x09, + 0x00,0x00,0x13,0x00,0x13,0x00,0xd0,0x46,0xcf,0x86,0xd5,0x2c,0xd4,0x10,0x93,0x0c, + 0x52,0x04,0x13,0x00,0x11,0x04,0x15,0x00,0x13,0x00,0x13,0x00,0x53,0x04,0x13,0x00, + 0xd2,0x0c,0x91,0x08,0x10,0x04,0x13,0x00,0x13,0x09,0x13,0x00,0x91,0x08,0x10,0x04, + 0x13,0x00,0x14,0x00,0x13,0x00,0x94,0x14,0x93,0x10,0x92,0x0c,0x51,0x04,0x13,0x00, + 0x10,0x04,0x13,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0x55,0x04, + 0x10,0x00,0x54,0x04,0x10,0x00,0x53,0x04,0x10,0x00,0x92,0x0c,0x91,0x08,0x10,0x04, + 0x10,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xe3,0xa9,0x01,0xd2, + 0xb0,0xd1,0x6c,0xd0,0x3e,0xcf,0x86,0xd5,0x18,0x94,0x14,0x53,0x04,0x12,0x00,0x92, + 0x0c,0x91,0x08,0x10,0x04,0x12,0x00,0x00,0x00,0x12,0x00,0x12,0x00,0x12,0x00,0x54, + 0x04,0x12,0x00,0xd3,0x10,0x52,0x04,0x12,0x00,0x51,0x04,0x12,0x00,0x10,0x04,0x12, + 0x00,0x00,0x00,0x52,0x04,0x12,0x00,0x51,0x04,0x12,0x00,0x10,0x04,0x12,0x00,0x12, + 0x09,0xcf,0x86,0xd5,0x14,0x94,0x10,0x93,0x0c,0x52,0x04,0x12,0x00,0x11,0x04,0x12, + 0x00,0x00,0x00,0x00,0x00,0x12,0x00,0x94,0x14,0x53,0x04,0x12,0x00,0x52,0x04,0x12, + 0x00,0x91,0x08,0x10,0x04,0x12,0x00,0x00,0x00,0x00,0x00,0x12,0x00,0xd0,0x3e,0xcf, + 0x86,0xd5,0x14,0x54,0x04,0x12,0x00,0x93,0x0c,0x92,0x08,0x11,0x04,0x00,0x00,0x12, + 0x00,0x12,0x00,0x12,0x00,0xd4,0x14,0x53,0x04,0x12,0x00,0x92,0x0c,0x91,0x08,0x10, + 0x04,0x00,0x00,0x12,0x00,0x12,0x00,0x12,0x00,0x93,0x10,0x52,0x04,0x12,0x00,0x51, + 0x04,0x12,0x00,0x10,0x04,0x12,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xd1, + 0xa0,0xd0,0x52,0xcf,0x86,0xd5,0x24,0x94,0x20,0xd3,0x10,0x52,0x04,0x13,0x00,0x51, + 0x04,0x13,0x00,0x10,0x04,0x13,0x00,0x00,0x00,0x92,0x0c,0x51,0x04,0x13,0x00,0x10, + 0x04,0x00,0x00,0x13,0x00,0x13,0x00,0x13,0x00,0x54,0x04,0x13,0x00,0xd3,0x10,0x52, + 0x04,0x13,0x00,0x51,0x04,0x13,0x00,0x10,0x04,0x13,0x00,0x00,0x00,0xd2,0x0c,0x51, + 0x04,0x00,0x00,0x10,0x04,0x13,0x00,0x00,0x00,0x51,0x04,0x13,0x00,0x10,0x04,0x00, + 0x00,0x13,0x00,0xcf,0x86,0xd5,0x28,0xd4,0x18,0x93,0x14,0xd2,0x0c,0x51,0x04,0x13, + 0x00,0x10,0x04,0x13,0x07,0x13,0x00,0x11,0x04,0x13,0x09,0x13,0x00,0x00,0x00,0x53, + 0x04,0x13,0x00,0x92,0x08,0x11,0x04,0x13,0x00,0x00,0x00,0x00,0x00,0x94,0x20,0xd3, + 0x10,0x52,0x04,0x14,0x00,0x51,0x04,0x14,0x00,0x10,0x04,0x00,0x00,0x14,0x00,0x92, + 0x0c,0x91,0x08,0x10,0x04,0x14,0x00,0x00,0x00,0x14,0x00,0x14,0x00,0x14,0x00,0xd0, + 0x52,0xcf,0x86,0xd5,0x3c,0xd4,0x14,0x53,0x04,0x14,0x00,0x52,0x04,0x14,0x00,0x51, + 0x04,0x14,0x00,0x10,0x04,0x14,0x00,0x00,0x00,0xd3,0x18,0xd2,0x0c,0x51,0x04,0x14, + 0x00,0x10,0x04,0x00,0x00,0x14,0x00,0x51,0x04,0x14,0x00,0x10,0x04,0x14,0x00,0x14, + 0x09,0x92,0x0c,0x91,0x08,0x10,0x04,0x14,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x94, + 0x10,0x53,0x04,0x14,0x00,0x92,0x08,0x11,0x04,0x14,0x00,0x00,0x00,0x00,0x00,0x00, + 0x00,0xcf,0x06,0x00,0x00,0xd2,0x2a,0xd1,0x06,0xcf,0x06,0x00,0x00,0xd0,0x06,0xcf, + 0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x14,0x00,0x53,0x04,0x14, + 0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x14,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd1, + 0x06,0xcf,0x06,0x00,0x00,0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x15, + 0x00,0x54,0x04,0x15,0x00,0xd3,0x0c,0x92,0x08,0x11,0x04,0x15,0x00,0x00,0x00,0x00, + 0x00,0x52,0x04,0x00,0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x15,0x00,0xd0, + 0xca,0xcf,0x86,0xd5,0xc2,0xd4,0x54,0xd3,0x06,0xcf,0x06,0x09,0x00,0xd2,0x06,0xcf, + 0x06,0x09,0x00,0xd1,0x24,0xd0,0x06,0xcf,0x06,0x09,0x00,0xcf,0x86,0x55,0x04,0x09, + 0x00,0x94,0x14,0x53,0x04,0x09,0x00,0x52,0x04,0x09,0x00,0x51,0x04,0x09,0x00,0x10, + 0x04,0x09,0x00,0x10,0x00,0x10,0x00,0xd0,0x1e,0xcf,0x86,0x95,0x18,0x54,0x04,0x10, + 0x00,0x53,0x04,0x10,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x10,0x00,0x11,0x00,0x00, + 0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xd3,0x68,0xd2,0x46,0xd1,0x40,0xd0, + 0x06,0xcf,0x06,0x09,0x00,0xcf,0x86,0x55,0x04,0x09,0x00,0xd4,0x20,0xd3,0x10,0x92, + 0x0c,0x51,0x04,0x09,0x00,0x10,0x04,0x09,0x00,0x10,0x00,0x10,0x00,0x52,0x04,0x10, + 0x00,0x51,0x04,0x10,0x00,0x10,0x04,0x10,0x00,0x00,0x00,0x93,0x10,0x52,0x04,0x09, + 0x00,0x91,0x08,0x10,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x11, + 0x00,0xd1,0x1c,0xd0,0x06,0xcf,0x06,0x11,0x00,0xcf,0x86,0x95,0x10,0x94,0x0c,0x93, + 0x08,0x12,0x04,0x11,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00, + 0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x86,0xd5,0x4c,0xd4,0x06,0xcf, + 0x06,0x0b,0x00,0xd3,0x40,0xd2,0x3a,0xd1,0x34,0xd0,0x2e,0xcf,0x86,0x55,0x04,0x0b, + 0x00,0xd4,0x14,0x53,0x04,0x0b,0x00,0x52,0x04,0x0b,0x00,0x51,0x04,0x0b,0x00,0x10, + 0x04,0x0b,0x00,0x00,0x00,0x53,0x04,0x15,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x15, + 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf, + 0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xd1,0x4c,0xd0,0x44,0xcf, + 0x86,0xd5,0x3c,0xd4,0x06,0xcf,0x06,0x00,0x00,0xd3,0x06,0xcf,0x06,0x11,0x00,0xd2, + 0x2a,0xd1,0x24,0xd0,0x06,0xcf,0x06,0x11,0x00,0xcf,0x86,0x95,0x18,0x94,0x14,0x93, + 0x10,0x52,0x04,0x11,0x00,0x51,0x04,0x11,0x00,0x10,0x04,0x11,0x00,0x00,0x00,0x00, + 0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00, + 0x00,0xcf,0x86,0xcf,0x06,0x00,0x00,0xe0,0xd2,0x01,0xcf,0x86,0xd5,0x06,0xcf,0x06, + 0x00,0x00,0xe4,0x0b,0x01,0xd3,0x06,0xcf,0x06,0x0c,0x00,0xd2,0x84,0xd1,0x50,0xd0, + 0x1e,0xcf,0x86,0x55,0x04,0x0c,0x00,0x54,0x04,0x0c,0x00,0x53,0x04,0x0c,0x00,0x92, + 0x0c,0x91,0x08,0x10,0x04,0x0c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0xd5, + 0x18,0x54,0x04,0x10,0x00,0x53,0x04,0x10,0x00,0x52,0x04,0x10,0x00,0x51,0x04,0x10, + 0x00,0x10,0x04,0x10,0x00,0x00,0x00,0x94,0x14,0x53,0x04,0x10,0x00,0xd2,0x08,0x11, + 0x04,0x10,0x00,0x00,0x00,0x11,0x04,0x00,0x00,0x10,0x00,0x00,0x00,0xd0,0x06,0xcf, + 0x06,0x00,0x00,0xcf,0x86,0xd5,0x08,0x14,0x04,0x00,0x00,0x10,0x00,0xd4,0x10,0x53, + 0x04,0x10,0x00,0x52,0x04,0x10,0x00,0x11,0x04,0x10,0x00,0x00,0x00,0x93,0x10,0x52, + 0x04,0x10,0x01,0x91,0x08,0x10,0x04,0x10,0x01,0x10,0x00,0x00,0x00,0x00,0x00,0xd1, + 0x6c,0xd0,0x1e,0xcf,0x86,0x55,0x04,0x10,0x00,0x54,0x04,0x10,0x00,0x93,0x10,0x52, + 0x04,0x10,0xe6,0x51,0x04,0x10,0xe6,0x10,0x04,0x10,0xe6,0x10,0x00,0x10,0x00,0xcf, + 0x86,0xd5,0x24,0xd4,0x10,0x93,0x0c,0x52,0x04,0x10,0x00,0x11,0x04,0x10,0x00,0x00, + 0x00,0x00,0x00,0x53,0x04,0x10,0x00,0x92,0x0c,0x51,0x04,0x10,0x00,0x10,0x04,0x00, + 0x00,0x10,0x00,0x10,0x00,0xd4,0x14,0x93,0x10,0x92,0x0c,0x51,0x04,0x10,0x00,0x10, + 0x04,0x00,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x53,0x04,0x10,0x00,0x52,0x04,0x00, + 0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x10,0x00,0x10,0x00,0xd0,0x0e,0xcf,0x86,0x95, + 0x08,0x14,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xd3,0x06,0xcf, + 0x06,0x00,0x00,0xd2,0x30,0xd1,0x0c,0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x06,0x14, + 0x00,0xd0,0x1e,0xcf,0x86,0x95,0x18,0x54,0x04,0x14,0x00,0x53,0x04,0x14,0x00,0x92, + 0x0c,0x51,0x04,0x14,0x00,0x10,0x04,0x14,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf, + 0x06,0x00,0x00,0xd1,0x4c,0xd0,0x06,0xcf,0x06,0x0d,0x00,0xcf,0x86,0xd5,0x2c,0x94, + 0x28,0xd3,0x10,0x52,0x04,0x0d,0x00,0x91,0x08,0x10,0x04,0x0d,0x00,0x15,0x00,0x15, + 0x00,0xd2,0x0c,0x51,0x04,0x15,0x00,0x10,0x04,0x15,0x00,0x00,0x00,0x51,0x04,0x00, + 0x00,0x10,0x04,0x00,0x00,0x15,0x00,0x0d,0x00,0x54,0x04,0x0d,0x00,0x53,0x04,0x0d, + 0x00,0x52,0x04,0x0d,0x00,0x51,0x04,0x0d,0x00,0x10,0x04,0x0d,0x00,0x15,0x00,0xd0, + 0x1e,0xcf,0x86,0x95,0x18,0x94,0x14,0x53,0x04,0x15,0x00,0x52,0x04,0x00,0x00,0x51, + 0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x0d,0x00,0x0d,0x00,0x00,0x00,0xcf,0x86,0x55, + 0x04,0x00,0x00,0x94,0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x12,0x00,0x13, + 0x00,0x15,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0xcf,0x06,0x12,0x00,0xe2, + 0xc6,0x01,0xd1,0x8e,0xd0,0x86,0xcf,0x86,0xd5,0x48,0xd4,0x06,0xcf,0x06,0x12,0x00, + 0xd3,0x06,0xcf,0x06,0x12,0x00,0xd2,0x06,0xcf,0x06,0x12,0x00,0xd1,0x06,0xcf,0x06, + 0x12,0x00,0xd0,0x06,0xcf,0x06,0x12,0x00,0xcf,0x86,0x55,0x04,0x12,0x00,0xd4,0x14, + 0x53,0x04,0x12,0x00,0x52,0x04,0x12,0x00,0x91,0x08,0x10,0x04,0x12,0x00,0x14,0x00, + 0x14,0x00,0x93,0x0c,0x92,0x08,0x11,0x04,0x14,0x00,0x15,0x00,0x15,0x00,0x00,0x00, + 0xd4,0x36,0xd3,0x06,0xcf,0x06,0x12,0x00,0xd2,0x2a,0xd1,0x06,0xcf,0x06,0x12,0x00, + 0xd0,0x06,0xcf,0x06,0x12,0x00,0xcf,0x86,0x55,0x04,0x12,0x00,0x54,0x04,0x12,0x00, + 0x93,0x10,0x92,0x0c,0x51,0x04,0x12,0x00,0x10,0x04,0x12,0x00,0x00,0x00,0x00,0x00, + 0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x86,0xcf,0x06,0x00,0x00, + 0xd0,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xcf,0x86,0xd5,0xa2,0xd4,0x9c,0xd3,0x74, + 0xd2,0x26,0xd1,0x20,0xd0,0x1a,0xcf,0x86,0x95,0x14,0x94,0x10,0x93,0x0c,0x92,0x08, + 0x11,0x04,0x0c,0x00,0x13,0x00,0x13,0x00,0x13,0x00,0x13,0x00,0x13,0x00,0xcf,0x06, + 0x13,0x00,0xcf,0x06,0x13,0x00,0xd1,0x48,0xd0,0x1e,0xcf,0x86,0x95,0x18,0x54,0x04, + 0x13,0x00,0x53,0x04,0x13,0x00,0x52,0x04,0x13,0x00,0x51,0x04,0x13,0x00,0x10,0x04, + 0x13,0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0xd5,0x18,0x54,0x04,0x00,0x00,0x93,0x10, + 0x92,0x0c,0x51,0x04,0x15,0x00,0x10,0x04,0x15,0x00,0x00,0x00,0x00,0x00,0x00,0x00, + 0x94,0x0c,0x93,0x08,0x12,0x04,0x00,0x00,0x15,0x00,0x00,0x00,0x13,0x00,0xcf,0x06, + 0x13,0x00,0xd2,0x22,0xd1,0x06,0xcf,0x06,0x13,0x00,0xd0,0x06,0xcf,0x06,0x13,0x00, + 0xcf,0x86,0x55,0x04,0x13,0x00,0x54,0x04,0x13,0x00,0x53,0x04,0x13,0x00,0x12,0x04, + 0x13,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf,0x06, + 0x00,0x00,0xd3,0x7f,0xd2,0x79,0xd1,0x34,0xd0,0x06,0xcf,0x06,0x10,0x00,0xcf,0x86, + 0x55,0x04,0x10,0x00,0xd4,0x14,0x53,0x04,0x10,0x00,0x92,0x0c,0x51,0x04,0x10,0x00, + 0x10,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0x53,0x04,0x10,0x00,0x52,0x04,0x10,0x00, + 0x91,0x08,0x10,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0xd0,0x3f,0xcf,0x86,0xd5,0x2c, + 0xd4,0x14,0x53,0x04,0x10,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x10,0x00,0x00,0x00, + 0x00,0x00,0x00,0x00,0x53,0x04,0x10,0x00,0xd2,0x08,0x11,0x04,0x10,0x00,0x00,0x00, + 0x51,0x04,0x10,0x00,0x10,0x04,0x10,0x01,0x10,0x00,0x94,0x0d,0x93,0x09,0x12,0x05, + 0x10,0xff,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00, + 0x00,0xcf,0x06,0x00,0x00,0xe1,0x96,0x04,0xd0,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00, + 0xcf,0x86,0xe5,0x33,0x04,0xe4,0x83,0x02,0xe3,0xf8,0x01,0xd2,0x26,0xd1,0x06,0xcf, + 0x06,0x05,0x00,0xd0,0x06,0xcf,0x06,0x05,0x00,0xcf,0x86,0x55,0x04,0x05,0x00,0x54, + 0x04,0x05,0x00,0x93,0x0c,0x52,0x04,0x05,0x00,0x11,0x04,0x05,0x00,0x00,0x00,0x00, + 0x00,0xd1,0xef,0xd0,0x2a,0xcf,0x86,0x55,0x04,0x05,0x00,0x94,0x20,0xd3,0x10,0x52, + 0x04,0x05,0x00,0x51,0x04,0x05,0x00,0x10,0x04,0x05,0x00,0x00,0x00,0x92,0x0c,0x91, + 0x08,0x10,0x04,0x00,0x00,0x0a,0x00,0x05,0x00,0x05,0x00,0x05,0x00,0xcf,0x86,0xd5, + 0x2a,0x54,0x04,0x05,0x00,0x53,0x04,0x05,0x00,0x52,0x04,0x05,0x00,0x51,0x04,0x05, + 0x00,0x10,0x0d,0x05,0xff,0xf0,0x9d,0x85,0x97,0xf0,0x9d,0x85,0xa5,0x00,0x05,0xff, + 0xf0,0x9d,0x85,0x98,0xf0,0x9d,0x85,0xa5,0x00,0xd4,0x75,0xd3,0x61,0xd2,0x44,0xd1, + 0x22,0x10,0x11,0x05,0xff,0xf0,0x9d,0x85,0x98,0xf0,0x9d,0x85,0xa5,0xf0,0x9d,0x85, + 0xae,0x00,0x05,0xff,0xf0,0x9d,0x85,0x98,0xf0,0x9d,0x85,0xa5,0xf0,0x9d,0x85,0xaf, + 0x00,0x10,0x11,0x05,0xff,0xf0,0x9d,0x85,0x98,0xf0,0x9d,0x85,0xa5,0xf0,0x9d,0x85, + 0xb0,0x00,0x05,0xff,0xf0,0x9d,0x85,0x98,0xf0,0x9d,0x85,0xa5,0xf0,0x9d,0x85,0xb1, + 0x00,0xd1,0x15,0x10,0x11,0x05,0xff,0xf0,0x9d,0x85,0x98,0xf0,0x9d,0x85,0xa5,0xf0, + 0x9d,0x85,0xb2,0x00,0x05,0xd8,0x10,0x04,0x05,0xd8,0x05,0x01,0xd2,0x08,0x11,0x04, + 0x05,0x01,0x05,0x00,0x91,0x08,0x10,0x04,0x05,0x00,0x05,0xe2,0x05,0xd8,0xd3,0x12, + 0x92,0x0d,0x51,0x04,0x05,0xd8,0x10,0x04,0x05,0xd8,0x05,0xff,0x00,0x05,0xff,0x00, + 0x92,0x0e,0x51,0x05,0x05,0xff,0x00,0x10,0x05,0x05,0xff,0x00,0x05,0xdc,0x05,0xdc, + 0xd0,0x97,0xcf,0x86,0xd5,0x28,0x94,0x24,0xd3,0x18,0xd2,0x0c,0x51,0x04,0x05,0xdc, + 0x10,0x04,0x05,0xdc,0x05,0x00,0x91,0x08,0x10,0x04,0x05,0x00,0x05,0xe6,0x05,0xe6, + 0x92,0x08,0x11,0x04,0x05,0xe6,0x05,0xdc,0x05,0x00,0x05,0x00,0xd4,0x14,0x53,0x04, + 0x05,0x00,0xd2,0x08,0x11,0x04,0x05,0x00,0x05,0xe6,0x11,0x04,0x05,0xe6,0x05,0x00, + 0x53,0x04,0x05,0x00,0xd2,0x15,0x51,0x04,0x05,0x00,0x10,0x04,0x05,0x00,0x05,0xff, + 0xf0,0x9d,0x86,0xb9,0xf0,0x9d,0x85,0xa5,0x00,0xd1,0x1e,0x10,0x0d,0x05,0xff,0xf0, + 0x9d,0x86,0xba,0xf0,0x9d,0x85,0xa5,0x00,0x05,0xff,0xf0,0x9d,0x86,0xb9,0xf0,0x9d, + 0x85,0xa5,0xf0,0x9d,0x85,0xae,0x00,0x10,0x11,0x05,0xff,0xf0,0x9d,0x86,0xba,0xf0, + 0x9d,0x85,0xa5,0xf0,0x9d,0x85,0xae,0x00,0x05,0xff,0xf0,0x9d,0x86,0xb9,0xf0,0x9d, + 0x85,0xa5,0xf0,0x9d,0x85,0xaf,0x00,0xcf,0x86,0xd5,0x31,0xd4,0x21,0x93,0x1d,0x92, + 0x19,0x91,0x15,0x10,0x11,0x05,0xff,0xf0,0x9d,0x86,0xba,0xf0,0x9d,0x85,0xa5,0xf0, + 0x9d,0x85,0xaf,0x00,0x05,0x00,0x05,0x00,0x05,0x00,0x05,0x00,0x53,0x04,0x05,0x00, + 0x52,0x04,0x05,0x00,0x11,0x04,0x05,0x00,0x11,0x00,0x94,0x14,0x53,0x04,0x11,0x00, + 0x92,0x0c,0x91,0x08,0x10,0x04,0x11,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, + 0xd2,0x44,0xd1,0x28,0xd0,0x06,0xcf,0x06,0x08,0x00,0xcf,0x86,0x95,0x1c,0x94,0x18, + 0x93,0x14,0xd2,0x08,0x11,0x04,0x08,0x00,0x08,0xe6,0x91,0x08,0x10,0x04,0x08,0xe6, + 0x08,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xd0,0x06,0xcf,0x06,0x00,0x00, + 0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x14,0x00,0x93,0x08,0x12,0x04,0x14,0x00, + 0x00,0x00,0x00,0x00,0xd1,0x40,0xd0,0x06,0xcf,0x06,0x07,0x00,0xcf,0x86,0xd5,0x18, + 0x54,0x04,0x07,0x00,0x93,0x10,0x52,0x04,0x07,0x00,0x51,0x04,0x07,0x00,0x10,0x04, + 0x07,0x00,0x00,0x00,0x00,0x00,0x54,0x04,0x09,0x00,0xd3,0x0c,0x92,0x08,0x11,0x04, + 0x09,0x00,0x14,0x00,0x14,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x14,0x00,0x00,0x00, + 0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xe3,0x5f,0x01,0xd2,0xb4,0xd1,0x24,0xd0, + 0x06,0xcf,0x06,0x05,0x00,0xcf,0x86,0x95,0x18,0x54,0x04,0x05,0x00,0x93,0x10,0x52, + 0x04,0x05,0x00,0x91,0x08,0x10,0x04,0x05,0x00,0x00,0x00,0x05,0x00,0x05,0x00,0x05, + 0x00,0xd0,0x6a,0xcf,0x86,0xd5,0x18,0x54,0x04,0x05,0x00,0x53,0x04,0x05,0x00,0x52, + 0x04,0x05,0x00,0x91,0x08,0x10,0x04,0x05,0x00,0x00,0x00,0x05,0x00,0xd4,0x34,0xd3, + 0x1c,0xd2,0x0c,0x51,0x04,0x00,0x00,0x10,0x04,0x05,0x00,0x00,0x00,0xd1,0x08,0x10, + 0x04,0x00,0x00,0x05,0x00,0x10,0x04,0x05,0x00,0x00,0x00,0xd2,0x0c,0x91,0x08,0x10, + 0x04,0x00,0x00,0x05,0x00,0x05,0x00,0x91,0x08,0x10,0x04,0x05,0x00,0x00,0x00,0x05, + 0x00,0x53,0x04,0x05,0x00,0xd2,0x0c,0x51,0x04,0x05,0x00,0x10,0x04,0x00,0x00,0x05, + 0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x05,0x00,0x05,0x00,0xcf,0x86,0x95,0x20,0x94, + 0x1c,0x93,0x18,0xd2,0x0c,0x91,0x08,0x10,0x04,0x05,0x00,0x07,0x00,0x05,0x00,0x91, + 0x08,0x10,0x04,0x00,0x00,0x05,0x00,0x05,0x00,0x05,0x00,0x05,0x00,0x05,0x00,0xd1, + 0xa4,0xd0,0x6a,0xcf,0x86,0xd5,0x48,0xd4,0x28,0xd3,0x10,0x52,0x04,0x05,0x00,0x51, + 0x04,0x05,0x00,0x10,0x04,0x00,0x00,0x05,0x00,0xd2,0x0c,0x51,0x04,0x05,0x00,0x10, + 0x04,0x05,0x00,0x00,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x05,0x00,0x05,0x00,0xd3, + 0x10,0x52,0x04,0x05,0x00,0x91,0x08,0x10,0x04,0x05,0x00,0x00,0x00,0x05,0x00,0x52, + 0x04,0x05,0x00,0x91,0x08,0x10,0x04,0x05,0x00,0x00,0x00,0x05,0x00,0x54,0x04,0x05, + 0x00,0x53,0x04,0x05,0x00,0xd2,0x0c,0x51,0x04,0x05,0x00,0x10,0x04,0x00,0x00,0x05, + 0x00,0x51,0x04,0x05,0x00,0x10,0x04,0x05,0x00,0x00,0x00,0xcf,0x86,0x95,0x34,0xd4, + 0x20,0xd3,0x14,0x52,0x04,0x05,0x00,0xd1,0x08,0x10,0x04,0x05,0x00,0x00,0x00,0x10, + 0x04,0x05,0x00,0x00,0x00,0x92,0x08,0x11,0x04,0x00,0x00,0x05,0x00,0x05,0x00,0x93, + 0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x05,0x00,0x00,0x00,0x05,0x00,0x05,0x00,0x05, + 0x00,0x05,0x00,0xcf,0x06,0x05,0x00,0xd2,0x26,0xd1,0x06,0xcf,0x06,0x05,0x00,0xd0, + 0x1a,0xcf,0x86,0x55,0x04,0x05,0x00,0x94,0x10,0x93,0x0c,0x52,0x04,0x05,0x00,0x11, + 0x04,0x08,0x00,0x00,0x00,0x05,0x00,0x05,0x00,0xcf,0x06,0x05,0x00,0xd1,0x06,0xcf, + 0x06,0x05,0x00,0xd0,0x06,0xcf,0x06,0x05,0x00,0xcf,0x86,0x95,0x18,0x94,0x14,0x53, + 0x04,0x05,0x00,0xd2,0x08,0x11,0x04,0x05,0x00,0x09,0x00,0x11,0x04,0x00,0x00,0x05, + 0x00,0x05,0x00,0x05,0x00,0xd4,0x52,0xd3,0x06,0xcf,0x06,0x11,0x00,0xd2,0x46,0xd1, + 0x06,0xcf,0x06,0x11,0x00,0xd0,0x3a,0xcf,0x86,0xd5,0x20,0xd4,0x0c,0x53,0x04,0x11, + 0x00,0x12,0x04,0x11,0x00,0x00,0x00,0x53,0x04,0x00,0x00,0x92,0x0c,0x51,0x04,0x00, + 0x00,0x10,0x04,0x00,0x00,0x11,0x00,0x11,0x00,0x94,0x14,0x93,0x10,0x92,0x0c,0x91, + 0x08,0x10,0x04,0x00,0x00,0x11,0x00,0x11,0x00,0x11,0x00,0x11,0x00,0x00,0x00,0xcf, + 0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xe0,0xc2,0x03,0xcf,0x86, + 0xe5,0x03,0x01,0xd4,0xfc,0xd3,0xc0,0xd2,0x66,0xd1,0x60,0xd0,0x5a,0xcf,0x86,0xd5, + 0x2c,0xd4,0x14,0x93,0x10,0x52,0x04,0x12,0xe6,0x51,0x04,0x12,0xe6,0x10,0x04,0x12, + 0xe6,0x00,0x00,0x12,0xe6,0x53,0x04,0x12,0xe6,0x92,0x10,0xd1,0x08,0x10,0x04,0x12, + 0xe6,0x00,0x00,0x10,0x04,0x00,0x00,0x12,0xe6,0x12,0xe6,0x94,0x28,0xd3,0x18,0xd2, + 0x0c,0x51,0x04,0x12,0xe6,0x10,0x04,0x00,0x00,0x12,0xe6,0x91,0x08,0x10,0x04,0x12, + 0xe6,0x00,0x00,0x12,0xe6,0x92,0x0c,0x51,0x04,0x12,0xe6,0x10,0x04,0x12,0xe6,0x00, + 0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xd1,0x54,0xd0, + 0x36,0xcf,0x86,0x55,0x04,0x15,0x00,0xd4,0x14,0x53,0x04,0x15,0x00,0x52,0x04,0x15, + 0x00,0x91,0x08,0x10,0x04,0x15,0x00,0x00,0x00,0x00,0x00,0xd3,0x10,0x52,0x04,0x15, + 0xe6,0x51,0x04,0x15,0xe6,0x10,0x04,0x15,0xe6,0x15,0x00,0x52,0x04,0x15,0x00,0x11, + 0x04,0x15,0x00,0x00,0x00,0xcf,0x86,0x95,0x18,0x94,0x14,0x53,0x04,0x15,0x00,0xd2, + 0x08,0x11,0x04,0x15,0x00,0x00,0x00,0x11,0x04,0x00,0x00,0x15,0x00,0x00,0x00,0x00, + 0x00,0xcf,0x06,0x00,0x00,0xd2,0x36,0xd1,0x06,0xcf,0x06,0x00,0x00,0xd0,0x06,0xcf, + 0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x15,0x00,0xd4,0x0c,0x53,0x04,0x15,0x00,0x12, + 0x04,0x15,0x00,0x15,0xe6,0x53,0x04,0x15,0x00,0xd2,0x08,0x11,0x04,0x15,0x00,0x00, + 0x00,0x51,0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x15,0x00,0xcf,0x06,0x00,0x00,0xcf, + 0x06,0x00,0x00,0xd4,0x82,0xd3,0x7c,0xd2,0x3e,0xd1,0x06,0xcf,0x06,0x10,0x00,0xd0, + 0x06,0xcf,0x06,0x10,0x00,0xcf,0x86,0x95,0x2c,0xd4,0x18,0x93,0x14,0x52,0x04,0x10, + 0x00,0xd1,0x08,0x10,0x04,0x10,0x00,0x00,0x00,0x10,0x04,0x00,0x00,0x10,0x00,0x10, + 0x00,0x93,0x10,0x52,0x04,0x10,0xdc,0x51,0x04,0x10,0xdc,0x10,0x04,0x10,0xdc,0x00, + 0x00,0x00,0x00,0x00,0x00,0xd1,0x38,0xd0,0x06,0xcf,0x06,0x12,0x00,0xcf,0x86,0x95, + 0x2c,0xd4,0x18,0xd3,0x08,0x12,0x04,0x12,0x00,0x12,0xe6,0x92,0x0c,0x51,0x04,0x12, + 0xe6,0x10,0x04,0x12,0x07,0x15,0x00,0x00,0x00,0x53,0x04,0x12,0x00,0xd2,0x08,0x11, + 0x04,0x12,0x00,0x00,0x00,0x11,0x04,0x00,0x00,0x12,0x00,0x00,0x00,0xcf,0x06,0x00, + 0x00,0xcf,0x06,0x00,0x00,0xd3,0x82,0xd2,0x48,0xd1,0x24,0xd0,0x06,0xcf,0x06,0x00, + 0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x00,0x00,0x93,0x10,0x92,0x0c,0x91, + 0x08,0x10,0x04,0x00,0x00,0x14,0x00,0x14,0x00,0x14,0x00,0x14,0x00,0xd0,0x1e,0xcf, + 0x86,0x55,0x04,0x14,0x00,0x54,0x04,0x14,0x00,0x93,0x10,0x52,0x04,0x14,0x00,0x91, + 0x08,0x10,0x04,0x14,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xd1, + 0x34,0xd0,0x2e,0xcf,0x86,0xd5,0x18,0x94,0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10, + 0x04,0x00,0x00,0x15,0x00,0x15,0x00,0x15,0x00,0x15,0x00,0x15,0x00,0x54,0x04,0x15, + 0x00,0x53,0x04,0x15,0x00,0x52,0x04,0x15,0x00,0x11,0x04,0x15,0x00,0x00,0x00,0xcf, + 0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xe2,0xb2,0x01,0xe1,0x41,0x01,0xd0,0x6e,0xcf, + 0x86,0xd5,0x18,0x94,0x14,0x93,0x10,0x52,0x04,0x0d,0x00,0x91,0x08,0x10,0x04,0x00, + 0x00,0x0d,0x00,0x0d,0x00,0x0d,0x00,0x0d,0x00,0xd4,0x30,0xd3,0x20,0xd2,0x10,0xd1, + 0x08,0x10,0x04,0x00,0x00,0x0d,0x00,0x10,0x04,0x0d,0x00,0x00,0x00,0xd1,0x08,0x10, + 0x04,0x0d,0x00,0x00,0x00,0x10,0x04,0x00,0x00,0x0d,0x00,0x92,0x0c,0x91,0x08,0x10, + 0x04,0x00,0x00,0x0d,0x00,0x0d,0x00,0x0d,0x00,0xd3,0x10,0x92,0x0c,0x51,0x04,0x0d, + 0x00,0x10,0x04,0x0d,0x00,0x00,0x00,0x0d,0x00,0x92,0x10,0xd1,0x08,0x10,0x04,0x00, + 0x00,0x0d,0x00,0x10,0x04,0x00,0x00,0x0d,0x00,0x00,0x00,0xcf,0x86,0xd5,0x74,0xd4, + 0x34,0xd3,0x18,0xd2,0x0c,0x51,0x04,0x00,0x00,0x10,0x04,0x0d,0x00,0x00,0x00,0x51, + 0x04,0x00,0x00,0x10,0x04,0x00,0x00,0x0d,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04,0x00, + 0x00,0x0d,0x00,0x10,0x04,0x00,0x00,0x0d,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x0d, + 0x00,0x0d,0x00,0xd3,0x20,0xd2,0x10,0xd1,0x08,0x10,0x04,0x00,0x00,0x0d,0x00,0x10, + 0x04,0x0d,0x00,0x00,0x00,0xd1,0x08,0x10,0x04,0x0d,0x00,0x00,0x00,0x10,0x04,0x00, + 0x00,0x0d,0x00,0xd2,0x10,0xd1,0x08,0x10,0x04,0x00,0x00,0x0d,0x00,0x10,0x04,0x00, + 0x00,0x0d,0x00,0xd1,0x08,0x10,0x04,0x00,0x00,0x0d,0x00,0x10,0x04,0x00,0x00,0x0d, + 0x00,0xd4,0x30,0xd3,0x20,0xd2,0x10,0xd1,0x08,0x10,0x04,0x00,0x00,0x0d,0x00,0x10, + 0x04,0x0d,0x00,0x00,0x00,0xd1,0x08,0x10,0x04,0x0d,0x00,0x00,0x00,0x10,0x04,0x00, + 0x00,0x0d,0x00,0x92,0x0c,0x51,0x04,0x0d,0x00,0x10,0x04,0x0d,0x00,0x00,0x00,0x0d, + 0x00,0xd3,0x10,0x92,0x0c,0x51,0x04,0x0d,0x00,0x10,0x04,0x0d,0x00,0x00,0x00,0x0d, + 0x00,0xd2,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x0d,0x00,0x0d,0x00,0xd1,0x08,0x10, + 0x04,0x0d,0x00,0x00,0x00,0x10,0x04,0x0d,0x00,0x00,0x00,0xd0,0x56,0xcf,0x86,0xd5, + 0x20,0xd4,0x14,0x53,0x04,0x0d,0x00,0x92,0x0c,0x51,0x04,0x0d,0x00,0x10,0x04,0x00, + 0x00,0x0d,0x00,0x0d,0x00,0x53,0x04,0x0d,0x00,0x12,0x04,0x0d,0x00,0x00,0x00,0xd4, + 0x28,0xd3,0x18,0xd2,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x0d,0x00,0x0d,0x00,0x91, + 0x08,0x10,0x04,0x00,0x00,0x0d,0x00,0x0d,0x00,0x92,0x0c,0x51,0x04,0x0d,0x00,0x10, + 0x04,0x00,0x00,0x0d,0x00,0x0d,0x00,0x53,0x04,0x0d,0x00,0x12,0x04,0x0d,0x00,0x00, + 0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x00,0x00,0x93,0x0c,0x92,0x08,0x11, + 0x04,0x0d,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x86,0xe5, + 0x96,0x05,0xe4,0x28,0x03,0xe3,0xed,0x01,0xd2,0xa0,0xd1,0x1c,0xd0,0x16,0xcf,0x86, + 0x55,0x04,0x0a,0x00,0x94,0x0c,0x53,0x04,0x0a,0x00,0x12,0x04,0x0a,0x00,0x00,0x00, + 0x0a,0x00,0xcf,0x06,0x0a,0x00,0xd0,0x46,0xcf,0x86,0xd5,0x10,0x54,0x04,0x0a,0x00, + 0x93,0x08,0x12,0x04,0x0a,0x00,0x00,0x00,0x00,0x00,0xd4,0x14,0x53,0x04,0x0c,0x00, + 0x52,0x04,0x0c,0x00,0x51,0x04,0x0c,0x00,0x10,0x04,0x0c,0x00,0x00,0x00,0xd3,0x10, + 0x92,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x0c,0x00,0x0c,0x00,0x0c,0x00,0x52,0x04, + 0x0c,0x00,0x51,0x04,0x0c,0x00,0x10,0x04,0x0c,0x00,0x10,0x00,0xcf,0x86,0xd5,0x28, + 0xd4,0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x0c,0x00,0x0c,0x00, + 0x0c,0x00,0x0c,0x00,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x00,0x00,0x0c,0x00, + 0x0c,0x00,0x0c,0x00,0x0c,0x00,0x54,0x04,0x10,0x00,0x93,0x0c,0x52,0x04,0x10,0x00, + 0x11,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0xd1,0xe4,0xd0,0x5a,0xcf,0x86,0xd5,0x20, + 0x94,0x1c,0x53,0x04,0x0b,0x00,0xd2,0x0c,0x51,0x04,0x0b,0x00,0x10,0x04,0x0b,0x00, + 0x10,0x00,0x91,0x08,0x10,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0x0b,0x00,0xd4,0x14, + 0x53,0x04,0x0b,0x00,0x52,0x04,0x0b,0x00,0x51,0x04,0x0b,0x00,0x10,0x04,0x0b,0x00, + 0x14,0x00,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x0c,0x00,0x0b,0x00,0x0c,0x00, + 0x0c,0x00,0x52,0x04,0x0c,0x00,0xd1,0x08,0x10,0x04,0x0c,0x00,0x0b,0x00,0x10,0x04, + 0x0c,0x00,0x0b,0x00,0xcf,0x86,0xd5,0x4c,0xd4,0x2c,0xd3,0x18,0xd2,0x0c,0x51,0x04, + 0x0c,0x00,0x10,0x04,0x0b,0x00,0x0c,0x00,0x51,0x04,0x0c,0x00,0x10,0x04,0x0b,0x00, + 0x0c,0x00,0xd2,0x08,0x11,0x04,0x0c,0x00,0x0b,0x00,0x51,0x04,0x0b,0x00,0x10,0x04, + 0x0b,0x00,0x0c,0x00,0xd3,0x10,0x52,0x04,0x0c,0x00,0x51,0x04,0x0c,0x00,0x10,0x04, + 0x0c,0x00,0x0b,0x00,0x52,0x04,0x0c,0x00,0x51,0x04,0x0c,0x00,0x10,0x04,0x0c,0x00, + 0x0b,0x00,0xd4,0x18,0x53,0x04,0x0c,0x00,0xd2,0x08,0x11,0x04,0x0c,0x00,0x0d,0x00, + 0x91,0x08,0x10,0x04,0x15,0x00,0x00,0x00,0x00,0x00,0x53,0x04,0x0c,0x00,0xd2,0x10, + 0xd1,0x08,0x10,0x04,0x0c,0x00,0x0b,0x00,0x10,0x04,0x0c,0x00,0x0b,0x00,0xd1,0x08, + 0x10,0x04,0x0b,0x00,0x0c,0x00,0x10,0x04,0x0c,0x00,0x0b,0x00,0xd0,0x4e,0xcf,0x86, + 0xd5,0x34,0xd4,0x14,0x53,0x04,0x0c,0x00,0xd2,0x08,0x11,0x04,0x0c,0x00,0x0b,0x00, + 0x11,0x04,0x0b,0x00,0x0c,0x00,0xd3,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x0b,0x00, + 0x0c,0x00,0x0c,0x00,0x0c,0x00,0x92,0x0c,0x51,0x04,0x0c,0x00,0x10,0x04,0x0c,0x00, + 0x12,0x00,0x12,0x00,0x94,0x14,0x53,0x04,0x12,0x00,0x52,0x04,0x12,0x00,0x91,0x08, + 0x10,0x04,0x12,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00, + 0x94,0x10,0x93,0x0c,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x0c,0x00,0x0c,0x00, + 0x0c,0x00,0xd2,0x7e,0xd1,0x78,0xd0,0x3e,0xcf,0x86,0xd5,0x1c,0x94,0x18,0x93,0x14, + 0x92,0x10,0xd1,0x08,0x10,0x04,0x0b,0x00,0x0c,0x00,0x10,0x04,0x0c,0x00,0x00,0x00, + 0x00,0x00,0x00,0x00,0x0b,0x00,0x54,0x04,0x0b,0x00,0xd3,0x0c,0x92,0x08,0x11,0x04, + 0x0b,0x00,0x0c,0x00,0x0c,0x00,0x92,0x0c,0x51,0x04,0x0c,0x00,0x10,0x04,0x0c,0x00, + 0x12,0x00,0x00,0x00,0xcf,0x86,0xd5,0x24,0xd4,0x14,0x53,0x04,0x0b,0x00,0x92,0x0c, + 0x91,0x08,0x10,0x04,0x0b,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x93,0x0c,0x92,0x08, + 0x11,0x04,0x0c,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x94,0x10,0x93,0x0c,0x52,0x04, + 0x13,0x00,0x11,0x04,0x13,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00, + 0xd1,0x58,0xd0,0x3a,0xcf,0x86,0x55,0x04,0x0c,0x00,0xd4,0x20,0xd3,0x10,0x92,0x0c, + 0x91,0x08,0x10,0x04,0x0c,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x52,0x04,0x10,0x00, + 0x91,0x08,0x10,0x04,0x10,0x00,0x11,0x00,0x11,0x00,0x93,0x10,0x52,0x04,0x0c,0x00, + 0x51,0x04,0x0c,0x00,0x10,0x04,0x10,0x00,0x0c,0x00,0x0c,0x00,0xcf,0x86,0x55,0x04, + 0x0c,0x00,0x54,0x04,0x0c,0x00,0x53,0x04,0x0c,0x00,0x52,0x04,0x0c,0x00,0x91,0x08, + 0x10,0x04,0x0c,0x00,0x10,0x00,0x11,0x00,0xd0,0x16,0xcf,0x86,0x95,0x10,0x54,0x04, + 0x0c,0x00,0x93,0x08,0x12,0x04,0x0c,0x00,0x10,0x00,0x10,0x00,0x0c,0x00,0xcf,0x86, + 0xd5,0x34,0xd4,0x28,0xd3,0x10,0x52,0x04,0x0c,0x00,0x91,0x08,0x10,0x04,0x0c,0x00, + 0x10,0x00,0x0c,0x00,0xd2,0x0c,0x51,0x04,0x0c,0x00,0x10,0x04,0x0c,0x00,0x10,0x00, + 0x51,0x04,0x10,0x00,0x10,0x04,0x10,0x00,0x11,0x00,0x93,0x08,0x12,0x04,0x11,0x00, + 0x10,0x00,0x10,0x00,0x54,0x04,0x0c,0x00,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04, + 0x0c,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x11,0x00,0xd3,0xfc,0xd2,0x6c,0xd1,0x3c, + 0xd0,0x1e,0xcf,0x86,0x55,0x04,0x0c,0x00,0x54,0x04,0x0c,0x00,0x53,0x04,0x0c,0x00, + 0x52,0x04,0x0c,0x00,0x51,0x04,0x0c,0x00,0x10,0x04,0x0c,0x00,0x10,0x00,0xcf,0x86, + 0x95,0x18,0x94,0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x0c,0x00,0x10,0x00, + 0x0c,0x00,0x0c,0x00,0x0c,0x00,0x0c,0x00,0x0c,0x00,0xd0,0x06,0xcf,0x06,0x0c,0x00, + 0xcf,0x86,0x55,0x04,0x0c,0x00,0x54,0x04,0x0c,0x00,0x53,0x04,0x0c,0x00,0xd2,0x0c, + 0x91,0x08,0x10,0x04,0x10,0x00,0x0c,0x00,0x0c,0x00,0xd1,0x08,0x10,0x04,0x0c,0x00, + 0x10,0x00,0x10,0x04,0x10,0x00,0x11,0x00,0xd1,0x54,0xd0,0x1a,0xcf,0x86,0x55,0x04, + 0x0c,0x00,0x54,0x04,0x0c,0x00,0x53,0x04,0x0c,0x00,0x52,0x04,0x0c,0x00,0x11,0x04, + 0x0c,0x00,0x10,0x00,0xcf,0x86,0xd5,0x1c,0x94,0x18,0xd3,0x08,0x12,0x04,0x0d,0x00, + 0x10,0x00,0x92,0x0c,0x51,0x04,0x10,0x00,0x10,0x04,0x10,0x00,0x11,0x00,0x11,0x00, + 0x0c,0x00,0xd4,0x08,0x13,0x04,0x0c,0x00,0x10,0x00,0x53,0x04,0x10,0x00,0x92,0x0c, + 0x51,0x04,0x10,0x00,0x10,0x04,0x12,0x00,0x10,0x00,0x10,0x00,0xd0,0x1e,0xcf,0x86, + 0x55,0x04,0x10,0x00,0x94,0x14,0x93,0x10,0x52,0x04,0x10,0x00,0x91,0x08,0x10,0x04, + 0x12,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0x10,0x00,0xcf,0x86,0x55,0x04,0x10,0x00, + 0x54,0x04,0x10,0x00,0x53,0x04,0x10,0x00,0x92,0x0c,0x51,0x04,0x10,0x00,0x10,0x04, + 0x10,0x00,0x0c,0x00,0x0c,0x00,0xe2,0x19,0x01,0xd1,0xa8,0xd0,0x7e,0xcf,0x86,0xd5, + 0x4c,0xd4,0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x0d,0x00,0x0c,0x00,0x0c, + 0x00,0x0c,0x00,0x0c,0x00,0xd3,0x1c,0xd2,0x0c,0x91,0x08,0x10,0x04,0x0c,0x00,0x0d, + 0x00,0x0c,0x00,0xd1,0x08,0x10,0x04,0x0c,0x00,0x0d,0x00,0x10,0x04,0x0c,0x00,0x0d, + 0x00,0xd2,0x10,0xd1,0x08,0x10,0x04,0x0c,0x00,0x0d,0x00,0x10,0x04,0x0c,0x00,0x0d, + 0x00,0x51,0x04,0x0c,0x00,0x10,0x04,0x0c,0x00,0x0d,0x00,0xd4,0x1c,0xd3,0x0c,0x52, + 0x04,0x0c,0x00,0x11,0x04,0x0c,0x00,0x0d,0x00,0x52,0x04,0x0c,0x00,0x91,0x08,0x10, + 0x04,0x0d,0x00,0x0c,0x00,0x0d,0x00,0x93,0x10,0x52,0x04,0x0c,0x00,0x91,0x08,0x10, + 0x04,0x0d,0x00,0x0c,0x00,0x0c,0x00,0x0c,0x00,0xcf,0x86,0x95,0x24,0x94,0x20,0x93, + 0x1c,0xd2,0x10,0xd1,0x08,0x10,0x04,0x0c,0x00,0x10,0x00,0x10,0x04,0x10,0x00,0x11, + 0x00,0x91,0x08,0x10,0x04,0x11,0x00,0x0c,0x00,0x0c,0x00,0x0c,0x00,0x10,0x00,0x10, + 0x00,0xd0,0x06,0xcf,0x06,0x0c,0x00,0xcf,0x86,0xd5,0x30,0xd4,0x10,0x93,0x0c,0x52, + 0x04,0x0c,0x00,0x11,0x04,0x0c,0x00,0x10,0x00,0x10,0x00,0x93,0x1c,0xd2,0x10,0xd1, + 0x08,0x10,0x04,0x11,0x00,0x12,0x00,0x10,0x04,0x12,0x00,0x13,0x00,0x91,0x08,0x10, + 0x04,0x13,0x00,0x15,0x00,0x00,0x00,0x00,0x00,0xd4,0x14,0x53,0x04,0x10,0x00,0x52, + 0x04,0x10,0x00,0x91,0x08,0x10,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0xd3,0x10,0x52, + 0x04,0x10,0x00,0x51,0x04,0x12,0x00,0x10,0x04,0x12,0x00,0x13,0x00,0x92,0x10,0xd1, + 0x08,0x10,0x04,0x13,0x00,0x14,0x00,0x10,0x04,0x15,0x00,0x00,0x00,0x00,0x00,0xd1, + 0x1c,0xd0,0x06,0xcf,0x06,0x0c,0x00,0xcf,0x86,0x55,0x04,0x0c,0x00,0x54,0x04,0x0c, + 0x00,0x93,0x08,0x12,0x04,0x0c,0x00,0x00,0x00,0x00,0x00,0xd0,0x06,0xcf,0x06,0x10, + 0x00,0xcf,0x86,0xd5,0x24,0x54,0x04,0x10,0x00,0xd3,0x10,0x52,0x04,0x10,0x00,0x91, + 0x08,0x10,0x04,0x10,0x00,0x14,0x00,0x14,0x00,0x92,0x0c,0x91,0x08,0x10,0x04,0x14, + 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x94,0x0c,0x53,0x04,0x15,0x00,0x12,0x04,0x15, + 0x00,0x00,0x00,0x00,0x00,0xe4,0x40,0x02,0xe3,0xc9,0x01,0xd2,0x5c,0xd1,0x34,0xd0, + 0x16,0xcf,0x86,0x95,0x10,0x94,0x0c,0x53,0x04,0x10,0x00,0x12,0x04,0x10,0x00,0x00, + 0x00,0x10,0x00,0x10,0x00,0xcf,0x86,0x95,0x18,0xd4,0x08,0x13,0x04,0x10,0x00,0x00, + 0x00,0x53,0x04,0x10,0x00,0x92,0x08,0x11,0x04,0x10,0x00,0x00,0x00,0x00,0x00,0x10, + 0x00,0xd0,0x22,0xcf,0x86,0xd5,0x0c,0x94,0x08,0x13,0x04,0x10,0x00,0x00,0x00,0x10, + 0x00,0x94,0x10,0x53,0x04,0x10,0x00,0x52,0x04,0x10,0x00,0x11,0x04,0x10,0x00,0x00, + 0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xd1,0xc0,0xd0,0x5e,0xcf,0x86,0xd5,0x30,0xd4, + 0x14,0x53,0x04,0x13,0x00,0x52,0x04,0x13,0x00,0x91,0x08,0x10,0x04,0x00,0x00,0x15, + 0x00,0x15,0x00,0x53,0x04,0x11,0x00,0xd2,0x0c,0x91,0x08,0x10,0x04,0x11,0x00,0x12, + 0x00,0x12,0x00,0x51,0x04,0x12,0x00,0x10,0x04,0x12,0x00,0x13,0x00,0xd4,0x08,0x13, + 0x04,0x12,0x00,0x13,0x00,0xd3,0x14,0x92,0x10,0xd1,0x08,0x10,0x04,0x12,0x00,0x13, + 0x00,0x10,0x04,0x13,0x00,0x12,0x00,0x12,0x00,0x52,0x04,0x12,0x00,0x51,0x04,0x12, + 0x00,0x10,0x04,0x12,0x00,0x15,0x00,0xcf,0x86,0xd5,0x28,0xd4,0x14,0x53,0x04,0x12, + 0x00,0x52,0x04,0x12,0x00,0x91,0x08,0x10,0x04,0x13,0x00,0x14,0x00,0x14,0x00,0x53, + 0x04,0x12,0x00,0x52,0x04,0x12,0x00,0x51,0x04,0x12,0x00,0x10,0x04,0x12,0x00,0x13, + 0x00,0xd4,0x0c,0x53,0x04,0x13,0x00,0x12,0x04,0x13,0x00,0x14,0x00,0xd3,0x1c,0xd2, + 0x10,0xd1,0x08,0x10,0x04,0x14,0x00,0x15,0x00,0x10,0x04,0x00,0x00,0x14,0x00,0x51, + 0x04,0x14,0x00,0x10,0x04,0x14,0x00,0x00,0x00,0x92,0x0c,0x51,0x04,0x00,0x00,0x10, + 0x04,0x14,0x00,0x15,0x00,0x14,0x00,0xd0,0x62,0xcf,0x86,0xd5,0x24,0xd4,0x14,0x93, + 0x10,0x52,0x04,0x11,0x00,0x91,0x08,0x10,0x04,0x11,0x00,0x12,0x00,0x12,0x00,0x12, + 0x00,0x93,0x0c,0x92,0x08,0x11,0x04,0x12,0x00,0x13,0x00,0x13,0x00,0x14,0x00,0xd4, + 0x2c,0xd3,0x18,0xd2,0x0c,0x51,0x04,0x14,0x00,0x10,0x04,0x14,0x00,0x00,0x00,0x91, + 0x08,0x10,0x04,0x00,0x00,0x15,0x00,0x15,0x00,0xd2,0x0c,0x51,0x04,0x15,0x00,0x10, + 0x04,0x15,0x00,0x00,0x00,0x11,0x04,0x00,0x00,0x15,0x00,0x53,0x04,0x14,0x00,0x92, + 0x08,0x11,0x04,0x14,0x00,0x15,0x00,0x15,0x00,0xcf,0x86,0xd5,0x30,0x94,0x2c,0xd3, + 0x14,0x92,0x10,0xd1,0x08,0x10,0x04,0x11,0x00,0x14,0x00,0x10,0x04,0x14,0x00,0x15, + 0x00,0x15,0x00,0xd2,0x0c,0x51,0x04,0x15,0x00,0x10,0x04,0x15,0x00,0x00,0x00,0x91, + 0x08,0x10,0x04,0x00,0x00,0x15,0x00,0x15,0x00,0x13,0x00,0x94,0x14,0x93,0x10,0x52, + 0x04,0x13,0x00,0x51,0x04,0x13,0x00,0x10,0x04,0x13,0x00,0x14,0x00,0x14,0x00,0x14, + 0x00,0xd2,0x70,0xd1,0x40,0xd0,0x06,0xcf,0x06,0x15,0x00,0xcf,0x86,0xd5,0x10,0x54, + 0x04,0x15,0x00,0x93,0x08,0x12,0x04,0x15,0x00,0x00,0x00,0x00,0x00,0xd4,0x10,0x53, + 0x04,0x14,0x00,0x52,0x04,0x14,0x00,0x11,0x04,0x14,0x00,0x00,0x00,0xd3,0x08,0x12, + 0x04,0x15,0x00,0x00,0x00,0x92,0x0c,0x51,0x04,0x15,0x00,0x10,0x04,0x15,0x00,0x00, + 0x00,0x00,0x00,0xd0,0x2a,0xcf,0x86,0x95,0x24,0xd4,0x14,0x93,0x10,0x92,0x0c,0x51, + 0x04,0x15,0x00,0x10,0x04,0x15,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x93,0x0c,0x52, + 0x04,0x15,0x00,0x11,0x04,0x15,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00, + 0x00,0xcf,0x06,0x00,0x00,0xd3,0x06,0xcf,0x06,0x00,0x00,0xd2,0x06,0xcf,0x06,0x00, + 0x00,0xd1,0x06,0xcf,0x06,0x00,0x00,0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55, + 0x04,0x00,0x00,0x54,0x04,0x00,0x00,0x53,0x04,0x00,0x00,0x52,0x04,0x00,0x00,0x11, + 0x04,0x00,0x00,0x02,0x00,0xe4,0xf9,0x12,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x05,0x00, + 0xd2,0xc2,0xd1,0x08,0xcf,0x86,0xcf,0x06,0x05,0x00,0xd0,0x44,0xcf,0x86,0xd5,0x3c, + 0xd4,0x06,0xcf,0x06,0x05,0x00,0xd3,0x06,0xcf,0x06,0x05,0x00,0xd2,0x2a,0xd1,0x06, + 0xcf,0x06,0x05,0x00,0xd0,0x06,0xcf,0x06,0x05,0x00,0xcf,0x86,0x95,0x18,0x54,0x04, + 0x05,0x00,0x93,0x10,0x52,0x04,0x05,0x00,0x51,0x04,0x05,0x00,0x10,0x04,0x05,0x00, + 0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x0b,0x00,0xcf,0x06,0x0b,0x00,0xcf,0x86, + 0xd5,0x3c,0xd4,0x06,0xcf,0x06,0x0b,0x00,0xd3,0x06,0xcf,0x06,0x0b,0x00,0xd2,0x06, + 0xcf,0x06,0x0b,0x00,0xd1,0x24,0xd0,0x1e,0xcf,0x86,0x55,0x04,0x0b,0x00,0x54,0x04, + 0x0b,0x00,0x93,0x10,0x52,0x04,0x0b,0x00,0x91,0x08,0x10,0x04,0x0b,0x00,0x00,0x00, + 0x00,0x00,0x00,0x00,0xcf,0x06,0x0c,0x00,0xcf,0x06,0x0c,0x00,0xd4,0x32,0xd3,0x2c, + 0xd2,0x26,0xd1,0x20,0xd0,0x1a,0xcf,0x86,0x95,0x14,0x54,0x04,0x0c,0x00,0x53,0x04, + 0x0c,0x00,0x52,0x04,0x0c,0x00,0x11,0x04,0x0c,0x00,0x00,0x00,0x11,0x00,0xcf,0x06, + 0x11,0x00,0xcf,0x06,0x11,0x00,0xcf,0x06,0x11,0x00,0xcf,0x06,0x11,0x00,0xcf,0x06, + 0x11,0x00,0xd1,0x48,0xd0,0x40,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x11,0x00,0xd4,0x06, + 0xcf,0x06,0x11,0x00,0xd3,0x06,0xcf,0x06,0x11,0x00,0xd2,0x26,0xd1,0x06,0xcf,0x06, + 0x11,0x00,0xd0,0x1a,0xcf,0x86,0x55,0x04,0x11,0x00,0x94,0x10,0x93,0x0c,0x92,0x08, + 0x11,0x04,0x11,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x13,0x00,0xcf,0x06,0x13,0x00, + 0xcf,0x06,0x13,0x00,0xcf,0x86,0xcf,0x06,0x13,0x00,0xd0,0x44,0xcf,0x86,0xd5,0x06, + 0xcf,0x06,0x13,0x00,0xd4,0x36,0xd3,0x06,0xcf,0x06,0x13,0x00,0xd2,0x06,0xcf,0x06, + 0x13,0x00,0xd1,0x06,0xcf,0x06,0x13,0x00,0xd0,0x06,0xcf,0x06,0x13,0x00,0xcf,0x86, + 0x55,0x04,0x13,0x00,0x94,0x14,0x93,0x10,0x92,0x0c,0x91,0x08,0x10,0x04,0x13,0x00, + 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x86, + 0xd5,0x06,0xcf,0x06,0x00,0x00,0xe4,0x68,0x11,0xe3,0x51,0x10,0xe2,0x17,0x08,0xe1, + 0x06,0x04,0xe0,0x03,0x02,0xcf,0x86,0xe5,0x06,0x01,0xd4,0x82,0xd3,0x41,0xd2,0x21, + 0xd1,0x10,0x10,0x08,0x05,0xff,0xe4,0xb8,0xbd,0x00,0x05,0xff,0xe4,0xb8,0xb8,0x00, + 0x10,0x08,0x05,0xff,0xe4,0xb9,0x81,0x00,0x05,0xff,0xf0,0xa0,0x84,0xa2,0x00,0xd1, + 0x10,0x10,0x08,0x05,0xff,0xe4,0xbd,0xa0,0x00,0x05,0xff,0xe4,0xbe,0xae,0x00,0x10, + 0x08,0x05,0xff,0xe4,0xbe,0xbb,0x00,0x05,0xff,0xe5,0x80,0x82,0x00,0xd2,0x20,0xd1, + 0x10,0x10,0x08,0x05,0xff,0xe5,0x81,0xba,0x00,0x05,0xff,0xe5,0x82,0x99,0x00,0x10, + 0x08,0x05,0xff,0xe5,0x83,0xa7,0x00,0x05,0xff,0xe5,0x83,0x8f,0x00,0xd1,0x11,0x10, + 0x08,0x05,0xff,0xe3,0x92,0x9e,0x00,0x05,0xff,0xf0,0xa0,0x98,0xba,0x00,0x10,0x08, + 0x05,0xff,0xe5,0x85,0x8d,0x00,0x05,0xff,0xe5,0x85,0x94,0x00,0xd3,0x42,0xd2,0x21, + 0xd1,0x10,0x10,0x08,0x05,0xff,0xe5,0x85,0xa4,0x00,0x05,0xff,0xe5,0x85,0xb7,0x00, + 0x10,0x09,0x05,0xff,0xf0,0xa0,0x94,0x9c,0x00,0x05,0xff,0xe3,0x92,0xb9,0x00,0xd1, + 0x10,0x10,0x08,0x05,0xff,0xe5,0x85,0xa7,0x00,0x05,0xff,0xe5,0x86,0x8d,0x00,0x10, + 0x09,0x05,0xff,0xf0,0xa0,0x95,0x8b,0x00,0x05,0xff,0xe5,0x86,0x97,0x00,0xd2,0x20, + 0xd1,0x10,0x10,0x08,0x05,0xff,0xe5,0x86,0xa4,0x00,0x05,0xff,0xe4,0xbb,0x8c,0x00, + 0x10,0x08,0x05,0xff,0xe5,0x86,0xac,0x00,0x05,0xff,0xe5,0x86,0xb5,0x00,0xd1,0x11, + 0x10,0x09,0x05,0xff,0xf0,0xa9,0x87,0x9f,0x00,0x05,0xff,0xe5,0x87,0xb5,0x00,0x10, + 0x08,0x05,0xff,0xe5,0x88,0x83,0x00,0x05,0xff,0xe3,0x93,0x9f,0x00,0xd4,0x80,0xd3, + 0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe5,0x88,0xbb,0x00,0x05,0xff,0xe5, + 0x89,0x86,0x00,0x10,0x08,0x05,0xff,0xe5,0x89,0xb2,0x00,0x05,0xff,0xe5,0x89,0xb7, + 0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe3,0x94,0x95,0x00,0x05,0xff,0xe5,0x8b,0x87, + 0x00,0x10,0x08,0x05,0xff,0xe5,0x8b,0x89,0x00,0x05,0xff,0xe5,0x8b,0xa4,0x00,0xd2, + 0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe5,0x8b,0xba,0x00,0x05,0xff,0xe5,0x8c,0x85, + 0x00,0x10,0x08,0x05,0xff,0xe5,0x8c,0x86,0x00,0x05,0xff,0xe5,0x8c,0x97,0x00,0xd1, + 0x10,0x10,0x08,0x05,0xff,0xe5,0x8d,0x89,0x00,0x05,0xff,0xe5,0x8d,0x91,0x00,0x10, + 0x08,0x05,0xff,0xe5,0x8d,0x9a,0x00,0x05,0xff,0xe5,0x8d,0xb3,0x00,0xd3,0x39,0xd2, + 0x18,0x91,0x10,0x10,0x08,0x05,0xff,0xe5,0x8d,0xbd,0x00,0x05,0xff,0xe5,0x8d,0xbf, + 0x00,0x05,0xff,0xe5,0x8d,0xbf,0x00,0xd1,0x11,0x10,0x09,0x05,0xff,0xf0,0xa0,0xa8, + 0xac,0x00,0x05,0xff,0xe7,0x81,0xb0,0x00,0x10,0x08,0x05,0xff,0xe5,0x8f,0x8a,0x00, + 0x05,0xff,0xe5,0x8f,0x9f,0x00,0xd2,0x21,0xd1,0x11,0x10,0x09,0x05,0xff,0xf0,0xa0, + 0xad,0xa3,0x00,0x05,0xff,0xe5,0x8f,0xab,0x00,0x10,0x08,0x05,0xff,0xe5,0x8f,0xb1, + 0x00,0x05,0xff,0xe5,0x90,0x86,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe5,0x92,0x9e, + 0x00,0x05,0xff,0xe5,0x90,0xb8,0x00,0x10,0x08,0x05,0xff,0xe5,0x91,0x88,0x00,0x05, + 0xff,0xe5,0x91,0xa8,0x00,0xcf,0x86,0xe5,0x02,0x01,0xd4,0x80,0xd3,0x40,0xd2,0x20, + 0xd1,0x10,0x10,0x08,0x05,0xff,0xe5,0x92,0xa2,0x00,0x05,0xff,0xe5,0x93,0xb6,0x00, + 0x10,0x08,0x05,0xff,0xe5,0x94,0x90,0x00,0x05,0xff,0xe5,0x95,0x93,0x00,0xd1,0x10, + 0x10,0x08,0x05,0xff,0xe5,0x95,0xa3,0x00,0x05,0xff,0xe5,0x96,0x84,0x00,0x10,0x08, + 0x05,0xff,0xe5,0x96,0x84,0x00,0x05,0xff,0xe5,0x96,0x99,0x00,0xd2,0x20,0xd1,0x10, + 0x10,0x08,0x05,0xff,0xe5,0x96,0xab,0x00,0x05,0xff,0xe5,0x96,0xb3,0x00,0x10,0x08, + 0x05,0xff,0xe5,0x97,0x82,0x00,0x05,0xff,0xe5,0x9c,0x96,0x00,0xd1,0x10,0x10,0x08, + 0x05,0xff,0xe5,0x98,0x86,0x00,0x05,0xff,0xe5,0x9c,0x97,0x00,0x10,0x08,0x05,0xff, + 0xe5,0x99,0x91,0x00,0x05,0xff,0xe5,0x99,0xb4,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10, + 0x10,0x08,0x05,0xff,0xe5,0x88,0x87,0x00,0x05,0xff,0xe5,0xa3,0xae,0x00,0x10,0x08, + 0x05,0xff,0xe5,0x9f,0x8e,0x00,0x05,0xff,0xe5,0x9f,0xb4,0x00,0xd1,0x10,0x10,0x08, + 0x05,0xff,0xe5,0xa0,0x8d,0x00,0x05,0xff,0xe5,0x9e,0x8b,0x00,0x10,0x08,0x05,0xff, + 0xe5,0xa0,0xb2,0x00,0x05,0xff,0xe5,0xa0,0xb1,0x00,0xd2,0x21,0xd1,0x11,0x10,0x08, + 0x05,0xff,0xe5,0xa2,0xac,0x00,0x05,0xff,0xf0,0xa1,0x93,0xa4,0x00,0x10,0x08,0x05, + 0xff,0xe5,0xa3,0xb2,0x00,0x05,0xff,0xe5,0xa3,0xb7,0x00,0xd1,0x10,0x10,0x08,0x05, + 0xff,0xe5,0xa4,0x86,0x00,0x05,0xff,0xe5,0xa4,0x9a,0x00,0x10,0x08,0x05,0xff,0xe5, + 0xa4,0xa2,0x00,0x05,0xff,0xe5,0xa5,0xa2,0x00,0xd4,0x7b,0xd3,0x42,0xd2,0x22,0xd1, + 0x12,0x10,0x09,0x05,0xff,0xf0,0xa1,0x9a,0xa8,0x00,0x05,0xff,0xf0,0xa1,0x9b,0xaa, + 0x00,0x10,0x08,0x05,0xff,0xe5,0xa7,0xac,0x00,0x05,0xff,0xe5,0xa8,0x9b,0x00,0xd1, + 0x10,0x10,0x08,0x05,0xff,0xe5,0xa8,0xa7,0x00,0x05,0xff,0xe5,0xa7,0x98,0x00,0x10, + 0x08,0x05,0xff,0xe5,0xa9,0xa6,0x00,0x05,0xff,0xe3,0x9b,0xae,0x00,0xd2,0x18,0x91, + 0x10,0x10,0x08,0x05,0xff,0xe3,0x9b,0xbc,0x00,0x05,0xff,0xe5,0xac,0x88,0x00,0x05, + 0xff,0xe5,0xac,0xbe,0x00,0xd1,0x11,0x10,0x09,0x05,0xff,0xf0,0xa1,0xa7,0x88,0x00, + 0x05,0xff,0xe5,0xaf,0x83,0x00,0x10,0x08,0x05,0xff,0xe5,0xaf,0x98,0x00,0x05,0xff, + 0xe5,0xaf,0xa7,0x00,0xd3,0x41,0xd2,0x21,0xd1,0x11,0x10,0x08,0x05,0xff,0xe5,0xaf, + 0xb3,0x00,0x05,0xff,0xf0,0xa1,0xac,0x98,0x00,0x10,0x08,0x05,0xff,0xe5,0xaf,0xbf, + 0x00,0x05,0xff,0xe5,0xb0,0x86,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe5,0xbd,0x93, + 0x00,0x05,0xff,0xe5,0xb0,0xa2,0x00,0x10,0x08,0x05,0xff,0xe3,0x9e,0x81,0x00,0x05, + 0xff,0xe5,0xb1,0xa0,0x00,0xd2,0x21,0xd1,0x10,0x10,0x08,0x05,0xff,0xe5,0xb1,0xae, + 0x00,0x05,0xff,0xe5,0xb3,0x80,0x00,0x10,0x08,0x05,0xff,0xe5,0xb2,0x8d,0x00,0x05, + 0xff,0xf0,0xa1,0xb7,0xa4,0x00,0xd1,0x11,0x10,0x08,0x05,0xff,0xe5,0xb5,0x83,0x00, + 0x05,0xff,0xf0,0xa1,0xb7,0xa6,0x00,0x10,0x08,0x05,0xff,0xe5,0xb5,0xae,0x00,0x05, + 0xff,0xe5,0xb5,0xab,0x00,0xe0,0x04,0x02,0xcf,0x86,0xd5,0xfe,0xd4,0x82,0xd3,0x40, + 0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe5,0xb5,0xbc,0x00,0x05,0xff,0xe5,0xb7, + 0xa1,0x00,0x10,0x08,0x05,0xff,0xe5,0xb7,0xa2,0x00,0x05,0xff,0xe3,0xa0,0xaf,0x00, + 0xd1,0x10,0x10,0x08,0x05,0xff,0xe5,0xb7,0xbd,0x00,0x05,0xff,0xe5,0xb8,0xa8,0x00, + 0x10,0x08,0x05,0xff,0xe5,0xb8,0xbd,0x00,0x05,0xff,0xe5,0xb9,0xa9,0x00,0xd2,0x21, + 0xd1,0x11,0x10,0x08,0x05,0xff,0xe3,0xa1,0xa2,0x00,0x05,0xff,0xf0,0xa2,0x86,0x83, + 0x00,0x10,0x08,0x05,0xff,0xe3,0xa1,0xbc,0x00,0x05,0xff,0xe5,0xba,0xb0,0x00,0xd1, + 0x10,0x10,0x08,0x05,0xff,0xe5,0xba,0xb3,0x00,0x05,0xff,0xe5,0xba,0xb6,0x00,0x10, + 0x08,0x05,0xff,0xe5,0xbb,0x8a,0x00,0x05,0xff,0xf0,0xaa,0x8e,0x92,0x00,0xd3,0x3b, + 0xd2,0x22,0xd1,0x11,0x10,0x08,0x05,0xff,0xe5,0xbb,0xbe,0x00,0x05,0xff,0xf0,0xa2, + 0x8c,0xb1,0x00,0x10,0x09,0x05,0xff,0xf0,0xa2,0x8c,0xb1,0x00,0x05,0xff,0xe8,0x88, + 0x81,0x00,0x51,0x08,0x05,0xff,0xe5,0xbc,0xa2,0x00,0x10,0x08,0x05,0xff,0xe3,0xa3, + 0x87,0x00,0x05,0xff,0xf0,0xa3,0x8a,0xb8,0x00,0xd2,0x21,0xd1,0x11,0x10,0x09,0x05, + 0xff,0xf0,0xa6,0x87,0x9a,0x00,0x05,0xff,0xe5,0xbd,0xa2,0x00,0x10,0x08,0x05,0xff, + 0xe5,0xbd,0xab,0x00,0x05,0xff,0xe3,0xa3,0xa3,0x00,0xd1,0x10,0x10,0x08,0x05,0xff, + 0xe5,0xbe,0x9a,0x00,0x05,0xff,0xe5,0xbf,0x8d,0x00,0x10,0x08,0x05,0xff,0xe5,0xbf, + 0x97,0x00,0x05,0xff,0xe5,0xbf,0xb9,0x00,0xd4,0x81,0xd3,0x41,0xd2,0x20,0xd1,0x10, + 0x10,0x08,0x05,0xff,0xe6,0x82,0x81,0x00,0x05,0xff,0xe3,0xa4,0xba,0x00,0x10,0x08, + 0x05,0xff,0xe3,0xa4,0x9c,0x00,0x05,0xff,0xe6,0x82,0x94,0x00,0xd1,0x11,0x10,0x09, + 0x05,0xff,0xf0,0xa2,0x9b,0x94,0x00,0x05,0xff,0xe6,0x83,0x87,0x00,0x10,0x08,0x05, + 0xff,0xe6,0x85,0x88,0x00,0x05,0xff,0xe6,0x85,0x8c,0x00,0xd2,0x20,0xd1,0x10,0x10, + 0x08,0x05,0xff,0xe6,0x85,0x8e,0x00,0x05,0xff,0xe6,0x85,0x8c,0x00,0x10,0x08,0x05, + 0xff,0xe6,0x85,0xba,0x00,0x05,0xff,0xe6,0x86,0x8e,0x00,0xd1,0x10,0x10,0x08,0x05, + 0xff,0xe6,0x86,0xb2,0x00,0x05,0xff,0xe6,0x86,0xa4,0x00,0x10,0x08,0x05,0xff,0xe6, + 0x86,0xaf,0x00,0x05,0xff,0xe6,0x87,0x9e,0x00,0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10, + 0x08,0x05,0xff,0xe6,0x87,0xb2,0x00,0x05,0xff,0xe6,0x87,0xb6,0x00,0x10,0x08,0x05, + 0xff,0xe6,0x88,0x90,0x00,0x05,0xff,0xe6,0x88,0x9b,0x00,0xd1,0x10,0x10,0x08,0x05, + 0xff,0xe6,0x89,0x9d,0x00,0x05,0xff,0xe6,0x8a,0xb1,0x00,0x10,0x08,0x05,0xff,0xe6, + 0x8b,0x94,0x00,0x05,0xff,0xe6,0x8d,0x90,0x00,0xd2,0x21,0xd1,0x11,0x10,0x09,0x05, + 0xff,0xf0,0xa2,0xac,0x8c,0x00,0x05,0xff,0xe6,0x8c,0xbd,0x00,0x10,0x08,0x05,0xff, + 0xe6,0x8b,0xbc,0x00,0x05,0xff,0xe6,0x8d,0xa8,0x00,0xd1,0x10,0x10,0x08,0x05,0xff, + 0xe6,0x8e,0x83,0x00,0x05,0xff,0xe6,0x8f,0xa4,0x00,0x10,0x09,0x05,0xff,0xf0,0xa2, + 0xaf,0xb1,0x00,0x05,0xff,0xe6,0x90,0xa2,0x00,0xcf,0x86,0xe5,0x03,0x01,0xd4,0x81, + 0xd3,0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0x8f,0x85,0x00,0x05,0xff, + 0xe6,0x8e,0xa9,0x00,0x10,0x08,0x05,0xff,0xe3,0xa8,0xae,0x00,0x05,0xff,0xe6,0x91, + 0xa9,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0x91,0xbe,0x00,0x05,0xff,0xe6,0x92, + 0x9d,0x00,0x10,0x08,0x05,0xff,0xe6,0x91,0xb7,0x00,0x05,0xff,0xe3,0xa9,0xac,0x00, + 0xd2,0x21,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0x95,0x8f,0x00,0x05,0xff,0xe6,0x95, + 0xac,0x00,0x10,0x09,0x05,0xff,0xf0,0xa3,0x80,0x8a,0x00,0x05,0xff,0xe6,0x97,0xa3, + 0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0x9b,0xb8,0x00,0x05,0xff,0xe6,0x99,0x89, + 0x00,0x10,0x08,0x05,0xff,0xe3,0xac,0x99,0x00,0x05,0xff,0xe6,0x9a,0x91,0x00,0xd3, + 0x40,0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe3,0xac,0x88,0x00,0x05,0xff,0xe3, + 0xab,0xa4,0x00,0x10,0x08,0x05,0xff,0xe5,0x86,0x92,0x00,0x05,0xff,0xe5,0x86,0x95, + 0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0x9c,0x80,0x00,0x05,0xff,0xe6,0x9a,0x9c, + 0x00,0x10,0x08,0x05,0xff,0xe8,0x82,0xad,0x00,0x05,0xff,0xe4,0x8f,0x99,0x00,0xd2, + 0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0x9c,0x97,0x00,0x05,0xff,0xe6,0x9c,0x9b, + 0x00,0x10,0x08,0x05,0xff,0xe6,0x9c,0xa1,0x00,0x05,0xff,0xe6,0x9d,0x9e,0x00,0xd1, + 0x11,0x10,0x08,0x05,0xff,0xe6,0x9d,0x93,0x00,0x05,0xff,0xf0,0xa3,0x8f,0x83,0x00, + 0x10,0x08,0x05,0xff,0xe3,0xad,0x89,0x00,0x05,0xff,0xe6,0x9f,0xba,0x00,0xd4,0x82, + 0xd3,0x41,0xd2,0x21,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0x9e,0x85,0x00,0x05,0xff, + 0xe6,0xa1,0x92,0x00,0x10,0x08,0x05,0xff,0xe6,0xa2,0x85,0x00,0x05,0xff,0xf0,0xa3, + 0x91,0xad,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0xa2,0x8e,0x00,0x05,0xff,0xe6, + 0xa0,0x9f,0x00,0x10,0x08,0x05,0xff,0xe6,0xa4,0x94,0x00,0x05,0xff,0xe3,0xae,0x9d, + 0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0xa5,0x82,0x00,0x05,0xff,0xe6, + 0xa6,0xa3,0x00,0x10,0x08,0x05,0xff,0xe6,0xa7,0xaa,0x00,0x05,0xff,0xe6,0xaa,0xa8, + 0x00,0xd1,0x11,0x10,0x09,0x05,0xff,0xf0,0xa3,0x9a,0xa3,0x00,0x05,0xff,0xe6,0xab, + 0x9b,0x00,0x10,0x08,0x05,0xff,0xe3,0xb0,0x98,0x00,0x05,0xff,0xe6,0xac,0xa1,0x00, + 0xd3,0x42,0xd2,0x21,0xd1,0x11,0x10,0x09,0x05,0xff,0xf0,0xa3,0xa2,0xa7,0x00,0x05, + 0xff,0xe6,0xad,0x94,0x00,0x10,0x08,0x05,0xff,0xe3,0xb1,0x8e,0x00,0x05,0xff,0xe6, + 0xad,0xb2,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0xae,0x9f,0x00,0x05,0xff,0xe6, + 0xae,0xba,0x00,0x10,0x08,0x05,0xff,0xe6,0xae,0xbb,0x00,0x05,0xff,0xf0,0xa3,0xaa, + 0x8d,0x00,0xd2,0x23,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa1,0xb4,0x8b,0x00,0x05, + 0xff,0xf0,0xa3,0xab,0xba,0x00,0x10,0x08,0x05,0xff,0xe6,0xb1,0x8e,0x00,0x05,0xff, + 0xf0,0xa3,0xb2,0xbc,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0xb2,0xbf,0x00,0x05, + 0xff,0xe6,0xb3,0x8d,0x00,0x10,0x08,0x05,0xff,0xe6,0xb1,0xa7,0x00,0x05,0xff,0xe6, + 0xb4,0x96,0x00,0xe1,0x1d,0x04,0xe0,0x0c,0x02,0xcf,0x86,0xe5,0x08,0x01,0xd4,0x82, + 0xd3,0x41,0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0xb4,0xbe,0x00,0x05,0xff, + 0xe6,0xb5,0xb7,0x00,0x10,0x08,0x05,0xff,0xe6,0xb5,0x81,0x00,0x05,0xff,0xe6,0xb5, + 0xa9,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0xb5,0xb8,0x00,0x05,0xff,0xe6,0xb6, + 0x85,0x00,0x10,0x09,0x05,0xff,0xf0,0xa3,0xb4,0x9e,0x00,0x05,0xff,0xe6,0xb4,0xb4, + 0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe6,0xb8,0xaf,0x00,0x05,0xff,0xe6, + 0xb9,0xae,0x00,0x10,0x08,0x05,0xff,0xe3,0xb4,0xb3,0x00,0x05,0xff,0xe6,0xbb,0x8b, + 0x00,0xd1,0x11,0x10,0x08,0x05,0xff,0xe6,0xbb,0x87,0x00,0x05,0xff,0xf0,0xa3,0xbb, + 0x91,0x00,0x10,0x08,0x05,0xff,0xe6,0xb7,0xb9,0x00,0x05,0xff,0xe6,0xbd,0xae,0x00, + 0xd3,0x42,0xd2,0x22,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa3,0xbd,0x9e,0x00,0x05, + 0xff,0xf0,0xa3,0xbe,0x8e,0x00,0x10,0x08,0x05,0xff,0xe6,0xbf,0x86,0x00,0x05,0xff, + 0xe7,0x80,0xb9,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe7,0x80,0x9e,0x00,0x05,0xff, + 0xe7,0x80,0x9b,0x00,0x10,0x08,0x05,0xff,0xe3,0xb6,0x96,0x00,0x05,0xff,0xe7,0x81, + 0x8a,0x00,0xd2,0x21,0xd1,0x10,0x10,0x08,0x05,0xff,0xe7,0x81,0xbd,0x00,0x05,0xff, + 0xe7,0x81,0xb7,0x00,0x10,0x08,0x05,0xff,0xe7,0x82,0xad,0x00,0x05,0xff,0xf0,0xa0, + 0x94,0xa5,0x00,0xd1,0x11,0x10,0x08,0x05,0xff,0xe7,0x85,0x85,0x00,0x05,0xff,0xf0, + 0xa4,0x89,0xa3,0x00,0x10,0x08,0x05,0xff,0xe7,0x86,0x9c,0x00,0x05,0xff,0xf0,0xa4, + 0x8e,0xab,0x00,0xd4,0x7b,0xd3,0x43,0xd2,0x21,0xd1,0x10,0x10,0x08,0x05,0xff,0xe7, + 0x88,0xa8,0x00,0x05,0xff,0xe7,0x88,0xb5,0x00,0x10,0x08,0x05,0xff,0xe7,0x89,0x90, + 0x00,0x05,0xff,0xf0,0xa4,0x98,0x88,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe7,0x8a, + 0x80,0x00,0x05,0xff,0xe7,0x8a,0x95,0x00,0x10,0x09,0x05,0xff,0xf0,0xa4,0x9c,0xb5, + 0x00,0x05,0xff,0xf0,0xa4,0xa0,0x94,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff, + 0xe7,0x8d,0xba,0x00,0x05,0xff,0xe7,0x8e,0x8b,0x00,0x10,0x08,0x05,0xff,0xe3,0xba, + 0xac,0x00,0x05,0xff,0xe7,0x8e,0xa5,0x00,0x51,0x08,0x05,0xff,0xe3,0xba,0xb8,0x00, + 0x10,0x08,0x05,0xff,0xe7,0x91,0x87,0x00,0x05,0xff,0xe7,0x91,0x9c,0x00,0xd3,0x42, + 0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe7,0x91,0xb1,0x00,0x05,0xff,0xe7,0x92, + 0x85,0x00,0x10,0x08,0x05,0xff,0xe7,0x93,0x8a,0x00,0x05,0xff,0xe3,0xbc,0x9b,0x00, + 0xd1,0x11,0x10,0x08,0x05,0xff,0xe7,0x94,0xa4,0x00,0x05,0xff,0xf0,0xa4,0xb0,0xb6, + 0x00,0x10,0x08,0x05,0xff,0xe7,0x94,0xbe,0x00,0x05,0xff,0xf0,0xa4,0xb2,0x92,0x00, + 0xd2,0x22,0xd1,0x11,0x10,0x08,0x05,0xff,0xe7,0x95,0xb0,0x00,0x05,0xff,0xf0,0xa2, + 0x86,0x9f,0x00,0x10,0x08,0x05,0xff,0xe7,0x98,0x90,0x00,0x05,0xff,0xf0,0xa4,0xbe, + 0xa1,0x00,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa4,0xbe,0xb8,0x00,0x05,0xff,0xf0, + 0xa5,0x81,0x84,0x00,0x10,0x08,0x05,0xff,0xe3,0xbf,0xbc,0x00,0x05,0xff,0xe4,0x80, + 0x88,0x00,0xcf,0x86,0xe5,0x04,0x01,0xd4,0x7d,0xd3,0x3c,0xd2,0x23,0xd1,0x11,0x10, + 0x08,0x05,0xff,0xe7,0x9b,0xb4,0x00,0x05,0xff,0xf0,0xa5,0x83,0xb3,0x00,0x10,0x09, + 0x05,0xff,0xf0,0xa5,0x83,0xb2,0x00,0x05,0xff,0xf0,0xa5,0x84,0x99,0x00,0x91,0x11, + 0x10,0x09,0x05,0xff,0xf0,0xa5,0x84,0xb3,0x00,0x05,0xff,0xe7,0x9c,0x9e,0x00,0x05, + 0xff,0xe7,0x9c,0x9f,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe7,0x9d,0x8a, + 0x00,0x05,0xff,0xe4,0x80,0xb9,0x00,0x10,0x08,0x05,0xff,0xe7,0x9e,0x8b,0x00,0x05, + 0xff,0xe4,0x81,0x86,0x00,0xd1,0x11,0x10,0x08,0x05,0xff,0xe4,0x82,0x96,0x00,0x05, + 0xff,0xf0,0xa5,0x90,0x9d,0x00,0x10,0x08,0x05,0xff,0xe7,0xa1,0x8e,0x00,0x05,0xff, + 0xe7,0xa2,0x8c,0x00,0xd3,0x43,0xd2,0x21,0xd1,0x10,0x10,0x08,0x05,0xff,0xe7,0xa3, + 0x8c,0x00,0x05,0xff,0xe4,0x83,0xa3,0x00,0x10,0x09,0x05,0xff,0xf0,0xa5,0x98,0xa6, + 0x00,0x05,0xff,0xe7,0xa5,0x96,0x00,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa5,0x9a, + 0x9a,0x00,0x05,0xff,0xf0,0xa5,0x9b,0x85,0x00,0x10,0x08,0x05,0xff,0xe7,0xa6,0x8f, + 0x00,0x05,0xff,0xe7,0xa7,0xab,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe4, + 0x84,0xaf,0x00,0x05,0xff,0xe7,0xa9,0x80,0x00,0x10,0x08,0x05,0xff,0xe7,0xa9,0x8a, + 0x00,0x05,0xff,0xe7,0xa9,0x8f,0x00,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa5,0xa5, + 0xbc,0x00,0x05,0xff,0xf0,0xa5,0xaa,0xa7,0x00,0x10,0x09,0x05,0xff,0xf0,0xa5,0xaa, + 0xa7,0x00,0x05,0xff,0xe7,0xab,0xae,0x00,0xd4,0x83,0xd3,0x42,0xd2,0x21,0xd1,0x11, + 0x10,0x08,0x05,0xff,0xe4,0x88,0x82,0x00,0x05,0xff,0xf0,0xa5,0xae,0xab,0x00,0x10, + 0x08,0x05,0xff,0xe7,0xaf,0x86,0x00,0x05,0xff,0xe7,0xaf,0x89,0x00,0xd1,0x11,0x10, + 0x08,0x05,0xff,0xe4,0x88,0xa7,0x00,0x05,0xff,0xf0,0xa5,0xb2,0x80,0x00,0x10,0x08, + 0x05,0xff,0xe7,0xb3,0x92,0x00,0x05,0xff,0xe4,0x8a,0xa0,0x00,0xd2,0x21,0xd1,0x10, + 0x10,0x08,0x05,0xff,0xe7,0xb3,0xa8,0x00,0x05,0xff,0xe7,0xb3,0xa3,0x00,0x10,0x08, + 0x05,0xff,0xe7,0xb4,0x80,0x00,0x05,0xff,0xf0,0xa5,0xbe,0x86,0x00,0xd1,0x10,0x10, + 0x08,0x05,0xff,0xe7,0xb5,0xa3,0x00,0x05,0xff,0xe4,0x8c,0x81,0x00,0x10,0x08,0x05, + 0xff,0xe7,0xb7,0x87,0x00,0x05,0xff,0xe7,0xb8,0x82,0x00,0xd3,0x44,0xd2,0x22,0xd1, + 0x10,0x10,0x08,0x05,0xff,0xe7,0xb9,0x85,0x00,0x05,0xff,0xe4,0x8c,0xb4,0x00,0x10, + 0x09,0x05,0xff,0xf0,0xa6,0x88,0xa8,0x00,0x05,0xff,0xf0,0xa6,0x89,0x87,0x00,0xd1, + 0x11,0x10,0x08,0x05,0xff,0xe4,0x8d,0x99,0x00,0x05,0xff,0xf0,0xa6,0x8b,0x99,0x00, + 0x10,0x08,0x05,0xff,0xe7,0xbd,0xba,0x00,0x05,0xff,0xf0,0xa6,0x8c,0xbe,0x00,0xd2, + 0x21,0xd1,0x10,0x10,0x08,0x05,0xff,0xe7,0xbe,0x95,0x00,0x05,0xff,0xe7,0xbf,0xba, + 0x00,0x10,0x08,0x05,0xff,0xe8,0x80,0x85,0x00,0x05,0xff,0xf0,0xa6,0x93,0x9a,0x00, + 0xd1,0x11,0x10,0x09,0x05,0xff,0xf0,0xa6,0x94,0xa3,0x00,0x05,0xff,0xe8,0x81,0xa0, + 0x00,0x10,0x09,0x05,0xff,0xf0,0xa6,0x96,0xa8,0x00,0x05,0xff,0xe8,0x81,0xb0,0x00, + 0xe0,0x11,0x02,0xcf,0x86,0xe5,0x07,0x01,0xd4,0x85,0xd3,0x42,0xd2,0x21,0xd1,0x11, + 0x10,0x09,0x05,0xff,0xf0,0xa3,0x8d,0x9f,0x00,0x05,0xff,0xe4,0x8f,0x95,0x00,0x10, + 0x08,0x05,0xff,0xe8,0x82,0xb2,0x00,0x05,0xff,0xe8,0x84,0x83,0x00,0xd1,0x10,0x10, + 0x08,0x05,0xff,0xe4,0x90,0x8b,0x00,0x05,0xff,0xe8,0x84,0xbe,0x00,0x10,0x08,0x05, + 0xff,0xe5,0xaa,0xb5,0x00,0x05,0xff,0xf0,0xa6,0x9e,0xa7,0x00,0xd2,0x23,0xd1,0x12, + 0x10,0x09,0x05,0xff,0xf0,0xa6,0x9e,0xb5,0x00,0x05,0xff,0xf0,0xa3,0x8e,0x93,0x00, + 0x10,0x09,0x05,0xff,0xf0,0xa3,0x8e,0x9c,0x00,0x05,0xff,0xe8,0x88,0x81,0x00,0xd1, + 0x10,0x10,0x08,0x05,0xff,0xe8,0x88,0x84,0x00,0x05,0xff,0xe8,0xbe,0x9e,0x00,0x10, + 0x08,0x05,0xff,0xe4,0x91,0xab,0x00,0x05,0xff,0xe8,0x8a,0x91,0x00,0xd3,0x41,0xd2, + 0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe8,0x8a,0x8b,0x00,0x05,0xff,0xe8,0x8a,0x9d, + 0x00,0x10,0x08,0x05,0xff,0xe5,0x8a,0xb3,0x00,0x05,0xff,0xe8,0x8a,0xb1,0x00,0xd1, + 0x10,0x10,0x08,0x05,0xff,0xe8,0x8a,0xb3,0x00,0x05,0xff,0xe8,0x8a,0xbd,0x00,0x10, + 0x08,0x05,0xff,0xe8,0x8b,0xa6,0x00,0x05,0xff,0xf0,0xa6,0xac,0xbc,0x00,0xd2,0x20, + 0xd1,0x10,0x10,0x08,0x05,0xff,0xe8,0x8b,0xa5,0x00,0x05,0xff,0xe8,0x8c,0x9d,0x00, + 0x10,0x08,0x05,0xff,0xe8,0x8d,0xa3,0x00,0x05,0xff,0xe8,0x8e,0xad,0x00,0xd1,0x10, + 0x10,0x08,0x05,0xff,0xe8,0x8c,0xa3,0x00,0x05,0xff,0xe8,0x8e,0xbd,0x00,0x10,0x08, + 0x05,0xff,0xe8,0x8f,0xa7,0x00,0x05,0xff,0xe8,0x91,0x97,0x00,0xd4,0x85,0xd3,0x43, + 0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe8,0x8d,0x93,0x00,0x05,0xff,0xe8,0x8f, + 0x8a,0x00,0x10,0x08,0x05,0xff,0xe8,0x8f,0x8c,0x00,0x05,0xff,0xe8,0x8f,0x9c,0x00, + 0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa6,0xb0,0xb6,0x00,0x05,0xff,0xf0,0xa6,0xb5, + 0xab,0x00,0x10,0x09,0x05,0xff,0xf0,0xa6,0xb3,0x95,0x00,0x05,0xff,0xe4,0x94,0xab, + 0x00,0xd2,0x21,0xd1,0x10,0x10,0x08,0x05,0xff,0xe8,0x93,0xb1,0x00,0x05,0xff,0xe8, + 0x93,0xb3,0x00,0x10,0x08,0x05,0xff,0xe8,0x94,0x96,0x00,0x05,0xff,0xf0,0xa7,0x8f, + 0x8a,0x00,0xd1,0x11,0x10,0x08,0x05,0xff,0xe8,0x95,0xa4,0x00,0x05,0xff,0xf0,0xa6, + 0xbc,0xac,0x00,0x10,0x08,0x05,0xff,0xe4,0x95,0x9d,0x00,0x05,0xff,0xe4,0x95,0xa1, + 0x00,0xd3,0x42,0xd2,0x22,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa6,0xbe,0xb1,0x00, + 0x05,0xff,0xf0,0xa7,0x83,0x92,0x00,0x10,0x08,0x05,0xff,0xe4,0x95,0xab,0x00,0x05, + 0xff,0xe8,0x99,0x90,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe8,0x99,0x9c,0x00,0x05, + 0xff,0xe8,0x99,0xa7,0x00,0x10,0x08,0x05,0xff,0xe8,0x99,0xa9,0x00,0x05,0xff,0xe8, + 0x9a,0xa9,0x00,0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe8,0x9a,0x88,0x00,0x05, + 0xff,0xe8,0x9c,0x8e,0x00,0x10,0x08,0x05,0xff,0xe8,0x9b,0xa2,0x00,0x05,0xff,0xe8, + 0x9d,0xb9,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe8,0x9c,0xa8,0x00,0x05,0xff,0xe8, + 0x9d,0xab,0x00,0x10,0x08,0x05,0xff,0xe8,0x9e,0x86,0x00,0x05,0xff,0xe4,0x97,0x97, + 0x00,0xcf,0x86,0xe5,0x08,0x01,0xd4,0x83,0xd3,0x41,0xd2,0x20,0xd1,0x10,0x10,0x08, + 0x05,0xff,0xe8,0x9f,0xa1,0x00,0x05,0xff,0xe8,0xa0,0x81,0x00,0x10,0x08,0x05,0xff, + 0xe4,0x97,0xb9,0x00,0x05,0xff,0xe8,0xa1,0xa0,0x00,0xd1,0x11,0x10,0x08,0x05,0xff, + 0xe8,0xa1,0xa3,0x00,0x05,0xff,0xf0,0xa7,0x99,0xa7,0x00,0x10,0x08,0x05,0xff,0xe8, + 0xa3,0x97,0x00,0x05,0xff,0xe8,0xa3,0x9e,0x00,0xd2,0x21,0xd1,0x10,0x10,0x08,0x05, + 0xff,0xe4,0x98,0xb5,0x00,0x05,0xff,0xe8,0xa3,0xba,0x00,0x10,0x08,0x05,0xff,0xe3, + 0x92,0xbb,0x00,0x05,0xff,0xf0,0xa7,0xa2,0xae,0x00,0xd1,0x11,0x10,0x09,0x05,0xff, + 0xf0,0xa7,0xa5,0xa6,0x00,0x05,0xff,0xe4,0x9a,0xbe,0x00,0x10,0x08,0x05,0xff,0xe4, + 0x9b,0x87,0x00,0x05,0xff,0xe8,0xaa,0xa0,0x00,0xd3,0x41,0xd2,0x21,0xd1,0x10,0x10, + 0x08,0x05,0xff,0xe8,0xab,0xad,0x00,0x05,0xff,0xe8,0xae,0x8a,0x00,0x10,0x08,0x05, + 0xff,0xe8,0xb1,0x95,0x00,0x05,0xff,0xf0,0xa7,0xb2,0xa8,0x00,0xd1,0x10,0x10,0x08, + 0x05,0xff,0xe8,0xb2,0xab,0x00,0x05,0xff,0xe8,0xb3,0x81,0x00,0x10,0x08,0x05,0xff, + 0xe8,0xb4,0x9b,0x00,0x05,0xff,0xe8,0xb5,0xb7,0x00,0xd2,0x22,0xd1,0x12,0x10,0x09, + 0x05,0xff,0xf0,0xa7,0xbc,0xaf,0x00,0x05,0xff,0xf0,0xa0,0xa0,0x84,0x00,0x10,0x08, + 0x05,0xff,0xe8,0xb7,0x8b,0x00,0x05,0xff,0xe8,0xb6,0xbc,0x00,0xd1,0x11,0x10,0x08, + 0x05,0xff,0xe8,0xb7,0xb0,0x00,0x05,0xff,0xf0,0xa0,0xa3,0x9e,0x00,0x10,0x08,0x05, + 0xff,0xe8,0xbb,0x94,0x00,0x05,0xff,0xe8,0xbc,0xb8,0x00,0xd4,0x84,0xd3,0x43,0xd2, + 0x22,0xd1,0x12,0x10,0x09,0x05,0xff,0xf0,0xa8,0x97,0x92,0x00,0x05,0xff,0xf0,0xa8, + 0x97,0xad,0x00,0x10,0x08,0x05,0xff,0xe9,0x82,0x94,0x00,0x05,0xff,0xe9,0x83,0xb1, + 0x00,0xd1,0x11,0x10,0x08,0x05,0xff,0xe9,0x84,0x91,0x00,0x05,0xff,0xf0,0xa8,0x9c, + 0xae,0x00,0x10,0x08,0x05,0xff,0xe9,0x84,0x9b,0x00,0x05,0xff,0xe9,0x88,0xb8,0x00, + 0xd2,0x20,0xd1,0x10,0x10,0x08,0x05,0xff,0xe9,0x8b,0x97,0x00,0x05,0xff,0xe9,0x8b, + 0x98,0x00,0x10,0x08,0x05,0xff,0xe9,0x89,0xbc,0x00,0x05,0xff,0xe9,0x8f,0xb9,0x00, + 0xd1,0x11,0x10,0x08,0x05,0xff,0xe9,0x90,0x95,0x00,0x05,0xff,0xf0,0xa8,0xaf,0xba, + 0x00,0x10,0x08,0x05,0xff,0xe9,0x96,0x8b,0x00,0x05,0xff,0xe4,0xa6,0x95,0x00,0xd3, + 0x43,0xd2,0x21,0xd1,0x11,0x10,0x08,0x05,0xff,0xe9,0x96,0xb7,0x00,0x05,0xff,0xf0, + 0xa8,0xb5,0xb7,0x00,0x10,0x08,0x05,0xff,0xe4,0xa7,0xa6,0x00,0x05,0xff,0xe9,0x9b, + 0x83,0x00,0xd1,0x10,0x10,0x08,0x05,0xff,0xe5,0xb6,0xb2,0x00,0x05,0xff,0xe9,0x9c, + 0xa3,0x00,0x10,0x09,0x05,0xff,0xf0,0xa9,0x85,0x85,0x00,0x05,0xff,0xf0,0xa9,0x88, + 0x9a,0x00,0xd2,0x21,0xd1,0x10,0x10,0x08,0x05,0xff,0xe4,0xa9,0xae,0x00,0x05,0xff, + 0xe4,0xa9,0xb6,0x00,0x10,0x08,0x05,0xff,0xe9,0x9f,0xa0,0x00,0x05,0xff,0xf0,0xa9, + 0x90,0x8a,0x00,0x91,0x11,0x10,0x08,0x05,0xff,0xe4,0xaa,0xb2,0x00,0x05,0xff,0xf0, + 0xa9,0x92,0x96,0x00,0x05,0xff,0xe9,0xa0,0x8b,0x00,0xe2,0x10,0x01,0xe1,0x09,0x01, + 0xe0,0x02,0x01,0xcf,0x86,0x95,0xfb,0xd4,0x82,0xd3,0x41,0xd2,0x21,0xd1,0x11,0x10, + 0x08,0x05,0xff,0xe9,0xa0,0xa9,0x00,0x05,0xff,0xf0,0xa9,0x96,0xb6,0x00,0x10,0x08, + 0x05,0xff,0xe9,0xa3,0xa2,0x00,0x05,0xff,0xe4,0xac,0xb3,0x00,0xd1,0x10,0x10,0x08, + 0x05,0xff,0xe9,0xa4,0xa9,0x00,0x05,0xff,0xe9,0xa6,0xa7,0x00,0x10,0x08,0x05,0xff, + 0xe9,0xa7,0x82,0x00,0x05,0xff,0xe9,0xa7,0xbe,0x00,0xd2,0x21,0xd1,0x11,0x10,0x08, + 0x05,0xff,0xe4,0xaf,0x8e,0x00,0x05,0xff,0xf0,0xa9,0xac,0xb0,0x00,0x10,0x08,0x05, + 0xff,0xe9,0xac,0x92,0x00,0x05,0xff,0xe9,0xb1,0x80,0x00,0xd1,0x10,0x10,0x08,0x05, + 0xff,0xe9,0xb3,0xbd,0x00,0x05,0xff,0xe4,0xb3,0x8e,0x00,0x10,0x08,0x05,0xff,0xe4, + 0xb3,0xad,0x00,0x05,0xff,0xe9,0xb5,0xa7,0x00,0xd3,0x44,0xd2,0x23,0xd1,0x11,0x10, + 0x09,0x05,0xff,0xf0,0xaa,0x83,0x8e,0x00,0x05,0xff,0xe4,0xb3,0xb8,0x00,0x10,0x09, + 0x05,0xff,0xf0,0xaa,0x84,0x85,0x00,0x05,0xff,0xf0,0xaa,0x88,0x8e,0x00,0xd1,0x11, + 0x10,0x09,0x05,0xff,0xf0,0xaa,0x8a,0x91,0x00,0x05,0xff,0xe9,0xba,0xbb,0x00,0x10, + 0x08,0x05,0xff,0xe4,0xb5,0x96,0x00,0x05,0xff,0xe9,0xbb,0xb9,0x00,0xd2,0x20,0xd1, + 0x10,0x10,0x08,0x05,0xff,0xe9,0xbb,0xbe,0x00,0x05,0xff,0xe9,0xbc,0x85,0x00,0x10, + 0x08,0x05,0xff,0xe9,0xbc,0x8f,0x00,0x05,0xff,0xe9,0xbc,0x96,0x00,0x91,0x11,0x10, + 0x08,0x05,0xff,0xe9,0xbc,0xbb,0x00,0x05,0xff,0xf0,0xaa,0x98,0x80,0x00,0x00,0x00, + 0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xcf,0x06,0x00,0x00,0xd3,0x06, + 0xcf,0x06,0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1,0x06,0xcf,0x06,0x00,0x00, + 0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x00,0x00, + 0x53,0x04,0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x02,0x00,0xd3,0x08, + 0xcf,0x86,0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd1,0x08, + 0xcf,0x86,0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xcf,0x86, + 0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf,0x06,0x00,0x00,0xd3,0x06,0xcf,0x06, + 0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1,0x06,0xcf,0x06,0x00,0x00,0xd0,0x06, + 0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x00,0x00,0x53,0x04, + 0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x02,0x00,0xcf,0x86,0xd5,0xc0, + 0xd4,0x60,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf,0x86,0xcf,0x06, + 0x00,0x00,0xd1,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf,0x86,0xcf,0x06, + 0x00,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf,0x06,0x00,0x00, + 0xd3,0x06,0xcf,0x06,0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1,0x06,0xcf,0x06, + 0x00,0x00,0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04, + 0x00,0x00,0x53,0x04,0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x02,0x00, + 0xd3,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00, + 0xd1,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00, + 0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf,0x06,0x00,0x00,0xd3,0x06, + 0xcf,0x06,0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1,0x06,0xcf,0x06,0x00,0x00, + 0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x00,0x00, + 0x53,0x04,0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x02,0x00,0xd4,0x60, + 0xd3,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00, + 0xd1,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00, + 0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf,0x06,0x00,0x00,0xd3,0x06, + 0xcf,0x06,0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1,0x06,0xcf,0x06,0x00,0x00, + 0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x00,0x00, + 0x53,0x04,0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x02,0x00,0xd3,0x08, + 0xcf,0x86,0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd1,0x08, + 0xcf,0x86,0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xcf,0x86, + 0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf,0x06,0x00,0x00,0xd3,0x06,0xcf,0x06, + 0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1,0x06,0xcf,0x06,0x00,0x00,0xd0,0x06, + 0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x00,0x00,0x53,0x04, + 0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x02,0x00,0xe0,0x83,0x01,0xcf, + 0x86,0xd5,0xc0,0xd4,0x60,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf, + 0x86,0xcf,0x06,0x00,0x00,0xd1,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf, + 0x86,0xcf,0x06,0x00,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf, + 0x06,0x00,0x00,0xd3,0x06,0xcf,0x06,0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1, + 0x06,0xcf,0x06,0x00,0x00,0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00, + 0x00,0x54,0x04,0x00,0x00,0x53,0x04,0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00, + 0x00,0x02,0x00,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf,0x86,0xcf, + 0x06,0x00,0x00,0xd1,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf,0x86,0xcf, + 0x06,0x00,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf,0x06,0x00, + 0x00,0xd3,0x06,0xcf,0x06,0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1,0x06,0xcf, + 0x06,0x00,0x00,0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54, + 0x04,0x00,0x00,0x53,0x04,0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x02, + 0x00,0xd4,0x60,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf,0x86,0xcf, + 0x06,0x00,0x00,0xd1,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf,0x86,0xcf, + 0x06,0x00,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf,0x06,0x00, + 0x00,0xd3,0x06,0xcf,0x06,0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1,0x06,0xcf, + 0x06,0x00,0x00,0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54, + 0x04,0x00,0x00,0x53,0x04,0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x02, + 0x00,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf,0x86,0xcf,0x06,0x00, + 0x00,0xd1,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf,0x86,0xcf,0x06,0x00, + 0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf,0x06,0x00,0x00,0xd3, + 0x06,0xcf,0x06,0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1,0x06,0xcf,0x06,0x00, + 0x00,0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x00, + 0x00,0x53,0x04,0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x02,0x00,0xcf, + 0x86,0xd5,0xc0,0xd4,0x60,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf, + 0x86,0xcf,0x06,0x00,0x00,0xd1,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf, + 0x86,0xcf,0x06,0x00,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf, + 0x06,0x00,0x00,0xd3,0x06,0xcf,0x06,0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1, + 0x06,0xcf,0x06,0x00,0x00,0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00, + 0x00,0x54,0x04,0x00,0x00,0x53,0x04,0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00, + 0x00,0x02,0x00,0xd3,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf,0x86,0xcf, + 0x06,0x00,0x00,0xd1,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf,0x86,0xcf, + 0x06,0x00,0x00,0xcf,0x86,0xd5,0x06,0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf,0x06,0x00, + 0x00,0xd3,0x06,0xcf,0x06,0x00,0x00,0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1,0x06,0xcf, + 0x06,0x00,0x00,0xd0,0x06,0xcf,0x06,0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54, + 0x04,0x00,0x00,0x53,0x04,0x00,0x00,0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x02, + 0x00,0xd4,0xd9,0xd3,0x81,0xd2,0x79,0xd1,0x71,0xd0,0x69,0xcf,0x86,0xd5,0x60,0xd4, + 0x59,0xd3,0x52,0xd2,0x33,0xd1,0x2c,0xd0,0x25,0xcf,0x86,0x95,0x1e,0x94,0x19,0x93, + 0x14,0x92,0x0f,0x91,0x0a,0x10,0x05,0x00,0xff,0x00,0x05,0xff,0x00,0x00,0xff,0x00, + 0x00,0xff,0x00,0x00,0xff,0x00,0x00,0xff,0x00,0x05,0xff,0x00,0xcf,0x06,0x05,0xff, + 0x00,0xcf,0x06,0x00,0xff,0x00,0xd1,0x07,0xcf,0x06,0x07,0xff,0x00,0xd0,0x07,0xcf, + 0x06,0x07,0xff,0x00,0xcf,0x86,0x55,0x05,0x07,0xff,0x00,0x14,0x05,0x07,0xff,0x00, + 0x00,0xff,0x00,0xcf,0x06,0x00,0xff,0x00,0xcf,0x06,0x00,0xff,0x00,0xcf,0x06,0x00, + 0xff,0x00,0xcf,0x86,0xcf,0x06,0x00,0x00,0xcf,0x86,0xcf,0x06,0x00,0x00,0xcf,0x86, + 0xcf,0x06,0x00,0x00,0xd2,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xd1,0x08,0xcf,0x86, + 0xcf,0x06,0x00,0x00,0xd0,0x08,0xcf,0x86,0xcf,0x06,0x00,0x00,0xcf,0x86,0xd5,0x06, + 0xcf,0x06,0x00,0x00,0xd4,0x06,0xcf,0x06,0x00,0x00,0xd3,0x06,0xcf,0x06,0x00,0x00, + 0xd2,0x06,0xcf,0x06,0x00,0x00,0xd1,0x06,0xcf,0x06,0x00,0x00,0xd0,0x06,0xcf,0x06, + 0x00,0x00,0xcf,0x86,0x55,0x04,0x00,0x00,0x54,0x04,0x00,0x00,0x53,0x04,0x00,0x00, + 0x52,0x04,0x00,0x00,0x11,0x04,0x00,0x00,0x02,0x00,0xcf,0x86,0xcf,0x06,0x02,0x00, + 0x81,0x80,0xcf,0x86,0x85,0x84,0xcf,0x86,0xcf,0x06,0x02,0x00,0x00,0x00,0x00,0x00 +}; diff --git a/scripts/Makefile b/scripts/Makefile index b87e3e0ade4d..9d442ee050bd 100644 --- a/scripts/Makefile +++ b/scripts/Makefile @@ -20,7 +20,6 @@ hostprogs-$(CONFIG_ASN1) += asn1_compiler hostprogs-$(CONFIG_MODULE_SIG) += sign-file hostprogs-$(CONFIG_SYSTEM_TRUSTED_KEYRING) += extract-cert hostprogs-$(CONFIG_SYSTEM_EXTRA_CERTIFICATE) += insert-sys-cert -hostprogs-$(CONFIG_UNICODE) += mkutf8data HOSTCFLAGS_sortextable.o = -I$(srctree)/tools/include HOSTCFLAGS_asn1_compiler.o = -I$(srctree)/include diff --git a/scripts/mkutf8data.c b/scripts/mkutf8data.c deleted file mode 100644 index ff2025ac5a32..000000000000 --- a/scripts/mkutf8data.c +++ /dev/null @@ -1,3419 +0,0 @@ -/* - * Copyright (c) 2014 SGI. - * All rights reserved. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public License as - * published by the Free Software Foundation. - * - * This program is distributed in the hope that it would be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write the Free Software Foundation, - * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - */ - -/* Generator for a compact trie for unicode normalization */ - -#include -#include -#include -#include -#include -#include -#include -#include - -/* Default names of the in- and output files. */ - -#define AGE_NAME "DerivedAge.txt" -#define CCC_NAME "DerivedCombiningClass.txt" -#define PROP_NAME "DerivedCoreProperties.txt" -#define DATA_NAME "UnicodeData.txt" -#define FOLD_NAME "CaseFolding.txt" -#define NORM_NAME "NormalizationCorrections.txt" -#define TEST_NAME "NormalizationTest.txt" -#define UTF8_NAME "utf8data.h" - -const char *age_name = AGE_NAME; -const char *ccc_name = CCC_NAME; -const char *prop_name = PROP_NAME; -const char *data_name = DATA_NAME; -const char *fold_name = FOLD_NAME; -const char *norm_name = NORM_NAME; -const char *test_name = TEST_NAME; -const char *utf8_name = UTF8_NAME; - -int verbose = 0; - -/* An arbitrary line size limit on input lines. */ - -#define LINESIZE 1024 -char line[LINESIZE]; -char buf0[LINESIZE]; -char buf1[LINESIZE]; -char buf2[LINESIZE]; -char buf3[LINESIZE]; - -const char *argv0; - -#define ARRAY_SIZE(x) (sizeof(x) / sizeof((x)[0])) - -/* ------------------------------------------------------------------ */ - -/* - * Unicode version numbers consist of three parts: major, minor, and a - * revision. These numbers are packed into an unsigned int to obtain - * a single version number. - * - * To save space in the generated trie, the unicode version is not - * stored directly, instead we calculate a generation number from the - * unicode versions seen in the DerivedAge file, and use that as an - * index into a table of unicode versions. - */ -#define UNICODE_MAJ_SHIFT (16) -#define UNICODE_MIN_SHIFT (8) - -#define UNICODE_MAJ_MAX ((unsigned short)-1) -#define UNICODE_MIN_MAX ((unsigned char)-1) -#define UNICODE_REV_MAX ((unsigned char)-1) - -#define UNICODE_AGE(MAJ,MIN,REV) \ - (((unsigned int)(MAJ) << UNICODE_MAJ_SHIFT) | \ - ((unsigned int)(MIN) << UNICODE_MIN_SHIFT) | \ - ((unsigned int)(REV))) - -unsigned int *ages; -int ages_count; - -unsigned int unicode_maxage; - -static int age_valid(unsigned int major, unsigned int minor, - unsigned int revision) -{ - if (major > UNICODE_MAJ_MAX) - return 0; - if (minor > UNICODE_MIN_MAX) - return 0; - if (revision > UNICODE_REV_MAX) - return 0; - return 1; -} - -/* ------------------------------------------------------------------ */ - -/* - * utf8trie_t - * - * A compact binary tree, used to decode UTF-8 characters. - * - * Internal nodes are one byte for the node itself, and up to three - * bytes for an offset into the tree. The first byte contains the - * following information: - * NEXTBYTE - flag - advance to next byte if set - * BITNUM - 3 bit field - the bit number to tested - * OFFLEN - 2 bit field - number of bytes in the offset - * if offlen == 0 (non-branching node) - * RIGHTPATH - 1 bit field - set if the following node is for the - * right-hand path (tested bit is set) - * TRIENODE - 1 bit field - set if the following node is an internal - * node, otherwise it is a leaf node - * if offlen != 0 (branching node) - * LEFTNODE - 1 bit field - set if the left-hand node is internal - * RIGHTNODE - 1 bit field - set if the right-hand node is internal - * - * Due to the way utf8 works, there cannot be branching nodes with - * NEXTBYTE set, and moreover those nodes always have a righthand - * descendant. - */ -typedef unsigned char utf8trie_t; -#define BITNUM 0x07 -#define NEXTBYTE 0x08 -#define OFFLEN 0x30 -#define OFFLEN_SHIFT 4 -#define RIGHTPATH 0x40 -#define TRIENODE 0x80 -#define RIGHTNODE 0x40 -#define LEFTNODE 0x80 - -/* - * utf8leaf_t - * - * The leaves of the trie are embedded in the trie, and so the same - * underlying datatype, unsigned char. - * - * leaf[0]: The unicode version, stored as a generation number that is - * an index into utf8agetab[]. With this we can filter code - * points based on the unicode version in which they were - * defined. The CCC of a non-defined code point is 0. - * leaf[1]: Canonical Combining Class. During normalization, we need - * to do a stable sort into ascending order of all characters - * with a non-zero CCC that occur between two characters with - * a CCC of 0, or at the begin or end of a string. - * The unicode standard guarantees that all CCC values are - * between 0 and 254 inclusive, which leaves 255 available as - * a special value. - * Code points with CCC 0 are known as stoppers. - * leaf[2]: Decomposition. If leaf[1] == 255, then leaf[2] is the - * start of a NUL-terminated string that is the decomposition - * of the character. - * The CCC of a decomposable character is the same as the CCC - * of the first character of its decomposition. - * Some characters decompose as the empty string: these are - * characters with the Default_Ignorable_Code_Point property. - * These do affect normalization, as they all have CCC 0. - * - * The decompositions in the trie have been fully expanded. - * - * Casefolding, if applicable, is also done using decompositions. - */ -typedef unsigned char utf8leaf_t; - -#define LEAF_GEN(LEAF) ((LEAF)[0]) -#define LEAF_CCC(LEAF) ((LEAF)[1]) -#define LEAF_STR(LEAF) ((const char*)((LEAF) + 2)) - -#define MAXGEN (255) - -#define MINCCC (0) -#define MAXCCC (254) -#define STOPPER (0) -#define DECOMPOSE (255) -#define HANGUL ((char)(255)) - -#define UTF8HANGULLEAF (12) - -struct tree; -static utf8leaf_t *utf8nlookup(struct tree *, unsigned char *, - const char *, size_t); -static utf8leaf_t *utf8lookup(struct tree *, unsigned char *, const char *); - -unsigned char *utf8data; -size_t utf8data_size; - -utf8trie_t *nfdi; -utf8trie_t *nfdicf; - -/* ------------------------------------------------------------------ */ - -/* - * UTF8 valid ranges. - * - * The UTF-8 encoding spreads the bits of a 32bit word over several - * bytes. This table gives the ranges that can be held and how they'd - * be represented. - * - * 0x00000000 0x0000007F: 0xxxxxxx - * 0x00000000 0x000007FF: 110xxxxx 10xxxxxx - * 0x00000000 0x0000FFFF: 1110xxxx 10xxxxxx 10xxxxxx - * 0x00000000 0x001FFFFF: 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx - * 0x00000000 0x03FFFFFF: 111110xx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx - * 0x00000000 0x7FFFFFFF: 1111110x 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx - * - * There is an additional requirement on UTF-8, in that only the - * shortest representation of a 32bit value is to be used. A decoder - * must not decode sequences that do not satisfy this requirement. - * Thus the allowed ranges have a lower bound. - * - * 0x00000000 0x0000007F: 0xxxxxxx - * 0x00000080 0x000007FF: 110xxxxx 10xxxxxx - * 0x00000800 0x0000FFFF: 1110xxxx 10xxxxxx 10xxxxxx - * 0x00010000 0x001FFFFF: 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx - * 0x00200000 0x03FFFFFF: 111110xx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx - * 0x04000000 0x7FFFFFFF: 1111110x 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx - * - * Actual unicode characters are limited to the range 0x0 - 0x10FFFF, - * 17 planes of 65536 values. This limits the sequences actually seen - * even more, to just the following. - * - * 0 - 0x7f: 0 0x7f - * 0x80 - 0x7ff: 0xc2 0x80 0xdf 0xbf - * 0x800 - 0xffff: 0xe0 0xa0 0x80 0xef 0xbf 0xbf - * 0x10000 - 0x10ffff: 0xf0 0x90 0x80 0x80 0xf4 0x8f 0xbf 0xbf - * - * Even within those ranges not all values are allowed: the surrogates - * 0xd800 - 0xdfff should never be seen. - * - * Note that the longest sequence seen with valid usage is 4 bytes, - * the same a single UTF-32 character. This makes the UTF-8 - * representation of Unicode strictly smaller than UTF-32. - * - * The shortest sequence requirement was introduced by: - * Corrigendum #1: UTF-8 Shortest Form - * It can be found here: - * http://www.unicode.org/versions/corrigendum1.html - * - */ - -#define UTF8_2_BITS 0xC0 -#define UTF8_3_BITS 0xE0 -#define UTF8_4_BITS 0xF0 -#define UTF8_N_BITS 0x80 -#define UTF8_2_MASK 0xE0 -#define UTF8_3_MASK 0xF0 -#define UTF8_4_MASK 0xF8 -#define UTF8_N_MASK 0xC0 -#define UTF8_V_MASK 0x3F -#define UTF8_V_SHIFT 6 - -static int utf8encode(char *str, unsigned int val) -{ - int len; - - if (val < 0x80) { - str[0] = val; - len = 1; - } else if (val < 0x800) { - str[1] = val & UTF8_V_MASK; - str[1] |= UTF8_N_BITS; - val >>= UTF8_V_SHIFT; - str[0] = val; - str[0] |= UTF8_2_BITS; - len = 2; - } else if (val < 0x10000) { - str[2] = val & UTF8_V_MASK; - str[2] |= UTF8_N_BITS; - val >>= UTF8_V_SHIFT; - str[1] = val & UTF8_V_MASK; - str[1] |= UTF8_N_BITS; - val >>= UTF8_V_SHIFT; - str[0] = val; - str[0] |= UTF8_3_BITS; - len = 3; - } else if (val < 0x110000) { - str[3] = val & UTF8_V_MASK; - str[3] |= UTF8_N_BITS; - val >>= UTF8_V_SHIFT; - str[2] = val & UTF8_V_MASK; - str[2] |= UTF8_N_BITS; - val >>= UTF8_V_SHIFT; - str[1] = val & UTF8_V_MASK; - str[1] |= UTF8_N_BITS; - val >>= UTF8_V_SHIFT; - str[0] = val; - str[0] |= UTF8_4_BITS; - len = 4; - } else { - printf("%#x: illegal val\n", val); - len = 0; - } - return len; -} - -static unsigned int utf8decode(const char *str) -{ - const unsigned char *s = (const unsigned char*)str; - unsigned int unichar = 0; - - if (*s < 0x80) { - unichar = *s; - } else if (*s < UTF8_3_BITS) { - unichar = *s++ & 0x1F; - unichar <<= UTF8_V_SHIFT; - unichar |= *s & 0x3F; - } else if (*s < UTF8_4_BITS) { - unichar = *s++ & 0x0F; - unichar <<= UTF8_V_SHIFT; - unichar |= *s++ & 0x3F; - unichar <<= UTF8_V_SHIFT; - unichar |= *s & 0x3F; - } else { - unichar = *s++ & 0x0F; - unichar <<= UTF8_V_SHIFT; - unichar |= *s++ & 0x3F; - unichar <<= UTF8_V_SHIFT; - unichar |= *s++ & 0x3F; - unichar <<= UTF8_V_SHIFT; - unichar |= *s & 0x3F; - } - return unichar; -} - -static int utf32valid(unsigned int unichar) -{ - return unichar < 0x110000; -} - -#define HANGUL_SYLLABLE(U) ((U) >= 0xAC00 && (U) <= 0xD7A3) - -#define NODE 1 -#define LEAF 0 - -struct tree { - void *root; - int childnode; - const char *type; - unsigned int maxage; - struct tree *next; - int (*leaf_equal)(void *, void *); - void (*leaf_print)(void *, int); - int (*leaf_mark)(void *); - int (*leaf_size)(void *); - int *(*leaf_index)(struct tree *, void *); - unsigned char *(*leaf_emit)(void *, unsigned char *); - int leafindex[0x110000]; - int index; -}; - -struct node { - int index; - int offset; - int mark; - int size; - struct node *parent; - void *left; - void *right; - unsigned char bitnum; - unsigned char nextbyte; - unsigned char leftnode; - unsigned char rightnode; - unsigned int keybits; - unsigned int keymask; -}; - -/* - * Example lookup function for a tree. - */ -static void *lookup(struct tree *tree, const char *key) -{ - struct node *node; - void *leaf = NULL; - - node = tree->root; - while (!leaf && node) { - if (node->nextbyte) - key++; - if (*key & (1 << (node->bitnum & 7))) { - /* Right leg */ - if (node->rightnode == NODE) { - node = node->right; - } else if (node->rightnode == LEAF) { - leaf = node->right; - } else { - node = NULL; - } - } else { - /* Left leg */ - if (node->leftnode == NODE) { - node = node->left; - } else if (node->leftnode == LEAF) { - leaf = node->left; - } else { - node = NULL; - } - } - } - - return leaf; -} - -/* - * A simple non-recursive tree walker: keep track of visits to the - * left and right branches in the leftmask and rightmask. - */ -static void tree_walk(struct tree *tree) -{ - struct node *node; - unsigned int leftmask; - unsigned int rightmask; - unsigned int bitmask; - int indent = 1; - int nodes, singletons, leaves; - - nodes = singletons = leaves = 0; - - printf("%s_%x root %p\n", tree->type, tree->maxage, tree->root); - if (tree->childnode == LEAF) { - assert(tree->root); - tree->leaf_print(tree->root, indent); - leaves = 1; - } else { - assert(tree->childnode == NODE); - node = tree->root; - leftmask = rightmask = 0; - while (node) { - printf("%*snode @ %p bitnum %d nextbyte %d" - " left %p right %p mask %x bits %x\n", - indent, "", node, - node->bitnum, node->nextbyte, - node->left, node->right, - node->keymask, node->keybits); - nodes += 1; - if (!(node->left && node->right)) - singletons += 1; - - while (node) { - bitmask = 1 << node->bitnum; - if ((leftmask & bitmask) == 0) { - leftmask |= bitmask; - if (node->leftnode == LEAF) { - assert(node->left); - tree->leaf_print(node->left, - indent+1); - leaves += 1; - } else if (node->left) { - assert(node->leftnode == NODE); - indent += 1; - node = node->left; - break; - } - } - if ((rightmask & bitmask) == 0) { - rightmask |= bitmask; - if (node->rightnode == LEAF) { - assert(node->right); - tree->leaf_print(node->right, - indent+1); - leaves += 1; - } else if (node->right) { - assert(node->rightnode == NODE); - indent += 1; - node = node->right; - break; - } - } - leftmask &= ~bitmask; - rightmask &= ~bitmask; - node = node->parent; - indent -= 1; - } - } - } - printf("nodes %d leaves %d singletons %d\n", - nodes, leaves, singletons); -} - -/* - * Allocate an initialize a new internal node. - */ -static struct node *alloc_node(struct node *parent) -{ - struct node *node; - int bitnum; - - node = malloc(sizeof(*node)); - node->left = node->right = NULL; - node->parent = parent; - node->leftnode = NODE; - node->rightnode = NODE; - node->keybits = 0; - node->keymask = 0; - node->mark = 0; - node->index = 0; - node->offset = -1; - node->size = 4; - - if (node->parent) { - bitnum = parent->bitnum; - if ((bitnum & 7) == 0) { - node->bitnum = bitnum + 7 + 8; - node->nextbyte = 1; - } else { - node->bitnum = bitnum - 1; - node->nextbyte = 0; - } - } else { - node->bitnum = 7; - node->nextbyte = 0; - } - - return node; -} - -/* - * Insert a new leaf into the tree, and collapse any subtrees that are - * fully populated and end in identical leaves. A nextbyte tagged - * internal node will not be removed to preserve the tree's integrity. - * Note that due to the structure of utf8, no nextbyte tagged node - * will be a candidate for removal. - */ -static int insert(struct tree *tree, char *key, int keylen, void *leaf) -{ - struct node *node; - struct node *parent; - void **cursor; - int keybits; - - assert(keylen >= 1 && keylen <= 4); - - node = NULL; - cursor = &tree->root; - keybits = 8 * keylen; - - /* Insert, creating path along the way. */ - while (keybits) { - if (!*cursor) - *cursor = alloc_node(node); - node = *cursor; - if (node->nextbyte) - key++; - if (*key & (1 << (node->bitnum & 7))) - cursor = &node->right; - else - cursor = &node->left; - keybits--; - } - *cursor = leaf; - - /* Merge subtrees if possible. */ - while (node) { - if (*key & (1 << (node->bitnum & 7))) - node->rightnode = LEAF; - else - node->leftnode = LEAF; - if (node->nextbyte) - break; - if (node->leftnode == NODE || node->rightnode == NODE) - break; - assert(node->left); - assert(node->right); - /* Compare */ - if (! tree->leaf_equal(node->left, node->right)) - break; - /* Keep left, drop right leaf. */ - leaf = node->left; - /* Check in parent */ - parent = node->parent; - if (!parent) { - /* root of tree! */ - tree->root = leaf; - tree->childnode = LEAF; - } else if (parent->left == node) { - parent->left = leaf; - parent->leftnode = LEAF; - if (parent->right) { - parent->keymask = 0; - parent->keybits = 0; - } else { - parent->keymask |= (1 << node->bitnum); - } - } else if (parent->right == node) { - parent->right = leaf; - parent->rightnode = LEAF; - if (parent->left) { - parent->keymask = 0; - parent->keybits = 0; - } else { - parent->keymask |= (1 << node->bitnum); - parent->keybits |= (1 << node->bitnum); - } - } else { - /* internal tree error */ - assert(0); - } - free(node); - node = parent; - } - - /* Propagate keymasks up along singleton chains. */ - while (node) { - parent = node->parent; - if (!parent) - break; - /* Nix the mask for parents with two children. */ - if (node->keymask == 0) { - parent->keymask = 0; - parent->keybits = 0; - } else if (parent->left && parent->right) { - parent->keymask = 0; - parent->keybits = 0; - } else { - assert((parent->keymask & node->keymask) == 0); - parent->keymask |= node->keymask; - parent->keymask |= (1 << parent->bitnum); - parent->keybits |= node->keybits; - if (parent->right) - parent->keybits |= (1 << parent->bitnum); - } - node = parent; - } - - return 0; -} - -/* - * Prune internal nodes. - * - * Fully populated subtrees that end at the same leaf have already - * been collapsed. There are still internal nodes that have for both - * their left and right branches a sequence of singletons that make - * identical choices and end in identical leaves. The keymask and - * keybits collected in the nodes describe the choices made in these - * singleton chains. When they are identical for the left and right - * branch of a node, and the two leaves comare identical, the node in - * question can be removed. - * - * Note that nodes with the nextbyte tag set will not be removed by - * this to ensure tree integrity. Note as well that the structure of - * utf8 ensures that these nodes would not have been candidates for - * removal in any case. - */ -static void prune(struct tree *tree) -{ - struct node *node; - struct node *left; - struct node *right; - struct node *parent; - void *leftleaf; - void *rightleaf; - unsigned int leftmask; - unsigned int rightmask; - unsigned int bitmask; - int count; - - if (verbose > 0) - printf("Pruning %s_%x\n", tree->type, tree->maxage); - - count = 0; - if (tree->childnode == LEAF) - return; - if (!tree->root) - return; - - leftmask = rightmask = 0; - node = tree->root; - while (node) { - if (node->nextbyte) - goto advance; - if (node->leftnode == LEAF) - goto advance; - if (node->rightnode == LEAF) - goto advance; - if (!node->left) - goto advance; - if (!node->right) - goto advance; - left = node->left; - right = node->right; - if (left->keymask == 0) - goto advance; - if (right->keymask == 0) - goto advance; - if (left->keymask != right->keymask) - goto advance; - if (left->keybits != right->keybits) - goto advance; - leftleaf = NULL; - while (!leftleaf) { - assert(left->left || left->right); - if (left->leftnode == LEAF) - leftleaf = left->left; - else if (left->rightnode == LEAF) - leftleaf = left->right; - else if (left->left) - left = left->left; - else if (left->right) - left = left->right; - else - assert(0); - } - rightleaf = NULL; - while (!rightleaf) { - assert(right->left || right->right); - if (right->leftnode == LEAF) - rightleaf = right->left; - else if (right->rightnode == LEAF) - rightleaf = right->right; - else if (right->left) - right = right->left; - else if (right->right) - right = right->right; - else - assert(0); - } - if (! tree->leaf_equal(leftleaf, rightleaf)) - goto advance; - /* - * This node has identical singleton-only subtrees. - * Remove it. - */ - parent = node->parent; - left = node->left; - right = node->right; - if (parent->left == node) - parent->left = left; - else if (parent->right == node) - parent->right = left; - else - assert(0); - left->parent = parent; - left->keymask |= (1 << node->bitnum); - node->left = NULL; - while (node) { - bitmask = 1 << node->bitnum; - leftmask &= ~bitmask; - rightmask &= ~bitmask; - if (node->leftnode == NODE && node->left) { - left = node->left; - free(node); - count++; - node = left; - } else if (node->rightnode == NODE && node->right) { - right = node->right; - free(node); - count++; - node = right; - } else { - node = NULL; - } - } - /* Propagate keymasks up along singleton chains. */ - node = parent; - /* Force re-check */ - bitmask = 1 << node->bitnum; - leftmask &= ~bitmask; - rightmask &= ~bitmask; - for (;;) { - if (node->left && node->right) - break; - if (node->left) { - left = node->left; - node->keymask |= left->keymask; - node->keybits |= left->keybits; - } - if (node->right) { - right = node->right; - node->keymask |= right->keymask; - node->keybits |= right->keybits; - } - node->keymask |= (1 << node->bitnum); - node = node->parent; - /* Force re-check */ - bitmask = 1 << node->bitnum; - leftmask &= ~bitmask; - rightmask &= ~bitmask; - } - advance: - bitmask = 1 << node->bitnum; - if ((leftmask & bitmask) == 0 && - node->leftnode == NODE && - node->left) { - leftmask |= bitmask; - node = node->left; - } else if ((rightmask & bitmask) == 0 && - node->rightnode == NODE && - node->right) { - rightmask |= bitmask; - node = node->right; - } else { - leftmask &= ~bitmask; - rightmask &= ~bitmask; - node = node->parent; - } - } - if (verbose > 0) - printf("Pruned %d nodes\n", count); -} - -/* - * Mark the nodes in the tree that lead to leaves that must be - * emitted. - */ -static void mark_nodes(struct tree *tree) -{ - struct node *node; - struct node *n; - unsigned int leftmask; - unsigned int rightmask; - unsigned int bitmask; - int marked; - - marked = 0; - if (verbose > 0) - printf("Marking %s_%x\n", tree->type, tree->maxage); - if (tree->childnode == LEAF) - goto done; - - assert(tree->childnode == NODE); - node = tree->root; - leftmask = rightmask = 0; - while (node) { - bitmask = 1 << node->bitnum; - if ((leftmask & bitmask) == 0) { - leftmask |= bitmask; - if (node->leftnode == LEAF) { - assert(node->left); - if (tree->leaf_mark(node->left)) { - n = node; - while (n && !n->mark) { - marked++; - n->mark = 1; - n = n->parent; - } - } - } else if (node->left) { - assert(node->leftnode == NODE); - node = node->left; - continue; - } - } - if ((rightmask & bitmask) == 0) { - rightmask |= bitmask; - if (node->rightnode == LEAF) { - assert(node->right); - if (tree->leaf_mark(node->right)) { - n = node; - while (n && !n->mark) { - marked++; - n->mark = 1; - n = n->parent; - } - } - } else if (node->right) { - assert(node->rightnode == NODE); - node = node->right; - continue; - } - } - leftmask &= ~bitmask; - rightmask &= ~bitmask; - node = node->parent; - } - - /* second pass: left siblings and singletons */ - - assert(tree->childnode == NODE); - node = tree->root; - leftmask = rightmask = 0; - while (node) { - bitmask = 1 << node->bitnum; - if ((leftmask & bitmask) == 0) { - leftmask |= bitmask; - if (node->leftnode == LEAF) { - assert(node->left); - if (tree->leaf_mark(node->left)) { - n = node; - while (n && !n->mark) { - marked++; - n->mark = 1; - n = n->parent; - } - } - } else if (node->left) { - assert(node->leftnode == NODE); - node = node->left; - if (!node->mark && node->parent->mark) { - marked++; - node->mark = 1; - } - continue; - } - } - if ((rightmask & bitmask) == 0) { - rightmask |= bitmask; - if (node->rightnode == LEAF) { - assert(node->right); - if (tree->leaf_mark(node->right)) { - n = node; - while (n && !n->mark) { - marked++; - n->mark = 1; - n = n->parent; - } - } - } else if (node->right) { - assert(node->rightnode == NODE); - node = node->right; - if (!node->mark && node->parent->mark && - !node->parent->left) { - marked++; - node->mark = 1; - } - continue; - } - } - leftmask &= ~bitmask; - rightmask &= ~bitmask; - node = node->parent; - } -done: - if (verbose > 0) - printf("Marked %d nodes\n", marked); -} - -/* - * Compute the index of each node and leaf, which is the offset in the - * emitted trie. These values must be pre-computed because relative - * offsets between nodes are used to navigate the tree. - */ -static int index_nodes(struct tree *tree, int index) -{ - struct node *node; - unsigned int leftmask; - unsigned int rightmask; - unsigned int bitmask; - int count; - int indent; - - /* Align to a cache line (or half a cache line?). */ - while (index % 64) - index++; - tree->index = index; - indent = 1; - count = 0; - - if (verbose > 0) - printf("Indexing %s_%x: %d\n", tree->type, tree->maxage, index); - if (tree->childnode == LEAF) { - index += tree->leaf_size(tree->root); - goto done; - } - - assert(tree->childnode == NODE); - node = tree->root; - leftmask = rightmask = 0; - while (node) { - if (!node->mark) - goto skip; - count++; - if (node->index != index) - node->index = index; - index += node->size; -skip: - while (node) { - bitmask = 1 << node->bitnum; - if (node->mark && (leftmask & bitmask) == 0) { - leftmask |= bitmask; - if (node->leftnode == LEAF) { - assert(node->left); - *tree->leaf_index(tree, node->left) = - index; - index += tree->leaf_size(node->left); - count++; - } else if (node->left) { - assert(node->leftnode == NODE); - indent += 1; - node = node->left; - break; - } - } - if (node->mark && (rightmask & bitmask) == 0) { - rightmask |= bitmask; - if (node->rightnode == LEAF) { - assert(node->right); - *tree->leaf_index(tree, node->right) = index; - index += tree->leaf_size(node->right); - count++; - } else if (node->right) { - assert(node->rightnode == NODE); - indent += 1; - node = node->right; - break; - } - } - leftmask &= ~bitmask; - rightmask &= ~bitmask; - node = node->parent; - indent -= 1; - } - } -done: - /* Round up to a multiple of 16 */ - while (index % 16) - index++; - if (verbose > 0) - printf("Final index %d\n", index); - return index; -} - -/* - * Mark the nodes in a subtree, helper for size_nodes(). - */ -static int mark_subtree(struct node *node) -{ - int changed; - - if (!node || node->mark) - return 0; - node->mark = 1; - node->index = node->parent->index; - changed = 1; - if (node->leftnode == NODE) - changed += mark_subtree(node->left); - if (node->rightnode == NODE) - changed += mark_subtree(node->right); - return changed; -} - -/* - * Compute the size of nodes and leaves. We start by assuming that - * each node needs to store a three-byte offset. The indexes of the - * nodes are calculated based on that, and then this function is - * called to see if the sizes of some nodes can be reduced. This is - * repeated until no more changes are seen. - */ -static int size_nodes(struct tree *tree) -{ - struct tree *next; - struct node *node; - struct node *right; - struct node *n; - unsigned int leftmask; - unsigned int rightmask; - unsigned int bitmask; - unsigned int pathbits; - unsigned int pathmask; - unsigned int nbit; - int changed; - int offset; - int size; - int indent; - - indent = 1; - changed = 0; - size = 0; - - if (verbose > 0) - printf("Sizing %s_%x\n", tree->type, tree->maxage); - if (tree->childnode == LEAF) - goto done; - - assert(tree->childnode == NODE); - pathbits = 0; - pathmask = 0; - node = tree->root; - leftmask = rightmask = 0; - while (node) { - if (!node->mark) - goto skip; - offset = 0; - if (!node->left || !node->right) { - size = 1; - } else { - if (node->rightnode == NODE) { - /* - * If the right node is not marked, - * look for a corresponding node in - * the next tree. Such a node need - * not exist. - */ - right = node->right; - next = tree->next; - while (!right->mark) { - assert(next); - n = next->root; - while (n->bitnum != node->bitnum) { - nbit = 1 << n->bitnum; - if (!(pathmask & nbit)) - break; - if (pathbits & nbit) { - if (n->rightnode == LEAF) - break; - n = n->right; - } else { - if (n->leftnode == LEAF) - break; - n = n->left; - } - } - if (n->bitnum != node->bitnum) - break; - n = n->right; - right = n; - next = next->next; - } - /* Make sure the right node is marked. */ - if (!right->mark) - changed += mark_subtree(right); - offset = right->index - node->index; - } else { - offset = *tree->leaf_index(tree, node->right); - offset -= node->index; - } - assert(offset >= 0); - assert(offset <= 0xffffff); - if (offset <= 0xff) { - size = 2; - } else if (offset <= 0xffff) { - size = 3; - } else { /* offset <= 0xffffff */ - size = 4; - } - } - if (node->size != size || node->offset != offset) { - node->size = size; - node->offset = offset; - changed++; - } -skip: - while (node) { - bitmask = 1 << node->bitnum; - pathmask |= bitmask; - if (node->mark && (leftmask & bitmask) == 0) { - leftmask |= bitmask; - if (node->leftnode == LEAF) { - assert(node->left); - } else if (node->left) { - assert(node->leftnode == NODE); - indent += 1; - node = node->left; - break; - } - } - if (node->mark && (rightmask & bitmask) == 0) { - rightmask |= bitmask; - pathbits |= bitmask; - if (node->rightnode == LEAF) { - assert(node->right); - } else if (node->right) { - assert(node->rightnode == NODE); - indent += 1; - node = node->right; - break; - } - } - leftmask &= ~bitmask; - rightmask &= ~bitmask; - pathmask &= ~bitmask; - pathbits &= ~bitmask; - node = node->parent; - indent -= 1; - } - } -done: - if (verbose > 0) - printf("Found %d changes\n", changed); - return changed; -} - -/* - * Emit a trie for the given tree into the data array. - */ -static void emit(struct tree *tree, unsigned char *data) -{ - struct node *node; - unsigned int leftmask; - unsigned int rightmask; - unsigned int bitmask; - int offlen; - int offset; - int index; - int indent; - int size; - int bytes; - int leaves; - int nodes[4]; - unsigned char byte; - - nodes[0] = nodes[1] = nodes[2] = nodes[3] = 0; - leaves = 0; - bytes = 0; - index = tree->index; - data += index; - indent = 1; - if (verbose > 0) - printf("Emitting %s_%x\n", tree->type, tree->maxage); - if (tree->childnode == LEAF) { - assert(tree->root); - tree->leaf_emit(tree->root, data); - size = tree->leaf_size(tree->root); - index += size; - leaves++; - goto done; - } - - assert(tree->childnode == NODE); - node = tree->root; - leftmask = rightmask = 0; - while (node) { - if (!node->mark) - goto skip; - assert(node->offset != -1); - assert(node->index == index); - - byte = 0; - if (node->nextbyte) - byte |= NEXTBYTE; - byte |= (node->bitnum & BITNUM); - if (node->left && node->right) { - if (node->leftnode == NODE) - byte |= LEFTNODE; - if (node->rightnode == NODE) - byte |= RIGHTNODE; - if (node->offset <= 0xff) - offlen = 1; - else if (node->offset <= 0xffff) - offlen = 2; - else - offlen = 3; - nodes[offlen]++; - offset = node->offset; - byte |= offlen << OFFLEN_SHIFT; - *data++ = byte; - index++; - while (offlen--) { - *data++ = offset & 0xff; - index++; - offset >>= 8; - } - } else if (node->left) { - if (node->leftnode == NODE) - byte |= TRIENODE; - nodes[0]++; - *data++ = byte; - index++; - } else if (node->right) { - byte |= RIGHTNODE; - if (node->rightnode == NODE) - byte |= TRIENODE; - nodes[0]++; - *data++ = byte; - index++; - } else { - assert(0); - } -skip: - while (node) { - bitmask = 1 << node->bitnum; - if (node->mark && (leftmask & bitmask) == 0) { - leftmask |= bitmask; - if (node->leftnode == LEAF) { - assert(node->left); - data = tree->leaf_emit(node->left, - data); - size = tree->leaf_size(node->left); - index += size; - bytes += size; - leaves++; - } else if (node->left) { - assert(node->leftnode == NODE); - indent += 1; - node = node->left; - break; - } - } - if (node->mark && (rightmask & bitmask) == 0) { - rightmask |= bitmask; - if (node->rightnode == LEAF) { - assert(node->right); - data = tree->leaf_emit(node->right, - data); - size = tree->leaf_size(node->right); - index += size; - bytes += size; - leaves++; - } else if (node->right) { - assert(node->rightnode == NODE); - indent += 1; - node = node->right; - break; - } - } - leftmask &= ~bitmask; - rightmask &= ~bitmask; - node = node->parent; - indent -= 1; - } - } -done: - if (verbose > 0) { - printf("Emitted %d (%d) leaves", - leaves, bytes); - printf(" %d (%d+%d+%d+%d) nodes", - nodes[0] + nodes[1] + nodes[2] + nodes[3], - nodes[0], nodes[1], nodes[2], nodes[3]); - printf(" %d total\n", index - tree->index); - } -} - -/* ------------------------------------------------------------------ */ - -/* - * Unicode data. - * - * We need to keep track of the Canonical Combining Class, the Age, - * and decompositions for a code point. - * - * For the Age, we store the index into the ages table. Effectively - * this is a generation number that the table maps to a unicode - * version. - * - * The correction field is used to indicate that this entry is in the - * corrections array, which contains decompositions that were - * corrected in later revisions. The value of the correction field is - * the Unicode version in which the mapping was corrected. - */ -struct unicode_data { - unsigned int code; - int ccc; - int gen; - int correction; - unsigned int *utf32nfdi; - unsigned int *utf32nfdicf; - char *utf8nfdi; - char *utf8nfdicf; -}; - -struct unicode_data unicode_data[0x110000]; -struct unicode_data *corrections; -int corrections_count; - -struct tree *nfdi_tree; -struct tree *nfdicf_tree; - -struct tree *trees; -int trees_count; - -/* - * Check the corrections array to see if this entry was corrected at - * some point. - */ -static struct unicode_data *corrections_lookup(struct unicode_data *u) -{ - int i; - - for (i = 0; i != corrections_count; i++) - if (u->code == corrections[i].code) - return &corrections[i]; - return u; -} - -static int nfdi_equal(void *l, void *r) -{ - struct unicode_data *left = l; - struct unicode_data *right = r; - - if (left->gen != right->gen) - return 0; - if (left->ccc != right->ccc) - return 0; - if (left->utf8nfdi && right->utf8nfdi && - strcmp(left->utf8nfdi, right->utf8nfdi) == 0) - return 1; - if (left->utf8nfdi || right->utf8nfdi) - return 0; - return 1; -} - -static int nfdicf_equal(void *l, void *r) -{ - struct unicode_data *left = l; - struct unicode_data *right = r; - - if (left->gen != right->gen) - return 0; - if (left->ccc != right->ccc) - return 0; - if (left->utf8nfdicf && right->utf8nfdicf && - strcmp(left->utf8nfdicf, right->utf8nfdicf) == 0) - return 1; - if (left->utf8nfdicf && right->utf8nfdicf) - return 0; - if (left->utf8nfdicf || right->utf8nfdicf) - return 0; - if (left->utf8nfdi && right->utf8nfdi && - strcmp(left->utf8nfdi, right->utf8nfdi) == 0) - return 1; - if (left->utf8nfdi || right->utf8nfdi) - return 0; - return 1; -} - -static void nfdi_print(void *l, int indent) -{ - struct unicode_data *leaf = l; - - printf("%*sleaf @ %p code %X ccc %d gen %d", indent, "", leaf, - leaf->code, leaf->ccc, leaf->gen); - - if (leaf->utf8nfdi && leaf->utf8nfdi[0] == HANGUL) - printf(" nfdi \"%s\"", "HANGUL SYLLABLE"); - else if (leaf->utf8nfdi) - printf(" nfdi \"%s\"", (const char*)leaf->utf8nfdi); - - printf("\n"); -} - -static void nfdicf_print(void *l, int indent) -{ - struct unicode_data *leaf = l; - - printf("%*sleaf @ %p code %X ccc %d gen %d", indent, "", leaf, - leaf->code, leaf->ccc, leaf->gen); - - if (leaf->utf8nfdicf) - printf(" nfdicf \"%s\"", (const char*)leaf->utf8nfdicf); - else if (leaf->utf8nfdi && leaf->utf8nfdi[0] == HANGUL) - printf(" nfdi \"%s\"", "HANGUL SYLLABLE"); - else if (leaf->utf8nfdi) - printf(" nfdi \"%s\"", (const char*)leaf->utf8nfdi); - printf("\n"); -} - -static int nfdi_mark(void *l) -{ - return 1; -} - -static int nfdicf_mark(void *l) -{ - struct unicode_data *leaf = l; - - if (leaf->utf8nfdicf) - return 1; - return 0; -} - -static int correction_mark(void *l) -{ - struct unicode_data *leaf = l; - - return leaf->correction; -} - -static int nfdi_size(void *l) -{ - struct unicode_data *leaf = l; - int size = 2; - - if (HANGUL_SYLLABLE(leaf->code)) - size += 1; - else if (leaf->utf8nfdi) - size += strlen(leaf->utf8nfdi) + 1; - return size; -} - -static int nfdicf_size(void *l) -{ - struct unicode_data *leaf = l; - int size = 2; - - if (HANGUL_SYLLABLE(leaf->code)) - size += 1; - else if (leaf->utf8nfdicf) - size += strlen(leaf->utf8nfdicf) + 1; - else if (leaf->utf8nfdi) - size += strlen(leaf->utf8nfdi) + 1; - return size; -} - -static int *nfdi_index(struct tree *tree, void *l) -{ - struct unicode_data *leaf = l; - - return &tree->leafindex[leaf->code]; -} - -static int *nfdicf_index(struct tree *tree, void *l) -{ - struct unicode_data *leaf = l; - - return &tree->leafindex[leaf->code]; -} - -static unsigned char *nfdi_emit(void *l, unsigned char *data) -{ - struct unicode_data *leaf = l; - unsigned char *s; - - *data++ = leaf->gen; - - if (HANGUL_SYLLABLE(leaf->code)) { - *data++ = DECOMPOSE; - *data++ = HANGUL; - } else if (leaf->utf8nfdi) { - *data++ = DECOMPOSE; - s = (unsigned char*)leaf->utf8nfdi; - while ((*data++ = *s++) != 0) - ; - } else { - *data++ = leaf->ccc; - } - return data; -} - -static unsigned char *nfdicf_emit(void *l, unsigned char *data) -{ - struct unicode_data *leaf = l; - unsigned char *s; - - *data++ = leaf->gen; - - if (HANGUL_SYLLABLE(leaf->code)) { - *data++ = DECOMPOSE; - *data++ = HANGUL; - } else if (leaf->utf8nfdicf) { - *data++ = DECOMPOSE; - s = (unsigned char*)leaf->utf8nfdicf; - while ((*data++ = *s++) != 0) - ; - } else if (leaf->utf8nfdi) { - *data++ = DECOMPOSE; - s = (unsigned char*)leaf->utf8nfdi; - while ((*data++ = *s++) != 0) - ; - } else { - *data++ = leaf->ccc; - } - return data; -} - -static void utf8_create(struct unicode_data *data) -{ - char utf[18*4+1]; - char *u; - unsigned int *um; - int i; - - if (data->utf8nfdi) { - assert(data->utf8nfdi[0] == HANGUL); - return; - } - - u = utf; - um = data->utf32nfdi; - if (um) { - for (i = 0; um[i]; i++) - u += utf8encode(u, um[i]); - *u = '\0'; - data->utf8nfdi = strdup(utf); - } - u = utf; - um = data->utf32nfdicf; - if (um) { - for (i = 0; um[i]; i++) - u += utf8encode(u, um[i]); - *u = '\0'; - if (!data->utf8nfdi || strcmp(data->utf8nfdi, utf)) - data->utf8nfdicf = strdup(utf); - } -} - -static void utf8_init(void) -{ - unsigned int unichar; - int i; - - for (unichar = 0; unichar != 0x110000; unichar++) - utf8_create(&unicode_data[unichar]); - - for (i = 0; i != corrections_count; i++) - utf8_create(&corrections[i]); -} - -static void trees_init(void) -{ - struct unicode_data *data; - unsigned int maxage; - unsigned int nextage; - int count; - int i; - int j; - - /* Count the number of different ages. */ - count = 0; - nextage = (unsigned int)-1; - do { - maxage = nextage; - nextage = 0; - for (i = 0; i <= corrections_count; i++) { - data = &corrections[i]; - if (nextage < data->correction && - data->correction < maxage) - nextage = data->correction; - } - count++; - } while (nextage); - - /* Two trees per age: nfdi and nfdicf */ - trees_count = count * 2; - trees = calloc(trees_count, sizeof(struct tree)); - - /* Assign ages to the trees. */ - count = trees_count; - nextage = (unsigned int)-1; - do { - maxage = nextage; - trees[--count].maxage = maxage; - trees[--count].maxage = maxage; - nextage = 0; - for (i = 0; i <= corrections_count; i++) { - data = &corrections[i]; - if (nextage < data->correction && - data->correction < maxage) - nextage = data->correction; - } - } while (nextage); - - /* The ages assigned above are off by one. */ - for (i = 0; i != trees_count; i++) { - j = 0; - while (ages[j] < trees[i].maxage) - j++; - trees[i].maxage = ages[j-1]; - } - - /* Set up the forwarding between trees. */ - trees[trees_count-2].next = &trees[trees_count-1]; - trees[trees_count-1].leaf_mark = nfdi_mark; - trees[trees_count-2].leaf_mark = nfdicf_mark; - for (i = 0; i != trees_count-2; i += 2) { - trees[i].next = &trees[trees_count-2]; - trees[i].leaf_mark = correction_mark; - trees[i+1].next = &trees[trees_count-1]; - trees[i+1].leaf_mark = correction_mark; - } - - /* Assign the callouts. */ - for (i = 0; i != trees_count; i += 2) { - trees[i].type = "nfdicf"; - trees[i].leaf_equal = nfdicf_equal; - trees[i].leaf_print = nfdicf_print; - trees[i].leaf_size = nfdicf_size; - trees[i].leaf_index = nfdicf_index; - trees[i].leaf_emit = nfdicf_emit; - - trees[i+1].type = "nfdi"; - trees[i+1].leaf_equal = nfdi_equal; - trees[i+1].leaf_print = nfdi_print; - trees[i+1].leaf_size = nfdi_size; - trees[i+1].leaf_index = nfdi_index; - trees[i+1].leaf_emit = nfdi_emit; - } - - /* Finish init. */ - for (i = 0; i != trees_count; i++) - trees[i].childnode = NODE; -} - -static void trees_populate(void) -{ - struct unicode_data *data; - unsigned int unichar; - char keyval[4]; - int keylen; - int i; - - for (i = 0; i != trees_count; i++) { - if (verbose > 0) { - printf("Populating %s_%x\n", - trees[i].type, trees[i].maxage); - } - for (unichar = 0; unichar != 0x110000; unichar++) { - if (unicode_data[unichar].gen < 0) - continue; - keylen = utf8encode(keyval, unichar); - data = corrections_lookup(&unicode_data[unichar]); - if (data->correction <= trees[i].maxage) - data = &unicode_data[unichar]; - insert(&trees[i], keyval, keylen, data); - } - } -} - -static void trees_reduce(void) -{ - int i; - int size; - int changed; - - for (i = 0; i != trees_count; i++) - prune(&trees[i]); - for (i = 0; i != trees_count; i++) - mark_nodes(&trees[i]); - do { - size = 0; - for (i = 0; i != trees_count; i++) - size = index_nodes(&trees[i], size); - changed = 0; - for (i = 0; i != trees_count; i++) - changed += size_nodes(&trees[i]); - } while (changed); - - utf8data = calloc(size, 1); - utf8data_size = size; - for (i = 0; i != trees_count; i++) - emit(&trees[i], utf8data); - - if (verbose > 0) { - for (i = 0; i != trees_count; i++) { - printf("%s_%x idx %d\n", - trees[i].type, trees[i].maxage, trees[i].index); - } - } - - nfdi = utf8data + trees[trees_count-1].index; - nfdicf = utf8data + trees[trees_count-2].index; - - nfdi_tree = &trees[trees_count-1]; - nfdicf_tree = &trees[trees_count-2]; -} - -static void verify(struct tree *tree) -{ - struct unicode_data *data; - utf8leaf_t *leaf; - unsigned int unichar; - char key[4]; - unsigned char hangul[UTF8HANGULLEAF]; - int report; - int nocf; - - if (verbose > 0) - printf("Verifying %s_%x\n", tree->type, tree->maxage); - nocf = strcmp(tree->type, "nfdicf"); - - for (unichar = 0; unichar != 0x110000; unichar++) { - report = 0; - data = corrections_lookup(&unicode_data[unichar]); - if (data->correction <= tree->maxage) - data = &unicode_data[unichar]; - utf8encode(key,unichar); - leaf = utf8lookup(tree, hangul, key); - - if (!leaf) { - if (data->gen != -1) - report++; - if (unichar < 0xd800 || unichar > 0xdfff) - report++; - } else { - if (unichar >= 0xd800 && unichar <= 0xdfff) - report++; - if (data->gen == -1) - report++; - if (data->gen != LEAF_GEN(leaf)) - report++; - if (LEAF_CCC(leaf) == DECOMPOSE) { - if (HANGUL_SYLLABLE(data->code)) { - if (data->utf8nfdi[0] != HANGUL) - report++; - } else if (nocf) { - if (!data->utf8nfdi) { - report++; - } else if (strcmp(data->utf8nfdi, - LEAF_STR(leaf))) { - report++; - } - } else { - if (!data->utf8nfdicf && - !data->utf8nfdi) { - report++; - } else if (data->utf8nfdicf) { - if (strcmp(data->utf8nfdicf, - LEAF_STR(leaf))) - report++; - } else if (strcmp(data->utf8nfdi, - LEAF_STR(leaf))) { - report++; - } - } - } else if (data->ccc != LEAF_CCC(leaf)) { - report++; - } - } - if (report) { - printf("%X code %X gen %d ccc %d" - " nfdi -> \"%s\"", - unichar, data->code, data->gen, - data->ccc, - data->utf8nfdi); - if (leaf) { - printf(" gen %d ccc %d" - " nfdi -> \"%s\"", - LEAF_GEN(leaf), - LEAF_CCC(leaf), - LEAF_CCC(leaf) == DECOMPOSE ? - LEAF_STR(leaf) : ""); - } - printf("\n"); - } - } -} - -static void trees_verify(void) -{ - int i; - - for (i = 0; i != trees_count; i++) - verify(&trees[i]); -} - -/* ------------------------------------------------------------------ */ - -static void help(void) -{ - printf("Usage: %s [options]\n", argv0); - printf("\n"); - printf("This program creates an a data trie used for parsing and\n"); - printf("normalization of UTF-8 strings. The trie is derived from\n"); - printf("a set of input files from the Unicode character database\n"); - printf("found at: http://www.unicode.org/Public/UCD/latest/ucd/\n"); - printf("\n"); - printf("The generated tree supports two normalization forms:\n"); - printf("\n"); - printf("\tnfdi:\n"); - printf("\t- Apply unicode normalization form NFD.\n"); - printf("\t- Remove any Default_Ignorable_Code_Point.\n"); - printf("\n"); - printf("\tnfdicf:\n"); - printf("\t- Apply unicode normalization form NFD.\n"); - printf("\t- Remove any Default_Ignorable_Code_Point.\n"); - printf("\t- Apply a full casefold (C + F).\n"); - printf("\n"); - printf("These forms were chosen as being most useful when dealing\n"); - printf("with file names: NFD catches most cases where characters\n"); - printf("should be considered equivalent. The ignorables are mostly\n"); - printf("invisible, making names hard to type.\n"); - printf("\n"); - printf("The options to specify the files to be used are listed\n"); - printf("below with their default values, which are the names used\n"); - printf("by version 11.0.0 of the Unicode Character Database.\n"); - printf("\n"); - printf("The input files:\n"); - printf("\t-a %s\n", AGE_NAME); - printf("\t-c %s\n", CCC_NAME); - printf("\t-p %s\n", PROP_NAME); - printf("\t-d %s\n", DATA_NAME); - printf("\t-f %s\n", FOLD_NAME); - printf("\t-n %s\n", NORM_NAME); - printf("\n"); - printf("Additionally, the generated tables are tested using:\n"); - printf("\t-t %s\n", TEST_NAME); - printf("\n"); - printf("Finally, the output file:\n"); - printf("\t-o %s\n", UTF8_NAME); - printf("\n"); -} - -static void usage(void) -{ - help(); - exit(1); -} - -static void open_fail(const char *name, int error) -{ - printf("Error %d opening %s: %s\n", error, name, strerror(error)); - exit(1); -} - -static void file_fail(const char *filename) -{ - printf("Error parsing %s\n", filename); - exit(1); -} - -static void line_fail(const char *filename, const char *line) -{ - printf("Error parsing %s:%s\n", filename, line); - exit(1); -} - -/* ------------------------------------------------------------------ */ - -static void print_utf32(unsigned int *utf32str) -{ - int i; - - for (i = 0; utf32str[i]; i++) - printf(" %X", utf32str[i]); -} - -static void print_utf32nfdi(unsigned int unichar) -{ - printf(" %X ->", unichar); - print_utf32(unicode_data[unichar].utf32nfdi); - printf("\n"); -} - -static void print_utf32nfdicf(unsigned int unichar) -{ - printf(" %X ->", unichar); - print_utf32(unicode_data[unichar].utf32nfdicf); - printf("\n"); -} - -/* ------------------------------------------------------------------ */ - -static void age_init(void) -{ - FILE *file; - unsigned int first; - unsigned int last; - unsigned int unichar; - unsigned int major; - unsigned int minor; - unsigned int revision; - int gen; - int count; - int ret; - - if (verbose > 0) - printf("Parsing %s\n", age_name); - - file = fopen(age_name, "r"); - if (!file) - open_fail(age_name, errno); - count = 0; - - gen = 0; - while (fgets(line, LINESIZE, file)) { - ret = sscanf(line, "# Age=V%d_%d_%d", - &major, &minor, &revision); - if (ret == 3) { - ages_count++; - if (verbose > 1) - printf(" Age V%d_%d_%d\n", - major, minor, revision); - if (!age_valid(major, minor, revision)) - line_fail(age_name, line); - continue; - } - ret = sscanf(line, "# Age=V%d_%d", &major, &minor); - if (ret == 2) { - ages_count++; - if (verbose > 1) - printf(" Age V%d_%d\n", major, minor); - if (!age_valid(major, minor, 0)) - line_fail(age_name, line); - continue; - } - } - - /* We must have found something above. */ - if (verbose > 1) - printf("%d age entries\n", ages_count); - if (ages_count == 0 || ages_count > MAXGEN) - file_fail(age_name); - - /* There is a 0 entry. */ - ages_count++; - ages = calloc(ages_count + 1, sizeof(*ages)); - /* And a guard entry. */ - ages[ages_count] = (unsigned int)-1; - - rewind(file); - count = 0; - gen = 0; - while (fgets(line, LINESIZE, file)) { - ret = sscanf(line, "# Age=V%d_%d_%d", - &major, &minor, &revision); - if (ret == 3) { - ages[++gen] = - UNICODE_AGE(major, minor, revision); - if (verbose > 1) - printf(" Age V%d_%d_%d = gen %d\n", - major, minor, revision, gen); - if (!age_valid(major, minor, revision)) - line_fail(age_name, line); - continue; - } - ret = sscanf(line, "# Age=V%d_%d", &major, &minor); - if (ret == 2) { - ages[++gen] = UNICODE_AGE(major, minor, 0); - if (verbose > 1) - printf(" Age V%d_%d = %d\n", - major, minor, gen); - if (!age_valid(major, minor, 0)) - line_fail(age_name, line); - continue; - } - ret = sscanf(line, "%X..%X ; %d.%d #", - &first, &last, &major, &minor); - if (ret == 4) { - for (unichar = first; unichar <= last; unichar++) - unicode_data[unichar].gen = gen; - count += 1 + last - first; - if (verbose > 1) - printf(" %X..%X gen %d\n", first, last, gen); - if (!utf32valid(first) || !utf32valid(last)) - line_fail(age_name, line); - continue; - } - ret = sscanf(line, "%X ; %d.%d #", &unichar, &major, &minor); - if (ret == 3) { - unicode_data[unichar].gen = gen; - count++; - if (verbose > 1) - printf(" %X gen %d\n", unichar, gen); - if (!utf32valid(unichar)) - line_fail(age_name, line); - continue; - } - } - unicode_maxage = ages[gen]; - fclose(file); - - /* Nix surrogate block */ - if (verbose > 1) - printf(" Removing surrogate block D800..DFFF\n"); - for (unichar = 0xd800; unichar <= 0xdfff; unichar++) - unicode_data[unichar].gen = -1; - - if (verbose > 0) - printf("Found %d entries\n", count); - if (count == 0) - file_fail(age_name); -} - -static void ccc_init(void) -{ - FILE *file; - unsigned int first; - unsigned int last; - unsigned int unichar; - unsigned int value; - int count; - int ret; - - if (verbose > 0) - printf("Parsing %s\n", ccc_name); - - file = fopen(ccc_name, "r"); - if (!file) - open_fail(ccc_name, errno); - - count = 0; - while (fgets(line, LINESIZE, file)) { - ret = sscanf(line, "%X..%X ; %d #", &first, &last, &value); - if (ret == 3) { - for (unichar = first; unichar <= last; unichar++) { - unicode_data[unichar].ccc = value; - count++; - } - if (verbose > 1) - printf(" %X..%X ccc %d\n", first, last, value); - if (!utf32valid(first) || !utf32valid(last)) - line_fail(ccc_name, line); - continue; - } - ret = sscanf(line, "%X ; %d #", &unichar, &value); - if (ret == 2) { - unicode_data[unichar].ccc = value; - count++; - if (verbose > 1) - printf(" %X ccc %d\n", unichar, value); - if (!utf32valid(unichar)) - line_fail(ccc_name, line); - continue; - } - } - fclose(file); - - if (verbose > 0) - printf("Found %d entries\n", count); - if (count == 0) - file_fail(ccc_name); -} - -static int ignore_compatibility_form(char *type) -{ - int i; - char *ignored_types[] = {"font", "noBreak", "initial", "medial", - "final", "isolated", "circle", "super", - "sub", "vertical", "wide", "narrow", - "small", "square", "fraction", "compat"}; - - for (i = 0 ; i < ARRAY_SIZE(ignored_types); i++) - if (strcmp(type, ignored_types[i]) == 0) - return 1; - return 0; -} - -static void nfdi_init(void) -{ - FILE *file; - unsigned int unichar; - unsigned int mapping[19]; /* Magic - guaranteed not to be exceeded. */ - char *s; - char *type; - unsigned int *um; - int count; - int i; - int ret; - - if (verbose > 0) - printf("Parsing %s\n", data_name); - file = fopen(data_name, "r"); - if (!file) - open_fail(data_name, errno); - - count = 0; - while (fgets(line, LINESIZE, file)) { - ret = sscanf(line, "%X;%*[^;];%*[^;];%*[^;];%*[^;];%[^;];", - &unichar, buf0); - if (ret != 2) - continue; - if (!utf32valid(unichar)) - line_fail(data_name, line); - - s = buf0; - /* skip over */ - if (*s == '<') { - type = ++s; - while (*++s != '>'); - *s++ = '\0'; - if(ignore_compatibility_form(type)) - continue; - } - /* decode the decomposition into UTF-32 */ - i = 0; - while (*s) { - mapping[i] = strtoul(s, &s, 16); - if (!utf32valid(mapping[i])) - line_fail(data_name, line); - i++; - } - mapping[i++] = 0; - - um = malloc(i * sizeof(unsigned int)); - memcpy(um, mapping, i * sizeof(unsigned int)); - unicode_data[unichar].utf32nfdi = um; - - if (verbose > 1) - print_utf32nfdi(unichar); - count++; - } - fclose(file); - if (verbose > 0) - printf("Found %d entries\n", count); - if (count == 0) - file_fail(data_name); -} - -static void nfdicf_init(void) -{ - FILE *file; - unsigned int unichar; - unsigned int mapping[19]; /* Magic - guaranteed not to be exceeded. */ - char status; - char *s; - unsigned int *um; - int i; - int count; - int ret; - - if (verbose > 0) - printf("Parsing %s\n", fold_name); - file = fopen(fold_name, "r"); - if (!file) - open_fail(fold_name, errno); - - count = 0; - while (fgets(line, LINESIZE, file)) { - ret = sscanf(line, "%X; %c; %[^;];", &unichar, &status, buf0); - if (ret != 3) - continue; - if (!utf32valid(unichar)) - line_fail(fold_name, line); - /* Use the C+F casefold. */ - if (status != 'C' && status != 'F') - continue; - s = buf0; - if (*s == '<') - while (*s++ != ' ') - ; - i = 0; - while (*s) { - mapping[i] = strtoul(s, &s, 16); - if (!utf32valid(mapping[i])) - line_fail(fold_name, line); - i++; - } - mapping[i++] = 0; - - um = malloc(i * sizeof(unsigned int)); - memcpy(um, mapping, i * sizeof(unsigned int)); - unicode_data[unichar].utf32nfdicf = um; - - if (verbose > 1) - print_utf32nfdicf(unichar); - count++; - } - fclose(file); - if (verbose > 0) - printf("Found %d entries\n", count); - if (count == 0) - file_fail(fold_name); -} - -static void ignore_init(void) -{ - FILE *file; - unsigned int unichar; - unsigned int first; - unsigned int last; - unsigned int *um; - int count; - int ret; - - if (verbose > 0) - printf("Parsing %s\n", prop_name); - file = fopen(prop_name, "r"); - if (!file) - open_fail(prop_name, errno); - assert(file); - count = 0; - while (fgets(line, LINESIZE, file)) { - ret = sscanf(line, "%X..%X ; %s # ", &first, &last, buf0); - if (ret == 3) { - if (strcmp(buf0, "Default_Ignorable_Code_Point")) - continue; - if (!utf32valid(first) || !utf32valid(last)) - line_fail(prop_name, line); - for (unichar = first; unichar <= last; unichar++) { - free(unicode_data[unichar].utf32nfdi); - um = malloc(sizeof(unsigned int)); - *um = 0; - unicode_data[unichar].utf32nfdi = um; - free(unicode_data[unichar].utf32nfdicf); - um = malloc(sizeof(unsigned int)); - *um = 0; - unicode_data[unichar].utf32nfdicf = um; - count++; - } - if (verbose > 1) - printf(" %X..%X Default_Ignorable_Code_Point\n", - first, last); - continue; - } - ret = sscanf(line, "%X ; %s # ", &unichar, buf0); - if (ret == 2) { - if (strcmp(buf0, "Default_Ignorable_Code_Point")) - continue; - if (!utf32valid(unichar)) - line_fail(prop_name, line); - free(unicode_data[unichar].utf32nfdi); - um = malloc(sizeof(unsigned int)); - *um = 0; - unicode_data[unichar].utf32nfdi = um; - free(unicode_data[unichar].utf32nfdicf); - um = malloc(sizeof(unsigned int)); - *um = 0; - unicode_data[unichar].utf32nfdicf = um; - if (verbose > 1) - printf(" %X Default_Ignorable_Code_Point\n", - unichar); - count++; - continue; - } - } - fclose(file); - - if (verbose > 0) - printf("Found %d entries\n", count); - if (count == 0) - file_fail(prop_name); -} - -static void corrections_init(void) -{ - FILE *file; - unsigned int unichar; - unsigned int major; - unsigned int minor; - unsigned int revision; - unsigned int age; - unsigned int *um; - unsigned int mapping[19]; /* Magic - guaranteed not to be exceeded. */ - char *s; - int i; - int count; - int ret; - - if (verbose > 0) - printf("Parsing %s\n", norm_name); - file = fopen(norm_name, "r"); - if (!file) - open_fail(norm_name, errno); - - count = 0; - while (fgets(line, LINESIZE, file)) { - ret = sscanf(line, "%X;%[^;];%[^;];%d.%d.%d #", - &unichar, buf0, buf1, - &major, &minor, &revision); - if (ret != 6) - continue; - if (!utf32valid(unichar) || !age_valid(major, minor, revision)) - line_fail(norm_name, line); - count++; - } - corrections = calloc(count, sizeof(struct unicode_data)); - corrections_count = count; - rewind(file); - - count = 0; - while (fgets(line, LINESIZE, file)) { - ret = sscanf(line, "%X;%[^;];%[^;];%d.%d.%d #", - &unichar, buf0, buf1, - &major, &minor, &revision); - if (ret != 6) - continue; - if (!utf32valid(unichar) || !age_valid(major, minor, revision)) - line_fail(norm_name, line); - corrections[count] = unicode_data[unichar]; - assert(corrections[count].code == unichar); - age = UNICODE_AGE(major, minor, revision); - corrections[count].correction = age; - - i = 0; - s = buf0; - while (*s) { - mapping[i] = strtoul(s, &s, 16); - if (!utf32valid(mapping[i])) - line_fail(norm_name, line); - i++; - } - mapping[i++] = 0; - - um = malloc(i * sizeof(unsigned int)); - memcpy(um, mapping, i * sizeof(unsigned int)); - corrections[count].utf32nfdi = um; - - if (verbose > 1) - printf(" %X -> %s -> %s V%d_%d_%d\n", - unichar, buf0, buf1, major, minor, revision); - count++; - } - fclose(file); - - if (verbose > 0) - printf("Found %d entries\n", count); - if (count == 0) - file_fail(norm_name); -} - -/* ------------------------------------------------------------------ */ - -/* - * Hangul decomposition (algorithm from Section 3.12 of Unicode 6.3.0) - * - * AC00;;Lo;0;L;;;;;N;;;;; - * D7A3;;Lo;0;L;;;;;N;;;;; - * - * SBase = 0xAC00 - * LBase = 0x1100 - * VBase = 0x1161 - * TBase = 0x11A7 - * LCount = 19 - * VCount = 21 - * TCount = 28 - * NCount = 588 (VCount * TCount) - * SCount = 11172 (LCount * NCount) - * - * Decomposition: - * SIndex = s - SBase - * - * LV (Canonical/Full) - * LIndex = SIndex / NCount - * VIndex = (Sindex % NCount) / TCount - * LPart = LBase + LIndex - * VPart = VBase + VIndex - * - * LVT (Canonical) - * LVIndex = (SIndex / TCount) * TCount - * TIndex = (Sindex % TCount) - * LVPart = SBase + LVIndex - * TPart = TBase + TIndex - * - * LVT (Full) - * LIndex = SIndex / NCount - * VIndex = (Sindex % NCount) / TCount - * TIndex = (Sindex % TCount) - * LPart = LBase + LIndex - * VPart = VBase + VIndex - * if (TIndex == 0) { - * d = - * } else { - * TPart = TBase + TIndex - * d = - * } - * - */ - -static void hangul_decompose(void) -{ - unsigned int sb = 0xAC00; - unsigned int lb = 0x1100; - unsigned int vb = 0x1161; - unsigned int tb = 0x11a7; - /* unsigned int lc = 19; */ - unsigned int vc = 21; - unsigned int tc = 28; - unsigned int nc = (vc * tc); - /* unsigned int sc = (lc * nc); */ - unsigned int unichar; - unsigned int mapping[4]; - unsigned int *um; - int count; - int i; - - if (verbose > 0) - printf("Decomposing hangul\n"); - /* Hangul */ - count = 0; - for (unichar = 0xAC00; unichar <= 0xD7A3; unichar++) { - unsigned int si = unichar - sb; - unsigned int li = si / nc; - unsigned int vi = (si % nc) / tc; - unsigned int ti = si % tc; - - i = 0; - mapping[i++] = lb + li; - mapping[i++] = vb + vi; - if (ti) - mapping[i++] = tb + ti; - mapping[i++] = 0; - - assert(!unicode_data[unichar].utf32nfdi); - um = malloc(i * sizeof(unsigned int)); - memcpy(um, mapping, i * sizeof(unsigned int)); - unicode_data[unichar].utf32nfdi = um; - - assert(!unicode_data[unichar].utf32nfdicf); - um = malloc(i * sizeof(unsigned int)); - memcpy(um, mapping, i * sizeof(unsigned int)); - unicode_data[unichar].utf32nfdicf = um; - - /* - * Add a cookie as a reminder that the hangul syllable - * decompositions must not be stored in the generated - * trie. - */ - unicode_data[unichar].utf8nfdi = malloc(2); - unicode_data[unichar].utf8nfdi[0] = HANGUL; - unicode_data[unichar].utf8nfdi[1] = '\0'; - - if (verbose > 1) - print_utf32nfdi(unichar); - - count++; - } - if (verbose > 0) - printf("Created %d entries\n", count); -} - -static void nfdi_decompose(void) -{ - unsigned int unichar; - unsigned int mapping[19]; /* Magic - guaranteed not to be exceeded. */ - unsigned int *um; - unsigned int *dc; - int count; - int i; - int j; - int ret; - - if (verbose > 0) - printf("Decomposing nfdi\n"); - - count = 0; - for (unichar = 0; unichar != 0x110000; unichar++) { - if (!unicode_data[unichar].utf32nfdi) - continue; - for (;;) { - ret = 1; - i = 0; - um = unicode_data[unichar].utf32nfdi; - while (*um) { - dc = unicode_data[*um].utf32nfdi; - if (dc) { - for (j = 0; dc[j]; j++) - mapping[i++] = dc[j]; - ret = 0; - } else { - mapping[i++] = *um; - } - um++; - } - mapping[i++] = 0; - if (ret) - break; - free(unicode_data[unichar].utf32nfdi); - um = malloc(i * sizeof(unsigned int)); - memcpy(um, mapping, i * sizeof(unsigned int)); - unicode_data[unichar].utf32nfdi = um; - } - /* Add this decomposition to nfdicf if there is no entry. */ - if (!unicode_data[unichar].utf32nfdicf) { - um = malloc(i * sizeof(unsigned int)); - memcpy(um, mapping, i * sizeof(unsigned int)); - unicode_data[unichar].utf32nfdicf = um; - } - if (verbose > 1) - print_utf32nfdi(unichar); - count++; - } - if (verbose > 0) - printf("Processed %d entries\n", count); -} - -static void nfdicf_decompose(void) -{ - unsigned int unichar; - unsigned int mapping[19]; /* Magic - guaranteed not to be exceeded. */ - unsigned int *um; - unsigned int *dc; - int count; - int i; - int j; - int ret; - - if (verbose > 0) - printf("Decomposing nfdicf\n"); - count = 0; - for (unichar = 0; unichar != 0x110000; unichar++) { - if (!unicode_data[unichar].utf32nfdicf) - continue; - for (;;) { - ret = 1; - i = 0; - um = unicode_data[unichar].utf32nfdicf; - while (*um) { - dc = unicode_data[*um].utf32nfdicf; - if (dc) { - for (j = 0; dc[j]; j++) - mapping[i++] = dc[j]; - ret = 0; - } else { - mapping[i++] = *um; - } - um++; - } - mapping[i++] = 0; - if (ret) - break; - free(unicode_data[unichar].utf32nfdicf); - um = malloc(i * sizeof(unsigned int)); - memcpy(um, mapping, i * sizeof(unsigned int)); - unicode_data[unichar].utf32nfdicf = um; - } - if (verbose > 1) - print_utf32nfdicf(unichar); - count++; - } - if (verbose > 0) - printf("Processed %d entries\n", count); -} - -/* ------------------------------------------------------------------ */ - -int utf8agemax(struct tree *, const char *); -int utf8nagemax(struct tree *, const char *, size_t); -int utf8agemin(struct tree *, const char *); -int utf8nagemin(struct tree *, const char *, size_t); -ssize_t utf8len(struct tree *, const char *); -ssize_t utf8nlen(struct tree *, const char *, size_t); -struct utf8cursor; -int utf8cursor(struct utf8cursor *, struct tree *, const char *); -int utf8ncursor(struct utf8cursor *, struct tree *, const char *, size_t); -int utf8byte(struct utf8cursor *); - -/* - * Hangul decomposition (algorithm from Section 3.12 of Unicode 6.3.0) - * - * AC00;;Lo;0;L;;;;;N;;;;; - * D7A3;;Lo;0;L;;;;;N;;;;; - * - * SBase = 0xAC00 - * LBase = 0x1100 - * VBase = 0x1161 - * TBase = 0x11A7 - * LCount = 19 - * VCount = 21 - * TCount = 28 - * NCount = 588 (VCount * TCount) - * SCount = 11172 (LCount * NCount) - * - * Decomposition: - * SIndex = s - SBase - * - * LV (Canonical/Full) - * LIndex = SIndex / NCount - * VIndex = (Sindex % NCount) / TCount - * LPart = LBase + LIndex - * VPart = VBase + VIndex - * - * LVT (Canonical) - * LVIndex = (SIndex / TCount) * TCount - * TIndex = (Sindex % TCount) - * LVPart = SBase + LVIndex - * TPart = TBase + TIndex - * - * LVT (Full) - * LIndex = SIndex / NCount - * VIndex = (Sindex % NCount) / TCount - * TIndex = (Sindex % TCount) - * LPart = LBase + LIndex - * VPart = VBase + VIndex - * if (TIndex == 0) { - * d = - * } else { - * TPart = TBase + TIndex - * d = - * } - */ - -/* Constants */ -#define SB (0xAC00) -#define LB (0x1100) -#define VB (0x1161) -#define TB (0x11A7) -#define LC (19) -#define VC (21) -#define TC (28) -#define NC (VC * TC) -#define SC (LC * NC) - -/* Algorithmic decomposition of hangul syllable. */ -static utf8leaf_t *utf8hangul(const char *str, unsigned char *hangul) -{ - unsigned int si; - unsigned int li; - unsigned int vi; - unsigned int ti; - unsigned char *h; - - /* Calculate the SI, LI, VI, and TI values. */ - si = utf8decode(str) - SB; - li = si / NC; - vi = (si % NC) / TC; - ti = si % TC; - - /* Fill in base of leaf. */ - h = hangul; - LEAF_GEN(h) = 2; - LEAF_CCC(h) = DECOMPOSE; - h += 2; - - /* Add LPart, a 3-byte UTF-8 sequence. */ - h += utf8encode((char *)h, li + LB); - - /* Add VPart, a 3-byte UTF-8 sequence. */ - h += utf8encode((char *)h, vi + VB); - - /* Add TPart if required, also a 3-byte UTF-8 sequence. */ - if (ti) - h += utf8encode((char *)h, ti + TB); - - /* Terminate string. */ - h[0] = '\0'; - - return hangul; -} - -/* - * Use trie to scan s, touching at most len bytes. - * Returns the leaf if one exists, NULL otherwise. - * - * A non-NULL return guarantees that the UTF-8 sequence starting at s - * is well-formed and corresponds to a known unicode code point. The - * shorthand for this will be "is valid UTF-8 unicode". - */ -static utf8leaf_t *utf8nlookup(struct tree *tree, unsigned char *hangul, - const char *s, size_t len) -{ - utf8trie_t *trie; - int offlen; - int offset; - int mask; - int node; - - if (!tree) - return NULL; - if (len == 0) - return NULL; - node = 1; - trie = utf8data + tree->index; - while (node) { - offlen = (*trie & OFFLEN) >> OFFLEN_SHIFT; - if (*trie & NEXTBYTE) { - if (--len == 0) - return NULL; - s++; - } - mask = 1 << (*trie & BITNUM); - if (*s & mask) { - /* Right leg */ - if (offlen) { - /* Right node at offset of trie */ - node = (*trie & RIGHTNODE); - offset = trie[offlen]; - while (--offlen) { - offset <<= 8; - offset |= trie[offlen]; - } - trie += offset; - } else if (*trie & RIGHTPATH) { - /* Right node after this node */ - node = (*trie & TRIENODE); - trie++; - } else { - /* No right node. */ - return NULL; - } - } else { - /* Left leg */ - if (offlen) { - /* Left node after this node. */ - node = (*trie & LEFTNODE); - trie += offlen + 1; - } else if (*trie & RIGHTPATH) { - /* No left node. */ - return NULL; - } else { - /* Left node after this node */ - node = (*trie & TRIENODE); - trie++; - } - } - } - /* - * Hangul decomposition is done algorithmically. These are the - * codepoints >= 0xAC00 and <= 0xD7A3. Their UTF-8 encoding is - * always 3 bytes long, so s has been advanced twice, and the - * start of the sequence is at s-2. - */ - if (LEAF_CCC(trie) == DECOMPOSE && LEAF_STR(trie)[0] == HANGUL) - trie = utf8hangul(s - 2, hangul); - return trie; -} - -/* - * Use trie to scan s. - * Returns the leaf if one exists, NULL otherwise. - * - * Forwards to trie_nlookup(). - */ -static utf8leaf_t *utf8lookup(struct tree *tree, unsigned char *hangul, - const char *s) -{ - return utf8nlookup(tree, hangul, s, (size_t)-1); -} - -/* - * Return the number of bytes used by the current UTF-8 sequence. - * Assumes the input points to the first byte of a valid UTF-8 - * sequence. - */ -static inline int utf8clen(const char *s) -{ - unsigned char c = *s; - return 1 + (c >= 0xC0) + (c >= 0xE0) + (c >= 0xF0); -} - -/* - * Maximum age of any character in s. - * Return -1 if s is not valid UTF-8 unicode. - * Return 0 if only non-assigned code points are used. - */ -int utf8agemax(struct tree *tree, const char *s) -{ - utf8leaf_t *leaf; - int age = 0; - int leaf_age; - unsigned char hangul[UTF8HANGULLEAF]; - - if (!tree) - return -1; - - while (*s) { - leaf = utf8lookup(tree, hangul, s); - if (!leaf) - return -1; - leaf_age = ages[LEAF_GEN(leaf)]; - if (leaf_age <= tree->maxage && leaf_age > age) - age = leaf_age; - s += utf8clen(s); - } - return age; -} - -/* - * Minimum age of any character in s. - * Return -1 if s is not valid UTF-8 unicode. - * Return 0 if non-assigned code points are used. - */ -int utf8agemin(struct tree *tree, const char *s) -{ - utf8leaf_t *leaf; - int age; - int leaf_age; - unsigned char hangul[UTF8HANGULLEAF]; - - if (!tree) - return -1; - age = tree->maxage; - while (*s) { - leaf = utf8lookup(tree, hangul, s); - if (!leaf) - return -1; - leaf_age = ages[LEAF_GEN(leaf)]; - if (leaf_age <= tree->maxage && leaf_age < age) - age = leaf_age; - s += utf8clen(s); - } - return age; -} - -/* - * Maximum age of any character in s, touch at most len bytes. - * Return -1 if s is not valid UTF-8 unicode. - */ -int utf8nagemax(struct tree *tree, const char *s, size_t len) -{ - utf8leaf_t *leaf; - int age = 0; - int leaf_age; - unsigned char hangul[UTF8HANGULLEAF]; - - if (!tree) - return -1; - - while (len && *s) { - leaf = utf8nlookup(tree, hangul, s, len); - if (!leaf) - return -1; - leaf_age = ages[LEAF_GEN(leaf)]; - if (leaf_age <= tree->maxage && leaf_age > age) - age = leaf_age; - len -= utf8clen(s); - s += utf8clen(s); - } - return age; -} - -/* - * Maximum age of any character in s, touch at most len bytes. - * Return -1 if s is not valid UTF-8 unicode. - */ -int utf8nagemin(struct tree *tree, const char *s, size_t len) -{ - utf8leaf_t *leaf; - int leaf_age; - int age; - unsigned char hangul[UTF8HANGULLEAF]; - - if (!tree) - return -1; - age = tree->maxage; - while (len && *s) { - leaf = utf8nlookup(tree, hangul, s, len); - if (!leaf) - return -1; - leaf_age = ages[LEAF_GEN(leaf)]; - if (leaf_age <= tree->maxage && leaf_age < age) - age = leaf_age; - len -= utf8clen(s); - s += utf8clen(s); - } - return age; -} - -/* - * Length of the normalization of s. - * Return -1 if s is not valid UTF-8 unicode. - * - * A string of Default_Ignorable_Code_Point has length 0. - */ -ssize_t utf8len(struct tree *tree, const char *s) -{ - utf8leaf_t *leaf; - size_t ret = 0; - unsigned char hangul[UTF8HANGULLEAF]; - - if (!tree) - return -1; - while (*s) { - leaf = utf8lookup(tree, hangul, s); - if (!leaf) - return -1; - if (ages[LEAF_GEN(leaf)] > tree->maxage) - ret += utf8clen(s); - else if (LEAF_CCC(leaf) == DECOMPOSE) - ret += strlen(LEAF_STR(leaf)); - else - ret += utf8clen(s); - s += utf8clen(s); - } - return ret; -} - -/* - * Length of the normalization of s, touch at most len bytes. - * Return -1 if s is not valid UTF-8 unicode. - */ -ssize_t utf8nlen(struct tree *tree, const char *s, size_t len) -{ - utf8leaf_t *leaf; - size_t ret = 0; - unsigned char hangul[UTF8HANGULLEAF]; - - if (!tree) - return -1; - while (len && *s) { - leaf = utf8nlookup(tree, hangul, s, len); - if (!leaf) - return -1; - if (ages[LEAF_GEN(leaf)] > tree->maxage) - ret += utf8clen(s); - else if (LEAF_CCC(leaf) == DECOMPOSE) - ret += strlen(LEAF_STR(leaf)); - else - ret += utf8clen(s); - len -= utf8clen(s); - s += utf8clen(s); - } - return ret; -} - -/* - * Cursor structure used by the normalizer. - */ -struct utf8cursor { - struct tree *tree; - const char *s; - const char *p; - const char *ss; - const char *sp; - unsigned int len; - unsigned int slen; - short int ccc; - short int nccc; - unsigned int unichar; - unsigned char hangul[UTF8HANGULLEAF]; -}; - -/* - * Set up an utf8cursor for use by utf8byte(). - * - * s : string. - * len : length of s. - * u8c : pointer to cursor. - * trie : utf8trie_t to use for normalization. - * - * Returns -1 on error, 0 on success. - */ -int utf8ncursor(struct utf8cursor *u8c, struct tree *tree, const char *s, - size_t len) -{ - if (!tree) - return -1; - if (!s) - return -1; - u8c->tree = tree; - u8c->s = s; - u8c->p = NULL; - u8c->ss = NULL; - u8c->sp = NULL; - u8c->len = len; - u8c->slen = 0; - u8c->ccc = STOPPER; - u8c->nccc = STOPPER; - u8c->unichar = 0; - /* Check we didn't clobber the maximum length. */ - if (u8c->len != len) - return -1; - /* The first byte of s may not be an utf8 continuation. */ - if (len > 0 && (*s & 0xC0) == 0x80) - return -1; - return 0; -} - -/* - * Set up an utf8cursor for use by utf8byte(). - * - * s : NUL-terminated string. - * u8c : pointer to cursor. - * trie : utf8trie_t to use for normalization. - * - * Returns -1 on error, 0 on success. - */ -int utf8cursor(struct utf8cursor *u8c, struct tree *tree, const char *s) -{ - return utf8ncursor(u8c, tree, s, (unsigned int)-1); -} - -/* - * Get one byte from the normalized form of the string described by u8c. - * - * Returns the byte cast to an unsigned char on succes, and -1 on failure. - * - * The cursor keeps track of the location in the string in u8c->s. - * When a character is decomposed, the current location is stored in - * u8c->p, and u8c->s is set to the start of the decomposition. Note - * that bytes from a decomposition do not count against u8c->len. - * - * Characters are emitted if they match the current CCC in u8c->ccc. - * Hitting end-of-string while u8c->ccc == STOPPER means we're done, - * and the function returns 0 in that case. - * - * Sorting by CCC is done by repeatedly scanning the string. The - * values of u8c->s and u8c->p are stored in u8c->ss and u8c->sp at - * the start of the scan. The first pass finds the lowest CCC to be - * emitted and stores it in u8c->nccc, the second pass emits the - * characters with this CCC and finds the next lowest CCC. This limits - * the number of passes to 1 + the number of different CCCs in the - * sequence being scanned. - * - * Therefore: - * u8c->p != NULL -> a decomposition is being scanned. - * u8c->ss != NULL -> this is a repeating scan. - * u8c->ccc == -1 -> this is the first scan of a repeating scan. - */ -int utf8byte(struct utf8cursor *u8c) -{ - utf8leaf_t *leaf; - int ccc; - - for (;;) { - /* Check for the end of a decomposed character. */ - if (u8c->p && *u8c->s == '\0') { - u8c->s = u8c->p; - u8c->p = NULL; - } - - /* Check for end-of-string. */ - if (!u8c->p && (u8c->len == 0 || *u8c->s == '\0')) { - /* There is no next byte. */ - if (u8c->ccc == STOPPER) - return 0; - /* End-of-string during a scan counts as a stopper. */ - ccc = STOPPER; - goto ccc_mismatch; - } else if ((*u8c->s & 0xC0) == 0x80) { - /* This is a continuation of the current character. */ - if (!u8c->p) - u8c->len--; - return (unsigned char)*u8c->s++; - } - - /* Look up the data for the current character. */ - if (u8c->p) { - leaf = utf8lookup(u8c->tree, u8c->hangul, u8c->s); - } else { - leaf = utf8nlookup(u8c->tree, u8c->hangul, - u8c->s, u8c->len); - } - - /* No leaf found implies that the input is a binary blob. */ - if (!leaf) - return -1; - - /* Characters that are too new have CCC 0. */ - if (ages[LEAF_GEN(leaf)] > u8c->tree->maxage) { - ccc = STOPPER; - } else if ((ccc = LEAF_CCC(leaf)) == DECOMPOSE) { - u8c->len -= utf8clen(u8c->s); - u8c->p = u8c->s + utf8clen(u8c->s); - u8c->s = LEAF_STR(leaf); - /* Empty decomposition implies CCC 0. */ - if (*u8c->s == '\0') { - if (u8c->ccc == STOPPER) - continue; - ccc = STOPPER; - goto ccc_mismatch; - } - leaf = utf8lookup(u8c->tree, u8c->hangul, u8c->s); - ccc = LEAF_CCC(leaf); - } - u8c->unichar = utf8decode(u8c->s); - - /* - * If this is not a stopper, then see if it updates - * the next canonical class to be emitted. - */ - if (ccc != STOPPER && u8c->ccc < ccc && ccc < u8c->nccc) - u8c->nccc = ccc; - - /* - * Return the current byte if this is the current - * combining class. - */ - if (ccc == u8c->ccc) { - if (!u8c->p) - u8c->len--; - return (unsigned char)*u8c->s++; - } - - /* Current combining class mismatch. */ - ccc_mismatch: - if (u8c->nccc == STOPPER) { - /* - * Scan forward for the first canonical class - * to be emitted. Save the position from - * which to restart. - */ - assert(u8c->ccc == STOPPER); - u8c->ccc = MINCCC - 1; - u8c->nccc = ccc; - u8c->sp = u8c->p; - u8c->ss = u8c->s; - u8c->slen = u8c->len; - if (!u8c->p) - u8c->len -= utf8clen(u8c->s); - u8c->s += utf8clen(u8c->s); - } else if (ccc != STOPPER) { - /* Not a stopper, and not the ccc we're emitting. */ - if (!u8c->p) - u8c->len -= utf8clen(u8c->s); - u8c->s += utf8clen(u8c->s); - } else if (u8c->nccc != MAXCCC + 1) { - /* At a stopper, restart for next ccc. */ - u8c->ccc = u8c->nccc; - u8c->nccc = MAXCCC + 1; - u8c->s = u8c->ss; - u8c->p = u8c->sp; - u8c->len = u8c->slen; - } else { - /* All done, proceed from here. */ - u8c->ccc = STOPPER; - u8c->nccc = STOPPER; - u8c->sp = NULL; - u8c->ss = NULL; - u8c->slen = 0; - } - } -} - -/* ------------------------------------------------------------------ */ - -static int normalize_line(struct tree *tree) -{ - char *s; - char *t; - int c; - struct utf8cursor u8c; - - /* First test: null-terminated string. */ - s = buf2; - t = buf3; - if (utf8cursor(&u8c, tree, s)) - return -1; - while ((c = utf8byte(&u8c)) > 0) - if (c != (unsigned char)*t++) - return -1; - if (c < 0) - return -1; - if (*t != 0) - return -1; - - /* Second test: length-limited string. */ - s = buf2; - /* Replace NUL with a value that will cause an error if seen. */ - s[strlen(s) + 1] = -1; - t = buf3; - if (utf8cursor(&u8c, tree, s)) - return -1; - while ((c = utf8byte(&u8c)) > 0) - if (c != (unsigned char)*t++) - return -1; - if (c < 0) - return -1; - if (*t != 0) - return -1; - - return 0; -} - -static void normalization_test(void) -{ - FILE *file; - unsigned int unichar; - struct unicode_data *data; - char *s; - char *t; - int ret; - int ignorables; - int tests = 0; - int failures = 0; - - if (verbose > 0) - printf("Parsing %s\n", test_name); - /* Step one, read data from file. */ - file = fopen(test_name, "r"); - if (!file) - open_fail(test_name, errno); - - while (fgets(line, LINESIZE, file)) { - ret = sscanf(line, "%[^;];%*[^;];%[^;];%*[^;];%*[^;];", - buf0, buf1); - if (ret != 2 || *line == '#') - continue; - s = buf0; - t = buf2; - while (*s) { - unichar = strtoul(s, &s, 16); - t += utf8encode(t, unichar); - } - *t = '\0'; - - ignorables = 0; - s = buf1; - t = buf3; - while (*s) { - unichar = strtoul(s, &s, 16); - data = &unicode_data[unichar]; - if (data->utf8nfdi && !*data->utf8nfdi) - ignorables = 1; - else - t += utf8encode(t, unichar); - } - *t = '\0'; - - tests++; - if (normalize_line(nfdi_tree) < 0) { - printf("Line %s -> %s", buf0, buf1); - if (ignorables) - printf(" (ignorables removed)"); - printf(" failure\n"); - failures++; - } - } - fclose(file); - if (verbose > 0) - printf("Ran %d tests with %d failures\n", tests, failures); - if (failures) - file_fail(test_name); -} - -/* ------------------------------------------------------------------ */ - -static void write_file(void) -{ - FILE *file; - int i; - int j; - int t; - int gen; - - if (verbose > 0) - printf("Writing %s\n", utf8_name); - file = fopen(utf8_name, "w"); - if (!file) - open_fail(utf8_name, errno); - - fprintf(file, "/* This file is generated code, do not edit. */\n"); - fprintf(file, "#ifndef __INCLUDED_FROM_UTF8NORM_C__\n"); - fprintf(file, "#error Only nls_utf8-norm.c should include this file.\n"); - fprintf(file, "#endif\n"); - fprintf(file, "\n"); - fprintf(file, "static const unsigned int utf8vers = %#x;\n", - unicode_maxage); - fprintf(file, "\n"); - fprintf(file, "static const unsigned int utf8agetab[] = {\n"); - for (i = 0; i != ages_count; i++) - fprintf(file, "\t%#x%s\n", ages[i], - ages[i] == unicode_maxage ? "" : ","); - fprintf(file, "};\n"); - fprintf(file, "\n"); - fprintf(file, "static const struct utf8data utf8nfdicfdata[] = {\n"); - t = 0; - for (gen = 0; gen < ages_count; gen++) { - fprintf(file, "\t{ %#x, %d }%s\n", - ages[gen], trees[t].index, - ages[gen] == unicode_maxage ? "" : ","); - if (trees[t].maxage == ages[gen]) - t += 2; - } - fprintf(file, "};\n"); - fprintf(file, "\n"); - fprintf(file, "static const struct utf8data utf8nfdidata[] = {\n"); - t = 1; - for (gen = 0; gen < ages_count; gen++) { - fprintf(file, "\t{ %#x, %d }%s\n", - ages[gen], trees[t].index, - ages[gen] == unicode_maxage ? "" : ","); - if (trees[t].maxage == ages[gen]) - t += 2; - } - fprintf(file, "};\n"); - fprintf(file, "\n"); - fprintf(file, "static const unsigned char utf8data[%zd] = {\n", - utf8data_size); - t = 0; - for (i = 0; i != utf8data_size; i += 16) { - if (i == trees[t].index) { - fprintf(file, "\t/* %s_%x */\n", - trees[t].type, trees[t].maxage); - if (t < trees_count-1) - t++; - } - fprintf(file, "\t"); - for (j = i; j != i + 16; j++) - fprintf(file, "0x%.2x%s", utf8data[j], - (j < utf8data_size -1 ? "," : "")); - fprintf(file, "\n"); - } - fprintf(file, "};\n"); - fclose(file); -} - -/* ------------------------------------------------------------------ */ - -int main(int argc, char *argv[]) -{ - unsigned int unichar; - int opt; - - argv0 = argv[0]; - - while ((opt = getopt(argc, argv, "a:c:d:f:hn:o:p:t:v")) != -1) { - switch (opt) { - case 'a': - age_name = optarg; - break; - case 'c': - ccc_name = optarg; - break; - case 'd': - data_name = optarg; - break; - case 'f': - fold_name = optarg; - break; - case 'n': - norm_name = optarg; - break; - case 'o': - utf8_name = optarg; - break; - case 'p': - prop_name = optarg; - break; - case 't': - test_name = optarg; - break; - case 'v': - verbose++; - break; - case 'h': - help(); - exit(0); - default: - usage(); - } - } - - if (verbose > 1) - help(); - for (unichar = 0; unichar != 0x110000; unichar++) - unicode_data[unichar].code = unichar; - age_init(); - ccc_init(); - nfdi_init(); - nfdicf_init(); - ignore_init(); - corrections_init(); - hangul_decompose(); - nfdi_decompose(); - nfdicf_decompose(); - utf8_init(); - trees_init(); - trees_populate(); - trees_reduce(); - trees_verify(); - /* Prevent "unused function" warning. */ - (void)lookup(nfdi_tree, " "); - if (verbose > 2) - tree_walk(nfdi_tree); - if (verbose > 2) - tree_walk(nfdicf_tree); - normalization_test(); - write_file(); - - return 0; -} -- cgit v1.2.3 From c8e3993dd5b90d4e1c5a0edf853fa91add12b302 Mon Sep 17 00:00:00 2001 From: Robin Murphy Date: Tue, 23 Apr 2019 15:12:34 +0100 Subject: dt-bindings: hwmon (pwm-fan) Remove dead "cooling-*-state" properties The old "cooling-{min,max}-state" properties for thermal bindings were ratified to "cooling-{min,max}-level" by commit eb168b70dea5 ("of: thermal: Fix inconsitency between cooling-*-state and cooling-*-level"), which were later removed entirely by commit e04907dbc259 ("dt-bindings: thermal: Remove "cooling-{min|max}-level" properties"). The pwm-fan binding, however, was apparently in-flight in parallel with that ratification, and so managed to introduce an example of the old properties which escaped the scope of the later cleanup and has thus continued to be dutifully copied for new boards despite being useless. Clean up these remaining undocumented anachronisms to minimise any further confusion. Acked-by: Guenter Roeck Reviewed-by: Krzysztof Kozlowski Acked-by: Thierry Reding Acked-by: Heiko Stuebner Acked-by: Shawn Guo Reviewed-by: Rob Herring Signed-off-by: Robin Murphy Signed-off-by: Olof Johansson --- Documentation/devicetree/bindings/hwmon/pwm-fan.txt | 2 -- arch/arm/boot/dts/exynos4412-odroidu3.dts | 2 -- arch/arm/boot/dts/exynos5410-odroidxu.dts | 2 -- arch/arm/boot/dts/exynos5422-odroidxu3-common.dtsi | 2 -- arch/arm/boot/dts/imx6qdl-emcon.dtsi | 2 -- arch/arm64/boot/dts/nvidia/tegra194-p2972-0000.dts | 2 -- arch/arm64/boot/dts/rockchip/rk3368-lion.dtsi | 2 -- arch/arm64/boot/dts/rockchip/rk3399-puma.dtsi | 2 -- 8 files changed, 16 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/hwmon/pwm-fan.txt b/Documentation/devicetree/bindings/hwmon/pwm-fan.txt index 49ca5d83ed13..716e84f3bbb2 100644 --- a/Documentation/devicetree/bindings/hwmon/pwm-fan.txt +++ b/Documentation/devicetree/bindings/hwmon/pwm-fan.txt @@ -12,8 +12,6 @@ Optional properties: Example: fan0: pwm-fan { compatible = "pwm-fan"; - cooling-min-state = <0>; - cooling-max-state = <3>; #cooling-cells = <2>; pwms = <&pwm 0 10000 0>; cooling-levels = <0 102 170 230>; diff --git a/arch/arm/boot/dts/exynos4412-odroidu3.dts b/arch/arm/boot/dts/exynos4412-odroidu3.dts index 88891ff5f238..96d99887bceb 100644 --- a/arch/arm/boot/dts/exynos4412-odroidu3.dts +++ b/arch/arm/boot/dts/exynos4412-odroidu3.dts @@ -34,8 +34,6 @@ fan0: pwm-fan { compatible = "pwm-fan"; pwms = <&pwm 0 10000 0>; - cooling-min-state = <0>; - cooling-max-state = <3>; #cooling-cells = <2>; cooling-levels = <0 102 170 230>; }; diff --git a/arch/arm/boot/dts/exynos5410-odroidxu.dts b/arch/arm/boot/dts/exynos5410-odroidxu.dts index 434a7591ff63..8f9e08f940ab 100644 --- a/arch/arm/boot/dts/exynos5410-odroidxu.dts +++ b/arch/arm/boot/dts/exynos5410-odroidxu.dts @@ -38,8 +38,6 @@ fan0: pwm-fan { compatible = "pwm-fan"; pwms = <&pwm 0 20972 0>; - cooling-min-state = <0>; - cooling-max-state = <3>; #cooling-cells = <2>; cooling-levels = <0 130 170 230>; }; diff --git a/arch/arm/boot/dts/exynos5422-odroidxu3-common.dtsi b/arch/arm/boot/dts/exynos5422-odroidxu3-common.dtsi index 5f195ad7e467..93a48f2dda49 100644 --- a/arch/arm/boot/dts/exynos5422-odroidxu3-common.dtsi +++ b/arch/arm/boot/dts/exynos5422-odroidxu3-common.dtsi @@ -44,8 +44,6 @@ fan0: pwm-fan { compatible = "pwm-fan"; pwms = <&pwm 0 20972 0>; - cooling-min-state = <0>; - cooling-max-state = <3>; #cooling-cells = <2>; cooling-levels = <0 130 170 230>; }; diff --git a/arch/arm/boot/dts/imx6qdl-emcon.dtsi b/arch/arm/boot/dts/imx6qdl-emcon.dtsi index 397e205551c4..70d26616d771 100644 --- a/arch/arm/boot/dts/imx6qdl-emcon.dtsi +++ b/arch/arm/boot/dts/imx6qdl-emcon.dtsi @@ -77,8 +77,6 @@ pwm_fan: pwm-fan { compatible = "pwm-fan"; - cooling-min-state = <0>; - cooling-max-state = <4>; #cooling-cells = <2>; pwms = <&pwm4 0 50000>; cooling-levels = <0 64 127 191 255>; diff --git a/arch/arm64/boot/dts/nvidia/tegra194-p2972-0000.dts b/arch/arm64/boot/dts/nvidia/tegra194-p2972-0000.dts index b62e96945846..73801b48d1d8 100644 --- a/arch/arm64/boot/dts/nvidia/tegra194-p2972-0000.dts +++ b/arch/arm64/boot/dts/nvidia/tegra194-p2972-0000.dts @@ -57,8 +57,6 @@ pwms = <&pwm4 0 45334>; cooling-levels = <0 64 128 255>; - cooling-min-state = <0>; - cooling-max-state = <3>; #cooling-cells = <2>; }; diff --git a/arch/arm64/boot/dts/rockchip/rk3368-lion.dtsi b/arch/arm64/boot/dts/rockchip/rk3368-lion.dtsi index 1b35d612b660..cc35c88dafd9 100644 --- a/arch/arm64/boot/dts/rockchip/rk3368-lion.dtsi +++ b/arch/arm64/boot/dts/rockchip/rk3368-lion.dtsi @@ -56,8 +56,6 @@ fan: fan@18 { compatible = "ti,amc6821"; reg = <0x18>; - cooling-min-state = <0>; - cooling-max-state = <9>; #cooling-cells = <2>; }; diff --git a/arch/arm64/boot/dts/rockchip/rk3399-puma.dtsi b/arch/arm64/boot/dts/rockchip/rk3399-puma.dtsi index 4f75bb6b2f14..12f24d1eea81 100644 --- a/arch/arm64/boot/dts/rockchip/rk3399-puma.dtsi +++ b/arch/arm64/boot/dts/rockchip/rk3399-puma.dtsi @@ -370,8 +370,6 @@ fan: fan@18 { compatible = "ti,amc6821"; reg = <0x18>; - cooling-min-state = <0>; - cooling-max-state = <9>; #cooling-cells = <2>; }; -- cgit v1.2.3 From fbfe07d440f2c55070a0358f66560bb4f9fb92e7 Mon Sep 17 00:00:00 2001 From: Sebastian Ott Date: Tue, 26 Feb 2019 16:07:32 +0100 Subject: s390/pci: add parameter to force floating irqs Provide a kernel parameter to force the usage of floating interrupts. Signed-off-by: Sebastian Ott Signed-off-by: Martin Schwidefsky --- Documentation/admin-guide/kernel-parameters.txt | 1 + arch/s390/include/asm/pci.h | 1 + arch/s390/pci/pci.c | 5 +++++ arch/s390/pci/pci_irq.c | 3 +++ 4 files changed, 10 insertions(+) (limited to 'Documentation') diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt index 2b8ee90bb644..abc1b6e305c4 100644 --- a/Documentation/admin-guide/kernel-parameters.txt +++ b/Documentation/admin-guide/kernel-parameters.txt @@ -3394,6 +3394,7 @@ bridges without forcing it upstream. Note: this removes isolation between devices and may put more devices in an IOMMU group. + force_floating [S390] Force usage of floating interrupts. pcie_aspm= [PCIE] Forcibly enable or disable PCIe Active State Power Management. diff --git a/arch/s390/include/asm/pci.h b/arch/s390/include/asm/pci.h index a285754d0742..328013219aec 100644 --- a/arch/s390/include/asm/pci.h +++ b/arch/s390/include/asm/pci.h @@ -163,6 +163,7 @@ static inline bool zdev_enabled(struct zpci_dev *zdev) } extern const struct attribute_group *zpci_attr_groups[]; +extern unsigned int s390_pci_force_floating __initdata; /* ----------------------------------------------------------------------------- Prototypes diff --git a/arch/s390/pci/pci.c b/arch/s390/pci/pci.c index 716e773af788..db096fd16f46 100644 --- a/arch/s390/pci/pci.c +++ b/arch/s390/pci/pci.c @@ -741,6 +741,7 @@ static void zpci_mem_exit(void) } static unsigned int s390_pci_probe __initdata = 1; +unsigned int s390_pci_force_floating __initdata; static unsigned int s390_pci_initialized; char * __init pcibios_setup(char *str) @@ -749,6 +750,10 @@ char * __init pcibios_setup(char *str) s390_pci_probe = 0; return NULL; } + if (!strcmp(str, "force_floating")) { + s390_pci_force_floating = 1; + return NULL; + } return str; } diff --git a/arch/s390/pci/pci_irq.c b/arch/s390/pci/pci_irq.c index c73ab855a2ca..d80616ae8dd8 100644 --- a/arch/s390/pci/pci_irq.c +++ b/arch/s390/pci/pci_irq.c @@ -433,6 +433,9 @@ int __init zpci_irq_init(void) int rc; irq_delivery = sclp.has_dirq ? DIRECTED : FLOATING; + if (s390_pci_force_floating) + irq_delivery = FLOATING; + if (irq_delivery == DIRECTED) zpci_airq.handler = zpci_directed_irq_handler; -- cgit v1.2.3 From 56271303808fb86375ec33183d56c21fdeb836ea Mon Sep 17 00:00:00 2001 From: Sebastian Ott Date: Thu, 18 Apr 2019 21:39:06 +0200 Subject: s390/pci: add parameter to disable usage of MIO instructions Allow users to disable usage of MIO instructions by specifying pci=nomio at the kernel command line. Signed-off-by: Sebastian Ott Signed-off-by: Martin Schwidefsky --- Documentation/admin-guide/kernel-parameters.txt | 1 + arch/s390/pci/pci.c | 7 ++++++- 2 files changed, 7 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt index abc1b6e305c4..055284c31e37 100644 --- a/Documentation/admin-guide/kernel-parameters.txt +++ b/Documentation/admin-guide/kernel-parameters.txt @@ -3395,6 +3395,7 @@ this removes isolation between devices and may put more devices in an IOMMU group. force_floating [S390] Force usage of floating interrupts. + nomio [S390] Do not use MIO instructions. pcie_aspm= [PCIE] Forcibly enable or disable PCIe Active State Power Management. diff --git a/arch/s390/pci/pci.c b/arch/s390/pci/pci.c index dff8f4526c8d..0ebb7c405a25 100644 --- a/arch/s390/pci/pci.c +++ b/arch/s390/pci/pci.c @@ -850,6 +850,7 @@ static void zpci_mem_exit(void) } static unsigned int s390_pci_probe __initdata = 1; +static unsigned int s390_pci_no_mio __initdata; unsigned int s390_pci_force_floating __initdata; static unsigned int s390_pci_initialized; @@ -859,6 +860,10 @@ char * __init pcibios_setup(char *str) s390_pci_probe = 0; return NULL; } + if (!strcmp(str, "nomio")) { + s390_pci_no_mio = 1; + return NULL; + } if (!strcmp(str, "force_floating")) { s390_pci_force_floating = 1; return NULL; @@ -881,7 +886,7 @@ static int __init pci_base_init(void) if (!test_facility(69) || !test_facility(71)) return 0; - if (test_facility(153)) + if (test_facility(153) && !s390_pci_no_mio) static_branch_enable(&have_mio); rc = zpci_debug_init(); -- cgit v1.2.3 From 6fee3787ea7aebf25fecdce325ee9b2150c5727b Mon Sep 17 00:00:00 2001 From: Fabrizio Castro Date: Mon, 29 Apr 2019 09:51:24 +0100 Subject: dt-bindings: usb-xhci: Add r8a774c0 support Document RZ/G2E (R8A774C0) SoC bindings. Signed-off-by: Fabrizio Castro Reviewed-by: Geert Uytterhoeven Reviewed-by: Simon Horman Reviewed-by: Rob Herring Signed-off-by: Greg Kroah-Hartman --- Documentation/devicetree/bindings/usb/usb-xhci.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/usb/usb-xhci.txt b/Documentation/devicetree/bindings/usb/usb-xhci.txt index fea8b1545751..97400e8f8605 100644 --- a/Documentation/devicetree/bindings/usb/usb-xhci.txt +++ b/Documentation/devicetree/bindings/usb/usb-xhci.txt @@ -10,6 +10,7 @@ Required properties: - "renesas,xhci-r8a7743" for r8a7743 SoC - "renesas,xhci-r8a7744" for r8a7744 SoC - "renesas,xhci-r8a774a1" for r8a774a1 SoC + - "renesas,xhci-r8a774c0" for r8a774c0 SoC - "renesas,xhci-r8a7790" for r8a7790 SoC - "renesas,xhci-r8a7791" for r8a7791 SoC - "renesas,xhci-r8a7793" for r8a7793 SoC -- cgit v1.2.3 From 5f2c54e7153f2b30b7ee5c65ec5eb2b38a7b962d Mon Sep 17 00:00:00 2001 From: Biju Das Date: Mon, 29 Apr 2019 11:22:57 +0100 Subject: dt-bindings: usb: renesas_usbhs: Add support for r8a77470 Document support for RZ/G1C (R8A77470) SoC. Signed-off-by: Biju Das Reviewed-by: Rob Herring Reviewed-by: Simon Horman Reviewed-by: Yoshihiro Shimoda Signed-off-by: Greg Kroah-Hartman --- Documentation/devicetree/bindings/usb/renesas_usbhs.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/usb/renesas_usbhs.txt b/Documentation/devicetree/bindings/usb/renesas_usbhs.txt index d93b6a1504f2..b8acc2a994a8 100644 --- a/Documentation/devicetree/bindings/usb/renesas_usbhs.txt +++ b/Documentation/devicetree/bindings/usb/renesas_usbhs.txt @@ -6,6 +6,7 @@ Required properties: - "renesas,usbhs-r8a7743" for r8a7743 (RZ/G1M) compatible device - "renesas,usbhs-r8a7744" for r8a7744 (RZ/G1N) compatible device - "renesas,usbhs-r8a7745" for r8a7745 (RZ/G1E) compatible device + - "renesas,usbhs-r8a77470" for r8a77470 (RZ/G1C) compatible device - "renesas,usbhs-r8a774a1" for r8a774a1 (RZ/G2M) compatible device - "renesas,usbhs-r8a774c0" for r8a774c0 (RZ/G2E) compatible device - "renesas,usbhs-r8a7790" for r8a7790 (R-Car H2) compatible device -- cgit v1.2.3 From dbcdae185a704068c22984d6d05acc140ec03a8f Mon Sep 17 00:00:00 2001 From: Andrew Jones Date: Mon, 29 Apr 2019 10:27:10 +0200 Subject: Documentation: kvm: fix dirty log ioctl arch lists KVM_GET_DIRTY_LOG is implemented by all architectures, not just x86, and KVM_CAP_MANUAL_DIRTY_LOG_PROTECT is additionally implemented by arm, arm64, and mips. Signed-off-by: Andrew Jones Signed-off-by: Paolo Bonzini --- Documentation/virtual/kvm/api.txt | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/api.txt b/Documentation/virtual/kvm/api.txt index 67068c47c591..7f3ebc9e7cee 100644 --- a/Documentation/virtual/kvm/api.txt +++ b/Documentation/virtual/kvm/api.txt @@ -321,7 +321,7 @@ cpu's hardware control block. 4.8 KVM_GET_DIRTY_LOG (vm ioctl) Capability: basic -Architectures: x86 +Architectures: all Type: vm ioctl Parameters: struct kvm_dirty_log (in/out) Returns: 0 on success, -1 on error @@ -3810,7 +3810,7 @@ to I/O ports. 4.117 KVM_CLEAR_DIRTY_LOG (vm ioctl) Capability: KVM_CAP_MANUAL_DIRTY_LOG_PROTECT -Architectures: x86 +Architectures: x86, arm, arm64, mips Type: vm ioctl Parameters: struct kvm_dirty_log (in) Returns: 0 on success, -1 on error @@ -4799,7 +4799,7 @@ and injected exceptions. 7.18 KVM_CAP_MANUAL_DIRTY_LOG_PROTECT -Architectures: all +Architectures: x86, arm, arm64, mips Parameters: args[0] whether feature should be enabled or not With this capability enabled, KVM_GET_DIRTY_LOG will not automatically -- cgit v1.2.3 From b1072b4f6e845ad41de0a01fe3b3c5d5c6ac2c71 Mon Sep 17 00:00:00 2001 From: Shubhrajyoti Datta Date: Tue, 9 Apr 2019 13:15:23 +0530 Subject: dt-bindings: xilinx-uartps: Add support for cts-override Flow control is configurable in xilinx-uartps Add a dt binding to check for the same. Signed-off-by: Shubhrajyoti Datta Reviewed-by: Rob Herring Signed-off-by: Greg Kroah-Hartman --- Documentation/devicetree/bindings/serial/cdns,uart.txt | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/serial/cdns,uart.txt b/Documentation/devicetree/bindings/serial/cdns,uart.txt index 227bb770b027..4efc560f90ab 100644 --- a/Documentation/devicetree/bindings/serial/cdns,uart.txt +++ b/Documentation/devicetree/bindings/serial/cdns,uart.txt @@ -12,6 +12,11 @@ Required properties: See ../clocks/clock-bindings.txt for details. +Optional properties: +- cts-override : Override the CTS modem status signal. This signal will + always be reported as active instead of being obtained from the modem status + register. Define this if your serial port does not use this pin + Example: uart@e0000000 { compatible = "cdns,uart-r1p8"; -- cgit v1.2.3 From e5c8fe558c5fb7fe37227bacdcf857881498ebf3 Mon Sep 17 00:00:00 2001 From: Paul Walmsley Date: Fri, 12 Apr 2019 19:01:11 -0700 Subject: dt-bindings: serial: add documentation for the SiFive UART driver Add DT binding documentation for the Linux driver for the SiFive asynchronous serial IP block. This revision incorporates changes based on feedback from Rob Herring . Signed-off-by: Paul Walmsley Signed-off-by: Paul Walmsley Cc: linux-serial@vger.kernel.org Cc: devicetree@vger.kernel.org Cc: linux-riscv@lists.infradead.org Cc: linux-kernel@vger.kernel.org Cc: Greg Kroah-Hartman Cc: Mark Rutland Cc: Palmer Dabbelt Reviewed-by: Rob Herring Signed-off-by: Greg Kroah-Hartman --- .../devicetree/bindings/serial/sifive-serial.txt | 33 ++++++++++++++++++++++ 1 file changed, 33 insertions(+) create mode 100644 Documentation/devicetree/bindings/serial/sifive-serial.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/serial/sifive-serial.txt b/Documentation/devicetree/bindings/serial/sifive-serial.txt new file mode 100644 index 000000000000..c86b1e524159 --- /dev/null +++ b/Documentation/devicetree/bindings/serial/sifive-serial.txt @@ -0,0 +1,33 @@ +SiFive asynchronous serial interface (UART) + +Required properties: + +- compatible: should be something similar to + "sifive,-uart" for the UART as integrated + on a particular chip, and "sifive,uart" for the + general UART IP block programming model. Supported + compatible strings as of the date of this writing are: + "sifive,fu540-c000-uart" for the SiFive UART v0 as + integrated onto the SiFive FU540 chip, or "sifive,uart0" + for the SiFive UART v0 IP block with no chip integration + tweaks (if any) +- reg: address and length of the register space +- interrupts: Should contain the UART interrupt identifier +- clocks: Should contain a clock identifier for the UART's parent clock + + +UART HDL that corresponds to the IP block version numbers can be found +here: + +https://github.com/sifive/sifive-blocks/tree/master/src/main/scala/devices/uart + + +Example: + +uart0: serial@10010000 { + compatible = "sifive,fu540-c000-uart", "sifive,uart0"; + interrupt-parent = <&plic0>; + interrupts = <80>; + reg = <0x0 0x10010000 0x0 0x1000>; + clocks = <&prci PRCI_CLK_TLCLK>; +}; -- cgit v1.2.3 From f52e30ebfd6290343074a7a655b1bad3556f8b6f Mon Sep 17 00:00:00 2001 From: Clément Péron Date: Tue, 9 Apr 2019 18:05:50 +0200 Subject: dt-bindings: mfd: axp20x: Add fallback for axp805 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit axp805 is actually compatible and used with axp806 as fallback. But it's actually undocumented and trig a warning with checkpatch. DT compatible string "x-powers,axp805" appears un-documented. Add this compatible in the dt-bindings documentation. Signed-off-by: Clément Péron Signed-off-by: Rob Herring --- Documentation/devicetree/bindings/mfd/axp20x.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mfd/axp20x.txt b/Documentation/devicetree/bindings/mfd/axp20x.txt index 2af4ff95d6bc..4991a6415796 100644 --- a/Documentation/devicetree/bindings/mfd/axp20x.txt +++ b/Documentation/devicetree/bindings/mfd/axp20x.txt @@ -25,6 +25,7 @@ Required properties: * "x-powers,axp223" * "x-powers,axp803" * "x-powers,axp806" + * "x-powers,axp805", "x-powers,axp806" * "x-powers,axp809" * "x-powers,axp813" - reg: The I2C slave address or RSB hardware address for the AXP chip -- cgit v1.2.3 From a6c6cb2e8bdf5abe53656c9d625fc3b7974432ff Mon Sep 17 00:00:00 2001 From: Paul Walmsley Date: Thu, 11 Apr 2019 01:27:34 -0700 Subject: dt-bindings: clk: add documentation for the SiFive PRCI driver Add DT binding documentation for the Linux driver for the SiFive PRCI clock & reset control IP block, as found on the SiFive FU540 chip. This version includes changes requested by Stephen Boyd and Rob Herring , and fixes some errors in the initial version. Signed-off-by: Paul Walmsley Signed-off-by: Paul Walmsley Cc: Michael Turquette Cc: Stephen Boyd Cc: Rob Herring Cc: Mark Rutland Cc: Palmer Dabbelt Cc: Megan Wachs Cc: linux-clk@vger.kernel.org Cc: devicetree@vger.kernel.org Cc: linux-riscv@lists.infradead.org Cc: linux-kernel@vger.kernel.org Reviewed-by: Rob Herring Signed-off-by: Stephen Boyd --- .../bindings/clock/sifive/fu540-prci.txt | 46 ++++++++++++++++++++++ 1 file changed, 46 insertions(+) create mode 100644 Documentation/devicetree/bindings/clock/sifive/fu540-prci.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/clock/sifive/fu540-prci.txt b/Documentation/devicetree/bindings/clock/sifive/fu540-prci.txt new file mode 100644 index 000000000000..349808f4fb8c --- /dev/null +++ b/Documentation/devicetree/bindings/clock/sifive/fu540-prci.txt @@ -0,0 +1,46 @@ +SiFive FU540 PRCI bindings + +On the FU540 family of SoCs, most system-wide clock and reset integration +is via the PRCI IP block. + +Required properties: +- compatible: Should be "sifive,-prci". Only one value is + supported: "sifive,fu540-c000-prci" +- reg: Should describe the PRCI's register target physical address region +- clocks: Should point to the hfclk device tree node and the rtcclk + device tree node. The RTC clock here is not a time-of-day clock, + but is instead a high-stability clock source for system timers + and cycle counters. +- #clock-cells: Should be <1> + +The clock consumer should specify the desired clock via the clock ID +macros defined in include/dt-bindings/clock/sifive-fu540-prci.h. +These macros begin with PRCI_CLK_. + +The hfclk and rtcclk nodes are required, and represent physical +crystals or resonators located on the PCB. These nodes should be present +underneath /, rather than /soc. + +Examples: + +/* under /, in PCB-specific DT data */ +hfclk: hfclk { + #clock-cells = <0>; + compatible = "fixed-clock"; + clock-frequency = <33333333>; + clock-output-names = "hfclk"; +}; +rtcclk: rtcclk { + #clock-cells = <0>; + compatible = "fixed-clock"; + clock-frequency = <1000000>; + clock-output-names = "rtcclk"; +}; + +/* under /soc, in SoC-specific DT data */ +prci: clock-controller@10000000 { + compatible = "sifive,fu540-c000-prci"; + reg = <0x0 0x10000000 0x0 0x1000>; + clocks = <&hfclk>, <&rtcclk>; + #clock-cells = <1>; +}; -- cgit v1.2.3 From 083284961ad0015ad8ec9cc3739f2856d2d7fae8 Mon Sep 17 00:00:00 2001 From: Patrick Venture Date: Tue, 16 Apr 2019 08:41:38 -0700 Subject: dt-bindings: Add ir38064 as a trivial device The ir38064 is a voltage regulator from Infineon. Signed-off-by: Patrick Venture Acked-by: Guenter Roeck Signed-off-by: Rob Herring --- Documentation/devicetree/bindings/trivial-devices.yaml | 2 ++ 1 file changed, 2 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/trivial-devices.yaml b/Documentation/devicetree/bindings/trivial-devices.yaml index d79fb22bde39..92184ef0db2e 100644 --- a/Documentation/devicetree/bindings/trivial-devices.yaml +++ b/Documentation/devicetree/bindings/trivial-devices.yaml @@ -92,6 +92,8 @@ properties: - fsl,sgtl5000 # G751: Digital Temperature Sensor and Thermal Watchdog with Two-Wire Interface - gmt,g751 + # Infineon IR38064 Voltage Regulator + - infineon,ir38064 # Infineon SLB9635 (Soft-) I2C TPM (old protocol, max 100khz) - infineon,slb9635tt # Infineon SLB9645 I2C TPM (new protocol, max 400khz) -- cgit v1.2.3 From 57ddd16b111ba865cab2fa6188f72adb54332b1e Mon Sep 17 00:00:00 2001 From: Patrick Venture Date: Tue, 16 Apr 2019 08:41:47 -0700 Subject: dt-bindings: Add isl68137 as a trivial device The isl68137 is a digital output 7-phrase configurable PWM controller with an AVSBus interface from Intersil. Signed-off-by: Patrick Venture Acked-by: Guenter Roeck Signed-off-by: Rob Herring --- Documentation/devicetree/bindings/trivial-devices.yaml | 2 ++ 1 file changed, 2 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/trivial-devices.yaml b/Documentation/devicetree/bindings/trivial-devices.yaml index 92184ef0db2e..747fd3f689dc 100644 --- a/Documentation/devicetree/bindings/trivial-devices.yaml +++ b/Documentation/devicetree/bindings/trivial-devices.yaml @@ -104,6 +104,8 @@ properties: - isil,isl29028 # Intersil ISL29030 Ambient Light and Proximity Sensor - isil,isl29030 + # Intersil ISL68137 Digital Output Configurable PWM Controller + - isil,isl68137 # 5 Bit Programmable, Pulse-Width Modulator - maxim,ds1050 # Low-Power, 4-/12-Channel, 2-Wire Serial, 12-Bit ADCs -- cgit v1.2.3 From 13bda2d07791d0093728aed7698e76d2977e7639 Mon Sep 17 00:00:00 2001 From: Luca Weiss Date: Mon, 29 Apr 2019 23:56:09 -0700 Subject: Input: add a driver for GPIO controllable vibrators Provide a simple driver for GPIO controllable vibrators. It will be used by the Fairphone 2. Signed-off-by: Luca Weiss Reviewed-by: Rob Herring Signed-off-by: Dmitry Torokhov --- .../devicetree/bindings/input/gpio-vibrator.yaml | 37 ++++ drivers/input/misc/Kconfig | 12 ++ drivers/input/misc/Makefile | 1 + drivers/input/misc/gpio-vibra.c | 207 +++++++++++++++++++++ 4 files changed, 257 insertions(+) create mode 100644 Documentation/devicetree/bindings/input/gpio-vibrator.yaml create mode 100644 drivers/input/misc/gpio-vibra.c (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/input/gpio-vibrator.yaml b/Documentation/devicetree/bindings/input/gpio-vibrator.yaml new file mode 100644 index 000000000000..903475f52dbd --- /dev/null +++ b/Documentation/devicetree/bindings/input/gpio-vibrator.yaml @@ -0,0 +1,37 @@ +# SPDX-License-Identifier: GPL-2.0 +%YAML 1.2 +--- +$id: http://devicetree.org/schemas/bindings/input/gpio-vibrator.yaml# +$schema: http://devicetree.org/meta-schemas/core.yaml# + +title: GPIO vibrator + +maintainers: + - Luca Weiss + +description: |+ + Registers a GPIO device as vibrator, where the on/off capability is controlled by a GPIO. + +properties: + compatible: + const: gpio-vibrator + + enable-gpios: + maxItems: 1 + + vcc-supply: + description: Regulator that provides power + +required: + - compatible + - enable-gpios + +examples: + - | + #include + + vibrator { + compatible = "gpio-vibrator"; + enable-gpios = <&msmgpio 86 GPIO_ACTIVE_HIGH>; + vcc-supply = <&pm8941_l18>; + }; diff --git a/drivers/input/misc/Kconfig b/drivers/input/misc/Kconfig index e39aef84f357..16f41eece6d2 100644 --- a/drivers/input/misc/Kconfig +++ b/drivers/input/misc/Kconfig @@ -290,6 +290,18 @@ config INPUT_GPIO_DECODER To compile this driver as a module, choose M here: the module will be called gpio_decoder. +config INPUT_GPIO_VIBRA + tristate "GPIO vibrator support" + depends on GPIOLIB || COMPILE_TEST + select INPUT_FF_MEMLESS + help + Say Y here to get support for GPIO based vibrator devices. + + If unsure, say N. + + To compile this driver as a module, choose M here: the module will be + called gpio-vibra. + config INPUT_IXP4XX_BEEPER tristate "IXP4XX Beeper support" depends on ARCH_IXP4XX diff --git a/drivers/input/misc/Makefile b/drivers/input/misc/Makefile index 96a6419cb1f2..d871991c2eee 100644 --- a/drivers/input/misc/Makefile +++ b/drivers/input/misc/Makefile @@ -36,6 +36,7 @@ obj-$(CONFIG_INPUT_DRV2667_HAPTICS) += drv2667.o obj-$(CONFIG_INPUT_GP2A) += gp2ap002a00f.o obj-$(CONFIG_INPUT_GPIO_BEEPER) += gpio-beeper.o obj-$(CONFIG_INPUT_GPIO_DECODER) += gpio_decoder.o +obj-$(CONFIG_INPUT_GPIO_VIBRA) += gpio-vibra.o obj-$(CONFIG_INPUT_HISI_POWERKEY) += hisi_powerkey.o obj-$(CONFIG_HP_SDC_RTC) += hp_sdc_rtc.o obj-$(CONFIG_INPUT_IMS_PCU) += ims-pcu.o diff --git a/drivers/input/misc/gpio-vibra.c b/drivers/input/misc/gpio-vibra.c new file mode 100644 index 000000000000..f79f75595dd7 --- /dev/null +++ b/drivers/input/misc/gpio-vibra.c @@ -0,0 +1,207 @@ +// SPDX-License-Identifier: GPL-2.0+ +/* + * GPIO vibrator driver + * + * Copyright (C) 2019 Luca Weiss + * + * Based on PWM vibrator driver: + * Copyright (C) 2017 Collabora Ltd. + * + * Based on previous work from: + * Copyright (C) 2012 Dmitry Torokhov + * + * Based on PWM beeper driver: + * Copyright (C) 2010, Lars-Peter Clausen + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include + +struct gpio_vibrator { + struct input_dev *input; + struct gpio_desc *gpio; + struct regulator *vcc; + + struct work_struct play_work; + bool running; + bool vcc_on; +}; + +static int gpio_vibrator_start(struct gpio_vibrator *vibrator) +{ + struct device *pdev = vibrator->input->dev.parent; + int err; + + if (!vibrator->vcc_on) { + err = regulator_enable(vibrator->vcc); + if (err) { + dev_err(pdev, "failed to enable regulator: %d\n", err); + return err; + } + vibrator->vcc_on = true; + } + + gpiod_set_value_cansleep(vibrator->gpio, 1); + + return 0; +} + +static void gpio_vibrator_stop(struct gpio_vibrator *vibrator) +{ + gpiod_set_value_cansleep(vibrator->gpio, 0); + + if (vibrator->vcc_on) { + regulator_disable(vibrator->vcc); + vibrator->vcc_on = false; + } +} + +static void gpio_vibrator_play_work(struct work_struct *work) +{ + struct gpio_vibrator *vibrator = + container_of(work, struct gpio_vibrator, play_work); + + if (vibrator->running) + gpio_vibrator_start(vibrator); + else + gpio_vibrator_stop(vibrator); +} + +static int gpio_vibrator_play_effect(struct input_dev *dev, void *data, + struct ff_effect *effect) +{ + struct gpio_vibrator *vibrator = input_get_drvdata(dev); + int level; + + level = effect->u.rumble.strong_magnitude; + if (!level) + level = effect->u.rumble.weak_magnitude; + + vibrator->running = level; + schedule_work(&vibrator->play_work); + + return 0; +} + +static void gpio_vibrator_close(struct input_dev *input) +{ + struct gpio_vibrator *vibrator = input_get_drvdata(input); + + cancel_work_sync(&vibrator->play_work); + gpio_vibrator_stop(vibrator); + vibrator->running = false; +} + +static int gpio_vibrator_probe(struct platform_device *pdev) +{ + struct gpio_vibrator *vibrator; + int err; + + vibrator = devm_kzalloc(&pdev->dev, sizeof(*vibrator), GFP_KERNEL); + if (!vibrator) + return -ENOMEM; + + vibrator->input = devm_input_allocate_device(&pdev->dev); + if (!vibrator->input) + return -ENOMEM; + + vibrator->vcc = devm_regulator_get(&pdev->dev, "vcc"); + err = PTR_ERR_OR_ZERO(vibrator->vcc); + if (err) { + if (err != -EPROBE_DEFER) + dev_err(&pdev->dev, "Failed to request regulator: %d\n", + err); + return err; + } + + vibrator->gpio = devm_gpiod_get(&pdev->dev, "enable", GPIOD_OUT_LOW); + err = PTR_ERR_OR_ZERO(vibrator->gpio); + if (err) { + if (err != -EPROBE_DEFER) + dev_err(&pdev->dev, "Failed to request main gpio: %d\n", + err); + return err; + } + + INIT_WORK(&vibrator->play_work, gpio_vibrator_play_work); + + vibrator->input->name = "gpio-vibrator"; + vibrator->input->id.bustype = BUS_HOST; + vibrator->input->close = gpio_vibrator_close; + + input_set_drvdata(vibrator->input, vibrator); + input_set_capability(vibrator->input, EV_FF, FF_RUMBLE); + + err = input_ff_create_memless(vibrator->input, NULL, + gpio_vibrator_play_effect); + if (err) { + dev_err(&pdev->dev, "Couldn't create FF dev: %d\n", err); + return err; + } + + err = input_register_device(vibrator->input); + if (err) { + dev_err(&pdev->dev, "Couldn't register input dev: %d\n", err); + return err; + } + + platform_set_drvdata(pdev, vibrator); + + return 0; +} + +static int __maybe_unused gpio_vibrator_suspend(struct device *dev) +{ + struct platform_device *pdev = to_platform_device(dev); + struct gpio_vibrator *vibrator = platform_get_drvdata(pdev); + + cancel_work_sync(&vibrator->play_work); + if (vibrator->running) + gpio_vibrator_stop(vibrator); + + return 0; +} + +static int __maybe_unused gpio_vibrator_resume(struct device *dev) +{ + struct platform_device *pdev = to_platform_device(dev); + struct gpio_vibrator *vibrator = platform_get_drvdata(pdev); + + if (vibrator->running) + gpio_vibrator_start(vibrator); + + return 0; +} + +static SIMPLE_DEV_PM_OPS(gpio_vibrator_pm_ops, + gpio_vibrator_suspend, gpio_vibrator_resume); + +#ifdef CONFIG_OF +static const struct of_device_id gpio_vibra_dt_match_table[] = { + { .compatible = "gpio-vibrator" }, + {} +}; +MODULE_DEVICE_TABLE(of, gpio_vibra_dt_match_table); +#endif + +static struct platform_driver gpio_vibrator_driver = { + .probe = gpio_vibrator_probe, + .driver = { + .name = "gpio-vibrator", + .pm = &gpio_vibrator_pm_ops, + .of_match_table = of_match_ptr(gpio_vibra_dt_match_table), + }, +}; +module_platform_driver(gpio_vibrator_driver); + +MODULE_AUTHOR("Luca Weiss "); +MODULE_DESCRIPTION("GPIO vibrator driver"); +MODULE_LICENSE("GPL"); +MODULE_ALIAS("platform:gpio-vibrator"); -- cgit v1.2.3 From 7b5bb55d0dad859ee5bb41b1664e2ac577378c38 Mon Sep 17 00:00:00 2001 From: Jeff LaBundy Date: Tue, 30 Apr 2019 00:16:11 -0700 Subject: Input: add support for Azoteq IQS550/572/525 This patch adds support for the Azoteq IQS550/572/525 family of trackpad/touchscreen controllers. The driver has been tested with an IQS550EV02 evaluation board. A demonstration of the driver's capabilities is available here: https://youtu.be/sRNNx4XZBts Signed-off-by: Jeff LaBundy Reviewed-by: Rob Herring Signed-off-by: Dmitry Torokhov --- .../bindings/input/touchscreen/iqs5xx.txt | 80 ++ .../devicetree/bindings/vendor-prefixes.txt | 1 + drivers/input/touchscreen/Kconfig | 10 + drivers/input/touchscreen/Makefile | 1 + drivers/input/touchscreen/iqs5xx.c | 1133 ++++++++++++++++++++ 5 files changed, 1225 insertions(+) create mode 100644 Documentation/devicetree/bindings/input/touchscreen/iqs5xx.txt create mode 100644 drivers/input/touchscreen/iqs5xx.c (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/input/touchscreen/iqs5xx.txt b/Documentation/devicetree/bindings/input/touchscreen/iqs5xx.txt new file mode 100644 index 000000000000..efa0820e2469 --- /dev/null +++ b/Documentation/devicetree/bindings/input/touchscreen/iqs5xx.txt @@ -0,0 +1,80 @@ +Azoteq IQS550/572/525 Trackpad/Touchscreen Controller + +Required properties: + +- compatible : Must be equal to one of the following: + "azoteq,iqs550" + "azoteq,iqs572" + "azoteq,iqs525" + +- reg : I2C slave address for the device. + +- interrupts : GPIO to which the device's active-high RDY + output is connected (see [0]). + +- reset-gpios : GPIO to which the device's active-low NRST + input is connected (see [1]). + +Optional properties: + +- touchscreen-min-x : See [2]. + +- touchscreen-min-y : See [2]. + +- touchscreen-size-x : See [2]. If this property is omitted, the + maximum x-coordinate is specified by the + device's "X Resolution" register. + +- touchscreen-size-y : See [2]. If this property is omitted, the + maximum y-coordinate is specified by the + device's "Y Resolution" register. + +- touchscreen-max-pressure : See [2]. Pressure is expressed as the sum of + the deltas across all channels impacted by a + touch event. A channel's delta is calculated + as its count value minus a reference, where + the count value is inversely proportional to + the channel's capacitance. + +- touchscreen-fuzz-x : See [2]. + +- touchscreen-fuzz-y : See [2]. + +- touchscreen-fuzz-pressure : See [2]. + +- touchscreen-inverted-x : See [2]. Inversion is applied relative to that + which may already be specified by the device's + FLIP_X and FLIP_Y register fields. + +- touchscreen-inverted-y : See [2]. Inversion is applied relative to that + which may already be specified by the device's + FLIP_X and FLIP_Y register fields. + +- touchscreen-swapped-x-y : See [2]. Swapping is applied relative to that + which may already be specified by the device's + SWITCH_XY_AXIS register field. + +[0]: Documentation/devicetree/bindings/interrupt-controller/interrupts.txt +[1]: Documentation/devicetree/bindings/gpio/gpio.txt +[2]: Documentation/devicetree/bindings/input/touchscreen/touchscreen.txt + +Example: + + &i2c1 { + /* ... */ + + touchscreen@74 { + compatible = "azoteq,iqs550"; + reg = <0x74>; + interrupt-parent = <&gpio>; + interrupts = <17 4>; + reset-gpios = <&gpio 27 1>; + + touchscreen-size-x = <640>; + touchscreen-size-y = <480>; + + touchscreen-max-pressure = <16000>; + }; + + /* ... */ + }; diff --git a/Documentation/devicetree/bindings/vendor-prefixes.txt b/Documentation/devicetree/bindings/vendor-prefixes.txt index 4b1a2a8fcc16..51f99549161e 100644 --- a/Documentation/devicetree/bindings/vendor-prefixes.txt +++ b/Documentation/devicetree/bindings/vendor-prefixes.txt @@ -53,6 +53,7 @@ avic Shanghai AVIC Optoelectronics Co., Ltd. avnet Avnet, Inc. axentia Axentia Technologies AB axis Axis Communications AB +azoteq Azoteq (Pty) Ltd bananapi BIPAI KEJI LIMITED bhf Beckhoff Automation GmbH & Co. KG bitmain Bitmain Technologies diff --git a/drivers/input/touchscreen/Kconfig b/drivers/input/touchscreen/Kconfig index 6c16aaeb4191..d8337ed50af4 100644 --- a/drivers/input/touchscreen/Kconfig +++ b/drivers/input/touchscreen/Kconfig @@ -1311,4 +1311,14 @@ config TOUCHSCREEN_ROHM_BU21023 To compile this driver as a module, choose M here: the module will be called bu21023_ts. +config TOUCHSCREEN_IQS5XX + tristate "Azoteq IQS550/572/525 trackpad/touchscreen controller" + depends on I2C + help + Say Y to enable support for the Azoteq IQS550/572/525 + family of trackpad/touchscreen controllers. + + To compile this driver as a module, choose M here: the + module will be called iqs5xx. + endif diff --git a/drivers/input/touchscreen/Makefile b/drivers/input/touchscreen/Makefile index fcc7605fba8d..084a596a0c8b 100644 --- a/drivers/input/touchscreen/Makefile +++ b/drivers/input/touchscreen/Makefile @@ -110,3 +110,4 @@ obj-$(CONFIG_TOUCHSCREEN_ZFORCE) += zforce_ts.o obj-$(CONFIG_TOUCHSCREEN_COLIBRI_VF50) += colibri-vf50-ts.o obj-$(CONFIG_TOUCHSCREEN_ROHM_BU21023) += rohm_bu21023.o obj-$(CONFIG_TOUCHSCREEN_RASPBERRYPI_FW) += raspberrypi-ts.o +obj-$(CONFIG_TOUCHSCREEN_IQS5XX) += iqs5xx.o diff --git a/drivers/input/touchscreen/iqs5xx.c b/drivers/input/touchscreen/iqs5xx.c new file mode 100644 index 000000000000..b832fe062645 --- /dev/null +++ b/drivers/input/touchscreen/iqs5xx.c @@ -0,0 +1,1133 @@ +// SPDX-License-Identifier: GPL-2.0+ +/* + * Azoteq IQS550/572/525 Trackpad/Touchscreen Controller + * + * Copyright (C) 2018 + * Author: Jeff LaBundy + * + * These devices require firmware exported from a PC-based configuration tool + * made available by the vendor. Firmware files may be pushed to the device's + * nonvolatile memory by writing the filename to the 'fw_file' sysfs control. + * + * Link to PC-based configuration tool and data sheet: http://www.azoteq.com/ + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#define IQS5XX_FW_FILE_LEN 64 +#define IQS5XX_NUM_RETRIES 10 +#define IQS5XX_NUM_POINTS 256 +#define IQS5XX_NUM_CONTACTS 5 +#define IQS5XX_WR_BYTES_MAX 2 + +#define IQS5XX_PROD_NUM_IQS550 40 +#define IQS5XX_PROD_NUM_IQS572 58 +#define IQS5XX_PROD_NUM_IQS525 52 +#define IQS5XX_PROJ_NUM_A000 0 +#define IQS5XX_PROJ_NUM_B000 15 +#define IQS5XX_MAJOR_VER_MIN 2 + +#define IQS5XX_RESUME 0x00 +#define IQS5XX_SUSPEND 0x01 + +#define IQS5XX_SW_INPUT_EVENT 0x10 +#define IQS5XX_SETUP_COMPLETE 0x40 +#define IQS5XX_EVENT_MODE 0x01 +#define IQS5XX_TP_EVENT 0x04 + +#define IQS5XX_FLIP_X 0x01 +#define IQS5XX_FLIP_Y 0x02 +#define IQS5XX_SWITCH_XY_AXIS 0x04 + +#define IQS5XX_PROD_NUM 0x0000 +#define IQS5XX_ABS_X 0x0016 +#define IQS5XX_ABS_Y 0x0018 +#define IQS5XX_SYS_CTRL0 0x0431 +#define IQS5XX_SYS_CTRL1 0x0432 +#define IQS5XX_SYS_CFG0 0x058E +#define IQS5XX_SYS_CFG1 0x058F +#define IQS5XX_TOTAL_RX 0x063D +#define IQS5XX_TOTAL_TX 0x063E +#define IQS5XX_XY_CFG0 0x0669 +#define IQS5XX_X_RES 0x066E +#define IQS5XX_Y_RES 0x0670 +#define IQS5XX_CHKSM 0x83C0 +#define IQS5XX_APP 0x8400 +#define IQS5XX_CSTM 0xBE00 +#define IQS5XX_PMAP_END 0xBFFF +#define IQS5XX_END_COMM 0xEEEE + +#define IQS5XX_CHKSM_LEN (IQS5XX_APP - IQS5XX_CHKSM) +#define IQS5XX_APP_LEN (IQS5XX_CSTM - IQS5XX_APP) +#define IQS5XX_CSTM_LEN (IQS5XX_PMAP_END + 1 - IQS5XX_CSTM) +#define IQS5XX_PMAP_LEN (IQS5XX_PMAP_END + 1 - IQS5XX_CHKSM) + +#define IQS5XX_REC_HDR_LEN 4 +#define IQS5XX_REC_LEN_MAX 255 +#define IQS5XX_REC_TYPE_DATA 0x00 +#define IQS5XX_REC_TYPE_EOF 0x01 + +#define IQS5XX_BL_ADDR_MASK 0x40 +#define IQS5XX_BL_CMD_VER 0x00 +#define IQS5XX_BL_CMD_READ 0x01 +#define IQS5XX_BL_CMD_EXEC 0x02 +#define IQS5XX_BL_CMD_CRC 0x03 +#define IQS5XX_BL_BLK_LEN_MAX 64 +#define IQS5XX_BL_ID 0x0200 +#define IQS5XX_BL_STATUS_RESET 0x00 +#define IQS5XX_BL_STATUS_AVAIL 0xA5 +#define IQS5XX_BL_STATUS_NONE 0xEE +#define IQS5XX_BL_CRC_PASS 0x00 +#define IQS5XX_BL_CRC_FAIL 0x01 +#define IQS5XX_BL_ATTEMPTS 3 + +struct iqs5xx_private { + struct i2c_client *client; + struct input_dev *input; + struct gpio_desc *reset_gpio; + struct mutex lock; + u8 bl_status; +}; + +struct iqs5xx_dev_id_info { + __be16 prod_num; + __be16 proj_num; + u8 major_ver; + u8 minor_ver; + u8 bl_status; +} __packed; + +struct iqs5xx_ihex_rec { + char start; + char len[2]; + char addr[4]; + char type[2]; + char data[2]; +} __packed; + +struct iqs5xx_touch_data { + __be16 abs_x; + __be16 abs_y; + __be16 strength; + u8 area; +} __packed; + +static int iqs5xx_read_burst(struct i2c_client *client, + u16 reg, void *val, u16 len) +{ + __be16 reg_buf = cpu_to_be16(reg); + int ret, i; + struct i2c_msg msg[] = { + { + .addr = client->addr, + .flags = 0, + .len = sizeof(reg_buf), + .buf = (u8 *)®_buf, + }, + { + .addr = client->addr, + .flags = I2C_M_RD, + .len = len, + .buf = (u8 *)val, + }, + }; + + /* + * The first addressing attempt outside of a communication window fails + * and must be retried, after which the device clock stretches until it + * is available. + */ + for (i = 0; i < IQS5XX_NUM_RETRIES; i++) { + ret = i2c_transfer(client->adapter, msg, ARRAY_SIZE(msg)); + if (ret == ARRAY_SIZE(msg)) + return 0; + + usleep_range(200, 300); + } + + if (ret >= 0) + ret = -EIO; + + dev_err(&client->dev, "Failed to read from address 0x%04X: %d\n", + reg, ret); + + return ret; +} + +static int iqs5xx_read_word(struct i2c_client *client, u16 reg, u16 *val) +{ + __be16 val_buf; + int error; + + error = iqs5xx_read_burst(client, reg, &val_buf, sizeof(val_buf)); + if (error) + return error; + + *val = be16_to_cpu(val_buf); + + return 0; +} + +static int iqs5xx_read_byte(struct i2c_client *client, u16 reg, u8 *val) +{ + return iqs5xx_read_burst(client, reg, val, sizeof(*val)); +} + +static int iqs5xx_write_burst(struct i2c_client *client, + u16 reg, const void *val, u16 len) +{ + int ret, i; + u16 mlen = sizeof(reg) + len; + u8 mbuf[sizeof(reg) + IQS5XX_WR_BYTES_MAX]; + + if (len > IQS5XX_WR_BYTES_MAX) + return -EINVAL; + + put_unaligned_be16(reg, mbuf); + memcpy(mbuf + sizeof(reg), val, len); + + /* + * The first addressing attempt outside of a communication window fails + * and must be retried, after which the device clock stretches until it + * is available. + */ + for (i = 0; i < IQS5XX_NUM_RETRIES; i++) { + ret = i2c_master_send(client, mbuf, mlen); + if (ret == mlen) + return 0; + + usleep_range(200, 300); + } + + if (ret >= 0) + ret = -EIO; + + dev_err(&client->dev, "Failed to write to address 0x%04X: %d\n", + reg, ret); + + return ret; +} + +static int iqs5xx_write_word(struct i2c_client *client, u16 reg, u16 val) +{ + __be16 val_buf = cpu_to_be16(val); + + return iqs5xx_write_burst(client, reg, &val_buf, sizeof(val_buf)); +} + +static int iqs5xx_write_byte(struct i2c_client *client, u16 reg, u8 val) +{ + return iqs5xx_write_burst(client, reg, &val, sizeof(val)); +} + +static void iqs5xx_reset(struct i2c_client *client) +{ + struct iqs5xx_private *iqs5xx = i2c_get_clientdata(client); + + gpiod_set_value_cansleep(iqs5xx->reset_gpio, 1); + usleep_range(200, 300); + + gpiod_set_value_cansleep(iqs5xx->reset_gpio, 0); +} + +static int iqs5xx_bl_cmd(struct i2c_client *client, u8 bl_cmd, u16 bl_addr) +{ + struct i2c_msg msg; + int ret; + u8 mbuf[sizeof(bl_cmd) + sizeof(bl_addr)]; + + msg.addr = client->addr ^ IQS5XX_BL_ADDR_MASK; + msg.flags = 0; + msg.len = sizeof(bl_cmd); + msg.buf = mbuf; + + *mbuf = bl_cmd; + + switch (bl_cmd) { + case IQS5XX_BL_CMD_VER: + case IQS5XX_BL_CMD_CRC: + case IQS5XX_BL_CMD_EXEC: + break; + case IQS5XX_BL_CMD_READ: + msg.len += sizeof(bl_addr); + put_unaligned_be16(bl_addr, mbuf + sizeof(bl_cmd)); + break; + default: + return -EINVAL; + } + + ret = i2c_transfer(client->adapter, &msg, 1); + if (ret != 1) + goto msg_fail; + + switch (bl_cmd) { + case IQS5XX_BL_CMD_VER: + msg.len = sizeof(u16); + break; + case IQS5XX_BL_CMD_CRC: + msg.len = sizeof(u8); + /* + * This delay saves the bus controller the trouble of having to + * tolerate a relatively long clock-stretching period while the + * CRC is calculated. + */ + msleep(50); + break; + case IQS5XX_BL_CMD_EXEC: + usleep_range(10000, 10100); + /* fall through */ + default: + return 0; + } + + msg.flags = I2C_M_RD; + + ret = i2c_transfer(client->adapter, &msg, 1); + if (ret != 1) + goto msg_fail; + + if (bl_cmd == IQS5XX_BL_CMD_VER && + get_unaligned_be16(mbuf) != IQS5XX_BL_ID) { + dev_err(&client->dev, "Unrecognized bootloader ID: 0x%04X\n", + get_unaligned_be16(mbuf)); + return -EINVAL; + } + + if (bl_cmd == IQS5XX_BL_CMD_CRC && *mbuf != IQS5XX_BL_CRC_PASS) { + dev_err(&client->dev, "Bootloader CRC failed\n"); + return -EIO; + } + + return 0; + +msg_fail: + if (ret >= 0) + ret = -EIO; + + if (bl_cmd != IQS5XX_BL_CMD_VER) + dev_err(&client->dev, + "Unsuccessful bootloader command 0x%02X: %d\n", + bl_cmd, ret); + + return ret; +} + +static int iqs5xx_bl_open(struct i2c_client *client) +{ + int error, i, j; + + /* + * The device opens a bootloader polling window for 2 ms following the + * release of reset. If the host cannot establish communication during + * this time frame, it must cycle reset again. + */ + for (i = 0; i < IQS5XX_BL_ATTEMPTS; i++) { + iqs5xx_reset(client); + + for (j = 0; j < IQS5XX_NUM_RETRIES; j++) { + error = iqs5xx_bl_cmd(client, IQS5XX_BL_CMD_VER, 0); + if (!error || error == -EINVAL) + return error; + } + } + + dev_err(&client->dev, "Failed to open bootloader: %d\n", error); + + return error; +} + +static int iqs5xx_bl_write(struct i2c_client *client, + u16 bl_addr, u8 *pmap_data, u16 pmap_len) +{ + struct i2c_msg msg; + int ret, i; + u8 mbuf[sizeof(bl_addr) + IQS5XX_BL_BLK_LEN_MAX]; + + if (pmap_len % IQS5XX_BL_BLK_LEN_MAX) + return -EINVAL; + + msg.addr = client->addr ^ IQS5XX_BL_ADDR_MASK; + msg.flags = 0; + msg.len = sizeof(mbuf); + msg.buf = mbuf; + + for (i = 0; i < pmap_len; i += IQS5XX_BL_BLK_LEN_MAX) { + put_unaligned_be16(bl_addr + i, mbuf); + memcpy(mbuf + sizeof(bl_addr), pmap_data + i, + sizeof(mbuf) - sizeof(bl_addr)); + + ret = i2c_transfer(client->adapter, &msg, 1); + if (ret != 1) + goto msg_fail; + + usleep_range(10000, 10100); + } + + return 0; + +msg_fail: + if (ret >= 0) + ret = -EIO; + + dev_err(&client->dev, "Failed to write block at address 0x%04X: %d\n", + bl_addr + i, ret); + + return ret; +} + +static int iqs5xx_bl_verify(struct i2c_client *client, + u16 bl_addr, u8 *pmap_data, u16 pmap_len) +{ + struct i2c_msg msg; + int ret, i; + u8 bl_data[IQS5XX_BL_BLK_LEN_MAX]; + + if (pmap_len % IQS5XX_BL_BLK_LEN_MAX) + return -EINVAL; + + msg.addr = client->addr ^ IQS5XX_BL_ADDR_MASK; + msg.flags = I2C_M_RD; + msg.len = sizeof(bl_data); + msg.buf = bl_data; + + for (i = 0; i < pmap_len; i += IQS5XX_BL_BLK_LEN_MAX) { + ret = iqs5xx_bl_cmd(client, IQS5XX_BL_CMD_READ, bl_addr + i); + if (ret) + return ret; + + ret = i2c_transfer(client->adapter, &msg, 1); + if (ret != 1) + goto msg_fail; + + if (memcmp(bl_data, pmap_data + i, sizeof(bl_data))) { + dev_err(&client->dev, + "Failed to verify block at address 0x%04X\n", + bl_addr + i); + return -EIO; + } + } + + return 0; + +msg_fail: + if (ret >= 0) + ret = -EIO; + + dev_err(&client->dev, "Failed to read block at address 0x%04X: %d\n", + bl_addr + i, ret); + + return ret; +} + +static int iqs5xx_set_state(struct i2c_client *client, u8 state) +{ + struct iqs5xx_private *iqs5xx = i2c_get_clientdata(client); + int error1, error2; + + if (iqs5xx->bl_status == IQS5XX_BL_STATUS_RESET) + return 0; + + mutex_lock(&iqs5xx->lock); + + /* + * Addressing the device outside of a communication window prompts it + * to assert the RDY output, so disable the interrupt line to prevent + * the handler from servicing a false interrupt. + */ + disable_irq(client->irq); + + error1 = iqs5xx_write_byte(client, IQS5XX_SYS_CTRL1, state); + error2 = iqs5xx_write_byte(client, IQS5XX_END_COMM, 0); + + usleep_range(50, 100); + enable_irq(client->irq); + + mutex_unlock(&iqs5xx->lock); + + if (error1) + return error1; + + return error2; +} + +static int iqs5xx_open(struct input_dev *input) +{ + struct iqs5xx_private *iqs5xx = input_get_drvdata(input); + + return iqs5xx_set_state(iqs5xx->client, IQS5XX_RESUME); +} + +static void iqs5xx_close(struct input_dev *input) +{ + struct iqs5xx_private *iqs5xx = input_get_drvdata(input); + + iqs5xx_set_state(iqs5xx->client, IQS5XX_SUSPEND); +} + +static int iqs5xx_axis_init(struct i2c_client *client) +{ + struct iqs5xx_private *iqs5xx = i2c_get_clientdata(client); + struct touchscreen_properties prop; + struct input_dev *input; + int error; + u16 max_x, max_x_hw; + u16 max_y, max_y_hw; + u8 val; + + if (!iqs5xx->input) { + input = devm_input_allocate_device(&client->dev); + if (!input) + return -ENOMEM; + + input->name = client->name; + input->id.bustype = BUS_I2C; + input->open = iqs5xx_open; + input->close = iqs5xx_close; + + input_set_capability(input, EV_ABS, ABS_MT_POSITION_X); + input_set_capability(input, EV_ABS, ABS_MT_POSITION_Y); + input_set_capability(input, EV_ABS, ABS_MT_PRESSURE); + + error = input_mt_init_slots(input, + IQS5XX_NUM_CONTACTS, INPUT_MT_DIRECT); + if (error) { + dev_err(&client->dev, + "Failed to initialize slots: %d\n", error); + return error; + } + + input_set_drvdata(input, iqs5xx); + iqs5xx->input = input; + } + + touchscreen_parse_properties(iqs5xx->input, true, &prop); + + error = iqs5xx_read_byte(client, IQS5XX_TOTAL_RX, &val); + if (error) + return error; + max_x_hw = (val - 1) * IQS5XX_NUM_POINTS; + + error = iqs5xx_read_byte(client, IQS5XX_TOTAL_TX, &val); + if (error) + return error; + max_y_hw = (val - 1) * IQS5XX_NUM_POINTS; + + error = iqs5xx_read_byte(client, IQS5XX_XY_CFG0, &val); + if (error) + return error; + + if (val & IQS5XX_SWITCH_XY_AXIS) + swap(max_x_hw, max_y_hw); + + if (prop.swap_x_y) + val ^= IQS5XX_SWITCH_XY_AXIS; + + if (prop.invert_x) + val ^= prop.swap_x_y ? IQS5XX_FLIP_Y : IQS5XX_FLIP_X; + + if (prop.invert_y) + val ^= prop.swap_x_y ? IQS5XX_FLIP_X : IQS5XX_FLIP_Y; + + error = iqs5xx_write_byte(client, IQS5XX_XY_CFG0, val); + if (error) + return error; + + if (prop.max_x > max_x_hw) { + dev_err(&client->dev, "Invalid maximum x-coordinate: %u > %u\n", + prop.max_x, max_x_hw); + return -EINVAL; + } else if (prop.max_x == 0) { + error = iqs5xx_read_word(client, IQS5XX_X_RES, &max_x); + if (error) + return error; + + input_abs_set_max(iqs5xx->input, + prop.swap_x_y ? ABS_MT_POSITION_Y : + ABS_MT_POSITION_X, + max_x); + } else { + max_x = (u16)prop.max_x; + } + + if (prop.max_y > max_y_hw) { + dev_err(&client->dev, "Invalid maximum y-coordinate: %u > %u\n", + prop.max_y, max_y_hw); + return -EINVAL; + } else if (prop.max_y == 0) { + error = iqs5xx_read_word(client, IQS5XX_Y_RES, &max_y); + if (error) + return error; + + input_abs_set_max(iqs5xx->input, + prop.swap_x_y ? ABS_MT_POSITION_X : + ABS_MT_POSITION_Y, + max_y); + } else { + max_y = (u16)prop.max_y; + } + + /* + * Write horizontal and vertical resolution to the device in case its + * original defaults were overridden or swapped as per the properties + * specified in the device tree. + */ + error = iqs5xx_write_word(client, + prop.swap_x_y ? IQS5XX_Y_RES : IQS5XX_X_RES, + max_x); + if (error) + return error; + + return iqs5xx_write_word(client, + prop.swap_x_y ? IQS5XX_X_RES : IQS5XX_Y_RES, + max_y); +} + +static int iqs5xx_dev_init(struct i2c_client *client) +{ + struct iqs5xx_private *iqs5xx = i2c_get_clientdata(client); + struct iqs5xx_dev_id_info *dev_id_info; + int error; + u8 val; + u8 buf[sizeof(*dev_id_info) + 1]; + + error = iqs5xx_read_burst(client, IQS5XX_PROD_NUM, + &buf[1], sizeof(*dev_id_info)); + if (error) + return iqs5xx_bl_open(client); + + /* + * A000 and B000 devices use 8-bit and 16-bit addressing, respectively. + * Querying an A000 device's version information with 16-bit addressing + * gives the appearance that the data is shifted by one byte; a nonzero + * leading array element suggests this could be the case (in which case + * the missing zero is prepended). + */ + buf[0] = 0; + dev_id_info = (struct iqs5xx_dev_id_info *)&buf[(buf[1] > 0) ? 0 : 1]; + + switch (be16_to_cpu(dev_id_info->prod_num)) { + case IQS5XX_PROD_NUM_IQS550: + case IQS5XX_PROD_NUM_IQS572: + case IQS5XX_PROD_NUM_IQS525: + break; + default: + dev_err(&client->dev, "Unrecognized product number: %u\n", + be16_to_cpu(dev_id_info->prod_num)); + return -EINVAL; + } + + switch (be16_to_cpu(dev_id_info->proj_num)) { + case IQS5XX_PROJ_NUM_A000: + dev_err(&client->dev, "Unsupported project number: %u\n", + be16_to_cpu(dev_id_info->proj_num)); + return iqs5xx_bl_open(client); + case IQS5XX_PROJ_NUM_B000: + break; + default: + dev_err(&client->dev, "Unrecognized project number: %u\n", + be16_to_cpu(dev_id_info->proj_num)); + return -EINVAL; + } + + if (dev_id_info->major_ver < IQS5XX_MAJOR_VER_MIN) { + dev_err(&client->dev, "Unsupported major version: %u\n", + dev_id_info->major_ver); + return iqs5xx_bl_open(client); + } + + switch (dev_id_info->bl_status) { + case IQS5XX_BL_STATUS_AVAIL: + case IQS5XX_BL_STATUS_NONE: + break; + default: + dev_err(&client->dev, + "Unrecognized bootloader status: 0x%02X\n", + dev_id_info->bl_status); + return -EINVAL; + } + + error = iqs5xx_axis_init(client); + if (error) + return error; + + error = iqs5xx_read_byte(client, IQS5XX_SYS_CFG0, &val); + if (error) + return error; + + val |= IQS5XX_SETUP_COMPLETE; + val &= ~IQS5XX_SW_INPUT_EVENT; + error = iqs5xx_write_byte(client, IQS5XX_SYS_CFG0, val); + if (error) + return error; + + val = IQS5XX_TP_EVENT | IQS5XX_EVENT_MODE; + error = iqs5xx_write_byte(client, IQS5XX_SYS_CFG1, val); + if (error) + return error; + + error = iqs5xx_write_byte(client, IQS5XX_END_COMM, 0); + if (error) + return error; + + iqs5xx->bl_status = dev_id_info->bl_status; + + /* + * Closure of the first communication window that appears following the + * release of reset appears to kick off an initialization period during + * which further communication is met with clock stretching. The return + * from this function is delayed so that further communication attempts + * avoid this period. + */ + msleep(100); + + return 0; +} + +static irqreturn_t iqs5xx_irq(int irq, void *data) +{ + struct iqs5xx_private *iqs5xx = data; + struct iqs5xx_touch_data touch_data[IQS5XX_NUM_CONTACTS]; + struct i2c_client *client = iqs5xx->client; + struct input_dev *input = iqs5xx->input; + int error, i; + + /* + * This check is purely a precaution, as the device does not assert the + * RDY output during bootloader mode. If the device operates outside of + * bootloader mode, the input device is guaranteed to be allocated. + */ + if (iqs5xx->bl_status == IQS5XX_BL_STATUS_RESET) + return IRQ_NONE; + + error = iqs5xx_read_burst(client, IQS5XX_ABS_X, + touch_data, sizeof(touch_data)); + if (error) + return IRQ_NONE; + + for (i = 0; i < ARRAY_SIZE(touch_data); i++) { + u16 pressure = be16_to_cpu(touch_data[i].strength); + + input_mt_slot(input, i); + if (input_mt_report_slot_state(input, MT_TOOL_FINGER, + pressure != 0)) { + input_report_abs(input, ABS_MT_POSITION_X, + be16_to_cpu(touch_data[i].abs_x)); + input_report_abs(input, ABS_MT_POSITION_Y, + be16_to_cpu(touch_data[i].abs_y)); + input_report_abs(input, ABS_MT_PRESSURE, pressure); + } + } + + input_mt_sync_frame(input); + input_sync(input); + + error = iqs5xx_write_byte(client, IQS5XX_END_COMM, 0); + if (error) + return IRQ_NONE; + + /* + * Once the communication window is closed, a small delay is added to + * ensure the device's RDY output has been deasserted by the time the + * interrupt handler returns. + */ + usleep_range(50, 100); + + return IRQ_HANDLED; +} + +static int iqs5xx_fw_file_parse(struct i2c_client *client, + const char *fw_file, u8 *pmap) +{ + const struct firmware *fw; + struct iqs5xx_ihex_rec *rec; + size_t pos = 0; + int error, i; + u16 rec_num = 1; + u16 rec_addr; + u8 rec_len, rec_type, rec_chksm, chksm; + u8 rec_hdr[IQS5XX_REC_HDR_LEN]; + u8 rec_data[IQS5XX_REC_LEN_MAX]; + + /* + * Firmware exported from the vendor's configuration tool deviates from + * standard ihex as follows: (1) the checksum for records corresponding + * to user-exported settings is not recalculated, and (2) an address of + * 0xFFFF is used for the EOF record. + * + * Because the ihex2fw tool tolerates neither (1) nor (2), the slightly + * nonstandard ihex firmware is parsed directly by the driver. + */ + error = request_firmware(&fw, fw_file, &client->dev); + if (error) { + dev_err(&client->dev, "Failed to request firmware %s: %d\n", + fw_file, error); + return error; + } + + do { + if (pos + sizeof(*rec) > fw->size) { + dev_err(&client->dev, "Insufficient firmware size\n"); + error = -EINVAL; + break; + } + rec = (struct iqs5xx_ihex_rec *)(fw->data + pos); + pos += sizeof(*rec); + + if (rec->start != ':') { + dev_err(&client->dev, "Invalid start at record %u\n", + rec_num); + error = -EINVAL; + break; + } + + error = hex2bin(rec_hdr, rec->len, sizeof(rec_hdr)); + if (error) { + dev_err(&client->dev, "Invalid header at record %u\n", + rec_num); + break; + } + + rec_len = *rec_hdr; + rec_addr = get_unaligned_be16(rec_hdr + sizeof(rec_len)); + rec_type = *(rec_hdr + sizeof(rec_len) + sizeof(rec_addr)); + + if (pos + rec_len * 2 > fw->size) { + dev_err(&client->dev, "Insufficient firmware size\n"); + error = -EINVAL; + break; + } + pos += (rec_len * 2); + + error = hex2bin(rec_data, rec->data, rec_len); + if (error) { + dev_err(&client->dev, "Invalid data at record %u\n", + rec_num); + break; + } + + error = hex2bin(&rec_chksm, + rec->data + rec_len * 2, sizeof(rec_chksm)); + if (error) { + dev_err(&client->dev, "Invalid checksum at record %u\n", + rec_num); + break; + } + + chksm = 0; + for (i = 0; i < sizeof(rec_hdr); i++) + chksm += rec_hdr[i]; + for (i = 0; i < rec_len; i++) + chksm += rec_data[i]; + chksm = ~chksm + 1; + + if (chksm != rec_chksm && rec_addr < IQS5XX_CSTM) { + dev_err(&client->dev, + "Incorrect checksum at record %u\n", + rec_num); + error = -EINVAL; + break; + } + + switch (rec_type) { + case IQS5XX_REC_TYPE_DATA: + if (rec_addr < IQS5XX_CHKSM || + rec_addr > IQS5XX_PMAP_END) { + dev_err(&client->dev, + "Invalid address at record %u\n", + rec_num); + error = -EINVAL; + } else { + memcpy(pmap + rec_addr - IQS5XX_CHKSM, + rec_data, rec_len); + } + break; + case IQS5XX_REC_TYPE_EOF: + break; + default: + dev_err(&client->dev, "Invalid type at record %u\n", + rec_num); + error = -EINVAL; + } + + if (error) + break; + + rec_num++; + while (pos < fw->size) { + if (*(fw->data + pos) == ':') + break; + pos++; + } + } while (rec_type != IQS5XX_REC_TYPE_EOF); + + release_firmware(fw); + + return error; +} + +static int iqs5xx_fw_file_write(struct i2c_client *client, const char *fw_file) +{ + struct iqs5xx_private *iqs5xx = i2c_get_clientdata(client); + int error; + u8 *pmap; + + if (iqs5xx->bl_status == IQS5XX_BL_STATUS_NONE) + return -EPERM; + + pmap = kzalloc(IQS5XX_PMAP_LEN, GFP_KERNEL); + if (!pmap) + return -ENOMEM; + + error = iqs5xx_fw_file_parse(client, fw_file, pmap); + if (error) + goto err_kfree; + + mutex_lock(&iqs5xx->lock); + + /* + * Disable the interrupt line in case the first attempt(s) to enter the + * bootloader don't happen quickly enough, in which case the device may + * assert the RDY output until the next attempt. + */ + disable_irq(client->irq); + + iqs5xx->bl_status = IQS5XX_BL_STATUS_RESET; + + error = iqs5xx_bl_cmd(client, IQS5XX_BL_CMD_VER, 0); + if (error) { + error = iqs5xx_bl_open(client); + if (error) + goto err_reset; + } + + error = iqs5xx_bl_write(client, IQS5XX_CHKSM, pmap, IQS5XX_PMAP_LEN); + if (error) + goto err_reset; + + error = iqs5xx_bl_cmd(client, IQS5XX_BL_CMD_CRC, 0); + if (error) + goto err_reset; + + error = iqs5xx_bl_verify(client, IQS5XX_CSTM, + pmap + IQS5XX_CHKSM_LEN + IQS5XX_APP_LEN, + IQS5XX_CSTM_LEN); + if (error) + goto err_reset; + + error = iqs5xx_bl_cmd(client, IQS5XX_BL_CMD_EXEC, 0); + +err_reset: + if (error) { + iqs5xx_reset(client); + usleep_range(10000, 10100); + } + + error = iqs5xx_dev_init(client); + if (!error && iqs5xx->bl_status == IQS5XX_BL_STATUS_RESET) + error = -EINVAL; + + enable_irq(client->irq); + + mutex_unlock(&iqs5xx->lock); + +err_kfree: + kfree(pmap); + + return error; +} + +static ssize_t fw_file_store(struct device *dev, struct device_attribute *attr, + const char *buf, size_t count) +{ + struct iqs5xx_private *iqs5xx = dev_get_drvdata(dev); + struct i2c_client *client = iqs5xx->client; + size_t len = count; + bool input_reg = !iqs5xx->input; + char fw_file[IQS5XX_FW_FILE_LEN + 1]; + int error; + + if (!len) + return -EINVAL; + + if (buf[len - 1] == '\n') + len--; + + if (len > IQS5XX_FW_FILE_LEN) + return -ENAMETOOLONG; + + memcpy(fw_file, buf, len); + fw_file[len] = '\0'; + + error = iqs5xx_fw_file_write(client, fw_file); + if (error) + return error; + + /* + * If the input device was not allocated already, it is guaranteed to + * be allocated by this point and can finally be registered. + */ + if (input_reg) { + error = input_register_device(iqs5xx->input); + if (error) { + dev_err(&client->dev, + "Failed to register device: %d\n", + error); + return error; + } + } + + return count; +} + +static DEVICE_ATTR_WO(fw_file); + +static struct attribute *iqs5xx_attrs[] = { + &dev_attr_fw_file.attr, + NULL, +}; + +static const struct attribute_group iqs5xx_attr_group = { + .attrs = iqs5xx_attrs, +}; + +static int __maybe_unused iqs5xx_suspend(struct device *dev) +{ + struct iqs5xx_private *iqs5xx = dev_get_drvdata(dev); + struct input_dev *input = iqs5xx->input; + int error = 0; + + if (!input) + return error; + + mutex_lock(&input->mutex); + + if (input->users) + error = iqs5xx_set_state(iqs5xx->client, IQS5XX_SUSPEND); + + mutex_unlock(&input->mutex); + + return error; +} + +static int __maybe_unused iqs5xx_resume(struct device *dev) +{ + struct iqs5xx_private *iqs5xx = dev_get_drvdata(dev); + struct input_dev *input = iqs5xx->input; + int error = 0; + + if (!input) + return error; + + mutex_lock(&input->mutex); + + if (input->users) + error = iqs5xx_set_state(iqs5xx->client, IQS5XX_RESUME); + + mutex_unlock(&input->mutex); + + return error; +} + +static SIMPLE_DEV_PM_OPS(iqs5xx_pm, iqs5xx_suspend, iqs5xx_resume); + +static int iqs5xx_probe(struct i2c_client *client, + const struct i2c_device_id *id) +{ + struct iqs5xx_private *iqs5xx; + int error; + + iqs5xx = devm_kzalloc(&client->dev, sizeof(*iqs5xx), GFP_KERNEL); + if (!iqs5xx) + return -ENOMEM; + + dev_set_drvdata(&client->dev, iqs5xx); + + i2c_set_clientdata(client, iqs5xx); + iqs5xx->client = client; + + iqs5xx->reset_gpio = devm_gpiod_get(&client->dev, + "reset", GPIOD_OUT_LOW); + if (IS_ERR(iqs5xx->reset_gpio)) { + error = PTR_ERR(iqs5xx->reset_gpio); + dev_err(&client->dev, "Failed to request GPIO: %d\n", error); + return error; + } + + mutex_init(&iqs5xx->lock); + + iqs5xx_reset(client); + usleep_range(10000, 10100); + + error = iqs5xx_dev_init(client); + if (error) + return error; + + error = devm_request_threaded_irq(&client->dev, client->irq, + NULL, iqs5xx_irq, IRQF_ONESHOT, + client->name, iqs5xx); + if (error) { + dev_err(&client->dev, "Failed to request IRQ: %d\n", error); + return error; + } + + error = devm_device_add_group(&client->dev, &iqs5xx_attr_group); + if (error) { + dev_err(&client->dev, "Failed to add attributes: %d\n", error); + return error; + } + + if (iqs5xx->input) { + error = input_register_device(iqs5xx->input); + if (error) + dev_err(&client->dev, + "Failed to register device: %d\n", + error); + } + + return error; +} + +static const struct i2c_device_id iqs5xx_id[] = { + { "iqs550", 0 }, + { "iqs572", 1 }, + { "iqs525", 2 }, + { } +}; +MODULE_DEVICE_TABLE(i2c, iqs5xx_id); + +static const struct of_device_id iqs5xx_of_match[] = { + { .compatible = "azoteq,iqs550" }, + { .compatible = "azoteq,iqs572" }, + { .compatible = "azoteq,iqs525" }, + { } +}; +MODULE_DEVICE_TABLE(of, iqs5xx_of_match); + +static struct i2c_driver iqs5xx_i2c_driver = { + .driver = { + .name = "iqs5xx", + .of_match_table = iqs5xx_of_match, + .pm = &iqs5xx_pm, + }, + .id_table = iqs5xx_id, + .probe = iqs5xx_probe, +}; +module_i2c_driver(iqs5xx_i2c_driver); + +MODULE_AUTHOR("Jeff LaBundy "); +MODULE_DESCRIPTION("Azoteq IQS550/572/525 Trackpad/Touchscreen Controller"); +MODULE_LICENSE("GPL"); -- cgit v1.2.3 From 90c73795afa24890bd2ae4f3b359de04b4147d37 Mon Sep 17 00:00:00 2001 From: Cédric Le Goater Date: Thu, 18 Apr 2019 12:39:27 +0200 Subject: KVM: PPC: Book3S HV: Add a new KVM device for the XIVE native exploitation mode MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This is the basic framework for the new KVM device supporting the XIVE native exploitation mode. The user interface exposes a new KVM device to be created by QEMU, only available when running on a L0 hypervisor. Support for nested guests is not available yet. The XIVE device reuses the device structure of the XICS-on-XIVE device as they have a lot in common. That could possibly change in the future if the need arise. Signed-off-by: Cédric Le Goater Reviewed-by: David Gibson Signed-off-by: Paul Mackerras --- Documentation/virtual/kvm/devices/xive.txt | 19 +++ arch/powerpc/include/asm/kvm_host.h | 1 + arch/powerpc/include/asm/kvm_ppc.h | 8 ++ arch/powerpc/include/uapi/asm/kvm.h | 3 + arch/powerpc/kvm/Makefile | 2 +- arch/powerpc/kvm/book3s.c | 7 +- arch/powerpc/kvm/book3s_xive_native.c | 179 +++++++++++++++++++++++++++++ include/uapi/linux/kvm.h | 2 + 8 files changed, 219 insertions(+), 2 deletions(-) create mode 100644 Documentation/virtual/kvm/devices/xive.txt create mode 100644 arch/powerpc/kvm/book3s_xive_native.c (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/devices/xive.txt b/Documentation/virtual/kvm/devices/xive.txt new file mode 100644 index 000000000000..fdbd2ff92a88 --- /dev/null +++ b/Documentation/virtual/kvm/devices/xive.txt @@ -0,0 +1,19 @@ +POWER9 eXternal Interrupt Virtualization Engine (XIVE Gen1) +========================================================== + +Device types supported: + KVM_DEV_TYPE_XIVE POWER9 XIVE Interrupt Controller generation 1 + +This device acts as a VM interrupt controller. It provides the KVM +interface to configure the interrupt sources of a VM in the underlying +POWER9 XIVE interrupt controller. + +Only one XIVE instance may be instantiated. A guest XIVE device +requires a POWER9 host and the guest OS should have support for the +XIVE native exploitation interrupt mode. If not, it should run using +the legacy interrupt mode, referred as XICS (POWER7/8). + +* Groups: + + 1. KVM_DEV_XIVE_GRP_CTRL + Provides global controls on the device diff --git a/arch/powerpc/include/asm/kvm_host.h b/arch/powerpc/include/asm/kvm_host.h index 07cefa53222e..9074f1d7613c 100644 --- a/arch/powerpc/include/asm/kvm_host.h +++ b/arch/powerpc/include/asm/kvm_host.h @@ -225,6 +225,7 @@ extern struct kvm_device_ops kvm_xics_ops; struct kvmppc_xive; struct kvmppc_xive_vcpu; extern struct kvm_device_ops kvm_xive_ops; +extern struct kvm_device_ops kvm_xive_native_ops; struct kvmppc_passthru_irqmap; diff --git a/arch/powerpc/include/asm/kvm_ppc.h b/arch/powerpc/include/asm/kvm_ppc.h index 0e99a6f8066f..f746d85f36c7 100644 --- a/arch/powerpc/include/asm/kvm_ppc.h +++ b/arch/powerpc/include/asm/kvm_ppc.h @@ -593,6 +593,10 @@ extern int kvmppc_xive_set_icp(struct kvm_vcpu *vcpu, u64 icpval); extern int kvmppc_xive_set_irq(struct kvm *kvm, int irq_source_id, u32 irq, int level, bool line_status); extern void kvmppc_xive_push_vcpu(struct kvm_vcpu *vcpu); + +extern void kvmppc_xive_native_init_module(void); +extern void kvmppc_xive_native_exit_module(void); + #else static inline int kvmppc_xive_set_xive(struct kvm *kvm, u32 irq, u32 server, u32 priority) { return -1; } @@ -616,6 +620,10 @@ static inline int kvmppc_xive_set_icp(struct kvm_vcpu *vcpu, u64 icpval) { retur static inline int kvmppc_xive_set_irq(struct kvm *kvm, int irq_source_id, u32 irq, int level, bool line_status) { return -ENODEV; } static inline void kvmppc_xive_push_vcpu(struct kvm_vcpu *vcpu) { } + +static inline void kvmppc_xive_native_init_module(void) { } +static inline void kvmppc_xive_native_exit_module(void) { } + #endif /* CONFIG_KVM_XIVE */ #if defined(CONFIG_PPC_POWERNV) && defined(CONFIG_KVM_BOOK3S_64_HANDLER) diff --git a/arch/powerpc/include/uapi/asm/kvm.h b/arch/powerpc/include/uapi/asm/kvm.h index 26ca425f4c2c..be0ce1f17625 100644 --- a/arch/powerpc/include/uapi/asm/kvm.h +++ b/arch/powerpc/include/uapi/asm/kvm.h @@ -677,4 +677,7 @@ struct kvm_ppc_cpu_char { #define KVM_XICS_PRESENTED (1ULL << 43) #define KVM_XICS_QUEUED (1ULL << 44) +/* POWER9 XIVE Native Interrupt Controller */ +#define KVM_DEV_XIVE_GRP_CTRL 1 + #endif /* __LINUX_KVM_POWERPC_H */ diff --git a/arch/powerpc/kvm/Makefile b/arch/powerpc/kvm/Makefile index 3223aec88b2c..4c67cc79de7c 100644 --- a/arch/powerpc/kvm/Makefile +++ b/arch/powerpc/kvm/Makefile @@ -94,7 +94,7 @@ endif kvm-book3s_64-objs-$(CONFIG_KVM_XICS) += \ book3s_xics.o -kvm-book3s_64-objs-$(CONFIG_KVM_XIVE) += book3s_xive.o +kvm-book3s_64-objs-$(CONFIG_KVM_XIVE) += book3s_xive.o book3s_xive_native.o kvm-book3s_64-objs-$(CONFIG_SPAPR_TCE_IOMMU) += book3s_64_vio.o kvm-book3s_64-module-objs := \ diff --git a/arch/powerpc/kvm/book3s.c b/arch/powerpc/kvm/book3s.c index 10c5579d20ce..7c3348fa27e1 100644 --- a/arch/powerpc/kvm/book3s.c +++ b/arch/powerpc/kvm/book3s.c @@ -1050,6 +1050,9 @@ static int kvmppc_book3s_init(void) if (xics_on_xive()) { kvmppc_xive_init_module(); kvm_register_device_ops(&kvm_xive_ops, KVM_DEV_TYPE_XICS); + kvmppc_xive_native_init_module(); + kvm_register_device_ops(&kvm_xive_native_ops, + KVM_DEV_TYPE_XIVE); } else #endif kvm_register_device_ops(&kvm_xics_ops, KVM_DEV_TYPE_XICS); @@ -1060,8 +1063,10 @@ static int kvmppc_book3s_init(void) static void kvmppc_book3s_exit(void) { #ifdef CONFIG_KVM_XICS - if (xics_on_xive()) + if (xics_on_xive()) { kvmppc_xive_exit_module(); + kvmppc_xive_native_exit_module(); + } #endif #ifdef CONFIG_KVM_BOOK3S_32_HANDLER kvmppc_book3s_exit_pr(); diff --git a/arch/powerpc/kvm/book3s_xive_native.c b/arch/powerpc/kvm/book3s_xive_native.c new file mode 100644 index 000000000000..751259394150 --- /dev/null +++ b/arch/powerpc/kvm/book3s_xive_native.c @@ -0,0 +1,179 @@ +// SPDX-License-Identifier: GPL-2.0 +/* + * Copyright (c) 2017-2019, IBM Corporation. + */ + +#define pr_fmt(fmt) "xive-kvm: " fmt + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include + +#include "book3s_xive.h" + +static int kvmppc_xive_native_set_attr(struct kvm_device *dev, + struct kvm_device_attr *attr) +{ + switch (attr->group) { + case KVM_DEV_XIVE_GRP_CTRL: + break; + } + return -ENXIO; +} + +static int kvmppc_xive_native_get_attr(struct kvm_device *dev, + struct kvm_device_attr *attr) +{ + return -ENXIO; +} + +static int kvmppc_xive_native_has_attr(struct kvm_device *dev, + struct kvm_device_attr *attr) +{ + switch (attr->group) { + case KVM_DEV_XIVE_GRP_CTRL: + break; + } + return -ENXIO; +} + +static void kvmppc_xive_native_free(struct kvm_device *dev) +{ + struct kvmppc_xive *xive = dev->private; + struct kvm *kvm = xive->kvm; + + debugfs_remove(xive->dentry); + + pr_devel("Destroying xive native device\n"); + + if (kvm) + kvm->arch.xive = NULL; + + if (xive->vp_base != XIVE_INVALID_VP) + xive_native_free_vp_block(xive->vp_base); + + kfree(xive); + kfree(dev); +} + +static int kvmppc_xive_native_create(struct kvm_device *dev, u32 type) +{ + struct kvmppc_xive *xive; + struct kvm *kvm = dev->kvm; + int ret = 0; + + pr_devel("Creating xive native device\n"); + + if (kvm->arch.xive) + return -EEXIST; + + xive = kzalloc(sizeof(*xive), GFP_KERNEL); + if (!xive) + return -ENOMEM; + + dev->private = xive; + xive->dev = dev; + xive->kvm = kvm; + kvm->arch.xive = xive; + + /* + * Allocate a bunch of VPs. KVM_MAX_VCPUS is a large value for + * a default. Getting the max number of CPUs the VM was + * configured with would improve our usage of the XIVE VP space. + */ + xive->vp_base = xive_native_alloc_vp_block(KVM_MAX_VCPUS); + pr_devel("VP_Base=%x\n", xive->vp_base); + + if (xive->vp_base == XIVE_INVALID_VP) + ret = -ENXIO; + + xive->single_escalation = xive_native_has_single_escalation(); + + if (ret) + kfree(xive); + + return ret; +} + +static int xive_native_debug_show(struct seq_file *m, void *private) +{ + struct kvmppc_xive *xive = m->private; + struct kvm *kvm = xive->kvm; + + if (!kvm) + return 0; + + return 0; +} + +static int xive_native_debug_open(struct inode *inode, struct file *file) +{ + return single_open(file, xive_native_debug_show, inode->i_private); +} + +static const struct file_operations xive_native_debug_fops = { + .open = xive_native_debug_open, + .read = seq_read, + .llseek = seq_lseek, + .release = single_release, +}; + +static void xive_native_debugfs_init(struct kvmppc_xive *xive) +{ + char *name; + + name = kasprintf(GFP_KERNEL, "kvm-xive-%p", xive); + if (!name) { + pr_err("%s: no memory for name\n", __func__); + return; + } + + xive->dentry = debugfs_create_file(name, 0444, powerpc_debugfs_root, + xive, &xive_native_debug_fops); + + pr_debug("%s: created %s\n", __func__, name); + kfree(name); +} + +static void kvmppc_xive_native_init(struct kvm_device *dev) +{ + struct kvmppc_xive *xive = (struct kvmppc_xive *)dev->private; + + /* Register some debug interfaces */ + xive_native_debugfs_init(xive); +} + +struct kvm_device_ops kvm_xive_native_ops = { + .name = "kvm-xive-native", + .create = kvmppc_xive_native_create, + .init = kvmppc_xive_native_init, + .destroy = kvmppc_xive_native_free, + .set_attr = kvmppc_xive_native_set_attr, + .get_attr = kvmppc_xive_native_get_attr, + .has_attr = kvmppc_xive_native_has_attr, +}; + +void kvmppc_xive_native_init_module(void) +{ + ; +} + +void kvmppc_xive_native_exit_module(void) +{ + ; +} diff --git a/include/uapi/linux/kvm.h b/include/uapi/linux/kvm.h index 6d4ea4b6c922..e6368163d3a0 100644 --- a/include/uapi/linux/kvm.h +++ b/include/uapi/linux/kvm.h @@ -1211,6 +1211,8 @@ enum kvm_device_type { #define KVM_DEV_TYPE_ARM_VGIC_V3 KVM_DEV_TYPE_ARM_VGIC_V3 KVM_DEV_TYPE_ARM_VGIC_ITS, #define KVM_DEV_TYPE_ARM_VGIC_ITS KVM_DEV_TYPE_ARM_VGIC_ITS + KVM_DEV_TYPE_XIVE, +#define KVM_DEV_TYPE_XIVE KVM_DEV_TYPE_XIVE KVM_DEV_TYPE_MAX, }; -- cgit v1.2.3 From eacc56bb9de3e6830ddc169553772cd6de59ee4c Mon Sep 17 00:00:00 2001 From: Cédric Le Goater Date: Thu, 18 Apr 2019 12:39:28 +0200 Subject: KVM: PPC: Book3S HV: XIVE: Introduce a new capability KVM_CAP_PPC_IRQ_XIVE MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The user interface exposes a new capability KVM_CAP_PPC_IRQ_XIVE to let QEMU connect the vCPU presenters to the XIVE KVM device if required. The capability is not advertised for now as the full support for the XIVE native exploitation mode is not yet available. When this is case, the capability will be advertised on PowerNV Hypervisors only. Nested guests (pseries KVM Hypervisor) are not supported. Internally, the interface to the new KVM device is protected with a new interrupt mode: KVMPPC_IRQ_XIVE. Signed-off-by: Cédric Le Goater Reviewed-by: David Gibson Signed-off-by: Paul Mackerras --- Documentation/virtual/kvm/api.txt | 9 ++ arch/powerpc/include/asm/kvm_host.h | 1 + arch/powerpc/include/asm/kvm_ppc.h | 13 +++ arch/powerpc/kvm/book3s_xive.c | 88 ++++++++++---------- arch/powerpc/kvm/book3s_xive.h | 11 +++ arch/powerpc/kvm/book3s_xive_native.c | 150 ++++++++++++++++++++++++++++++++++ arch/powerpc/kvm/powerpc.c | 36 ++++++++ include/uapi/linux/kvm.h | 1 + 8 files changed, 268 insertions(+), 41 deletions(-) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/api.txt b/Documentation/virtual/kvm/api.txt index 67068c47c591..e38eb17b7be6 100644 --- a/Documentation/virtual/kvm/api.txt +++ b/Documentation/virtual/kvm/api.txt @@ -4504,6 +4504,15 @@ struct kvm_sync_regs { struct kvm_vcpu_events events; }; +6.75 KVM_CAP_PPC_IRQ_XIVE + +Architectures: ppc +Target: vcpu +Parameters: args[0] is the XIVE device fd + args[1] is the XIVE CPU number (server ID) for this vcpu + +This capability connects the vcpu to an in-kernel XIVE device. + 7. Capabilities that can be enabled on VMs ------------------------------------------ diff --git a/arch/powerpc/include/asm/kvm_host.h b/arch/powerpc/include/asm/kvm_host.h index 9074f1d7613c..eac25fd7e631 100644 --- a/arch/powerpc/include/asm/kvm_host.h +++ b/arch/powerpc/include/asm/kvm_host.h @@ -453,6 +453,7 @@ struct kvmppc_passthru_irqmap { #define KVMPPC_IRQ_DEFAULT 0 #define KVMPPC_IRQ_MPIC 1 #define KVMPPC_IRQ_XICS 2 /* Includes a XIVE option */ +#define KVMPPC_IRQ_XIVE 3 /* XIVE native exploitation mode */ #define MMIO_HPTE_CACHE_SIZE 4 diff --git a/arch/powerpc/include/asm/kvm_ppc.h b/arch/powerpc/include/asm/kvm_ppc.h index f746d85f36c7..9fc2753e516e 100644 --- a/arch/powerpc/include/asm/kvm_ppc.h +++ b/arch/powerpc/include/asm/kvm_ppc.h @@ -594,6 +594,14 @@ extern int kvmppc_xive_set_irq(struct kvm *kvm, int irq_source_id, u32 irq, int level, bool line_status); extern void kvmppc_xive_push_vcpu(struct kvm_vcpu *vcpu); +static inline int kvmppc_xive_enabled(struct kvm_vcpu *vcpu) +{ + return vcpu->arch.irq_type == KVMPPC_IRQ_XIVE; +} + +extern int kvmppc_xive_native_connect_vcpu(struct kvm_device *dev, + struct kvm_vcpu *vcpu, u32 cpu); +extern void kvmppc_xive_native_cleanup_vcpu(struct kvm_vcpu *vcpu); extern void kvmppc_xive_native_init_module(void); extern void kvmppc_xive_native_exit_module(void); @@ -621,6 +629,11 @@ static inline int kvmppc_xive_set_irq(struct kvm *kvm, int irq_source_id, u32 ir int level, bool line_status) { return -ENODEV; } static inline void kvmppc_xive_push_vcpu(struct kvm_vcpu *vcpu) { } +static inline int kvmppc_xive_enabled(struct kvm_vcpu *vcpu) + { return 0; } +static inline int kvmppc_xive_native_connect_vcpu(struct kvm_device *dev, + struct kvm_vcpu *vcpu, u32 cpu) { return -EBUSY; } +static inline void kvmppc_xive_native_cleanup_vcpu(struct kvm_vcpu *vcpu) { } static inline void kvmppc_xive_native_init_module(void) { } static inline void kvmppc_xive_native_exit_module(void) { } diff --git a/arch/powerpc/kvm/book3s_xive.c b/arch/powerpc/kvm/book3s_xive.c index f78d002f0fe0..e7f1ada1c3de 100644 --- a/arch/powerpc/kvm/book3s_xive.c +++ b/arch/powerpc/kvm/book3s_xive.c @@ -380,11 +380,6 @@ static int xive_select_target(struct kvm *kvm, u32 *server, u8 prio) return -EBUSY; } -static u32 xive_vp(struct kvmppc_xive *xive, u32 server) -{ - return xive->vp_base + kvmppc_pack_vcpu_id(xive->kvm, server); -} - static u8 xive_lock_and_mask(struct kvmppc_xive *xive, struct kvmppc_xive_src_block *sb, struct kvmppc_xive_irq_state *state) @@ -430,8 +425,8 @@ static u8 xive_lock_and_mask(struct kvmppc_xive *xive, */ if (xd->flags & OPAL_XIVE_IRQ_MASK_VIA_FW) { xive_native_configure_irq(hw_num, - xive_vp(xive, state->act_server), - MASKED, state->number); + kvmppc_xive_vp(xive, state->act_server), + MASKED, state->number); /* set old_p so we can track if an H_EOI was done */ state->old_p = true; state->old_q = false; @@ -486,8 +481,8 @@ static void xive_finish_unmask(struct kvmppc_xive *xive, */ if (xd->flags & OPAL_XIVE_IRQ_MASK_VIA_FW) { xive_native_configure_irq(hw_num, - xive_vp(xive, state->act_server), - state->act_priority, state->number); + kvmppc_xive_vp(xive, state->act_server), + state->act_priority, state->number); /* If an EOI is needed, do it here */ if (!state->old_p) xive_vm_source_eoi(hw_num, xd); @@ -563,7 +558,7 @@ static int xive_target_interrupt(struct kvm *kvm, kvmppc_xive_select_irq(state, &hw_num, NULL); return xive_native_configure_irq(hw_num, - xive_vp(xive, server), + kvmppc_xive_vp(xive, server), prio, state->number); } @@ -951,7 +946,7 @@ int kvmppc_xive_set_mapped(struct kvm *kvm, unsigned long guest_irq, * which is fine for a never started interrupt. */ xive_native_configure_irq(hw_irq, - xive_vp(xive, state->act_server), + kvmppc_xive_vp(xive, state->act_server), state->act_priority, state->number); /* @@ -1027,7 +1022,7 @@ int kvmppc_xive_clr_mapped(struct kvm *kvm, unsigned long guest_irq, /* Reconfigure the IPI */ xive_native_configure_irq(state->ipi_number, - xive_vp(xive, state->act_server), + kvmppc_xive_vp(xive, state->act_server), state->act_priority, state->number); /* @@ -1049,7 +1044,7 @@ int kvmppc_xive_clr_mapped(struct kvm *kvm, unsigned long guest_irq, } EXPORT_SYMBOL_GPL(kvmppc_xive_clr_mapped); -static void kvmppc_xive_disable_vcpu_interrupts(struct kvm_vcpu *vcpu) +void kvmppc_xive_disable_vcpu_interrupts(struct kvm_vcpu *vcpu) { struct kvmppc_xive_vcpu *xc = vcpu->arch.xive_vcpu; struct kvm *kvm = vcpu->kvm; @@ -1166,7 +1161,7 @@ int kvmppc_xive_connect_vcpu(struct kvm_device *dev, xc->xive = xive; xc->vcpu = vcpu; xc->server_num = cpu; - xc->vp_id = xive_vp(xive, cpu); + xc->vp_id = kvmppc_xive_vp(xive, cpu); xc->mfrr = 0xff; xc->valid = true; @@ -1883,6 +1878,43 @@ static int kvmppc_xive_create(struct kvm_device *dev, u32 type) return 0; } +int kvmppc_xive_debug_show_queues(struct seq_file *m, struct kvm_vcpu *vcpu) +{ + struct kvmppc_xive_vcpu *xc = vcpu->arch.xive_vcpu; + unsigned int i; + + for (i = 0; i < KVMPPC_XIVE_Q_COUNT; i++) { + struct xive_q *q = &xc->queues[i]; + u32 i0, i1, idx; + + if (!q->qpage && !xc->esc_virq[i]) + continue; + + seq_printf(m, " [q%d]: ", i); + + if (q->qpage) { + idx = q->idx; + i0 = be32_to_cpup(q->qpage + idx); + idx = (idx + 1) & q->msk; + i1 = be32_to_cpup(q->qpage + idx); + seq_printf(m, "T=%d %08x %08x...\n", q->toggle, + i0, i1); + } + if (xc->esc_virq[i]) { + struct irq_data *d = irq_get_irq_data(xc->esc_virq[i]); + struct xive_irq_data *xd = + irq_data_get_irq_handler_data(d); + u64 pq = xive_vm_esb_load(xd, XIVE_ESB_GET); + + seq_printf(m, "E:%c%c I(%d:%llx:%llx)", + (pq & XIVE_ESB_VAL_P) ? 'P' : 'p', + (pq & XIVE_ESB_VAL_Q) ? 'Q' : 'q', + xc->esc_virq[i], pq, xd->eoi_page); + seq_puts(m, "\n"); + } + } + return 0; +} static int xive_debug_show(struct seq_file *m, void *private) { @@ -1908,7 +1940,6 @@ static int xive_debug_show(struct seq_file *m, void *private) kvm_for_each_vcpu(i, vcpu, kvm) { struct kvmppc_xive_vcpu *xc = vcpu->arch.xive_vcpu; - unsigned int i; if (!xc) continue; @@ -1918,33 +1949,8 @@ static int xive_debug_show(struct seq_file *m, void *private) xc->server_num, xc->cppr, xc->hw_cppr, xc->mfrr, xc->pending, xc->stat_rm_h_xirr, xc->stat_vm_h_xirr); - for (i = 0; i < KVMPPC_XIVE_Q_COUNT; i++) { - struct xive_q *q = &xc->queues[i]; - u32 i0, i1, idx; - if (!q->qpage && !xc->esc_virq[i]) - continue; - - seq_printf(m, " [q%d]: ", i); - - if (q->qpage) { - idx = q->idx; - i0 = be32_to_cpup(q->qpage + idx); - idx = (idx + 1) & q->msk; - i1 = be32_to_cpup(q->qpage + idx); - seq_printf(m, "T=%d %08x %08x... \n", q->toggle, i0, i1); - } - if (xc->esc_virq[i]) { - struct irq_data *d = irq_get_irq_data(xc->esc_virq[i]); - struct xive_irq_data *xd = irq_data_get_irq_handler_data(d); - u64 pq = xive_vm_esb_load(xd, XIVE_ESB_GET); - seq_printf(m, "E:%c%c I(%d:%llx:%llx)", - (pq & XIVE_ESB_VAL_P) ? 'P' : 'p', - (pq & XIVE_ESB_VAL_Q) ? 'Q' : 'q', - xc->esc_virq[i], pq, xd->eoi_page); - seq_printf(m, "\n"); - } - } + kvmppc_xive_debug_show_queues(m, vcpu); t_rm_h_xirr += xc->stat_rm_h_xirr; t_rm_h_ipoll += xc->stat_rm_h_ipoll; diff --git a/arch/powerpc/kvm/book3s_xive.h b/arch/powerpc/kvm/book3s_xive.h index a08ae6fd4c51..d366df69b9cb 100644 --- a/arch/powerpc/kvm/book3s_xive.h +++ b/arch/powerpc/kvm/book3s_xive.h @@ -198,6 +198,11 @@ static inline struct kvmppc_xive_src_block *kvmppc_xive_find_source(struct kvmpp return xive->src_blocks[bid]; } +static inline u32 kvmppc_xive_vp(struct kvmppc_xive *xive, u32 server) +{ + return xive->vp_base + kvmppc_pack_vcpu_id(xive->kvm, server); +} + /* * Mapping between guest priorities and host priorities * is as follow. @@ -248,5 +253,11 @@ extern int (*__xive_vm_h_ipi)(struct kvm_vcpu *vcpu, unsigned long server, extern int (*__xive_vm_h_cppr)(struct kvm_vcpu *vcpu, unsigned long cppr); extern int (*__xive_vm_h_eoi)(struct kvm_vcpu *vcpu, unsigned long xirr); +/* + * Common Xive routines for XICS-over-XIVE and XIVE native + */ +void kvmppc_xive_disable_vcpu_interrupts(struct kvm_vcpu *vcpu); +int kvmppc_xive_debug_show_queues(struct seq_file *m, struct kvm_vcpu *vcpu); + #endif /* CONFIG_KVM_XICS */ #endif /* _KVM_PPC_BOOK3S_XICS_H */ diff --git a/arch/powerpc/kvm/book3s_xive_native.c b/arch/powerpc/kvm/book3s_xive_native.c index 751259394150..6fa73cfd9d9c 100644 --- a/arch/powerpc/kvm/book3s_xive_native.c +++ b/arch/powerpc/kvm/book3s_xive_native.c @@ -26,6 +26,134 @@ #include "book3s_xive.h" +static void kvmppc_xive_native_cleanup_queue(struct kvm_vcpu *vcpu, int prio) +{ + struct kvmppc_xive_vcpu *xc = vcpu->arch.xive_vcpu; + struct xive_q *q = &xc->queues[prio]; + + xive_native_disable_queue(xc->vp_id, q, prio); + if (q->qpage) { + put_page(virt_to_page(q->qpage)); + q->qpage = NULL; + } +} + +void kvmppc_xive_native_cleanup_vcpu(struct kvm_vcpu *vcpu) +{ + struct kvmppc_xive_vcpu *xc = vcpu->arch.xive_vcpu; + int i; + + if (!kvmppc_xive_enabled(vcpu)) + return; + + if (!xc) + return; + + pr_devel("native_cleanup_vcpu(cpu=%d)\n", xc->server_num); + + /* Ensure no interrupt is still routed to that VP */ + xc->valid = false; + kvmppc_xive_disable_vcpu_interrupts(vcpu); + + /* Disable the VP */ + xive_native_disable_vp(xc->vp_id); + + /* Free the queues & associated interrupts */ + for (i = 0; i < KVMPPC_XIVE_Q_COUNT; i++) { + /* Free the escalation irq */ + if (xc->esc_virq[i]) { + free_irq(xc->esc_virq[i], vcpu); + irq_dispose_mapping(xc->esc_virq[i]); + kfree(xc->esc_virq_names[i]); + xc->esc_virq[i] = 0; + } + + /* Free the queue */ + kvmppc_xive_native_cleanup_queue(vcpu, i); + } + + /* Free the VP */ + kfree(xc); + + /* Cleanup the vcpu */ + vcpu->arch.irq_type = KVMPPC_IRQ_DEFAULT; + vcpu->arch.xive_vcpu = NULL; +} + +int kvmppc_xive_native_connect_vcpu(struct kvm_device *dev, + struct kvm_vcpu *vcpu, u32 server_num) +{ + struct kvmppc_xive *xive = dev->private; + struct kvmppc_xive_vcpu *xc = NULL; + int rc; + + pr_devel("native_connect_vcpu(server=%d)\n", server_num); + + if (dev->ops != &kvm_xive_native_ops) { + pr_devel("Wrong ops !\n"); + return -EPERM; + } + if (xive->kvm != vcpu->kvm) + return -EPERM; + if (vcpu->arch.irq_type != KVMPPC_IRQ_DEFAULT) + return -EBUSY; + if (server_num >= KVM_MAX_VCPUS) { + pr_devel("Out of bounds !\n"); + return -EINVAL; + } + + mutex_lock(&vcpu->kvm->lock); + + if (kvmppc_xive_find_server(vcpu->kvm, server_num)) { + pr_devel("Duplicate !\n"); + rc = -EEXIST; + goto bail; + } + + xc = kzalloc(sizeof(*xc), GFP_KERNEL); + if (!xc) { + rc = -ENOMEM; + goto bail; + } + + vcpu->arch.xive_vcpu = xc; + xc->xive = xive; + xc->vcpu = vcpu; + xc->server_num = server_num; + + xc->vp_id = kvmppc_xive_vp(xive, server_num); + xc->valid = true; + vcpu->arch.irq_type = KVMPPC_IRQ_XIVE; + + rc = xive_native_get_vp_info(xc->vp_id, &xc->vp_cam, &xc->vp_chip_id); + if (rc) { + pr_err("Failed to get VP info from OPAL: %d\n", rc); + goto bail; + } + + /* + * Enable the VP first as the single escalation mode will + * affect escalation interrupts numbering + */ + rc = xive_native_enable_vp(xc->vp_id, xive->single_escalation); + if (rc) { + pr_err("Failed to enable VP in OPAL: %d\n", rc); + goto bail; + } + + /* Configure VCPU fields for use by assembly push/pull */ + vcpu->arch.xive_saved_state.w01 = cpu_to_be64(0xff000000); + vcpu->arch.xive_cam_word = cpu_to_be32(xc->vp_cam | TM_QW1W2_VO); + + /* TODO: reset all queues to a clean state ? */ +bail: + mutex_unlock(&vcpu->kvm->lock); + if (rc) + kvmppc_xive_native_cleanup_vcpu(vcpu); + + return rc; +} + static int kvmppc_xive_native_set_attr(struct kvm_device *dev, struct kvm_device_attr *attr) { @@ -114,10 +242,32 @@ static int xive_native_debug_show(struct seq_file *m, void *private) { struct kvmppc_xive *xive = m->private; struct kvm *kvm = xive->kvm; + struct kvm_vcpu *vcpu; + unsigned int i; if (!kvm) return 0; + seq_puts(m, "=========\nVCPU state\n=========\n"); + + kvm_for_each_vcpu(i, vcpu, kvm) { + struct kvmppc_xive_vcpu *xc = vcpu->arch.xive_vcpu; + + if (!xc) + continue; + + seq_printf(m, "cpu server %#x NSR=%02x CPPR=%02x IBP=%02x PIPR=%02x w01=%016llx w2=%08x\n", + xc->server_num, + vcpu->arch.xive_saved_state.nsr, + vcpu->arch.xive_saved_state.cppr, + vcpu->arch.xive_saved_state.ipb, + vcpu->arch.xive_saved_state.pipr, + vcpu->arch.xive_saved_state.w01, + (u32) vcpu->arch.xive_cam_word); + + kvmppc_xive_debug_show_queues(m, vcpu); + } + return 0; } diff --git a/arch/powerpc/kvm/powerpc.c b/arch/powerpc/kvm/powerpc.c index 8885377ec3e0..b0858ee61460 100644 --- a/arch/powerpc/kvm/powerpc.c +++ b/arch/powerpc/kvm/powerpc.c @@ -570,6 +570,15 @@ int kvm_vm_ioctl_check_extension(struct kvm *kvm, long ext) case KVM_CAP_PPC_GET_CPU_CHAR: r = 1; break; +#ifdef CONFIG_KVM_XIVE + case KVM_CAP_PPC_IRQ_XIVE: + /* + * Return false until all the XIVE infrastructure is + * in place including support for migration. + */ + r = 0; + break; +#endif case KVM_CAP_PPC_ALLOC_HTAB: r = hv_enabled; @@ -753,6 +762,9 @@ void kvm_arch_vcpu_free(struct kvm_vcpu *vcpu) else kvmppc_xics_free_icp(vcpu); break; + case KVMPPC_IRQ_XIVE: + kvmppc_xive_native_cleanup_vcpu(vcpu); + break; } kvmppc_core_vcpu_free(vcpu); @@ -1941,6 +1953,30 @@ static int kvm_vcpu_ioctl_enable_cap(struct kvm_vcpu *vcpu, break; } #endif /* CONFIG_KVM_XICS */ +#ifdef CONFIG_KVM_XIVE + case KVM_CAP_PPC_IRQ_XIVE: { + struct fd f; + struct kvm_device *dev; + + r = -EBADF; + f = fdget(cap->args[0]); + if (!f.file) + break; + + r = -ENXIO; + if (!xive_enabled()) + break; + + r = -EPERM; + dev = kvm_device_from_filp(f.file); + if (dev) + r = kvmppc_xive_native_connect_vcpu(dev, vcpu, + cap->args[1]); + + fdput(f); + break; + } +#endif /* CONFIG_KVM_XIVE */ #ifdef CONFIG_KVM_BOOK3S_HV_POSSIBLE case KVM_CAP_PPC_FWNMI: r = -EINVAL; diff --git a/include/uapi/linux/kvm.h b/include/uapi/linux/kvm.h index e6368163d3a0..52bf74a1616e 100644 --- a/include/uapi/linux/kvm.h +++ b/include/uapi/linux/kvm.h @@ -988,6 +988,7 @@ struct kvm_ppc_resize_hpt { #define KVM_CAP_ARM_VM_IPA_SIZE 165 #define KVM_CAP_MANUAL_DIRTY_LOG_PROTECT 166 #define KVM_CAP_HYPERV_CPUID 167 +#define KVM_CAP_PPC_IRQ_XIVE 168 #ifdef KVM_CAP_IRQ_ROUTING -- cgit v1.2.3 From 4131f83c3d64e591014dad14c7f8070c538b9422 Mon Sep 17 00:00:00 2001 From: Cédric Le Goater Date: Thu, 18 Apr 2019 12:39:29 +0200 Subject: KVM: PPC: Book3S HV: XIVE: add a control to initialize a source MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The XIVE KVM device maintains a list of interrupt sources for the VM which are allocated in the pool of generic interrupts (IPIs) of the main XIVE IC controller. These are used for the CPU IPIs as well as for virtual device interrupts. The IRQ number space is defined by QEMU. The XIVE device reuses the source structures of the XICS-on-XIVE device for the source blocks (2-level tree) and for the source interrupts. Under XIVE native, the source interrupt caches mostly configuration information and is less used than under the XICS-on-XIVE device in which hcalls are still necessary at run-time. When a source is initialized in KVM, an IPI interrupt source is simply allocated at the OPAL level and then MASKED. KVM only needs to know about its type: LSI or MSI. Signed-off-by: Cédric Le Goater Reviewed-by: David Gibson Signed-off-by: Paul Mackerras --- Documentation/virtual/kvm/devices/xive.txt | 15 ++++ arch/powerpc/include/uapi/asm/kvm.h | 5 ++ arch/powerpc/kvm/book3s_xive.c | 8 +-- arch/powerpc/kvm/book3s_xive.h | 10 +++ arch/powerpc/kvm/book3s_xive_native.c | 106 +++++++++++++++++++++++++++++ 5 files changed, 140 insertions(+), 4 deletions(-) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/devices/xive.txt b/Documentation/virtual/kvm/devices/xive.txt index fdbd2ff92a88..cd8bfc37b72e 100644 --- a/Documentation/virtual/kvm/devices/xive.txt +++ b/Documentation/virtual/kvm/devices/xive.txt @@ -17,3 +17,18 @@ the legacy interrupt mode, referred as XICS (POWER7/8). 1. KVM_DEV_XIVE_GRP_CTRL Provides global controls on the device + + 2. KVM_DEV_XIVE_GRP_SOURCE (write only) + Initializes a new source in the XIVE device and mask it. + Attributes: + Interrupt source number (64-bit) + The kvm_device_attr.addr points to a __u64 value: + bits: | 63 .... 2 | 1 | 0 + values: | unused | level | type + - type: 0:MSI 1:LSI + - level: assertion level in case of an LSI. + Errors: + -E2BIG: Interrupt source number is out of range + -ENOMEM: Could not create a new source block + -EFAULT: Invalid user pointer for attr->addr. + -ENXIO: Could not allocate underlying HW interrupt diff --git a/arch/powerpc/include/uapi/asm/kvm.h b/arch/powerpc/include/uapi/asm/kvm.h index be0ce1f17625..d468294c2a67 100644 --- a/arch/powerpc/include/uapi/asm/kvm.h +++ b/arch/powerpc/include/uapi/asm/kvm.h @@ -679,5 +679,10 @@ struct kvm_ppc_cpu_char { /* POWER9 XIVE Native Interrupt Controller */ #define KVM_DEV_XIVE_GRP_CTRL 1 +#define KVM_DEV_XIVE_GRP_SOURCE 2 /* 64-bit source identifier */ + +/* Layout of 64-bit XIVE source attribute values */ +#define KVM_XIVE_LEVEL_SENSITIVE (1ULL << 0) +#define KVM_XIVE_LEVEL_ASSERTED (1ULL << 1) #endif /* __LINUX_KVM_POWERPC_H */ diff --git a/arch/powerpc/kvm/book3s_xive.c b/arch/powerpc/kvm/book3s_xive.c index e7f1ada1c3de..6c9f9fd0855f 100644 --- a/arch/powerpc/kvm/book3s_xive.c +++ b/arch/powerpc/kvm/book3s_xive.c @@ -1480,8 +1480,8 @@ static int xive_get_source(struct kvmppc_xive *xive, long irq, u64 addr) return 0; } -static struct kvmppc_xive_src_block *xive_create_src_block(struct kvmppc_xive *xive, - int irq) +struct kvmppc_xive_src_block *kvmppc_xive_create_src_block( + struct kvmppc_xive *xive, int irq) { struct kvm *kvm = xive->kvm; struct kvmppc_xive_src_block *sb; @@ -1560,7 +1560,7 @@ static int xive_set_source(struct kvmppc_xive *xive, long irq, u64 addr) sb = kvmppc_xive_find_source(xive, irq, &idx); if (!sb) { pr_devel("No source, creating source block...\n"); - sb = xive_create_src_block(xive, irq); + sb = kvmppc_xive_create_src_block(xive, irq); if (!sb) { pr_devel("Failed to create block...\n"); return -ENOMEM; @@ -1784,7 +1784,7 @@ static void kvmppc_xive_cleanup_irq(u32 hw_num, struct xive_irq_data *xd) xive_cleanup_irq_data(xd); } -static void kvmppc_xive_free_sources(struct kvmppc_xive_src_block *sb) +void kvmppc_xive_free_sources(struct kvmppc_xive_src_block *sb) { int i; diff --git a/arch/powerpc/kvm/book3s_xive.h b/arch/powerpc/kvm/book3s_xive.h index d366df69b9cb..1be921cb5dcb 100644 --- a/arch/powerpc/kvm/book3s_xive.h +++ b/arch/powerpc/kvm/book3s_xive.h @@ -12,6 +12,13 @@ #ifdef CONFIG_KVM_XICS #include "book3s_xics.h" +/* + * The XIVE Interrupt source numbers are within the range 0 to + * KVMPPC_XICS_NR_IRQS. + */ +#define KVMPPC_XIVE_FIRST_IRQ 0 +#define KVMPPC_XIVE_NR_IRQS KVMPPC_XICS_NR_IRQS + /* * State for one guest irq source. * @@ -258,6 +265,9 @@ extern int (*__xive_vm_h_eoi)(struct kvm_vcpu *vcpu, unsigned long xirr); */ void kvmppc_xive_disable_vcpu_interrupts(struct kvm_vcpu *vcpu); int kvmppc_xive_debug_show_queues(struct seq_file *m, struct kvm_vcpu *vcpu); +struct kvmppc_xive_src_block *kvmppc_xive_create_src_block( + struct kvmppc_xive *xive, int irq); +void kvmppc_xive_free_sources(struct kvmppc_xive_src_block *sb); #endif /* CONFIG_KVM_XICS */ #endif /* _KVM_PPC_BOOK3S_XICS_H */ diff --git a/arch/powerpc/kvm/book3s_xive_native.c b/arch/powerpc/kvm/book3s_xive_native.c index 6fa73cfd9d9c..5f2bd6c137b7 100644 --- a/arch/powerpc/kvm/book3s_xive_native.c +++ b/arch/powerpc/kvm/book3s_xive_native.c @@ -26,6 +26,17 @@ #include "book3s_xive.h" +static u8 xive_vm_esb_load(struct xive_irq_data *xd, u32 offset) +{ + u64 val; + + if (xd->flags & XIVE_IRQ_FLAG_SHIFT_BUG) + offset |= offset << 4; + + val = in_be64(xd->eoi_mmio + offset); + return (u8)val; +} + static void kvmppc_xive_native_cleanup_queue(struct kvm_vcpu *vcpu, int prio) { struct kvmppc_xive_vcpu *xc = vcpu->arch.xive_vcpu; @@ -154,12 +165,94 @@ bail: return rc; } +static int kvmppc_xive_native_set_source(struct kvmppc_xive *xive, long irq, + u64 addr) +{ + struct kvmppc_xive_src_block *sb; + struct kvmppc_xive_irq_state *state; + u64 __user *ubufp = (u64 __user *) addr; + u64 val; + u16 idx; + int rc; + + pr_devel("%s irq=0x%lx\n", __func__, irq); + + if (irq < KVMPPC_XIVE_FIRST_IRQ || irq >= KVMPPC_XIVE_NR_IRQS) + return -E2BIG; + + sb = kvmppc_xive_find_source(xive, irq, &idx); + if (!sb) { + pr_debug("No source, creating source block...\n"); + sb = kvmppc_xive_create_src_block(xive, irq); + if (!sb) { + pr_err("Failed to create block...\n"); + return -ENOMEM; + } + } + state = &sb->irq_state[idx]; + + if (get_user(val, ubufp)) { + pr_err("fault getting user info !\n"); + return -EFAULT; + } + + arch_spin_lock(&sb->lock); + + /* + * If the source doesn't already have an IPI, allocate + * one and get the corresponding data + */ + if (!state->ipi_number) { + state->ipi_number = xive_native_alloc_irq(); + if (state->ipi_number == 0) { + pr_err("Failed to allocate IRQ !\n"); + rc = -ENXIO; + goto unlock; + } + xive_native_populate_irq_data(state->ipi_number, + &state->ipi_data); + pr_debug("%s allocated hw_irq=0x%x for irq=0x%lx\n", __func__, + state->ipi_number, irq); + } + + /* Restore LSI state */ + if (val & KVM_XIVE_LEVEL_SENSITIVE) { + state->lsi = true; + if (val & KVM_XIVE_LEVEL_ASSERTED) + state->asserted = true; + pr_devel(" LSI ! Asserted=%d\n", state->asserted); + } + + /* Mask IRQ to start with */ + state->act_server = 0; + state->act_priority = MASKED; + xive_vm_esb_load(&state->ipi_data, XIVE_ESB_SET_PQ_01); + xive_native_configure_irq(state->ipi_number, 0, MASKED, 0); + + /* Increment the number of valid sources and mark this one valid */ + if (!state->valid) + xive->src_count++; + state->valid = true; + + rc = 0; + +unlock: + arch_spin_unlock(&sb->lock); + + return rc; +} + static int kvmppc_xive_native_set_attr(struct kvm_device *dev, struct kvm_device_attr *attr) { + struct kvmppc_xive *xive = dev->private; + switch (attr->group) { case KVM_DEV_XIVE_GRP_CTRL: break; + case KVM_DEV_XIVE_GRP_SOURCE: + return kvmppc_xive_native_set_source(xive, attr->attr, + attr->addr); } return -ENXIO; } @@ -176,6 +269,11 @@ static int kvmppc_xive_native_has_attr(struct kvm_device *dev, switch (attr->group) { case KVM_DEV_XIVE_GRP_CTRL: break; + case KVM_DEV_XIVE_GRP_SOURCE: + if (attr->attr >= KVMPPC_XIVE_FIRST_IRQ && + attr->attr < KVMPPC_XIVE_NR_IRQS) + return 0; + break; } return -ENXIO; } @@ -184,6 +282,7 @@ static void kvmppc_xive_native_free(struct kvm_device *dev) { struct kvmppc_xive *xive = dev->private; struct kvm *kvm = xive->kvm; + int i; debugfs_remove(xive->dentry); @@ -192,6 +291,13 @@ static void kvmppc_xive_native_free(struct kvm_device *dev) if (kvm) kvm->arch.xive = NULL; + for (i = 0; i <= xive->max_sbid; i++) { + if (xive->src_blocks[i]) + kvmppc_xive_free_sources(xive->src_blocks[i]); + kfree(xive->src_blocks[i]); + xive->src_blocks[i] = NULL; + } + if (xive->vp_base != XIVE_INVALID_VP) xive_native_free_vp_block(xive->vp_base); -- cgit v1.2.3 From e8676ce50e224d507946b1c535bc13584e6b49ff Mon Sep 17 00:00:00 2001 From: Cédric Le Goater Date: Thu, 18 Apr 2019 12:39:30 +0200 Subject: KVM: PPC: Book3S HV: XIVE: Add a control to configure a source MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This control will be used by the H_INT_SET_SOURCE_CONFIG hcall from QEMU to configure the target of a source and also to restore the configuration of a source when migrating the VM. The XIVE source interrupt structure is extended with the value of the Effective Interrupt Source Number. The EISN is the interrupt number pushed in the event queue that the guest OS will use to dispatch events internally. Caching the EISN value in KVM eases the test when checking if a reconfiguration is indeed needed. Signed-off-by: Cédric Le Goater Reviewed-by: David Gibson Signed-off-by: Paul Mackerras --- Documentation/virtual/kvm/devices/xive.txt | 21 +++++++ arch/powerpc/include/uapi/asm/kvm.h | 11 ++++ arch/powerpc/kvm/book3s_xive.c | 5 +- arch/powerpc/kvm/book3s_xive.h | 4 ++ arch/powerpc/kvm/book3s_xive_native.c | 97 ++++++++++++++++++++++++++++++ 5 files changed, 136 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/devices/xive.txt b/Documentation/virtual/kvm/devices/xive.txt index cd8bfc37b72e..33c64b2cdbe8 100644 --- a/Documentation/virtual/kvm/devices/xive.txt +++ b/Documentation/virtual/kvm/devices/xive.txt @@ -32,3 +32,24 @@ the legacy interrupt mode, referred as XICS (POWER7/8). -ENOMEM: Could not create a new source block -EFAULT: Invalid user pointer for attr->addr. -ENXIO: Could not allocate underlying HW interrupt + + 3. KVM_DEV_XIVE_GRP_SOURCE_CONFIG (write only) + Configures source targeting + Attributes: + Interrupt source number (64-bit) + The kvm_device_attr.addr points to a __u64 value: + bits: | 63 .... 33 | 32 | 31 .. 3 | 2 .. 0 + values: | eisn | mask | server | priority + - priority: 0-7 interrupt priority level + - server: CPU number chosen to handle the interrupt + - mask: mask flag (unused) + - eisn: Effective Interrupt Source Number + Errors: + -ENOENT: Unknown source number + -EINVAL: Not initialized source number + -EINVAL: Invalid priority + -EINVAL: Invalid CPU number. + -EFAULT: Invalid user pointer for attr->addr. + -ENXIO: CPU event queues not configured or configuration of the + underlying HW interrupt failed + -EBUSY: No CPU available to serve interrupt diff --git a/arch/powerpc/include/uapi/asm/kvm.h b/arch/powerpc/include/uapi/asm/kvm.h index d468294c2a67..e8161e21629b 100644 --- a/arch/powerpc/include/uapi/asm/kvm.h +++ b/arch/powerpc/include/uapi/asm/kvm.h @@ -680,9 +680,20 @@ struct kvm_ppc_cpu_char { /* POWER9 XIVE Native Interrupt Controller */ #define KVM_DEV_XIVE_GRP_CTRL 1 #define KVM_DEV_XIVE_GRP_SOURCE 2 /* 64-bit source identifier */ +#define KVM_DEV_XIVE_GRP_SOURCE_CONFIG 3 /* 64-bit source identifier */ /* Layout of 64-bit XIVE source attribute values */ #define KVM_XIVE_LEVEL_SENSITIVE (1ULL << 0) #define KVM_XIVE_LEVEL_ASSERTED (1ULL << 1) +/* Layout of 64-bit XIVE source configuration attribute values */ +#define KVM_XIVE_SOURCE_PRIORITY_SHIFT 0 +#define KVM_XIVE_SOURCE_PRIORITY_MASK 0x7 +#define KVM_XIVE_SOURCE_SERVER_SHIFT 3 +#define KVM_XIVE_SOURCE_SERVER_MASK 0xfffffff8ULL +#define KVM_XIVE_SOURCE_MASKED_SHIFT 32 +#define KVM_XIVE_SOURCE_MASKED_MASK 0x100000000ULL +#define KVM_XIVE_SOURCE_EISN_SHIFT 33 +#define KVM_XIVE_SOURCE_EISN_MASK 0xfffffffe00000000ULL + #endif /* __LINUX_KVM_POWERPC_H */ diff --git a/arch/powerpc/kvm/book3s_xive.c b/arch/powerpc/kvm/book3s_xive.c index 6c9f9fd0855f..e09f3addffe5 100644 --- a/arch/powerpc/kvm/book3s_xive.c +++ b/arch/powerpc/kvm/book3s_xive.c @@ -342,7 +342,7 @@ static int xive_try_pick_queue(struct kvm_vcpu *vcpu, u8 prio) return atomic_add_unless(&q->count, 1, max) ? 0 : -EBUSY; } -static int xive_select_target(struct kvm *kvm, u32 *server, u8 prio) +int kvmppc_xive_select_target(struct kvm *kvm, u32 *server, u8 prio) { struct kvm_vcpu *vcpu; int i, rc; @@ -530,7 +530,7 @@ static int xive_target_interrupt(struct kvm *kvm, * priority. The count for that new target will have * already been incremented. */ - rc = xive_select_target(kvm, &server, prio); + rc = kvmppc_xive_select_target(kvm, &server, prio); /* * We failed to find a target ? Not much we can do @@ -1504,6 +1504,7 @@ struct kvmppc_xive_src_block *kvmppc_xive_create_src_block( for (i = 0; i < KVMPPC_XICS_IRQ_PER_ICS; i++) { sb->irq_state[i].number = (bid << KVMPPC_XICS_ICS_SHIFT) | i; + sb->irq_state[i].eisn = 0; sb->irq_state[i].guest_priority = MASKED; sb->irq_state[i].saved_priority = MASKED; sb->irq_state[i].act_priority = MASKED; diff --git a/arch/powerpc/kvm/book3s_xive.h b/arch/powerpc/kvm/book3s_xive.h index 1be921cb5dcb..ae26fe653d98 100644 --- a/arch/powerpc/kvm/book3s_xive.h +++ b/arch/powerpc/kvm/book3s_xive.h @@ -61,6 +61,9 @@ struct kvmppc_xive_irq_state { bool saved_p; bool saved_q; u8 saved_scan_prio; + + /* Xive native */ + u32 eisn; /* Guest Effective IRQ number */ }; /* Select the "right" interrupt (IPI vs. passthrough) */ @@ -268,6 +271,7 @@ int kvmppc_xive_debug_show_queues(struct seq_file *m, struct kvm_vcpu *vcpu); struct kvmppc_xive_src_block *kvmppc_xive_create_src_block( struct kvmppc_xive *xive, int irq); void kvmppc_xive_free_sources(struct kvmppc_xive_src_block *sb); +int kvmppc_xive_select_target(struct kvm *kvm, u32 *server, u8 prio); #endif /* CONFIG_KVM_XICS */ #endif /* _KVM_PPC_BOOK3S_XICS_H */ diff --git a/arch/powerpc/kvm/book3s_xive_native.c b/arch/powerpc/kvm/book3s_xive_native.c index 5f2bd6c137b7..492825a35958 100644 --- a/arch/powerpc/kvm/book3s_xive_native.c +++ b/arch/powerpc/kvm/book3s_xive_native.c @@ -242,6 +242,99 @@ unlock: return rc; } +static int kvmppc_xive_native_update_source_config(struct kvmppc_xive *xive, + struct kvmppc_xive_src_block *sb, + struct kvmppc_xive_irq_state *state, + u32 server, u8 priority, bool masked, + u32 eisn) +{ + struct kvm *kvm = xive->kvm; + u32 hw_num; + int rc = 0; + + arch_spin_lock(&sb->lock); + + if (state->act_server == server && state->act_priority == priority && + state->eisn == eisn) + goto unlock; + + pr_devel("new_act_prio=%d new_act_server=%d mask=%d act_server=%d act_prio=%d\n", + priority, server, masked, state->act_server, + state->act_priority); + + kvmppc_xive_select_irq(state, &hw_num, NULL); + + if (priority != MASKED && !masked) { + rc = kvmppc_xive_select_target(kvm, &server, priority); + if (rc) + goto unlock; + + state->act_priority = priority; + state->act_server = server; + state->eisn = eisn; + + rc = xive_native_configure_irq(hw_num, + kvmppc_xive_vp(xive, server), + priority, eisn); + } else { + state->act_priority = MASKED; + state->act_server = 0; + state->eisn = 0; + + rc = xive_native_configure_irq(hw_num, 0, MASKED, 0); + } + +unlock: + arch_spin_unlock(&sb->lock); + return rc; +} + +static int kvmppc_xive_native_set_source_config(struct kvmppc_xive *xive, + long irq, u64 addr) +{ + struct kvmppc_xive_src_block *sb; + struct kvmppc_xive_irq_state *state; + u64 __user *ubufp = (u64 __user *) addr; + u16 src; + u64 kvm_cfg; + u32 server; + u8 priority; + bool masked; + u32 eisn; + + sb = kvmppc_xive_find_source(xive, irq, &src); + if (!sb) + return -ENOENT; + + state = &sb->irq_state[src]; + + if (!state->valid) + return -EINVAL; + + if (get_user(kvm_cfg, ubufp)) + return -EFAULT; + + pr_devel("%s irq=0x%lx cfg=%016llx\n", __func__, irq, kvm_cfg); + + priority = (kvm_cfg & KVM_XIVE_SOURCE_PRIORITY_MASK) >> + KVM_XIVE_SOURCE_PRIORITY_SHIFT; + server = (kvm_cfg & KVM_XIVE_SOURCE_SERVER_MASK) >> + KVM_XIVE_SOURCE_SERVER_SHIFT; + masked = (kvm_cfg & KVM_XIVE_SOURCE_MASKED_MASK) >> + KVM_XIVE_SOURCE_MASKED_SHIFT; + eisn = (kvm_cfg & KVM_XIVE_SOURCE_EISN_MASK) >> + KVM_XIVE_SOURCE_EISN_SHIFT; + + if (priority != xive_prio_from_guest(priority)) { + pr_err("invalid priority for queue %d for VCPU %d\n", + priority, server); + return -EINVAL; + } + + return kvmppc_xive_native_update_source_config(xive, sb, state, server, + priority, masked, eisn); +} + static int kvmppc_xive_native_set_attr(struct kvm_device *dev, struct kvm_device_attr *attr) { @@ -253,6 +346,9 @@ static int kvmppc_xive_native_set_attr(struct kvm_device *dev, case KVM_DEV_XIVE_GRP_SOURCE: return kvmppc_xive_native_set_source(xive, attr->attr, attr->addr); + case KVM_DEV_XIVE_GRP_SOURCE_CONFIG: + return kvmppc_xive_native_set_source_config(xive, attr->attr, + attr->addr); } return -ENXIO; } @@ -270,6 +366,7 @@ static int kvmppc_xive_native_has_attr(struct kvm_device *dev, case KVM_DEV_XIVE_GRP_CTRL: break; case KVM_DEV_XIVE_GRP_SOURCE: + case KVM_DEV_XIVE_GRP_SOURCE_CONFIG: if (attr->attr >= KVMPPC_XIVE_FIRST_IRQ && attr->attr < KVMPPC_XIVE_NR_IRQS) return 0; -- cgit v1.2.3 From 13ce3297c5766b9541b6a7a255794c5168a7ae1a Mon Sep 17 00:00:00 2001 From: Cédric Le Goater Date: Thu, 18 Apr 2019 12:39:31 +0200 Subject: KVM: PPC: Book3S HV: XIVE: Add controls for the EQ configuration MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit These controls will be used by the H_INT_SET_QUEUE_CONFIG and H_INT_GET_QUEUE_CONFIG hcalls from QEMU to configure the underlying Event Queue in the XIVE IC. They will also be used to restore the configuration of the XIVE EQs and to capture the internal run-time state of the EQs. Both 'get' and 'set' rely on an OPAL call to access the EQ toggle bit and EQ index which are updated by the XIVE IC when event notifications are enqueued in the EQ. The value of the guest physical address of the event queue is saved in the XIVE internal xive_q structure for later use. That is when migration needs to mark the EQ pages dirty to capture a consistent memory state of the VM. To be noted that H_INT_SET_QUEUE_CONFIG does not require the extra OPAL call setting the EQ toggle bit and EQ index to configure the EQ, but restoring the EQ state will. Signed-off-by: Cédric Le Goater Reviewed-by: David Gibson Signed-off-by: Paul Mackerras --- Documentation/virtual/kvm/devices/xive.txt | 34 ++++ arch/powerpc/include/asm/xive.h | 2 + arch/powerpc/include/uapi/asm/kvm.h | 19 +++ arch/powerpc/kvm/book3s_xive.c | 15 +- arch/powerpc/kvm/book3s_xive.h | 2 + arch/powerpc/kvm/book3s_xive_native.c | 249 +++++++++++++++++++++++++++++ 6 files changed, 315 insertions(+), 6 deletions(-) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/devices/xive.txt b/Documentation/virtual/kvm/devices/xive.txt index 33c64b2cdbe8..cc13bfd5cf53 100644 --- a/Documentation/virtual/kvm/devices/xive.txt +++ b/Documentation/virtual/kvm/devices/xive.txt @@ -53,3 +53,37 @@ the legacy interrupt mode, referred as XICS (POWER7/8). -ENXIO: CPU event queues not configured or configuration of the underlying HW interrupt failed -EBUSY: No CPU available to serve interrupt + + 4. KVM_DEV_XIVE_GRP_EQ_CONFIG (read-write) + Configures an event queue of a CPU + Attributes: + EQ descriptor identifier (64-bit) + The EQ descriptor identifier is a tuple (server, priority) : + bits: | 63 .... 32 | 31 .. 3 | 2 .. 0 + values: | unused | server | priority + The kvm_device_attr.addr points to : + struct kvm_ppc_xive_eq { + __u32 flags; + __u32 qshift; + __u64 qaddr; + __u32 qtoggle; + __u32 qindex; + __u8 pad[40]; + }; + - flags: queue flags + KVM_XIVE_EQ_ALWAYS_NOTIFY (required) + forces notification without using the coalescing mechanism + provided by the XIVE END ESBs. + - qshift: queue size (power of 2) + - qaddr: real address of queue + - qtoggle: current queue toggle bit + - qindex: current queue index + - pad: reserved for future use + Errors: + -ENOENT: Invalid CPU number + -EINVAL: Invalid priority + -EINVAL: Invalid flags + -EINVAL: Invalid queue size + -EINVAL: Invalid queue address + -EFAULT: Invalid user pointer for attr->addr. + -EIO: Configuration of the underlying HW failed diff --git a/arch/powerpc/include/asm/xive.h b/arch/powerpc/include/asm/xive.h index b579a943407b..c4e88abd3b67 100644 --- a/arch/powerpc/include/asm/xive.h +++ b/arch/powerpc/include/asm/xive.h @@ -73,6 +73,8 @@ struct xive_q { u32 esc_irq; atomic_t count; atomic_t pending_count; + u64 guest_qaddr; + u32 guest_qshift; }; /* Global enable flags for the XIVE support */ diff --git a/arch/powerpc/include/uapi/asm/kvm.h b/arch/powerpc/include/uapi/asm/kvm.h index e8161e21629b..85005400fd86 100644 --- a/arch/powerpc/include/uapi/asm/kvm.h +++ b/arch/powerpc/include/uapi/asm/kvm.h @@ -681,6 +681,7 @@ struct kvm_ppc_cpu_char { #define KVM_DEV_XIVE_GRP_CTRL 1 #define KVM_DEV_XIVE_GRP_SOURCE 2 /* 64-bit source identifier */ #define KVM_DEV_XIVE_GRP_SOURCE_CONFIG 3 /* 64-bit source identifier */ +#define KVM_DEV_XIVE_GRP_EQ_CONFIG 4 /* 64-bit EQ identifier */ /* Layout of 64-bit XIVE source attribute values */ #define KVM_XIVE_LEVEL_SENSITIVE (1ULL << 0) @@ -696,4 +697,22 @@ struct kvm_ppc_cpu_char { #define KVM_XIVE_SOURCE_EISN_SHIFT 33 #define KVM_XIVE_SOURCE_EISN_MASK 0xfffffffe00000000ULL +/* Layout of 64-bit EQ identifier */ +#define KVM_XIVE_EQ_PRIORITY_SHIFT 0 +#define KVM_XIVE_EQ_PRIORITY_MASK 0x7 +#define KVM_XIVE_EQ_SERVER_SHIFT 3 +#define KVM_XIVE_EQ_SERVER_MASK 0xfffffff8ULL + +/* Layout of EQ configuration values (64 bytes) */ +struct kvm_ppc_xive_eq { + __u32 flags; + __u32 qshift; + __u64 qaddr; + __u32 qtoggle; + __u32 qindex; + __u8 pad[40]; +}; + +#define KVM_XIVE_EQ_ALWAYS_NOTIFY 0x00000001 + #endif /* __LINUX_KVM_POWERPC_H */ diff --git a/arch/powerpc/kvm/book3s_xive.c b/arch/powerpc/kvm/book3s_xive.c index e09f3addffe5..c1b7aa7dbc28 100644 --- a/arch/powerpc/kvm/book3s_xive.c +++ b/arch/powerpc/kvm/book3s_xive.c @@ -166,7 +166,8 @@ static irqreturn_t xive_esc_irq(int irq, void *data) return IRQ_HANDLED; } -static int xive_attach_escalation(struct kvm_vcpu *vcpu, u8 prio) +int kvmppc_xive_attach_escalation(struct kvm_vcpu *vcpu, u8 prio, + bool single_escalation) { struct kvmppc_xive_vcpu *xc = vcpu->arch.xive_vcpu; struct xive_q *q = &xc->queues[prio]; @@ -185,7 +186,7 @@ static int xive_attach_escalation(struct kvm_vcpu *vcpu, u8 prio) return -EIO; } - if (xc->xive->single_escalation) + if (single_escalation) name = kasprintf(GFP_KERNEL, "kvm-%d-%d", vcpu->kvm->arch.lpid, xc->server_num); else @@ -217,7 +218,7 @@ static int xive_attach_escalation(struct kvm_vcpu *vcpu, u8 prio) * interrupt, thus leaving it effectively masked after * it fires once. */ - if (xc->xive->single_escalation) { + if (single_escalation) { struct irq_data *d = irq_get_irq_data(xc->esc_virq[prio]); struct xive_irq_data *xd = irq_data_get_irq_handler_data(d); @@ -291,7 +292,8 @@ static int xive_check_provisioning(struct kvm *kvm, u8 prio) continue; rc = xive_provision_queue(vcpu, prio); if (rc == 0 && !xive->single_escalation) - xive_attach_escalation(vcpu, prio); + kvmppc_xive_attach_escalation(vcpu, prio, + xive->single_escalation); if (rc) return rc; } @@ -1214,7 +1216,8 @@ int kvmppc_xive_connect_vcpu(struct kvm_device *dev, if (xive->qmap & (1 << i)) { r = xive_provision_queue(vcpu, i); if (r == 0 && !xive->single_escalation) - xive_attach_escalation(vcpu, i); + kvmppc_xive_attach_escalation( + vcpu, i, xive->single_escalation); if (r) goto bail; } else { @@ -1229,7 +1232,7 @@ int kvmppc_xive_connect_vcpu(struct kvm_device *dev, } /* If not done above, attach priority 0 escalation */ - r = xive_attach_escalation(vcpu, 0); + r = kvmppc_xive_attach_escalation(vcpu, 0, xive->single_escalation); if (r) goto bail; diff --git a/arch/powerpc/kvm/book3s_xive.h b/arch/powerpc/kvm/book3s_xive.h index ae26fe653d98..622f594d93e1 100644 --- a/arch/powerpc/kvm/book3s_xive.h +++ b/arch/powerpc/kvm/book3s_xive.h @@ -272,6 +272,8 @@ struct kvmppc_xive_src_block *kvmppc_xive_create_src_block( struct kvmppc_xive *xive, int irq); void kvmppc_xive_free_sources(struct kvmppc_xive_src_block *sb); int kvmppc_xive_select_target(struct kvm *kvm, u32 *server, u8 prio); +int kvmppc_xive_attach_escalation(struct kvm_vcpu *vcpu, u8 prio, + bool single_escalation); #endif /* CONFIG_KVM_XICS */ #endif /* _KVM_PPC_BOOK3S_XICS_H */ diff --git a/arch/powerpc/kvm/book3s_xive_native.c b/arch/powerpc/kvm/book3s_xive_native.c index 492825a35958..3e7cdcacc932 100644 --- a/arch/powerpc/kvm/book3s_xive_native.c +++ b/arch/powerpc/kvm/book3s_xive_native.c @@ -335,6 +335,243 @@ static int kvmppc_xive_native_set_source_config(struct kvmppc_xive *xive, priority, masked, eisn); } +static int xive_native_validate_queue_size(u32 qshift) +{ + /* + * We only support 64K pages for the moment. This is also + * advertised in the DT property "ibm,xive-eq-sizes" + */ + switch (qshift) { + case 0: /* EQ reset */ + case 16: + return 0; + case 12: + case 21: + case 24: + default: + return -EINVAL; + } +} + +static int kvmppc_xive_native_set_queue_config(struct kvmppc_xive *xive, + long eq_idx, u64 addr) +{ + struct kvm *kvm = xive->kvm; + struct kvm_vcpu *vcpu; + struct kvmppc_xive_vcpu *xc; + void __user *ubufp = (void __user *) addr; + u32 server; + u8 priority; + struct kvm_ppc_xive_eq kvm_eq; + int rc; + __be32 *qaddr = 0; + struct page *page; + struct xive_q *q; + gfn_t gfn; + unsigned long page_size; + + /* + * Demangle priority/server tuple from the EQ identifier + */ + priority = (eq_idx & KVM_XIVE_EQ_PRIORITY_MASK) >> + KVM_XIVE_EQ_PRIORITY_SHIFT; + server = (eq_idx & KVM_XIVE_EQ_SERVER_MASK) >> + KVM_XIVE_EQ_SERVER_SHIFT; + + if (copy_from_user(&kvm_eq, ubufp, sizeof(kvm_eq))) + return -EFAULT; + + vcpu = kvmppc_xive_find_server(kvm, server); + if (!vcpu) { + pr_err("Can't find server %d\n", server); + return -ENOENT; + } + xc = vcpu->arch.xive_vcpu; + + if (priority != xive_prio_from_guest(priority)) { + pr_err("Trying to restore invalid queue %d for VCPU %d\n", + priority, server); + return -EINVAL; + } + q = &xc->queues[priority]; + + pr_devel("%s VCPU %d priority %d fl:%x shift:%d addr:%llx g:%d idx:%d\n", + __func__, server, priority, kvm_eq.flags, + kvm_eq.qshift, kvm_eq.qaddr, kvm_eq.qtoggle, kvm_eq.qindex); + + /* + * sPAPR specifies a "Unconditional Notify (n) flag" for the + * H_INT_SET_QUEUE_CONFIG hcall which forces notification + * without using the coalescing mechanisms provided by the + * XIVE END ESBs. This is required on KVM as notification + * using the END ESBs is not supported. + */ + if (kvm_eq.flags != KVM_XIVE_EQ_ALWAYS_NOTIFY) { + pr_err("invalid flags %d\n", kvm_eq.flags); + return -EINVAL; + } + + rc = xive_native_validate_queue_size(kvm_eq.qshift); + if (rc) { + pr_err("invalid queue size %d\n", kvm_eq.qshift); + return rc; + } + + /* reset queue and disable queueing */ + if (!kvm_eq.qshift) { + q->guest_qaddr = 0; + q->guest_qshift = 0; + + rc = xive_native_configure_queue(xc->vp_id, q, priority, + NULL, 0, true); + if (rc) { + pr_err("Failed to reset queue %d for VCPU %d: %d\n", + priority, xc->server_num, rc); + return rc; + } + + if (q->qpage) { + put_page(virt_to_page(q->qpage)); + q->qpage = NULL; + } + + return 0; + } + + if (kvm_eq.qaddr & ((1ull << kvm_eq.qshift) - 1)) { + pr_err("queue page is not aligned %llx/%llx\n", kvm_eq.qaddr, + 1ull << kvm_eq.qshift); + return -EINVAL; + } + + gfn = gpa_to_gfn(kvm_eq.qaddr); + page = gfn_to_page(kvm, gfn); + if (is_error_page(page)) { + pr_err("Couldn't get queue page %llx!\n", kvm_eq.qaddr); + return -EINVAL; + } + + page_size = kvm_host_page_size(kvm, gfn); + if (1ull << kvm_eq.qshift > page_size) { + pr_warn("Incompatible host page size %lx!\n", page_size); + return -EINVAL; + } + + qaddr = page_to_virt(page) + (kvm_eq.qaddr & ~PAGE_MASK); + + /* + * Backup the queue page guest address to the mark EQ page + * dirty for migration. + */ + q->guest_qaddr = kvm_eq.qaddr; + q->guest_qshift = kvm_eq.qshift; + + /* + * Unconditional Notification is forced by default at the + * OPAL level because the use of END ESBs is not supported by + * Linux. + */ + rc = xive_native_configure_queue(xc->vp_id, q, priority, + (__be32 *) qaddr, kvm_eq.qshift, true); + if (rc) { + pr_err("Failed to configure queue %d for VCPU %d: %d\n", + priority, xc->server_num, rc); + put_page(page); + return rc; + } + + /* + * Only restore the queue state when needed. When doing the + * H_INT_SET_SOURCE_CONFIG hcall, it should not. + */ + if (kvm_eq.qtoggle != 1 || kvm_eq.qindex != 0) { + rc = xive_native_set_queue_state(xc->vp_id, priority, + kvm_eq.qtoggle, + kvm_eq.qindex); + if (rc) + goto error; + } + + rc = kvmppc_xive_attach_escalation(vcpu, priority, + xive->single_escalation); +error: + if (rc) + kvmppc_xive_native_cleanup_queue(vcpu, priority); + return rc; +} + +static int kvmppc_xive_native_get_queue_config(struct kvmppc_xive *xive, + long eq_idx, u64 addr) +{ + struct kvm *kvm = xive->kvm; + struct kvm_vcpu *vcpu; + struct kvmppc_xive_vcpu *xc; + struct xive_q *q; + void __user *ubufp = (u64 __user *) addr; + u32 server; + u8 priority; + struct kvm_ppc_xive_eq kvm_eq; + u64 qaddr; + u64 qshift; + u64 qeoi_page; + u32 escalate_irq; + u64 qflags; + int rc; + + /* + * Demangle priority/server tuple from the EQ identifier + */ + priority = (eq_idx & KVM_XIVE_EQ_PRIORITY_MASK) >> + KVM_XIVE_EQ_PRIORITY_SHIFT; + server = (eq_idx & KVM_XIVE_EQ_SERVER_MASK) >> + KVM_XIVE_EQ_SERVER_SHIFT; + + vcpu = kvmppc_xive_find_server(kvm, server); + if (!vcpu) { + pr_err("Can't find server %d\n", server); + return -ENOENT; + } + xc = vcpu->arch.xive_vcpu; + + if (priority != xive_prio_from_guest(priority)) { + pr_err("invalid priority for queue %d for VCPU %d\n", + priority, server); + return -EINVAL; + } + q = &xc->queues[priority]; + + memset(&kvm_eq, 0, sizeof(kvm_eq)); + + if (!q->qpage) + return 0; + + rc = xive_native_get_queue_info(xc->vp_id, priority, &qaddr, &qshift, + &qeoi_page, &escalate_irq, &qflags); + if (rc) + return rc; + + kvm_eq.flags = 0; + if (qflags & OPAL_XIVE_EQ_ALWAYS_NOTIFY) + kvm_eq.flags |= KVM_XIVE_EQ_ALWAYS_NOTIFY; + + kvm_eq.qshift = q->guest_qshift; + kvm_eq.qaddr = q->guest_qaddr; + + rc = xive_native_get_queue_state(xc->vp_id, priority, &kvm_eq.qtoggle, + &kvm_eq.qindex); + if (rc) + return rc; + + pr_devel("%s VCPU %d priority %d fl:%x shift:%d addr:%llx g:%d idx:%d\n", + __func__, server, priority, kvm_eq.flags, + kvm_eq.qshift, kvm_eq.qaddr, kvm_eq.qtoggle, kvm_eq.qindex); + + if (copy_to_user(ubufp, &kvm_eq, sizeof(kvm_eq))) + return -EFAULT; + + return 0; +} + static int kvmppc_xive_native_set_attr(struct kvm_device *dev, struct kvm_device_attr *attr) { @@ -349,6 +586,9 @@ static int kvmppc_xive_native_set_attr(struct kvm_device *dev, case KVM_DEV_XIVE_GRP_SOURCE_CONFIG: return kvmppc_xive_native_set_source_config(xive, attr->attr, attr->addr); + case KVM_DEV_XIVE_GRP_EQ_CONFIG: + return kvmppc_xive_native_set_queue_config(xive, attr->attr, + attr->addr); } return -ENXIO; } @@ -356,6 +596,13 @@ static int kvmppc_xive_native_set_attr(struct kvm_device *dev, static int kvmppc_xive_native_get_attr(struct kvm_device *dev, struct kvm_device_attr *attr) { + struct kvmppc_xive *xive = dev->private; + + switch (attr->group) { + case KVM_DEV_XIVE_GRP_EQ_CONFIG: + return kvmppc_xive_native_get_queue_config(xive, attr->attr, + attr->addr); + } return -ENXIO; } @@ -371,6 +618,8 @@ static int kvmppc_xive_native_has_attr(struct kvm_device *dev, attr->attr < KVMPPC_XIVE_NR_IRQS) return 0; break; + case KVM_DEV_XIVE_GRP_EQ_CONFIG: + return 0; } return -ENXIO; } -- cgit v1.2.3 From 5ca806474859a0e94584b3a63f9509a25758408e Mon Sep 17 00:00:00 2001 From: Cédric Le Goater Date: Thu, 18 Apr 2019 12:39:32 +0200 Subject: KVM: PPC: Book3S HV: XIVE: Add a global reset control MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This control is to be used by the H_INT_RESET hcall from QEMU. Its purpose is to clear all configuration of the sources and EQs. This is necessary in case of a kexec (for a kdump kernel for instance) to make sure that no remaining configuration is left from the previous boot setup so that the new kernel can start safely from a clean state. The queue 7 is ignored when the XIVE device is configured to run in single escalation mode. Prio 7 is used by escalations. The XIVE VP is kept enabled as the vCPU is still active and connected to the XIVE device. Signed-off-by: Cédric Le Goater Reviewed-by: David Gibson Signed-off-by: Paul Mackerras --- Documentation/virtual/kvm/devices/xive.txt | 5 ++ arch/powerpc/include/uapi/asm/kvm.h | 1 + arch/powerpc/kvm/book3s_xive_native.c | 85 ++++++++++++++++++++++++++++++ 3 files changed, 91 insertions(+) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/devices/xive.txt b/Documentation/virtual/kvm/devices/xive.txt index cc13bfd5cf53..429cbc4cf960 100644 --- a/Documentation/virtual/kvm/devices/xive.txt +++ b/Documentation/virtual/kvm/devices/xive.txt @@ -17,6 +17,11 @@ the legacy interrupt mode, referred as XICS (POWER7/8). 1. KVM_DEV_XIVE_GRP_CTRL Provides global controls on the device + Attributes: + 1.1 KVM_DEV_XIVE_RESET (write only) + Resets the interrupt controller configuration for sources and event + queues. To be used by kexec and kdump. + Errors: none 2. KVM_DEV_XIVE_GRP_SOURCE (write only) Initializes a new source in the XIVE device and mask it. diff --git a/arch/powerpc/include/uapi/asm/kvm.h b/arch/powerpc/include/uapi/asm/kvm.h index 85005400fd86..f045f9dee42e 100644 --- a/arch/powerpc/include/uapi/asm/kvm.h +++ b/arch/powerpc/include/uapi/asm/kvm.h @@ -679,6 +679,7 @@ struct kvm_ppc_cpu_char { /* POWER9 XIVE Native Interrupt Controller */ #define KVM_DEV_XIVE_GRP_CTRL 1 +#define KVM_DEV_XIVE_RESET 1 #define KVM_DEV_XIVE_GRP_SOURCE 2 /* 64-bit source identifier */ #define KVM_DEV_XIVE_GRP_SOURCE_CONFIG 3 /* 64-bit source identifier */ #define KVM_DEV_XIVE_GRP_EQ_CONFIG 4 /* 64-bit EQ identifier */ diff --git a/arch/powerpc/kvm/book3s_xive_native.c b/arch/powerpc/kvm/book3s_xive_native.c index 3e7cdcacc932..b9597d80c95a 100644 --- a/arch/powerpc/kvm/book3s_xive_native.c +++ b/arch/powerpc/kvm/book3s_xive_native.c @@ -572,6 +572,83 @@ static int kvmppc_xive_native_get_queue_config(struct kvmppc_xive *xive, return 0; } +static void kvmppc_xive_reset_sources(struct kvmppc_xive_src_block *sb) +{ + int i; + + for (i = 0; i < KVMPPC_XICS_IRQ_PER_ICS; i++) { + struct kvmppc_xive_irq_state *state = &sb->irq_state[i]; + + if (!state->valid) + continue; + + if (state->act_priority == MASKED) + continue; + + state->eisn = 0; + state->act_server = 0; + state->act_priority = MASKED; + xive_vm_esb_load(&state->ipi_data, XIVE_ESB_SET_PQ_01); + xive_native_configure_irq(state->ipi_number, 0, MASKED, 0); + if (state->pt_number) { + xive_vm_esb_load(state->pt_data, XIVE_ESB_SET_PQ_01); + xive_native_configure_irq(state->pt_number, + 0, MASKED, 0); + } + } +} + +static int kvmppc_xive_reset(struct kvmppc_xive *xive) +{ + struct kvm *kvm = xive->kvm; + struct kvm_vcpu *vcpu; + unsigned int i; + + pr_devel("%s\n", __func__); + + mutex_lock(&kvm->lock); + + kvm_for_each_vcpu(i, vcpu, kvm) { + struct kvmppc_xive_vcpu *xc = vcpu->arch.xive_vcpu; + unsigned int prio; + + if (!xc) + continue; + + kvmppc_xive_disable_vcpu_interrupts(vcpu); + + for (prio = 0; prio < KVMPPC_XIVE_Q_COUNT; prio++) { + + /* Single escalation, no queue 7 */ + if (prio == 7 && xive->single_escalation) + break; + + if (xc->esc_virq[prio]) { + free_irq(xc->esc_virq[prio], vcpu); + irq_dispose_mapping(xc->esc_virq[prio]); + kfree(xc->esc_virq_names[prio]); + xc->esc_virq[prio] = 0; + } + + kvmppc_xive_native_cleanup_queue(vcpu, prio); + } + } + + for (i = 0; i <= xive->max_sbid; i++) { + struct kvmppc_xive_src_block *sb = xive->src_blocks[i]; + + if (sb) { + arch_spin_lock(&sb->lock); + kvmppc_xive_reset_sources(sb); + arch_spin_unlock(&sb->lock); + } + } + + mutex_unlock(&kvm->lock); + + return 0; +} + static int kvmppc_xive_native_set_attr(struct kvm_device *dev, struct kvm_device_attr *attr) { @@ -579,6 +656,10 @@ static int kvmppc_xive_native_set_attr(struct kvm_device *dev, switch (attr->group) { case KVM_DEV_XIVE_GRP_CTRL: + switch (attr->attr) { + case KVM_DEV_XIVE_RESET: + return kvmppc_xive_reset(xive); + } break; case KVM_DEV_XIVE_GRP_SOURCE: return kvmppc_xive_native_set_source(xive, attr->attr, @@ -611,6 +692,10 @@ static int kvmppc_xive_native_has_attr(struct kvm_device *dev, { switch (attr->group) { case KVM_DEV_XIVE_GRP_CTRL: + switch (attr->attr) { + case KVM_DEV_XIVE_RESET: + return 0; + } break; case KVM_DEV_XIVE_GRP_SOURCE: case KVM_DEV_XIVE_GRP_SOURCE_CONFIG: -- cgit v1.2.3 From 7b46b6169ab80f8f415a0ca2ea4aa7f1afdcc4f3 Mon Sep 17 00:00:00 2001 From: Cédric Le Goater Date: Thu, 18 Apr 2019 12:39:33 +0200 Subject: KVM: PPC: Book3S HV: XIVE: Add a control to sync the sources MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This control will be used by the H_INT_SYNC hcall from QEMU to flush event notifications on the XIVE IC owning the source. Signed-off-by: Cédric Le Goater Reviewed-by: David Gibson Signed-off-by: Paul Mackerras --- Documentation/virtual/kvm/devices/xive.txt | 8 +++++++ arch/powerpc/include/uapi/asm/kvm.h | 1 + arch/powerpc/kvm/book3s_xive_native.c | 36 ++++++++++++++++++++++++++++++ 3 files changed, 45 insertions(+) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/devices/xive.txt b/Documentation/virtual/kvm/devices/xive.txt index 429cbc4cf960..1e7f19d7594b 100644 --- a/Documentation/virtual/kvm/devices/xive.txt +++ b/Documentation/virtual/kvm/devices/xive.txt @@ -92,3 +92,11 @@ the legacy interrupt mode, referred as XICS (POWER7/8). -EINVAL: Invalid queue address -EFAULT: Invalid user pointer for attr->addr. -EIO: Configuration of the underlying HW failed + + 5. KVM_DEV_XIVE_GRP_SOURCE_SYNC (write only) + Synchronize the source to flush event notifications + Attributes: + Interrupt source number (64-bit) + Errors: + -ENOENT: Unknown source number + -EINVAL: Not initialized source number diff --git a/arch/powerpc/include/uapi/asm/kvm.h b/arch/powerpc/include/uapi/asm/kvm.h index f045f9dee42e..e4abe30f6fc6 100644 --- a/arch/powerpc/include/uapi/asm/kvm.h +++ b/arch/powerpc/include/uapi/asm/kvm.h @@ -683,6 +683,7 @@ struct kvm_ppc_cpu_char { #define KVM_DEV_XIVE_GRP_SOURCE 2 /* 64-bit source identifier */ #define KVM_DEV_XIVE_GRP_SOURCE_CONFIG 3 /* 64-bit source identifier */ #define KVM_DEV_XIVE_GRP_EQ_CONFIG 4 /* 64-bit EQ identifier */ +#define KVM_DEV_XIVE_GRP_SOURCE_SYNC 5 /* 64-bit source identifier */ /* Layout of 64-bit XIVE source attribute values */ #define KVM_XIVE_LEVEL_SENSITIVE (1ULL << 0) diff --git a/arch/powerpc/kvm/book3s_xive_native.c b/arch/powerpc/kvm/book3s_xive_native.c index b9597d80c95a..65380416d101 100644 --- a/arch/powerpc/kvm/book3s_xive_native.c +++ b/arch/powerpc/kvm/book3s_xive_native.c @@ -335,6 +335,38 @@ static int kvmppc_xive_native_set_source_config(struct kvmppc_xive *xive, priority, masked, eisn); } +static int kvmppc_xive_native_sync_source(struct kvmppc_xive *xive, + long irq, u64 addr) +{ + struct kvmppc_xive_src_block *sb; + struct kvmppc_xive_irq_state *state; + struct xive_irq_data *xd; + u32 hw_num; + u16 src; + int rc = 0; + + pr_devel("%s irq=0x%lx", __func__, irq); + + sb = kvmppc_xive_find_source(xive, irq, &src); + if (!sb) + return -ENOENT; + + state = &sb->irq_state[src]; + + rc = -EINVAL; + + arch_spin_lock(&sb->lock); + + if (state->valid) { + kvmppc_xive_select_irq(state, &hw_num, &xd); + xive_native_sync_source(hw_num); + rc = 0; + } + + arch_spin_unlock(&sb->lock); + return rc; +} + static int xive_native_validate_queue_size(u32 qshift) { /* @@ -670,6 +702,9 @@ static int kvmppc_xive_native_set_attr(struct kvm_device *dev, case KVM_DEV_XIVE_GRP_EQ_CONFIG: return kvmppc_xive_native_set_queue_config(xive, attr->attr, attr->addr); + case KVM_DEV_XIVE_GRP_SOURCE_SYNC: + return kvmppc_xive_native_sync_source(xive, attr->attr, + attr->addr); } return -ENXIO; } @@ -699,6 +734,7 @@ static int kvmppc_xive_native_has_attr(struct kvm_device *dev, break; case KVM_DEV_XIVE_GRP_SOURCE: case KVM_DEV_XIVE_GRP_SOURCE_CONFIG: + case KVM_DEV_XIVE_GRP_SOURCE_SYNC: if (attr->attr >= KVMPPC_XIVE_FIRST_IRQ && attr->attr < KVMPPC_XIVE_NR_IRQS) return 0; -- cgit v1.2.3 From e6714bd1671da9d8dfb5332075df251b746fd0fd Mon Sep 17 00:00:00 2001 From: Cédric Le Goater Date: Thu, 18 Apr 2019 12:39:34 +0200 Subject: KVM: PPC: Book3S HV: XIVE: Add a control to dirty the XIVE EQ pages MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit When migration of a VM is initiated, a first copy of the RAM is transferred to the destination before the VM is stopped, but there is no guarantee that the EQ pages in which the event notifications are queued have not been modified. To make sure migration will capture a consistent memory state, the XIVE device should perform a XIVE quiesce sequence to stop the flow of event notifications and stabilize the EQs. This is the purpose of the KVM_DEV_XIVE_EQ_SYNC control which will also marks the EQ pages dirty to force their transfer. Signed-off-by: Cédric Le Goater Reviewed-by: David Gibson Signed-off-by: Paul Mackerras --- Documentation/virtual/kvm/devices/xive.txt | 29 ++++++++++ arch/powerpc/include/uapi/asm/kvm.h | 1 + arch/powerpc/kvm/book3s_xive_native.c | 85 ++++++++++++++++++++++++++++++ 3 files changed, 115 insertions(+) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/devices/xive.txt b/Documentation/virtual/kvm/devices/xive.txt index 1e7f19d7594b..7ffd4c7be7b5 100644 --- a/Documentation/virtual/kvm/devices/xive.txt +++ b/Documentation/virtual/kvm/devices/xive.txt @@ -23,6 +23,12 @@ the legacy interrupt mode, referred as XICS (POWER7/8). queues. To be used by kexec and kdump. Errors: none + 1.2 KVM_DEV_XIVE_EQ_SYNC (write only) + Sync all the sources and queues and mark the EQ pages dirty. This + to make sure that a consistent memory state is captured when + migrating the VM. + Errors: none + 2. KVM_DEV_XIVE_GRP_SOURCE (write only) Initializes a new source in the XIVE device and mask it. Attributes: @@ -100,3 +106,26 @@ the legacy interrupt mode, referred as XICS (POWER7/8). Errors: -ENOENT: Unknown source number -EINVAL: Not initialized source number + +* Migration: + + Saving the state of a VM using the XIVE native exploitation mode + should follow a specific sequence. When the VM is stopped : + + 1. Mask all sources (PQ=01) to stop the flow of events. + + 2. Sync the XIVE device with the KVM control KVM_DEV_XIVE_EQ_SYNC to + flush any in-flight event notification and to stabilize the EQs. At + this stage, the EQ pages are marked dirty to make sure they are + transferred in the migration sequence. + + 3. Capture the state of the source targeting, the EQs configuration + and the state of thread interrupt context registers. + + Restore is similar : + + 1. Restore the EQ configuration. As targeting depends on it. + 2. Restore targeting + 3. Restore the thread interrupt contexts + 4. Restore the source states + 5. Let the vCPU run diff --git a/arch/powerpc/include/uapi/asm/kvm.h b/arch/powerpc/include/uapi/asm/kvm.h index e4abe30f6fc6..12744608a61c 100644 --- a/arch/powerpc/include/uapi/asm/kvm.h +++ b/arch/powerpc/include/uapi/asm/kvm.h @@ -680,6 +680,7 @@ struct kvm_ppc_cpu_char { /* POWER9 XIVE Native Interrupt Controller */ #define KVM_DEV_XIVE_GRP_CTRL 1 #define KVM_DEV_XIVE_RESET 1 +#define KVM_DEV_XIVE_EQ_SYNC 2 #define KVM_DEV_XIVE_GRP_SOURCE 2 /* 64-bit source identifier */ #define KVM_DEV_XIVE_GRP_SOURCE_CONFIG 3 /* 64-bit source identifier */ #define KVM_DEV_XIVE_GRP_EQ_CONFIG 4 /* 64-bit EQ identifier */ diff --git a/arch/powerpc/kvm/book3s_xive_native.c b/arch/powerpc/kvm/book3s_xive_native.c index 65380416d101..16d23ef3bd39 100644 --- a/arch/powerpc/kvm/book3s_xive_native.c +++ b/arch/powerpc/kvm/book3s_xive_native.c @@ -681,6 +681,88 @@ static int kvmppc_xive_reset(struct kvmppc_xive *xive) return 0; } +static void kvmppc_xive_native_sync_sources(struct kvmppc_xive_src_block *sb) +{ + int j; + + for (j = 0; j < KVMPPC_XICS_IRQ_PER_ICS; j++) { + struct kvmppc_xive_irq_state *state = &sb->irq_state[j]; + struct xive_irq_data *xd; + u32 hw_num; + + if (!state->valid) + continue; + + /* + * The struct kvmppc_xive_irq_state reflects the state + * of the EAS configuration and not the state of the + * source. The source is masked setting the PQ bits to + * '-Q', which is what is being done before calling + * the KVM_DEV_XIVE_EQ_SYNC control. + * + * If a source EAS is configured, OPAL syncs the XIVE + * IC of the source and the XIVE IC of the previous + * target if any. + * + * So it should be fine ignoring MASKED sources as + * they have been synced already. + */ + if (state->act_priority == MASKED) + continue; + + kvmppc_xive_select_irq(state, &hw_num, &xd); + xive_native_sync_source(hw_num); + xive_native_sync_queue(hw_num); + } +} + +static int kvmppc_xive_native_vcpu_eq_sync(struct kvm_vcpu *vcpu) +{ + struct kvmppc_xive_vcpu *xc = vcpu->arch.xive_vcpu; + unsigned int prio; + + if (!xc) + return -ENOENT; + + for (prio = 0; prio < KVMPPC_XIVE_Q_COUNT; prio++) { + struct xive_q *q = &xc->queues[prio]; + + if (!q->qpage) + continue; + + /* Mark EQ page dirty for migration */ + mark_page_dirty(vcpu->kvm, gpa_to_gfn(q->guest_qaddr)); + } + return 0; +} + +static int kvmppc_xive_native_eq_sync(struct kvmppc_xive *xive) +{ + struct kvm *kvm = xive->kvm; + struct kvm_vcpu *vcpu; + unsigned int i; + + pr_devel("%s\n", __func__); + + mutex_lock(&kvm->lock); + for (i = 0; i <= xive->max_sbid; i++) { + struct kvmppc_xive_src_block *sb = xive->src_blocks[i]; + + if (sb) { + arch_spin_lock(&sb->lock); + kvmppc_xive_native_sync_sources(sb); + arch_spin_unlock(&sb->lock); + } + } + + kvm_for_each_vcpu(i, vcpu, kvm) { + kvmppc_xive_native_vcpu_eq_sync(vcpu); + } + mutex_unlock(&kvm->lock); + + return 0; +} + static int kvmppc_xive_native_set_attr(struct kvm_device *dev, struct kvm_device_attr *attr) { @@ -691,6 +773,8 @@ static int kvmppc_xive_native_set_attr(struct kvm_device *dev, switch (attr->attr) { case KVM_DEV_XIVE_RESET: return kvmppc_xive_reset(xive); + case KVM_DEV_XIVE_EQ_SYNC: + return kvmppc_xive_native_eq_sync(xive); } break; case KVM_DEV_XIVE_GRP_SOURCE: @@ -729,6 +813,7 @@ static int kvmppc_xive_native_has_attr(struct kvm_device *dev, case KVM_DEV_XIVE_GRP_CTRL: switch (attr->attr) { case KVM_DEV_XIVE_RESET: + case KVM_DEV_XIVE_EQ_SYNC: return 0; } break; -- cgit v1.2.3 From e4945b9da52b36052b7c509ca31c5ead1d165b24 Mon Sep 17 00:00:00 2001 From: Cédric Le Goater Date: Thu, 18 Apr 2019 12:39:35 +0200 Subject: KVM: PPC: Book3S HV: XIVE: Add get/set accessors for the VP XIVE state MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The state of the thread interrupt management registers needs to be collected for migration. These registers are cached under the 'xive_saved_state.w01' field of the VCPU when the VPCU context is pulled from the HW thread. An OPAL call retrieves the backup of the IPB register in the underlying XIVE NVT structure and merges it in the KVM state. Signed-off-by: Cédric Le Goater Reviewed-by: David Gibson Signed-off-by: Paul Mackerras --- Documentation/virtual/kvm/api.txt | 1 + Documentation/virtual/kvm/devices/xive.txt | 17 +++++++ arch/powerpc/include/asm/kvm_ppc.h | 11 +++++ arch/powerpc/include/uapi/asm/kvm.h | 2 + arch/powerpc/kvm/book3s.c | 24 ++++++++++ arch/powerpc/kvm/book3s_xive_native.c | 76 ++++++++++++++++++++++++++++++ 6 files changed, 131 insertions(+) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/api.txt b/Documentation/virtual/kvm/api.txt index e38eb17b7be6..5b505520a616 100644 --- a/Documentation/virtual/kvm/api.txt +++ b/Documentation/virtual/kvm/api.txt @@ -1985,6 +1985,7 @@ registers, find a list below: PPC | KVM_REG_PPC_TLB3PS | 32 PPC | KVM_REG_PPC_EPTCFG | 32 PPC | KVM_REG_PPC_ICP_STATE | 64 + PPC | KVM_REG_PPC_VP_STATE | 128 PPC | KVM_REG_PPC_TB_OFFSET | 64 PPC | KVM_REG_PPC_SPMC1 | 32 PPC | KVM_REG_PPC_SPMC2 | 32 diff --git a/Documentation/virtual/kvm/devices/xive.txt b/Documentation/virtual/kvm/devices/xive.txt index 7ffd4c7be7b5..525d1eebcf34 100644 --- a/Documentation/virtual/kvm/devices/xive.txt +++ b/Documentation/virtual/kvm/devices/xive.txt @@ -107,6 +107,23 @@ the legacy interrupt mode, referred as XICS (POWER7/8). -ENOENT: Unknown source number -EINVAL: Not initialized source number +* VCPU state + + The XIVE IC maintains VP interrupt state in an internal structure + called the NVT. When a VP is not dispatched on a HW processor + thread, this structure can be updated by HW if the VP is the target + of an event notification. + + It is important for migration to capture the cached IPB from the NVT + as it synthesizes the priorities of the pending interrupts. We + capture a bit more to report debug information. + + KVM_REG_PPC_VP_STATE (2 * 64bits) + bits: | 63 .... 32 | 31 .... 0 | + values: | TIMA word0 | TIMA word1 | + bits: | 127 .......... 64 | + values: | unused | + * Migration: Saving the state of a VM using the XIVE native exploitation mode diff --git a/arch/powerpc/include/asm/kvm_ppc.h b/arch/powerpc/include/asm/kvm_ppc.h index 9fc2753e516e..bc892380e6cd 100644 --- a/arch/powerpc/include/asm/kvm_ppc.h +++ b/arch/powerpc/include/asm/kvm_ppc.h @@ -269,6 +269,7 @@ union kvmppc_one_reg { u64 addr; u64 length; } vpaval; + u64 xive_timaval[2]; }; struct kvmppc_ops { @@ -604,6 +605,10 @@ extern int kvmppc_xive_native_connect_vcpu(struct kvm_device *dev, extern void kvmppc_xive_native_cleanup_vcpu(struct kvm_vcpu *vcpu); extern void kvmppc_xive_native_init_module(void); extern void kvmppc_xive_native_exit_module(void); +extern int kvmppc_xive_native_get_vp(struct kvm_vcpu *vcpu, + union kvmppc_one_reg *val); +extern int kvmppc_xive_native_set_vp(struct kvm_vcpu *vcpu, + union kvmppc_one_reg *val); #else static inline int kvmppc_xive_set_xive(struct kvm *kvm, u32 irq, u32 server, @@ -636,6 +641,12 @@ static inline int kvmppc_xive_native_connect_vcpu(struct kvm_device *dev, static inline void kvmppc_xive_native_cleanup_vcpu(struct kvm_vcpu *vcpu) { } static inline void kvmppc_xive_native_init_module(void) { } static inline void kvmppc_xive_native_exit_module(void) { } +static inline int kvmppc_xive_native_get_vp(struct kvm_vcpu *vcpu, + union kvmppc_one_reg *val) +{ return 0; } +static inline int kvmppc_xive_native_set_vp(struct kvm_vcpu *vcpu, + union kvmppc_one_reg *val) +{ return -ENOENT; } #endif /* CONFIG_KVM_XIVE */ diff --git a/arch/powerpc/include/uapi/asm/kvm.h b/arch/powerpc/include/uapi/asm/kvm.h index 12744608a61c..cd3f16b70a2e 100644 --- a/arch/powerpc/include/uapi/asm/kvm.h +++ b/arch/powerpc/include/uapi/asm/kvm.h @@ -482,6 +482,8 @@ struct kvm_ppc_cpu_char { #define KVM_REG_PPC_ICP_PPRI_SHIFT 16 /* pending irq priority */ #define KVM_REG_PPC_ICP_PPRI_MASK 0xff +#define KVM_REG_PPC_VP_STATE (KVM_REG_PPC | KVM_REG_SIZE_U128 | 0x8d) + /* Device control API: PPC-specific devices */ #define KVM_DEV_MPIC_GRP_MISC 1 #define KVM_DEV_MPIC_BASE_ADDR 0 /* 64-bit */ diff --git a/arch/powerpc/kvm/book3s.c b/arch/powerpc/kvm/book3s.c index 7c3348fa27e1..efd15101eef0 100644 --- a/arch/powerpc/kvm/book3s.c +++ b/arch/powerpc/kvm/book3s.c @@ -651,6 +651,18 @@ int kvmppc_get_one_reg(struct kvm_vcpu *vcpu, u64 id, *val = get_reg_val(id, kvmppc_xics_get_icp(vcpu)); break; #endif /* CONFIG_KVM_XICS */ +#ifdef CONFIG_KVM_XIVE + case KVM_REG_PPC_VP_STATE: + if (!vcpu->arch.xive_vcpu) { + r = -ENXIO; + break; + } + if (xive_enabled()) + r = kvmppc_xive_native_get_vp(vcpu, val); + else + r = -ENXIO; + break; +#endif /* CONFIG_KVM_XIVE */ case KVM_REG_PPC_FSCR: *val = get_reg_val(id, vcpu->arch.fscr); break; @@ -724,6 +736,18 @@ int kvmppc_set_one_reg(struct kvm_vcpu *vcpu, u64 id, r = kvmppc_xics_set_icp(vcpu, set_reg_val(id, *val)); break; #endif /* CONFIG_KVM_XICS */ +#ifdef CONFIG_KVM_XIVE + case KVM_REG_PPC_VP_STATE: + if (!vcpu->arch.xive_vcpu) { + r = -ENXIO; + break; + } + if (xive_enabled()) + r = kvmppc_xive_native_set_vp(vcpu, val); + else + r = -ENXIO; + break; +#endif /* CONFIG_KVM_XIVE */ case KVM_REG_PPC_FSCR: vcpu->arch.fscr = set_reg_val(id, *val); break; diff --git a/arch/powerpc/kvm/book3s_xive_native.c b/arch/powerpc/kvm/book3s_xive_native.c index 16d23ef3bd39..2f9d5e9439a6 100644 --- a/arch/powerpc/kvm/book3s_xive_native.c +++ b/arch/powerpc/kvm/book3s_xive_native.c @@ -896,6 +896,82 @@ static int kvmppc_xive_native_create(struct kvm_device *dev, u32 type) return ret; } +/* + * Interrupt Pending Buffer (IPB) offset + */ +#define TM_IPB_SHIFT 40 +#define TM_IPB_MASK (((u64) 0xFF) << TM_IPB_SHIFT) + +int kvmppc_xive_native_get_vp(struct kvm_vcpu *vcpu, union kvmppc_one_reg *val) +{ + struct kvmppc_xive_vcpu *xc = vcpu->arch.xive_vcpu; + u64 opal_state; + int rc; + + if (!kvmppc_xive_enabled(vcpu)) + return -EPERM; + + if (!xc) + return -ENOENT; + + /* Thread context registers. We only care about IPB and CPPR */ + val->xive_timaval[0] = vcpu->arch.xive_saved_state.w01; + + /* Get the VP state from OPAL */ + rc = xive_native_get_vp_state(xc->vp_id, &opal_state); + if (rc) + return rc; + + /* + * Capture the backup of IPB register in the NVT structure and + * merge it in our KVM VP state. + */ + val->xive_timaval[0] |= cpu_to_be64(opal_state & TM_IPB_MASK); + + pr_devel("%s NSR=%02x CPPR=%02x IBP=%02x PIPR=%02x w01=%016llx w2=%08x opal=%016llx\n", + __func__, + vcpu->arch.xive_saved_state.nsr, + vcpu->arch.xive_saved_state.cppr, + vcpu->arch.xive_saved_state.ipb, + vcpu->arch.xive_saved_state.pipr, + vcpu->arch.xive_saved_state.w01, + (u32) vcpu->arch.xive_cam_word, opal_state); + + return 0; +} + +int kvmppc_xive_native_set_vp(struct kvm_vcpu *vcpu, union kvmppc_one_reg *val) +{ + struct kvmppc_xive_vcpu *xc = vcpu->arch.xive_vcpu; + struct kvmppc_xive *xive = vcpu->kvm->arch.xive; + + pr_devel("%s w01=%016llx vp=%016llx\n", __func__, + val->xive_timaval[0], val->xive_timaval[1]); + + if (!kvmppc_xive_enabled(vcpu)) + return -EPERM; + + if (!xc || !xive) + return -ENOENT; + + /* We can't update the state of a "pushed" VCPU */ + if (WARN_ON(vcpu->arch.xive_pushed)) + return -EBUSY; + + /* + * Restore the thread context registers. IPB and CPPR should + * be the only ones that matter. + */ + vcpu->arch.xive_saved_state.w01 = val->xive_timaval[0]; + + /* + * There is no need to restore the XIVE internal state (IPB + * stored in the NVT) as the IPB register was merged in KVM VP + * state when captured. + */ + return 0; +} + static int xive_native_debug_show(struct seq_file *m, void *private) { struct kvmppc_xive *xive = m->private; -- cgit v1.2.3 From 39e9af3de5ca936098bc80ebe14401426673c208 Mon Sep 17 00:00:00 2001 From: Cédric Le Goater Date: Thu, 18 Apr 2019 12:39:37 +0200 Subject: KVM: PPC: Book3S HV: XIVE: Add a TIMA mapping MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Each thread has an associated Thread Interrupt Management context composed of a set of registers. These registers let the thread handle priority management and interrupt acknowledgment. The most important are : - Interrupt Pending Buffer (IPB) - Current Processor Priority (CPPR) - Notification Source Register (NSR) They are exposed to software in four different pages each proposing a view with a different privilege. The first page is for the physical thread context and the second for the hypervisor. Only the third (operating system) and the fourth (user level) are exposed the guest. A custom VM fault handler will populate the VMA with the appropriate pages, which should only be the OS page for now. Signed-off-by: Cédric Le Goater Reviewed-by: David Gibson Signed-off-by: Paul Mackerras --- Documentation/virtual/kvm/devices/xive.txt | 23 ++++++++++++++++++ arch/powerpc/include/asm/xive.h | 1 + arch/powerpc/include/uapi/asm/kvm.h | 2 ++ arch/powerpc/kvm/book3s_xive_native.c | 39 ++++++++++++++++++++++++++++++ arch/powerpc/sysdev/xive/native.c | 11 +++++++++ 5 files changed, 76 insertions(+) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/devices/xive.txt b/Documentation/virtual/kvm/devices/xive.txt index 525d1eebcf34..0cd7847ec38a 100644 --- a/Documentation/virtual/kvm/devices/xive.txt +++ b/Documentation/virtual/kvm/devices/xive.txt @@ -13,6 +13,29 @@ requires a POWER9 host and the guest OS should have support for the XIVE native exploitation interrupt mode. If not, it should run using the legacy interrupt mode, referred as XICS (POWER7/8). +* Device Mappings + + The KVM device exposes different MMIO ranges of the XIVE HW which + are required for interrupt management. These are exposed to the + guest in VMAs populated with a custom VM fault handler. + + 1. Thread Interrupt Management Area (TIMA) + + Each thread has an associated Thread Interrupt Management context + composed of a set of registers. These registers let the thread + handle priority management and interrupt acknowledgment. The most + important are : + + - Interrupt Pending Buffer (IPB) + - Current Processor Priority (CPPR) + - Notification Source Register (NSR) + + They are exposed to software in four different pages each proposing + a view with a different privilege. The first page is for the + physical thread context and the second for the hypervisor. Only the + third (operating system) and the fourth (user level) are exposed the + guest. + * Groups: 1. KVM_DEV_XIVE_GRP_CTRL diff --git a/arch/powerpc/include/asm/xive.h b/arch/powerpc/include/asm/xive.h index c4e88abd3b67..eaf76f57023a 100644 --- a/arch/powerpc/include/asm/xive.h +++ b/arch/powerpc/include/asm/xive.h @@ -23,6 +23,7 @@ * same offset regardless of where the code is executing */ extern void __iomem *xive_tima; +extern unsigned long xive_tima_os; /* * Offset in the TM area of our current execution level (provided by diff --git a/arch/powerpc/include/uapi/asm/kvm.h b/arch/powerpc/include/uapi/asm/kvm.h index cd3f16b70a2e..0998e8edc91a 100644 --- a/arch/powerpc/include/uapi/asm/kvm.h +++ b/arch/powerpc/include/uapi/asm/kvm.h @@ -720,4 +720,6 @@ struct kvm_ppc_xive_eq { #define KVM_XIVE_EQ_ALWAYS_NOTIFY 0x00000001 +#define KVM_XIVE_TIMA_PAGE_OFFSET 0 + #endif /* __LINUX_KVM_POWERPC_H */ diff --git a/arch/powerpc/kvm/book3s_xive_native.c b/arch/powerpc/kvm/book3s_xive_native.c index 2f9d5e9439a6..f5314da0cb45 100644 --- a/arch/powerpc/kvm/book3s_xive_native.c +++ b/arch/powerpc/kvm/book3s_xive_native.c @@ -165,6 +165,44 @@ bail: return rc; } +static vm_fault_t xive_native_tima_fault(struct vm_fault *vmf) +{ + struct vm_area_struct *vma = vmf->vma; + + switch (vmf->pgoff - vma->vm_pgoff) { + case 0: /* HW - forbid access */ + case 1: /* HV - forbid access */ + return VM_FAULT_SIGBUS; + case 2: /* OS */ + vmf_insert_pfn(vma, vmf->address, xive_tima_os >> PAGE_SHIFT); + return VM_FAULT_NOPAGE; + case 3: /* USER - TODO */ + default: + return VM_FAULT_SIGBUS; + } +} + +static const struct vm_operations_struct xive_native_tima_vmops = { + .fault = xive_native_tima_fault, +}; + +static int kvmppc_xive_native_mmap(struct kvm_device *dev, + struct vm_area_struct *vma) +{ + /* We only allow mappings at fixed offset for now */ + if (vma->vm_pgoff == KVM_XIVE_TIMA_PAGE_OFFSET) { + if (vma_pages(vma) > 4) + return -EINVAL; + vma->vm_ops = &xive_native_tima_vmops; + } else { + return -EINVAL; + } + + vma->vm_flags |= VM_IO | VM_PFNMAP; + vma->vm_page_prot = pgprot_noncached_wc(vma->vm_page_prot); + return 0; +} + static int kvmppc_xive_native_set_source(struct kvmppc_xive *xive, long irq, u64 addr) { @@ -1050,6 +1088,7 @@ struct kvm_device_ops kvm_xive_native_ops = { .set_attr = kvmppc_xive_native_set_attr, .get_attr = kvmppc_xive_native_get_attr, .has_attr = kvmppc_xive_native_has_attr, + .mmap = kvmppc_xive_native_mmap, }; void kvmppc_xive_native_init_module(void) diff --git a/arch/powerpc/sysdev/xive/native.c b/arch/powerpc/sysdev/xive/native.c index 0c037e933e55..7782201e5fe8 100644 --- a/arch/powerpc/sysdev/xive/native.c +++ b/arch/powerpc/sysdev/xive/native.c @@ -521,6 +521,9 @@ u32 xive_native_default_eq_shift(void) } EXPORT_SYMBOL_GPL(xive_native_default_eq_shift); +unsigned long xive_tima_os; +EXPORT_SYMBOL_GPL(xive_tima_os); + bool __init xive_native_init(void) { struct device_node *np; @@ -573,6 +576,14 @@ bool __init xive_native_init(void) for_each_possible_cpu(cpu) kvmppc_set_xive_tima(cpu, r.start, tima); + /* Resource 2 is OS window */ + if (of_address_to_resource(np, 2, &r)) { + pr_err("Failed to get thread mgmnt area resource\n"); + return false; + } + + xive_tima_os = r.start; + /* Grab size of provisionning pages */ xive_parse_provisioning(np); -- cgit v1.2.3 From 6520ca64cde71b75dae54f3fcb33517a93d82486 Mon Sep 17 00:00:00 2001 From: Cédric Le Goater Date: Thu, 18 Apr 2019 12:39:38 +0200 Subject: KVM: PPC: Book3S HV: XIVE: Add a mapping for the source ESB pages MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Each source is associated with an Event State Buffer (ESB) with a even/odd pair of pages which provides commands to manage the source: to trigger, to EOI, to turn off the source for instance. The custom VM fault handler will deduce the guest IRQ number from the offset of the fault, and the ESB page of the associated XIVE interrupt will be inserted into the VMA using the internal structure caching information on the interrupts. Signed-off-by: Cédric Le Goater Reviewed-by: David Gibson Signed-off-by: Paul Mackerras --- Documentation/virtual/kvm/devices/xive.txt | 7 ++++ arch/powerpc/include/uapi/asm/kvm.h | 1 + arch/powerpc/kvm/book3s_xive_native.c | 57 ++++++++++++++++++++++++++++++ 3 files changed, 65 insertions(+) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/devices/xive.txt b/Documentation/virtual/kvm/devices/xive.txt index 0cd7847ec38a..69ee62d3d4dc 100644 --- a/Documentation/virtual/kvm/devices/xive.txt +++ b/Documentation/virtual/kvm/devices/xive.txt @@ -36,6 +36,13 @@ the legacy interrupt mode, referred as XICS (POWER7/8). third (operating system) and the fourth (user level) are exposed the guest. + 2. Event State Buffer (ESB) + + Each source is associated with an Event State Buffer (ESB) with + either a pair of even/odd pair of pages which provides commands to + manage the source: to trigger, to EOI, to turn off the source for + instance. + * Groups: 1. KVM_DEV_XIVE_GRP_CTRL diff --git a/arch/powerpc/include/uapi/asm/kvm.h b/arch/powerpc/include/uapi/asm/kvm.h index 0998e8edc91a..b0f72dea8b11 100644 --- a/arch/powerpc/include/uapi/asm/kvm.h +++ b/arch/powerpc/include/uapi/asm/kvm.h @@ -721,5 +721,6 @@ struct kvm_ppc_xive_eq { #define KVM_XIVE_EQ_ALWAYS_NOTIFY 0x00000001 #define KVM_XIVE_TIMA_PAGE_OFFSET 0 +#define KVM_XIVE_ESB_PAGE_OFFSET 4 #endif /* __LINUX_KVM_POWERPC_H */ diff --git a/arch/powerpc/kvm/book3s_xive_native.c b/arch/powerpc/kvm/book3s_xive_native.c index f5314da0cb45..465eb90ff23e 100644 --- a/arch/powerpc/kvm/book3s_xive_native.c +++ b/arch/powerpc/kvm/book3s_xive_native.c @@ -165,6 +165,59 @@ bail: return rc; } +static vm_fault_t xive_native_esb_fault(struct vm_fault *vmf) +{ + struct vm_area_struct *vma = vmf->vma; + struct kvm_device *dev = vma->vm_file->private_data; + struct kvmppc_xive *xive = dev->private; + struct kvmppc_xive_src_block *sb; + struct kvmppc_xive_irq_state *state; + struct xive_irq_data *xd; + u32 hw_num; + u16 src; + u64 page; + unsigned long irq; + u64 page_offset; + + /* + * Linux/KVM uses a two pages ESB setting, one for trigger and + * one for EOI + */ + page_offset = vmf->pgoff - vma->vm_pgoff; + irq = page_offset / 2; + + sb = kvmppc_xive_find_source(xive, irq, &src); + if (!sb) { + pr_devel("%s: source %lx not found !\n", __func__, irq); + return VM_FAULT_SIGBUS; + } + + state = &sb->irq_state[src]; + kvmppc_xive_select_irq(state, &hw_num, &xd); + + arch_spin_lock(&sb->lock); + + /* + * first/even page is for trigger + * second/odd page is for EOI and management. + */ + page = page_offset % 2 ? xd->eoi_page : xd->trig_page; + arch_spin_unlock(&sb->lock); + + if (WARN_ON(!page)) { + pr_err("%s: acessing invalid ESB page for source %lx !\n", + __func__, irq); + return VM_FAULT_SIGBUS; + } + + vmf_insert_pfn(vma, vmf->address, page >> PAGE_SHIFT); + return VM_FAULT_NOPAGE; +} + +static const struct vm_operations_struct xive_native_esb_vmops = { + .fault = xive_native_esb_fault, +}; + static vm_fault_t xive_native_tima_fault(struct vm_fault *vmf) { struct vm_area_struct *vma = vmf->vma; @@ -194,6 +247,10 @@ static int kvmppc_xive_native_mmap(struct kvm_device *dev, if (vma_pages(vma) > 4) return -EINVAL; vma->vm_ops = &xive_native_tima_vmops; + } else if (vma->vm_pgoff == KVM_XIVE_ESB_PAGE_OFFSET) { + if (vma_pages(vma) > KVMPPC_XIVE_NR_IRQS * 2) + return -EINVAL; + vma->vm_ops = &xive_native_esb_vmops; } else { return -EINVAL; } -- cgit v1.2.3 From 232b984b7d55e68971962f07f1dd1d1eb1be52e0 Mon Sep 17 00:00:00 2001 From: Cédric Le Goater Date: Thu, 18 Apr 2019 12:39:39 +0200 Subject: KVM: PPC: Book3S HV: XIVE: Add passthrough support MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The KVM XICS-over-XIVE device and the proposed KVM XIVE native device implement an IRQ space for the guest using the generic IPI interrupts of the XIVE IC controller. These interrupts are allocated at the OPAL level and "mapped" into the guest IRQ number space in the range 0-0x1FFF. Interrupt management is performed in the XIVE way: using loads and stores on the addresses of the XIVE IPI interrupt ESB pages. Both KVM devices share the same internal structure caching information on the interrupts, among which the xive_irq_data struct containing the addresses of the IPI ESB pages and an extra one in case of pass-through. The later contains the addresses of the ESB pages of the underlying HW controller interrupts, PHB4 in all cases for now. A guest, when running in the XICS legacy interrupt mode, lets the KVM XICS-over-XIVE device "handle" interrupt management, that is to perform the loads and stores on the addresses of the ESB pages of the guest interrupts. However, when running in XIVE native exploitation mode, the KVM XIVE native device exposes the interrupt ESB pages to the guest and lets the guest perform directly the loads and stores. The VMA exposing the ESB pages make use of a custom VM fault handler which role is to populate the VMA with appropriate pages. When a fault occurs, the guest IRQ number is deduced from the offset, and the ESB pages of associated XIVE IPI interrupt are inserted in the VMA (using the internal structure caching information on the interrupts). Supporting device passthrough in the guest running in XIVE native exploitation mode adds some extra refinements because the ESB pages of a different HW controller (PHB4) need to be exposed to the guest along with the initial IPI ESB pages of the XIVE IC controller. But the overall mechanic is the same. When the device HW irqs are mapped into or unmapped from the guest IRQ number space, the passthru_irq helpers, kvmppc_xive_set_mapped() and kvmppc_xive_clr_mapped(), are called to record or clear the passthrough interrupt information and to perform the switch. The approach taken by this patch is to clear the ESB pages of the guest IRQ number being mapped and let the VM fault handler repopulate. The handler will insert the ESB page corresponding to the HW interrupt of the device being passed-through or the initial IPI ESB page if the device is being removed. Signed-off-by: Cédric Le Goater Reviewed-by: David Gibson Signed-off-by: Paul Mackerras --- Documentation/virtual/kvm/devices/xive.txt | 19 ++++++++++++++ arch/powerpc/kvm/book3s_xive.c | 15 +++++++++++ arch/powerpc/kvm/book3s_xive.h | 9 +++++++ arch/powerpc/kvm/book3s_xive_native.c | 41 ++++++++++++++++++++++++++++++ 4 files changed, 84 insertions(+) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/devices/xive.txt b/Documentation/virtual/kvm/devices/xive.txt index 69ee62d3d4dc..9a24a4525253 100644 --- a/Documentation/virtual/kvm/devices/xive.txt +++ b/Documentation/virtual/kvm/devices/xive.txt @@ -43,6 +43,25 @@ the legacy interrupt mode, referred as XICS (POWER7/8). manage the source: to trigger, to EOI, to turn off the source for instance. + 3. Device pass-through + + When a device is passed-through into the guest, the source + interrupts are from a different HW controller (PHB4) and the ESB + pages exposed to the guest should accommadate this change. + + The passthru_irq helpers, kvmppc_xive_set_mapped() and + kvmppc_xive_clr_mapped() are called when the device HW irqs are + mapped into or unmapped from the guest IRQ number space. The KVM + device extends these helpers to clear the ESB pages of the guest IRQ + number being mapped and then lets the VM fault handler repopulate. + The handler will insert the ESB page corresponding to the HW + interrupt of the device being passed-through or the initial IPI ESB + page if the device has being removed. + + The ESB remapping is fully transparent to the guest and the OS + device driver. All handling is done within VFIO and the above + helpers in KVM-PPC. + * Groups: 1. KVM_DEV_XIVE_GRP_CTRL diff --git a/arch/powerpc/kvm/book3s_xive.c b/arch/powerpc/kvm/book3s_xive.c index c1b7aa7dbc28..480a3fc6b9fd 100644 --- a/arch/powerpc/kvm/book3s_xive.c +++ b/arch/powerpc/kvm/book3s_xive.c @@ -937,6 +937,13 @@ int kvmppc_xive_set_mapped(struct kvm *kvm, unsigned long guest_irq, /* Turn the IPI hard off */ xive_vm_esb_load(&state->ipi_data, XIVE_ESB_SET_PQ_01); + /* + * Reset ESB guest mapping. Needed when ESB pages are exposed + * to the guest in XIVE native mode + */ + if (xive->ops && xive->ops->reset_mapped) + xive->ops->reset_mapped(kvm, guest_irq); + /* Grab info about irq */ state->pt_number = hw_irq; state->pt_data = irq_data_get_irq_handler_data(host_data); @@ -1022,6 +1029,14 @@ int kvmppc_xive_clr_mapped(struct kvm *kvm, unsigned long guest_irq, state->pt_number = 0; state->pt_data = NULL; + /* + * Reset ESB guest mapping. Needed when ESB pages are exposed + * to the guest in XIVE native mode + */ + if (xive->ops && xive->ops->reset_mapped) { + xive->ops->reset_mapped(kvm, guest_irq); + } + /* Reconfigure the IPI */ xive_native_configure_irq(state->ipi_number, kvmppc_xive_vp(xive, state->act_server), diff --git a/arch/powerpc/kvm/book3s_xive.h b/arch/powerpc/kvm/book3s_xive.h index 622f594d93e1..e011622dc038 100644 --- a/arch/powerpc/kvm/book3s_xive.h +++ b/arch/powerpc/kvm/book3s_xive.h @@ -94,6 +94,11 @@ struct kvmppc_xive_src_block { struct kvmppc_xive_irq_state irq_state[KVMPPC_XICS_IRQ_PER_ICS]; }; +struct kvmppc_xive; + +struct kvmppc_xive_ops { + int (*reset_mapped)(struct kvm *kvm, unsigned long guest_irq); +}; struct kvmppc_xive { struct kvm *kvm; @@ -132,6 +137,10 @@ struct kvmppc_xive { /* Flags */ u8 single_escalation; + + struct kvmppc_xive_ops *ops; + struct address_space *mapping; + struct mutex mapping_lock; }; #define KVMPPC_XIVE_Q_COUNT 8 diff --git a/arch/powerpc/kvm/book3s_xive_native.c b/arch/powerpc/kvm/book3s_xive_native.c index 465eb90ff23e..62648f833adf 100644 --- a/arch/powerpc/kvm/book3s_xive_native.c +++ b/arch/powerpc/kvm/book3s_xive_native.c @@ -11,6 +11,7 @@ #include #include #include +#include #include #include #include @@ -165,6 +166,35 @@ bail: return rc; } +/* + * Device passthrough support + */ +static int kvmppc_xive_native_reset_mapped(struct kvm *kvm, unsigned long irq) +{ + struct kvmppc_xive *xive = kvm->arch.xive; + + if (irq >= KVMPPC_XIVE_NR_IRQS) + return -EINVAL; + + /* + * Clear the ESB pages of the IRQ number being mapped (or + * unmapped) into the guest and let the the VM fault handler + * repopulate with the appropriate ESB pages (device or IC) + */ + pr_debug("clearing esb pages for girq 0x%lx\n", irq); + mutex_lock(&xive->mapping_lock); + if (xive->mapping) + unmap_mapping_range(xive->mapping, + irq * (2ull << PAGE_SHIFT), + 2ull << PAGE_SHIFT, 1); + mutex_unlock(&xive->mapping_lock); + return 0; +} + +static struct kvmppc_xive_ops kvmppc_xive_native_ops = { + .reset_mapped = kvmppc_xive_native_reset_mapped, +}; + static vm_fault_t xive_native_esb_fault(struct vm_fault *vmf) { struct vm_area_struct *vma = vmf->vma; @@ -242,6 +272,8 @@ static const struct vm_operations_struct xive_native_tima_vmops = { static int kvmppc_xive_native_mmap(struct kvm_device *dev, struct vm_area_struct *vma) { + struct kvmppc_xive *xive = dev->private; + /* We only allow mappings at fixed offset for now */ if (vma->vm_pgoff == KVM_XIVE_TIMA_PAGE_OFFSET) { if (vma_pages(vma) > 4) @@ -257,6 +289,13 @@ static int kvmppc_xive_native_mmap(struct kvm_device *dev, vma->vm_flags |= VM_IO | VM_PFNMAP; vma->vm_page_prot = pgprot_noncached_wc(vma->vm_page_prot); + + /* + * Grab the KVM device file address_space to be able to clear + * the ESB pages mapping when a device is passed-through into + * the guest. + */ + xive->mapping = vma->vm_file->f_mapping; return 0; } @@ -971,6 +1010,7 @@ static int kvmppc_xive_native_create(struct kvm_device *dev, u32 type) xive->dev = dev; xive->kvm = kvm; kvm->arch.xive = xive; + mutex_init(&xive->mapping_lock); /* * Allocate a bunch of VPs. KVM_MAX_VCPUS is a large value for @@ -984,6 +1024,7 @@ static int kvmppc_xive_native_create(struct kvm_device *dev, u32 type) ret = -ENXIO; xive->single_escalation = xive_native_has_single_escalation(); + xive->ops = &kvmppc_xive_native_ops; if (ret) kfree(xive); -- cgit v1.2.3 From 1b8868861366acaf42c07c375e15fc7bb3c38189 Mon Sep 17 00:00:00 2001 From: Masahiro Yamada Date: Mon, 29 Apr 2019 23:53:50 +0900 Subject: dontdiff: update with Kconfig build artifacts Add generated *conf-cfg files. Commit 694c49a7c01c ("kconfig: drop localization support") removed "gconf.glade.h" and "kxgettext". "kconfig" and "lxdialog" should not be excluded either. Signed-off-by: Masahiro Yamada Signed-off-by: Jonathan Corbet --- Documentation/dontdiff | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) (limited to 'Documentation') diff --git a/Documentation/dontdiff b/Documentation/dontdiff index ef25a066d952..15c54da5c763 100644 --- a/Documentation/dontdiff +++ b/Documentation/dontdiff @@ -127,7 +127,7 @@ flask.h fore200e_mkfirm fore200e_pca_fw.c* gconf -gconf.glade.h +gconf-cfg gen-devlist gen_crc32table gen_init_cpio @@ -148,24 +148,22 @@ int32.c int4.c int8.c kallsyms -kconfig keywords.c ksym.c* ksym.h* -kxgettext *lex.c *lex.*.c linux logo_*.c logo_*_clut224.c logo_*_mono.c -lxdialog mach-types mach-types.h machtypes.h map map_hugetlb mconf +mconf-cfg miboot* mk_elfconfig mkboot @@ -181,6 +179,7 @@ modules.builtin modules.order modversions.h* nconf +nconf-cfg ncscope.* offset.h oui.c* @@ -200,6 +199,7 @@ pnmtologo ppc_defs.h* pss_boot.h qconf +qconf-cfg r100_reg_safe.h r200_reg_safe.h r300_reg_safe.h -- cgit v1.2.3 From fbf7c7e046ee4e45d18e541335c2177524e4dbd1 Mon Sep 17 00:00:00 2001 From: Federico Vaga Date: Mon, 29 Apr 2019 23:45:14 +0200 Subject: doc: fix typo in PGP guide Fix typo in the GPG guide for maintainers Signed-off-by: Federico Vaga Signed-off-by: Jonathan Corbet --- Documentation/process/maintainer-pgp-guide.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/process/maintainer-pgp-guide.rst b/Documentation/process/maintainer-pgp-guide.rst index aff9b1a4d77b..4bab7464ff8c 100644 --- a/Documentation/process/maintainer-pgp-guide.rst +++ b/Documentation/process/maintainer-pgp-guide.rst @@ -943,7 +943,7 @@ have on your keyring:: Next, open the `PGP pathfinder`_. In the "From" field, paste the key fingerprint of Linus Torvalds from the output above. In the "To" field, -paste they key-id you found via ``gpg --search`` of the unknown key, and +paste the key-id you found via ``gpg --search`` of the unknown key, and check the results: - `Finding paths to Linus`_ -- cgit v1.2.3 From 678f784cd6cdd523fe4fb98c45dc7a6a673c2461 Mon Sep 17 00:00:00 2001 From: Federico Vaga Date: Mon, 29 Apr 2019 23:47:20 +0200 Subject: doc:it_IT: translation alignment Align Italian translation after the following changes in Documentation bba757d8578f coding-style.rst: Generic alloc functions do not need OOM logging d8e8bcc3d8de docs: doc-guide: remove the extension from .rst files Signed-off-by: Federico Vaga Signed-off-by: Jonathan Corbet --- .../translations/it_IT/core-api/memory-allocation.rst | 13 +++++++++++++ Documentation/translations/it_IT/doc-guide/index.rst | 6 +++--- Documentation/translations/it_IT/process/coding-style.rst | 8 +++++++- 3 files changed, 23 insertions(+), 4 deletions(-) create mode 100644 Documentation/translations/it_IT/core-api/memory-allocation.rst (limited to 'Documentation') diff --git a/Documentation/translations/it_IT/core-api/memory-allocation.rst b/Documentation/translations/it_IT/core-api/memory-allocation.rst new file mode 100644 index 000000000000..11d5148f8d6b --- /dev/null +++ b/Documentation/translations/it_IT/core-api/memory-allocation.rst @@ -0,0 +1,13 @@ +.. include:: ../disclaimer-ita.rst + +:Original: :ref:`Documentation/core-api/memory-allocation.rst ` + +.. _it_memory_allocation: + +================================ +Guida all'allocazione di memoria +================================ + +.. warning:: + + TODO ancora da tradurre diff --git a/Documentation/translations/it_IT/doc-guide/index.rst b/Documentation/translations/it_IT/doc-guide/index.rst index 7a6562b547ee..9fffff626711 100644 --- a/Documentation/translations/it_IT/doc-guide/index.rst +++ b/Documentation/translations/it_IT/doc-guide/index.rst @@ -12,9 +12,9 @@ Come scrivere la documentazione del kernel .. toctree:: :maxdepth: 1 - sphinx.rst - kernel-doc.rst - parse-headers.rst + sphinx + kernel-doc + parse-headers .. only:: subproject and html diff --git a/Documentation/translations/it_IT/process/coding-style.rst b/Documentation/translations/it_IT/process/coding-style.rst index 2fd0e7f79d55..5ef534c95e69 100644 --- a/Documentation/translations/it_IT/process/coding-style.rst +++ b/Documentation/translations/it_IT/process/coding-style.rst @@ -859,7 +859,8 @@ racchiusa in #ifdef, potete usare printk(KERN_DEBUG ...). Il kernel fornisce i seguenti assegnatori ad uso generico: kmalloc(), kzalloc(), kmalloc_array(), kcalloc(), vmalloc(), e vzalloc(). -Per maggiori informazioni, consultate la documentazione dell'API. +Per maggiori informazioni, consultate la documentazione dell'API: +:ref:`Documentation/translations/it_IT/core-api/memory-allocation.rst ` Il modo preferito per passare la dimensione di una struttura è il seguente: @@ -890,6 +891,11 @@ Il modo preferito per assegnare un vettore a zero è il seguente: Entrambe verificano la condizione di overflow per la dimensione d'assegnamento n * sizeof(...), se accade ritorneranno NULL. +Questi allocatori generici producono uno *stack dump* in caso di fallimento +a meno che non venga esplicitamente specificato __GFP_NOWARN. Quindi, nella +maggior parte dei casi, è inutile stampare messaggi aggiuntivi quando uno di +questi allocatori ritornano un puntatore NULL. + 15) Il morbo inline ------------------- -- cgit v1.2.3 From 7d10bdbd6df3d23ac2a54972a3a0559d1e3811ac Mon Sep 17 00:00:00 2001 From: Mike Rapoport Date: Sun, 28 Apr 2019 15:17:43 +0300 Subject: docs/vm: add documentation of memory models Describe what {FLAT,DISCONTIG,SPARSE}MEM are and how they manage to maintain pfn <-> struct page correspondence. Signed-off-by: Mike Rapoport Acked-by: Randy Dunlap Signed-off-by: Jonathan Corbet --- Documentation/vm/index.rst | 1 + Documentation/vm/memory-model.rst | 183 ++++++++++++++++++++++++++++++++++++++ 2 files changed, 184 insertions(+) create mode 100644 Documentation/vm/memory-model.rst (limited to 'Documentation') diff --git a/Documentation/vm/index.rst b/Documentation/vm/index.rst index b58cc3bfe777..e8d943b21cf9 100644 --- a/Documentation/vm/index.rst +++ b/Documentation/vm/index.rst @@ -37,6 +37,7 @@ descriptions of data structures and algorithms. hwpoison hugetlbfs_reserv ksm + memory-model mmu_notifier numa overcommit-accounting diff --git a/Documentation/vm/memory-model.rst b/Documentation/vm/memory-model.rst new file mode 100644 index 000000000000..382f72ace1fc --- /dev/null +++ b/Documentation/vm/memory-model.rst @@ -0,0 +1,183 @@ +.. SPDX-License-Identifier: GPL-2.0 + +.. _physical_memory_model: + +===================== +Physical Memory Model +===================== + +Physical memory in a system may be addressed in different ways. The +simplest case is when the physical memory starts at address 0 and +spans a contiguous range up to the maximal address. It could be, +however, that this range contains small holes that are not accessible +for the CPU. Then there could be several contiguous ranges at +completely distinct addresses. And, don't forget about NUMA, where +different memory banks are attached to different CPUs. + +Linux abstracts this diversity using one of the three memory models: +FLATMEM, DISCONTIGMEM and SPARSEMEM. Each architecture defines what +memory models it supports, what the default memory model is and +whether it is possible to manually override that default. + +.. note:: + At time of this writing, DISCONTIGMEM is considered deprecated, + although it is still in use by several architectures. + +All the memory models track the status of physical page frames using +:c:type:`struct page` arranged in one or more arrays. + +Regardless of the selected memory model, there exists one-to-one +mapping between the physical page frame number (PFN) and the +corresponding `struct page`. + +Each memory model defines :c:func:`pfn_to_page` and :c:func:`page_to_pfn` +helpers that allow the conversion from PFN to `struct page` and vice +versa. + +FLATMEM +======= + +The simplest memory model is FLATMEM. This model is suitable for +non-NUMA systems with contiguous, or mostly contiguous, physical +memory. + +In the FLATMEM memory model, there is a global `mem_map` array that +maps the entire physical memory. For most architectures, the holes +have entries in the `mem_map` array. The `struct page` objects +corresponding to the holes are never fully initialized. + +To allocate the `mem_map` array, architecture specific setup code +should call :c:func:`free_area_init_node` function or its convenience +wrapper :c:func:`free_area_init`. Yet, the mappings array is not +usable until the call to :c:func:`memblock_free_all` that hands all +the memory to the page allocator. + +If an architecture enables `CONFIG_ARCH_HAS_HOLES_MEMORYMODEL` option, +it may free parts of the `mem_map` array that do not cover the +actual physical pages. In such case, the architecture specific +:c:func:`pfn_valid` implementation should take the holes in the +`mem_map` into account. + +With FLATMEM, the conversion between a PFN and the `struct page` is +straightforward: `PFN - ARCH_PFN_OFFSET` is an index to the +`mem_map` array. + +The `ARCH_PFN_OFFSET` defines the first page frame number for +systems with physical memory starting at address different from 0. + +DISCONTIGMEM +============ + +The DISCONTIGMEM model treats the physical memory as a collection of +`nodes` similarly to how Linux NUMA support does. For each node Linux +constructs an independent memory management subsystem represented by +`struct pglist_data` (or `pg_data_t` for short). Among other +things, `pg_data_t` holds the `node_mem_map` array that maps +physical pages belonging to that node. The `node_start_pfn` field of +`pg_data_t` is the number of the first page frame belonging to that +node. + +The architecture setup code should call :c:func:`free_area_init_node` for +each node in the system to initialize the `pg_data_t` object and its +`node_mem_map`. + +Every `node_mem_map` behaves exactly as FLATMEM's `mem_map` - +every physical page frame in a node has a `struct page` entry in the +`node_mem_map` array. When DISCONTIGMEM is enabled, a portion of the +`flags` field of the `struct page` encodes the node number of the +node hosting that page. + +The conversion between a PFN and the `struct page` in the +DISCONTIGMEM model became slightly more complex as it has to determine +which node hosts the physical page and which `pg_data_t` object +holds the `struct page`. + +Architectures that support DISCONTIGMEM provide :c:func:`pfn_to_nid` +to convert PFN to the node number. The opposite conversion helper +:c:func:`page_to_nid` is generic as it uses the node number encoded in +page->flags. + +Once the node number is known, the PFN can be used to index +appropriate `node_mem_map` array to access the `struct page` and +the offset of the `struct page` from the `node_mem_map` plus +`node_start_pfn` is the PFN of that page. + +SPARSEMEM +========= + +SPARSEMEM is the most versatile memory model available in Linux and it +is the only memory model that supports several advanced features such +as hot-plug and hot-remove of the physical memory, alternative memory +maps for non-volatile memory devices and deferred initialization of +the memory map for larger systems. + +The SPARSEMEM model presents the physical memory as a collection of +sections. A section is represented with :c:type:`struct mem_section` +that contains `section_mem_map` that is, logically, a pointer to an +array of struct pages. However, it is stored with some other magic +that aids the sections management. The section size and maximal number +of section is specified using `SECTION_SIZE_BITS` and +`MAX_PHYSMEM_BITS` constants defined by each architecture that +supports SPARSEMEM. While `MAX_PHYSMEM_BITS` is an actual width of a +physical address that an architecture supports, the +`SECTION_SIZE_BITS` is an arbitrary value. + +The maximal number of sections is denoted `NR_MEM_SECTIONS` and +defined as + +.. math:: + + NR\_MEM\_SECTIONS = 2 ^ {(MAX\_PHYSMEM\_BITS - SECTION\_SIZE\_BITS)} + +The `mem_section` objects are arranged in a two-dimensional array +called `mem_sections`. The size and placement of this array depend +on `CONFIG_SPARSEMEM_EXTREME` and the maximal possible number of +sections: + +* When `CONFIG_SPARSEMEM_EXTREME` is disabled, the `mem_sections` + array is static and has `NR_MEM_SECTIONS` rows. Each row holds a + single `mem_section` object. +* When `CONFIG_SPARSEMEM_EXTREME` is enabled, the `mem_sections` + array is dynamically allocated. Each row contains PAGE_SIZE worth of + `mem_section` objects and the number of rows is calculated to fit + all the memory sections. + +The architecture setup code should call :c:func:`memory_present` for +each active memory range or use :c:func:`memblocks_present` or +:c:func:`sparse_memory_present_with_active_regions` wrappers to +initialize the memory sections. Next, the actual memory maps should be +set up using :c:func:`sparse_init`. + +With SPARSEMEM there are two possible ways to convert a PFN to the +corresponding `struct page` - a "classic sparse" and "sparse +vmemmap". The selection is made at build time and it is determined by +the value of `CONFIG_SPARSEMEM_VMEMMAP`. + +The classic sparse encodes the section number of a page in page->flags +and uses high bits of a PFN to access the section that maps that page +frame. Inside a section, the PFN is the index to the array of pages. + +The sparse vmemmap uses a virtually mapped memory map to optimize +pfn_to_page and page_to_pfn operations. There is a global `struct +page *vmemmap` pointer that points to a virtually contiguous array of +`struct page` objects. A PFN is an index to that array and the the +offset of the `struct page` from `vmemmap` is the PFN of that +page. + +To use vmemmap, an architecture has to reserve a range of virtual +addresses that will map the physical pages containing the memory +map and make sure that `vmemmap` points to that range. In addition, +the architecture should implement :c:func:`vmemmap_populate` method +that will allocate the physical memory and create page tables for the +virtual memory map. If an architecture does not have any special +requirements for the vmemmap mappings, it can use default +:c:func:`vmemmap_populate_basepages` provided by the generic memory +management. + +The virtually mapped memory map allows storing `struct page` objects +for persistent memory devices in pre-allocated storage on those +devices. This storage is represented with :c:type:`struct vmem_altmap` +that is eventually passed to vmemmap_populate() through a long chain +of function calls. The vmemmap_populate() implementation may use the +`vmem_altmap` along with :c:func:`altmap_alloc_block_buf` helper to +allocate memory map on the persistent memory device. -- cgit v1.2.3 From 41f0a9542a253d79506584ab6353bcd6c4916150 Mon Sep 17 00:00:00 2001 From: Ralph Campbell Date: Fri, 26 Apr 2019 11:04:29 -0700 Subject: docs/vm: Minor editorial changes in the THP and hugetlbfs Some minor wording changes and typo corrections. Signed-off-by: Ralph Campbell Acked-by: Randy Dunlap Acked-by: Mike Kravetz Cc: Mike Rapoport Signed-off-by: Jonathan Corbet --- Documentation/vm/hugetlbfs_reserv.rst | 17 ++++---- Documentation/vm/transhuge.rst | 73 ++++++++++++++++++----------------- 2 files changed, 46 insertions(+), 44 deletions(-) (limited to 'Documentation') diff --git a/Documentation/vm/hugetlbfs_reserv.rst b/Documentation/vm/hugetlbfs_reserv.rst index 9d200762114f..f143954e0d05 100644 --- a/Documentation/vm/hugetlbfs_reserv.rst +++ b/Documentation/vm/hugetlbfs_reserv.rst @@ -85,10 +85,10 @@ Reservation Map Location (Private or Shared) A huge page mapping or segment is either private or shared. If private, it is typically only available to a single address space (task). If shared, it can be mapped into multiple address spaces (tasks). The location and -semantics of the reservation map is significantly different for two types +semantics of the reservation map is significantly different for the two types of mappings. Location differences are: -- For private mappings, the reservation map hangs off the the VMA structure. +- For private mappings, the reservation map hangs off the VMA structure. Specifically, vma->vm_private_data. This reserve map is created at the time the mapping (mmap(MAP_PRIVATE)) is created. - For shared mappings, the reservation map hangs off the inode. Specifically, @@ -109,15 +109,15 @@ These operations result in a call to the routine hugetlb_reserve_pages():: struct vm_area_struct *vma, vm_flags_t vm_flags) -The first thing hugetlb_reserve_pages() does is check for the NORESERVE +The first thing hugetlb_reserve_pages() does is check if the NORESERVE flag was specified in either the shmget() or mmap() call. If NORESERVE -was specified, then this routine returns immediately as no reservation +was specified, then this routine returns immediately as no reservations are desired. The arguments 'from' and 'to' are huge page indices into the mapping or underlying file. For shmget(), 'from' is always 0 and 'to' corresponds to the length of the segment/mapping. For mmap(), the offset argument could -be used to specify the offset into the underlying file. In such a case +be used to specify the offset into the underlying file. In such a case, the 'from' and 'to' arguments have been adjusted by this offset. One of the big differences between PRIVATE and SHARED mappings is the way @@ -138,7 +138,8 @@ to indicate this VMA owns the reservations. The reservation map is consulted to determine how many huge page reservations are needed for the current mapping/segment. For private mappings, this is -always the value (to - from). However, for shared mappings it is possible that some reservations may already exist within the range (to - from). See the +always the value (to - from). However, for shared mappings it is possible that +some reservations may already exist within the range (to - from). See the section :ref:`Reservation Map Modifications ` for details on how this is accomplished. @@ -165,7 +166,7 @@ these counters. If there were enough free huge pages and the global count resv_huge_pages was adjusted, then the reservation map associated with the mapping is modified to reflect the reservations. In the case of a shared mapping, a -file_region will exist that includes the range 'from' 'to'. For private +file_region will exist that includes the range 'from' - 'to'. For private mappings, no modifications are made to the reservation map as lack of an entry indicates a reservation exists. @@ -239,7 +240,7 @@ subpool accounting when the page is freed. The routine vma_commit_reservation() is then called to adjust the reserve map based on the consumption of the reservation. In general, this involves ensuring the page is represented within a file_region structure of the region -map. For shared mappings where the the reservation was present, an entry +map. For shared mappings where the reservation was present, an entry in the reserve map already existed so no change is made. However, if there was no reservation in a shared mapping or this was a private mapping a new entry must be created. diff --git a/Documentation/vm/transhuge.rst b/Documentation/vm/transhuge.rst index 8df380657430..37c57ca32629 100644 --- a/Documentation/vm/transhuge.rst +++ b/Documentation/vm/transhuge.rst @@ -4,8 +4,9 @@ Transparent Hugepage Support ============================ -This document describes design principles Transparent Hugepage (THP) -Support and its interaction with other parts of the memory management. +This document describes design principles for Transparent Hugepage (THP) +support and its interaction with other parts of the memory management +system. Design principles ================= @@ -37,23 +38,23 @@ get_user_pages and follow_page get_user_pages and follow_page if run on a hugepage, will return the head or tail pages as usual (exactly as they would do on -hugetlbfs). Most gup users will only care about the actual physical +hugetlbfs). Most GUP users will only care about the actual physical address of the page and its temporary pinning to release after the I/O is complete, so they won't ever notice the fact the page is huge. But if any driver is going to mangle over the page structure of the tail page (like for checking page->mapping or other bits that are relevant for the head page and not the tail page), it should be updated to jump -to check head page instead. Taking reference on any head/tail page would -prevent page from being split by anyone. +to check head page instead. Taking a reference on any head/tail page would +prevent the page from being split by anyone. .. note:: these aren't new constraints to the GUP API, and they match the - same constrains that applies to hugetlbfs too, so any driver capable + same constraints that apply to hugetlbfs too, so any driver capable of handling GUP on hugetlbfs will also work fine on transparent hugepage backed mappings. In case you can't handle compound pages if they're returned by -follow_page, the FOLL_SPLIT bit can be specified as parameter to +follow_page, the FOLL_SPLIT bit can be specified as a parameter to follow_page, so that it will split the hugepages before returning them. @@ -66,11 +67,11 @@ pmd_offset. It's trivial to make the code transparent hugepage aware by just grepping for "pmd_offset" and adding split_huge_pmd where missing after pmd_offset returns the pmd. Thanks to the graceful fallback design, with a one liner change, you can avoid to write -hundred if not thousand of lines of complex code to make your code +hundreds if not thousands of lines of complex code to make your code hugepage aware. If you're not walking pagetables but you run into a physical hugepage -but you can't handle it natively in your code, you can split it by +that you can't handle natively in your code, you can split it by calling split_huge_page(page). This is what the Linux VM does before it tries to swapout the hugepage for example. split_huge_page() can fail if the page is pinned and you must handle this correctly. @@ -97,18 +98,18 @@ split_huge_page() or split_huge_pmd() has a cost. To make pagetable walks huge pmd aware, all you need to do is to call pmd_trans_huge() on the pmd returned by pmd_offset. You must hold the -mmap_sem in read (or write) mode to be sure an huge pmd cannot be +mmap_sem in read (or write) mode to be sure a huge pmd cannot be created from under you by khugepaged (khugepaged collapse_huge_page takes the mmap_sem in write mode in addition to the anon_vma lock). If pmd_trans_huge returns false, you just fallback in the old code paths. If instead pmd_trans_huge returns true, you have to take the page table lock (pmd_lock()) and re-run pmd_trans_huge. Taking the -page table lock will prevent the huge pmd to be converted into a +page table lock will prevent the huge pmd being converted into a regular pmd from under you (split_huge_pmd can run in parallel to the pagetable walk). If the second pmd_trans_huge returns false, you should just drop the page table lock and fallback to the old code as -before. Otherwise you can proceed to process the huge pmd and the -hugepage natively. Once finished you can drop the page table lock. +before. Otherwise, you can proceed to process the huge pmd and the +hugepage natively. Once finished, you can drop the page table lock. Refcounts and transparent huge pages ==================================== @@ -116,61 +117,61 @@ Refcounts and transparent huge pages Refcounting on THP is mostly consistent with refcounting on other compound pages: - - get_page()/put_page() and GUP operate in head page's ->_refcount. + - get_page()/put_page() and GUP operate on head page's ->_refcount. - ->_refcount in tail pages is always zero: get_page_unless_zero() never - succeed on tail pages. + succeeds on tail pages. - map/unmap of the pages with PTE entry increment/decrement ->_mapcount on relevant sub-page of the compound page. - - map/unmap of the whole compound page accounted in compound_mapcount + - map/unmap of the whole compound page is accounted for in compound_mapcount (stored in first tail page). For file huge pages, we also increment ->_mapcount of all sub-pages in order to have race-free detection of last unmap of subpages. PageDoubleMap() indicates that the page is *possibly* mapped with PTEs. -For anonymous pages PageDoubleMap() also indicates ->_mapcount in all +For anonymous pages, PageDoubleMap() also indicates ->_mapcount in all subpages is offset up by one. This additional reference is required to get race-free detection of unmap of subpages when we have them mapped with both PMDs and PTEs. -This is optimization required to lower overhead of per-subpage mapcount -tracking. The alternative is alter ->_mapcount in all subpages on each +This optimization is required to lower the overhead of per-subpage mapcount +tracking. The alternative is to alter ->_mapcount in all subpages on each map/unmap of the whole compound page. -For anonymous pages, we set PG_double_map when a PMD of the page got split -for the first time, but still have PMD mapping. The additional references -go away with last compound_mapcount. +For anonymous pages, we set PG_double_map when a PMD of the page is split +for the first time, but still have a PMD mapping. The additional references +go away with the last compound_mapcount. -File pages get PG_double_map set on first map of the page with PTE and -goes away when the page gets evicted from page cache. +File pages get PG_double_map set on the first map of the page with PTE and +goes away when the page gets evicted from the page cache. split_huge_page internally has to distribute the refcounts in the head page to the tail pages before clearing all PG_head/tail bits from the page structures. It can be done easily for refcounts taken by page table -entries. But we don't have enough information on how to distribute any +entries, but we don't have enough information on how to distribute any additional pins (i.e. from get_user_pages). split_huge_page() fails any -requests to split pinned huge page: it expects page count to be equal to -sum of mapcount of all sub-pages plus one (split_huge_page caller must -have reference for head page). +requests to split pinned huge pages: it expects page count to be equal to +the sum of mapcount of all sub-pages plus one (split_huge_page caller must +have a reference to the head page). split_huge_page uses migration entries to stabilize page->_refcount and -page->_mapcount of anonymous pages. File pages just got unmapped. +page->_mapcount of anonymous pages. File pages just get unmapped. -We safe against physical memory scanners too: the only legitimate way -scanner can get reference to a page is get_page_unless_zero(). +We are safe against physical memory scanners too: the only legitimate way +a scanner can get a reference to a page is get_page_unless_zero(). All tail pages have zero ->_refcount until atomic_add(). This prevents the scanner from getting a reference to the tail page up to that point. After the -atomic_add() we don't care about the ->_refcount value. We already known how +atomic_add() we don't care about the ->_refcount value. We already know how many references should be uncharged from the head page. For head page get_page_unless_zero() will succeed and we don't mind. It's -clear where reference should go after split: it will stay on head page. +clear where references should go after split: it will stay on the head page. -Note that split_huge_pmd() doesn't have any limitation on refcounting: +Note that split_huge_pmd() doesn't have any limitations on refcounting: pmd can be split at any point and never fails. Partial unmap and deferred_split_huge_page() @@ -182,10 +183,10 @@ in page_remove_rmap() and queue the THP for splitting if memory pressure comes. Splitting will free up unused subpages. Splitting the page right away is not an option due to locking context in -the place where we can detect partial unmap. It's also might be +the place where we can detect partial unmap. It also might be counterproductive since in many cases partial unmap happens during exit(2) if a THP crosses a VMA boundary. -Function deferred_split_huge_page() is used to queue page for splitting. +The function deferred_split_huge_page() is used to queue a page for splitting. The splitting itself will happen when we get memory pressure via shrinker interface. -- cgit v1.2.3 From 6989303a3b2d864fd8e17d3fa3365d3e9649a598 Mon Sep 17 00:00:00 2001 From: Marc Zyngier Date: Mon, 15 Apr 2019 13:03:54 +0100 Subject: arm64: Apply ARM64_ERRATUM_1188873 to Neoverse-N1 Neoverse-N1 is also affected by ARM64_ERRATUM_1188873, so let's add it to the list of affected CPUs. Signed-off-by: Marc Zyngier [will: Update silicon-errata.txt] Signed-off-by: Will Deacon --- Documentation/arm64/silicon-errata.txt | 1 + arch/arm64/Kconfig | 11 ++++++----- arch/arm64/kernel/cpu_errata.c | 13 +++++++++++-- 3 files changed, 18 insertions(+), 7 deletions(-) (limited to 'Documentation') diff --git a/Documentation/arm64/silicon-errata.txt b/Documentation/arm64/silicon-errata.txt index d1e2bb801e1b..d5a124d7e242 100644 --- a/Documentation/arm64/silicon-errata.txt +++ b/Documentation/arm64/silicon-errata.txt @@ -61,6 +61,7 @@ stable kernels. | ARM | Cortex-A76 | #1188873 | ARM64_ERRATUM_1188873 | | ARM | Cortex-A76 | #1165522 | ARM64_ERRATUM_1165522 | | ARM | Cortex-A76 | #1286807 | ARM64_ERRATUM_1286807 | +| ARM | Neoverse-N1 | #1188873 | ARM64_ERRATUM_1188873 | | ARM | MMU-500 | #841119,#826419 | N/A | | | | | | | Cavium | ThunderX ITS | #22375, #24313 | CAVIUM_ERRATUM_22375 | diff --git a/arch/arm64/Kconfig b/arch/arm64/Kconfig index 560f2a860637..fcda4e21fa8f 100644 --- a/arch/arm64/Kconfig +++ b/arch/arm64/Kconfig @@ -475,16 +475,17 @@ config ARM64_ERRATUM_1024718 If unsure, say Y. config ARM64_ERRATUM_1188873 - bool "Cortex-A76: MRC read following MRRC read of specific Generic Timer in AArch32 might give incorrect result" + bool "Cortex-A76/Neoverse-N1: MRC read following MRRC read of specific Generic Timer in AArch32 might give incorrect result" default y depends on COMPAT select ARM_ARCH_TIMER_OOL_WORKAROUND help - This option adds work arounds for ARM Cortex-A76 erratum 1188873 + This option adds work arounds for ARM Cortex-A76/Neoverse-N1 + erratum 1188873 - Affected Cortex-A76 cores (r0p0, r1p0, r2p0) could cause - register corruption when accessing the timer registers from - AArch32 userspace. + Affected Cortex-A76/Neoverse-N1 cores (r0p0, r1p0, r2p0) could + cause register corruption when accessing the timer registers + from AArch32 userspace. If unsure, say Y. diff --git a/arch/arm64/kernel/cpu_errata.c b/arch/arm64/kernel/cpu_errata.c index 9950bb0cbd52..06f1c8aae1dc 100644 --- a/arch/arm64/kernel/cpu_errata.c +++ b/arch/arm64/kernel/cpu_errata.c @@ -603,6 +603,16 @@ static const struct midr_range workaround_clean_cache[] = { }; #endif +#ifdef CONFIG_ARM64_ERRATUM_1188873 +static const struct midr_range erratum_1188873_list[] = { + /* Cortex-A76 r0p0 to r2p0 */ + MIDR_RANGE(MIDR_CORTEX_A76, 0, 0, 2, 0), + /* Neoverse-N1 r0p0 to r2p0 */ + MIDR_RANGE(MIDR_NEOVERSE_N1, 0, 0, 2, 0), + {}, +}; +#endif + const struct arm64_cpu_capabilities arm64_errata[] = { #ifdef CONFIG_ARM64_WORKAROUND_CLEAN_CACHE { @@ -725,10 +735,9 @@ const struct arm64_cpu_capabilities arm64_errata[] = { #endif #ifdef CONFIG_ARM64_ERRATUM_1188873 { - /* Cortex-A76 r0p0 to r2p0 */ .desc = "ARM erratum 1188873", .capability = ARM64_WORKAROUND_1188873, - ERRATA_MIDR_RANGE(MIDR_CORTEX_A76, 0, 0, 2, 0), + ERRATA_MIDR_RANGE_LIST(erratum_1188873_list), }, #endif #ifdef CONFIG_ARM64_ERRATUM_1165522 -- cgit v1.2.3 From 70833b84dac2d017ea119660e331b7dc7635c3a7 Mon Sep 17 00:00:00 2001 From: Paul Cercueil Date: Tue, 30 Apr 2019 09:59:38 -0500 Subject: dt-bindings: usb: Add usb-phy property to the jz4740-musb node Add a required 'usb-phy' property, to obtain a phandle to the USB PHY from devicetree. Signed-off-by: Paul Cercueil Reviewed-by: Rob Herring Signed-off-by: Bin Liu Signed-off-by: Greg Kroah-Hartman --- Documentation/devicetree/bindings/usb/ingenic,jz4740-musb.txt | 8 ++++++++ 1 file changed, 8 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/usb/ingenic,jz4740-musb.txt b/Documentation/devicetree/bindings/usb/ingenic,jz4740-musb.txt index 620355cee63f..16808721f3ff 100644 --- a/Documentation/devicetree/bindings/usb/ingenic,jz4740-musb.txt +++ b/Documentation/devicetree/bindings/usb/ingenic,jz4740-musb.txt @@ -8,9 +8,15 @@ Required properties: - interrupt-names: must be "mc" - clocks: phandle to the "udc" clock - clock-names: must be "udc" +- phys: phandle to the USB PHY Example: +usb_phy: usb-phy@0 { + compatible = "usb-nop-xceiv"; + #phy-cells = <0>; +}; + udc: usb@13040000 { compatible = "ingenic,jz4740-musb"; reg = <0x13040000 0x10000>; @@ -21,4 +27,6 @@ udc: usb@13040000 { clocks = <&cgu JZ4740_CLK_UDC>; clock-names = "udc"; + + phys = <&usb_phy>; }; -- cgit v1.2.3 From 0d672fffb447aa1699d76fdacd90dc31eeb66d97 Mon Sep 17 00:00:00 2001 From: Eddie James Date: Wed, 24 Apr 2019 11:16:59 -0400 Subject: media: dt-bindings: aspeed-video: Add missing memory-region property Missed documenting this property in the initial commit. Signed-off-by: Eddie James Reviewed-by: Rob Herring Signed-off-by: Hans Verkuil Signed-off-by: Mauro Carvalho Chehab --- Documentation/devicetree/bindings/media/aspeed-video.txt | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/media/aspeed-video.txt b/Documentation/devicetree/bindings/media/aspeed-video.txt index 78b464ae2672..ce2894506e1f 100644 --- a/Documentation/devicetree/bindings/media/aspeed-video.txt +++ b/Documentation/devicetree/bindings/media/aspeed-video.txt @@ -14,6 +14,11 @@ Required properties: the VE - interrupts: the interrupt associated with the VE on this platform +Optional properties: + - memory-region: + phandle to a memory region to allocate from, as defined in + Documentation/devicetree/bindings/reserved-memory/reserved-memory.txt + Example: video-engine@1e700000 { @@ -23,4 +28,5 @@ video-engine@1e700000 { clock-names = "vclk", "eclk"; resets = <&syscon ASPEED_RESET_VIDEO>; interrupts = <7>; + memory-region = <&video_engine_memory>; }; -- cgit v1.2.3 From 76d58e0f07ec203bbdfcaabd9a9fc10a5a3ed5ea Mon Sep 17 00:00:00 2001 From: Paolo Bonzini Date: Wed, 17 Apr 2019 15:28:44 +0200 Subject: KVM: fix KVM_CLEAR_DIRTY_LOG for memory slots of unaligned size If a memory slot's size is not a multiple of 64 pages (256K), then the KVM_CLEAR_DIRTY_LOG API is unusable: clearing the final 64 pages either requires the requested page range to go beyond memslot->npages, or requires log->num_pages to be unaligned, and kvm_clear_dirty_log_protect requires log->num_pages to be both in range and aligned. To allow this case, allow log->num_pages not to be a multiple of 64 if it ends exactly on the last page of the slot. Reported-by: Peter Xu Fixes: 98938aa8edd6 ("KVM: validate userspace input in kvm_clear_dirty_log_protect()", 2019-01-02) Signed-off-by: Paolo Bonzini --- Documentation/virtual/kvm/api.txt | 5 +++-- tools/testing/selftests/kvm/dirty_log_test.c | 9 ++++++--- virt/kvm/kvm_main.c | 7 ++++--- 3 files changed, 13 insertions(+), 8 deletions(-) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/api.txt b/Documentation/virtual/kvm/api.txt index 7f3ebc9e7cee..64b38dfcc243 100644 --- a/Documentation/virtual/kvm/api.txt +++ b/Documentation/virtual/kvm/api.txt @@ -3830,8 +3830,9 @@ The ioctl clears the dirty status of pages in a memory slot, according to the bitmap that is passed in struct kvm_clear_dirty_log's dirty_bitmap field. Bit 0 of the bitmap corresponds to page "first_page" in the memory slot, and num_pages is the size in bits of the input bitmap. -Both first_page and num_pages must be a multiple of 64. For each bit -that is set in the input bitmap, the corresponding page is marked "clean" +first_page must be a multiple of 64; num_pages must also be a multiple of +64 unless first_page + num_pages is the size of the memory slot. For each +bit that is set in the input bitmap, the corresponding page is marked "clean" in KVM's dirty bitmap, and dirty tracking is re-enabled for that page (for example via write-protection, or by clearing the dirty bit in a page table entry). diff --git a/tools/testing/selftests/kvm/dirty_log_test.c b/tools/testing/selftests/kvm/dirty_log_test.c index 4715cfba20dc..93f99c6b7d79 100644 --- a/tools/testing/selftests/kvm/dirty_log_test.c +++ b/tools/testing/selftests/kvm/dirty_log_test.c @@ -288,8 +288,11 @@ static void run_test(enum vm_guest_mode mode, unsigned long iterations, #endif max_gfn = (1ul << (guest_pa_bits - guest_page_shift)) - 1; guest_page_size = (1ul << guest_page_shift); - /* 1G of guest page sized pages */ - guest_num_pages = (1ul << (30 - guest_page_shift)); + /* + * A little more than 1G of guest page sized pages. Cover the + * case where the size is not aligned to 64 pages. + */ + guest_num_pages = (1ul << (30 - guest_page_shift)) + 3; host_page_size = getpagesize(); host_num_pages = (guest_num_pages * guest_page_size) / host_page_size + !!((guest_num_pages * guest_page_size) % host_page_size); @@ -359,7 +362,7 @@ static void run_test(enum vm_guest_mode mode, unsigned long iterations, kvm_vm_get_dirty_log(vm, TEST_MEM_SLOT_INDEX, bmap); #ifdef USE_CLEAR_DIRTY_LOG kvm_vm_clear_dirty_log(vm, TEST_MEM_SLOT_INDEX, bmap, 0, - DIV_ROUND_UP(host_num_pages, 64) * 64); + host_num_pages); #endif vm_dirty_log_verify(bmap); iteration++; diff --git a/virt/kvm/kvm_main.c b/virt/kvm/kvm_main.c index dc8edc97ba85..a704d1f9bd96 100644 --- a/virt/kvm/kvm_main.c +++ b/virt/kvm/kvm_main.c @@ -1240,7 +1240,7 @@ int kvm_clear_dirty_log_protect(struct kvm *kvm, if (as_id >= KVM_ADDRESS_SPACE_NUM || id >= KVM_USER_MEM_SLOTS) return -EINVAL; - if ((log->first_page & 63) || (log->num_pages & 63)) + if (log->first_page & 63) return -EINVAL; slots = __kvm_memslots(kvm, as_id); @@ -1253,8 +1253,9 @@ int kvm_clear_dirty_log_protect(struct kvm *kvm, n = kvm_dirty_bitmap_bytes(memslot); if (log->first_page > memslot->npages || - log->num_pages > memslot->npages - log->first_page) - return -EINVAL; + log->num_pages > memslot->npages - log->first_page || + (log->num_pages < memslot->npages - log->first_page && (log->num_pages & 63))) + return -EINVAL; *flush = false; dirty_bitmap_buffer = kvm_second_dirty_bitmap(memslot); -- cgit v1.2.3 From 3a1e5e4a2c7a1ec63e6d70a7e921f62bcbb57b85 Mon Sep 17 00:00:00 2001 From: Radim Krčmář Date: Mon, 29 Apr 2019 15:25:35 +0200 Subject: Revert "KVM: doc: Document the life cycle of a VM and its resources" MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This reverts commit 919f6cd8bb2fe7151f8aecebc3b3d1ca2567396e. The patch was applied twice. The first commit is eca6be566d47029f945a5f8e1c94d374e31df2ca. Reported-by: Cornelia Huck Signed-off-by: Radim Krčmář Signed-off-by: Paolo Bonzini --- Documentation/virtual/kvm/api.txt | 17 ----------------- 1 file changed, 17 deletions(-) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/api.txt b/Documentation/virtual/kvm/api.txt index b62ad0d94234..26dc1280b49b 100644 --- a/Documentation/virtual/kvm/api.txt +++ b/Documentation/virtual/kvm/api.txt @@ -69,23 +69,6 @@ by and on behalf of the VM's process may not be freed/unaccounted when the VM is shut down. -It is important to note that althought VM ioctls may only be issued from -the process that created the VM, a VM's lifecycle is associated with its -file descriptor, not its creator (process). In other words, the VM and -its resources, *including the associated address space*, are not freed -until the last reference to the VM's file descriptor has been released. -For example, if fork() is issued after ioctl(KVM_CREATE_VM), the VM will -not be freed until both the parent (original) process and its child have -put their references to the VM's file descriptor. - -Because a VM's resources are not freed until the last reference to its -file descriptor is released, creating additional references to a VM via -via fork(), dup(), etc... without careful consideration is strongly -discouraged and may have unwanted side effects, e.g. memory allocated -by and on behalf of the VM's process may not be freed/unaccounted when -the VM is shut down. - - 3. Extensions ------------- -- cgit v1.2.3 From 65c4189de8c1d995f6bc2cc96b22206405466b53 Mon Sep 17 00:00:00 2001 From: Paolo Bonzini Date: Wed, 17 Apr 2019 15:28:44 +0200 Subject: KVM: fix KVM_CLEAR_DIRTY_LOG for memory slots of unaligned size If a memory slot's size is not a multiple of 64 pages (256K), then the KVM_CLEAR_DIRTY_LOG API is unusable: clearing the final 64 pages either requires the requested page range to go beyond memslot->npages, or requires log->num_pages to be unaligned, and kvm_clear_dirty_log_protect requires log->num_pages to be both in range and aligned. To allow this case, allow log->num_pages not to be a multiple of 64 if it ends exactly on the last page of the slot. Reported-by: Peter Xu Fixes: 98938aa8edd6 ("KVM: validate userspace input in kvm_clear_dirty_log_protect()", 2019-01-02) Signed-off-by: Paolo Bonzini --- Documentation/virtual/kvm/api.txt | 5 +++-- tools/testing/selftests/kvm/dirty_log_test.c | 4 ++-- virt/kvm/kvm_main.c | 7 ++++--- 3 files changed, 9 insertions(+), 7 deletions(-) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/api.txt b/Documentation/virtual/kvm/api.txt index 26dc1280b49b..675cb0bea903 100644 --- a/Documentation/virtual/kvm/api.txt +++ b/Documentation/virtual/kvm/api.txt @@ -3812,8 +3812,9 @@ The ioctl clears the dirty status of pages in a memory slot, according to the bitmap that is passed in struct kvm_clear_dirty_log's dirty_bitmap field. Bit 0 of the bitmap corresponds to page "first_page" in the memory slot, and num_pages is the size in bits of the input bitmap. -Both first_page and num_pages must be a multiple of 64. For each bit -that is set in the input bitmap, the corresponding page is marked "clean" +first_page must be a multiple of 64; num_pages must also be a multiple of +64 unless first_page + num_pages is the size of the memory slot. For each +bit that is set in the input bitmap, the corresponding page is marked "clean" in KVM's dirty bitmap, and dirty tracking is re-enabled for that page (for example via write-protection, or by clearing the dirty bit in a page table entry). diff --git a/tools/testing/selftests/kvm/dirty_log_test.c b/tools/testing/selftests/kvm/dirty_log_test.c index 4715cfba20dc..052fb5856df4 100644 --- a/tools/testing/selftests/kvm/dirty_log_test.c +++ b/tools/testing/selftests/kvm/dirty_log_test.c @@ -289,7 +289,7 @@ static void run_test(enum vm_guest_mode mode, unsigned long iterations, max_gfn = (1ul << (guest_pa_bits - guest_page_shift)) - 1; guest_page_size = (1ul << guest_page_shift); /* 1G of guest page sized pages */ - guest_num_pages = (1ul << (30 - guest_page_shift)); + guest_num_pages = (1ul << (30 - guest_page_shift)) + 3; host_page_size = getpagesize(); host_num_pages = (guest_num_pages * guest_page_size) / host_page_size + !!((guest_num_pages * guest_page_size) % host_page_size); @@ -359,7 +359,7 @@ static void run_test(enum vm_guest_mode mode, unsigned long iterations, kvm_vm_get_dirty_log(vm, TEST_MEM_SLOT_INDEX, bmap); #ifdef USE_CLEAR_DIRTY_LOG kvm_vm_clear_dirty_log(vm, TEST_MEM_SLOT_INDEX, bmap, 0, - DIV_ROUND_UP(host_num_pages, 64) * 64); + host_num_pages); #endif vm_dirty_log_verify(bmap); iteration++; diff --git a/virt/kvm/kvm_main.c b/virt/kvm/kvm_main.c index 71ac0de892dc..e9ca417b9ae9 100644 --- a/virt/kvm/kvm_main.c +++ b/virt/kvm/kvm_main.c @@ -1240,7 +1240,7 @@ int kvm_clear_dirty_log_protect(struct kvm *kvm, if (as_id >= KVM_ADDRESS_SPACE_NUM || id >= KVM_USER_MEM_SLOTS) return -EINVAL; - if ((log->first_page & 63) || (log->num_pages & 63)) + if (log->first_page & 63) return -EINVAL; slots = __kvm_memslots(kvm, as_id); @@ -1253,8 +1253,9 @@ int kvm_clear_dirty_log_protect(struct kvm *kvm, n = kvm_dirty_bitmap_bytes(memslot); if (log->first_page > memslot->npages || - log->num_pages > memslot->npages - log->first_page) - return -EINVAL; + log->num_pages > memslot->npages - log->first_page || + (log->num_pages < memslot->npages - log->first_page && (log->num_pages & 63))) + return -EINVAL; *flush = false; dirty_bitmap_buffer = kvm_second_dirty_bitmap(memslot); -- cgit v1.2.3 From e4f3fabd67480bf2ad3f71aa6126ffb8bb7dc712 Mon Sep 17 00:00:00 2001 From: Bryan Gurney Date: Thu, 7 Mar 2019 15:42:39 -0500 Subject: dm: add dust target Add the dm-dust target, which simulates the behavior of bad sectors at arbitrary locations, and the ability to enable the emulation of the read failures at an arbitrary time. This target behaves similarly to a linear target. At a given time, the user can send a message to the target to start failing read requests on specific blocks. When the failure behavior is enabled, reads of blocks configured "bad" will fail with EIO. Writes of blocks configured "bad" will result in the following: 1. Remove the block from the "bad block list". 2. Successfully complete the write. After this point, the block will successfully contain the written data, and will service reads and writes normally. This emulates the behavior of a "remapped sector" on a hard disk drive. dm-dust provides logging of which blocks have been added or removed to the "bad block list", as well as logging when a block has been removed from the bad block list. These messages can be used alongside the messages from the driver using a dm-dust device to analyze the driver's behavior when a read fails at a given time. (This logging can be reduced via a "quiet" mode, if desired.) NOTE: If the block size is larger than 512 bytes, only the first sector of each "dust block" is detected. Placing a limiting layer above a dust target, to limit the minimum I/O size to the dust block size, will ensure proper emulation of the given large block size. Signed-off-by: Bryan Gurney Co-developed-by: Joe Shimkus Co-developed-by: John Dorminy Co-developed-by: John Pittman Co-developed-by: Thomas Jaskiewicz Signed-off-by: Mike Snitzer --- Documentation/device-mapper/dm-dust.txt | 272 +++++++++++++++++ drivers/md/Kconfig | 9 + drivers/md/Makefile | 1 + drivers/md/dm-dust.c | 515 ++++++++++++++++++++++++++++++++ 4 files changed, 797 insertions(+) create mode 100644 Documentation/device-mapper/dm-dust.txt create mode 100644 drivers/md/dm-dust.c (limited to 'Documentation') diff --git a/Documentation/device-mapper/dm-dust.txt b/Documentation/device-mapper/dm-dust.txt new file mode 100644 index 000000000000..954d402a1f6a --- /dev/null +++ b/Documentation/device-mapper/dm-dust.txt @@ -0,0 +1,272 @@ +dm-dust +======= + +This target emulates the behavior of bad sectors at arbitrary +locations, and the ability to enable the emulation of the failures +at an arbitrary time. + +This target behaves similarly to a linear target. At a given time, +the user can send a message to the target to start failing read +requests on specific blocks (to emulate the behavior of a hard disk +drive with bad sectors). + +When the failure behavior is enabled (i.e.: when the output of +"dmsetup status" displays "fail_read_on_bad_block"), reads of blocks +in the "bad block list" will fail with EIO ("Input/output error"). + +Writes of blocks in the "bad block list will result in the following: + +1. Remove the block from the "bad block list". +2. Successfully complete the write. + +This emulates the "remapped sector" behavior of a drive with bad +sectors. + +Normally, a drive that is encountering bad sectors will most likely +encounter more bad sectors, at an unknown time or location. +With dm-dust, the user can use the "addbadblock" and "removebadblock" +messages to add arbitrary bad blocks at new locations, and the +"enable" and "disable" messages to modulate the state of whether the +configured "bad blocks" will be treated as bad, or bypassed. +This allows the pre-writing of test data and metadata prior to +simulating a "failure" event where bad sectors start to appear. + +Table parameters: +----------------- + + +Mandatory parameters: + : path to the block device. + : offset to data area from start of device_path + : block size in bytes + (minimum 512, maximum 1073741824, must be a power of 2) + +Usage instructions: +------------------- + +First, find the size (in 512-byte sectors) of the device to be used: + +$ sudo blockdev --getsz /dev/vdb1 +33552384 + +Create the dm-dust device: +(For a device with a block size of 512 bytes) +$ sudo dmsetup create dust1 --table '0 33552384 dust /dev/vdb1 0 512' + +(For a device with a block size of 4096 bytes) +$ sudo dmsetup create dust1 --table '0 33552384 dust /dev/vdb1 0 4096' + +Check the status of the read behavior ("bypass" indicates that all I/O +will be passed through to the underlying device): +$ sudo dmsetup status dust1 +0 33552384 dust 252:17 bypass + +$ sudo dd if=/dev/mapper/dust1 of=/dev/null bs=512 count=128 iflag=direct +128+0 records in +128+0 records out + +$ sudo dd if=/dev/zero of=/dev/mapper/dust1 bs=512 count=128 oflag=direct +128+0 records in +128+0 records out + +Adding and removing bad blocks: +------------------------------- + +At any time (i.e.: whether the device has the "bad block" emulation +enabled or disabled), bad blocks may be added or removed from the +device via the "addbadblock" and "removebadblock" messages: + +$ sudo dmsetup message dust1 0 addbadblock 60 +kernel: device-mapper: dust: badblock added at block 60 + +$ sudo dmsetup message dust1 0 addbadblock 67 +kernel: device-mapper: dust: badblock added at block 67 + +$ sudo dmsetup message dust1 0 addbadblock 72 +kernel: device-mapper: dust: badblock added at block 72 + +These bad blocks will be stored in the "bad block list". +While the device is in "bypass" mode, reads and writes will succeed: + +$ sudo dmsetup status dust1 +0 33552384 dust 252:17 bypass + +Enabling block read failures: +----------------------------- + +To enable the "fail read on bad block" behavior, send the "enable" message: + +$ sudo dmsetup message dust1 0 enable +kernel: device-mapper: dust: enabling read failures on bad sectors + +$ sudo dmsetup status dust1 +0 33552384 dust 252:17 fail_read_on_bad_block + +With the device in "fail read on bad block" mode, attempting to read a +block will encounter an "Input/output error": + +$ sudo dd if=/dev/mapper/dust1 of=/dev/null bs=512 count=1 skip=67 iflag=direct +dd: error reading '/dev/mapper/dust1': Input/output error +0+0 records in +0+0 records out +0 bytes copied, 0.00040651 s, 0.0 kB/s + +...and writing to the bad blocks will remove the blocks from the list, +therefore emulating the "remap" behavior of hard disk drives: + +$ sudo dd if=/dev/zero of=/dev/mapper/dust1 bs=512 count=128 oflag=direct +128+0 records in +128+0 records out + +kernel: device-mapper: dust: block 60 removed from badblocklist by write +kernel: device-mapper: dust: block 67 removed from badblocklist by write +kernel: device-mapper: dust: block 72 removed from badblocklist by write +kernel: device-mapper: dust: block 87 removed from badblocklist by write + +Bad block add/remove error handling: +------------------------------------ + +Attempting to add a bad block that already exists in the list will +result in an "Invalid argument" error, as well as a helpful message: + +$ sudo dmsetup message dust1 0 addbadblock 88 +device-mapper: message ioctl on dust1 failed: Invalid argument +kernel: device-mapper: dust: block 88 already in badblocklist + +Attempting to remove a bad block that doesn't exist in the list will +result in an "Invalid argument" error, as well as a helpful message: + +$ sudo dmsetup message dust1 0 removebadblock 87 +device-mapper: message ioctl on dust1 failed: Invalid argument +kernel: device-mapper: dust: block 87 not found in badblocklist + +Counting the number of bad blocks in the bad block list: +-------------------------------------------------------- + +To count the number of bad blocks configured in the device, run the +following message command: + +$ sudo dmsetup message dust1 0 countbadblocks + +A message will print with the number of bad blocks currently +configured on the device: + +kernel: device-mapper: dust: countbadblocks: 895 badblock(s) found + +Querying for specific bad blocks: +--------------------------------- + +To find out if a specific block is in the bad block list, run the +following message command: + +$ sudo dmsetup message dust1 0 queryblock 72 + +The following message will print if the block is in the list: +device-mapper: dust: queryblock: block 72 found in badblocklist + +The following message will print if the block is in the list: +device-mapper: dust: queryblock: block 72 not found in badblocklist + +The "queryblock" message command will work in both the "enabled" +and "disabled" modes, allowing the verification of whether a block +will be treated as "bad" without having to issue I/O to the device, +or having to "enable" the bad block emulation. + +Clearing the bad block list: +---------------------------- + +To clear the bad block list (without needing to individually run +a "removebadblock" message command for every block), run the +following message command: + +$ sudo dmsetup message dust1 0 clearbadblocks + +After clearing the bad block list, the following message will appear: + +kernel: device-mapper: dust: clearbadblocks: badblocks cleared + +If there were no bad blocks to clear, the following message will +appear: + +kernel: device-mapper: dust: clearbadblocks: no badblocks found + +Message commands list: +---------------------- + +Below is a list of the messages that can be sent to a dust device: + +Operations on blocks (requires a argument): + +addbadblock +queryblock +removebadblock + +...where is a block number within range of the device + (corresponding to the block size of the device.) + +Single argument message commands: + +countbadblocks +clearbadblocks +disable +enable +quiet + +Device removal: +--------------- + +When finished, remove the device via the "dmsetup remove" command: + +$ sudo dmsetup remove dust1 + +Quiet mode: +----------- + +On test runs with many bad blocks, it may be desirable to avoid +excessive logging (from bad blocks added, removed, or "remapped"). +This can be done by enabling "quiet mode" via the following message: + +$ sudo dmsetup message dust1 0 quiet + +This will suppress log messages from add / remove / removed by write +operations. Log messages from "countbadblocks" or "queryblock" +message commands will still print in quiet mode. + +The status of quiet mode can be seen by running "dmsetup status": + +$ sudo dmsetup status dust1 +0 33552384 dust 252:17 fail_read_on_bad_block quiet + +To disable quiet mode, send the "quiet" message again: + +$ sudo dmsetup message dust1 0 quiet + +$ sudo dmsetup status dust1 +0 33552384 dust 252:17 fail_read_on_bad_block verbose + +(The presence of "verbose" indicates normal logging.) + +"Why not...?" +------------- + +scsi_debug has a "medium error" mode that can fail reads on one +specified sector (sector 0x1234, hardcoded in the source code), but +it uses RAM for the persistent storage, which drastically decreases +the potential device size. + +dm-flakey fails all I/O from all block locations at a specified time +frequency, and not a given point in time. + +When a bad sector occurs on a hard disk drive, reads to that sector +are failed by the device, usually resulting in an error code of EIO +("I/O error") or ENODATA ("No data available"). However, a write to +the sector may succeed, and result in the sector becoming readable +after the device controller no longer experiences errors reading the +sector (or after a reallocation of the sector). However, there may +be bad sectors that occur on the device in the future, in a different, +unpredictable location. + +This target seeks to provide a device that can exhibit the behavior +of a bad sector at a known sector location, at a known time, based +on a large storage device (at least tens of gigabytes, not occupying +system memory). diff --git a/drivers/md/Kconfig b/drivers/md/Kconfig index 2557f198e175..db269a348b20 100644 --- a/drivers/md/Kconfig +++ b/drivers/md/Kconfig @@ -436,6 +436,15 @@ config DM_DELAY If unsure, say N. +config DM_DUST + tristate "Bad sector simulation target" + depends on BLK_DEV_DM + ---help--- + A target that simulates bad sector behavior. + Useful for testing. + + If unsure, say N. + config DM_INIT bool "DM \"dm-mod.create=\" parameter support" depends on BLK_DEV_DM=y diff --git a/drivers/md/Makefile b/drivers/md/Makefile index a52b703e588e..be7a6eb92abc 100644 --- a/drivers/md/Makefile +++ b/drivers/md/Makefile @@ -48,6 +48,7 @@ obj-$(CONFIG_DM_BUFIO) += dm-bufio.o obj-$(CONFIG_DM_BIO_PRISON) += dm-bio-prison.o obj-$(CONFIG_DM_CRYPT) += dm-crypt.o obj-$(CONFIG_DM_DELAY) += dm-delay.o +obj-$(CONFIG_DM_DUST) += dm-dust.o obj-$(CONFIG_DM_FLAKEY) += dm-flakey.o obj-$(CONFIG_DM_MULTIPATH) += dm-multipath.o dm-round-robin.o obj-$(CONFIG_DM_MULTIPATH_QL) += dm-queue-length.o diff --git a/drivers/md/dm-dust.c b/drivers/md/dm-dust.c new file mode 100644 index 000000000000..178587bdc626 --- /dev/null +++ b/drivers/md/dm-dust.c @@ -0,0 +1,515 @@ +// SPDX-License-Identifier: GPL-2.0 +/* + * Copyright (c) 2018 Red Hat, Inc. + * + * This is a test "dust" device, which fails reads on specified + * sectors, emulating the behavior of a hard disk drive sending + * a "Read Medium Error" sense. + * + */ + +#include +#include +#include + +#define DM_MSG_PREFIX "dust" + +struct badblock { + struct rb_node node; + sector_t bb; +}; + +struct dust_device { + struct dm_dev *dev; + struct rb_root badblocklist; + unsigned long long badblock_count; + spinlock_t dust_lock; + unsigned int blksz; + unsigned int sect_per_block; + sector_t start; + bool fail_read_on_bb:1; + bool quiet_mode:1; +}; + +static struct badblock *dust_rb_search(struct rb_root *root, sector_t blk) +{ + struct rb_node *node = root->rb_node; + + while (node) { + struct badblock *bblk = rb_entry(node, struct badblock, node); + + if (bblk->bb > blk) + node = node->rb_left; + else if (bblk->bb < blk) + node = node->rb_right; + else + return bblk; + } + + return NULL; +} + +static bool dust_rb_insert(struct rb_root *root, struct badblock *new) +{ + struct badblock *bblk; + struct rb_node **link = &root->rb_node, *parent = NULL; + sector_t value = new->bb; + + while (*link) { + parent = *link; + bblk = rb_entry(parent, struct badblock, node); + + if (bblk->bb > value) + link = &(*link)->rb_left; + else if (bblk->bb < value) + link = &(*link)->rb_right; + else + return false; + } + + rb_link_node(&new->node, parent, link); + rb_insert_color(&new->node, root); + + return true; +} + +static int dust_remove_block(struct dust_device *dd, unsigned long long block) +{ + struct badblock *bblock; + unsigned long flags; + + spin_lock_irqsave(&dd->dust_lock, flags); + bblock = dust_rb_search(&dd->badblocklist, block * dd->sect_per_block); + + if (bblock == NULL) { + if (!dd->quiet_mode) { + DMERR("%s: block %llu not found in badblocklist", + __func__, block); + } + spin_unlock_irqrestore(&dd->dust_lock, flags); + return -EINVAL; + } + + rb_erase(&bblock->node, &dd->badblocklist); + dd->badblock_count--; + if (!dd->quiet_mode) + DMINFO("%s: badblock removed at block %llu", __func__, block); + kfree(bblock); + spin_unlock_irqrestore(&dd->dust_lock, flags); + + return 0; +} + +static int dust_add_block(struct dust_device *dd, unsigned long long block) +{ + struct badblock *bblock; + unsigned long flags; + + bblock = kmalloc(sizeof(*bblock), GFP_KERNEL); + if (bblock == NULL) { + if (!dd->quiet_mode) + DMERR("%s: badblock allocation failed", __func__); + return -ENOMEM; + } + + spin_lock_irqsave(&dd->dust_lock, flags); + bblock->bb = block * dd->sect_per_block; + if (!dust_rb_insert(&dd->badblocklist, bblock)) { + if (!dd->quiet_mode) { + DMERR("%s: block %llu already in badblocklist", + __func__, block); + } + spin_unlock_irqrestore(&dd->dust_lock, flags); + kfree(bblock); + return -EINVAL; + } + + dd->badblock_count++; + if (!dd->quiet_mode) + DMINFO("%s: badblock added at block %llu", __func__, block); + spin_unlock_irqrestore(&dd->dust_lock, flags); + + return 0; +} + +static int dust_query_block(struct dust_device *dd, unsigned long long block) +{ + struct badblock *bblock; + unsigned long flags; + + spin_lock_irqsave(&dd->dust_lock, flags); + bblock = dust_rb_search(&dd->badblocklist, block * dd->sect_per_block); + if (bblock != NULL) + DMINFO("%s: block %llu found in badblocklist", __func__, block); + else + DMINFO("%s: block %llu not found in badblocklist", __func__, block); + spin_unlock_irqrestore(&dd->dust_lock, flags); + + return 0; +} + +static int __dust_map_read(struct dust_device *dd, sector_t thisblock) +{ + struct badblock *bblk = dust_rb_search(&dd->badblocklist, thisblock); + + if (bblk) + return DM_MAPIO_KILL; + + return DM_MAPIO_REMAPPED; +} + +static int dust_map_read(struct dust_device *dd, sector_t thisblock, + bool fail_read_on_bb) +{ + unsigned long flags; + int ret = DM_MAPIO_REMAPPED; + + if (fail_read_on_bb) { + spin_lock_irqsave(&dd->dust_lock, flags); + ret = __dust_map_read(dd, thisblock); + spin_unlock_irqrestore(&dd->dust_lock, flags); + } + + return ret; +} + +static void __dust_map_write(struct dust_device *dd, sector_t thisblock) +{ + struct badblock *bblk = dust_rb_search(&dd->badblocklist, thisblock); + + if (bblk) { + rb_erase(&bblk->node, &dd->badblocklist); + dd->badblock_count--; + kfree(bblk); + if (!dd->quiet_mode) { + sector_div(thisblock, dd->sect_per_block); + DMINFO("block %llu removed from badblocklist by write", + (unsigned long long)thisblock); + } + } +} + +static int dust_map_write(struct dust_device *dd, sector_t thisblock, + bool fail_read_on_bb) +{ + unsigned long flags; + + if (fail_read_on_bb) { + spin_lock_irqsave(&dd->dust_lock, flags); + __dust_map_write(dd, thisblock); + spin_unlock_irqrestore(&dd->dust_lock, flags); + } + + return DM_MAPIO_REMAPPED; +} + +static int dust_map(struct dm_target *ti, struct bio *bio) +{ + struct dust_device *dd = ti->private; + int ret; + + bio_set_dev(bio, dd->dev->bdev); + bio->bi_iter.bi_sector = dd->start + dm_target_offset(ti, bio->bi_iter.bi_sector); + + if (bio_data_dir(bio) == READ) + ret = dust_map_read(dd, bio->bi_iter.bi_sector, dd->fail_read_on_bb); + else + ret = dust_map_write(dd, bio->bi_iter.bi_sector, dd->fail_read_on_bb); + + return ret; +} + +static bool __dust_clear_badblocks(struct rb_root *tree, + unsigned long long count) +{ + struct rb_node *node = NULL, *nnode = NULL; + + nnode = rb_first(tree); + if (nnode == NULL) { + BUG_ON(count != 0); + return false; + } + + while (nnode) { + node = nnode; + nnode = rb_next(node); + rb_erase(node, tree); + count--; + kfree(node); + } + BUG_ON(count != 0); + BUG_ON(tree->rb_node != NULL); + + return true; +} + +static int dust_clear_badblocks(struct dust_device *dd) +{ + unsigned long flags; + struct rb_root badblocklist; + unsigned long long badblock_count; + + spin_lock_irqsave(&dd->dust_lock, flags); + badblocklist = dd->badblocklist; + badblock_count = dd->badblock_count; + dd->badblocklist = RB_ROOT; + dd->badblock_count = 0; + spin_unlock_irqrestore(&dd->dust_lock, flags); + + if (!__dust_clear_badblocks(&badblocklist, badblock_count)) + DMINFO("%s: no badblocks found", __func__); + else + DMINFO("%s: badblocks cleared", __func__); + + return 0; +} + +/* + * Target parameters: + * + * + * + * device_path: path to the block device + * offset: offset to data area from start of device_path + * blksz: block size (minimum 512, maximum 1073741824, must be a power of 2) + */ +static int dust_ctr(struct dm_target *ti, unsigned int argc, char **argv) +{ + struct dust_device *dd; + unsigned long long tmp; + char dummy; + unsigned int blksz; + unsigned int sect_per_block; + sector_t DUST_MAX_BLKSZ_SECTORS = 2097152; + sector_t max_block_sectors = min(ti->len, DUST_MAX_BLKSZ_SECTORS); + + if (argc != 3) { + ti->error = "Invalid argument count"; + return -EINVAL; + } + + if (kstrtouint(argv[2], 10, &blksz) || !blksz) { + ti->error = "Invalid block size parameter"; + return -EINVAL; + } + + if (blksz < 512) { + ti->error = "Block size must be at least 512"; + return -EINVAL; + } + + if (!is_power_of_2(blksz)) { + ti->error = "Block size must be a power of 2"; + return -EINVAL; + } + + if (to_sector(blksz) > max_block_sectors) { + ti->error = "Block size is too large"; + return -EINVAL; + } + + sect_per_block = (blksz >> SECTOR_SHIFT); + + if (sscanf(argv[1], "%llu%c", &tmp, &dummy) != 1 || tmp != (sector_t)tmp) { + ti->error = "Invalid device offset sector"; + return -EINVAL; + } + + dd = kzalloc(sizeof(struct dust_device), GFP_KERNEL); + if (dd == NULL) { + ti->error = "Cannot allocate context"; + return -ENOMEM; + } + + if (dm_get_device(ti, argv[0], dm_table_get_mode(ti->table), &dd->dev)) { + ti->error = "Device lookup failed"; + kfree(dd); + return -EINVAL; + } + + dd->sect_per_block = sect_per_block; + dd->blksz = blksz; + dd->start = tmp; + + /* + * Whether to fail a read on a "bad" block. + * Defaults to false; enabled later by message. + */ + dd->fail_read_on_bb = false; + + /* + * Initialize bad block list rbtree. + */ + dd->badblocklist = RB_ROOT; + dd->badblock_count = 0; + spin_lock_init(&dd->dust_lock); + + dd->quiet_mode = false; + + BUG_ON(dm_set_target_max_io_len(ti, dd->sect_per_block) != 0); + + ti->num_discard_bios = 1; + ti->num_flush_bios = 1; + ti->private = dd; + + return 0; +} + +static void dust_dtr(struct dm_target *ti) +{ + struct dust_device *dd = ti->private; + + __dust_clear_badblocks(&dd->badblocklist, dd->badblock_count); + dm_put_device(ti, dd->dev); + kfree(dd); +} + +static int dust_message(struct dm_target *ti, unsigned int argc, char **argv, + char *result_buf, unsigned int maxlen) +{ + struct dust_device *dd = ti->private; + sector_t size = i_size_read(dd->dev->bdev->bd_inode) >> SECTOR_SHIFT; + bool invalid_msg = false; + int result = -EINVAL; + unsigned long long tmp, block; + unsigned long flags; + char dummy; + + if (argc == 1) { + if (!strcasecmp(argv[0], "addbadblock") || + !strcasecmp(argv[0], "removebadblock") || + !strcasecmp(argv[0], "queryblock")) { + DMERR("%s requires an additional argument", argv[0]); + } else if (!strcasecmp(argv[0], "disable")) { + DMINFO("disabling read failures on bad sectors"); + dd->fail_read_on_bb = false; + result = 0; + } else if (!strcasecmp(argv[0], "enable")) { + DMINFO("enabling read failures on bad sectors"); + dd->fail_read_on_bb = true; + result = 0; + } else if (!strcasecmp(argv[0], "countbadblocks")) { + spin_lock_irqsave(&dd->dust_lock, flags); + DMINFO("countbadblocks: %llu badblock(s) found", + dd->badblock_count); + spin_unlock_irqrestore(&dd->dust_lock, flags); + result = 0; + } else if (!strcasecmp(argv[0], "clearbadblocks")) { + result = dust_clear_badblocks(dd); + } else if (!strcasecmp(argv[0], "quiet")) { + if (!dd->quiet_mode) + dd->quiet_mode = true; + else + dd->quiet_mode = false; + result = 0; + } else { + invalid_msg = true; + } + } else if (argc == 2) { + if (sscanf(argv[1], "%llu%c", &tmp, &dummy) != 1) + return result; + + block = tmp; + sector_div(size, dd->sect_per_block); + if (block > size || block < 0) { + DMERR("selected block value out of range"); + return result; + } + + if (!strcasecmp(argv[0], "addbadblock")) + result = dust_add_block(dd, block); + else if (!strcasecmp(argv[0], "removebadblock")) + result = dust_remove_block(dd, block); + else if (!strcasecmp(argv[0], "queryblock")) + result = dust_query_block(dd, block); + else + invalid_msg = true; + + } else + DMERR("invalid number of arguments '%d'", argc); + + if (invalid_msg) + DMERR("unrecognized message '%s' received", argv[0]); + + return result; +} + +static void dust_status(struct dm_target *ti, status_type_t type, + unsigned int status_flags, char *result, unsigned int maxlen) +{ + struct dust_device *dd = ti->private; + unsigned int sz = 0; + + switch (type) { + case STATUSTYPE_INFO: + DMEMIT("%s %s %s", dd->dev->name, + dd->fail_read_on_bb ? "fail_read_on_bad_block" : "bypass", + dd->quiet_mode ? "quiet" : "verbose"); + break; + + case STATUSTYPE_TABLE: + DMEMIT("%s %llu %u", dd->dev->name, + (unsigned long long)dd->start, dd->blksz); + break; + } +} + +static int dust_prepare_ioctl(struct dm_target *ti, struct block_device **bdev) +{ + struct dust_device *dd = ti->private; + struct dm_dev *dev = dd->dev; + + *bdev = dev->bdev; + + /* + * Only pass ioctls through if the device sizes match exactly. + */ + if (dd->start || + ti->len != i_size_read(dev->bdev->bd_inode) >> SECTOR_SHIFT) + return 1; + + return 0; +} + +static int dust_iterate_devices(struct dm_target *ti, iterate_devices_callout_fn fn, + void *data) +{ + struct dust_device *dd = ti->private; + + return fn(ti, dd->dev, dd->start, ti->len, data); +} + +static struct target_type dust_target = { + .name = "dust", + .version = {1, 0, 0}, + .module = THIS_MODULE, + .ctr = dust_ctr, + .dtr = dust_dtr, + .iterate_devices = dust_iterate_devices, + .map = dust_map, + .message = dust_message, + .status = dust_status, + .prepare_ioctl = dust_prepare_ioctl, +}; + +int __init dm_dust_init(void) +{ + int result = dm_register_target(&dust_target); + + if (result < 0) + DMERR("dm_register_target failed %d", result); + + return result; +} + +void __exit dm_dust_exit(void) +{ + dm_unregister_target(&dust_target); +} + +module_init(dm_dust_init); +module_exit(dm_dust_exit); + +MODULE_DESCRIPTION(DM_NAME " dust test target"); +MODULE_AUTHOR("Bryan Gurney "); +MODULE_LICENSE("GPL"); -- cgit v1.2.3 From c1b0f9fa064a90532a4184a31ce0847a979069f5 Mon Sep 17 00:00:00 2001 From: Andrew Lunn Date: Sun, 28 Apr 2019 02:56:24 +0200 Subject: dt-bindings: net: DSA: Remove legacy binding Now that the code to support the legacy binding has been removed, remove the documentation for it. Signed-off-by: Andrew Lunn Signed-off-by: David S. Miller --- Documentation/devicetree/bindings/net/dsa/dsa.txt | 155 ---------------------- 1 file changed, 155 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/net/dsa/dsa.txt b/Documentation/devicetree/bindings/net/dsa/dsa.txt index d66a5292b9d3..c107d2848888 100644 --- a/Documentation/devicetree/bindings/net/dsa/dsa.txt +++ b/Documentation/devicetree/bindings/net/dsa/dsa.txt @@ -1,12 +1,6 @@ Distributed Switch Architecture Device Tree Bindings ---------------------------------------------------- -Two bindings exist, one of which has been deprecated due to -limitations. - -Current Binding ---------------- - Switches are true Linux devices and can be probed by any means. Once probed, they register to the DSA framework, passing a node pointer. This node is expected to fulfil the following binding, and @@ -262,152 +256,3 @@ linked into one DSA cluster. }; }; }; - -Deprecated Binding ------------------- - -The deprecated binding makes use of a platform device to represent the -switches. The switches themselves are not Linux devices, and make use -of an MDIO bus for management. - -Required properties: -- compatible : Should be "marvell,dsa" -- #address-cells : Must be 2, first cell is the address on the MDIO bus - and second cell is the address in the switch tree. - Second cell is used only when cascading/chaining. -- #size-cells : Must be 0 -- dsa,ethernet : Should be a phandle to a valid Ethernet device node -- dsa,mii-bus : Should be a phandle to a valid MDIO bus device node - -Optional properties: -- interrupts : property with a value describing the switch - interrupt number (not supported by the driver) - -A DSA node can contain multiple switch chips which are therefore child nodes of -the parent DSA node. The maximum number of allowed child nodes is 4 -(DSA_MAX_SWITCHES). -Each of these switch child nodes should have the following required properties: - -- reg : Contains two fields. The first one describes the - address on the MII bus. The second is the switch - number that must be unique in cascaded configurations -- #address-cells : Must be 1 -- #size-cells : Must be 0 - -A switch child node has the following optional property: - -- eeprom-length : Set to the length of an EEPROM connected to the - switch. Must be set if the switch can not detect - the presence and/or size of a connected EEPROM, - otherwise optional. - -A switch may have multiple "port" children nodes - -Each port children node must have the following mandatory properties: -- reg : Describes the port address in the switch -- label : Describes the label associated with this port, special - labels are "cpu" to indicate a CPU port and "dsa" to - indicate an uplink/downlink port. - -Note that a port labelled "dsa" will imply checking for the uplink phandle -described below. - -Optional property: -- link : Should be a list of phandles to another switch's DSA port. - This property is only used when switches are being - chained/cascaded together. This port is used as outgoing port - towards the phandle port, which can be more than one hop away. - -- phy-handle : Phandle to a PHY on an external MDIO bus, not the - switch internal one. See - Documentation/devicetree/bindings/net/ethernet.txt - for details. - -- phy-mode : String representing the connection to the designated - PHY node specified by the 'phy-handle' property. See - Documentation/devicetree/bindings/net/ethernet.txt - for details. - -- mii-bus : Should be a phandle to a valid MDIO bus device node. - This mii-bus will be used in preference to the - global dsa,mii-bus defined above, for this switch. - -Optional subnodes: -- fixed-link : Fixed-link subnode describing a link to a non-MDIO - managed entity. See - Documentation/devicetree/bindings/net/fixed-link.txt - for details. - -Example: - - dsa@0 { - compatible = "marvell,dsa"; - #address-cells = <2>; - #size-cells = <0>; - - interrupts = <10>; - dsa,ethernet = <ðernet0>; - dsa,mii-bus = <&mii_bus0>; - - switch@0 { - #address-cells = <1>; - #size-cells = <0>; - reg = <16 0>; /* MDIO address 16, switch 0 in tree */ - - port@0 { - reg = <0>; - label = "lan1"; - phy-handle = <&phy0>; - }; - - port@1 { - reg = <1>; - label = "lan2"; - }; - - port@5 { - reg = <5>; - label = "cpu"; - }; - - switch0port6: port@6 { - reg = <6>; - label = "dsa"; - link = <&switch1port0 - &switch2port0>; - }; - }; - - switch@1 { - #address-cells = <1>; - #size-cells = <0>; - reg = <17 1>; /* MDIO address 17, switch 1 in tree */ - mii-bus = <&mii_bus1>; - reset-gpios = <&gpio5 1 GPIO_ACTIVE_LOW>; - - switch1port0: port@0 { - reg = <0>; - label = "dsa"; - link = <&switch0port6>; - }; - switch1port1: port@1 { - reg = <1>; - label = "dsa"; - link = <&switch2port1>; - }; - }; - - switch@2 { - #address-cells = <1>; - #size-cells = <0>; - reg = <18 2>; /* MDIO address 18, switch 2 in tree */ - mii-bus = <&mii_bus1>; - - switch2port0: port@0 { - reg = <0>; - label = "dsa"; - link = <&switch1port1 - &switch0port6>; - }; - }; - }; -- cgit v1.2.3 From c59a89972258102e7d22cda5927e6c8121d84f26 Mon Sep 17 00:00:00 2001 From: Eric Biggers Date: Thu, 11 Apr 2019 16:16:27 -0700 Subject: Documentation/filesystems/vfs.txt: remove bogus "Last updated" date This file has actually been updated over 100 times since the claimed "Last updated" date. Signed-off-by: Eric Biggers Signed-off-by: Al Viro --- Documentation/filesystems/vfs.txt | 2 -- 1 file changed, 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/filesystems/vfs.txt b/Documentation/filesystems/vfs.txt index 761c6fd24a53..33120f220f86 100644 --- a/Documentation/filesystems/vfs.txt +++ b/Documentation/filesystems/vfs.txt @@ -3,8 +3,6 @@ Original author: Richard Gooch - Last updated on June 24, 2007. - Copyright (C) 1999 Richard Gooch Copyright (C) 2005 Pekka Enberg -- cgit v1.2.3 From dcb2cb1f26f91df486492e2f2c2d62fe751fd21a Mon Sep 17 00:00:00 2001 From: Eric Biggers Date: Thu, 11 Apr 2019 16:16:28 -0700 Subject: Documentation/filesystems/vfs.txt: document how ->i_link works Signed-off-by: Eric Biggers Signed-off-by: Al Viro --- Documentation/filesystems/vfs.txt | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'Documentation') diff --git a/Documentation/filesystems/vfs.txt b/Documentation/filesystems/vfs.txt index 33120f220f86..57fc576b1f3e 100644 --- a/Documentation/filesystems/vfs.txt +++ b/Documentation/filesystems/vfs.txt @@ -463,6 +463,12 @@ otherwise noted. argument. If request can't be handled without leaving RCU mode, have it return ERR_PTR(-ECHILD). + If the filesystem stores the symlink target in ->i_link, the + VFS may use it directly without calling ->get_link(); however, + ->get_link() must still be provided. ->i_link must not be + freed until after an RCU grace period. Writing to ->i_link + post-iget() time requires a 'release' memory barrier. + readlink: this is now just an override for use by readlink(2) for the cases when ->get_link uses nd_jump_link() or object is not in fact a symlink. Normally filesystems should only implement -- cgit v1.2.3 From 1a6a31655071106a34ae06353390891a80c54371 Mon Sep 17 00:00:00 2001 From: Eric Biggers Date: Thu, 11 Apr 2019 16:16:29 -0700 Subject: Documentation/filesystems/Locking: fix ->get_link() prototype Signed-off-by: Eric Biggers Signed-off-by: Al Viro --- Documentation/filesystems/Locking | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/filesystems/Locking b/Documentation/filesystems/Locking index efea228ccd8a..428455bf9c97 100644 --- a/Documentation/filesystems/Locking +++ b/Documentation/filesystems/Locking @@ -52,7 +52,7 @@ prototypes: int (*rename) (struct inode *, struct dentry *, struct inode *, struct dentry *, unsigned int); int (*readlink) (struct dentry *, char __user *,int); - const char *(*get_link) (struct dentry *, struct inode *, void **); + const char *(*get_link) (struct dentry *, struct inode *, struct delayed_call *); void (*truncate) (struct inode *); int (*permission) (struct inode *, int, unsigned int); int (*get_acl)(struct inode *, int); -- cgit v1.2.3 From 754c9477ae78727d31692c76190b5567c567f435 Mon Sep 17 00:00:00 2001 From: Peter Ujfalusi Date: Tue, 30 Apr 2019 15:42:20 +0530 Subject: firmware: ti_sci: Add RM mapping table for am654 Add the resource mapping table for AM654 SoC as defined in http://downloads.ti.com/tisci/esd/latest/5_soc_doc/am6x/resasg_types.html Introduce a new compatible for AM654 "ti,am654-sci" for using this resource map table. Reviewed-by: Rob Herring Acked-by: Tony Lindgren Signed-off-by: Peter Ujfalusi Signed-off-by: Lokesh Vutla Acked-by: Nishanth Menon Signed-off-by: Marc Zyngier --- .../devicetree/bindings/arm/keystone/ti,sci.txt | 3 ++- drivers/firmware/ti_sci.c | 23 ++++++++++++++++++++++ 2 files changed, 25 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/keystone/ti,sci.txt b/Documentation/devicetree/bindings/arm/keystone/ti,sci.txt index b56a02c10ae6..6f0cd31c1520 100644 --- a/Documentation/devicetree/bindings/arm/keystone/ti,sci.txt +++ b/Documentation/devicetree/bindings/arm/keystone/ti,sci.txt @@ -24,7 +24,8 @@ relationship between the TI-SCI parent node to the child node. Required properties: ------------------- -- compatible: should be "ti,k2g-sci" +- compatible: should be "ti,k2g-sci" for TI 66AK2G SoC + should be "ti,am654-sci" for for TI AM654 SoC - mbox-names: "rx" - Mailbox corresponding to receive path "tx" - Mailbox corresponding to transmit path diff --git a/drivers/firmware/ti_sci.c b/drivers/firmware/ti_sci.c index 4ccdf9a53648..551895535767 100644 --- a/drivers/firmware/ti_sci.c +++ b/drivers/firmware/ti_sci.c @@ -2282,10 +2282,33 @@ static const struct ti_sci_desc ti_sci_pmmc_k2g_desc = { /* Limited by MBOX_TX_QUEUE_LEN. K2G can handle upto 128 messages! */ .max_msgs = 20, .max_msg_size = 64, + .rm_type_map = NULL, +}; + +static struct ti_sci_rm_type_map ti_sci_am654_rm_type_map[] = { + {.dev_id = 56, .type = 0x00b}, /* GIC_IRQ */ + {.dev_id = 179, .type = 0x000}, /* MAIN_NAV_UDMASS_IA0 */ + {.dev_id = 187, .type = 0x009}, /* MAIN_NAV_RA */ + {.dev_id = 188, .type = 0x006}, /* MAIN_NAV_UDMAP */ + {.dev_id = 194, .type = 0x007}, /* MCU_NAV_UDMAP */ + {.dev_id = 195, .type = 0x00a}, /* MCU_NAV_RA */ + {.dev_id = 0, .type = 0x000}, /* end of table */ +}; + +/* Description for AM654 */ +static const struct ti_sci_desc ti_sci_pmmc_am654_desc = { + .default_host_id = 12, + /* Conservative duration */ + .max_rx_timeout_ms = 10000, + /* Limited by MBOX_TX_QUEUE_LEN. K2G can handle upto 128 messages! */ + .max_msgs = 20, + .max_msg_size = 60, + .rm_type_map = ti_sci_am654_rm_type_map, }; static const struct of_device_id ti_sci_of_match[] = { {.compatible = "ti,k2g-sci", .data = &ti_sci_pmmc_k2g_desc}, + {.compatible = "ti,am654-sci", .data = &ti_sci_pmmc_am654_desc}, { /* Sentinel */ }, }; MODULE_DEVICE_TABLE(of, ti_sci_of_match); -- cgit v1.2.3 From 67d2075ad695b4c8ce08208abbc9eb1846d7ab81 Mon Sep 17 00:00:00 2001 From: Lokesh Vutla Date: Tue, 30 Apr 2019 15:42:24 +0530 Subject: dt-bindings: irqchip: Introduce TISCI Interrupt router bindings Add the DT binding documentation for Interrupt router driver. Signed-off-by: Lokesh Vutla Reviewed-by: Rob Herring Signed-off-by: Marc Zyngier --- .../bindings/interrupt-controller/ti,sci-intr.txt | 82 ++++++++++++++++++++++ MAINTAINERS | 1 + 2 files changed, 83 insertions(+) create mode 100644 Documentation/devicetree/bindings/interrupt-controller/ti,sci-intr.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/interrupt-controller/ti,sci-intr.txt b/Documentation/devicetree/bindings/interrupt-controller/ti,sci-intr.txt new file mode 100644 index 000000000000..1a8718f8855d --- /dev/null +++ b/Documentation/devicetree/bindings/interrupt-controller/ti,sci-intr.txt @@ -0,0 +1,82 @@ +Texas Instruments K3 Interrupt Router +===================================== + +The Interrupt Router (INTR) module provides a mechanism to mux M +interrupt inputs to N interrupt outputs, where all M inputs are selectable +to be driven per N output. An Interrupt Router can either handle edge triggered +or level triggered interrupts and that is fixed in hardware. + + Interrupt Router + +----------------------+ + | Inputs Outputs | + +-------+ | +------+ +-----+ | + | GPIO |----------->| | irq0 | | 0 | | Host IRQ + +-------+ | +------+ +-----+ | controller + | . . | +-------+ + +-------+ | . . |----->| IRQ | + | INTA |----------->| . . | +-------+ + +-------+ | . +-----+ | + | +------+ | N | | + | | irqM | +-----+ | + | +------+ | + | | + +----------------------+ + +There is one register per output (MUXCNTL_N) that controls the selection. +Configuration of these MUXCNTL_N registers is done by a system controller +(like the Device Memory and Security Controller on K3 AM654 SoC). System +controller will keep track of the used and unused registers within the Router. +Driver should request the system controller to get the range of GIC IRQs +assigned to the requesting hosts. It is the drivers responsibility to keep +track of Host IRQs. + +Communication between the host processor running an OS and the system +controller happens through a protocol called TI System Control Interface +(TISCI protocol). For more details refer: +Documentation/devicetree/bindings/arm/keystone/ti,sci.txt + +TISCI Interrupt Router Node: +---------------------------- +Required Properties: +- compatible: Must be "ti,sci-intr". +- ti,intr-trigger-type: Should be one of the following: + 1: If intr supports edge triggered interrupts. + 4: If intr supports level triggered interrupts. +- interrupt-controller: Identifies the node as an interrupt controller +- #interrupt-cells: Specifies the number of cells needed to encode an + interrupt source. The value should be 2. + First cell should contain the TISCI device ID of source + Second cell should contain the interrupt source offset + within the device. +- ti,sci: Phandle to TI-SCI compatible System controller node. +- ti,sci-dst-id: TISCI device ID of the destination IRQ controller. +- ti,sci-rm-range-girq: Array of TISCI subtype ids representing the host irqs + assigned to this interrupt router. Each subtype id + corresponds to a range of host irqs. + +For more details on TISCI IRQ resource management refer: +http://downloads.ti.com/tisci/esd/latest/2_tisci_msgs/rm/rm_irq.html + +Example: +-------- +The following example demonstrates both interrupt router node and the consumer +node(main gpio) on the AM654 SoC: + +main_intr: interrupt-controller0 { + compatible = "ti,sci-intr"; + ti,intr-trigger-type = <1>; + interrupt-controller; + interrupt-parent = <&gic500>; + #interrupt-cells = <2>; + ti,sci = <&dmsc>; + ti,sci-dst-id = <56>; + ti,sci-rm-range-girq = <0x1>; +}; + +main_gpio0: gpio@600000 { + ... + interrupt-parent = <&main_intr>; + interrupts = <57 256>, <57 257>, <57 258>, + <57 259>, <57 260>, <57 261>; + ... +}; diff --git a/MAINTAINERS b/MAINTAINERS index 3671fdea5010..b40762656a6d 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -15349,6 +15349,7 @@ F: Documentation/devicetree/bindings/reset/ti,sci-reset.txt F: Documentation/devicetree/bindings/clock/ti,sci-clk.txt F: drivers/clk/keystone/sci-clk.c F: drivers/reset/reset-ti-sci.c +F: Documentation/devicetree/bindings/interrupt-controller/ti,sci-intr.txt Texas Instruments ASoC drivers M: Peter Ujfalusi -- cgit v1.2.3 From accaf1fbfb5daebc9e5ea55644ff8fff3679b838 Mon Sep 17 00:00:00 2001 From: Lokesh Vutla Date: Tue, 30 Apr 2019 15:42:26 +0530 Subject: dt-bindings: irqchip: Introduce TISCI Interrupt Aggregator bindings Add the DT binding documentation for Interrupt Aggregator driver. Signed-off-by: Lokesh Vutla Reviewed-by: Rob Herring Signed-off-by: Marc Zyngier --- .../bindings/interrupt-controller/ti,sci-inta.txt | 66 ++++++++++++++++++++++ MAINTAINERS | 1 + 2 files changed, 67 insertions(+) create mode 100644 Documentation/devicetree/bindings/interrupt-controller/ti,sci-inta.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/interrupt-controller/ti,sci-inta.txt b/Documentation/devicetree/bindings/interrupt-controller/ti,sci-inta.txt new file mode 100644 index 000000000000..7841cb099e13 --- /dev/null +++ b/Documentation/devicetree/bindings/interrupt-controller/ti,sci-inta.txt @@ -0,0 +1,66 @@ +Texas Instruments K3 Interrupt Aggregator +========================================= + +The Interrupt Aggregator (INTA) provides a centralized machine +which handles the termination of system events to that they can +be coherently processed by the host(s) in the system. A maximum +of 64 events can be mapped to a single interrupt. + + + Interrupt Aggregator + +-----------------------------------------+ + | Intmap VINT | + | +--------------+ +------------+ | + m ------>| | vint | bit | | 0 |.....|63| vint0 | + . | +--------------+ +------------+ | +------+ + . | . . | | HOST | +Globalevents ------>| . . |------>| IRQ | + . | . . | | CTRL | + . | . . | +------+ + n ------>| +--------------+ +------------+ | + | | vint | bit | | 0 |.....|63| vintx | + | +--------------+ +------------+ | + | | + +-----------------------------------------+ + +Configuration of these Intmap registers that maps global events to vint is done +by a system controller (like the Device Memory and Security Controller on K3 +AM654 SoC). Driver should request the system controller to get the range +of global events and vints assigned to the requesting host. Management +of these requested resources should be handled by driver and requests +system controller to map specific global event to vint, bit pair. + +Communication between the host processor running an OS and the system +controller happens through a protocol called TI System Control Interface +(TISCI protocol). For more details refer: +Documentation/devicetree/bindings/arm/keystone/ti,sci.txt + +TISCI Interrupt Aggregator Node: +------------------------------- +- compatible: Must be "ti,sci-inta". +- reg: Should contain registers location and length. +- interrupt-controller: Identifies the node as an interrupt controller +- msi-controller: Identifies the node as an MSI controller. +- interrupt-parent: phandle of irq parent. +- ti,sci: Phandle to TI-SCI compatible System controller node. +- ti,sci-dev-id: TISCI device ID of the Interrupt Aggregator. +- ti,sci-rm-range-vint: Array of TISCI subtype ids representing vints(inta + outputs) range within this INTA, assigned to the + requesting host context. +- ti,sci-rm-range-global-event: Array of TISCI subtype ids representing the + global events range reaching this IA and are assigned + to the requesting host context. + +Example: +-------- +main_udmass_inta: interrupt-controller@33d00000 { + compatible = "ti,sci-inta"; + reg = <0x0 0x33d00000 0x0 0x100000>; + interrupt-controller; + msi-controller; + interrupt-parent = <&main_navss_intr>; + ti,sci = <&dmsc>; + ti,sci-dev-id = <179>; + ti,sci-rm-range-vint = <0x0>; + ti,sci-rm-range-global-event = <0x1>; +}; diff --git a/MAINTAINERS b/MAINTAINERS index 63851f106b5c..461db0a8233f 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -15350,6 +15350,7 @@ F: Documentation/devicetree/bindings/clock/ti,sci-clk.txt F: drivers/clk/keystone/sci-clk.c F: drivers/reset/reset-ti-sci.c F: Documentation/devicetree/bindings/interrupt-controller/ti,sci-intr.txt +F: Documentation/devicetree/bindings/interrupt-controller/ti,sci-inta.txt F: drivers/irqchip/irq-ti-sci-intr.c Texas Instruments ASoC drivers -- cgit v1.2.3 From 799381e49b4e7b0177664cdbc54a2de8b41647a8 Mon Sep 17 00:00:00 2001 From: Randy Dunlap Date: Sun, 28 Apr 2019 18:10:39 -0700 Subject: Documentation: fix netdev-FAQ.rst markup warning Fix ReST underline warning: ./Documentation/networking/netdev-FAQ.rst:135: WARNING: Title underline too short. Q: I made changes to only a few patches in a patch series should I resend only those changed? -------------------------------------------------------------------------------------------- Fixes: ffa91253739c ("Documentation: networking: Update netdev-FAQ regarding patches") Signed-off-by: Randy Dunlap Cc: Florian Fainelli Signed-off-by: David S. Miller --- Documentation/networking/netdev-FAQ.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/networking/netdev-FAQ.rst b/Documentation/networking/netdev-FAQ.rst index 8c7a713cf657..642fa963be3c 100644 --- a/Documentation/networking/netdev-FAQ.rst +++ b/Documentation/networking/netdev-FAQ.rst @@ -132,7 +132,7 @@ version that should be applied. If there is any doubt, the maintainer will reply and ask what should be done. Q: I made changes to only a few patches in a patch series should I resend only those changed? --------------------------------------------------------------------------------------------- +--------------------------------------------------------------------------------------------- A: No, please resend the entire patch series and make sure you do number your patches such that it is clear this is the latest and greatest set of patches that can be applied. -- cgit v1.2.3 From a111b7c0f20e13b54df2fa959b3dc0bdf1925ae6 Mon Sep 17 00:00:00 2001 From: Josh Poimboeuf Date: Fri, 12 Apr 2019 15:39:32 -0500 Subject: arm64/speculation: Support 'mitigations=' cmdline option Configure arm64 runtime CPU speculation bug mitigations in accordance with the 'mitigations=' cmdline option. This affects Meltdown, Spectre v2, and Speculative Store Bypass. The default behavior is unchanged. Signed-off-by: Josh Poimboeuf [will: reorder checks so KASLR implies KPTI and SSBS is affected by cmdline] Signed-off-by: Will Deacon --- Documentation/admin-guide/kernel-parameters.txt | 8 +++++--- arch/arm64/kernel/cpu_errata.c | 6 +++++- arch/arm64/kernel/cpufeature.c | 8 +++++++- 3 files changed, 17 insertions(+), 5 deletions(-) (limited to 'Documentation') diff --git a/Documentation/admin-guide/kernel-parameters.txt b/Documentation/admin-guide/kernel-parameters.txt index 6a929258faf7..ce226f7ee566 100644 --- a/Documentation/admin-guide/kernel-parameters.txt +++ b/Documentation/admin-guide/kernel-parameters.txt @@ -2545,8 +2545,8 @@ http://repo.or.cz/w/linux-2.6/mini2440.git mitigations= - [X86,PPC,S390] Control optional mitigations for CPU - vulnerabilities. This is a set of curated, + [X86,PPC,S390,ARM64] Control optional mitigations for + CPU vulnerabilities. This is a set of curated, arch-independent options, each of which is an aggregation of existing arch-specific options. @@ -2555,11 +2555,13 @@ improves system performance, but it may also expose users to several CPU vulnerabilities. Equivalent to: nopti [X86,PPC] + kpti=0 [ARM64] nospectre_v1 [PPC] nobp=0 [S390] - nospectre_v2 [X86,PPC,S390] + nospectre_v2 [X86,PPC,S390,ARM64] spectre_v2_user=off [X86] spec_store_bypass_disable=off [X86,PPC] + ssbd=force-off [ARM64] l1tf=off [X86] auto (default) diff --git a/arch/arm64/kernel/cpu_errata.c b/arch/arm64/kernel/cpu_errata.c index 44ef98be001e..1b9ce0fdd81d 100644 --- a/arch/arm64/kernel/cpu_errata.c +++ b/arch/arm64/kernel/cpu_errata.c @@ -19,6 +19,7 @@ #include #include #include +#include #include #include #include @@ -386,6 +387,9 @@ static bool has_ssbd_mitigation(const struct arm64_cpu_capabilities *entry, WARN_ON(scope != SCOPE_LOCAL_CPU || preemptible()); + if (cpu_mitigations_off()) + ssbd_state = ARM64_SSBD_FORCE_DISABLE; + /* delay setting __ssb_safe until we get a firmware response */ if (is_midr_in_range_list(read_cpuid_id(), entry->midr_range_list)) this_cpu_safe = true; @@ -589,7 +593,7 @@ check_branch_predictor(const struct arm64_cpu_capabilities *entry, int scope) } /* forced off */ - if (__nospectre_v2) { + if (__nospectre_v2 || cpu_mitigations_off()) { pr_info_once("spectrev2 mitigation disabled by command line option\n"); __hardenbp_enab = false; return false; diff --git a/arch/arm64/kernel/cpufeature.c b/arch/arm64/kernel/cpufeature.c index 703ee8564fbd..f3b32d88f165 100644 --- a/arch/arm64/kernel/cpufeature.c +++ b/arch/arm64/kernel/cpufeature.c @@ -25,6 +25,7 @@ #include #include #include +#include #include #include #include @@ -966,7 +967,7 @@ static bool unmap_kernel_at_el0(const struct arm64_cpu_capabilities *entry, MIDR_ALL_VERSIONS(MIDR_HISI_TSV110), { /* sentinel */ } }; - char const *str = "command line option"; + char const *str = "kpti command line option"; bool meltdown_safe; meltdown_safe = is_midr_in_range_list(read_cpuid_id(), kpti_safe_list); @@ -996,6 +997,11 @@ static bool unmap_kernel_at_el0(const struct arm64_cpu_capabilities *entry, } } + if (cpu_mitigations_off() && !__kpti_forced) { + str = "mitigations=off"; + __kpti_forced = -1; + } + if (!IS_ENABLED(CONFIG_UNMAP_KERNEL_AT_EL0)) { pr_info_once("kernel page table isolation disabled by kernel configuration\n"); return false; -- cgit v1.2.3 From 4ad499c94264a2ee05aacc518b9bde658318e510 Mon Sep 17 00:00:00 2001 From: Josh Poimboeuf Date: Fri, 12 Apr 2019 22:56:21 -0500 Subject: Documentation: Add ARM64 to kernel-parameters.rst Add ARM64 to the legend of architectures. It's already used in several places in kernel-parameters.txt. Suggested-by: Randy Dunlap Signed-off-by: Josh Poimboeuf Signed-off-by: Will Deacon --- Documentation/admin-guide/kernel-parameters.rst | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/admin-guide/kernel-parameters.rst b/Documentation/admin-guide/kernel-parameters.rst index b8d0bc07ed0a..0124980dca2d 100644 --- a/Documentation/admin-guide/kernel-parameters.rst +++ b/Documentation/admin-guide/kernel-parameters.rst @@ -88,6 +88,7 @@ parameter is applicable:: APIC APIC support is enabled. APM Advanced Power Management support is enabled. ARM ARM architecture is enabled. + ARM64 ARM64 architecture is enabled. AX25 Appropriate AX.25 support is enabled. CLK Common clock infrastructure is enabled. CMA Contiguous Memory Area support is enabled. -- cgit v1.2.3 From 9bc755d2cf54510629bfb9ef591a4af10343699e Mon Sep 17 00:00:00 2001 From: Kishon Vijay Abraham I Date: Fri, 26 Apr 2019 18:16:20 +0530 Subject: dt-bindings: PCI: Add PCI EP DT binding documentation for AM654 Add devicetree binding documentation for PCIe in EP mode present in AM654 SoC. Signed-off-by: Kishon Vijay Abraham I Signed-off-by: Lorenzo Pieralisi Reviewed-by: Rob Herring --- .../devicetree/bindings/pci/pci-keystone.txt | 44 ++++++++++++++++++++++ 1 file changed, 44 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/pci/pci-keystone.txt b/Documentation/devicetree/bindings/pci/pci-keystone.txt index 5c60e911b8b1..47202a2938f2 100644 --- a/Documentation/devicetree/bindings/pci/pci-keystone.txt +++ b/Documentation/devicetree/bindings/pci/pci-keystone.txt @@ -69,3 +69,47 @@ Optional properties:- DesignWare DT Properties not applicable for Keystone PCI 1. pcie_bus clock-names not used. Instead, a phandle to phys is used. + +AM654 PCIe Endpoint +=================== + +Required Properties:- + +compatibility: Should be "ti,am654-pcie-ep" for EP on AM654x SoC +reg: Four register ranges as listed in the reg-names property +reg-names: "dbics" for the DesignWare PCIe registers, "app" for the + TI specific application registers, "atu" for the + Address Translation Unit configuration registers and + "addr_space" used to map remote RC address space +num-ib-windows: As specified in + Documentation/devicetree/bindings/pci/designware-pcie.txt +num-ob-windows: As specified in + Documentation/devicetree/bindings/pci/designware-pcie.txt +num-lanes: As specified in + Documentation/devicetree/bindings/pci/designware-pcie.txt +power-domains: As documented by the generic PM domain bindings in + Documentation/devicetree/bindings/power/power_domain.txt. +ti,syscon-pcie-mode: phandle to the device control module required to configure + PCI in either RC mode or EP mode. + +Optional properties:- + +phys: list of PHY specifiers (used by generic PHY framework) +phy-names: must be "pcie-phy0", "pcie-phy1", "pcie-phyN".. based on the + number of lanes as specified in *num-lanes* property. +("phys" and "phy-names" DT bindings are specified in +Documentation/devicetree/bindings/phy/phy-bindings.txt) +interrupts: platform interrupt for error interrupts. + +pcie-ep { + compatible = "ti,am654-pcie-ep"; + reg = <0x5500000 0x1000>, <0x5501000 0x1000>, + <0x10000000 0x8000000>, <0x5506000 0x1000>; + reg-names = "app", "dbics", "addr_space", "atu"; + power-domains = <&k3_pds 120>; + ti,syscon-pcie-mode = <&pcie0_mode>; + num-lanes = <1>; + num-ib-windows = <16>; + num-ob-windows = <16>; + interrupts = ; +}; -- cgit v1.2.3 From 195712bfdddf777603ec12f67023ef6151bb2e1c Mon Sep 17 00:00:00 2001 From: Rob Herring Date: Wed, 1 May 2019 13:12:28 -0500 Subject: dt-bindings: Update schema project location to devicetree.org github group The DT schema tools are moving from my personal GH repo to the devicetree.org group on GH. The new location is here: https://github.com/devicetree-org/dt-schema.git The old repo will be kept as a mirror. Signed-off-by: Rob Herring --- Documentation/devicetree/writing-schema.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/writing-schema.md b/Documentation/devicetree/writing-schema.md index a3652d33a48f..dc032db36262 100644 --- a/Documentation/devicetree/writing-schema.md +++ b/Documentation/devicetree/writing-schema.md @@ -97,7 +97,7 @@ The DT schema project must be installed in order to validate the DT schema binding documents and validate DTS files using the DT schema. The DT schema project can be installed with pip: -`pip3 install git+https://github.com/robherring/yaml-bindings.git@master` +`pip3 install git+https://github.com/devicetree-org/dt-schema.git@master` dtc must also be built with YAML output support enabled. This requires that libyaml and its headers be installed on the host system. -- cgit v1.2.3 From ba6cc85084178e5bce50f6a00411e457c21c47df Mon Sep 17 00:00:00 2001 From: Nick Crews Date: Thu, 18 Apr 2019 10:43:12 -0600 Subject: power: supply: core: Add Standard, Adaptive, and Custom charge types Add "Standard", "Adaptive", and "Custom" modes to the charge_type property, to expand the existing "Trickle" and "Fast" modes. I am adding them in order to support a new Chrome OS device, but these properties should be general enough that they can be used on other devices. The meaning of "Standard" is obvious, but "Adaptive" and "Custom" are more tricky: "Adaptive" means that the charge controller uses some custom algorithm to change the charge type automatically, with no configuration needed. "Custom" means that the charge controller uses the POWER_SUPPLY_PROP_CHARGE_CONTROL_* properties as configuration for some other algorithm. v5 changes: - Split up adding the charge types and adding the POWER_SUPPLY_PROP_CHARGE_CONTROL_START_THRESHOLD and POWER_SUPPLY_PROP_CHARGE_CONTROL_END_THRESHOLD properties into two different commits. v4 changes: - Add documentation for the new properties, and add documentation for the the previously missing charge_control_limit and charge_control_limit_max properties. Signed-off-by: Nick Crews Reviewed-by: Enric Balletbo i Serra Signed-off-by: Sebastian Reichel --- Documentation/ABI/testing/sysfs-class-power | 12 +++++++++--- drivers/power/supply/power_supply_sysfs.c | 2 +- include/linux/power_supply.h | 8 ++++++-- 3 files changed, 16 insertions(+), 6 deletions(-) (limited to 'Documentation') diff --git a/Documentation/ABI/testing/sysfs-class-power b/Documentation/ABI/testing/sysfs-class-power index 5e23e22dce1b..544c4e0ef8b6 100644 --- a/Documentation/ABI/testing/sysfs-class-power +++ b/Documentation/ABI/testing/sysfs-class-power @@ -119,10 +119,16 @@ Date: July 2009 Contact: linux-pm@vger.kernel.org Description: Represents the type of charging currently being applied to the - battery. + battery. "Trickle", "Fast", and "Standard" all mean different + charging speeds. "Adaptive" means that the charger uses some + algorithm to adjust the charge rate dynamically, without + any user configuration required. "Custom" means that the charger + uses the charge_control_* properties as configuration for some + different algorithm. - Access: Read - Valid values: "Unknown", "N/A", "Trickle", "Fast" + Access: Read, Write + Valid values: "Unknown", "N/A", "Trickle", "Fast", "Standard", + "Adaptive", "Custom" What: /sys/class/power_supply//charge_term_current Date: July 2014 diff --git a/drivers/power/supply/power_supply_sysfs.c b/drivers/power/supply/power_supply_sysfs.c index dce24f596160..64dff5cfecc3 100644 --- a/drivers/power/supply/power_supply_sysfs.c +++ b/drivers/power/supply/power_supply_sysfs.c @@ -56,7 +56,7 @@ static const char * const power_supply_status_text[] = { }; static const char * const power_supply_charge_type_text[] = { - "Unknown", "N/A", "Trickle", "Fast" + "Unknown", "N/A", "Trickle", "Fast", "Standard", "Adaptive", "Custom" }; static const char * const power_supply_health_text[] = { diff --git a/include/linux/power_supply.h b/include/linux/power_supply.h index 2f9c201a54d1..e86e05d8134d 100644 --- a/include/linux/power_supply.h +++ b/include/linux/power_supply.h @@ -40,11 +40,15 @@ enum { POWER_SUPPLY_STATUS_FULL, }; +/* What algorithm is the charger using? */ enum { POWER_SUPPLY_CHARGE_TYPE_UNKNOWN = 0, POWER_SUPPLY_CHARGE_TYPE_NONE, - POWER_SUPPLY_CHARGE_TYPE_TRICKLE, - POWER_SUPPLY_CHARGE_TYPE_FAST, + POWER_SUPPLY_CHARGE_TYPE_TRICKLE, /* slow speed */ + POWER_SUPPLY_CHARGE_TYPE_FAST, /* fast speed */ + POWER_SUPPLY_CHARGE_TYPE_STANDARD, /* normal speed */ + POWER_SUPPLY_CHARGE_TYPE_ADAPTIVE, /* dynamically adjusted speed */ + POWER_SUPPLY_CHARGE_TYPE_CUSTOM, /* use CHARGE_CONTROL_* props */ }; enum { -- cgit v1.2.3 From 813cab8f3994250e136819ae48fbd1c95d980466 Mon Sep 17 00:00:00 2001 From: Nick Crews Date: Thu, 18 Apr 2019 10:43:13 -0600 Subject: power: supply: core: Add CHARGE_CONTROL_{START_THRESHOLD,END_THRESHOLD} properties Add POWER_SUPPLY_PROP_CHARGE_CONTROL_START_THRESHOLD and POWER_SUPPLY_PROP_CHARGE_CONTROL_END_THRESHOLD properties, to expand the existing CHARGE_CONTROL_* properties. I am adding them in order to support a new Chrome OS device, but these properties should be general enough that they can be used on other devices. When the charge_type is "Custom", the charge controller uses the POWER_SUPPLY_PROP_CHARGE_CONTROL_* properties as configuration for some other algorithm. For example, in the use case that I am supporting, this means the battery begins charging when the percentage level drops below POWER_SUPPLY_PROP_CHARGE_CONTROL_START_THRESHOLD and charging ceases when the percentage level goes above POWER_SUPPLY_PROP_CHARGE_CONTROL_END_THRESHOLD. v5 changes: - Add the other missing CHARGE_CONTROL_* properties documentation in a separate commit - Split up adding the charge types and adding the POWER_SUPPLY_PROP_CHARGE_CONTROL_START_THRESHOLD and POWER_SUPPLY_PROP_CHARGE_CONTROL_END_THRESHOLD properties into two different commits. v4 changes: - Add documentation for the new properties, and add documentation for the the previously missing charge_control_limit and charge_control_limit_max properties. Signed-off-by: Nick Crews Reviewed-by: Enric Balletbo i Serra Signed-off-by: Sebastian Reichel --- Documentation/ABI/testing/sysfs-class-power | 20 ++++++++++++++++++++ drivers/power/supply/power_supply_sysfs.c | 2 ++ include/linux/power_supply.h | 2 ++ 3 files changed, 24 insertions(+) (limited to 'Documentation') diff --git a/Documentation/ABI/testing/sysfs-class-power b/Documentation/ABI/testing/sysfs-class-power index 544c4e0ef8b6..a5b144f61de8 100644 --- a/Documentation/ABI/testing/sysfs-class-power +++ b/Documentation/ABI/testing/sysfs-class-power @@ -114,6 +114,26 @@ Description: Access: Read Valid values: Represented in microamps +What: /sys/class/power_supply//charge_control_start_threshold +Date: April 2019 +Contact: linux-pm@vger.kernel.org +Description: + Represents a battery percentage level, below which charging will + begin. + + Access: Read, Write + Valid values: 0 - 100 (percent) + +What: /sys/class/power_supply//charge_control_end_threshold +Date: April 2019 +Contact: linux-pm@vger.kernel.org +Description: + Represents a battery percentage level, above which charging will + stop. + + Access: Read, Write + Valid values: 0 - 100 (percent) + What: /sys/class/power_supply//charge_type Date: July 2009 Contact: linux-pm@vger.kernel.org diff --git a/drivers/power/supply/power_supply_sysfs.c b/drivers/power/supply/power_supply_sysfs.c index 64dff5cfecc3..6104a3f03d46 100644 --- a/drivers/power/supply/power_supply_sysfs.c +++ b/drivers/power/supply/power_supply_sysfs.c @@ -274,6 +274,8 @@ static struct device_attribute power_supply_attrs[] = { POWER_SUPPLY_ATTR(constant_charge_voltage_max), POWER_SUPPLY_ATTR(charge_control_limit), POWER_SUPPLY_ATTR(charge_control_limit_max), + POWER_SUPPLY_ATTR(charge_control_start_threshold), + POWER_SUPPLY_ATTR(charge_control_end_threshold), POWER_SUPPLY_ATTR(input_current_limit), POWER_SUPPLY_ATTR(energy_full_design), POWER_SUPPLY_ATTR(energy_empty_design), diff --git a/include/linux/power_supply.h b/include/linux/power_supply.h index e86e05d8134d..d59205170232 100644 --- a/include/linux/power_supply.h +++ b/include/linux/power_supply.h @@ -125,6 +125,8 @@ enum power_supply_property { POWER_SUPPLY_PROP_CONSTANT_CHARGE_VOLTAGE_MAX, POWER_SUPPLY_PROP_CHARGE_CONTROL_LIMIT, POWER_SUPPLY_PROP_CHARGE_CONTROL_LIMIT_MAX, + POWER_SUPPLY_PROP_CHARGE_CONTROL_START_THRESHOLD, /* in percents! */ + POWER_SUPPLY_PROP_CHARGE_CONTROL_END_THRESHOLD, /* in percents! */ POWER_SUPPLY_PROP_INPUT_CURRENT_LIMIT, POWER_SUPPLY_PROP_ENERGY_FULL_DESIGN, POWER_SUPPLY_PROP_ENERGY_EMPTY_DESIGN, -- cgit v1.2.3 From 61e93655fc30cee7c91c85d6c41b96500d228d19 Mon Sep 17 00:00:00 2001 From: Nick Crews Date: Thu, 18 Apr 2019 10:43:14 -0600 Subject: power: supply: core: Add missing documentation for CHARGE_CONTROL_* properties The existing POWER_SUPPLY_PROP_CHARGE_CONTROL_LIMIT and POWER_SUPPLY_PROP_CHARGE_CONTROL_LIMIT_MAX properties don't have documentation. I add that documentation here. v5 changes: - Split this commit out from the previous two commits. Signed-off-by: Nick Crews Reviewed-by: Enric Balletbo i Serra Signed-off-by: Sebastian Reichel --- Documentation/ABI/testing/sysfs-class-power | 19 +++++++++++++++++++ 1 file changed, 19 insertions(+) (limited to 'Documentation') diff --git a/Documentation/ABI/testing/sysfs-class-power b/Documentation/ABI/testing/sysfs-class-power index a5b144f61de8..b77e30b9014e 100644 --- a/Documentation/ABI/testing/sysfs-class-power +++ b/Documentation/ABI/testing/sysfs-class-power @@ -114,6 +114,25 @@ Description: Access: Read Valid values: Represented in microamps +What: /sys/class/power_supply//charge_control_limit +Date: Oct 2012 +Contact: linux-pm@vger.kernel.org +Description: + Maximum allowable charging current. Used for charge rate + throttling for thermal cooling or improving battery health. + + Access: Read, Write + Valid values: Represented in microamps + +What: /sys/class/power_supply//charge_control_limit_max +Date: Oct 2012 +Contact: linux-pm@vger.kernel.org +Description: + Maximum legal value for the charge_control_limit property. + + Access: Read + Valid values: Represented in microamps + What: /sys/class/power_supply//charge_control_start_threshold Date: April 2019 Contact: linux-pm@vger.kernel.org -- cgit v1.2.3 From 9231b4603ef266cdf242d44c3164d6ee69447a1b Mon Sep 17 00:00:00 2001 From: Cao Van Dong Date: Thu, 11 Apr 2019 16:54:21 +0900 Subject: spi: sh-msiof: Document r8a77470 bindings Document SoC specific bindings for R-Car RZ/G1C(r8a77470) SoC. Signed-off-by: Cao Van Dong Signed-off-by: Mark Brown --- Documentation/devicetree/bindings/spi/sh-msiof.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/spi/sh-msiof.txt b/Documentation/devicetree/bindings/spi/sh-msiof.txt index 37cf69586d10..18e14ee257b2 100644 --- a/Documentation/devicetree/bindings/spi/sh-msiof.txt +++ b/Documentation/devicetree/bindings/spi/sh-msiof.txt @@ -4,6 +4,7 @@ Required properties: - compatible : "renesas,msiof-r8a7743" (RZ/G1M) "renesas,msiof-r8a7744" (RZ/G1N) "renesas,msiof-r8a7745" (RZ/G1E) + "renesas,msiof-r8a77470" (RZ/G1C) "renesas,msiof-r8a774a1" (RZ/G2M) "renesas,msiof-r8a774c0" (RZ/G2E) "renesas,msiof-r8a7790" (R-Car H2) -- cgit v1.2.3 From bf6e839657598b77e40eb18225f8660c4778cb19 Mon Sep 17 00:00:00 2001 From: Leilk Liu Date: Wed, 17 Apr 2019 16:47:16 +0800 Subject: dt-bindings: spi: spi-mt65xx: add support for MT8516 Add binding documentation of spi-mt65xx for MT8516 SOC. Signed-off-by: Leilk Liu Reviewed-by: Matthias Brugger Signed-off-by: Mark Brown --- Documentation/devicetree/bindings/spi/spi-mt65xx.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/spi/spi-mt65xx.txt b/Documentation/devicetree/bindings/spi/spi-mt65xx.txt index 69c356767cf8..c0f6c8ecfa2e 100644 --- a/Documentation/devicetree/bindings/spi/spi-mt65xx.txt +++ b/Documentation/devicetree/bindings/spi/spi-mt65xx.txt @@ -10,6 +10,7 @@ Required properties: - mediatek,mt8135-spi: for mt8135 platforms - mediatek,mt8173-spi: for mt8173 platforms - mediatek,mt8183-spi: for mt8183 platforms + - "mediatek,mt8516-spi", "mediatek,mt2712-spi": for mt8516 platforms - #address-cells: should be 1. -- cgit v1.2.3 From 21c7f3e31ec582bf7f0fa4068333acd22b8cb445 Mon Sep 17 00:00:00 2001 From: Cao Van Dong Date: Thu, 11 Apr 2019 16:54:18 +0900 Subject: ASoC: rsnd: Document r8a77470 bindings Document SoC specific bindings for R-Car RZ/G1C(r8a77470) SoC. Signed-off-by: Cao Van Dong Signed-off-by: Mark Brown --- Documentation/devicetree/bindings/sound/renesas,rsnd.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/sound/renesas,rsnd.txt b/Documentation/devicetree/bindings/sound/renesas,rsnd.txt index b34afa66fb00..5c52182f7dcf 100644 --- a/Documentation/devicetree/bindings/sound/renesas,rsnd.txt +++ b/Documentation/devicetree/bindings/sound/renesas,rsnd.txt @@ -266,6 +266,7 @@ Required properties: - "renesas,rcar_sound-r8a7743" (RZ/G1M) - "renesas,rcar_sound-r8a7744" (RZ/G1N) - "renesas,rcar_sound-r8a7745" (RZ/G1E) + - "renesas,rcar_sound-r8a77470" (RZ/G1C) - "renesas,rcar_sound-r8a774a1" (RZ/G2M) - "renesas,rcar_sound-r8a774c0" (RZ/G2E) - "renesas,rcar_sound-r8a7778" (R-Car M1A) -- cgit v1.2.3 From d04195b0a351b6c7bc086bd8590e5f303122a0be Mon Sep 17 00:00:00 2001 From: Viorel Suman Date: Wed, 10 Apr 2019 11:06:37 +0000 Subject: ASoC: fsl_audmix: remove "model" attribute from DT document Remove "model" attribute from fsl_audmix DT document. Signed-off-by: Viorel Suman Acked-by: Nicolin Chen Signed-off-by: Mark Brown --- Documentation/devicetree/bindings/sound/fsl,audmix.txt | 4 ---- 1 file changed, 4 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/sound/fsl,audmix.txt b/Documentation/devicetree/bindings/sound/fsl,audmix.txt index 45f807ec21a5..840b7e0d6a63 100644 --- a/Documentation/devicetree/bindings/sound/fsl,audmix.txt +++ b/Documentation/devicetree/bindings/sound/fsl,audmix.txt @@ -38,9 +38,6 @@ Device driver required properties: to SAI interfaces to be provided, the first SAI in the list being used to route the AUDMIX output. - - model : Must contain machine driver name which will configure - and instantiate the appropriate audio card. - Device driver configuration example: ====================================== audmix: audmix@59840000 { @@ -50,5 +47,4 @@ Device driver configuration example: clock-names = "ipg"; power-domains = <&pd_audmix>; dais = <&sai4>, <&sai5>; - model = "imx-audmix"; }; -- cgit v1.2.3 From fdb0da89f4ba0c74d7d3b9e6f471e96a5766820b Mon Sep 17 00:00:00 2001 From: Al Viro Date: Wed, 10 Apr 2019 14:43:44 -0400 Subject: new inode method: ->free_inode() A lot of ->destroy_inode() instances end with call_rcu() of a callback that does RCU-delayed part of freeing. Introduce a new method for doing just that, with saner signature. Rules: ->destroy_inode ->free_inode f g immediate call of f(), RCU-delayed call of g() f NULL immediate call of f(), no RCU-delayed calls NULL g RCU-delayed call of g() NULL NULL RCU-delayed default freeing IOW, NULL ->free_inode gives the same behaviour as now. Note that NULL, NULL is equivalent to NULL, free_inode_nonrcu; we could mandate the latter form, but that would have very little benefit beyond making rules a bit more symmetric. It would break backwards compatibility, require extra boilerplate and expected semantics for (NULL, NULL) pair would have no use whatsoever... Signed-off-by: Al Viro --- Documentation/filesystems/Locking | 2 ++ Documentation/filesystems/porting | 25 +++++++++++++++++ fs/inode.c | 56 ++++++++++++++++++++++++--------------- include/linux/fs.h | 6 ++++- 4 files changed, 66 insertions(+), 23 deletions(-) (limited to 'Documentation') diff --git a/Documentation/filesystems/Locking b/Documentation/filesystems/Locking index efea228ccd8a..7b20c385cc02 100644 --- a/Documentation/filesystems/Locking +++ b/Documentation/filesystems/Locking @@ -118,6 +118,7 @@ set: exclusive --------------------------- super_operations --------------------------- prototypes: struct inode *(*alloc_inode)(struct super_block *sb); + void (*free_inode)(struct inode *); void (*destroy_inode)(struct inode *); void (*dirty_inode) (struct inode *, int flags); int (*write_inode) (struct inode *, struct writeback_control *wbc); @@ -139,6 +140,7 @@ locking rules: All may block [not true, see below] s_umount alloc_inode: +free_inode: called from RCU callback destroy_inode: dirty_inode: write_inode: diff --git a/Documentation/filesystems/porting b/Documentation/filesystems/porting index cf43bc4dbf31..b8d3ddd8b8db 100644 --- a/Documentation/filesystems/porting +++ b/Documentation/filesystems/porting @@ -638,3 +638,28 @@ in your dentry operations instead. inode to d_splice_alias() will also do the right thing (equivalent of d_add(dentry, NULL); return NULL;), so that kind of special cases also doesn't need a separate treatment. +-- +[strongly recommended] + take the RCU-delayed parts of ->destroy_inode() into a new method - + ->free_inode(). If ->destroy_inode() becomes empty - all the better, + just get rid of it. Synchronous work (e.g. the stuff that can't + be done from an RCU callback, or any WARN_ON() where we want the + stack trace) *might* be movable to ->evict_inode(); however, + that goes only for the things that are not needed to balance something + done by ->alloc_inode(). IOW, if it's cleaning up the stuff that + might have accumulated over the life of in-core inode, ->evict_inode() + might be a fit. + + Rules for inode destruction: + * if ->destroy_inode() is non-NULL, it gets called + * if ->free_inode() is non-NULL, it gets scheduled by call_rcu() + * combination of NULL ->destroy_inode and NULL ->free_inode is + treated as NULL/free_inode_nonrcu, to preserve the compatibility. + + Note that the callback (be it via ->free_inode() or explicit call_rcu() + in ->destroy_inode()) is *NOT* ordered wrt superblock destruction; + as the matter of fact, the superblock and all associated structures + might be already gone. The filesystem driver is guaranteed to be still + there, but that's it. Freeing memory in the callback is fine; doing + more than that is possible, but requires a lot of care and is best + avoided. diff --git a/fs/inode.c b/fs/inode.c index e9d97add2b36..627e1766503a 100644 --- a/fs/inode.c +++ b/fs/inode.c @@ -202,12 +202,28 @@ out: } EXPORT_SYMBOL(inode_init_always); +void free_inode_nonrcu(struct inode *inode) +{ + kmem_cache_free(inode_cachep, inode); +} +EXPORT_SYMBOL(free_inode_nonrcu); + +static void i_callback(struct rcu_head *head) +{ + struct inode *inode = container_of(head, struct inode, i_rcu); + if (inode->free_inode) + inode->free_inode(inode); + else + free_inode_nonrcu(inode); +} + static struct inode *alloc_inode(struct super_block *sb) { + const struct super_operations *ops = sb->s_op; struct inode *inode; - if (sb->s_op->alloc_inode) - inode = sb->s_op->alloc_inode(sb); + if (ops->alloc_inode) + inode = ops->alloc_inode(sb); else inode = kmem_cache_alloc(inode_cachep, GFP_KERNEL); @@ -215,22 +231,19 @@ static struct inode *alloc_inode(struct super_block *sb) return NULL; if (unlikely(inode_init_always(sb, inode))) { - if (inode->i_sb->s_op->destroy_inode) - inode->i_sb->s_op->destroy_inode(inode); - else - kmem_cache_free(inode_cachep, inode); + if (ops->destroy_inode) { + ops->destroy_inode(inode); + if (!ops->free_inode) + return NULL; + } + inode->free_inode = ops->free_inode; + i_callback(&inode->i_rcu); return NULL; } return inode; } -void free_inode_nonrcu(struct inode *inode) -{ - kmem_cache_free(inode_cachep, inode); -} -EXPORT_SYMBOL(free_inode_nonrcu); - void __destroy_inode(struct inode *inode) { BUG_ON(inode_has_buffers(inode)); @@ -253,20 +266,19 @@ void __destroy_inode(struct inode *inode) } EXPORT_SYMBOL(__destroy_inode); -static void i_callback(struct rcu_head *head) -{ - struct inode *inode = container_of(head, struct inode, i_rcu); - kmem_cache_free(inode_cachep, inode); -} - static void destroy_inode(struct inode *inode) { + const struct super_operations *ops = inode->i_sb->s_op; + BUG_ON(!list_empty(&inode->i_lru)); __destroy_inode(inode); - if (inode->i_sb->s_op->destroy_inode) - inode->i_sb->s_op->destroy_inode(inode); - else - call_rcu(&inode->i_rcu, i_callback); + if (ops->destroy_inode) { + ops->destroy_inode(inode); + if (!ops->free_inode) + return; + } + inode->free_inode = ops->free_inode; + call_rcu(&inode->i_rcu, i_callback); } /** diff --git a/include/linux/fs.h b/include/linux/fs.h index dd28e7679089..92732286b748 100644 --- a/include/linux/fs.h +++ b/include/linux/fs.h @@ -694,7 +694,10 @@ struct inode { #ifdef CONFIG_IMA atomic_t i_readcount; /* struct files open RO */ #endif - const struct file_operations *i_fop; /* former ->i_op->default_file_ops */ + union { + const struct file_operations *i_fop; /* former ->i_op->default_file_ops */ + void (*free_inode)(struct inode *); + }; struct file_lock_context *i_flctx; struct address_space i_data; struct list_head i_devices; @@ -1903,6 +1906,7 @@ extern loff_t vfs_dedupe_file_range_one(struct file *src_file, loff_t src_pos, struct super_operations { struct inode *(*alloc_inode)(struct super_block *sb); void (*destroy_inode)(struct inode *); + void (*free_inode)(struct inode *); void (*dirty_inode) (struct inode *, int flags); int (*write_inode) (struct inode *, struct writeback_control *wbc); -- cgit v1.2.3 From 29b861ea7742e571c1940366944eabc24d612e98 Mon Sep 17 00:00:00 2001 From: Joel Stanley Date: Mon, 1 Apr 2019 16:41:56 +1030 Subject: Documentation: powerpc: Expand the DAWR acronym Those not of us not drowning in POWER might not know what this means. Signed-off-by: Joel Stanley Acked-by: Michael Neuling Signed-off-by: Michael Ellerman --- Documentation/powerpc/DAWR-POWER9.txt | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) (limited to 'Documentation') diff --git a/Documentation/powerpc/DAWR-POWER9.txt b/Documentation/powerpc/DAWR-POWER9.txt index bdec03650941..ecdbb076438c 100644 --- a/Documentation/powerpc/DAWR-POWER9.txt +++ b/Documentation/powerpc/DAWR-POWER9.txt @@ -1,10 +1,10 @@ DAWR issues on POWER9 ============================ -On POWER9 the DAWR can cause a checkstop if it points to cache -inhibited (CI) memory. Currently Linux has no way to disinguish CI -memory when configuring the DAWR, so (for now) the DAWR is disabled by -this commit: +On POWER9 the Data Address Watchpoint Register (DAWR) can cause a checkstop +if it points to cache inhibited (CI) memory. Currently Linux has no way to +disinguish CI memory when configuring the DAWR, so (for now) the DAWR is +disabled by this commit: commit 9654153158d3e0684a1bdb76dbababdb7111d5a0 Author: Michael Neuling -- cgit v1.2.3 From 635b90f47d7f8a3777c229a2ac0d5f0fee006795 Mon Sep 17 00:00:00 2001 From: Leo Yan Date: Thu, 2 May 2019 10:54:02 -0600 Subject: dt-bindings: arm: coresight: Add new compatible for static replicator CoreSight uses below bindings for replicator: Dynamic replicator, aka. configurable replicator: "arm,coresight-dynamic-replicator", "arm,primecell"; Static replicator, aka. non-configurable replicator: "arm,coresight-replicator"; The compatible string "arm,coresight-replicator" is not an explicit naming to express the replicator is 'static'. To unify the naming convention, this patch introduces a new compatible string "arm,coresight-static-replicator" for the static replicator; the compatible string "arm,coresight-replicator" is kept for backward compatibility, but tag it as obsolete and suggest to use the new compatible string. As result CoreSight replicator have below bindings: Dynamic replicator: "arm,coresight-dynamic-replicator", "arm,primecell"; Static replicator: "arm,coresight-static-replicator"; "arm,coresight-replicator"; (obsolete) Signed-off-by: Leo Yan Reviewed-by: Suzuki K Poulose Reviewed-by: Rob Herring Signed-off-by: Mathieu Poirier Signed-off-by: Greg Kroah-Hartman --- Documentation/devicetree/bindings/arm/coresight.txt | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/coresight.txt b/Documentation/devicetree/bindings/arm/coresight.txt index f8aff65ab921..d02d160fa8ac 100644 --- a/Documentation/devicetree/bindings/arm/coresight.txt +++ b/Documentation/devicetree/bindings/arm/coresight.txt @@ -69,7 +69,10 @@ its hardware characteristcs. * compatible: Currently supported value is (note the absence of the AMBA markee): - - "arm,coresight-replicator" + - Coresight Non-configurable Replicator: + "arm,coresight-static-replicator"; + "arm,coresight-replicator"; (OBSOLETE. For backward + compatibility and will be removed) * port or ports: see "Graph bindings for Coresight" below. @@ -169,7 +172,7 @@ Example: /* non-configurable replicators don't show up on the * AMBA bus. As such no need to add "arm,primecell". */ - compatible = "arm,coresight-replicator"; + compatible = "arm,coresight-static-replicator"; out-ports { #address-cells = <1>; -- cgit v1.2.3 From d3b18ad63dca3ff3b5a169cbbe629b1d039a4483 Mon Sep 17 00:00:00 2001 From: Leo Yan Date: Thu, 2 May 2019 10:54:04 -0600 Subject: dt-bindings: arm: coresight: Unify funnel DT binding Following the same fashion with replicator DT binding, this patch is to unify the DT binding for funnel to support static and dynamic modes; finally we get the funnel DT binding as below: Before patch: Static funnel, aka. non-configurable funnel: Not supported; Dynamic funnel, aka. configurable funnel: "arm,coresight-funnel", "arm,primecell"; After patch: Static funnel: "arm,coresight-static-funnel"; Dynamic funnel: "arm,coresight-dynamic-funnel", "arm,primecell"; "arm,coresight-funnel", "arm,primecell"; (obsolete) At the end of this patch, it gives an example for static funnel DT binding, and updates the dynamic funnel example. Cc: Mathieu Poirier Cc: Suzuki K Poulose Cc: Wanglai Shi Signed-off-by: Leo Yan Reviewed-by: Suzuki K Poulose Reviewed-by: Rob Herring Signed-off-by: Mathieu Poirier Signed-off-by: Greg Kroah-Hartman --- .../devicetree/bindings/arm/coresight.txt | 53 ++++++++++++++++++++-- 1 file changed, 48 insertions(+), 5 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/coresight.txt b/Documentation/devicetree/bindings/arm/coresight.txt index d02d160fa8ac..8a88ddebc1a2 100644 --- a/Documentation/devicetree/bindings/arm/coresight.txt +++ b/Documentation/devicetree/bindings/arm/coresight.txt @@ -8,7 +8,8 @@ through the intermediate links connecting the source to the currently selected sink. Each CoreSight component device should use these properties to describe its hardware characteristcs. -* Required properties for all components *except* non-configurable replicators: +* Required properties for all components *except* non-configurable replicators + and non-configurable funnels: * compatible: These have to be supplemented with "arm,primecell" as drivers are using the AMBA bus interface. Possible values include: @@ -24,8 +25,10 @@ its hardware characteristcs. discovered at boot time when the device is probed. "arm,coresight-tmc", "arm,primecell"; - - Trace Funnel: - "arm,coresight-funnel", "arm,primecell"; + - Trace Programmable Funnel: + "arm,coresight-dynamic-funnel", "arm,primecell"; + "arm,coresight-funnel", "arm,primecell"; (OBSOLETE. For + backward compatibility and will be removed) - Embedded Trace Macrocell (version 3.x) and Program Flow Trace Macrocell: @@ -65,7 +68,7 @@ its hardware characteristcs. "stm-stimulus-base", each corresponding to the areas defined in "reg". * Required properties for devices that don't show up on the AMBA bus, such as - non-configurable replicators: + non-configurable replicators and non-configurable funnels: * compatible: Currently supported value is (note the absence of the AMBA markee): @@ -74,6 +77,9 @@ its hardware characteristcs. "arm,coresight-replicator"; (OBSOLETE. For backward compatibility and will be removed) + - Coresight Non-configurable Funnel: + "arm,coresight-static-funnel"; + * port or ports: see "Graph bindings for Coresight" below. * Optional properties for ETM/PTMs: @@ -203,8 +209,45 @@ Example: }; }; + funnel { + /* + * non-configurable funnel don't show up on the AMBA + * bus. As such no need to add "arm,primecell". + */ + compatible = "arm,coresight-static-funnel"; + clocks = <&crg_ctrl HI3660_PCLK>; + clock-names = "apb_pclk"; + + out-ports { + port { + combo_funnel_out: endpoint { + remote-endpoint = <&top_funnel_in>; + }; + }; + }; + + in-ports { + #address-cells = <1>; + #size-cells = <0>; + + port@0 { + reg = <0>; + combo_funnel_in0: endpoint { + remote-endpoint = <&cluster0_etf_out>; + }; + }; + + port@1 { + reg = <1>; + combo_funnel_in1: endpoint { + remote-endpoint = <&cluster1_etf_out>; + }; + }; + }; + }; + funnel@20040000 { - compatible = "arm,coresight-funnel", "arm,primecell"; + compatible = "arm,coresight-dynamic-funnel", "arm,primecell"; reg = <0 0x20040000 0 0x1000>; clocks = <&oscclk6a>; -- cgit v1.2.3 From 3342ce35a183fc6c1c8625d702ecf43915bc41ce Mon Sep 17 00:00:00 2001 From: Serge Semin Date: Thu, 25 Apr 2019 00:12:05 +0300 Subject: usb: usb251xb: Add US lanes inversion dts-bindings Since a separate US ports lanes polarity inversion property is going to be available the bindings doc-file should be updated with information about swap-us-lanes bool property, which will be responsible for it. Signed-off-by: Serge Semin Acked-by: Richard Leitner Reviewed-by: Rob Herring Signed-off-by: Greg Kroah-Hartman --- Documentation/devicetree/bindings/usb/usb251xb.txt | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/usb/usb251xb.txt b/Documentation/devicetree/bindings/usb/usb251xb.txt index 17915f64b8ee..bc7945e9dbfe 100644 --- a/Documentation/devicetree/bindings/usb/usb251xb.txt +++ b/Documentation/devicetree/bindings/usb/usb251xb.txt @@ -64,8 +64,10 @@ Optional properties : - power-on-time-ms : Specifies the time it takes from the time the host initiates the power-on sequence to a port until the port has adequate power. The value is given in ms in a 0 - 510 range (default is 100ms). - - swap-dx-lanes : Specifies the ports which will swap the differential-pair - (D+/D-), default is not-swapped. + - swap-dx-lanes : Specifies the downstream ports which will swap the + differential-pair (D+/D-), default is not-swapped. + - swap-us-lanes : Selects the upstream port differential-pair (D+/D-) + swapping (boolean, default is not-swapped) Examples: usb2512b@2c { -- cgit v1.2.3 From 67d06e6efa41c4135cfc4c4c5c9b55d5e3a9b6f7 Mon Sep 17 00:00:00 2001 From: Mesih Kilinc Date: Mon, 11 Feb 2019 12:21:07 +0300 Subject: dt-bindings: timer: Add Allwinner suniv timer Add compatible string for Allwinner suniv timer which is similar to sun4i timer. Signed-off-by: Mesih Kilinc Acked-by: Maxime Ripard Reviewed-by: Rob Herring Signed-off-by: Daniel Lezcano --- Documentation/devicetree/bindings/timer/allwinner,sun4i-timer.txt | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/timer/allwinner,sun4i-timer.txt b/Documentation/devicetree/bindings/timer/allwinner,sun4i-timer.txt index 5c2e23574ca0..3da9d515c03a 100644 --- a/Documentation/devicetree/bindings/timer/allwinner,sun4i-timer.txt +++ b/Documentation/devicetree/bindings/timer/allwinner,sun4i-timer.txt @@ -2,7 +2,9 @@ Allwinner A1X SoCs Timer Controller Required properties: -- compatible : should be "allwinner,sun4i-a10-timer" +- compatible : should be one of the following: + "allwinner,sun4i-a10-timer" + "allwinner,suniv-f1c100s-timer" - reg : Specifies base physical address and size of the registers. - interrupts : The interrupt of the first timer - clocks: phandle to the source clock (usually a 24 MHz fixed clock) -- cgit v1.2.3 From c50495aa4cfcaace5f61174ab3069d5047d14f17 Mon Sep 17 00:00:00 2001 From: Christian Lamparter Date: Tue, 16 May 2017 22:11:20 +0200 Subject: dt-bindings: pinctrl: fix bias-pull,up typo This patch fixes a shared typo in several qcom pinctrl dt-bindings. Signed-off-by: Christian Lamparter Acked-by: Bjorn Andersson Signed-off-by: Rob Herring --- Documentation/devicetree/bindings/pinctrl/qcom,apq8064-pinctrl.txt | 2 +- Documentation/devicetree/bindings/pinctrl/qcom,ipq4019-pinctrl.txt | 2 +- Documentation/devicetree/bindings/pinctrl/qcom,ipq8064-pinctrl.txt | 2 +- Documentation/devicetree/bindings/pinctrl/qcom,msm8660-pinctrl.txt | 2 +- Documentation/devicetree/bindings/pinctrl/qcom,msm8974-pinctrl.txt | 2 +- 5 files changed, 5 insertions(+), 5 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/pinctrl/qcom,apq8064-pinctrl.txt b/Documentation/devicetree/bindings/pinctrl/qcom,apq8064-pinctrl.txt index c2dbb3e8d840..4e90ddd77784 100644 --- a/Documentation/devicetree/bindings/pinctrl/qcom,apq8064-pinctrl.txt +++ b/Documentation/devicetree/bindings/pinctrl/qcom,apq8064-pinctrl.txt @@ -42,7 +42,7 @@ information about e.g. the mux function. The following generic properties as defined in pinctrl-bindings.txt are valid to specify in a pin configuration subnode: - pins, function, bias-disable, bias-pull-down, bias-pull,up, drive-strength, + pins, function, bias-disable, bias-pull-down, bias-pull-up, drive-strength, output-low, output-high. Non-empty subnodes must specify the 'pins' property. diff --git a/Documentation/devicetree/bindings/pinctrl/qcom,ipq4019-pinctrl.txt b/Documentation/devicetree/bindings/pinctrl/qcom,ipq4019-pinctrl.txt index 991be0cd0948..84be0f2c6f3b 100644 --- a/Documentation/devicetree/bindings/pinctrl/qcom,ipq4019-pinctrl.txt +++ b/Documentation/devicetree/bindings/pinctrl/qcom,ipq4019-pinctrl.txt @@ -44,7 +44,7 @@ information about e.g. the mux function. The following generic properties as defined in pinctrl-bindings.txt are valid to specify in a pin configuration subnode: - pins, function, bias-disable, bias-pull-down, bias-pull,up, drive-strength. + pins, function, bias-disable, bias-pull-down, bias-pull-up, drive-strength. Non-empty subnodes must specify the 'pins' property. Note that not all properties are valid for all pins. diff --git a/Documentation/devicetree/bindings/pinctrl/qcom,ipq8064-pinctrl.txt b/Documentation/devicetree/bindings/pinctrl/qcom,ipq8064-pinctrl.txt index 7ed56a1b70fc..a7aaaa7db83b 100644 --- a/Documentation/devicetree/bindings/pinctrl/qcom,ipq8064-pinctrl.txt +++ b/Documentation/devicetree/bindings/pinctrl/qcom,ipq8064-pinctrl.txt @@ -42,7 +42,7 @@ information about e.g. the mux function. The following generic properties as defined in pinctrl-bindings.txt are valid to specify in a pin configuration subnode: - pins, function, bias-disable, bias-pull-down, bias-pull,up, drive-strength, + pins, function, bias-disable, bias-pull-down, bias-pull-up, drive-strength, output-low, output-high. Non-empty subnodes must specify the 'pins' property. diff --git a/Documentation/devicetree/bindings/pinctrl/qcom,msm8660-pinctrl.txt b/Documentation/devicetree/bindings/pinctrl/qcom,msm8660-pinctrl.txt index cdc4787e59d2..f095209848c8 100644 --- a/Documentation/devicetree/bindings/pinctrl/qcom,msm8660-pinctrl.txt +++ b/Documentation/devicetree/bindings/pinctrl/qcom,msm8660-pinctrl.txt @@ -42,7 +42,7 @@ information about e.g. the mux function. The following generic properties as defined in pinctrl-bindings.txt are valid to specify in a pin configuration subnode: - pins, function, bias-disable, bias-pull-down, bias-pull,up, drive-strength, + pins, function, bias-disable, bias-pull-down, bias-pull-up, drive-strength, output-low, output-high. Non-empty subnodes must specify the 'pins' property. diff --git a/Documentation/devicetree/bindings/pinctrl/qcom,msm8974-pinctrl.txt b/Documentation/devicetree/bindings/pinctrl/qcom,msm8974-pinctrl.txt index c22e6c425d0b..004056506679 100644 --- a/Documentation/devicetree/bindings/pinctrl/qcom,msm8974-pinctrl.txt +++ b/Documentation/devicetree/bindings/pinctrl/qcom,msm8974-pinctrl.txt @@ -41,7 +41,7 @@ information about e.g. the mux function. The following generic properties as defined in pinctrl-bindings.txt are valid to specify in a pin configuration subnode: - pins, function, bias-disable, bias-pull-down, bias-pull,up, drive-strength. + pins, function, bias-disable, bias-pull-down, bias-pull-up, drive-strength. Non-empty subnodes must specify the 'pins' property. Note that not all properties are valid for all pins. -- cgit v1.2.3 From 7a76b97325c2cc6c6599a2b3b15d32aebf2f48ee Mon Sep 17 00:00:00 2001 From: Neil Armstrong Date: Tue, 23 Apr 2019 10:51:24 +0200 Subject: dt-bindings: usb: dwc2: Add Amlogic G12A DWC2 Compatible Adds the specific compatible string for the DWC2 IP found in the Amlogic G12A SoC Family. Signed-off-by: Neil Armstrong Reviewed-by: Martin Blumenstingl Reviewed-by: Rob Herring Signed-off-by: Felipe Balbi --- Documentation/devicetree/bindings/usb/dwc2.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/usb/dwc2.txt b/Documentation/devicetree/bindings/usb/dwc2.txt index 6dc3c4a34483..e150b7b227c9 100644 --- a/Documentation/devicetree/bindings/usb/dwc2.txt +++ b/Documentation/devicetree/bindings/usb/dwc2.txt @@ -14,6 +14,7 @@ Required properties: - "amlogic,meson8-usb": The DWC2 USB controller instance in Amlogic Meson8 SoCs; - "amlogic,meson8b-usb": The DWC2 USB controller instance in Amlogic Meson8b SoCs; - "amlogic,meson-gxbb-usb": The DWC2 USB controller instance in Amlogic S905 SoCs; + - "amlogic,meson-g12a-usb": The DWC2 USB controller instance in Amlogic G12A SoCs; - "amcc,dwc-otg": The DWC2 USB controller instance in AMCC Canyonlands 460EX SoCs; - snps,dwc2: A generic DWC2 USB controller with default parameters. - "st,stm32f4x9-fsotg": The DWC2 USB FS/HS controller instance in STM32F4x9 SoCs -- cgit v1.2.3 From e8c77fa091808c7e27ad15c7256743b6c2406b02 Mon Sep 17 00:00:00 2001 From: Neil Armstrong Date: Tue, 23 Apr 2019 10:51:25 +0200 Subject: dt-bindings: usb: dwc3: Add Amlogic G12A DWC3 Glue Bindings Adds the bindings for the Amlogic G12A USB Glue HW. The Amlogic G12A SoC Family embeds 2 USB Controllers : - a DWC3 IP configured as Host for USB2 and USB3 - a DWC2 IP configured as Peripheral USB2 Only A glue connects these both controllers to 2 USB2 PHYs, and optionnally to an USB3+PCIE Combo PHY shared with the PCIE controller. The Glue configures the UTMI 8bit interfaces for the USB2 PHYs, including routing of the OTG PHY between the DWC3 and DWC2 controllers, and setups the on-chip OTG mode selection for this PHY. The PHYs phandles are passed to the Glue node since the Glue controls the interface with the PHY, not the DWC3 controller. Signed-off-by: Neil Armstrong Reviewed-by: Martin Blumenstingl Reviewed-by: Rob Herring Signed-off-by: Felipe Balbi --- .../devicetree/bindings/usb/amlogic,dwc3.txt | 88 ++++++++++++++++++++++ 1 file changed, 88 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/usb/amlogic,dwc3.txt b/Documentation/devicetree/bindings/usb/amlogic,dwc3.txt index 9a8b631904fd..b9f04e617eb7 100644 --- a/Documentation/devicetree/bindings/usb/amlogic,dwc3.txt +++ b/Documentation/devicetree/bindings/usb/amlogic,dwc3.txt @@ -40,3 +40,91 @@ Example device nodes: phy-names = "usb2-phy", "usb3-phy"; }; }; + +Amlogic Meson G12A DWC3 USB SoC Controller Glue + +The Amlogic G12A embeds a DWC3 USB IP Core configured for USB2 and USB3 +in host-only mode, and a DWC2 IP Core configured for USB2 peripheral mode +only. + +A glue connects the DWC3 core to USB2 PHYs and optionnaly to an USB3 PHY. + +One of the USB2 PHY can be re-routed in peripheral mode to a DWC2 USB IP. + +The DWC3 Glue controls the PHY routing and power, an interrupt line is +connected to the Glue to serve as OTG ID change detection. + +Required properties: +- compatible: Should be "amlogic,meson-g12a-usb-ctrl" +- clocks: a handle for the "USB" clock +- resets: a handle for the shared "USB" reset line +- reg: The base address and length of the registers +- interrupts: the interrupt specifier for the OTG detection +- phys: handle to used PHYs on the system + - a <0> phandle can be used if a PHY is not used +- phy-names: names of the used PHYs on the system : + - "usb2-phy0" for USB2 PHY0 if USBHOST_A port is used + - "usb2-phy1" for USB2 PHY1 if USBOTG_B port is used + - "usb3-phy0" for USB3 PHY if USB3_0 is used +- dr_mode: should be "host", "peripheral", or "otg" depending on + the usage and configuration of the OTG Capable port. + - "host" and "peripheral" means a fixed Host or Device only connection + - "otg" means the port can be used as both Host or Device and + be switched automatically using the OTG ID pin. + +Optional properties: +- vbus-supply: should be a phandle to the regulator controlling the VBUS + power supply when used in OTG switchable mode + +Required child nodes: + +A child node must exist to represent the core DWC3 IP block. The name of +the node is not important. The content of the node is defined in dwc3.txt. + +A child node must exist to represent the core DWC2 IP block. The name of +the node is not important. The content of the node is defined in dwc2.txt. + +PHY documentation is provided in the following places: +- Documentation/devicetree/bindings/phy/meson-g12a-usb2-phy.txt +- Documentation/devicetree/bindings/phy/meson-g12a-usb3-pcie-phy.txt + +Example device nodes: + usb: usb@ffe09000 { + compatible = "amlogic,meson-g12a-usb-ctrl"; + reg = <0x0 0xffe09000 0x0 0xa0>; + interrupts = ; + #address-cells = <2>; + #size-cells = <2>; + ranges; + + clocks = <&clkc CLKID_USB>; + resets = <&reset RESET_USB>; + + dr_mode = "otg"; + + phys = <&usb2_phy0>, <&usb2_phy1>, + <&usb3_pcie_phy PHY_TYPE_USB3>; + phy-names = "usb2-phy0", "usb2-phy1", "usb3-phy0"; + + dwc2: usb@ff400000 { + compatible = "amlogic,meson-g12a-usb", "snps,dwc2"; + reg = <0x0 0xff400000 0x0 0x40000>; + interrupts = ; + clocks = <&clkc CLKID_USB1_DDR_BRIDGE>; + clock-names = "ddr"; + phys = <&usb2_phy1>; + dr_mode = "peripheral"; + g-rx-fifo-size = <192>; + g-np-tx-fifo-size = <128>; + g-tx-fifo-size = <128 128 16 16 16>; + }; + + dwc3: usb@ff500000 { + compatible = "snps,dwc3"; + reg = <0x0 0xff500000 0x0 0x100000>; + interrupts = ; + dr_mode = "host"; + snps,dis_u2_susphy_quirk; + snps,quirk-frame-length-adjustment; + }; + }; -- cgit v1.2.3 From 86847dca8b8bd6145f41986399b4b882a6b55623 Mon Sep 17 00:00:00 2001 From: Martin Blumenstingl Date: Wed, 6 Mar 2019 22:24:31 +0100 Subject: dt-bindings: usb: dwc2: document the vbus-supply property Various boards have an external VBUS supply regulator. This regulator depends on the current mode of the controller which is defined as: - dr_mode set to either "host" or "peripheral" (fixed value) - dr_mode set to "otg", based on the OTG status the dwc2 controller internally switches between "host" and "peripheral" mode (selection happens at runtime) Based on the current mode the regulator has to be enabled or disabled: - host: provide power to the connected USB device, thus the regulator has to be enabled - peripheral: the host device to which the controller is connected provides power, thus the regulator has to be disabled Add the dt-bindings documentation for this property so .dts authors know that this property exists and how it behaves. Fixes: 531ef5ebea9639 ("usb: dwc2: add support for host mode external vbus supply") Acked-by: Rob Herring Signed-off-by: Martin Blumenstingl Signed-off-by: Felipe Balbi --- Documentation/devicetree/bindings/usb/dwc2.txt | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/usb/dwc2.txt b/Documentation/devicetree/bindings/usb/dwc2.txt index e150b7b227c9..0294572deea3 100644 --- a/Documentation/devicetree/bindings/usb/dwc2.txt +++ b/Documentation/devicetree/bindings/usb/dwc2.txt @@ -32,6 +32,10 @@ Refer to clk/clock-bindings.txt for generic clock consumer properties Optional properties: - phys: phy provider specifier - phy-names: shall be "usb2-phy" +- vbus-supply: reference to the VBUS regulator. Depending on the current mode + this is enabled (in "host" mode") or disabled (in "peripheral" mode). The + regulator is updated if the controller is configured in "otg" mode and the + status changes between "host" and "peripheral". Refer to phy/phy-bindings.txt for generic phy consumer properties - dr_mode: shall be one of "host", "peripheral" and "otg" Refer to usb/generic.txt -- cgit v1.2.3 From cc389eaabd7082a14e46aaa5a02f87c9eef37d7f Mon Sep 17 00:00:00 2001 From: Douglas Anderson Date: Tue, 16 Apr 2019 14:53:48 -0700 Subject: dt-bindings: usb: dwc2: Document quirk to reset PHY upon wakeup On Rockchip rk3288 there's a hardware quirk where we need to assert the reset signal to the PHY when we get a remote wakeup on one of the two ports. Document this quirk in the bindings. Signed-off-by: Douglas Anderson Reviewed-by: Matthias Kaehlcke Signed-off-by: Felipe Balbi --- Documentation/devicetree/bindings/usb/dwc2.txt | 2 ++ 1 file changed, 2 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/usb/dwc2.txt b/Documentation/devicetree/bindings/usb/dwc2.txt index 0294572deea3..49eac0dc86b0 100644 --- a/Documentation/devicetree/bindings/usb/dwc2.txt +++ b/Documentation/devicetree/bindings/usb/dwc2.txt @@ -42,6 +42,8 @@ Refer to phy/phy-bindings.txt for generic phy consumer properties - g-rx-fifo-size: size of rx fifo size in gadget mode. - g-np-tx-fifo-size: size of non-periodic tx fifo size in gadget mode. - g-tx-fifo-size: size of periodic tx fifo per endpoint (except ep0) in gadget mode. +- snps,reset-phy-on-wake: If present indicates that we need to reset the PHY when + we detect a wakeup. This is due to a hardware errata. Deprecated properties: - g-use-dma: gadget DMA mode is automatically detected -- cgit v1.2.3 From 07b734fbdea2662ab79a7501e2d758dcc658a9e2 Mon Sep 17 00:00:00 2001 From: Manivannan Sadhasivam Date: Wed, 24 Apr 2019 17:32:20 +0530 Subject: dt-bindings: pinctrl: Add BM1880 pinctrl binding Add pinctrl binding for Bitmain BM1880 SoC. The SoC is not capable of handling pinconf, thereby supporting only pinmux and this limitation is documented. Signed-off-by: Manivannan Sadhasivam Signed-off-by: Linus Walleij --- .../bindings/pinctrl/bitmain,bm1880-pinctrl.txt | 98 ++++++++++++++++++++++ 1 file changed, 98 insertions(+) create mode 100644 Documentation/devicetree/bindings/pinctrl/bitmain,bm1880-pinctrl.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/pinctrl/bitmain,bm1880-pinctrl.txt b/Documentation/devicetree/bindings/pinctrl/bitmain,bm1880-pinctrl.txt new file mode 100644 index 000000000000..ed34bb1ee81c --- /dev/null +++ b/Documentation/devicetree/bindings/pinctrl/bitmain,bm1880-pinctrl.txt @@ -0,0 +1,98 @@ +Bitmain BM1880 Pin Controller + +This binding describes the pin controller found in the BM1880 SoC. + +Required Properties: + +- compatible: Should be "bitmain,bm1880-pinctrl" +- reg: Offset and length of pinctrl space in SCTRL. + +Please refer to pinctrl-bindings.txt in this directory for details of the +common pinctrl bindings used by client devices, including the meaning of the +phrase "pin configuration node". + +The pin configuration nodes act as a container for an arbitrary number of +subnodes. Each of these subnodes represents some desired configuration for a +pin, a group, or a list of pins or groups. This configuration for BM1880 SoC +includes only pinmux as there is no pinconf support available in SoC. + +Each configuration node can consist of multiple nodes describing the pinmux +options. The name of each subnode is not important; all subnodes should be +enumerated and processed purely based on their content. + +The following generic properties as defined in pinctrl-bindings.txt are valid +to specify in a pinmux subnode: + +Required Properties: + +- pins: An array of strings, each string containing the name of a pin. + Valid values for pins are: + + MIO0 - MIO111 + +- groups: An array of strings, each string containing the name of a pin + group. Valid values for groups are: + + nand_grp, spi_grp, emmc_grp, sdio_grp, eth0_grp, pwm0_grp, + pwm1_grp, pwm2_grp, pwm3_grp, pwm4_grp, pwm5_grp, pwm6_grp, + pwm7_grp, pwm8_grp, pwm9_grp, pwm10_grp, pwm11_grp, pwm12_grp, + pwm13_grp, pwm14_grp, pwm15_grp, pwm16_grp, pwm17_grp, + pwm18_grp, pwm19_grp, pwm20_grp, pwm21_grp, pwm22_grp, + pwm23_grp, pwm24_grp, pwm25_grp, pwm26_grp, pwm27_grp, + pwm28_grp, pwm29_grp, pwm30_grp, pwm31_grp, pwm32_grp, + pwm33_grp, pwm34_grp, pwm35_grp, pwm36_grp, i2c0_grp, + i2c1_grp, i2c2_grp, i2c3_grp, i2c4_grp, uart0_grp, uart1_grp, + uart2_grp, uart3_grp, uart4_grp, uart5_grp, uart6_grp, + uart7_grp, uart8_grp, uart9_grp, uart10_grp, uart11_grp, + uart12_grp, uart13_grp, uart14_grp, uart15_grp, gpio0_grp, + gpio1_grp, gpio2_grp, gpio3_grp, gpio4_grp, gpio5_grp, + gpio6_grp, gpio7_grp, gpio8_grp, gpio9_grp, gpio10_grp, + gpio11_grp, gpio12_grp, gpio13_grp, gpio14_grp, gpio15_grp, + gpio16_grp, gpio17_grp, gpio18_grp, gpio19_grp, gpio20_grp, + gpio21_grp, gpio22_grp, gpio23_grp, gpio24_grp, gpio25_grp, + gpio26_grp, gpio27_grp, gpio28_grp, gpio29_grp, gpio30_grp, + gpio31_grp, gpio32_grp, gpio33_grp, gpio34_grp, gpio35_grp, + gpio36_grp, gpio37_grp, gpio38_grp, gpio39_grp, gpio40_grp, + gpio41_grp, gpio42_grp, gpio43_grp, gpio44_grp, gpio45_grp, + gpio46_grp, gpio47_grp, gpio48_grp, gpio49_grp, gpio50_grp, + gpio51_grp, gpio52_grp, gpio53_grp, gpio54_grp, gpio55_grp, + gpio56_grp, gpio57_grp, gpio58_grp, gpio59_grp, gpio60_grp, + gpio61_grp, gpio62_grp, gpio63_grp, gpio64_grp, gpio65_grp, + gpio66_grp, gpio67_grp, eth1_grp, i2s0_grp, i2s0_mclkin_grp, + i2s1_grp, i2s1_mclkin_grp, spi0_grp + +- function: An array of strings, each string containing the name of the + pinmux functions. The following are the list of pinmux + functions available: + + nand, spi, emmc, sdio, eth0, pwm0, pwm1, pwm2, pwm3, pwm4, + pwm5, pwm6, pwm7, pwm8, pwm9, pwm10, pwm11, pwm12, pwm13, + pwm14, pwm15, pwm16, pwm17, pwm18, pwm19, pwm20, pwm21, pwm22, + pwm23, pwm24, pwm25, pwm26, pwm27, pwm28, pwm29, pwm30, pwm31, + pwm32, pwm33, pwm34, pwm35, pwm36, i2c0, i2c1, i2c2, i2c3, + i2c4, uart0, uart1, uart2, uart3, uart4, uart5, uart6, uart7, + uart8, uart9, uart10, uart11, uart12, uart13, uart14, uart15, + gpio0, gpio1, gpio2, gpio3, gpio4, gpio5, gpio6, gpio7, gpio8, + gpio9, gpio10, gpio11, gpio12, gpio13, gpio14, gpio15, gpio16, + gpio17, gpio18, gpio19, gpio20, gpio21, gpio22, gpio23, + gpio24, gpio25, gpio26, gpio27, gpio28, gpio29, gpio30, + gpio31, gpio32, gpio33, gpio34, gpio35, gpio36, gpio37, + gpio38, gpio39, gpio40, gpio41, gpio42, gpio43, gpio44, + gpio45, gpio46, gpio47, gpio48, gpio49, gpio50, gpio51, + gpio52, gpio53, gpio54, gpio55, gpio56, gpio57, gpio58, + gpio59, gpio60, gpio61, gpio62, gpio63, gpio64, gpio65, + gpio66, gpio67, eth1, i2s0, i2s0_mclkin, i2s1, i2s1_mclkin, + spi0 + +Example: + pinctrl: pinctrl@50 { + compatible = "bitmain,bm1880-pinctrl"; + reg = <0x50 0x4B0>; + + pinctrl_uart0_default: uart0-default { + pinmux { + groups = "uart0_grp"; + function = "uart0"; + }; + }; + }; -- cgit v1.2.3 From 6132c37ca543d45cc911043fb17b2d86593fb612 Mon Sep 17 00:00:00 2001 From: Christoph Hellwig Date: Tue, 30 Apr 2019 06:51:28 -0400 Subject: docs: Don't reference the ZLib license in license-rules.rst We never had a file called LICENSES/other/ZLib in the tree, so don't reference it. Instead mention the GPL v1 as an (bad) example. Signed-off-by: Christoph Hellwig Reviewed-by: Greg Kroah-Hartman Signed-off-by: Jonathan Corbet --- Documentation/process/license-rules.rst | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/process/license-rules.rst b/Documentation/process/license-rules.rst index 6b09033a8e9e..ade495fe6811 100644 --- a/Documentation/process/license-rules.rst +++ b/Documentation/process/license-rules.rst @@ -255,9 +255,9 @@ kernel, can be broken down into: Contains the Internet Systems Consortium license text and the required metatags:: - LICENSES/other/ZLib + LICENSES/other/GPL-1.0 - Contains the ZLIB license text and the required metatags. + Contains the GPL version 1 license text and the required metatags. Metatags: -- cgit v1.2.3 From 8ea8814fcdcb32cc667d090455649893a362c658 Mon Sep 17 00:00:00 2001 From: Christoph Hellwig Date: Tue, 30 Apr 2019 06:51:29 -0400 Subject: LICENSES: Clearly mark dual license only licenses Just like the CDDL the Apache license and the MPL must only be used as a choice in additional to an GPL2 compatible license. Copy over the boilerplate from the CDDL file to the other two after fixing it up to make it clear the licenses need to be GPL2 compatible, not just the more generic GPL compatible. For example the Apache 2 license is GPL3 compatible, but that doesn't matter for the kernel. Also move these licenses to a separate directory and document the rules in license-rules.rst. Signed-off-by: Christoph Hellwig Reviewed-by: Greg Kroah-Hartman Signed-off-by: Jonathan Corbet --- Documentation/process/license-rules.rst | 51 +++- LICENSES/dual/Apache-2.0 | 187 +++++++++++++ LICENSES/dual/CDDL-1.0 | 368 ++++++++++++++++++++++++ LICENSES/dual/MPL-1.1 | 482 ++++++++++++++++++++++++++++++++ LICENSES/other/Apache-2.0 | 183 ------------ LICENSES/other/CDDL-1.0 | 368 ------------------------ LICENSES/other/MPL-1.1 | 478 ------------------------------- 7 files changed, 1087 insertions(+), 1030 deletions(-) create mode 100644 LICENSES/dual/Apache-2.0 create mode 100644 LICENSES/dual/CDDL-1.0 create mode 100644 LICENSES/dual/MPL-1.1 delete mode 100644 LICENSES/other/Apache-2.0 delete mode 100644 LICENSES/other/CDDL-1.0 delete mode 100644 LICENSES/other/MPL-1.1 (limited to 'Documentation') diff --git a/Documentation/process/license-rules.rst b/Documentation/process/license-rules.rst index ade495fe6811..507b695fa9da 100644 --- a/Documentation/process/license-rules.rst +++ b/Documentation/process/license-rules.rst @@ -281,7 +281,56 @@ kernel, can be broken down into: | -3. _`Exceptions`: +3. Dual Licensing Only + + These licenses should only be used to dual license code with another + license in addition to a preferred license. These licenses are available + from the directory:: + + LICENSES/dual/ + + in the kernel source tree. + + The files in this directory contain the full license text and + `Metatags`_. The file names are identical to the SPDX license + identifier which shall be used for the license in source files. + + Examples:: + + LICENSES/dual/MPL-1.1 + + Contains the Mozilla Public License version 1.1 license text and the + required metatags:: + + LICENSES/dual/Apache-2.0 + + Contains the Apache License version 2.0 license text and the required + metatags. + + Metatags: + + The metatag requirements for 'other' licenses are identical to the + requirements of the `Preferred licenses`_. + + File format example:: + + Valid-License-Identifier: MPL-1.1 + SPDX-URL: https://spdx.org/licenses/MPL-1.1.html + Usage-Guide: + Do NOT use. The MPL-1.1 is not GPL2 compatible. It may only be used for + dual-licensed files where the other license is GPL2 compatible. + If you end up using this it MUST be used together with a GPL2 compatible + license using "OR". + To use the Mozilla Public License version 1.1 put the following SPDX + tag/value pair into a comment according to the placement guidelines in + the licensing rules documentation: + SPDX-License-Identifier: MPL-1.1 + License-Text: + Full license text + +| + +4. _`Exceptions`: Some licenses can be amended with exceptions which grant certain rights which the original license does not. These exceptions are available diff --git a/LICENSES/dual/Apache-2.0 b/LICENSES/dual/Apache-2.0 new file mode 100644 index 000000000000..6e89ddeab187 --- /dev/null +++ b/LICENSES/dual/Apache-2.0 @@ -0,0 +1,187 @@ +Valid-License-Identifier: Apache-2.0 +SPDX-URL: https://spdx.org/licenses/Apache-2.0.html +Usage-Guide: + Do NOT use. The Apache-2.0 is not GPL2 compatible. It may only be used + for dual-licensed files where the other license is GPL2 compatible. + If you end up using this it MUST be used together with a GPL2 compatible + license using "OR". + To use the Apache License version 2.0 put the following SPDX tag/value + pair into a comment according to the placement guidelines in the + licensing rules documentation: + SPDX-License-Identifier: Apache-2.0 +License-Text: + +Apache License + +Version 2.0, January 2004 + +http://www.apache.org/licenses/ + +TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION + +1. Definitions. + +"License" shall mean the terms and conditions for use, reproduction, and +distribution as defined by Sections 1 through 9 of this document. + +"Licensor" shall mean the copyright owner or entity authorized by the +copyright owner that is granting the License. + +"Legal Entity" shall mean the union of the acting entity and all other +entities that control, are controlled by, or are under common control with +that entity. For the purposes of this definition, "control" means (i) the +power, direct or indirect, to cause the direction or management of such +entity, whether by contract or otherwise, or (ii) ownership of fifty +percent (50%) or more of the outstanding shares, or (iii) beneficial +ownership of such entity. + +"You" (or "Your") shall mean an individual or Legal Entity exercising +permissions granted by this License. + +"Source" form shall mean the preferred form for making modifications, +including but not limited to software source code, documentation source, +and configuration files. + +"Object" form shall mean any form resulting from mechanical transformation +or translation of a Source form, including but not limited to compiled +object code, generated documentation, and conversions to other media types. + +"Work" shall mean the work of authorship, whether in Source or Object form, +made available under the License, as indicated by a copyright notice that +is included in or attached to the work (an example is provided in the +Appendix below). + +"Derivative Works" shall mean any work, whether in Source or Object form, +that is based on (or derived from) the Work and for which the editorial +revisions, annotations, elaborations, or other modifications represent, as +a whole, an original work of authorship. For the purposes of this License, +Derivative Works shall not include works that remain separable from, or +merely link (or bind by name) to the interfaces of, the Work and Derivative +Works thereof. + +"Contribution" shall mean any work of authorship, including the original +version of the Work and any modifications or additions to that Work or +Derivative Works thereof, that is intentionally submitted to Licensor for +inclusion in the Work by the copyright owner or by an individual or Legal +Entity authorized to submit on behalf of the copyright owner. For the +purposes of this definition, "submitted" means any form of electronic, +verbal, or written communication sent to the Licensor or its +representatives, including but not limited to communication on electronic +mailing lists, source code control systems, and issue tracking systems that +are managed by, or on behalf of, the Licensor for the purpose of discussing +and improving the Work, but excluding communication that is conspicuously +marked or otherwise designated in writing by the copyright owner as "Not a +Contribution." + +"Contributor" shall mean Licensor and any individual or Legal Entity on +behalf of whom a Contribution has been received by Licensor and +subsequently incorporated within the Work. + +2. Grant of Copyright License. Subject to the terms and conditions of this + License, each Contributor hereby grants to You a perpetual, worldwide, + non-exclusive, no-charge, royalty-free, irrevocable copyright license to + reproduce, prepare Derivative Works of, publicly display, publicly + perform, sublicense, and distribute the Work and such Derivative Works + in Source or Object form. + +3. Grant of Patent License. Subject to the terms and conditions of this + License, each Contributor hereby grants to You a perpetual, worldwide, + non-exclusive, no-charge, royalty-free, irrevocable (except as stated in + this section) patent license to make, have made, use, offer to sell, + sell, import, and otherwise transfer the Work, where such license + applies only to those patent claims licensable by such Contributor that + are necessarily infringed by their Contribution(s) alone or by + combination of their Contribution(s) with the Work to which such + Contribution(s) was submitted. If You institute patent litigation + against any entity (including a cross-claim or counterclaim in a + lawsuit) alleging that the Work or a Contribution incorporated within + the Work constitutes direct or contributory patent infringement, then + any patent licenses granted to You under this License for that Work + shall terminate as of the date such litigation is filed. + +4. Redistribution. You may reproduce and distribute copies of the Work or + Derivative Works thereof in any medium, with or without modifications, + and in Source or Object form, provided that You meet the following + conditions: + + a. You must give any other recipients of the Work or Derivative Works a + copy of this License; and + + b. You must cause any modified files to carry prominent notices stating + that You changed the files; and + + c. You must retain, in the Source form of any Derivative Works that You + distribute, all copyright, patent, trademark, and attribution notices + from the Source form of the Work, excluding those notices that do not + pertain to any part of the Derivative Works; and + + d. If the Work includes a "NOTICE" text file as part of its + distribution, then any Derivative Works that You distribute must + include a readable copy of the attribution notices contained within + such NOTICE file, excluding those notices that do not pertain to any + part of the Derivative Works, in at least one of the following + places: within a NOTICE text file distributed as part of the + Derivative Works; within the Source form or documentation, if + provided along with the Derivative Works; or, within a display + generated by the Derivative Works, if and wherever such third-party + notices normally appear. The contents of the NOTICE file are for + informational purposes only and do not modify the License. You may + add Your own attribution notices within Derivative Works that You + distribute, alongside or as an addendum to the NOTICE text from the + Work, provided that such additional attribution notices cannot be + construed as modifying the License. + + You may add Your own copyright statement to Your modifications and may + provide additional or different license terms and conditions for use, + reproduction, or distribution of Your modifications, or for any such + Derivative Works as a whole, provided Your use, reproduction, and + distribution of the Work otherwise complies with the conditions stated + in this License. + +5. Submission of Contributions. Unless You explicitly state otherwise, any + Contribution intentionally submitted for inclusion in the Work by You to + the Licensor shall be under the terms and conditions of this License, + without any additional terms or conditions. Notwithstanding the above, + nothing herein shall supersede or modify the terms of any separate + license agreement you may have executed with Licensor regarding such + Contributions. + +6. Trademarks. This License does not grant permission to use the trade + names, trademarks, service marks, or product names of the Licensor, + except as required for reasonable and customary use in describing the + origin of the Work and reproducing the content of the NOTICE file. + +7. Disclaimer of Warranty. Unless required by applicable law or agreed to + in writing, Licensor provides the Work (and each Contributor provides + its Contributions) on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS + OF ANY KIND, either express or implied, including, without limitation, + any warranties or conditions of TITLE, NON-INFRINGEMENT, + MERCHANTABILITY, or FITNESS FOR A PARTICULAR PURPOSE. You are solely + responsible for determining the appropriateness of using or + redistributing the Work and assume any risks associated with Your + exercise of permissions under this License. + +8. Limitation of Liability. In no event and under no legal theory, whether + in tort (including negligence), contract, or otherwise, unless required + by applicable law (such as deliberate and grossly negligent acts) or + agreed to in writing, shall any Contributor be liable to You for + damages, including any direct, indirect, special, incidental, or + consequential damages of any character arising as a result of this + License or out of the use or inability to use the Work (including but + not limited to damages for loss of goodwill, work stoppage, computer + failure or malfunction, or any and all other commercial damages or + losses), even if such Contributor has been advised of the possibility of + such damages. + +9. Accepting Warranty or Additional Liability. While redistributing the + Work or Derivative Works thereof, You may choose to offer, and charge a + fee for, acceptance of support, warranty, indemnity, or other liability + obligations and/or rights consistent with this License. However, in + accepting such obligations, You may act only on Your own behalf and on + Your sole responsibility, not on behalf of any other Contributor, and + only if You agree to indemnify, defend, and hold each Contributor + harmless for any liability incurred by, or claims asserted against, such + Contributor by reason of your accepting any such warranty or additional + liability. + +END OF TERMS AND CONDITIONS diff --git a/LICENSES/dual/CDDL-1.0 b/LICENSES/dual/CDDL-1.0 new file mode 100644 index 000000000000..b0ca1016db79 --- /dev/null +++ b/LICENSES/dual/CDDL-1.0 @@ -0,0 +1,368 @@ +Valid-License-Identifier: CDDL-1.0 +SPDX-URL: https://spdx.org/licenses/CDDL-1.0.html +Usage-Guide: + Do NOT use. The CDDL-1.0 is not GPL2 compatible. It may only be used for + dual-licensed files where the other license is GPL2 compatible. + If you end up using this it MUST be used together with a GPL2 compatible + license using "OR". + To use the Common Development and Distribution License 1.0 put the + following SPDX tag/value pair into a comment according to the placement + guidelines in the licensing rules documentation: + SPDX-License-Identifier: ($GPL-COMPATIBLE-ID OR CDDL-1.0) + +License-Text: + +COMMON DEVELOPMENT AND DISTRIBUTION LICENSE (CDDL) +Version 1.0 + + 1. Definitions. + + 1.1. "Contributor" means each individual or entity that creates or + contributes to the creation of Modifications. + + 1.2. "Contributor Version" means the combination of the Original + Software, prior Modifications used by a Contributor (if any), + and the Modifications made by that particular Contributor. + + 1.3. "Covered Software" means (a) the Original Software, or (b) + Modifications, or (c) the combination of files containing + Original Software with files containing Modifications, in each + case including portions thereof. + + 1.4. "Executable" means the Covered Software in any form other than + Source Code. + + 1.5. "Initial Developer" means the individual or entity that first + makes Original Software available under this License. + + 1.6. "Larger Work" means a work which combines Covered Software or + portions thereof with code not governed by the terms of this + License. + + 1.7. "License" means this document. + + 1.8. "Licensable" means having the right to grant, to the maximum + extent possible, whether at the time of the initial grant or + subsequently acquired, any and all of the rights conveyed herein. + + 1.9. "Modifications" means the Source Code and Executable form of + any of the following: + + A. Any file that results from an addition to, deletion from or + modification of the contents of a file containing Original + Software or previous Modifications; + + B. Any new file that contains any part of the Original Software + or previous Modification; or + + C. Any new file that is contributed or otherwise made available + under the terms of this License. + + 1.10. "Original Software" means the Source Code and Executable form + of computer software code that is originally released under + this License. + + 1.11. "Patent Claims" means any patent claim(s), now owned or + hereafter acquired, including without limitation, method, + process, and apparatus claims, in any patent Licensable by + grantor. + + 1.12. "Source Code" means (a) the common form of computer software + code in which modifications are made and (b) associated + documentation included in or with such code. + + 1.13. "You" (or "Your") means an individual or a legal entity + exercising rights under, and complying with all of the terms + of, this License. For legal entities, "You" includes any + entity which controls, is controlled by, or is under common + control with You. For purposes of this definition, "control" + means (a) the power, direct or indirect, to cause the + direction or management of such entity, whether by contract + or otherwise, or (b) ownership of more than fifty percent + (50%) of the outstanding shares or beneficial ownership of + such entity. + + 2. License Grants. + 2.1. The Initial Developer Grant. + + Conditioned upon Your compliance with Section 3.1 below and subject + to third party intellectual property claims, the Initial Developer + hereby grants You a world-wide, royalty-free, non-exclusive + license: + + (a) under intellectual property rights (other than patent or + trademark) Licensable by Initial Developer, to use, + reproduce, modify, display, perform, sublicense and + distribute the Original Software (or portions thereof), + with or without Modifications, and/or as part of a Larger + Work; and + + (b) under Patent Claims infringed by the making, using or + selling of Original Software, to make, have made, use, + practice, sell, and offer for sale, and/or otherwise + dispose of the Original Software (or portions thereof). + + (c) The licenses granted in Sections 2.1(a) and (b) are + effective on the date Initial Developer first distributes + or otherwise makes the Original Software available to a + third party under the terms of this License. + + (d) Notwithstanding Section 2.1(b) above, no patent license is + granted: (1) for code that You delete from the Original + Software, or (2) for infringements caused by: (i) the + modification of the Original Software, or (ii) the + combination of the Original Software with other software or + devices. + + 2.2. Contributor Grant. + + Conditioned upon Your compliance with Section 3.1 below and subject + to third party intellectual property claims, each Contributor + hereby grants You a world-wide, royalty-free, non-exclusive + license: + + (a) under intellectual property rights (other than patent or + trademark) Licensable by Contributor to use, reproduce, + modify, display, perform, sublicense and distribute the + Modifications created by such Contributor (or portions + thereof), either on an unmodified basis, with other + Modifications, as Covered Software and/or as part of a + Larger Work; and + + (b) under Patent Claims infringed by the making, using, or + selling of Modifications made by that Contributor either + alone and/or in combination with its Contributor Version + (or portions of such combination), to make, use, sell, + offer for sale, have made, and/or otherwise dispose of: (1) + Modifications made by that Contributor (or portions + thereof); and (2) the combination of Modifications made by + that Contributor with its Contributor Version (or portions + of such combination). + + (c) The licenses granted in Sections 2.2(a) and 2.2(b) are + effective on the date Contributor first distributes or + otherwise makes the Modifications available to a third + party. + + (d) Notwithstanding Section 2.2(b) above, no patent license is + granted: (1) for any code that Contributor has deleted from + the Contributor Version; (2) for infringements caused by: + (i) third party modifications of Contributor Version, or + (ii) the combination of Modifications made by that + Contributor with other software (except as part of the + Contributor Version) or other devices; or (3) under Patent + Claims infringed by Covered Software in the absence of + Modifications made by that Contributor. + + 3. Distribution Obligations. + 3.1. Availability of Source Code. + + Any Covered Software that You distribute or otherwise make + available in Executable form must also be made available in Source + Code form and that Source Code form must be distributed only under + the terms of this License. You must include a copy of this License + with every copy of the Source Code form of the Covered Software You + distribute or otherwise make available. You must inform recipients + of any such Covered Software in Executable form as to how they can + obtain such Covered Software in Source Code form in a reasonable + manner on or through a medium customarily used for software + exchange. + + 3.2. Modifications. + + The Modifications that You create or to which You contribute are + governed by the terms of this License. You represent that You + believe Your Modifications are Your original creation(s) and/or You + have sufficient rights to grant the rights conveyed by this + License. + + 3.3. Required Notices. + + You must include a notice in each of Your Modifications that + identifies You as the Contributor of the Modification. You may not + remove or alter any copyright, patent or trademark notices + contained within the Covered Software, or any notices of licensing + or any descriptive text giving attribution to any Contributor or + the Initial Developer. + + 3.4. Application of Additional Terms. + + You may not offer or impose any terms on any Covered Software in + Source Code form that alters or restricts the applicable version of + this License or the recipients' rights hereunder. You may choose to + offer, and to charge a fee for, warranty, support, indemnity or + liability obligations to one or more recipients of Covered + Software. However, you may do so only on Your own behalf, and not + on behalf of the Initial Developer or any Contributor. You must + make it absolutely clear that any such warranty, support, indemnity + or liability obligation is offered by You alone, and You hereby + agree to indemnify the Initial Developer and every Contributor for + any liability incurred by the Initial Developer or such Contributor + as a result of warranty, support, indemnity or liability terms You + offer. + + 3.5. Distribution of Executable Versions. + + You may distribute the Executable form of the Covered Software + under the terms of this License or under the terms of a license of + Your choice, which may contain terms different from this License, + provided that You are in compliance with the terms of this License + and that the license for the Executable form does not attempt to + limit or alter the recipient's rights in the Source Code form from + the rights set forth in this License. If You distribute the Covered + Software in Executable form under a different license, You must + make it absolutely clear that any terms which differ from this + License are offered by You alone, not by the Initial Developer or + Contributor. You hereby agree to indemnify the Initial Developer + and every Contributor for any liability incurred by the Initial + Developer or such Contributor as a result of any such terms You + offer. + + 3.6. Larger Works. + + You may create a Larger Work by combining Covered Software with + other code not governed by the terms of this License and distribute + the Larger Work as a single product. In such a case, You must make + sure the requirements of this License are fulfilled for the Covered + Software. + + 4. Versions of the License. + 4.1. New Versions. + + Sun Microsystems, Inc. is the initial license steward and may + publish revised and/or new versions of this License from time to + time. Each version will be given a distinguishing version + number. Except as provided in Section 4.3, no one other than the + license steward has the right to modify this License. + + 4.2. Effect of New Versions. + + You may always continue to use, distribute or otherwise make the + Covered Software available under the terms of the version of the + License under which You originally received the Covered + Software. If the Initial Developer includes a notice in the + Original Software prohibiting it from being distributed or + otherwise made available under any subsequent version of the + License, You must distribute and make the Covered Software + available under the terms of the version of the License under which + You originally received the Covered Software. Otherwise, You may + also choose to use, distribute or otherwise make the Covered + Software available under the terms of any subsequent version of the + License published by the license steward. + + 4.3. Modified Versions. + + When You are an Initial Developer and You want to create a new + license for Your Original Software, You may create and use a + modified version of this License if You: (a) rename the license and + remove any references to the name of the license steward (except to + note that the license differs from this License); and (b) otherwise + make it clear that the license contains terms which differ from + this License. + + 5. DISCLAIMER OF WARRANTY. + + COVERED SOFTWARE IS PROVIDED UNDER THIS LICENSE ON AN "AS IS" BASIS, + WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, + WITHOUT LIMITATION, WARRANTIES THAT THE COVERED SOFTWARE IS FREE OF + DEFECTS, MERCHANTABLE, FIT FOR A PARTICULAR PURPOSE OR + NON-INFRINGING. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF + THE COVERED SOFTWARE IS WITH YOU. SHOULD ANY COVERED SOFTWARE PROVE + DEFECTIVE IN ANY RESPECT, YOU (NOT THE INITIAL DEVELOPER OR ANY OTHER + CONTRIBUTOR) ASSUME THE COST OF ANY NECESSARY SERVICING, REPAIR OR + CORRECTION. THIS DISCLAIMER OF WARRANTY CONSTITUTES AN ESSENTIAL PART + OF THIS LICENSE. NO USE OF ANY COVERED SOFTWARE IS AUTHORIZED HEREUNDER + EXCEPT UNDER THIS DISCLAIMER. + + 6. TERMINATION. + + 6.1. This License and the rights granted hereunder will terminate + automatically if You fail to comply with terms herein and fail to + cure such breach within 30 days of becoming aware of the + breach. Provisions which, by their nature, must remain in effect + beyond the termination of this License shall survive. + + 6.2. If You assert a patent infringement claim (excluding + declaratory judgment actions) against Initial Developer or a + Contributor (the Initial Developer or Contributor against whom You + assert such claim is referred to as "Participant") alleging that + the Participant Software (meaning the Contributor Version where the + Participant is a Contributor or the Original Software where the + Participant is the Initial Developer) directly or indirectly + infringes any patent, then any and all rights granted directly or + indirectly to You by such Participant, the Initial Developer (if + the Initial Developer is not the Participant) and all Contributors + under Sections 2.1 and/or 2.2 of this License shall, upon 60 days + notice from Participant terminate prospectively and automatically + at the expiration of such 60 day notice period, unless if within + such 60 day period You withdraw Your claim with respect to the + Participant Software against such Participant either unilaterally + or pursuant to a written agreement with Participant. + + 6.3. In the event of termination under Sections 6.1 or 6.2 above, + all end user licenses that have been validly granted by You or any + distributor hereunder prior to termination (excluding licenses + granted to You by any distributor) shall survive termination. + + 7. LIMITATION OF LIABILITY. + + UNDER NO CIRCUMSTANCES AND UNDER NO LEGAL THEORY, WHETHER TORT + (INCLUDING NEGLIGENCE), CONTRACT, OR OTHERWISE, SHALL YOU, THE INITIAL + DEVELOPER, ANY OTHER CONTRIBUTOR, OR ANY DISTRIBUTOR OF COVERED + SOFTWARE, OR ANY SUPPLIER OF ANY OF SUCH PARTIES, BE LIABLE TO ANY + PERSON FOR ANY INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES + OF ANY CHARACTER INCLUDING, WITHOUT LIMITATION, DAMAGES FOR LOST + PROFITS, LOSS OF GOODWILL, WORK STOPPAGE, COMPUTER FAILURE OR + MALFUNCTION, OR ANY AND ALL OTHER COMMERCIAL DAMAGES OR LOSSES, EVEN IF + SUCH PARTY SHALL HAVE BEEN INFORMED OF THE POSSIBILITY OF SUCH + DAMAGES. THIS LIMITATION OF LIABILITY SHALL NOT APPLY TO LIABILITY FOR + DEATH OR PERSONAL INJURY RESULTING FROM SUCH PARTY'S NEGLIGENCE TO THE + EXTENT APPLICABLE LAW PROHIBITS SUCH LIMITATION. SOME JURISDICTIONS DO + NOT ALLOW THE EXCLUSION OR LIMITATION OF INCIDENTAL OR CONSEQUENTIAL + DAMAGES, SO THIS EXCLUSION AND LIMITATION MAY NOT APPLY TO YOU. + + 8. U.S. GOVERNMENT END USERS. + + The Covered Software is a "commercial item," as that term is defined in + 48 C.F.R. 2.101 (Oct. 1995), consisting of "commercial computer + software" (as that term is defined at 48 C.F.R. $ 252.227-7014(a)(1)) + and "commercial computer software documentation" as such terms are used + in 48 C.F.R. 12.212 (Sept. 1995). Consistent with 48 C.F.R. 12.212 and + 48 C.F.R. 227.7202-1 through 227.7202-4 (June 1995), all + U.S. Government End Users acquire Covered Software with only those + rights set forth herein. This U.S. Government Rights clause is in lieu + of, and supersedes, any other FAR, DFAR, or other clause or provision + that addresses Government rights in computer software under this + License. + + 9. MISCELLANEOUS. + + This License represents the complete agreement concerning subject + matter hereof. If any provision of this License is held to be + unenforceable, such provision shall be reformed only to the extent + necessary to make it enforceable. This License shall be governed by the + law of the jurisdiction specified in a notice contained within the + Original Software (except to the extent applicable law, if any, + provides otherwise), excluding such jurisdiction's conflict-of-law + provisions. Any litigation relating to this License shall be subject to + the jurisdiction of the courts located in the jurisdiction and venue + specified in a notice contained within the Original Software, with the + losing party responsible for costs, including, without limitation, + court costs and reasonable attorneys' fees and expenses. The + application of the United Nations Convention on Contracts for the + International Sale of Goods is expressly excluded. Any law or + regulation which provides that the language of a contract shall be + construed against the drafter shall not apply to this License. You + agree that You alone are responsible for compliance with the United + States export administration regulations (and the export control laws + and regulation of any other countries) when You use, distribute or + otherwise make available any Covered Software. + + 10. RESPONSIBILITY FOR CLAIMS. + + As between Initial Developer and the Contributors, each party is + responsible for claims and damages arising, directly or indirectly, out + of its utilization of rights under this License and You agree to work + with Initial Developer and Contributors to distribute such + responsibility on an equitable basis. Nothing herein is intended or + shall be deemed to constitute any admission of liability. diff --git a/LICENSES/dual/MPL-1.1 b/LICENSES/dual/MPL-1.1 new file mode 100644 index 000000000000..61706859e1b2 --- /dev/null +++ b/LICENSES/dual/MPL-1.1 @@ -0,0 +1,482 @@ +Valid-License-Identifier: MPL-1.1 +SPDX-URL: https://spdx.org/licenses/MPL-1.1.html +Usage-Guide: + Do NOT use. The MPL-1.1 is not GPL2 compatible. It may only be used for + dual-licensed files where the other license is GPL2 compatible. + If you end up using this it MUST be used together with a GPL2 compatible + license using "OR". + To use the Mozilla Public License version 1.1 put the following SPDX + tag/value pair into a comment according to the placement guidelines in + the licensing rules documentation: + SPDX-License-Identifier: MPL-1.1 +License-Text: + + MOZILLA PUBLIC LICENSE + Version 1.1 + + --------------- + +1. Definitions. + + 1.0.1. "Commercial Use" means distribution or otherwise making the + Covered Code available to a third party. + + 1.1. "Contributor" means each entity that creates or contributes to + the creation of Modifications. + + 1.2. "Contributor Version" means the combination of the Original + Code, prior Modifications used by a Contributor, and the Modifications + made by that particular Contributor. + + 1.3. "Covered Code" means the Original Code or Modifications or the + combination of the Original Code and Modifications, in each case + including portions thereof. + + 1.4. "Electronic Distribution Mechanism" means a mechanism generally + accepted in the software development community for the electronic + transfer of data. + + 1.5. "Executable" means Covered Code in any form other than Source + Code. + + 1.6. "Initial Developer" means the individual or entity identified + as the Initial Developer in the Source Code notice required by Exhibit + A. + + 1.7. "Larger Work" means a work which combines Covered Code or + portions thereof with code not governed by the terms of this License. + + 1.8. "License" means this document. + + 1.8.1. "Licensable" means having the right to grant, to the maximum + extent possible, whether at the time of the initial grant or + subsequently acquired, any and all of the rights conveyed herein. + + 1.9. "Modifications" means any addition to or deletion from the + substance or structure of either the Original Code or any previous + Modifications. When Covered Code is released as a series of files, a + Modification is: + A. Any addition to or deletion from the contents of a file + containing Original Code or previous Modifications. + + B. Any new file that contains any part of the Original Code or + previous Modifications. + + 1.10. "Original Code" means Source Code of computer software code + which is described in the Source Code notice required by Exhibit A as + Original Code, and which, at the time of its release under this + License is not already Covered Code governed by this License. + + 1.10.1. "Patent Claims" means any patent claim(s), now owned or + hereafter acquired, including without limitation, method, process, + and apparatus claims, in any patent Licensable by grantor. + + 1.11. "Source Code" means the preferred form of the Covered Code for + making modifications to it, including all modules it contains, plus + any associated interface definition files, scripts used to control + compilation and installation of an Executable, or source code + differential comparisons against either the Original Code or another + well known, available Covered Code of the Contributor's choice. The + Source Code can be in a compressed or archival form, provided the + appropriate decompression or de-archiving software is widely available + for no charge. + + 1.12. "You" (or "Your") means an individual or a legal entity + exercising rights under, and complying with all of the terms of, this + License or a future version of this License issued under Section 6.1. + For legal entities, "You" includes any entity which controls, is + controlled by, or is under common control with You. For purposes of + this definition, "control" means (a) the power, direct or indirect, + to cause the direction or management of such entity, whether by + contract or otherwise, or (b) ownership of more than fifty percent + (50%) of the outstanding shares or beneficial ownership of such + entity. + +2. Source Code License. + + 2.1. The Initial Developer Grant. + The Initial Developer hereby grants You a world-wide, royalty-free, + non-exclusive license, subject to third party intellectual property + claims: + (a) under intellectual property rights (other than patent or + trademark) Licensable by Initial Developer to use, reproduce, + modify, display, perform, sublicense and distribute the Original + Code (or portions thereof) with or without Modifications, and/or + as part of a Larger Work; and + + (b) under Patents Claims infringed by the making, using or + selling of Original Code, to make, have made, use, practice, + sell, and offer for sale, and/or otherwise dispose of the + Original Code (or portions thereof). + + (c) the licenses granted in this Section 2.1(a) and (b) are + effective on the date Initial Developer first distributes + Original Code under the terms of this License. + + (d) Notwithstanding Section 2.1(b) above, no patent license is + granted: 1) for code that You delete from the Original Code; 2) + separate from the Original Code; or 3) for infringements caused + by: i) the modification of the Original Code or ii) the + combination of the Original Code with other software or devices. + + 2.2. Contributor Grant. + Subject to third party intellectual property claims, each Contributor + hereby grants You a world-wide, royalty-free, non-exclusive license + + (a) under intellectual property rights (other than patent or + trademark) Licensable by Contributor, to use, reproduce, modify, + display, perform, sublicense and distribute the Modifications + created by such Contributor (or portions thereof) either on an + unmodified basis, with other Modifications, as Covered Code + and/or as part of a Larger Work; and + + (b) under Patent Claims infringed by the making, using, or + selling of Modifications made by that Contributor either alone + and/or in combination with its Contributor Version (or portions + of such combination), to make, use, sell, offer for sale, have + made, and/or otherwise dispose of: 1) Modifications made by that + Contributor (or portions thereof); and 2) the combination of + Modifications made by that Contributor with its Contributor + Version (or portions of such combination). + + (c) the licenses granted in Sections 2.2(a) and 2.2(b) are + effective on the date Contributor first makes Commercial Use of + the Covered Code. + + (d) Notwithstanding Section 2.2(b) above, no patent license is + granted: 1) for any code that Contributor has deleted from the + Contributor Version; 2) separate from the Contributor Version; + 3) for infringements caused by: i) third party modifications of + Contributor Version or ii) the combination of Modifications made + by that Contributor with other software (except as part of the + Contributor Version) or other devices; or 4) under Patent Claims + infringed by Covered Code in the absence of Modifications made by + that Contributor. + +3. Distribution Obligations. + + 3.1. Application of License. + The Modifications which You create or to which You contribute are + governed by the terms of this License, including without limitation + Section 2.2. The Source Code version of Covered Code may be + distributed only under the terms of this License or a future version + of this License released under Section 6.1, and You must include a + copy of this License with every copy of the Source Code You + distribute. You may not offer or impose any terms on any Source Code + version that alters or restricts the applicable version of this + License or the recipients' rights hereunder. However, You may include + an additional document offering the additional rights described in + Section 3.5. + + 3.2. Availability of Source Code. + Any Modification which You create or to which You contribute must be + made available in Source Code form under the terms of this License + either on the same media as an Executable version or via an accepted + Electronic Distribution Mechanism to anyone to whom you made an + Executable version available; and if made available via Electronic + Distribution Mechanism, must remain available for at least twelve (12) + months after the date it initially became available, or at least six + (6) months after a subsequent version of that particular Modification + has been made available to such recipients. You are responsible for + ensuring that the Source Code version remains available even if the + Electronic Distribution Mechanism is maintained by a third party. + + 3.3. Description of Modifications. + You must cause all Covered Code to which You contribute to contain a + file documenting the changes You made to create that Covered Code and + the date of any change. You must include a prominent statement that + the Modification is derived, directly or indirectly, from Original + Code provided by the Initial Developer and including the name of the + Initial Developer in (a) the Source Code, and (b) in any notice in an + Executable version or related documentation in which You describe the + origin or ownership of the Covered Code. + + 3.4. Intellectual Property Matters + (a) Third Party Claims. + If Contributor has knowledge that a license under a third party's + intellectual property rights is required to exercise the rights + granted by such Contributor under Sections 2.1 or 2.2, + Contributor must include a text file with the Source Code + distribution titled "LEGAL" which describes the claim and the + party making the claim in sufficient detail that a recipient will + know whom to contact. If Contributor obtains such knowledge after + the Modification is made available as described in Section 3.2, + Contributor shall promptly modify the LEGAL file in all copies + Contributor makes available thereafter and shall take other steps + (such as notifying appropriate mailing lists or newsgroups) + reasonably calculated to inform those who received the Covered + Code that new knowledge has been obtained. + + (b) Contributor APIs. + If Contributor's Modifications include an application programming + interface and Contributor has knowledge of patent licenses which + are reasonably necessary to implement that API, Contributor must + also include this information in the LEGAL file. + + (c) Representations. + Contributor represents that, except as disclosed pursuant to + Section 3.4(a) above, Contributor believes that Contributor's + Modifications are Contributor's original creation(s) and/or + Contributor has sufficient rights to grant the rights conveyed by + this License. + + 3.5. Required Notices. + You must duplicate the notice in Exhibit A in each file of the Source + Code. If it is not possible to put such notice in a particular Source + Code file due to its structure, then You must include such notice in a + location (such as a relevant directory) where a user would be likely + to look for such a notice. If You created one or more Modification(s) + You may add your name as a Contributor to the notice described in + Exhibit A. You must also duplicate this License in any documentation + for the Source Code where You describe recipients' rights or ownership + rights relating to Covered Code. You may choose to offer, and to + charge a fee for, warranty, support, indemnity or liability + obligations to one or more recipients of Covered Code. However, You + may do so only on Your own behalf, and not on behalf of the Initial + Developer or any Contributor. You must make it absolutely clear than + any such warranty, support, indemnity or liability obligation is + offered by You alone, and You hereby agree to indemnify the Initial + Developer and every Contributor for any liability incurred by the + Initial Developer or such Contributor as a result of warranty, + support, indemnity or liability terms You offer. + + 3.6. Distribution of Executable Versions. + You may distribute Covered Code in Executable form only if the + requirements of Section 3.1-3.5 have been met for that Covered Code, + and if You include a notice stating that the Source Code version of + the Covered Code is available under the terms of this License, + including a description of how and where You have fulfilled the + obligations of Section 3.2. The notice must be conspicuously included + in any notice in an Executable version, related documentation or + collateral in which You describe recipients' rights relating to the + Covered Code. You may distribute the Executable version of Covered + Code or ownership rights under a license of Your choice, which may + contain terms different from this License, provided that You are in + compliance with the terms of this License and that the license for the + Executable version does not attempt to limit or alter the recipient's + rights in the Source Code version from the rights set forth in this + License. If You distribute the Executable version under a different + license You must make it absolutely clear that any terms which differ + from this License are offered by You alone, not by the Initial + Developer or any Contributor. You hereby agree to indemnify the + Initial Developer and every Contributor for any liability incurred by + the Initial Developer or such Contributor as a result of any such + terms You offer. + + 3.7. Larger Works. + You may create a Larger Work by combining Covered Code with other code + not governed by the terms of this License and distribute the Larger + Work as a single product. In such a case, You must make sure the + requirements of this License are fulfilled for the Covered Code. + +4. Inability to Comply Due to Statute or Regulation. + + If it is impossible for You to comply with any of the terms of this + License with respect to some or all of the Covered Code due to + statute, judicial order, or regulation then You must: (a) comply with + the terms of this License to the maximum extent possible; and (b) + describe the limitations and the code they affect. Such description + must be included in the LEGAL file described in Section 3.4 and must + be included with all distributions of the Source Code. Except to the + extent prohibited by statute or regulation, such description must be + sufficiently detailed for a recipient of ordinary skill to be able to + understand it. + +5. Application of this License. + + This License applies to code to which the Initial Developer has + attached the notice in Exhibit A and to related Covered Code. + +6. Versions of the License. + + 6.1. New Versions. + Netscape Communications Corporation ("Netscape") may publish revised + and/or new versions of the License from time to time. Each version + will be given a distinguishing version number. + + 6.2. Effect of New Versions. + Once Covered Code has been published under a particular version of the + License, You may always continue to use it under the terms of that + version. You may also choose to use such Covered Code under the terms + of any subsequent version of the License published by Netscape. No one + other than Netscape has the right to modify the terms applicable to + Covered Code created under this License. + + 6.3. Derivative Works. + If You create or use a modified version of this License (which you may + only do in order to apply it to code which is not already Covered Code + governed by this License), You must (a) rename Your license so that + the phrases "Mozilla", "MOZILLAPL", "MOZPL", "Netscape", + "MPL", "NPL" or any confusingly similar phrase do not appear in your + license (except to note that your license differs from this License) + and (b) otherwise make it clear that Your version of the license + contains terms which differ from the Mozilla Public License and + Netscape Public License. (Filling in the name of the Initial + Developer, Original Code or Contributor in the notice described in + Exhibit A shall not of themselves be deemed to be modifications of + this License.) + +7. DISCLAIMER OF WARRANTY. + + COVERED CODE IS PROVIDED UNDER THIS LICENSE ON AN "AS IS" BASIS, + WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, + WITHOUT LIMITATION, WARRANTIES THAT THE COVERED CODE IS FREE OF + DEFECTS, MERCHANTABLE, FIT FOR A PARTICULAR PURPOSE OR NON-INFRINGING. + THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE COVERED CODE + IS WITH YOU. SHOULD ANY COVERED CODE PROVE DEFECTIVE IN ANY RESPECT, + YOU (NOT THE INITIAL DEVELOPER OR ANY OTHER CONTRIBUTOR) ASSUME THE + COST OF ANY NECESSARY SERVICING, REPAIR OR CORRECTION. THIS DISCLAIMER + OF WARRANTY CONSTITUTES AN ESSENTIAL PART OF THIS LICENSE. NO USE OF + ANY COVERED CODE IS AUTHORIZED HEREUNDER EXCEPT UNDER THIS DISCLAIMER. + +8. TERMINATION. + + 8.1. This License and the rights granted hereunder will terminate + automatically if You fail to comply with terms herein and fail to cure + such breach within 30 days of becoming aware of the breach. All + sublicenses to the Covered Code which are properly granted shall + survive any termination of this License. Provisions which, by their + nature, must remain in effect beyond the termination of this License + shall survive. + + 8.2. If You initiate litigation by asserting a patent infringement + claim (excluding declatory judgment actions) against Initial Developer + or a Contributor (the Initial Developer or Contributor against whom + You file such action is referred to as "Participant") alleging that: + + (a) such Participant's Contributor Version directly or indirectly + infringes any patent, then any and all rights granted by such + Participant to You under Sections 2.1 and/or 2.2 of this License + shall, upon 60 days notice from Participant terminate prospectively, + unless if within 60 days after receipt of notice You either: (i) + agree in writing to pay Participant a mutually agreeable reasonable + royalty for Your past and future use of Modifications made by such + Participant, or (ii) withdraw Your litigation claim with respect to + the Contributor Version against such Participant. If within 60 days + of notice, a reasonable royalty and payment arrangement are not + mutually agreed upon in writing by the parties or the litigation claim + is not withdrawn, the rights granted by Participant to You under + Sections 2.1 and/or 2.2 automatically terminate at the expiration of + the 60 day notice period specified above. + + (b) any software, hardware, or device, other than such Participant's + Contributor Version, directly or indirectly infringes any patent, then + any rights granted to You by such Participant under Sections 2.1(b) + and 2.2(b) are revoked effective as of the date You first made, used, + sold, distributed, or had made, Modifications made by that + Participant. + + 8.3. If You assert a patent infringement claim against Participant + alleging that such Participant's Contributor Version directly or + indirectly infringes any patent where such claim is resolved (such as + by license or settlement) prior to the initiation of patent + infringement litigation, then the reasonable value of the licenses + granted by such Participant under Sections 2.1 or 2.2 shall be taken + into account in determining the amount or value of any payment or + license. + + 8.4. In the event of termination under Sections 8.1 or 8.2 above, + all end user license agreements (excluding distributors and resellers) + which have been validly granted by You or any distributor hereunder + prior to termination shall survive termination. + +9. LIMITATION OF LIABILITY. + + UNDER NO CIRCUMSTANCES AND UNDER NO LEGAL THEORY, WHETHER TORT + (INCLUDING NEGLIGENCE), CONTRACT, OR OTHERWISE, SHALL YOU, THE INITIAL + DEVELOPER, ANY OTHER CONTRIBUTOR, OR ANY DISTRIBUTOR OF COVERED CODE, + OR ANY SUPPLIER OF ANY OF SUCH PARTIES, BE LIABLE TO ANY PERSON FOR + ANY INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES OF ANY + CHARACTER INCLUDING, WITHOUT LIMITATION, DAMAGES FOR LOSS OF GOODWILL, + WORK STOPPAGE, COMPUTER FAILURE OR MALFUNCTION, OR ANY AND ALL OTHER + COMMERCIAL DAMAGES OR LOSSES, EVEN IF SUCH PARTY SHALL HAVE BEEN + INFORMED OF THE POSSIBILITY OF SUCH DAMAGES. THIS LIMITATION OF + LIABILITY SHALL NOT APPLY TO LIABILITY FOR DEATH OR PERSONAL INJURY + RESULTING FROM SUCH PARTY'S NEGLIGENCE TO THE EXTENT APPLICABLE LAW + PROHIBITS SUCH LIMITATION. SOME JURISDICTIONS DO NOT ALLOW THE + EXCLUSION OR LIMITATION OF INCIDENTAL OR CONSEQUENTIAL DAMAGES, SO + THIS EXCLUSION AND LIMITATION MAY NOT APPLY TO YOU. + +10. U.S. GOVERNMENT END USERS. + + The Covered Code is a "commercial item," as that term is defined in + 48 C.F.R. 2.101 (Oct. 1995), consisting of "commercial computer + software" and "commercial computer software documentation," as such + terms are used in 48 C.F.R. 12.212 (Sept. 1995). Consistent with 48 + C.F.R. 12.212 and 48 C.F.R. 227.7202-1 through 227.7202-4 (June 1995), + all U.S. Government End Users acquire Covered Code with only those + rights set forth herein. + +11. MISCELLANEOUS. + + This License represents the complete agreement concerning subject + matter hereof. If any provision of this License is held to be + unenforceable, such provision shall be reformed only to the extent + necessary to make it enforceable. This License shall be governed by + California law provisions (except to the extent applicable law, if + any, provides otherwise), excluding its conflict-of-law provisions. + With respect to disputes in which at least one party is a citizen of, + or an entity chartered or registered to do business in the United + States of America, any litigation relating to this License shall be + subject to the jurisdiction of the Federal Courts of the Northern + District of California, with venue lying in Santa Clara County, + California, with the losing party responsible for costs, including + without limitation, court costs and reasonable attorneys' fees and + expenses. The application of the United Nations Convention on + Contracts for the International Sale of Goods is expressly excluded. + Any law or regulation which provides that the language of a contract + shall be construed against the drafter shall not apply to this + License. + +12. RESPONSIBILITY FOR CLAIMS. + + As between Initial Developer and the Contributors, each party is + responsible for claims and damages arising, directly or indirectly, + out of its utilization of rights under this License and You agree to + work with Initial Developer and Contributors to distribute such + responsibility on an equitable basis. Nothing herein is intended or + shall be deemed to constitute any admission of liability. + +13. MULTIPLE-LICENSED CODE. + + Initial Developer may designate portions of the Covered Code as + "Multiple-Licensed". "Multiple-Licensed" means that the Initial + Developer permits you to utilize portions of the Covered Code under + Your choice of the MPL or the alternative licenses, if any, specified + by the Initial Developer in the file described in Exhibit A. + +EXHIBIT A -Mozilla Public License. + + ``The contents of this file are subject to the Mozilla Public License + Version 1.1 (the "License"); you may not use this file except in + compliance with the License. You may obtain a copy of the License at + https://www.mozilla.org/MPL/ + + Software distributed under the License is distributed on an "AS IS" + basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See the + License for the specific language governing rights and limitations + under the License. + + The Original Code is ______________________________________. + + The Initial Developer of the Original Code is ________________________. + Portions created by ______________________ are Copyright (C) ______ + _______________________. All Rights Reserved. + + Contributor(s): ______________________________________. + + Alternatively, the contents of this file may be used under the terms + of the _____ license (the "[___] License"), in which case the + provisions of [______] License are applicable instead of those + above. If you wish to allow use of your version of this file only + under the terms of the [____] License and not to allow others to use + your version of this file under the MPL, indicate your decision by + deleting the provisions above and replace them with the notice and + other provisions required by the [___] License. If you do not delete + the provisions above, a recipient may use your version of this file + under either the MPL or the [___] License." + + [NOTE: The text of this Exhibit A may differ slightly from the text of + the notices in the Source Code files of the Original Code. You should + use the text of this Exhibit A rather than the text found in the + Original Code Source Code for Your Modifications.] diff --git a/LICENSES/other/Apache-2.0 b/LICENSES/other/Apache-2.0 deleted file mode 100644 index 7cd903f573e5..000000000000 --- a/LICENSES/other/Apache-2.0 +++ /dev/null @@ -1,183 +0,0 @@ -Valid-License-Identifier: Apache-2.0 -SPDX-URL: https://spdx.org/licenses/Apache-2.0.html -Usage-Guide: - To use the Apache License version 2.0 put the following SPDX tag/value - pair into a comment according to the placement guidelines in the - licensing rules documentation: - SPDX-License-Identifier: Apache-2.0 -License-Text: - -Apache License - -Version 2.0, January 2004 - -http://www.apache.org/licenses/ - -TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION - -1. Definitions. - -"License" shall mean the terms and conditions for use, reproduction, and -distribution as defined by Sections 1 through 9 of this document. - -"Licensor" shall mean the copyright owner or entity authorized by the -copyright owner that is granting the License. - -"Legal Entity" shall mean the union of the acting entity and all other -entities that control, are controlled by, or are under common control with -that entity. For the purposes of this definition, "control" means (i) the -power, direct or indirect, to cause the direction or management of such -entity, whether by contract or otherwise, or (ii) ownership of fifty -percent (50%) or more of the outstanding shares, or (iii) beneficial -ownership of such entity. - -"You" (or "Your") shall mean an individual or Legal Entity exercising -permissions granted by this License. - -"Source" form shall mean the preferred form for making modifications, -including but not limited to software source code, documentation source, -and configuration files. - -"Object" form shall mean any form resulting from mechanical transformation -or translation of a Source form, including but not limited to compiled -object code, generated documentation, and conversions to other media types. - -"Work" shall mean the work of authorship, whether in Source or Object form, -made available under the License, as indicated by a copyright notice that -is included in or attached to the work (an example is provided in the -Appendix below). - -"Derivative Works" shall mean any work, whether in Source or Object form, -that is based on (or derived from) the Work and for which the editorial -revisions, annotations, elaborations, or other modifications represent, as -a whole, an original work of authorship. For the purposes of this License, -Derivative Works shall not include works that remain separable from, or -merely link (or bind by name) to the interfaces of, the Work and Derivative -Works thereof. - -"Contribution" shall mean any work of authorship, including the original -version of the Work and any modifications or additions to that Work or -Derivative Works thereof, that is intentionally submitted to Licensor for -inclusion in the Work by the copyright owner or by an individual or Legal -Entity authorized to submit on behalf of the copyright owner. For the -purposes of this definition, "submitted" means any form of electronic, -verbal, or written communication sent to the Licensor or its -representatives, including but not limited to communication on electronic -mailing lists, source code control systems, and issue tracking systems that -are managed by, or on behalf of, the Licensor for the purpose of discussing -and improving the Work, but excluding communication that is conspicuously -marked or otherwise designated in writing by the copyright owner as "Not a -Contribution." - -"Contributor" shall mean Licensor and any individual or Legal Entity on -behalf of whom a Contribution has been received by Licensor and -subsequently incorporated within the Work. - -2. Grant of Copyright License. Subject to the terms and conditions of this - License, each Contributor hereby grants to You a perpetual, worldwide, - non-exclusive, no-charge, royalty-free, irrevocable copyright license to - reproduce, prepare Derivative Works of, publicly display, publicly - perform, sublicense, and distribute the Work and such Derivative Works - in Source or Object form. - -3. Grant of Patent License. Subject to the terms and conditions of this - License, each Contributor hereby grants to You a perpetual, worldwide, - non-exclusive, no-charge, royalty-free, irrevocable (except as stated in - this section) patent license to make, have made, use, offer to sell, - sell, import, and otherwise transfer the Work, where such license - applies only to those patent claims licensable by such Contributor that - are necessarily infringed by their Contribution(s) alone or by - combination of their Contribution(s) with the Work to which such - Contribution(s) was submitted. If You institute patent litigation - against any entity (including a cross-claim or counterclaim in a - lawsuit) alleging that the Work or a Contribution incorporated within - the Work constitutes direct or contributory patent infringement, then - any patent licenses granted to You under this License for that Work - shall terminate as of the date such litigation is filed. - -4. Redistribution. You may reproduce and distribute copies of the Work or - Derivative Works thereof in any medium, with or without modifications, - and in Source or Object form, provided that You meet the following - conditions: - - a. You must give any other recipients of the Work or Derivative Works a - copy of this License; and - - b. You must cause any modified files to carry prominent notices stating - that You changed the files; and - - c. You must retain, in the Source form of any Derivative Works that You - distribute, all copyright, patent, trademark, and attribution notices - from the Source form of the Work, excluding those notices that do not - pertain to any part of the Derivative Works; and - - d. If the Work includes a "NOTICE" text file as part of its - distribution, then any Derivative Works that You distribute must - include a readable copy of the attribution notices contained within - such NOTICE file, excluding those notices that do not pertain to any - part of the Derivative Works, in at least one of the following - places: within a NOTICE text file distributed as part of the - Derivative Works; within the Source form or documentation, if - provided along with the Derivative Works; or, within a display - generated by the Derivative Works, if and wherever such third-party - notices normally appear. The contents of the NOTICE file are for - informational purposes only and do not modify the License. You may - add Your own attribution notices within Derivative Works that You - distribute, alongside or as an addendum to the NOTICE text from the - Work, provided that such additional attribution notices cannot be - construed as modifying the License. - - You may add Your own copyright statement to Your modifications and may - provide additional or different license terms and conditions for use, - reproduction, or distribution of Your modifications, or for any such - Derivative Works as a whole, provided Your use, reproduction, and - distribution of the Work otherwise complies with the conditions stated - in this License. - -5. Submission of Contributions. Unless You explicitly state otherwise, any - Contribution intentionally submitted for inclusion in the Work by You to - the Licensor shall be under the terms and conditions of this License, - without any additional terms or conditions. Notwithstanding the above, - nothing herein shall supersede or modify the terms of any separate - license agreement you may have executed with Licensor regarding such - Contributions. - -6. Trademarks. This License does not grant permission to use the trade - names, trademarks, service marks, or product names of the Licensor, - except as required for reasonable and customary use in describing the - origin of the Work and reproducing the content of the NOTICE file. - -7. Disclaimer of Warranty. Unless required by applicable law or agreed to - in writing, Licensor provides the Work (and each Contributor provides - its Contributions) on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS - OF ANY KIND, either express or implied, including, without limitation, - any warranties or conditions of TITLE, NON-INFRINGEMENT, - MERCHANTABILITY, or FITNESS FOR A PARTICULAR PURPOSE. You are solely - responsible for determining the appropriateness of using or - redistributing the Work and assume any risks associated with Your - exercise of permissions under this License. - -8. Limitation of Liability. In no event and under no legal theory, whether - in tort (including negligence), contract, or otherwise, unless required - by applicable law (such as deliberate and grossly negligent acts) or - agreed to in writing, shall any Contributor be liable to You for - damages, including any direct, indirect, special, incidental, or - consequential damages of any character arising as a result of this - License or out of the use or inability to use the Work (including but - not limited to damages for loss of goodwill, work stoppage, computer - failure or malfunction, or any and all other commercial damages or - losses), even if such Contributor has been advised of the possibility of - such damages. - -9. Accepting Warranty or Additional Liability. While redistributing the - Work or Derivative Works thereof, You may choose to offer, and charge a - fee for, acceptance of support, warranty, indemnity, or other liability - obligations and/or rights consistent with this License. However, in - accepting such obligations, You may act only on Your own behalf and on - Your sole responsibility, not on behalf of any other Contributor, and - only if You agree to indemnify, defend, and hold each Contributor - harmless for any liability incurred by, or claims asserted against, such - Contributor by reason of your accepting any such warranty or additional - liability. - -END OF TERMS AND CONDITIONS diff --git a/LICENSES/other/CDDL-1.0 b/LICENSES/other/CDDL-1.0 deleted file mode 100644 index 25f614276ddd..000000000000 --- a/LICENSES/other/CDDL-1.0 +++ /dev/null @@ -1,368 +0,0 @@ -Valid-License-Identifier: CDDL-1.0 -SPDX-URL: https://spdx.org/licenses/CDDL-1.0.html -Usage-Guide: - Do NOT use. The CDDL-1.0 is not GPL compatible. It may only be used for - dual-licensed files where the other license is GPL compatible. - If you end up using this it MUST be used together with a GPL2 compatible - license using "OR". - To use the Common Development and Distribution License 1.0 put the - following SPDX tag/value pair into a comment according to the placement - guidelines in the licensing rules documentation: - SPDX-License-Identifier: ($GPL-COMPATIBLE-ID OR CDDL-1.0) - -License-Text: - -COMMON DEVELOPMENT AND DISTRIBUTION LICENSE (CDDL) -Version 1.0 - - 1. Definitions. - - 1.1. "Contributor" means each individual or entity that creates or - contributes to the creation of Modifications. - - 1.2. "Contributor Version" means the combination of the Original - Software, prior Modifications used by a Contributor (if any), - and the Modifications made by that particular Contributor. - - 1.3. "Covered Software" means (a) the Original Software, or (b) - Modifications, or (c) the combination of files containing - Original Software with files containing Modifications, in each - case including portions thereof. - - 1.4. "Executable" means the Covered Software in any form other than - Source Code. - - 1.5. "Initial Developer" means the individual or entity that first - makes Original Software available under this License. - - 1.6. "Larger Work" means a work which combines Covered Software or - portions thereof with code not governed by the terms of this - License. - - 1.7. "License" means this document. - - 1.8. "Licensable" means having the right to grant, to the maximum - extent possible, whether at the time of the initial grant or - subsequently acquired, any and all of the rights conveyed herein. - - 1.9. "Modifications" means the Source Code and Executable form of - any of the following: - - A. Any file that results from an addition to, deletion from or - modification of the contents of a file containing Original - Software or previous Modifications; - - B. Any new file that contains any part of the Original Software - or previous Modification; or - - C. Any new file that is contributed or otherwise made available - under the terms of this License. - - 1.10. "Original Software" means the Source Code and Executable form - of computer software code that is originally released under - this License. - - 1.11. "Patent Claims" means any patent claim(s), now owned or - hereafter acquired, including without limitation, method, - process, and apparatus claims, in any patent Licensable by - grantor. - - 1.12. "Source Code" means (a) the common form of computer software - code in which modifications are made and (b) associated - documentation included in or with such code. - - 1.13. "You" (or "Your") means an individual or a legal entity - exercising rights under, and complying with all of the terms - of, this License. For legal entities, "You" includes any - entity which controls, is controlled by, or is under common - control with You. For purposes of this definition, "control" - means (a) the power, direct or indirect, to cause the - direction or management of such entity, whether by contract - or otherwise, or (b) ownership of more than fifty percent - (50%) of the outstanding shares or beneficial ownership of - such entity. - - 2. License Grants. - 2.1. The Initial Developer Grant. - - Conditioned upon Your compliance with Section 3.1 below and subject - to third party intellectual property claims, the Initial Developer - hereby grants You a world-wide, royalty-free, non-exclusive - license: - - (a) under intellectual property rights (other than patent or - trademark) Licensable by Initial Developer, to use, - reproduce, modify, display, perform, sublicense and - distribute the Original Software (or portions thereof), - with or without Modifications, and/or as part of a Larger - Work; and - - (b) under Patent Claims infringed by the making, using or - selling of Original Software, to make, have made, use, - practice, sell, and offer for sale, and/or otherwise - dispose of the Original Software (or portions thereof). - - (c) The licenses granted in Sections 2.1(a) and (b) are - effective on the date Initial Developer first distributes - or otherwise makes the Original Software available to a - third party under the terms of this License. - - (d) Notwithstanding Section 2.1(b) above, no patent license is - granted: (1) for code that You delete from the Original - Software, or (2) for infringements caused by: (i) the - modification of the Original Software, or (ii) the - combination of the Original Software with other software or - devices. - - 2.2. Contributor Grant. - - Conditioned upon Your compliance with Section 3.1 below and subject - to third party intellectual property claims, each Contributor - hereby grants You a world-wide, royalty-free, non-exclusive - license: - - (a) under intellectual property rights (other than patent or - trademark) Licensable by Contributor to use, reproduce, - modify, display, perform, sublicense and distribute the - Modifications created by such Contributor (or portions - thereof), either on an unmodified basis, with other - Modifications, as Covered Software and/or as part of a - Larger Work; and - - (b) under Patent Claims infringed by the making, using, or - selling of Modifications made by that Contributor either - alone and/or in combination with its Contributor Version - (or portions of such combination), to make, use, sell, - offer for sale, have made, and/or otherwise dispose of: (1) - Modifications made by that Contributor (or portions - thereof); and (2) the combination of Modifications made by - that Contributor with its Contributor Version (or portions - of such combination). - - (c) The licenses granted in Sections 2.2(a) and 2.2(b) are - effective on the date Contributor first distributes or - otherwise makes the Modifications available to a third - party. - - (d) Notwithstanding Section 2.2(b) above, no patent license is - granted: (1) for any code that Contributor has deleted from - the Contributor Version; (2) for infringements caused by: - (i) third party modifications of Contributor Version, or - (ii) the combination of Modifications made by that - Contributor with other software (except as part of the - Contributor Version) or other devices; or (3) under Patent - Claims infringed by Covered Software in the absence of - Modifications made by that Contributor. - - 3. Distribution Obligations. - 3.1. Availability of Source Code. - - Any Covered Software that You distribute or otherwise make - available in Executable form must also be made available in Source - Code form and that Source Code form must be distributed only under - the terms of this License. You must include a copy of this License - with every copy of the Source Code form of the Covered Software You - distribute or otherwise make available. You must inform recipients - of any such Covered Software in Executable form as to how they can - obtain such Covered Software in Source Code form in a reasonable - manner on or through a medium customarily used for software - exchange. - - 3.2. Modifications. - - The Modifications that You create or to which You contribute are - governed by the terms of this License. You represent that You - believe Your Modifications are Your original creation(s) and/or You - have sufficient rights to grant the rights conveyed by this - License. - - 3.3. Required Notices. - - You must include a notice in each of Your Modifications that - identifies You as the Contributor of the Modification. You may not - remove or alter any copyright, patent or trademark notices - contained within the Covered Software, or any notices of licensing - or any descriptive text giving attribution to any Contributor or - the Initial Developer. - - 3.4. Application of Additional Terms. - - You may not offer or impose any terms on any Covered Software in - Source Code form that alters or restricts the applicable version of - this License or the recipients' rights hereunder. You may choose to - offer, and to charge a fee for, warranty, support, indemnity or - liability obligations to one or more recipients of Covered - Software. However, you may do so only on Your own behalf, and not - on behalf of the Initial Developer or any Contributor. You must - make it absolutely clear that any such warranty, support, indemnity - or liability obligation is offered by You alone, and You hereby - agree to indemnify the Initial Developer and every Contributor for - any liability incurred by the Initial Developer or such Contributor - as a result of warranty, support, indemnity or liability terms You - offer. - - 3.5. Distribution of Executable Versions. - - You may distribute the Executable form of the Covered Software - under the terms of this License or under the terms of a license of - Your choice, which may contain terms different from this License, - provided that You are in compliance with the terms of this License - and that the license for the Executable form does not attempt to - limit or alter the recipient's rights in the Source Code form from - the rights set forth in this License. If You distribute the Covered - Software in Executable form under a different license, You must - make it absolutely clear that any terms which differ from this - License are offered by You alone, not by the Initial Developer or - Contributor. You hereby agree to indemnify the Initial Developer - and every Contributor for any liability incurred by the Initial - Developer or such Contributor as a result of any such terms You - offer. - - 3.6. Larger Works. - - You may create a Larger Work by combining Covered Software with - other code not governed by the terms of this License and distribute - the Larger Work as a single product. In such a case, You must make - sure the requirements of this License are fulfilled for the Covered - Software. - - 4. Versions of the License. - 4.1. New Versions. - - Sun Microsystems, Inc. is the initial license steward and may - publish revised and/or new versions of this License from time to - time. Each version will be given a distinguishing version - number. Except as provided in Section 4.3, no one other than the - license steward has the right to modify this License. - - 4.2. Effect of New Versions. - - You may always continue to use, distribute or otherwise make the - Covered Software available under the terms of the version of the - License under which You originally received the Covered - Software. If the Initial Developer includes a notice in the - Original Software prohibiting it from being distributed or - otherwise made available under any subsequent version of the - License, You must distribute and make the Covered Software - available under the terms of the version of the License under which - You originally received the Covered Software. Otherwise, You may - also choose to use, distribute or otherwise make the Covered - Software available under the terms of any subsequent version of the - License published by the license steward. - - 4.3. Modified Versions. - - When You are an Initial Developer and You want to create a new - license for Your Original Software, You may create and use a - modified version of this License if You: (a) rename the license and - remove any references to the name of the license steward (except to - note that the license differs from this License); and (b) otherwise - make it clear that the license contains terms which differ from - this License. - - 5. DISCLAIMER OF WARRANTY. - - COVERED SOFTWARE IS PROVIDED UNDER THIS LICENSE ON AN "AS IS" BASIS, - WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, - WITHOUT LIMITATION, WARRANTIES THAT THE COVERED SOFTWARE IS FREE OF - DEFECTS, MERCHANTABLE, FIT FOR A PARTICULAR PURPOSE OR - NON-INFRINGING. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF - THE COVERED SOFTWARE IS WITH YOU. SHOULD ANY COVERED SOFTWARE PROVE - DEFECTIVE IN ANY RESPECT, YOU (NOT THE INITIAL DEVELOPER OR ANY OTHER - CONTRIBUTOR) ASSUME THE COST OF ANY NECESSARY SERVICING, REPAIR OR - CORRECTION. THIS DISCLAIMER OF WARRANTY CONSTITUTES AN ESSENTIAL PART - OF THIS LICENSE. NO USE OF ANY COVERED SOFTWARE IS AUTHORIZED HEREUNDER - EXCEPT UNDER THIS DISCLAIMER. - - 6. TERMINATION. - - 6.1. This License and the rights granted hereunder will terminate - automatically if You fail to comply with terms herein and fail to - cure such breach within 30 days of becoming aware of the - breach. Provisions which, by their nature, must remain in effect - beyond the termination of this License shall survive. - - 6.2. If You assert a patent infringement claim (excluding - declaratory judgment actions) against Initial Developer or a - Contributor (the Initial Developer or Contributor against whom You - assert such claim is referred to as "Participant") alleging that - the Participant Software (meaning the Contributor Version where the - Participant is a Contributor or the Original Software where the - Participant is the Initial Developer) directly or indirectly - infringes any patent, then any and all rights granted directly or - indirectly to You by such Participant, the Initial Developer (if - the Initial Developer is not the Participant) and all Contributors - under Sections 2.1 and/or 2.2 of this License shall, upon 60 days - notice from Participant terminate prospectively and automatically - at the expiration of such 60 day notice period, unless if within - such 60 day period You withdraw Your claim with respect to the - Participant Software against such Participant either unilaterally - or pursuant to a written agreement with Participant. - - 6.3. In the event of termination under Sections 6.1 or 6.2 above, - all end user licenses that have been validly granted by You or any - distributor hereunder prior to termination (excluding licenses - granted to You by any distributor) shall survive termination. - - 7. LIMITATION OF LIABILITY. - - UNDER NO CIRCUMSTANCES AND UNDER NO LEGAL THEORY, WHETHER TORT - (INCLUDING NEGLIGENCE), CONTRACT, OR OTHERWISE, SHALL YOU, THE INITIAL - DEVELOPER, ANY OTHER CONTRIBUTOR, OR ANY DISTRIBUTOR OF COVERED - SOFTWARE, OR ANY SUPPLIER OF ANY OF SUCH PARTIES, BE LIABLE TO ANY - PERSON FOR ANY INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES - OF ANY CHARACTER INCLUDING, WITHOUT LIMITATION, DAMAGES FOR LOST - PROFITS, LOSS OF GOODWILL, WORK STOPPAGE, COMPUTER FAILURE OR - MALFUNCTION, OR ANY AND ALL OTHER COMMERCIAL DAMAGES OR LOSSES, EVEN IF - SUCH PARTY SHALL HAVE BEEN INFORMED OF THE POSSIBILITY OF SUCH - DAMAGES. THIS LIMITATION OF LIABILITY SHALL NOT APPLY TO LIABILITY FOR - DEATH OR PERSONAL INJURY RESULTING FROM SUCH PARTY'S NEGLIGENCE TO THE - EXTENT APPLICABLE LAW PROHIBITS SUCH LIMITATION. SOME JURISDICTIONS DO - NOT ALLOW THE EXCLUSION OR LIMITATION OF INCIDENTAL OR CONSEQUENTIAL - DAMAGES, SO THIS EXCLUSION AND LIMITATION MAY NOT APPLY TO YOU. - - 8. U.S. GOVERNMENT END USERS. - - The Covered Software is a "commercial item," as that term is defined in - 48 C.F.R. 2.101 (Oct. 1995), consisting of "commercial computer - software" (as that term is defined at 48 C.F.R. $ 252.227-7014(a)(1)) - and "commercial computer software documentation" as such terms are used - in 48 C.F.R. 12.212 (Sept. 1995). Consistent with 48 C.F.R. 12.212 and - 48 C.F.R. 227.7202-1 through 227.7202-4 (June 1995), all - U.S. Government End Users acquire Covered Software with only those - rights set forth herein. This U.S. Government Rights clause is in lieu - of, and supersedes, any other FAR, DFAR, or other clause or provision - that addresses Government rights in computer software under this - License. - - 9. MISCELLANEOUS. - - This License represents the complete agreement concerning subject - matter hereof. If any provision of this License is held to be - unenforceable, such provision shall be reformed only to the extent - necessary to make it enforceable. This License shall be governed by the - law of the jurisdiction specified in a notice contained within the - Original Software (except to the extent applicable law, if any, - provides otherwise), excluding such jurisdiction's conflict-of-law - provisions. Any litigation relating to this License shall be subject to - the jurisdiction of the courts located in the jurisdiction and venue - specified in a notice contained within the Original Software, with the - losing party responsible for costs, including, without limitation, - court costs and reasonable attorneys' fees and expenses. The - application of the United Nations Convention on Contracts for the - International Sale of Goods is expressly excluded. Any law or - regulation which provides that the language of a contract shall be - construed against the drafter shall not apply to this License. You - agree that You alone are responsible for compliance with the United - States export administration regulations (and the export control laws - and regulation of any other countries) when You use, distribute or - otherwise make available any Covered Software. - - 10. RESPONSIBILITY FOR CLAIMS. - - As between Initial Developer and the Contributors, each party is - responsible for claims and damages arising, directly or indirectly, out - of its utilization of rights under this License and You agree to work - with Initial Developer and Contributors to distribute such - responsibility on an equitable basis. Nothing herein is intended or - shall be deemed to constitute any admission of liability. diff --git a/LICENSES/other/MPL-1.1 b/LICENSES/other/MPL-1.1 deleted file mode 100644 index 568b6049efe6..000000000000 --- a/LICENSES/other/MPL-1.1 +++ /dev/null @@ -1,478 +0,0 @@ -Valid-License-Identifier: MPL-1.1 -SPDX-URL: https://spdx.org/licenses/MPL-1.1.html -Usage-Guide: - To use the Mozilla Public License version 1.1 put the following SPDX - tag/value pair into a comment according to the placement guidelines in - the licensing rules documentation: - SPDX-License-Identifier: MPL-1.1 -License-Text: - - MOZILLA PUBLIC LICENSE - Version 1.1 - - --------------- - -1. Definitions. - - 1.0.1. "Commercial Use" means distribution or otherwise making the - Covered Code available to a third party. - - 1.1. "Contributor" means each entity that creates or contributes to - the creation of Modifications. - - 1.2. "Contributor Version" means the combination of the Original - Code, prior Modifications used by a Contributor, and the Modifications - made by that particular Contributor. - - 1.3. "Covered Code" means the Original Code or Modifications or the - combination of the Original Code and Modifications, in each case - including portions thereof. - - 1.4. "Electronic Distribution Mechanism" means a mechanism generally - accepted in the software development community for the electronic - transfer of data. - - 1.5. "Executable" means Covered Code in any form other than Source - Code. - - 1.6. "Initial Developer" means the individual or entity identified - as the Initial Developer in the Source Code notice required by Exhibit - A. - - 1.7. "Larger Work" means a work which combines Covered Code or - portions thereof with code not governed by the terms of this License. - - 1.8. "License" means this document. - - 1.8.1. "Licensable" means having the right to grant, to the maximum - extent possible, whether at the time of the initial grant or - subsequently acquired, any and all of the rights conveyed herein. - - 1.9. "Modifications" means any addition to or deletion from the - substance or structure of either the Original Code or any previous - Modifications. When Covered Code is released as a series of files, a - Modification is: - A. Any addition to or deletion from the contents of a file - containing Original Code or previous Modifications. - - B. Any new file that contains any part of the Original Code or - previous Modifications. - - 1.10. "Original Code" means Source Code of computer software code - which is described in the Source Code notice required by Exhibit A as - Original Code, and which, at the time of its release under this - License is not already Covered Code governed by this License. - - 1.10.1. "Patent Claims" means any patent claim(s), now owned or - hereafter acquired, including without limitation, method, process, - and apparatus claims, in any patent Licensable by grantor. - - 1.11. "Source Code" means the preferred form of the Covered Code for - making modifications to it, including all modules it contains, plus - any associated interface definition files, scripts used to control - compilation and installation of an Executable, or source code - differential comparisons against either the Original Code or another - well known, available Covered Code of the Contributor's choice. The - Source Code can be in a compressed or archival form, provided the - appropriate decompression or de-archiving software is widely available - for no charge. - - 1.12. "You" (or "Your") means an individual or a legal entity - exercising rights under, and complying with all of the terms of, this - License or a future version of this License issued under Section 6.1. - For legal entities, "You" includes any entity which controls, is - controlled by, or is under common control with You. For purposes of - this definition, "control" means (a) the power, direct or indirect, - to cause the direction or management of such entity, whether by - contract or otherwise, or (b) ownership of more than fifty percent - (50%) of the outstanding shares or beneficial ownership of such - entity. - -2. Source Code License. - - 2.1. The Initial Developer Grant. - The Initial Developer hereby grants You a world-wide, royalty-free, - non-exclusive license, subject to third party intellectual property - claims: - (a) under intellectual property rights (other than patent or - trademark) Licensable by Initial Developer to use, reproduce, - modify, display, perform, sublicense and distribute the Original - Code (or portions thereof) with or without Modifications, and/or - as part of a Larger Work; and - - (b) under Patents Claims infringed by the making, using or - selling of Original Code, to make, have made, use, practice, - sell, and offer for sale, and/or otherwise dispose of the - Original Code (or portions thereof). - - (c) the licenses granted in this Section 2.1(a) and (b) are - effective on the date Initial Developer first distributes - Original Code under the terms of this License. - - (d) Notwithstanding Section 2.1(b) above, no patent license is - granted: 1) for code that You delete from the Original Code; 2) - separate from the Original Code; or 3) for infringements caused - by: i) the modification of the Original Code or ii) the - combination of the Original Code with other software or devices. - - 2.2. Contributor Grant. - Subject to third party intellectual property claims, each Contributor - hereby grants You a world-wide, royalty-free, non-exclusive license - - (a) under intellectual property rights (other than patent or - trademark) Licensable by Contributor, to use, reproduce, modify, - display, perform, sublicense and distribute the Modifications - created by such Contributor (or portions thereof) either on an - unmodified basis, with other Modifications, as Covered Code - and/or as part of a Larger Work; and - - (b) under Patent Claims infringed by the making, using, or - selling of Modifications made by that Contributor either alone - and/or in combination with its Contributor Version (or portions - of such combination), to make, use, sell, offer for sale, have - made, and/or otherwise dispose of: 1) Modifications made by that - Contributor (or portions thereof); and 2) the combination of - Modifications made by that Contributor with its Contributor - Version (or portions of such combination). - - (c) the licenses granted in Sections 2.2(a) and 2.2(b) are - effective on the date Contributor first makes Commercial Use of - the Covered Code. - - (d) Notwithstanding Section 2.2(b) above, no patent license is - granted: 1) for any code that Contributor has deleted from the - Contributor Version; 2) separate from the Contributor Version; - 3) for infringements caused by: i) third party modifications of - Contributor Version or ii) the combination of Modifications made - by that Contributor with other software (except as part of the - Contributor Version) or other devices; or 4) under Patent Claims - infringed by Covered Code in the absence of Modifications made by - that Contributor. - -3. Distribution Obligations. - - 3.1. Application of License. - The Modifications which You create or to which You contribute are - governed by the terms of this License, including without limitation - Section 2.2. The Source Code version of Covered Code may be - distributed only under the terms of this License or a future version - of this License released under Section 6.1, and You must include a - copy of this License with every copy of the Source Code You - distribute. You may not offer or impose any terms on any Source Code - version that alters or restricts the applicable version of this - License or the recipients' rights hereunder. However, You may include - an additional document offering the additional rights described in - Section 3.5. - - 3.2. Availability of Source Code. - Any Modification which You create or to which You contribute must be - made available in Source Code form under the terms of this License - either on the same media as an Executable version or via an accepted - Electronic Distribution Mechanism to anyone to whom you made an - Executable version available; and if made available via Electronic - Distribution Mechanism, must remain available for at least twelve (12) - months after the date it initially became available, or at least six - (6) months after a subsequent version of that particular Modification - has been made available to such recipients. You are responsible for - ensuring that the Source Code version remains available even if the - Electronic Distribution Mechanism is maintained by a third party. - - 3.3. Description of Modifications. - You must cause all Covered Code to which You contribute to contain a - file documenting the changes You made to create that Covered Code and - the date of any change. You must include a prominent statement that - the Modification is derived, directly or indirectly, from Original - Code provided by the Initial Developer and including the name of the - Initial Developer in (a) the Source Code, and (b) in any notice in an - Executable version or related documentation in which You describe the - origin or ownership of the Covered Code. - - 3.4. Intellectual Property Matters - (a) Third Party Claims. - If Contributor has knowledge that a license under a third party's - intellectual property rights is required to exercise the rights - granted by such Contributor under Sections 2.1 or 2.2, - Contributor must include a text file with the Source Code - distribution titled "LEGAL" which describes the claim and the - party making the claim in sufficient detail that a recipient will - know whom to contact. If Contributor obtains such knowledge after - the Modification is made available as described in Section 3.2, - Contributor shall promptly modify the LEGAL file in all copies - Contributor makes available thereafter and shall take other steps - (such as notifying appropriate mailing lists or newsgroups) - reasonably calculated to inform those who received the Covered - Code that new knowledge has been obtained. - - (b) Contributor APIs. - If Contributor's Modifications include an application programming - interface and Contributor has knowledge of patent licenses which - are reasonably necessary to implement that API, Contributor must - also include this information in the LEGAL file. - - (c) Representations. - Contributor represents that, except as disclosed pursuant to - Section 3.4(a) above, Contributor believes that Contributor's - Modifications are Contributor's original creation(s) and/or - Contributor has sufficient rights to grant the rights conveyed by - this License. - - 3.5. Required Notices. - You must duplicate the notice in Exhibit A in each file of the Source - Code. If it is not possible to put such notice in a particular Source - Code file due to its structure, then You must include such notice in a - location (such as a relevant directory) where a user would be likely - to look for such a notice. If You created one or more Modification(s) - You may add your name as a Contributor to the notice described in - Exhibit A. You must also duplicate this License in any documentation - for the Source Code where You describe recipients' rights or ownership - rights relating to Covered Code. You may choose to offer, and to - charge a fee for, warranty, support, indemnity or liability - obligations to one or more recipients of Covered Code. However, You - may do so only on Your own behalf, and not on behalf of the Initial - Developer or any Contributor. You must make it absolutely clear than - any such warranty, support, indemnity or liability obligation is - offered by You alone, and You hereby agree to indemnify the Initial - Developer and every Contributor for any liability incurred by the - Initial Developer or such Contributor as a result of warranty, - support, indemnity or liability terms You offer. - - 3.6. Distribution of Executable Versions. - You may distribute Covered Code in Executable form only if the - requirements of Section 3.1-3.5 have been met for that Covered Code, - and if You include a notice stating that the Source Code version of - the Covered Code is available under the terms of this License, - including a description of how and where You have fulfilled the - obligations of Section 3.2. The notice must be conspicuously included - in any notice in an Executable version, related documentation or - collateral in which You describe recipients' rights relating to the - Covered Code. You may distribute the Executable version of Covered - Code or ownership rights under a license of Your choice, which may - contain terms different from this License, provided that You are in - compliance with the terms of this License and that the license for the - Executable version does not attempt to limit or alter the recipient's - rights in the Source Code version from the rights set forth in this - License. If You distribute the Executable version under a different - license You must make it absolutely clear that any terms which differ - from this License are offered by You alone, not by the Initial - Developer or any Contributor. You hereby agree to indemnify the - Initial Developer and every Contributor for any liability incurred by - the Initial Developer or such Contributor as a result of any such - terms You offer. - - 3.7. Larger Works. - You may create a Larger Work by combining Covered Code with other code - not governed by the terms of this License and distribute the Larger - Work as a single product. In such a case, You must make sure the - requirements of this License are fulfilled for the Covered Code. - -4. Inability to Comply Due to Statute or Regulation. - - If it is impossible for You to comply with any of the terms of this - License with respect to some or all of the Covered Code due to - statute, judicial order, or regulation then You must: (a) comply with - the terms of this License to the maximum extent possible; and (b) - describe the limitations and the code they affect. Such description - must be included in the LEGAL file described in Section 3.4 and must - be included with all distributions of the Source Code. Except to the - extent prohibited by statute or regulation, such description must be - sufficiently detailed for a recipient of ordinary skill to be able to - understand it. - -5. Application of this License. - - This License applies to code to which the Initial Developer has - attached the notice in Exhibit A and to related Covered Code. - -6. Versions of the License. - - 6.1. New Versions. - Netscape Communications Corporation ("Netscape") may publish revised - and/or new versions of the License from time to time. Each version - will be given a distinguishing version number. - - 6.2. Effect of New Versions. - Once Covered Code has been published under a particular version of the - License, You may always continue to use it under the terms of that - version. You may also choose to use such Covered Code under the terms - of any subsequent version of the License published by Netscape. No one - other than Netscape has the right to modify the terms applicable to - Covered Code created under this License. - - 6.3. Derivative Works. - If You create or use a modified version of this License (which you may - only do in order to apply it to code which is not already Covered Code - governed by this License), You must (a) rename Your license so that - the phrases "Mozilla", "MOZILLAPL", "MOZPL", "Netscape", - "MPL", "NPL" or any confusingly similar phrase do not appear in your - license (except to note that your license differs from this License) - and (b) otherwise make it clear that Your version of the license - contains terms which differ from the Mozilla Public License and - Netscape Public License. (Filling in the name of the Initial - Developer, Original Code or Contributor in the notice described in - Exhibit A shall not of themselves be deemed to be modifications of - this License.) - -7. DISCLAIMER OF WARRANTY. - - COVERED CODE IS PROVIDED UNDER THIS LICENSE ON AN "AS IS" BASIS, - WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, - WITHOUT LIMITATION, WARRANTIES THAT THE COVERED CODE IS FREE OF - DEFECTS, MERCHANTABLE, FIT FOR A PARTICULAR PURPOSE OR NON-INFRINGING. - THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE COVERED CODE - IS WITH YOU. SHOULD ANY COVERED CODE PROVE DEFECTIVE IN ANY RESPECT, - YOU (NOT THE INITIAL DEVELOPER OR ANY OTHER CONTRIBUTOR) ASSUME THE - COST OF ANY NECESSARY SERVICING, REPAIR OR CORRECTION. THIS DISCLAIMER - OF WARRANTY CONSTITUTES AN ESSENTIAL PART OF THIS LICENSE. NO USE OF - ANY COVERED CODE IS AUTHORIZED HEREUNDER EXCEPT UNDER THIS DISCLAIMER. - -8. TERMINATION. - - 8.1. This License and the rights granted hereunder will terminate - automatically if You fail to comply with terms herein and fail to cure - such breach within 30 days of becoming aware of the breach. All - sublicenses to the Covered Code which are properly granted shall - survive any termination of this License. Provisions which, by their - nature, must remain in effect beyond the termination of this License - shall survive. - - 8.2. If You initiate litigation by asserting a patent infringement - claim (excluding declatory judgment actions) against Initial Developer - or a Contributor (the Initial Developer or Contributor against whom - You file such action is referred to as "Participant") alleging that: - - (a) such Participant's Contributor Version directly or indirectly - infringes any patent, then any and all rights granted by such - Participant to You under Sections 2.1 and/or 2.2 of this License - shall, upon 60 days notice from Participant terminate prospectively, - unless if within 60 days after receipt of notice You either: (i) - agree in writing to pay Participant a mutually agreeable reasonable - royalty for Your past and future use of Modifications made by such - Participant, or (ii) withdraw Your litigation claim with respect to - the Contributor Version against such Participant. If within 60 days - of notice, a reasonable royalty and payment arrangement are not - mutually agreed upon in writing by the parties or the litigation claim - is not withdrawn, the rights granted by Participant to You under - Sections 2.1 and/or 2.2 automatically terminate at the expiration of - the 60 day notice period specified above. - - (b) any software, hardware, or device, other than such Participant's - Contributor Version, directly or indirectly infringes any patent, then - any rights granted to You by such Participant under Sections 2.1(b) - and 2.2(b) are revoked effective as of the date You first made, used, - sold, distributed, or had made, Modifications made by that - Participant. - - 8.3. If You assert a patent infringement claim against Participant - alleging that such Participant's Contributor Version directly or - indirectly infringes any patent where such claim is resolved (such as - by license or settlement) prior to the initiation of patent - infringement litigation, then the reasonable value of the licenses - granted by such Participant under Sections 2.1 or 2.2 shall be taken - into account in determining the amount or value of any payment or - license. - - 8.4. In the event of termination under Sections 8.1 or 8.2 above, - all end user license agreements (excluding distributors and resellers) - which have been validly granted by You or any distributor hereunder - prior to termination shall survive termination. - -9. LIMITATION OF LIABILITY. - - UNDER NO CIRCUMSTANCES AND UNDER NO LEGAL THEORY, WHETHER TORT - (INCLUDING NEGLIGENCE), CONTRACT, OR OTHERWISE, SHALL YOU, THE INITIAL - DEVELOPER, ANY OTHER CONTRIBUTOR, OR ANY DISTRIBUTOR OF COVERED CODE, - OR ANY SUPPLIER OF ANY OF SUCH PARTIES, BE LIABLE TO ANY PERSON FOR - ANY INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES OF ANY - CHARACTER INCLUDING, WITHOUT LIMITATION, DAMAGES FOR LOSS OF GOODWILL, - WORK STOPPAGE, COMPUTER FAILURE OR MALFUNCTION, OR ANY AND ALL OTHER - COMMERCIAL DAMAGES OR LOSSES, EVEN IF SUCH PARTY SHALL HAVE BEEN - INFORMED OF THE POSSIBILITY OF SUCH DAMAGES. THIS LIMITATION OF - LIABILITY SHALL NOT APPLY TO LIABILITY FOR DEATH OR PERSONAL INJURY - RESULTING FROM SUCH PARTY'S NEGLIGENCE TO THE EXTENT APPLICABLE LAW - PROHIBITS SUCH LIMITATION. SOME JURISDICTIONS DO NOT ALLOW THE - EXCLUSION OR LIMITATION OF INCIDENTAL OR CONSEQUENTIAL DAMAGES, SO - THIS EXCLUSION AND LIMITATION MAY NOT APPLY TO YOU. - -10. U.S. GOVERNMENT END USERS. - - The Covered Code is a "commercial item," as that term is defined in - 48 C.F.R. 2.101 (Oct. 1995), consisting of "commercial computer - software" and "commercial computer software documentation," as such - terms are used in 48 C.F.R. 12.212 (Sept. 1995). Consistent with 48 - C.F.R. 12.212 and 48 C.F.R. 227.7202-1 through 227.7202-4 (June 1995), - all U.S. Government End Users acquire Covered Code with only those - rights set forth herein. - -11. MISCELLANEOUS. - - This License represents the complete agreement concerning subject - matter hereof. If any provision of this License is held to be - unenforceable, such provision shall be reformed only to the extent - necessary to make it enforceable. This License shall be governed by - California law provisions (except to the extent applicable law, if - any, provides otherwise), excluding its conflict-of-law provisions. - With respect to disputes in which at least one party is a citizen of, - or an entity chartered or registered to do business in the United - States of America, any litigation relating to this License shall be - subject to the jurisdiction of the Federal Courts of the Northern - District of California, with venue lying in Santa Clara County, - California, with the losing party responsible for costs, including - without limitation, court costs and reasonable attorneys' fees and - expenses. The application of the United Nations Convention on - Contracts for the International Sale of Goods is expressly excluded. - Any law or regulation which provides that the language of a contract - shall be construed against the drafter shall not apply to this - License. - -12. RESPONSIBILITY FOR CLAIMS. - - As between Initial Developer and the Contributors, each party is - responsible for claims and damages arising, directly or indirectly, - out of its utilization of rights under this License and You agree to - work with Initial Developer and Contributors to distribute such - responsibility on an equitable basis. Nothing herein is intended or - shall be deemed to constitute any admission of liability. - -13. MULTIPLE-LICENSED CODE. - - Initial Developer may designate portions of the Covered Code as - "Multiple-Licensed". "Multiple-Licensed" means that the Initial - Developer permits you to utilize portions of the Covered Code under - Your choice of the MPL or the alternative licenses, if any, specified - by the Initial Developer in the file described in Exhibit A. - -EXHIBIT A -Mozilla Public License. - - ``The contents of this file are subject to the Mozilla Public License - Version 1.1 (the "License"); you may not use this file except in - compliance with the License. You may obtain a copy of the License at - https://www.mozilla.org/MPL/ - - Software distributed under the License is distributed on an "AS IS" - basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See the - License for the specific language governing rights and limitations - under the License. - - The Original Code is ______________________________________. - - The Initial Developer of the Original Code is ________________________. - Portions created by ______________________ are Copyright (C) ______ - _______________________. All Rights Reserved. - - Contributor(s): ______________________________________. - - Alternatively, the contents of this file may be used under the terms - of the _____ license (the "[___] License"), in which case the - provisions of [______] License are applicable instead of those - above. If you wish to allow use of your version of this file only - under the terms of the [____] License and not to allow others to use - your version of this file under the MPL, indicate your decision by - deleting the provisions above and replace them with the notice and - other provisions required by the [___] License. If you do not delete - the provisions above, a recipient may use your version of this file - under either the MPL or the [___] License." - - [NOTE: The text of this Exhibit A may differ slightly from the text of - the notices in the Source Code files of the Original Code. You should - use the text of this Exhibit A rather than the text found in the - Original Code Source Code for Your Modifications.] -- cgit v1.2.3 From 62be257e986dab439537b3e1c19ef746a13e1860 Mon Sep 17 00:00:00 2001 From: Christoph Hellwig Date: Tue, 30 Apr 2019 06:51:30 -0400 Subject: LICENSES: Rename other to deprecated Make it clear in the directory name that these are not intended for new code. Signed-off-by: Christoph Hellwig Reviewed-by: Greg Kroah-Hartman Signed-off-by: Jonathan Corbet --- Documentation/process/license-rules.rst | 8 +- LICENSES/deprecated/GPL-1.0 | 260 ++++++++++++++++++++++++++++++++ LICENSES/deprecated/ISC | 24 +++ LICENSES/deprecated/Linux-OpenIB | 26 ++++ LICENSES/deprecated/X11 | 37 +++++ LICENSES/other/GPL-1.0 | 260 -------------------------------- LICENSES/other/ISC | 24 --- LICENSES/other/Linux-OpenIB | 26 ---- LICENSES/other/X11 | 37 ----- 9 files changed, 351 insertions(+), 351 deletions(-) create mode 100644 LICENSES/deprecated/GPL-1.0 create mode 100644 LICENSES/deprecated/ISC create mode 100644 LICENSES/deprecated/Linux-OpenIB create mode 100644 LICENSES/deprecated/X11 delete mode 100644 LICENSES/other/GPL-1.0 delete mode 100644 LICENSES/other/ISC delete mode 100644 LICENSES/other/Linux-OpenIB delete mode 100644 LICENSES/other/X11 (limited to 'Documentation') diff --git a/Documentation/process/license-rules.rst b/Documentation/process/license-rules.rst index 507b695fa9da..2ef44ada3f11 100644 --- a/Documentation/process/license-rules.rst +++ b/Documentation/process/license-rules.rst @@ -234,13 +234,13 @@ kernel, can be broken down into: | -2. Not recommended licenses: +2. Deprecated licenses: These licenses should only be used for existing code or for importing code from a different project. These licenses are available from the directory:: - LICENSES/other/ + LICENSES/deprecated/ in the kernel source tree. @@ -250,12 +250,12 @@ kernel, can be broken down into: Examples:: - LICENSES/other/ISC + LICENSES/deprecated/ISC Contains the Internet Systems Consortium license text and the required metatags:: - LICENSES/other/GPL-1.0 + LICENSES/deprecated/GPL-1.0 Contains the GPL version 1 license text and the required metatags. diff --git a/LICENSES/deprecated/GPL-1.0 b/LICENSES/deprecated/GPL-1.0 new file mode 100644 index 000000000000..3a4fa969e4c2 --- /dev/null +++ b/LICENSES/deprecated/GPL-1.0 @@ -0,0 +1,260 @@ +Valid-License-Identifier: GPL-1.0+ +SPDX-URL: https://spdx.org/licenses/GPL-1.0.html +Usage-Guide: + The GNU General Public License (GPL) version 1 should not be used in new + code. For existing kernel code the 'or any later version' option is + required to be compatible with the general license of the project: GPLv2. + To use the license in source code, put the following SPDX tag/value pair + into a comment according to the placement guidelines in the licensing + rules documentation: + SPDX-License-Identifier: GPL-1.0+ +License-Text: + + GNU GENERAL PUBLIC LICENSE + Version 1, February 1989 + + Copyright (C) 1989 Free Software Foundation, Inc. + 675 Mass Ave, Cambridge, MA 02139, USA + Everyone is permitted to copy and distribute verbatim copies + of this license document, but changing it is not allowed. + + Preamble + + The license agreements of most software companies try to keep users +at the mercy of those companies. By contrast, our General Public +License is intended to guarantee your freedom to share and change free +software--to make sure the software is free for all its users. The +General Public License applies to the Free Software Foundation's +software and to any other program whose authors commit to using it. +You can use it for your programs, too. + + When we speak of free software, we are referring to freedom, not +price. Specifically, the General Public License is designed to make +sure that you have the freedom to give away or sell copies of free +software, that you receive source code or can get it if you want it, +that you can change the software or use pieces of it in new free +programs; and that you know you can do these things. + + To protect your rights, we need to make restrictions that forbid +anyone to deny you these rights or to ask you to surrender the rights. +These restrictions translate to certain responsibilities for you if you +distribute copies of the software, or if you modify it. + + For example, if you distribute copies of a such a program, whether +gratis or for a fee, you must give the recipients all the rights that +you have. You must make sure that they, too, receive or can get the +source code. And you must tell them their rights. + + We protect your rights with two steps: (1) copyright the software, and +(2) offer you this license which gives you legal permission to copy, +distribute and/or modify the software. + + Also, for each author's protection and ours, we want to make certain +that everyone understands that there is no warranty for this free +software. If the software is modified by someone else and passed on, we +want its recipients to know that what they have is not the original, so +that any problems introduced by others will not reflect on the original +authors' reputations. + + The precise terms and conditions for copying, distribution and +modification follow. + + GNU GENERAL PUBLIC LICENSE + TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION + + 0. This License Agreement applies to any program or other work which +contains a notice placed by the copyright holder saying it may be +distributed under the terms of this General Public License. The +"Program", below, refers to any such program or work, and a "work based +on the Program" means either the Program or any work containing the +Program or a portion of it, either verbatim or with modifications. Each +licensee is addressed as "you". + + 1. You may copy and distribute verbatim copies of the Program's source +code as you receive it, in any medium, provided that you conspicuously and +appropriately publish on each copy an appropriate copyright notice and +disclaimer of warranty; keep intact all the notices that refer to this +General Public License and to the absence of any warranty; and give any +other recipients of the Program a copy of this General Public License +along with the Program. You may charge a fee for the physical act of +transferring a copy. + + 2. You may modify your copy or copies of the Program or any portion of +it, and copy and distribute such modifications under the terms of Paragraph +1 above, provided that you also do the following: + + a) cause the modified files to carry prominent notices stating that + you changed the files and the date of any change; and + + b) cause the whole of any work that you distribute or publish, that + in whole or in part contains the Program or any part thereof, either + with or without modifications, to be licensed at no charge to all + third parties under the terms of this General Public License (except + that you may choose to grant warranty protection to some or all + third parties, at your option). + + c) If the modified program normally reads commands interactively when + run, you must cause it, when started running for such interactive use + in the simplest and most usual way, to print or display an + announcement including an appropriate copyright notice and a notice + that there is no warranty (or else, saying that you provide a + warranty) and that users may redistribute the program under these + conditions, and telling the user how to view a copy of this General + Public License. + + d) You may charge a fee for the physical act of transferring a + copy, and you may at your option offer warranty protection in + exchange for a fee. + +Mere aggregation of another independent work with the Program (or its +derivative) on a volume of a storage or distribution medium does not bring +the other work under the scope of these terms. + + 3. You may copy and distribute the Program (or a portion or derivative of +it, under Paragraph 2) in object code or executable form under the terms of +Paragraphs 1 and 2 above provided that you also do one of the following: + + a) accompany it with the complete corresponding machine-readable + source code, which must be distributed under the terms of + Paragraphs 1 and 2 above; or, + + b) accompany it with a written offer, valid for at least three + years, to give any third party free (except for a nominal charge + for the cost of distribution) a complete machine-readable copy of the + corresponding source code, to be distributed under the terms of + Paragraphs 1 and 2 above; or, + + c) accompany it with the information you received as to where the + corresponding source code may be obtained. (This alternative is + allowed only for noncommercial distribution and only if you + received the program in object code or executable form alone.) + +Source code for a work means the preferred form of the work for making +modifications to it. For an executable file, complete source code means +all the source code for all modules it contains; but, as a special +exception, it need not include source code for modules which are standard +libraries that accompany the operating system on which the executable +file runs, or for standard header files or definitions files that +accompany that operating system. + + 4. You may not copy, modify, sublicense, distribute or transfer the +Program except as expressly provided under this General Public License. +Any attempt otherwise to copy, modify, sublicense, distribute or transfer +the Program is void, and will automatically terminate your rights to use +the Program under this License. However, parties who have received +copies, or rights to use copies, from you under this General Public +License will not have their licenses terminated so long as such parties +remain in full compliance. + + 5. By copying, distributing or modifying the Program (or any work based +on the Program) you indicate your acceptance of this license to do so, +and all its terms and conditions. + + 6. Each time you redistribute the Program (or any work based on the +Program), the recipient automatically receives a license from the original +licensor to copy, distribute or modify the Program subject to these +terms and conditions. You may not impose any further restrictions on the +recipients' exercise of the rights granted herein. + + 7. The Free Software Foundation may publish revised and/or new versions +of the General Public License from time to time. Such new versions will +be similar in spirit to the present version, but may differ in detail to +address new problems or concerns. + +Each version is given a distinguishing version number. If the Program +specifies a version number of the license which applies to it and "any +later version", you have the option of following the terms and conditions +either of that version or of any later version published by the Free +Software Foundation. If the Program does not specify a version number of +the license, you may choose any version ever published by the Free Software +Foundation. + + 8. If you wish to incorporate parts of the Program into other free +programs whose distribution conditions are different, write to the author +to ask for permission. For software which is copyrighted by the Free +Software Foundation, write to the Free Software Foundation; we sometimes +make exceptions for this. Our decision will be guided by the two goals +of preserving the free status of all derivatives of our free software and +of promoting the sharing and reuse of software generally. + + NO WARRANTY + + 9. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY +FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN +OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES +PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED +OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF +MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS +TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE +PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, +REPAIR OR CORRECTION. + + 10. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING +WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR +REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, +INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING +OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED +TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY +YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER +PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE +POSSIBILITY OF SUCH DAMAGES. + + END OF TERMS AND CONDITIONS + + Appendix: How to Apply These Terms to Your New Programs + + If you develop a new program, and you want it to be of the greatest +possible use to humanity, the best way to achieve this is to make it +free software which everyone can redistribute and change under these +terms. + + To do so, attach the following notices to the program. It is safest to +attach them to the start of each source file to most effectively convey +the exclusion of warranty; and each file should have at least the +"copyright" line and a pointer to where the full notice is found. + + + Copyright (C) 19yy + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 1, or (at your option) + any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + +Also add information on how to contact you by electronic and paper mail. + +If the program is interactive, make it output a short notice like this +when it starts in an interactive mode: + + Gnomovision version 69, Copyright (C) 19xx name of author + Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'. + This is free software, and you are welcome to redistribute it + under certain conditions; type `show c' for details. + +The hypothetical commands `show w' and `show c' should show the +appropriate parts of the General Public License. Of course, the +commands you use may be called something other than `show w' and `show +c'; they could even be mouse-clicks or menu items--whatever suits your +program. + +You should also get your employer (if you work as a programmer) or your +school, if any, to sign a "copyright disclaimer" for the program, if +necessary. Here a sample; alter the names: + + Yoyodyne, Inc., hereby disclaims all copyright interest in the + program `Gnomovision' (a program to direct compilers to make passes + at assemblers) written by James Hacker. + + , 1 April 1989 + Ty Coon, President of Vice + +That's all there is to it! diff --git a/LICENSES/deprecated/ISC b/LICENSES/deprecated/ISC new file mode 100644 index 000000000000..8953c3142079 --- /dev/null +++ b/LICENSES/deprecated/ISC @@ -0,0 +1,24 @@ +Valid-License-Identifier: ISC +SPDX-URL: https://spdx.org/licenses/ISC.html +Usage-Guide: + To use the ISC License put the following SPDX tag/value pair into a + comment according to the placement guidelines in the licensing rules + documentation: + SPDX-License-Identifier: ISC +License-Text: + +ISC License + +Copyright (c) + +Permission to use, copy, modify, and/or distribute this software for any +purpose with or without fee is hereby granted, provided that the above +copyright notice and this permission notice appear in all copies. + +THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES +WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF +MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY +SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES +WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION +OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN +CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. diff --git a/LICENSES/deprecated/Linux-OpenIB b/LICENSES/deprecated/Linux-OpenIB new file mode 100644 index 000000000000..1ad85f6b3a89 --- /dev/null +++ b/LICENSES/deprecated/Linux-OpenIB @@ -0,0 +1,26 @@ +Valid-License-Identifier: Linux-OpenIB +SPDX-URL: https://spdx.org/licenses/Linux-OpenIB.html +Usage-Guide: + To use the Linux Kernel Variant of OpenIB.org license put the following + SPDX tag/value pair into a comment according to the placement guidelines + in the licensing rules documentation: + SPDX-License-Identifier: Linux-OpenIB +License-Text: + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are met: + + - Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + + - Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +DEALINGS IN THE SOFTWARE. diff --git a/LICENSES/deprecated/X11 b/LICENSES/deprecated/X11 new file mode 100644 index 000000000000..fe4353fd0000 --- /dev/null +++ b/LICENSES/deprecated/X11 @@ -0,0 +1,37 @@ +Valid-License-Identifier: X11 +SPDX-URL: https://spdx.org/licenses/X11.html +Usage-Guide: + To use the X11 put the following SPDX tag/value pair into a comment + according to the placement guidelines in the licensing rules + documentation: + SPDX-License-Identifier: X11 +License-Text: + + +X11 License + +Copyright (C) 1996 X Consortium + +Permission is hereby granted, free of charge, to any person obtaining a +copy of this software and associated documentation files (the "Software"), +to deal in the Software without restriction, including without limitation +the rights to use, copy, modify, merge, publish, distribute, sublicense, +and/or sell copies of the Software, and to permit persons to whom the +Software is furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +X CONSORTIUM BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER +IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN +CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + +Except as contained in this notice, the name of the X Consortium shall not +be used in advertising or otherwise to promote the sale, use or other +dealings in this Software without prior written authorization from the X +Consortium. + +X Window System is a trademark of X Consortium, Inc. diff --git a/LICENSES/other/GPL-1.0 b/LICENSES/other/GPL-1.0 deleted file mode 100644 index 3a4fa969e4c2..000000000000 --- a/LICENSES/other/GPL-1.0 +++ /dev/null @@ -1,260 +0,0 @@ -Valid-License-Identifier: GPL-1.0+ -SPDX-URL: https://spdx.org/licenses/GPL-1.0.html -Usage-Guide: - The GNU General Public License (GPL) version 1 should not be used in new - code. For existing kernel code the 'or any later version' option is - required to be compatible with the general license of the project: GPLv2. - To use the license in source code, put the following SPDX tag/value pair - into a comment according to the placement guidelines in the licensing - rules documentation: - SPDX-License-Identifier: GPL-1.0+ -License-Text: - - GNU GENERAL PUBLIC LICENSE - Version 1, February 1989 - - Copyright (C) 1989 Free Software Foundation, Inc. - 675 Mass Ave, Cambridge, MA 02139, USA - Everyone is permitted to copy and distribute verbatim copies - of this license document, but changing it is not allowed. - - Preamble - - The license agreements of most software companies try to keep users -at the mercy of those companies. By contrast, our General Public -License is intended to guarantee your freedom to share and change free -software--to make sure the software is free for all its users. The -General Public License applies to the Free Software Foundation's -software and to any other program whose authors commit to using it. -You can use it for your programs, too. - - When we speak of free software, we are referring to freedom, not -price. Specifically, the General Public License is designed to make -sure that you have the freedom to give away or sell copies of free -software, that you receive source code or can get it if you want it, -that you can change the software or use pieces of it in new free -programs; and that you know you can do these things. - - To protect your rights, we need to make restrictions that forbid -anyone to deny you these rights or to ask you to surrender the rights. -These restrictions translate to certain responsibilities for you if you -distribute copies of the software, or if you modify it. - - For example, if you distribute copies of a such a program, whether -gratis or for a fee, you must give the recipients all the rights that -you have. You must make sure that they, too, receive or can get the -source code. And you must tell them their rights. - - We protect your rights with two steps: (1) copyright the software, and -(2) offer you this license which gives you legal permission to copy, -distribute and/or modify the software. - - Also, for each author's protection and ours, we want to make certain -that everyone understands that there is no warranty for this free -software. If the software is modified by someone else and passed on, we -want its recipients to know that what they have is not the original, so -that any problems introduced by others will not reflect on the original -authors' reputations. - - The precise terms and conditions for copying, distribution and -modification follow. - - GNU GENERAL PUBLIC LICENSE - TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION - - 0. This License Agreement applies to any program or other work which -contains a notice placed by the copyright holder saying it may be -distributed under the terms of this General Public License. The -"Program", below, refers to any such program or work, and a "work based -on the Program" means either the Program or any work containing the -Program or a portion of it, either verbatim or with modifications. Each -licensee is addressed as "you". - - 1. You may copy and distribute verbatim copies of the Program's source -code as you receive it, in any medium, provided that you conspicuously and -appropriately publish on each copy an appropriate copyright notice and -disclaimer of warranty; keep intact all the notices that refer to this -General Public License and to the absence of any warranty; and give any -other recipients of the Program a copy of this General Public License -along with the Program. You may charge a fee for the physical act of -transferring a copy. - - 2. You may modify your copy or copies of the Program or any portion of -it, and copy and distribute such modifications under the terms of Paragraph -1 above, provided that you also do the following: - - a) cause the modified files to carry prominent notices stating that - you changed the files and the date of any change; and - - b) cause the whole of any work that you distribute or publish, that - in whole or in part contains the Program or any part thereof, either - with or without modifications, to be licensed at no charge to all - third parties under the terms of this General Public License (except - that you may choose to grant warranty protection to some or all - third parties, at your option). - - c) If the modified program normally reads commands interactively when - run, you must cause it, when started running for such interactive use - in the simplest and most usual way, to print or display an - announcement including an appropriate copyright notice and a notice - that there is no warranty (or else, saying that you provide a - warranty) and that users may redistribute the program under these - conditions, and telling the user how to view a copy of this General - Public License. - - d) You may charge a fee for the physical act of transferring a - copy, and you may at your option offer warranty protection in - exchange for a fee. - -Mere aggregation of another independent work with the Program (or its -derivative) on a volume of a storage or distribution medium does not bring -the other work under the scope of these terms. - - 3. You may copy and distribute the Program (or a portion or derivative of -it, under Paragraph 2) in object code or executable form under the terms of -Paragraphs 1 and 2 above provided that you also do one of the following: - - a) accompany it with the complete corresponding machine-readable - source code, which must be distributed under the terms of - Paragraphs 1 and 2 above; or, - - b) accompany it with a written offer, valid for at least three - years, to give any third party free (except for a nominal charge - for the cost of distribution) a complete machine-readable copy of the - corresponding source code, to be distributed under the terms of - Paragraphs 1 and 2 above; or, - - c) accompany it with the information you received as to where the - corresponding source code may be obtained. (This alternative is - allowed only for noncommercial distribution and only if you - received the program in object code or executable form alone.) - -Source code for a work means the preferred form of the work for making -modifications to it. For an executable file, complete source code means -all the source code for all modules it contains; but, as a special -exception, it need not include source code for modules which are standard -libraries that accompany the operating system on which the executable -file runs, or for standard header files or definitions files that -accompany that operating system. - - 4. You may not copy, modify, sublicense, distribute or transfer the -Program except as expressly provided under this General Public License. -Any attempt otherwise to copy, modify, sublicense, distribute or transfer -the Program is void, and will automatically terminate your rights to use -the Program under this License. However, parties who have received -copies, or rights to use copies, from you under this General Public -License will not have their licenses terminated so long as such parties -remain in full compliance. - - 5. By copying, distributing or modifying the Program (or any work based -on the Program) you indicate your acceptance of this license to do so, -and all its terms and conditions. - - 6. Each time you redistribute the Program (or any work based on the -Program), the recipient automatically receives a license from the original -licensor to copy, distribute or modify the Program subject to these -terms and conditions. You may not impose any further restrictions on the -recipients' exercise of the rights granted herein. - - 7. The Free Software Foundation may publish revised and/or new versions -of the General Public License from time to time. Such new versions will -be similar in spirit to the present version, but may differ in detail to -address new problems or concerns. - -Each version is given a distinguishing version number. If the Program -specifies a version number of the license which applies to it and "any -later version", you have the option of following the terms and conditions -either of that version or of any later version published by the Free -Software Foundation. If the Program does not specify a version number of -the license, you may choose any version ever published by the Free Software -Foundation. - - 8. If you wish to incorporate parts of the Program into other free -programs whose distribution conditions are different, write to the author -to ask for permission. For software which is copyrighted by the Free -Software Foundation, write to the Free Software Foundation; we sometimes -make exceptions for this. Our decision will be guided by the two goals -of preserving the free status of all derivatives of our free software and -of promoting the sharing and reuse of software generally. - - NO WARRANTY - - 9. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY -FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN -OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES -PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED -OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF -MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS -TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE -PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, -REPAIR OR CORRECTION. - - 10. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING -WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR -REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, -INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING -OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED -TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY -YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER -PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE -POSSIBILITY OF SUCH DAMAGES. - - END OF TERMS AND CONDITIONS - - Appendix: How to Apply These Terms to Your New Programs - - If you develop a new program, and you want it to be of the greatest -possible use to humanity, the best way to achieve this is to make it -free software which everyone can redistribute and change under these -terms. - - To do so, attach the following notices to the program. It is safest to -attach them to the start of each source file to most effectively convey -the exclusion of warranty; and each file should have at least the -"copyright" line and a pointer to where the full notice is found. - - - Copyright (C) 19yy - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 1, or (at your option) - any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - -Also add information on how to contact you by electronic and paper mail. - -If the program is interactive, make it output a short notice like this -when it starts in an interactive mode: - - Gnomovision version 69, Copyright (C) 19xx name of author - Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'. - This is free software, and you are welcome to redistribute it - under certain conditions; type `show c' for details. - -The hypothetical commands `show w' and `show c' should show the -appropriate parts of the General Public License. Of course, the -commands you use may be called something other than `show w' and `show -c'; they could even be mouse-clicks or menu items--whatever suits your -program. - -You should also get your employer (if you work as a programmer) or your -school, if any, to sign a "copyright disclaimer" for the program, if -necessary. Here a sample; alter the names: - - Yoyodyne, Inc., hereby disclaims all copyright interest in the - program `Gnomovision' (a program to direct compilers to make passes - at assemblers) written by James Hacker. - - , 1 April 1989 - Ty Coon, President of Vice - -That's all there is to it! diff --git a/LICENSES/other/ISC b/LICENSES/other/ISC deleted file mode 100644 index 8953c3142079..000000000000 --- a/LICENSES/other/ISC +++ /dev/null @@ -1,24 +0,0 @@ -Valid-License-Identifier: ISC -SPDX-URL: https://spdx.org/licenses/ISC.html -Usage-Guide: - To use the ISC License put the following SPDX tag/value pair into a - comment according to the placement guidelines in the licensing rules - documentation: - SPDX-License-Identifier: ISC -License-Text: - -ISC License - -Copyright (c) - -Permission to use, copy, modify, and/or distribute this software for any -purpose with or without fee is hereby granted, provided that the above -copyright notice and this permission notice appear in all copies. - -THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES -WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF -MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY -SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES -WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION -OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN -CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. diff --git a/LICENSES/other/Linux-OpenIB b/LICENSES/other/Linux-OpenIB deleted file mode 100644 index 1ad85f6b3a89..000000000000 --- a/LICENSES/other/Linux-OpenIB +++ /dev/null @@ -1,26 +0,0 @@ -Valid-License-Identifier: Linux-OpenIB -SPDX-URL: https://spdx.org/licenses/Linux-OpenIB.html -Usage-Guide: - To use the Linux Kernel Variant of OpenIB.org license put the following - SPDX tag/value pair into a comment according to the placement guidelines - in the licensing rules documentation: - SPDX-License-Identifier: Linux-OpenIB -License-Text: - -Redistribution and use in source and binary forms, with or without -modification, are permitted provided that the following conditions are met: - - - Redistributions of source code must retain the above copyright - notice, this list of conditions and the following disclaimer. - - - Redistributions in binary form must reproduce the above copyright - notice, this list of conditions and the following disclaimer in the - documentation and/or other materials provided with the distribution. - -THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE -AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER -LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING -FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER -DEALINGS IN THE SOFTWARE. diff --git a/LICENSES/other/X11 b/LICENSES/other/X11 deleted file mode 100644 index fe4353fd0000..000000000000 --- a/LICENSES/other/X11 +++ /dev/null @@ -1,37 +0,0 @@ -Valid-License-Identifier: X11 -SPDX-URL: https://spdx.org/licenses/X11.html -Usage-Guide: - To use the X11 put the following SPDX tag/value pair into a comment - according to the placement guidelines in the licensing rules - documentation: - SPDX-License-Identifier: X11 -License-Text: - - -X11 License - -Copyright (C) 1996 X Consortium - -Permission is hereby granted, free of charge, to any person obtaining a -copy of this software and associated documentation files (the "Software"), -to deal in the Software without restriction, including without limitation -the rights to use, copy, modify, merge, publish, distribute, sublicense, -and/or sell copies of the Software, and to permit persons to whom the -Software is furnished to do so, subject to the following conditions: - -The above copyright notice and this permission notice shall be included in -all copies or substantial portions of the Software. - -THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE -X CONSORTIUM BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER -IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN -CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. - -Except as contained in this notice, the name of the X Consortium shall not -be used in advertising or otherwise to promote the sale, use or other -dealings in this Software without prior written authorization from the X -Consortium. - -X Window System is a trademark of X Consortium, Inc. -- cgit v1.2.3 From 04fdd5dd79a9012dad7b0e6ba676c5a61ca592e4 Mon Sep 17 00:00:00 2001 From: Harish Bandi Date: Fri, 26 Apr 2019 19:26:02 +0530 Subject: dt-bindings: net: bluetooth: Add device tree bindings for QTI chip WCN3998 Add compatible string for the Qualcomm WCN3998 Bluetooth controller Signed-off-by: Harish Bandi Reviewed-by: Rob Herring Signed-off-by: Marcel Holtmann --- Documentation/devicetree/bindings/net/qualcomm-bluetooth.txt | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/net/qualcomm-bluetooth.txt b/Documentation/devicetree/bindings/net/qualcomm-bluetooth.txt index 824c0e23c544..7ef6118abd3d 100644 --- a/Documentation/devicetree/bindings/net/qualcomm-bluetooth.txt +++ b/Documentation/devicetree/bindings/net/qualcomm-bluetooth.txt @@ -11,20 +11,21 @@ Required properties: - compatible: should contain one of the following: * "qcom,qca6174-bt" * "qcom,wcn3990-bt" + * "qcom,wcn3998-bt" Optional properties for compatible string qcom,qca6174-bt: - enable-gpios: gpio specifier used to enable chip - clocks: clock provided to the controller (SUSCLK_32KHZ) -Required properties for compatible string qcom,wcn3990-bt: +Required properties for compatible string qcom,wcn399x-bt: - vddio-supply: VDD_IO supply regulator handle. - vddxo-supply: VDD_XO supply regulator handle. - vddrf-supply: VDD_RF supply regulator handle. - vddch0-supply: VDD_CH0 supply regulator handle. -Optional properties for compatible string qcom,wcn3990-bt: +Optional properties for compatible string qcom,wcn399x-bt: - max-speed: see Documentation/devicetree/bindings/serial/slave-device.txt -- cgit v1.2.3 From 24beb83ad289c68bce7c01351cb90465bbb1940a Mon Sep 17 00:00:00 2001 From: Pu Wen Date: Tue, 30 Apr 2019 00:08:43 +0800 Subject: i2c-piix4: Add Hygon Dhyana SMBus support The Hygon Dhyana CPU has the SMBus device with PCI device ID 0x790b, which is the same as AMD CZ SMBus device. So add Hygon Dhyana support to the i2c-piix4 driver by using the code path of AMD. Signed-off-by: Pu Wen Reviewed-by: Jean Delvare Signed-off-by: Wolfram Sang --- Documentation/i2c/busses/i2c-piix4 | 2 ++ drivers/i2c/busses/Kconfig | 1 + drivers/i2c/busses/i2c-piix4.c | 15 +++++++++++---- 3 files changed, 14 insertions(+), 4 deletions(-) (limited to 'Documentation') diff --git a/Documentation/i2c/busses/i2c-piix4 b/Documentation/i2c/busses/i2c-piix4 index aa959fd22450..2703bc3acad0 100644 --- a/Documentation/i2c/busses/i2c-piix4 +++ b/Documentation/i2c/busses/i2c-piix4 @@ -15,6 +15,8 @@ Supported adapters: http://support.amd.com/us/Embedded_TechDocs/44413.pdf * AMD Hudson-2, ML, CZ Datasheet: Not publicly available + * Hygon CZ + Datasheet: Not publicly available * Standard Microsystems (SMSC) SLC90E66 (Victory66) southbridge Datasheet: Publicly available at the SMSC website http://www.smsc.com diff --git a/drivers/i2c/busses/Kconfig b/drivers/i2c/busses/Kconfig index 977161bb7062..26186439db6b 100644 --- a/drivers/i2c/busses/Kconfig +++ b/drivers/i2c/busses/Kconfig @@ -186,6 +186,7 @@ config I2C_PIIX4 AMD Hudson-2 AMD ML AMD CZ + Hygon CZ Serverworks OSB4 Serverworks CSB5 Serverworks CSB6 diff --git a/drivers/i2c/busses/i2c-piix4.c b/drivers/i2c/busses/i2c-piix4.c index 90946a8b9a75..e9a0514ae166 100644 --- a/drivers/i2c/busses/i2c-piix4.c +++ b/drivers/i2c/busses/i2c-piix4.c @@ -19,6 +19,7 @@ Serverworks OSB4, CSB5, CSB6, HT-1000, HT-1100 ATI IXP200, IXP300, IXP400, SB600, SB700/SP5100, SB800 AMD Hudson-2, ML, CZ + Hygon CZ SMSC Victory66 Note: we assume there can only be one device, with one or more @@ -289,7 +290,9 @@ static int piix4_setup_sb800(struct pci_dev *PIIX4_dev, PIIX4_dev->revision >= 0x41) || (PIIX4_dev->vendor == PCI_VENDOR_ID_AMD && PIIX4_dev->device == PCI_DEVICE_ID_AMD_KERNCZ_SMBUS && - PIIX4_dev->revision >= 0x49)) + PIIX4_dev->revision >= 0x49) || + (PIIX4_dev->vendor == PCI_VENDOR_ID_HYGON && + PIIX4_dev->device == PCI_DEVICE_ID_AMD_KERNCZ_SMBUS)) smb_en = 0x00; else smb_en = (aux) ? 0x28 : 0x2c; @@ -361,7 +364,8 @@ static int piix4_setup_sb800(struct pci_dev *PIIX4_dev, piix4_smba, i2ccfg >> 4); /* Find which register is used for port selection */ - if (PIIX4_dev->vendor == PCI_VENDOR_ID_AMD) { + if (PIIX4_dev->vendor == PCI_VENDOR_ID_AMD || + PIIX4_dev->vendor == PCI_VENDOR_ID_HYGON) { switch (PIIX4_dev->device) { case PCI_DEVICE_ID_AMD_KERNCZ_SMBUS: piix4_port_sel_sb800 = SB800_PIIX4_PORT_IDX_KERNCZ; @@ -794,6 +798,7 @@ static const struct pci_device_id piix4_ids[] = { { PCI_DEVICE(PCI_VENDOR_ID_ATI, PCI_DEVICE_ID_ATI_SBX00_SMBUS) }, { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_HUDSON2_SMBUS) }, { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_KERNCZ_SMBUS) }, + { PCI_DEVICE(PCI_VENDOR_ID_HYGON, PCI_DEVICE_ID_AMD_KERNCZ_SMBUS) }, { PCI_DEVICE(PCI_VENDOR_ID_SERVERWORKS, PCI_DEVICE_ID_SERVERWORKS_OSB4) }, { PCI_DEVICE(PCI_VENDOR_ID_SERVERWORKS, @@ -904,11 +909,13 @@ static int piix4_probe(struct pci_dev *dev, const struct pci_device_id *id) if ((dev->vendor == PCI_VENDOR_ID_ATI && dev->device == PCI_DEVICE_ID_ATI_SBX00_SMBUS && dev->revision >= 0x40) || - dev->vendor == PCI_VENDOR_ID_AMD) { + dev->vendor == PCI_VENDOR_ID_AMD || + dev->vendor == PCI_VENDOR_ID_HYGON) { bool notify_imc = false; is_sb800 = true; - if (dev->vendor == PCI_VENDOR_ID_AMD && + if ((dev->vendor == PCI_VENDOR_ID_AMD || + dev->vendor == PCI_VENDOR_ID_HYGON) && dev->device == PCI_DEVICE_ID_AMD_KERNCZ_SMBUS) { u8 imc; -- cgit v1.2.3 From 554aae35007e49f533d3d10e788295f7141725bc Mon Sep 17 00:00:00 2001 From: Vladimir Oltean Date: Thu, 2 May 2019 23:23:29 +0300 Subject: lib: Add support for generic packing operations This provides an unified API for accessing register bit fields regardless of memory layout. The basic unit of data for these API functions is the u64. The process of transforming an u64 from native CPU encoding into the peripheral's encoding is called 'pack', and transforming it from peripheral to native CPU encoding is 'unpack'. Signed-off-by: Vladimir Oltean Signed-off-by: David S. Miller --- Documentation/packing.txt | 149 ++++++++++++++++++++++++++++++++ MAINTAINERS | 8 ++ include/linux/packing.h | 49 +++++++++++ lib/Kconfig | 17 ++++ lib/Makefile | 1 + lib/packing.c | 213 ++++++++++++++++++++++++++++++++++++++++++++++ 6 files changed, 437 insertions(+) create mode 100644 Documentation/packing.txt create mode 100644 include/linux/packing.h create mode 100644 lib/packing.c (limited to 'Documentation') diff --git a/Documentation/packing.txt b/Documentation/packing.txt new file mode 100644 index 000000000000..f830c98645f1 --- /dev/null +++ b/Documentation/packing.txt @@ -0,0 +1,149 @@ +================================================ +Generic bitfield packing and unpacking functions +================================================ + +Problem statement +----------------- + +When working with hardware, one has to choose between several approaches of +interfacing with it. +One can memory-map a pointer to a carefully crafted struct over the hardware +device's memory region, and access its fields as struct members (potentially +declared as bitfields). But writing code this way would make it less portable, +due to potential endianness mismatches between the CPU and the hardware device. +Additionally, one has to pay close attention when translating register +definitions from the hardware documentation into bit field indices for the +structs. Also, some hardware (typically networking equipment) tends to group +its register fields in ways that violate any reasonable word boundaries +(sometimes even 64 bit ones). This creates the inconvenience of having to +define "high" and "low" portions of register fields within the struct. +A more robust alternative to struct field definitions would be to extract the +required fields by shifting the appropriate number of bits. But this would +still not protect from endianness mismatches, except if all memory accesses +were performed byte-by-byte. Also the code can easily get cluttered, and the +high-level idea might get lost among the many bit shifts required. +Many drivers take the bit-shifting approach and then attempt to reduce the +clutter with tailored macros, but more often than not these macros take +shortcuts that still prevent the code from being truly portable. + +The solution +------------ + +This API deals with 2 basic operations: + - Packing a CPU-usable number into a memory buffer (with hardware + constraints/quirks) + - Unpacking a memory buffer (which has hardware constraints/quirks) + into a CPU-usable number. + +The API offers an abstraction over said hardware constraints and quirks, +over CPU endianness and therefore between possible mismatches between +the two. + +The basic unit of these API functions is the u64. From the CPU's +perspective, bit 63 always means bit offset 7 of byte 7, albeit only +logically. The question is: where do we lay this bit out in memory? + +The following examples cover the memory layout of a packed u64 field. +The byte offsets in the packed buffer are always implicitly 0, 1, ... 7. +What the examples show is where the logical bytes and bits sit. + +1. Normally (no quirks), we would do it like this: + +63 62 61 60 59 58 57 56 55 54 53 52 51 50 49 48 47 46 45 44 43 42 41 40 39 38 37 36 35 34 33 32 +7 6 5 4 +31 30 29 28 27 26 25 24 23 22 21 20 19 18 17 16 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0 +3 2 1 0 + +That is, the MSByte (7) of the CPU-usable u64 sits at memory offset 0, and the +LSByte (0) of the u64 sits at memory offset 7. +This corresponds to what most folks would regard to as "big endian", where +bit i corresponds to the number 2^i. This is also referred to in the code +comments as "logical" notation. + + +2. If QUIRK_MSB_ON_THE_RIGHT is set, we do it like this: + +56 57 58 59 60 61 62 63 48 49 50 51 52 53 54 55 40 41 42 43 44 45 46 47 32 33 34 35 36 37 38 39 +7 6 5 4 +24 25 26 27 28 29 30 31 16 17 18 19 20 21 22 23 8 9 10 11 12 13 14 15 0 1 2 3 4 5 6 7 +3 2 1 0 + +That is, QUIRK_MSB_ON_THE_RIGHT does not affect byte positioning, but +inverts bit offsets inside a byte. + + +3. If QUIRK_LITTLE_ENDIAN is set, we do it like this: + +39 38 37 36 35 34 33 32 47 46 45 44 43 42 41 40 55 54 53 52 51 50 49 48 63 62 61 60 59 58 57 56 +4 5 6 7 +7 6 5 4 3 2 1 0 15 14 13 12 11 10 9 8 23 22 21 20 19 18 17 16 31 30 29 28 27 26 25 24 +0 1 2 3 + +Therefore, QUIRK_LITTLE_ENDIAN means that inside the memory region, every +byte from each 4-byte word is placed at its mirrored position compared to +the boundary of that word. + +4. If QUIRK_MSB_ON_THE_RIGHT and QUIRK_LITTLE_ENDIAN are both set, we do it + like this: + +32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 +4 5 6 7 +0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 +0 1 2 3 + + +5. If just QUIRK_LSW32_IS_FIRST is set, we do it like this: + +31 30 29 28 27 26 25 24 23 22 21 20 19 18 17 16 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0 +3 2 1 0 +63 62 61 60 59 58 57 56 55 54 53 52 51 50 49 48 47 46 45 44 43 42 41 40 39 38 37 36 35 34 33 32 +7 6 5 4 + +In this case the 8 byte memory region is interpreted as follows: first +4 bytes correspond to the least significant 4-byte word, next 4 bytes to +the more significant 4-byte word. + + +6. If QUIRK_LSW32_IS_FIRST and QUIRK_MSB_ON_THE_RIGHT are set, we do it like + this: + +24 25 26 27 28 29 30 31 16 17 18 19 20 21 22 23 8 9 10 11 12 13 14 15 0 1 2 3 4 5 6 7 +3 2 1 0 +56 57 58 59 60 61 62 63 48 49 50 51 52 53 54 55 40 41 42 43 44 45 46 47 32 33 34 35 36 37 38 39 +7 6 5 4 + + +7. If QUIRK_LSW32_IS_FIRST and QUIRK_LITTLE_ENDIAN are set, it looks like + this: + +7 6 5 4 3 2 1 0 15 14 13 12 11 10 9 8 23 22 21 20 19 18 17 16 31 30 29 28 27 26 25 24 +0 1 2 3 +39 38 37 36 35 34 33 32 47 46 45 44 43 42 41 40 55 54 53 52 51 50 49 48 63 62 61 60 59 58 57 56 +4 5 6 7 + + +8. If QUIRK_LSW32_IS_FIRST, QUIRK_LITTLE_ENDIAN and QUIRK_MSB_ON_THE_RIGHT + are set, it looks like this: + +0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 +0 1 2 3 +32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 +4 5 6 7 + + +We always think of our offsets as if there were no quirk, and we translate +them afterwards, before accessing the memory region. + +Intended use +------------ + +Drivers that opt to use this API first need to identify which of the above 3 +quirk combinations (for a total of 8) match what the hardware documentation +describes. Then they should wrap the packing() function, creating a new +xxx_packing() that calls it using the proper QUIRK_* one-hot bits set. + +The packing() function returns an int-encoded error code, which protects the +programmer against incorrect API use. The errors are not expected to occur +durring runtime, therefore it is reasonable for xxx_packing() to return void +and simply swallow those errors. Optionally it can dump stack or print the +error description. diff --git a/MAINTAINERS b/MAINTAINERS index 0af66fa919a8..ff029f3d0f13 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -11673,6 +11673,14 @@ L: linux-i2c@vger.kernel.org S: Orphan F: drivers/i2c/busses/i2c-pasemi.c +PACKING +M: Vladimir Oltean +L: netdev@vger.kernel.org +S: Supported +F: lib/packing.c +F: include/linux/packing.h +F: Documentation/packing.txt + PADATA PARALLEL EXECUTION MECHANISM M: Steffen Klassert L: linux-crypto@vger.kernel.org diff --git a/include/linux/packing.h b/include/linux/packing.h new file mode 100644 index 000000000000..54667735cc67 --- /dev/null +++ b/include/linux/packing.h @@ -0,0 +1,49 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright (c) 2016-2018, NXP Semiconductors + * Copyright (c) 2018-2019, Vladimir Oltean + */ +#ifndef _LINUX_PACKING_H +#define _LINUX_PACKING_H + +#include +#include + +#define QUIRK_MSB_ON_THE_RIGHT BIT(0) +#define QUIRK_LITTLE_ENDIAN BIT(1) +#define QUIRK_LSW32_IS_FIRST BIT(2) + +enum packing_op { + PACK, + UNPACK, +}; + +/** + * packing - Convert numbers (currently u64) between a packed and an unpacked + * format. Unpacked means laid out in memory in the CPU's native + * understanding of integers, while packed means anything else that + * requires translation. + * + * @pbuf: Pointer to a buffer holding the packed value. + * @uval: Pointer to an u64 holding the unpacked value. + * @startbit: The index (in logical notation, compensated for quirks) where + * the packed value starts within pbuf. Must be larger than, or + * equal to, endbit. + * @endbit: The index (in logical notation, compensated for quirks) where + * the packed value ends within pbuf. Must be smaller than, or equal + * to, startbit. + * @op: If PACK, then uval will be treated as const pointer and copied (packed) + * into pbuf, between startbit and endbit. + * If UNPACK, then pbuf will be treated as const pointer and the logical + * value between startbit and endbit will be copied (unpacked) to uval. + * @quirks: A bit mask of QUIRK_LITTLE_ENDIAN, QUIRK_LSW32_IS_FIRST and + * QUIRK_MSB_ON_THE_RIGHT. + * + * Return: 0 on success, EINVAL or ERANGE if called incorrectly. Assuming + * correct usage, return code may be discarded. + * If op is PACK, pbuf is modified. + * If op is UNPACK, uval is modified. + */ +int packing(void *pbuf, u64 *uval, int startbit, int endbit, size_t pbuflen, + enum packing_op op, u8 quirks); + +#endif diff --git a/lib/Kconfig b/lib/Kconfig index a9e56539bd11..ac1fcf06d8ea 100644 --- a/lib/Kconfig +++ b/lib/Kconfig @@ -18,6 +18,23 @@ config RAID6_PQ_BENCHMARK Benchmark all available RAID6 PQ functions on init and choose the fastest one. +config PACKING + bool "Generic bitfield packing and unpacking" + default n + help + This option provides the packing() helper function, which permits + converting bitfields between a CPU-usable representation and a + memory representation that can have any combination of these quirks: + - Is little endian (bytes are reversed within a 32-bit group) + - The least-significant 32-bit word comes first (within a 64-bit + group) + - The most significant bit of a byte is at its right (bit 0 of a + register description is numerically 2^7). + Drivers may use these helpers to match the bit indices as described + in the data sheets of the peripherals they are in control of. + + When in doubt, say N. + config BITREVERSE tristate diff --git a/lib/Makefile b/lib/Makefile index 3b08673e8881..7d4db18fabf1 100644 --- a/lib/Makefile +++ b/lib/Makefile @@ -108,6 +108,7 @@ obj-$(CONFIG_DEBUG_LIST) += list_debug.o obj-$(CONFIG_DEBUG_OBJECTS) += debugobjects.o obj-$(CONFIG_BITREVERSE) += bitrev.o +obj-$(CONFIG_PACKING) += packing.o obj-$(CONFIG_RATIONAL) += rational.o obj-$(CONFIG_CRC_CCITT) += crc-ccitt.o obj-$(CONFIG_CRC16) += crc16.o diff --git a/lib/packing.c b/lib/packing.c new file mode 100644 index 000000000000..50d1e9f2f5a7 --- /dev/null +++ b/lib/packing.c @@ -0,0 +1,213 @@ +// SPDX-License-Identifier: BSD-3-Clause OR GPL-2.0 +/* Copyright (c) 2016-2018, NXP Semiconductors + * Copyright (c) 2018-2019, Vladimir Oltean + */ +#include +#include +#include +#include +#include + +static int get_le_offset(int offset) +{ + int closest_multiple_of_4; + + closest_multiple_of_4 = (offset / 4) * 4; + offset -= closest_multiple_of_4; + return closest_multiple_of_4 + (3 - offset); +} + +static int get_reverse_lsw32_offset(int offset, size_t len) +{ + int closest_multiple_of_4; + int word_index; + + word_index = offset / 4; + closest_multiple_of_4 = word_index * 4; + offset -= closest_multiple_of_4; + word_index = (len / 4) - word_index - 1; + return word_index * 4 + offset; +} + +static u64 bit_reverse(u64 val, unsigned int width) +{ + u64 new_val = 0; + unsigned int bit; + unsigned int i; + + for (i = 0; i < width; i++) { + bit = (val & (1 << i)) != 0; + new_val |= (bit << (width - i - 1)); + } + return new_val; +} + +static void adjust_for_msb_right_quirk(u64 *to_write, int *box_start_bit, + int *box_end_bit, u8 *box_mask) +{ + int box_bit_width = *box_start_bit - *box_end_bit + 1; + int new_box_start_bit, new_box_end_bit; + + *to_write >>= *box_end_bit; + *to_write = bit_reverse(*to_write, box_bit_width); + *to_write <<= *box_end_bit; + + new_box_end_bit = box_bit_width - *box_start_bit - 1; + new_box_start_bit = box_bit_width - *box_end_bit - 1; + *box_mask = GENMASK_ULL(new_box_start_bit, new_box_end_bit); + *box_start_bit = new_box_start_bit; + *box_end_bit = new_box_end_bit; +} + +/** + * packing - Convert numbers (currently u64) between a packed and an unpacked + * format. Unpacked means laid out in memory in the CPU's native + * understanding of integers, while packed means anything else that + * requires translation. + * + * @pbuf: Pointer to a buffer holding the packed value. + * @uval: Pointer to an u64 holding the unpacked value. + * @startbit: The index (in logical notation, compensated for quirks) where + * the packed value starts within pbuf. Must be larger than, or + * equal to, endbit. + * @endbit: The index (in logical notation, compensated for quirks) where + * the packed value ends within pbuf. Must be smaller than, or equal + * to, startbit. + * @op: If PACK, then uval will be treated as const pointer and copied (packed) + * into pbuf, between startbit and endbit. + * If UNPACK, then pbuf will be treated as const pointer and the logical + * value between startbit and endbit will be copied (unpacked) to uval. + * @quirks: A bit mask of QUIRK_LITTLE_ENDIAN, QUIRK_LSW32_IS_FIRST and + * QUIRK_MSB_ON_THE_RIGHT. + * + * Return: 0 on success, EINVAL or ERANGE if called incorrectly. Assuming + * correct usage, return code may be discarded. + * If op is PACK, pbuf is modified. + * If op is UNPACK, uval is modified. + */ +int packing(void *pbuf, u64 *uval, int startbit, int endbit, size_t pbuflen, + enum packing_op op, u8 quirks) +{ + /* Number of bits for storing "uval" + * also width of the field to access in the pbuf + */ + u64 value_width; + /* Logical byte indices corresponding to the + * start and end of the field. + */ + int plogical_first_u8, plogical_last_u8, box; + + /* startbit is expected to be larger than endbit */ + if (startbit < endbit) + /* Invalid function call */ + return -EINVAL; + + value_width = startbit - endbit + 1; + if (value_width > 64) + return -ERANGE; + + /* Check if "uval" fits in "value_width" bits. + * If value_width is 64, the check will fail, but any + * 64-bit uval will surely fit. + */ + if (op == PACK && value_width < 64 && (*uval >= (1ull << value_width))) + /* Cannot store "uval" inside "value_width" bits. + * Truncating "uval" is most certainly not desirable, + * so simply erroring out is appropriate. + */ + return -ERANGE; + + /* Initialize parameter */ + if (op == UNPACK) + *uval = 0; + + /* Iterate through an idealistic view of the pbuf as an u64 with + * no quirks, u8 by u8 (aligned at u8 boundaries), from high to low + * logical bit significance. "box" denotes the current logical u8. + */ + plogical_first_u8 = startbit / 8; + plogical_last_u8 = endbit / 8; + + for (box = plogical_first_u8; box >= plogical_last_u8; box--) { + /* Bit indices into the currently accessed 8-bit box */ + int box_start_bit, box_end_bit, box_addr; + u8 box_mask; + /* Corresponding bits from the unpacked u64 parameter */ + int proj_start_bit, proj_end_bit; + u64 proj_mask; + + /* This u8 may need to be accessed in its entirety + * (from bit 7 to bit 0), or not, depending on the + * input arguments startbit and endbit. + */ + if (box == plogical_first_u8) + box_start_bit = startbit % 8; + else + box_start_bit = 7; + if (box == plogical_last_u8) + box_end_bit = endbit % 8; + else + box_end_bit = 0; + + /* We have determined the box bit start and end. + * Now we calculate where this (masked) u8 box would fit + * in the unpacked (CPU-readable) u64 - the u8 box's + * projection onto the unpacked u64. Though the + * box is u8, the projection is u64 because it may fall + * anywhere within the unpacked u64. + */ + proj_start_bit = ((box * 8) + box_start_bit) - endbit; + proj_end_bit = ((box * 8) + box_end_bit) - endbit; + proj_mask = GENMASK_ULL(proj_start_bit, proj_end_bit); + box_mask = GENMASK_ULL(box_start_bit, box_end_bit); + + /* Determine the offset of the u8 box inside the pbuf, + * adjusted for quirks. The adjusted box_addr will be used for + * effective addressing inside the pbuf (so it's not + * logical any longer). + */ + box_addr = pbuflen - box - 1; + if (quirks & QUIRK_LITTLE_ENDIAN) + box_addr = get_le_offset(box_addr); + if (quirks & QUIRK_LSW32_IS_FIRST) + box_addr = get_reverse_lsw32_offset(box_addr, + pbuflen); + + if (op == UNPACK) { + u64 pval; + + /* Read from pbuf, write to uval */ + pval = ((u8 *)pbuf)[box_addr] & box_mask; + if (quirks & QUIRK_MSB_ON_THE_RIGHT) + adjust_for_msb_right_quirk(&pval, + &box_start_bit, + &box_end_bit, + &box_mask); + + pval >>= box_end_bit; + pval <<= proj_end_bit; + *uval &= ~proj_mask; + *uval |= pval; + } else { + u64 pval; + + /* Write to pbuf, read from uval */ + pval = (*uval) & proj_mask; + pval >>= proj_end_bit; + if (quirks & QUIRK_MSB_ON_THE_RIGHT) + adjust_for_msb_right_quirk(&pval, + &box_start_bit, + &box_end_bit, + &box_mask); + + pval <<= box_end_bit; + ((u8 *)pbuf)[box_addr] &= ~box_mask; + ((u8 *)pbuf)[box_addr] |= pval; + } + } + return 0; +} +EXPORT_SYMBOL(packing); + +MODULE_LICENSE("GPL v2"); +MODULE_DESCRIPTION("Generic bitfield packing and unpacking"); -- cgit v1.2.3 From 4759209732d3f4657f65720e624fdd73419f7134 Mon Sep 17 00:00:00 2001 From: Vladimir Oltean Date: Thu, 2 May 2019 23:23:39 +0300 Subject: Documentation: net: dsa: Add details about NXP SJA1105 driver Signed-off-by: Vladimir Oltean Signed-off-by: David S. Miller --- Documentation/networking/dsa/index.rst | 1 + Documentation/networking/dsa/sja1105.rst | 166 +++++++++++++++++++++++++++++++ 2 files changed, 167 insertions(+) create mode 100644 Documentation/networking/dsa/sja1105.rst (limited to 'Documentation') diff --git a/Documentation/networking/dsa/index.rst b/Documentation/networking/dsa/index.rst index 5c488d345a1e..0e5b7a9be406 100644 --- a/Documentation/networking/dsa/index.rst +++ b/Documentation/networking/dsa/index.rst @@ -8,3 +8,4 @@ Distributed Switch Architecture dsa bcm_sf2 lan9303 + sja1105 diff --git a/Documentation/networking/dsa/sja1105.rst b/Documentation/networking/dsa/sja1105.rst new file mode 100644 index 000000000000..7c13b40915c0 --- /dev/null +++ b/Documentation/networking/dsa/sja1105.rst @@ -0,0 +1,166 @@ +========================= +NXP SJA1105 switch driver +========================= + +Overview +======== + +The NXP SJA1105 is a family of 6 devices: + +- SJA1105E: First generation, no TTEthernet +- SJA1105T: First generation, TTEthernet +- SJA1105P: Second generation, no TTEthernet, no SGMII +- SJA1105Q: Second generation, TTEthernet, no SGMII +- SJA1105R: Second generation, no TTEthernet, SGMII +- SJA1105S: Second generation, TTEthernet, SGMII + +These are SPI-managed automotive switches, with all ports being gigabit +capable, and supporting MII/RMII/RGMII and optionally SGMII on one port. + +Being automotive parts, their configuration interface is geared towards +set-and-forget use, with minimal dynamic interaction at runtime. They +require a static configuration to be composed by software and packed +with CRC and table headers, and sent over SPI. + +The static configuration is composed of several configuration tables. Each +table takes a number of entries. Some configuration tables can be (partially) +reconfigured at runtime, some not. Some tables are mandatory, some not: + +============================= ================== ============================= +Table Mandatory Reconfigurable +============================= ================== ============================= +Schedule no no +Schedule entry points if Scheduling no +VL Lookup no no +VL Policing if VL Lookup no +VL Forwarding if VL Lookup no +L2 Lookup no no +L2 Policing yes no +VLAN Lookup yes yes +L2 Forwarding yes partially (fully on P/Q/R/S) +MAC Config yes partially (fully on P/Q/R/S) +Schedule Params if Scheduling no +Schedule Entry Points Params if Scheduling no +VL Forwarding Params if VL Forwarding no +L2 Lookup Params no partially (fully on P/Q/R/S) +L2 Forwarding Params yes no +Clock Sync Params no no +AVB Params no no +General Params yes partially +Retagging no yes +xMII Params yes no +SGMII no yes +============================= ================== ============================= + + +Also the configuration is write-only (software cannot read it back from the +switch except for very few exceptions). + +The driver creates a static configuration at probe time, and keeps it at +all times in memory, as a shadow for the hardware state. When required to +change a hardware setting, the static configuration is also updated. +If that changed setting can be transmitted to the switch through the dynamic +reconfiguration interface, it is; otherwise the switch is reset and +reprogrammed with the updated static configuration. + +Switching features +================== + +The driver supports the configuration of L2 forwarding rules in hardware for +port bridging. The forwarding, broadcast and flooding domain between ports can +be restricted through two methods: either at the L2 forwarding level (isolate +one bridge's ports from another's) or at the VLAN port membership level +(isolate ports within the same bridge). The final forwarding decision taken by +the hardware is a logical AND of these two sets of rules. + +The hardware tags all traffic internally with a port-based VLAN (pvid), or it +decodes the VLAN information from the 802.1Q tag. Advanced VLAN classification +is not possible. Once attributed a VLAN tag, frames are checked against the +port's membership rules and dropped at ingress if they don't match any VLAN. +This behavior is available when switch ports are enslaved to a bridge with +``vlan_filtering 1``. + +Normally the hardware is not configurable with respect to VLAN awareness, but +by changing what TPID the switch searches 802.1Q tags for, the semantics of a +bridge with ``vlan_filtering 0`` can be kept (accept all traffic, tagged or +untagged), and therefore this mode is also supported. + +Segregating the switch ports in multiple bridges is supported (e.g. 2 + 2), but +all bridges should have the same level of VLAN awareness (either both have +``vlan_filtering`` 0, or both 1). Also an inevitable limitation of the fact +that VLAN awareness is global at the switch level is that once a bridge with +``vlan_filtering`` enslaves at least one switch port, the other un-bridged +ports are no longer available for standalone traffic termination. + +Device Tree bindings and board design +===================================== + +This section references ``Documentation/devicetree/bindings/net/dsa/sja1105.txt`` +and aims to showcase some potential switch caveats. + +RMII PHY role and out-of-band signaling +--------------------------------------- + +In the RMII spec, the 50 MHz clock signals are either driven by the MAC or by +an external oscillator (but not by the PHY). +But the spec is rather loose and devices go outside it in several ways. +Some PHYs go against the spec and may provide an output pin where they source +the 50 MHz clock themselves, in an attempt to be helpful. +On the other hand, the SJA1105 is only binary configurable - when in the RMII +MAC role it will also attempt to drive the clock signal. To prevent this from +happening it must be put in RMII PHY role. +But doing so has some unintended consequences. +In the RMII spec, the PHY can transmit extra out-of-band signals via RXD[1:0]. +These are practically some extra code words (/J/ and /K/) sent prior to the +preamble of each frame. The MAC does not have this out-of-band signaling +mechanism defined by the RMII spec. +So when the SJA1105 port is put in PHY role to avoid having 2 drivers on the +clock signal, inevitably an RMII PHY-to-PHY connection is created. The SJA1105 +emulates a PHY interface fully and generates the /J/ and /K/ symbols prior to +frame preambles, which the real PHY is not expected to understand. So the PHY +simply encodes the extra symbols received from the SJA1105-as-PHY onto the +100Base-Tx wire. +On the other side of the wire, some link partners might discard these extra +symbols, while others might choke on them and discard the entire Ethernet +frames that follow along. This looks like packet loss with some link partners +but not with others. +The take-away is that in RMII mode, the SJA1105 must be let to drive the +reference clock if connected to a PHY. + +RGMII fixed-link and internal delays +------------------------------------ + +As mentioned in the bindings document, the second generation of devices has +tunable delay lines as part of the MAC, which can be used to establish the +correct RGMII timing budget. +When powered up, these can shift the Rx and Tx clocks with a phase difference +between 73.8 and 101.7 degrees. +The catch is that the delay lines need to lock onto a clock signal with a +stable frequency. This means that there must be at least 2 microseconds of +silence between the clock at the old vs at the new frequency. Otherwise the +lock is lost and the delay lines must be reset (powered down and back up). +In RGMII the clock frequency changes with link speed (125 MHz at 1000 Mbps, 25 +MHz at 100 Mbps and 2.5 MHz at 10 Mbps), and link speed might change during the +AN process. +In the situation where the switch port is connected through an RGMII fixed-link +to a link partner whose link state life cycle is outside the control of Linux +(such as a different SoC), then the delay lines would remain unlocked (and +inactive) until there is manual intervention (ifdown/ifup on the switch port). +The take-away is that in RGMII mode, the switch's internal delays are only +reliable if the link partner never changes link speeds, or if it does, it does +so in a way that is coordinated with the switch port (practically, both ends of +the fixed-link are under control of the same Linux system). +As to why would a fixed-link interface ever change link speeds: there are +Ethernet controllers out there which come out of reset in 100 Mbps mode, and +their driver inevitably needs to change the speed and clock frequency if it's +required to work at gigabit. + +MDIO bus and PHY management +--------------------------- + +The SJA1105 does not have an MDIO bus and does not perform in-band AN either. +Therefore there is no link state notification coming from the switch device. +A board would need to hook up the PHYs connected to the switch to any other +MDIO bus available to Linux within the system (e.g. to the DSA master's MDIO +bus). Link state management then works by the driver manually keeping in sync +(over SPI commands) the MAC link speed with the settings negotiated by the PHY. -- cgit v1.2.3 From 013fe01d45ed095189fd746e45fdf75016fec1f6 Mon Sep 17 00:00:00 2001 From: Vladimir Oltean Date: Thu, 2 May 2019 23:23:40 +0300 Subject: dt-bindings: net: dsa: Add documentation for NXP SJA1105 driver Signed-off-by: Vladimir Oltean Reviewed-by: Florian Fainelli Signed-off-by: David S. Miller --- .../devicetree/bindings/net/dsa/sja1105.txt | 156 +++++++++++++++++++++ 1 file changed, 156 insertions(+) create mode 100644 Documentation/devicetree/bindings/net/dsa/sja1105.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/net/dsa/sja1105.txt b/Documentation/devicetree/bindings/net/dsa/sja1105.txt new file mode 100644 index 000000000000..13fd21074d48 --- /dev/null +++ b/Documentation/devicetree/bindings/net/dsa/sja1105.txt @@ -0,0 +1,156 @@ +NXP SJA1105 switch driver +========================= + +Required properties: + +- compatible: + Must be one of: + - "nxp,sja1105e" + - "nxp,sja1105t" + - "nxp,sja1105p" + - "nxp,sja1105q" + - "nxp,sja1105r" + - "nxp,sja1105s" + + Although the device ID could be detected at runtime, explicit bindings + are required in order to be able to statically check their validity. + For example, SGMII can only be specified on port 4 of R and S devices, + and the non-SGMII devices, while pin-compatible, are not equal in terms + of support for RGMII internal delays (supported on P/Q/R/S, but not on + E/T). + +Optional properties: + +- sja1105,role-mac: +- sja1105,role-phy: + Boolean properties that can be assigned under each port node. By + default (unless otherwise specified) a port is configured as MAC if it + is driving a PHY (phy-handle is present) or as PHY if it is PHY-less + (fixed-link specified, presumably because it is connected to a MAC). + The effect of this property (in either its implicit or explicit form) + is: + - In the case of MII or RMII it specifies whether the SJA1105 port is a + clock source or sink for this interface (not applicable for RGMII + where there is a Tx and an Rx clock). + - In the case of RGMII it affects the behavior regarding internal + delays: + 1. If sja1105,role-mac is specified, and the phy-mode property is one + of "rgmii-id", "rgmii-txid" or "rgmii-rxid", then the entity + designated to apply the delay/clock skew necessary for RGMII + is the PHY. The SJA1105 MAC does not apply any internal delays. + 2. If sja1105,role-phy is specified, and the phy-mode property is one + of the above, the designated entity to apply the internal delays + is the SJA1105 MAC (if hardware-supported). This is only supported + by the second-generation (P/Q/R/S) hardware. On a first-generation + E or T device, it is an error to specify an RGMII phy-mode other + than "rgmii" for a port that is in fixed-link mode. In that case, + the clock skew must either be added by the MAC at the other end of + the fixed-link, or by PCB serpentine traces on the board. + These properties are required, for example, in the case where SJA1105 + ports are at both ends of a MII/RMII PHY-less setup. One end would need + to have sja1105,role-mac, while the other sja1105,role-phy. + +See Documentation/devicetree/bindings/net/dsa/dsa.txt for the list of standard +DSA required and optional properties. + +Other observations +------------------ + +The SJA1105 SPI interface requires a CS-to-CLK time (t2 in UM10944) of at least +one half of t_CLK. At an SPI frequency of 1MHz, this means a minimum +cs_sck_delay of 500ns. Ensuring that this SPI timing requirement is observed +depends on the SPI bus master driver. + +Example +------- + +Ethernet switch connected via SPI to the host, CPU port wired to enet2: + +arch/arm/boot/dts/ls1021a-tsn.dts: + +/* SPI controller of the LS1021 */ +&dspi0 { + sja1105@1 { + reg = <0x1>; + #address-cells = <1>; + #size-cells = <0>; + compatible = "nxp,sja1105t"; + spi-max-frequency = <4000000>; + fsl,spi-cs-sck-delay = <1000>; + fsl,spi-sck-cs-delay = <1000>; + ports { + #address-cells = <1>; + #size-cells = <0>; + port@0 { + /* ETH5 written on chassis */ + label = "swp5"; + phy-handle = <&rgmii_phy6>; + phy-mode = "rgmii-id"; + reg = <0>; + /* Implicit "sja1105,role-mac;" */ + }; + port@1 { + /* ETH2 written on chassis */ + label = "swp2"; + phy-handle = <&rgmii_phy3>; + phy-mode = "rgmii-id"; + reg = <1>; + /* Implicit "sja1105,role-mac;" */ + }; + port@2 { + /* ETH3 written on chassis */ + label = "swp3"; + phy-handle = <&rgmii_phy4>; + phy-mode = "rgmii-id"; + reg = <2>; + /* Implicit "sja1105,role-mac;" */ + }; + port@3 { + /* ETH4 written on chassis */ + phy-handle = <&rgmii_phy5>; + label = "swp4"; + phy-mode = "rgmii-id"; + reg = <3>; + /* Implicit "sja1105,role-mac;" */ + }; + port@4 { + /* Internal port connected to eth2 */ + ethernet = <&enet2>; + phy-mode = "rgmii"; + reg = <4>; + /* Implicit "sja1105,role-phy;" */ + fixed-link { + speed = <1000>; + full-duplex; + }; + }; + }; + }; +}; + +/* MDIO controller of the LS1021 */ +&mdio0 { + /* BCM5464 */ + rgmii_phy3: ethernet-phy@3 { + reg = <0x3>; + }; + rgmii_phy4: ethernet-phy@4 { + reg = <0x4>; + }; + rgmii_phy5: ethernet-phy@5 { + reg = <0x5>; + }; + rgmii_phy6: ethernet-phy@6 { + reg = <0x6>; + }; +}; + +/* Ethernet master port of the LS1021 */ +&enet2 { + phy-connection-type = "rgmii"; + status = "ok"; + fixed-link { + speed = <1000>; + full-duplex; + }; +}; -- cgit v1.2.3 From e6ae3ca27477226eae77cc00d5fad89d7ce64aea Mon Sep 17 00:00:00 2001 From: Chris Brandt Date: Tue, 30 Apr 2019 08:23:05 -0500 Subject: dt-bindings: i2c: riic: document r7s9210 support Document support for the R7S9210 (RZ/A2) SoC. Also explicitly document bindings for the R7S72100 (RZ/A1) SoC. Signed-off-by: Chris Brandt Reviewed-by: Geert Uytterhoeven Reviewed-by: Rob Herring Signed-off-by: Wolfram Sang --- Documentation/devicetree/bindings/i2c/i2c-riic.txt | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/i2c/i2c-riic.txt b/Documentation/devicetree/bindings/i2c/i2c-riic.txt index 0bcc4716c319..e26fe3ad86a9 100644 --- a/Documentation/devicetree/bindings/i2c/i2c-riic.txt +++ b/Documentation/devicetree/bindings/i2c/i2c-riic.txt @@ -1,7 +1,10 @@ Device tree configuration for Renesas RIIC driver Required properties: -- compatible : "renesas,riic-". "renesas,riic-rz" as fallback +- compatible : + "renesas,riic-r7s72100" if the device is a part of a R7S72100 SoC. + "renesas,riic-r7s9210" if the device is a part of a R7S9210 SoC. + "renesas,riic-rz" for a generic RZ/A compatible device. - reg : address start and address range size of device - interrupts : 8 interrupts (TEI, RI, TI, SPI, STI, NAKI, ALI, TMOI) - clock-frequency : frequency of bus clock in Hz -- cgit v1.2.3 From 85d49eb130ad747abebb9b0ff151f8afa7733115 Mon Sep 17 00:00:00 2001 From: Alexander Shishkin Date: Fri, 3 May 2019 11:44:35 +0300 Subject: intel_th: SPDX-ify the documentation Add the SPDX header to the Intel TH documentation. Signed-off-by: Alexander Shishkin Tested-by: Mathieu Poirier Signed-off-by: Greg Kroah-Hartman --- Documentation/trace/intel_th.rst | 2 ++ 1 file changed, 2 insertions(+) (limited to 'Documentation') diff --git a/Documentation/trace/intel_th.rst b/Documentation/trace/intel_th.rst index 19e2d633f3c7..baa12eb09ef4 100644 --- a/Documentation/trace/intel_th.rst +++ b/Documentation/trace/intel_th.rst @@ -1,3 +1,5 @@ +.. SPDX-License-Identifier: GPL-2.0 + ======================= Intel(R) Trace Hub (TH) ======================= -- cgit v1.2.3 From 6cac7866c27418cd784fbb8041c2dddd6d966bc7 Mon Sep 17 00:00:00 2001 From: Alexander Shishkin Date: Fri, 3 May 2019 11:44:50 +0300 Subject: intel_th: msu: Add a sysfs attribute to trigger window switch Now that we have the means to trigger a window switch for the MSU trace store, add a sysfs file to allow triggering it from userspace. Signed-off-by: Alexander Shishkin Signed-off-by: Greg Kroah-Hartman --- .../ABI/testing/sysfs-bus-intel_th-devices-msc | 8 +++++++ drivers/hwtracing/intel_th/msu.c | 28 ++++++++++++++++++++++ 2 files changed, 36 insertions(+) (limited to 'Documentation') diff --git a/Documentation/ABI/testing/sysfs-bus-intel_th-devices-msc b/Documentation/ABI/testing/sysfs-bus-intel_th-devices-msc index b940c5d91cf7..f54ae244f3f1 100644 --- a/Documentation/ABI/testing/sysfs-bus-intel_th-devices-msc +++ b/Documentation/ABI/testing/sysfs-bus-intel_th-devices-msc @@ -30,4 +30,12 @@ Description: (RW) Configure MSC buffer size for "single" or "multi" modes. there are no active users and tracing is not enabled) and then allocates a new one. +What: /sys/bus/intel_th/devices/-msc/win_switch +Date: May 2019 +KernelVersion: 5.2 +Contact: Alexander Shishkin +Description: (RW) Trigger window switch for the MSC's buffer, in + multi-window mode. In "multi" mode, accepts writes of "1", thereby + triggering a window switch for the buffer. Returns an error in any + other operating mode or attempts to write something other than "1". diff --git a/drivers/hwtracing/intel_th/msu.c b/drivers/hwtracing/intel_th/msu.c index b0bb69942328..aed72b33675d 100644 --- a/drivers/hwtracing/intel_th/msu.c +++ b/drivers/hwtracing/intel_th/msu.c @@ -1572,10 +1572,38 @@ free_win: static DEVICE_ATTR_RW(nr_pages); +static ssize_t +win_switch_store(struct device *dev, struct device_attribute *attr, + const char *buf, size_t size) +{ + struct msc *msc = dev_get_drvdata(dev); + unsigned long val; + int ret; + + ret = kstrtoul(buf, 10, &val); + if (ret) + return ret; + + if (val != 1) + return -EINVAL; + + mutex_lock(&msc->buf_mutex); + if (msc->mode != MSC_MODE_MULTI) + ret = -ENOTSUPP; + else + ret = intel_th_trace_switch(msc->thdev); + mutex_unlock(&msc->buf_mutex); + + return ret ? ret : size; +} + +static DEVICE_ATTR_WO(win_switch); + static struct attribute *msc_output_attrs[] = { &dev_attr_wrap.attr, &dev_attr_mode.attr, &dev_attr_nr_pages.attr, + &dev_attr_win_switch.attr, NULL, }; -- cgit v1.2.3 From be889be7785d21d8958d51d35cf52b73826657df Mon Sep 17 00:00:00 2001 From: Iker Perez del Palomar Sustatxa Date: Fri, 3 May 2019 17:15:01 +0100 Subject: dt-bindings: hwmon: Add tmp75b to lm75.txt Update the LM75's devicetree definition to allow Texas Instruments TMP75B be probed. Signed-off-by: Iker Perez del Palomar Sustatxa Signed-off-by: Guenter Roeck --- Documentation/devicetree/bindings/hwmon/lm75.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/hwmon/lm75.txt b/Documentation/devicetree/bindings/hwmon/lm75.txt index 12d8cf7cf592..586b5ed70be7 100644 --- a/Documentation/devicetree/bindings/hwmon/lm75.txt +++ b/Documentation/devicetree/bindings/hwmon/lm75.txt @@ -25,6 +25,7 @@ Required properties: "ti,tmp175", "ti,tmp275", "ti,tmp75", + "ti,tmp75b", "ti,tmp75c", - reg: I2C bus address of the device -- cgit v1.2.3 From 7df8f2d00ddb54da995d552aa0f599b1daf7e662 Mon Sep 17 00:00:00 2001 From: Andrey Smirnov Date: Fri, 3 May 2019 10:00:42 -0700 Subject: dt-bindings: power: supply: Add bindings for Microchip UCS1002 Add bindings for Microchip UCS1002 Programmable USB Port Power Controller with Charger Emulation. Signed-off-by: Andrey Smirnov Reviewed-by: Rob Herring Cc: Enric Balletbo Serra Cc: Chris Healy Cc: Lucas Stach Cc: Fabio Estevam Cc: Guenter Roeck Cc: linux-kernel@vger.kernel.org Cc: linux-pm@vger.kernel.org Signed-off-by: Sebastian Reichel --- .../bindings/power/supply/microchip,ucs1002.txt | 27 ++++++++++++++++++++++ 1 file changed, 27 insertions(+) create mode 100644 Documentation/devicetree/bindings/power/supply/microchip,ucs1002.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/power/supply/microchip,ucs1002.txt b/Documentation/devicetree/bindings/power/supply/microchip,ucs1002.txt new file mode 100644 index 000000000000..1d284ad816bf --- /dev/null +++ b/Documentation/devicetree/bindings/power/supply/microchip,ucs1002.txt @@ -0,0 +1,27 @@ +Microchip UCS1002 USB Port Power Controller + +Required properties: +- compatible : Should be "microchip,ucs1002"; +- reg : I2C slave address + +Optional properties: +- interrupts : A list of interrupts lines present (could be either + corresponding to A_DET# pin, ALERT# pin, or both) +- interrupt-names : A list of interrupt names. Should contain (if + present): + - "a_det" for line connected to A_DET# pin + - "alert" for line connected to ALERT# pin + Both are expected to be IRQ_TYPE_EDGE_BOTH +Example: + +&i2c3 { + charger@32 { + compatible = "microchip,ucs1002"; + pinctrl-names = "default"; + pinctrl-0 = <&pinctrl_ucs1002_pins>; + reg = <0x32>; + interrupts-extended = <&gpio5 2 IRQ_TYPE_EDGE_BOTH>, + <&gpio3 21 IRQ_TYPE_EDGE_BOTH>; + interrupt-names = "a_det", "alert"; + }; +}; -- cgit v1.2.3 From 39abe9d88b30a51029b0b29a708a4f4459034565 Mon Sep 17 00:00:00 2001 From: Iker Perez del Palomar Sustatxa Date: Fri, 3 May 2019 17:15:00 +0100 Subject: hwmon: (lm75) Add support for TMP75B The TMP75B has a different control register, supports 12-bit resolution and the default conversion rate is 37 Hz. Signed-off-by: Iker Perez del Palomar Sustatxa Signed-off-by: Guenter Roeck --- Documentation/hwmon/lm75.rst | 6 ++++-- drivers/hwmon/lm75.c | 11 +++++++++++ 2 files changed, 15 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/hwmon/lm75.rst b/Documentation/hwmon/lm75.rst index 6fd4d2df5420..ba8acbd2a6cb 100644 --- a/Documentation/hwmon/lm75.rst +++ b/Documentation/hwmon/lm75.rst @@ -93,9 +93,9 @@ Supported chips: https://www.st.com/resource/en/datasheet/stlm75.pdf - * Texas Instruments TMP100, TMP101, TMP105, TMP112, TMP75, TMP75C, TMP175, TMP275 + * Texas Instruments TMP100, TMP101, TMP105, TMP112, TMP75, TMP75B, TMP75C, TMP175, TMP275 - Prefixes: 'tmp100', 'tmp101', 'tmp105', 'tmp112', 'tmp175', 'tmp75', 'tmp75c', 'tmp275' + Prefixes: 'tmp100', 'tmp101', 'tmp105', 'tmp112', 'tmp175', 'tmp75', 'tmp75b', 'tmp75c', 'tmp275' Addresses scanned: none @@ -111,6 +111,8 @@ Supported chips: http://www.ti.com/product/tmp75 + http://www.ti.com/product/tmp75b + http://www.ti.com/product/tmp75c http://www.ti.com/product/tmp175 diff --git a/drivers/hwmon/lm75.c b/drivers/hwmon/lm75.c index f307743edc25..423a382420b9 100644 --- a/drivers/hwmon/lm75.c +++ b/drivers/hwmon/lm75.c @@ -59,6 +59,7 @@ enum lm75_type { /* keep sorted in alphabetical order */ tmp175, tmp275, tmp75, + tmp75b, tmp75c, }; @@ -354,6 +355,11 @@ lm75_probe(struct i2c_client *client, const struct i2c_device_id *id) data->resolution = 12; data->sample_time = MSEC_PER_SEC / 2; break; + case tmp75b: /* not one-shot mode, Conversion rate 37Hz */ + clr_mask |= 1 << 15 | 0x3 << 13; + data->resolution = 12; + data->sample_time = MSEC_PER_SEC / 37; + break; case tmp75c: clr_mask |= 1 << 5; /* not one-shot mode */ data->resolution = 12; @@ -414,6 +420,7 @@ static const struct i2c_device_id lm75_ids[] = { { "tmp175", tmp175, }, { "tmp275", tmp275, }, { "tmp75", tmp75, }, + { "tmp75b", tmp75b, }, { "tmp75c", tmp75c, }, { /* LIST END */ } }; @@ -512,6 +519,10 @@ static const struct of_device_id __maybe_unused lm75_of_match[] = { .compatible = "ti,tmp75", .data = (void *)tmp75 }, + { + .compatible = "ti,tmp75b", + .data = (void *)tmp75b + }, { .compatible = "ti,tmp75c", .data = (void *)tmp75c -- cgit v1.2.3 From 376e5fd7ec341a4e9cee2bf64fb59285023056e3 Mon Sep 17 00:00:00 2001 From: Sven Schnelle Date: Tue, 9 Apr 2019 19:30:29 +0200 Subject: doc: update kprobes supported architecture list Now that kprobes and kretprobes are implemented, update the list in Documentation to reflect that. Signed-off-by: Sven Schnelle Signed-off-by: Helge Deller --- Documentation/features/debug/kprobes/arch-support.txt | 2 +- Documentation/kprobes.txt | 1 + 2 files changed, 2 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/features/debug/kprobes/arch-support.txt b/Documentation/features/debug/kprobes/arch-support.txt index f4e45bd58fea..e68239b5d2f0 100644 --- a/Documentation/features/debug/kprobes/arch-support.txt +++ b/Documentation/features/debug/kprobes/arch-support.txt @@ -21,7 +21,7 @@ | nds32: | TODO | | nios2: | TODO | | openrisc: | TODO | - | parisc: | TODO | + | parisc: | ok | | powerpc: | ok | | riscv: | ok | | s390: | ok | diff --git a/Documentation/kprobes.txt b/Documentation/kprobes.txt index 10f4499e677c..33041300d1ee 100644 --- a/Documentation/kprobes.txt +++ b/Documentation/kprobes.txt @@ -321,6 +321,7 @@ architectures: - ppc - mips - s390 +- parisc Configuring Kprobes =================== -- cgit v1.2.3 From 75da60ff53fb030e12ac83cdef1da0464b289d1a Mon Sep 17 00:00:00 2001 From: Sven Schnelle Date: Tue, 9 Apr 2019 22:05:24 +0200 Subject: parisc: update feature lists Update lists to reflect that we have now KGDB and kretprobes support. Signed-off-by: Sven Schnelle Signed-off-by: Helge Deller --- Documentation/features/debug/kgdb/arch-support.txt | 2 +- Documentation/features/debug/kretprobes/arch-support.txt | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/features/debug/kgdb/arch-support.txt b/Documentation/features/debug/kgdb/arch-support.txt index 3e6b8f07d5d0..38c40cfa0578 100644 --- a/Documentation/features/debug/kgdb/arch-support.txt +++ b/Documentation/features/debug/kgdb/arch-support.txt @@ -21,7 +21,7 @@ | nds32: | TODO | | nios2: | ok | | openrisc: | TODO | - | parisc: | TODO | + | parisc: | ok | | powerpc: | ok | | riscv: | TODO | | s390: | TODO | diff --git a/Documentation/features/debug/kretprobes/arch-support.txt b/Documentation/features/debug/kretprobes/arch-support.txt index 1d5651ef11f8..f17131b328e5 100644 --- a/Documentation/features/debug/kretprobes/arch-support.txt +++ b/Documentation/features/debug/kretprobes/arch-support.txt @@ -21,7 +21,7 @@ | nds32: | TODO | | nios2: | TODO | | openrisc: | TODO | - | parisc: | TODO | + | parisc: | ok | | powerpc: | ok | | riscv: | TODO | | s390: | ok | -- cgit v1.2.3 From c0e74dd25422e32f2e65ee868c8b5c828b8c5b61 Mon Sep 17 00:00:00 2001 From: Sameer Pujar Date: Thu, 2 May 2019 18:25:13 +0530 Subject: Documentation: DT: Add compatibility binding for Tegra186 Tegra186 Audio DMA controller has new updates from Tegra210 version. Thus add new compatibility binding string and the same can be used by Tegra194 as well. Signed-off-by: Sameer Pujar Reviewed-by: Jon Hunter Signed-off-by: Vinod Koul --- Documentation/devicetree/bindings/dma/nvidia,tegra210-adma.txt | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/dma/nvidia,tegra210-adma.txt b/Documentation/devicetree/bindings/dma/nvidia,tegra210-adma.txt index 2f35b047f772..245d3063715c 100644 --- a/Documentation/devicetree/bindings/dma/nvidia,tegra210-adma.txt +++ b/Documentation/devicetree/bindings/dma/nvidia,tegra210-adma.txt @@ -4,7 +4,9 @@ The Tegra Audio DMA controller that is used for transferring data between system memory and the Audio Processing Engine (APE). Required properties: -- compatible: Must be "nvidia,tegra210-adma". +- compatible: Should contain one of the following: + - "nvidia,tegra210-adma": for Tegra210 + - "nvidia,tegra186-adma": for Tegra186 and Tegra194 - reg: Should contain DMA registers location and length. This should be a single entry that includes all of the per-channel registers in one contiguous bank. -- cgit v1.2.3 From f6cc8b355c030ed673330b5fb31e5f6e546a33b4 Mon Sep 17 00:00:00 2001 From: Matteo Croce Date: Mon, 18 Mar 2019 02:19:15 +0100 Subject: watchdog: i6300esb: stop printing kernel addresses Since commit ad67b74d2469d9b8 ("printk: hash addresses printed with %p"), i6300esb prints "____ptrval____" instead of actual addresses: i6300ESB timer 0000:00:03.0: initialized (0x(____ptrval____)). heartbeat=30 sec (nowayout=1) Instead of changing the print to "%px", and leaking kernel addresses, just remove the print completely, cfr. e.g. commit 071929dbdd865f77 ("arm64: Stop printing the virtual memory layout"). Signed-off-by: Matteo Croce Reviewed-by: Guenter Roeck Signed-off-by: Guenter Roeck Signed-off-by: Wim Van Sebroeck --- Documentation/devicetree/bindings/watchdog/mtk-wdt.txt | 1 + drivers/watchdog/i6300esb.c | 4 ++-- 2 files changed, 3 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/watchdog/mtk-wdt.txt b/Documentation/devicetree/bindings/watchdog/mtk-wdt.txt index 8682d6a93e5b..fd380eb28df5 100644 --- a/Documentation/devicetree/bindings/watchdog/mtk-wdt.txt +++ b/Documentation/devicetree/bindings/watchdog/mtk-wdt.txt @@ -9,6 +9,7 @@ Required properties: "mediatek,mt7622-wdt", "mediatek,mt6589-wdt": for MT7622 "mediatek,mt7623-wdt", "mediatek,mt6589-wdt": for MT7623 "mediatek,mt7629-wdt", "mediatek,mt6589-wdt": for MT7629 + "mediatek,mt8516-wdt", "mediatek,mt6589-wdt": for MT8516 - reg : Specifies base physical address and size of the registers. diff --git a/drivers/watchdog/i6300esb.c b/drivers/watchdog/i6300esb.c index 950c71a8bb22..e312a2aeecad 100644 --- a/drivers/watchdog/i6300esb.c +++ b/drivers/watchdog/i6300esb.c @@ -328,8 +328,8 @@ static int esb_probe(struct pci_dev *pdev, goto err_unmap; } dev_info(&pdev->dev, - "initialized (0x%p). heartbeat=%d sec (nowayout=%d)\n", - edev->base, edev->wdd.timeout, nowayout); + "initialized. heartbeat=%d sec (nowayout=%d)\n", + edev->wdd.timeout, nowayout); return 0; err_unmap: -- cgit v1.2.3 From bb83520d269536f5d48b609a23ec0a1fdabbe503 Mon Sep 17 00:00:00 2001 From: Anson Huang Date: Thu, 21 Mar 2019 02:26:38 +0000 Subject: dt-bindings: watchdog: add i.MX system controller watchdog Add i.MX system controller watchdog binding doc. Signed-off-by: Anson Huang Acked-by: Rob Herring Signed-off-by: Guenter Roeck Signed-off-by: Wim Van Sebroeck --- .../bindings/watchdog/fsl-imx-sc-wdt.txt | 24 ++++++++++++++++++++++ 1 file changed, 24 insertions(+) create mode 100644 Documentation/devicetree/bindings/watchdog/fsl-imx-sc-wdt.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/watchdog/fsl-imx-sc-wdt.txt b/Documentation/devicetree/bindings/watchdog/fsl-imx-sc-wdt.txt new file mode 100644 index 000000000000..02b87e92ae68 --- /dev/null +++ b/Documentation/devicetree/bindings/watchdog/fsl-imx-sc-wdt.txt @@ -0,0 +1,24 @@ +* Freescale i.MX System Controller Watchdog + +i.MX system controller watchdog is for i.MX SoCs with system controller inside, +the watchdog is managed by system controller, users can ONLY communicate with +system controller from secure mode for watchdog operations, so Linux i.MX system +controller watchdog driver will call ARM SMC API and trap into ARM-Trusted-Firmware +for watchdog operations, ARM-Trusted-Firmware is running at secure EL3 mode and +it will request system controller to execute the watchdog operation passed from +Linux kernel. + +Required properties: +- compatible: Should be : + "fsl,imx8qxp-sc-wdt" + followed by "fsl,imx-sc-wdt"; + +Optional properties: +- timeout-sec : Contains the watchdog timeout in seconds. + +Examples: + +watchdog { + compatible = "fsl,imx8qxp-sc-wdt", "fsl,imx-sc-wdt"; + timeout-sec = <60>; +}; -- cgit v1.2.3 From 687e3d5550c7b0e4dca0179103741a44cd3f7864 Mon Sep 17 00:00:00 2001 From: Petr Štetiar Date: Fri, 3 May 2019 16:27:07 +0200 Subject: dt-bindings: doc: reflect new NVMEM of_get_mac_address behaviour MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit As of_get_mac_address now supports NVMEM under the hood, we need to update the bindings documentation with the new nvmem-cell* properties, which would mean copy&pasting a lot of redundant information to every binding documentation currently referencing some of the MAC address properties. So I've just removed all the references to the optional MAC address properties and replaced them with the small note referencing net/ethernet.txt file. Signed-off-by: Petr Štetiar Signed-off-by: David S. Miller --- Documentation/devicetree/bindings/net/altera_tse.txt | 5 ++--- Documentation/devicetree/bindings/net/amd-xgbe.txt | 5 +++-- Documentation/devicetree/bindings/net/brcm,amac.txt | 4 ++-- Documentation/devicetree/bindings/net/cpsw.txt | 4 +++- Documentation/devicetree/bindings/net/davinci_emac.txt | 5 +++-- Documentation/devicetree/bindings/net/dsa/dsa.txt | 5 ++--- Documentation/devicetree/bindings/net/ethernet.txt | 6 ++++-- Documentation/devicetree/bindings/net/hisilicon-femac.txt | 4 +++- .../devicetree/bindings/net/hisilicon-hix5hd2-gmac.txt | 4 +++- Documentation/devicetree/bindings/net/keystone-netcp.txt | 10 +++++----- Documentation/devicetree/bindings/net/macb.txt | 5 ++--- Documentation/devicetree/bindings/net/marvell-pxa168.txt | 4 +++- Documentation/devicetree/bindings/net/microchip,enc28j60.txt | 3 ++- Documentation/devicetree/bindings/net/microchip,lan78xx.txt | 5 ++--- Documentation/devicetree/bindings/net/qca,qca7000.txt | 4 +++- Documentation/devicetree/bindings/net/samsung-sxgbe.txt | 4 +++- .../devicetree/bindings/net/snps,dwc-qos-ethernet.txt | 5 +++-- .../devicetree/bindings/net/socionext,uniphier-ave4.txt | 4 ++-- Documentation/devicetree/bindings/net/socionext-netsec.txt | 5 +++-- .../devicetree/bindings/net/wireless/mediatek,mt76.txt | 5 +++-- Documentation/devicetree/bindings/net/wireless/qca,ath9k.txt | 4 ++-- 21 files changed, 58 insertions(+), 42 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/net/altera_tse.txt b/Documentation/devicetree/bindings/net/altera_tse.txt index 0e21df94a53f..0b7d4d3758ea 100644 --- a/Documentation/devicetree/bindings/net/altera_tse.txt +++ b/Documentation/devicetree/bindings/net/altera_tse.txt @@ -46,9 +46,8 @@ Required properties: - reg: phy id used to communicate to phy. - device_type: Must be "ethernet-phy". -Optional properties: -- local-mac-address: See ethernet.txt in the same directory. -- max-frame-size: See ethernet.txt in the same directory. +The MAC address will be determined using the optional properties defined in +ethernet.txt. Example: diff --git a/Documentation/devicetree/bindings/net/amd-xgbe.txt b/Documentation/devicetree/bindings/net/amd-xgbe.txt index 93dcb79a5f16..9c27dfcd1133 100644 --- a/Documentation/devicetree/bindings/net/amd-xgbe.txt +++ b/Documentation/devicetree/bindings/net/amd-xgbe.txt @@ -24,8 +24,6 @@ Required properties: - phy-mode: See ethernet.txt file in the same directory Optional properties: -- mac-address: mac address to be assigned to the device. Can be overridden - by UEFI. - dma-coherent: Present if dma operations are coherent - amd,per-channel-interrupt: Indicates that Rx and Tx complete will generate a unique interrupt for each DMA channel - this requires an additional @@ -34,6 +32,9 @@ Optional properties: 0 - 1GbE and 10GbE (default) 1 - 2.5GbE and 10GbE +The MAC address will be determined using the optional properties defined in +ethernet.txt. + The following optional properties are represented by an array with each value corresponding to a particular speed. The first array value represents the setting for the 1GbE speed, the second value for the 2.5GbE speed and diff --git a/Documentation/devicetree/bindings/net/brcm,amac.txt b/Documentation/devicetree/bindings/net/brcm,amac.txt index 0bfad656a9ff..0120ebe93262 100644 --- a/Documentation/devicetree/bindings/net/brcm,amac.txt +++ b/Documentation/devicetree/bindings/net/brcm,amac.txt @@ -16,8 +16,8 @@ Required properties: registers (required for Northstar2) - interrupts: Interrupt number -Optional properties: -- mac-address: See ethernet.txt file in the same directory +The MAC address will be determined using the optional properties +defined in ethernet.txt. Examples: diff --git a/Documentation/devicetree/bindings/net/cpsw.txt b/Documentation/devicetree/bindings/net/cpsw.txt index 3264e1978d25..7c7ac5eb0313 100644 --- a/Documentation/devicetree/bindings/net/cpsw.txt +++ b/Documentation/devicetree/bindings/net/cpsw.txt @@ -49,10 +49,12 @@ Required properties: Optional properties: - dual_emac_res_vlan : Specifies VID to be used to segregate the ports -- mac-address : See ethernet.txt file in the same directory - phy_id : Specifies slave phy id (deprecated, use phy-handle) - phy-handle : See ethernet.txt file in the same directory +The MAC address will be determined using the optional properties +defined in ethernet.txt. + Slave sub-nodes: - fixed-link : See fixed-link.txt file in the same directory diff --git a/Documentation/devicetree/bindings/net/davinci_emac.txt b/Documentation/devicetree/bindings/net/davinci_emac.txt index ca83dcc84fb8..5e3579e72e2d 100644 --- a/Documentation/devicetree/bindings/net/davinci_emac.txt +++ b/Documentation/devicetree/bindings/net/davinci_emac.txt @@ -20,11 +20,12 @@ Required properties: Optional properties: - phy-handle: See ethernet.txt file in the same directory. If absent, davinci_emac driver defaults to 100/FULL. -- nvmem-cells: phandle, reference to an nvmem node for the MAC address -- nvmem-cell-names: string, should be "mac-address" if nvmem is to be used - ti,davinci-rmii-en: 1 byte, 1 means use RMII - ti,davinci-no-bd-ram: boolean, does EMAC have BD RAM? +The MAC address will be determined using the optional properties +defined in ethernet.txt. + Example (enbw_cmc board): eth0: emac@1e20000 { compatible = "ti,davinci-dm6467-emac"; diff --git a/Documentation/devicetree/bindings/net/dsa/dsa.txt b/Documentation/devicetree/bindings/net/dsa/dsa.txt index c107d2848888..f66bb7ecdb82 100644 --- a/Documentation/devicetree/bindings/net/dsa/dsa.txt +++ b/Documentation/devicetree/bindings/net/dsa/dsa.txt @@ -65,9 +65,8 @@ properties, described in binding documents: Documentation/devicetree/bindings/net/fixed-link.txt for details. -- local-mac-address : See - Documentation/devicetree/bindings/net/ethernet.txt - for details. +The MAC address will be determined using the optional properties +defined in ethernet.txt. Example diff --git a/Documentation/devicetree/bindings/net/ethernet.txt b/Documentation/devicetree/bindings/net/ethernet.txt index a68621580584..699244428a28 100644 --- a/Documentation/devicetree/bindings/net/ethernet.txt +++ b/Documentation/devicetree/bindings/net/ethernet.txt @@ -4,12 +4,14 @@ NOTE: All 'phy*' properties documented below are Ethernet specific. For the generic PHY 'phys' property, see Documentation/devicetree/bindings/phy/phy-bindings.txt. -- local-mac-address: array of 6 bytes, specifies the MAC address that was - assigned to the network device; - mac-address: array of 6 bytes, specifies the MAC address that was last used by the boot program; should be used in cases where the MAC address assigned to the device by the boot program is different from the "local-mac-address" property; +- local-mac-address: array of 6 bytes, specifies the MAC address that was + assigned to the network device; +- nvmem-cells: phandle, reference to an nvmem node for the MAC address +- nvmem-cell-names: string, should be "mac-address" if nvmem is to be used - max-speed: number, specifies maximum speed in Mbit/s supported by the device; - max-frame-size: number, maximum transfer unit (IEEE defined MTU), rather than the maximum frame size (there's contradiction in the Devicetree diff --git a/Documentation/devicetree/bindings/net/hisilicon-femac.txt b/Documentation/devicetree/bindings/net/hisilicon-femac.txt index d11af5ecace8..5f96976f3cea 100644 --- a/Documentation/devicetree/bindings/net/hisilicon-femac.txt +++ b/Documentation/devicetree/bindings/net/hisilicon-femac.txt @@ -14,7 +14,6 @@ Required properties: the PHY reset signal(optional). - reset-names: should contain the reset signal name "mac"(required) and "phy"(optional). -- mac-address: see ethernet.txt [1]. - phy-mode: see ethernet.txt [1]. - phy-handle: see ethernet.txt [1]. - hisilicon,phy-reset-delays-us: triplet of delays if PHY reset signal given. @@ -22,6 +21,9 @@ Required properties: The 2nd cell is reset pulse in micro seconds. The 3rd cell is reset post-delay in micro seconds. +The MAC address will be determined using the optional properties +defined in ethernet.txt[1]. + [1] Documentation/devicetree/bindings/net/ethernet.txt Example: diff --git a/Documentation/devicetree/bindings/net/hisilicon-hix5hd2-gmac.txt b/Documentation/devicetree/bindings/net/hisilicon-hix5hd2-gmac.txt index eea73adc678f..cddf46bf6b63 100644 --- a/Documentation/devicetree/bindings/net/hisilicon-hix5hd2-gmac.txt +++ b/Documentation/devicetree/bindings/net/hisilicon-hix5hd2-gmac.txt @@ -18,7 +18,6 @@ Required properties: - #size-cells: must be <0>. - phy-mode: see ethernet.txt [1]. - phy-handle: see ethernet.txt [1]. -- mac-address: see ethernet.txt [1]. - clocks: clock phandle and specifier pair. - clock-names: contain the clock name "mac_core"(required) and "mac_ifc"(optional). - resets: should contain the phandle to the MAC core reset signal(optional), @@ -31,6 +30,9 @@ Required properties: The 2nd cell is reset pulse in micro seconds. The 3rd cell is reset post-delay in micro seconds. +The MAC address will be determined using the properties defined in +ethernet.txt[1]. + - PHY subnode: inherits from phy binding [2] [1] Documentation/devicetree/bindings/net/ethernet.txt diff --git a/Documentation/devicetree/bindings/net/keystone-netcp.txt b/Documentation/devicetree/bindings/net/keystone-netcp.txt index 04ba1dc34fd6..3a65aabc76a2 100644 --- a/Documentation/devicetree/bindings/net/keystone-netcp.txt +++ b/Documentation/devicetree/bindings/net/keystone-netcp.txt @@ -135,14 +135,14 @@ Optional properties: are swapped. The netcp driver will swap the two DWORDs back to the proper order when this property is set to 2 when it obtains the mac address from efuse. -- local-mac-address: the driver is designed to use the of_get_mac_address api - only if efuse-mac is 0. When efuse-mac is 0, the MAC - address is obtained from local-mac-address. If this - attribute is not present, then the driver will use a - random MAC address. - "netcp-device label": phandle to the device specification for each of NetCP sub-module attached to this interface. +The MAC address will be determined using the optional properties defined in +ethernet.txt, as provided by the of_get_mac_address API and only if efuse-mac +is set to 0. If any of the optional MAC address properties are not present, +then the driver will use random MAC address. + Example binding: netcp: netcp@2000000 { diff --git a/Documentation/devicetree/bindings/net/macb.txt b/Documentation/devicetree/bindings/net/macb.txt index 8b80515729d7..9c5e94482b5f 100644 --- a/Documentation/devicetree/bindings/net/macb.txt +++ b/Documentation/devicetree/bindings/net/macb.txt @@ -26,9 +26,8 @@ Required properties: Optional elements: 'tsu_clk' - clocks: Phandles to input clocks. -Optional properties: -- nvmem-cells: phandle, reference to an nvmem node for the MAC address -- nvmem-cell-names: string, should be "mac-address" if nvmem is to be used +The MAC address will be determined using the optional properties +defined in ethernet.txt. Optional properties for PHY child node: - reset-gpios : Should specify the gpio for phy reset diff --git a/Documentation/devicetree/bindings/net/marvell-pxa168.txt b/Documentation/devicetree/bindings/net/marvell-pxa168.txt index 845a148a346e..5574af3554aa 100644 --- a/Documentation/devicetree/bindings/net/marvell-pxa168.txt +++ b/Documentation/devicetree/bindings/net/marvell-pxa168.txt @@ -11,7 +11,9 @@ Optional properties: - #address-cells: must be 1 when using sub-nodes. - #size-cells: must be 0 when using sub-nodes. - phy-handle: see ethernet.txt file in the same directory. -- local-mac-address: see ethernet.txt file in the same directory. + +The MAC address will be determined using the optional properties +defined in ethernet.txt. Sub-nodes: Each PHY can be represented as a sub-node. This is not mandatory. diff --git a/Documentation/devicetree/bindings/net/microchip,enc28j60.txt b/Documentation/devicetree/bindings/net/microchip,enc28j60.txt index 24626e082b83..a8275921a896 100644 --- a/Documentation/devicetree/bindings/net/microchip,enc28j60.txt +++ b/Documentation/devicetree/bindings/net/microchip,enc28j60.txt @@ -21,8 +21,9 @@ Optional properties: - spi-max-frequency: Maximum frequency of the SPI bus when accessing the ENC28J60. According to the ENC28J80 datasheet, the chip allows a maximum of 20 MHz, however, board designs may need to limit this value. -- local-mac-address: See ethernet.txt in the same directory. +The MAC address will be determined using the optional properties +defined in ethernet.txt. Example (for NXP i.MX28 with pin control stuff for GPIO irq): diff --git a/Documentation/devicetree/bindings/net/microchip,lan78xx.txt b/Documentation/devicetree/bindings/net/microchip,lan78xx.txt index 76786a0f6d3d..11a679530ae6 100644 --- a/Documentation/devicetree/bindings/net/microchip,lan78xx.txt +++ b/Documentation/devicetree/bindings/net/microchip,lan78xx.txt @@ -7,9 +7,8 @@ The Device Tree properties, if present, override the OTP and EEPROM. Required properties: - compatible: Should be one of "usb424,7800", "usb424,7801" or "usb424,7850". -Optional properties: -- local-mac-address: see ethernet.txt -- mac-address: see ethernet.txt +The MAC address will be determined using the optional properties +defined in ethernet.txt. Optional properties of the embedded PHY: - microchip,led-modes: a 0..4 element vector, with each element configuring diff --git a/Documentation/devicetree/bindings/net/qca,qca7000.txt b/Documentation/devicetree/bindings/net/qca,qca7000.txt index e4a8a51086df..21c36e524993 100644 --- a/Documentation/devicetree/bindings/net/qca,qca7000.txt +++ b/Documentation/devicetree/bindings/net/qca,qca7000.txt @@ -23,7 +23,6 @@ Optional properties: Numbers smaller than 1000000 or greater than 16000000 are invalid. Missing the property will set the SPI frequency to 8000000 Hertz. -- local-mac-address : see ./ethernet.txt - qca,legacy-mode : Set the SPI data transfer of the QCA7000 to legacy mode. In this mode the SPI master must toggle the chip select between each data word. In burst mode these gaps aren't @@ -31,6 +30,9 @@ Optional properties: the QCA7000 is setup via GPIO pin strapping. If the property is missing the driver defaults to burst mode. +The MAC address will be determined using the optional properties +defined in ethernet.txt. + SPI Example: /* Freescale i.MX28 SPI master*/ diff --git a/Documentation/devicetree/bindings/net/samsung-sxgbe.txt b/Documentation/devicetree/bindings/net/samsung-sxgbe.txt index 46e591178911..2cff6d8a585a 100644 --- a/Documentation/devicetree/bindings/net/samsung-sxgbe.txt +++ b/Documentation/devicetree/bindings/net/samsung-sxgbe.txt @@ -21,10 +21,12 @@ Required properties: range. Optional properties: -- mac-address: 6 bytes, mac address - max-frame-size: Maximum Transfer Unit (IEEE defined MTU), rather than the maximum frame size. +The MAC address will be determined using the optional properties +defined in ethernet.txt. + Example: aliases { diff --git a/Documentation/devicetree/bindings/net/snps,dwc-qos-ethernet.txt b/Documentation/devicetree/bindings/net/snps,dwc-qos-ethernet.txt index 36f1aef585f0..ad3c6e109ce1 100644 --- a/Documentation/devicetree/bindings/net/snps,dwc-qos-ethernet.txt +++ b/Documentation/devicetree/bindings/net/snps,dwc-qos-ethernet.txt @@ -103,8 +103,6 @@ Required properties: Optional properties: - dma-coherent: Present if dma operations are coherent -- mac-address: See ethernet.txt in the same directory -- local-mac-address: See ethernet.txt in the same directory - phy-reset-gpios: Phandle and specifier for any GPIO used to reset the PHY. See ../gpio/gpio.txt. - snps,en-lpi: If present it enables use of the AXI low-power interface @@ -133,6 +131,9 @@ Optional properties: - device_type: Must be "ethernet-phy". - fixed-mode device tree subnode: see fixed-link.txt in the same directory +The MAC address will be determined using the optional properties +defined in ethernet.txt. + Examples: ethernet2@40010000 { clock-names = "phy_ref_clk", "apb_pclk"; diff --git a/Documentation/devicetree/bindings/net/socionext,uniphier-ave4.txt b/Documentation/devicetree/bindings/net/socionext,uniphier-ave4.txt index fc8f01718690..4e85fc495e87 100644 --- a/Documentation/devicetree/bindings/net/socionext,uniphier-ave4.txt +++ b/Documentation/devicetree/bindings/net/socionext,uniphier-ave4.txt @@ -31,8 +31,8 @@ Required properties: - socionext,syscon-phy-mode: A phandle to syscon with one argument that configures phy mode. The argument is the ID of MAC instance. -Optional properties: - - local-mac-address: See ethernet.txt in the same directory. +The MAC address will be determined using the optional properties +defined in ethernet.txt. Required subnode: - mdio: A container for child nodes representing phy nodes. diff --git a/Documentation/devicetree/bindings/net/socionext-netsec.txt b/Documentation/devicetree/bindings/net/socionext-netsec.txt index 0cff94fb0433..9d6c9feb12ff 100644 --- a/Documentation/devicetree/bindings/net/socionext-netsec.txt +++ b/Documentation/devicetree/bindings/net/socionext-netsec.txt @@ -26,11 +26,12 @@ Required properties: Optional properties: (See ethernet.txt file in the same directory) - dma-coherent: Boolean property, must only be present if memory accesses performed by the device are cache coherent. -- local-mac-address: See ethernet.txt in the same directory. -- mac-address: See ethernet.txt in the same directory. - max-speed: See ethernet.txt in the same directory. - max-frame-size: See ethernet.txt in the same directory. +The MAC address will be determined using the optional properties +defined in ethernet.txt. + Example: eth0: ethernet@522d0000 { compatible = "socionext,synquacer-netsec"; diff --git a/Documentation/devicetree/bindings/net/wireless/mediatek,mt76.txt b/Documentation/devicetree/bindings/net/wireless/mediatek,mt76.txt index 7b9a776230c0..74665502f4cf 100644 --- a/Documentation/devicetree/bindings/net/wireless/mediatek,mt76.txt +++ b/Documentation/devicetree/bindings/net/wireless/mediatek,mt76.txt @@ -13,11 +13,12 @@ properties: Optional properties: -- mac-address: See ethernet.txt in the parent directory -- local-mac-address: See ethernet.txt in the parent directory - ieee80211-freq-limit: See ieee80211.txt - mediatek,mtd-eeprom: Specify a MTD partition + offset containing EEPROM data +The driver is using of_get_mac_address API, so the MAC address can be as well +be set with corresponding optional properties defined in net/ethernet.txt. + Optional nodes: - led: Properties for a connected LED Optional properties: diff --git a/Documentation/devicetree/bindings/net/wireless/qca,ath9k.txt b/Documentation/devicetree/bindings/net/wireless/qca,ath9k.txt index b7396c8c271c..aaaeeb5f935b 100644 --- a/Documentation/devicetree/bindings/net/wireless/qca,ath9k.txt +++ b/Documentation/devicetree/bindings/net/wireless/qca,ath9k.txt @@ -34,9 +34,9 @@ Optional properties: ath9k wireless chip (in this case the calibration / EEPROM data will be loaded from userspace using the kernel firmware loader). -- mac-address: See ethernet.txt in the parent directory -- local-mac-address: See ethernet.txt in the parent directory +The MAC address will be determined using the optional properties defined in +net/ethernet.txt. In this example, the node is defined as child node of the PCI controller: &pci0 { -- cgit v1.2.3 From 0a58d471de3a34e435c5358cf533e74905eb0e7a Mon Sep 17 00:00:00 2001 From: Vladimir Oltean Date: Sun, 5 May 2019 13:19:29 +0300 Subject: Documentation: net: dsa: sja1105: Add info about supported traffic modes This adds a table which illustrates what combinations of management / regular traffic work depending on the state the switch ports are in. Signed-off-by: Vladimir Oltean Reviewed-by: Florian Fainelli Signed-off-by: David S. Miller --- Documentation/networking/dsa/sja1105.rst | 54 ++++++++++++++++++++++++++++++++ 1 file changed, 54 insertions(+) (limited to 'Documentation') diff --git a/Documentation/networking/dsa/sja1105.rst b/Documentation/networking/dsa/sja1105.rst index 7c13b40915c0..ea7bac438cfd 100644 --- a/Documentation/networking/dsa/sja1105.rst +++ b/Documentation/networking/dsa/sja1105.rst @@ -63,6 +63,38 @@ If that changed setting can be transmitted to the switch through the dynamic reconfiguration interface, it is; otherwise the switch is reset and reprogrammed with the updated static configuration. +Traffic support +=============== + +The switches do not support switch tagging in hardware. But they do support +customizing the TPID by which VLAN traffic is identified as such. The switch +driver is leveraging ``CONFIG_NET_DSA_TAG_8021Q`` by requesting that special +VLANs (with a custom TPID of ``ETH_P_EDSA`` instead of ``ETH_P_8021Q``) are +installed on its ports when not in ``vlan_filtering`` mode. This does not +interfere with the reception and transmission of real 802.1Q-tagged traffic, +because the switch does no longer parse those packets as VLAN after the TPID +change. +The TPID is restored when ``vlan_filtering`` is requested by the user through +the bridge layer, and general IP termination becomes no longer possible through +the switch netdevices in this mode. + +The switches have two programmable filters for link-local destination MACs. +These are used to trap BPDUs and PTP traffic to the master netdevice, and are +further used to support STP and 1588 ordinary clock/boundary clock +functionality. + +The following traffic modes are supported over the switch netdevices: + ++--------------------+------------+------------------+------------------+ +| | Standalone | Bridged with | Bridged with | +| | ports | vlan_filtering 0 | vlan_filtering 1 | ++====================+============+==================+==================+ +| Regular traffic | Yes | Yes | No (use master) | ++--------------------+------------+------------------+------------------+ +| Management traffic | Yes | Yes | Yes | +| (BPDU, PTP) | | | | ++--------------------+------------+------------------+------------------+ + Switching features ================== @@ -92,6 +124,28 @@ that VLAN awareness is global at the switch level is that once a bridge with ``vlan_filtering`` enslaves at least one switch port, the other un-bridged ports are no longer available for standalone traffic termination. +Topology and loop detection through STP is supported. + +L2 FDB manipulation (add/delete/dump) is currently possible for the first +generation devices. Aging time of FDB entries, as well as enabling fully static +management (no address learning and no flooding of unknown traffic) is not yet +configurable in the driver. + +A special comment about bridging with other netdevices (illustrated with an +example): + +A board has eth0, eth1, swp0@eth1, swp1@eth1, swp2@eth1, swp3@eth1. +The switch ports (swp0-3) are under br0. +It is desired that eth0 is turned into another switched port that communicates +with swp0-3. + +If br0 has vlan_filtering 0, then eth0 can simply be added to br0 with the +intended results. +If br0 has vlan_filtering 1, then a new br1 interface needs to be created that +enslaves eth0 and eth1 (the DSA master of the switch ports). This is because in +this mode, the switch ports beneath br0 are not capable of regular traffic, and +are only used as a conduit for switchdev operations. + Device Tree bindings and board design ===================================== -- cgit v1.2.3 From fdd20ec8786ab2950439c7e78871618f7e51f18b Mon Sep 17 00:00:00 2001 From: Geert Uytterhoeven Date: Mon, 6 May 2019 10:46:41 +0200 Subject: Documentation/features/time: Mark m68k having modern-timekeeping M68k no longer uses arch_gettimeoffset. Signed-off-by: Geert Uytterhoeven --- Documentation/features/time/modern-timekeeping/arch-support.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/features/time/modern-timekeeping/arch-support.txt b/Documentation/features/time/modern-timekeeping/arch-support.txt index 2855dfe2464d..1d46da165b75 100644 --- a/Documentation/features/time/modern-timekeeping/arch-support.txt +++ b/Documentation/features/time/modern-timekeeping/arch-support.txt @@ -15,7 +15,7 @@ | h8300: | ok | | hexagon: | ok | | ia64: | ok | - | m68k: | TODO | + | m68k: | ok | | microblaze: | ok | | mips: | ok | | nds32: | ok | -- cgit v1.2.3 From d3db80ca5744b5635554dd6171ecb8f3c3a5fd71 Mon Sep 17 00:00:00 2001 From: BOUGH CHEN Date: Mon, 29 Apr 2019 08:55:32 +0000 Subject: dt-bindings: mmc: fsl-imx-esdhc: add imx7ulp compatible string Add imx7ulp compatible string. Signed-off-by: Haibo Chen Reviewed-by: Dong Aisheng Reviewed-by: Rob Herring Signed-off-by: Ulf Hansson --- Documentation/devicetree/bindings/mmc/fsl-imx-esdhc.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mmc/fsl-imx-esdhc.txt b/Documentation/devicetree/bindings/mmc/fsl-imx-esdhc.txt index 540c65ed9cba..f707b8bee304 100644 --- a/Documentation/devicetree/bindings/mmc/fsl-imx-esdhc.txt +++ b/Documentation/devicetree/bindings/mmc/fsl-imx-esdhc.txt @@ -17,6 +17,7 @@ Required properties: "fsl,imx6sx-usdhc" "fsl,imx6ull-usdhc" "fsl,imx7d-usdhc" + "fsl,imx7ulp-usdhc" "fsl,imx8qxp-usdhc" Optional properties: -- cgit v1.2.3 From e57112e35c60a847914c75e5163db0f4ba078091 Mon Sep 17 00:00:00 2001 From: Fabien Parent Date: Sat, 23 Mar 2019 22:15:56 +0100 Subject: dt-bindings: mmc: Add support for MT8516 to mtk-sd Add binding documentation of mtk-sd for MT8516 SoCs. Signed-off-by: Fabien Parent Signed-off-by: Ulf Hansson --- Documentation/devicetree/bindings/mmc/mtk-sd.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mmc/mtk-sd.txt b/Documentation/devicetree/bindings/mmc/mtk-sd.txt index f5bcda3980cc..91a2ec59e497 100644 --- a/Documentation/devicetree/bindings/mmc/mtk-sd.txt +++ b/Documentation/devicetree/bindings/mmc/mtk-sd.txt @@ -11,6 +11,7 @@ Required properties: "mediatek,mt8135-mmc": for mmc host ip compatible with mt8135 "mediatek,mt8173-mmc": for mmc host ip compatible with mt8173 "mediatek,mt8183-mmc": for mmc host ip compatible with mt8183 + "mediatek,mt8516-mmc": for mmc host ip compatible with mt8516 "mediatek,mt2701-mmc": for mmc host ip compatible with mt2701 "mediatek,mt2712-mmc": for mmc host ip compatible with mt2712 "mediatek,mt7622-mmc": for MT7622 SoC -- cgit v1.2.3 From afb7c7910bf3c42b56f99c9d6bb82099d0a0794d Mon Sep 17 00:00:00 2001 From: NeilBrown Date: Sat, 4 May 2019 20:24:56 +1000 Subject: mmc: mtk-sd: add support for config found in mt7620 family SOCs. mt7620 family MIPS SOCs contain the mtk-sd silicon. Add support for this. Signed-off-by: NeilBrown Reviewed-by: Chaotian Jing Signed-off-by: Ulf Hansson --- Documentation/devicetree/bindings/mmc/mtk-sd.txt | 1 + drivers/mmc/host/mtk-sd.c | 12 ++++++++++++ 2 files changed, 13 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mmc/mtk-sd.txt b/Documentation/devicetree/bindings/mmc/mtk-sd.txt index 91a2ec59e497..8a532f4453f2 100644 --- a/Documentation/devicetree/bindings/mmc/mtk-sd.txt +++ b/Documentation/devicetree/bindings/mmc/mtk-sd.txt @@ -16,6 +16,7 @@ Required properties: "mediatek,mt2712-mmc": for mmc host ip compatible with mt2712 "mediatek,mt7622-mmc": for MT7622 SoC "mediatek,mt7623-mmc", "mediatek,mt2701-mmc": for MT7623 SoC + "mediatek,mt7620-mmc", for MT7621 SoC (and others) - reg: physical base address of the controller and length - interrupts: Should contain MSDC interrupt number diff --git a/drivers/mmc/host/mtk-sd.c b/drivers/mmc/host/mtk-sd.c index 469d4a717175..0c2be4f54b1f 100644 --- a/drivers/mmc/host/mtk-sd.c +++ b/drivers/mmc/host/mtk-sd.c @@ -517,6 +517,17 @@ static const struct mtk_mmc_compatible mt8516_compat = { .stop_clk_fix = true, }; +static const struct mtk_mmc_compatible mt7620_compat = { + .clk_div_bits = 8, + .hs400_tune = false, + .pad_tune_reg = MSDC_PAD_TUNE, + .async_fifo = false, + .data_tune = false, + .busy_check = false, + .stop_clk_fix = false, + .enhance_rx = false, +}; + static const struct of_device_id msdc_of_ids[] = { { .compatible = "mediatek,mt8135-mmc", .data = &mt8135_compat}, { .compatible = "mediatek,mt8173-mmc", .data = &mt8173_compat}, @@ -525,6 +536,7 @@ static const struct of_device_id msdc_of_ids[] = { { .compatible = "mediatek,mt2712-mmc", .data = &mt2712_compat}, { .compatible = "mediatek,mt7622-mmc", .data = &mt7622_compat}, { .compatible = "mediatek,mt8516-mmc", .data = &mt8516_compat}, + { .compatible = "mediatek,mt7620-mmc", .data = &mt7620_compat}, {} }; MODULE_DEVICE_TABLE(of, msdc_of_ids); -- cgit v1.2.3 From 343682173846c68f231929a5b84584ab7a845a0b Mon Sep 17 00:00:00 2001 From: Yinbo Zhu Date: Sun, 5 May 2019 05:57:24 +0000 Subject: dt-bindings: mmc: add DT bindings for ls1028a eSDHC host controller Add "fsl,ls1028a-esdhc" bindings for ls1028a eSDHC host controller Signed-off-by: Yinbo Zhu Signed-off-by: Ulf Hansson --- Documentation/devicetree/bindings/mmc/fsl-esdhc.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mmc/fsl-esdhc.txt b/Documentation/devicetree/bindings/mmc/fsl-esdhc.txt index 99c5cf8507e8..edb8cadb9541 100644 --- a/Documentation/devicetree/bindings/mmc/fsl-esdhc.txt +++ b/Documentation/devicetree/bindings/mmc/fsl-esdhc.txt @@ -17,6 +17,7 @@ Required properties: "fsl,t4240-esdhc" Possible compatibles for ARM: "fsl,ls1012a-esdhc" + "fsl,ls1028a-esdhc" "fsl,ls1088a-esdhc" "fsl,ls1043a-esdhc" "fsl,ls1046a-esdhc" -- cgit v1.2.3 From daa82b93f5b0bdc67e5cf594d55c0c8d84a406c9 Mon Sep 17 00:00:00 2001 From: Jonas Gorski Date: Thu, 28 Mar 2019 15:19:06 +0100 Subject: dt-bindings: mtd: describe the simple BCM963XX NOR flash layout Add binding documentation for the standard CFE based BCM963XX flash layout, found in most devices using a BCM63XX SoC with NOR flash. Reviewed-by: Rob Herring Signed-off-by: Jonas Gorski Reviewed-by: Florian Fainelli Signed-off-by: Richard Weinberger --- .../brcm,bcm963xx-cfe-nor-partitions.txt | 24 ++++++++++++++++++++++ 1 file changed, 24 insertions(+) create mode 100644 Documentation/devicetree/bindings/mtd/partitions/brcm,bcm963xx-cfe-nor-partitions.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mtd/partitions/brcm,bcm963xx-cfe-nor-partitions.txt b/Documentation/devicetree/bindings/mtd/partitions/brcm,bcm963xx-cfe-nor-partitions.txt new file mode 100644 index 000000000000..9f630e95f180 --- /dev/null +++ b/Documentation/devicetree/bindings/mtd/partitions/brcm,bcm963xx-cfe-nor-partitions.txt @@ -0,0 +1,24 @@ +Broadcom BCM963XX CFE Loader NOR Flash Partitions +================================================= + +Most Broadcom BCM63XX SoC based devices follow the Broadcom reference layout for +NOR. The first erase block used for the CFE bootloader, the last for an +NVRAM partition, and the remainder in-between for one to two firmware partitions +at fixed offsets. A valid firmware partition is identified by the ImageTag +header found at beginning of the second erase block, containing the rootfs and +kernel offsets and sizes within the firmware partition. + +Required properties: +- compatible : must be "brcm,bcm963xx-cfe-nor-partitions" + +Example: + +flash@1fc00000 { + compatible = "cfi-flash"; + reg = <0x1fc00000 0x400000>; + bank-width = <2>; + + partitions { + compatible = "brcm,bcm963xx-cfe-nor-partitions"; + }; +}; -- cgit v1.2.3 From 6744ebb0c798ac3717ceb5da1a479d9314dd641c Mon Sep 17 00:00:00 2001 From: Jonas Gorski Date: Thu, 28 Mar 2019 15:19:09 +0100 Subject: dt-bindings: mtd: describe BCM963XX ImageTag format and usage Describe how to use the BCM963XX ImageTag format in a mixed flash layout environment. Reviewed-by: Rob Herring Signed-off-by: Jonas Gorski Reviewed-by: Florian Fainelli Signed-off-by: Richard Weinberger --- .../mtd/partitions/brcm,bcm963xx-imagetag.txt | 45 ++++++++++++++++++++++ 1 file changed, 45 insertions(+) create mode 100644 Documentation/devicetree/bindings/mtd/partitions/brcm,bcm963xx-imagetag.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mtd/partitions/brcm,bcm963xx-imagetag.txt b/Documentation/devicetree/bindings/mtd/partitions/brcm,bcm963xx-imagetag.txt new file mode 100644 index 000000000000..f8b7418ed817 --- /dev/null +++ b/Documentation/devicetree/bindings/mtd/partitions/brcm,bcm963xx-imagetag.txt @@ -0,0 +1,45 @@ +Broadcom BCM963XX ImageTag Partition Container +============================================== + +Some Broadcom BCM63XX SoC based devices contain additional, non discoverable +partitions or non standard bootloader partition sizes. For these a mixed layout +needs to be used with an explicit firmware partition. + +The BCM963XX ImageTag is a simple firmware header describing the offsets and +sizes of the rootfs and kernel parts contained in the firmware. + +Required properties: +- compatible : must be "brcm,bcm963xx-imagetag" + +Example: + +flash@1e000000 { + compatible = "cfi-flash"; + reg = <0x1e000000 0x2000000>; + bank-width = <2>; + + partitions { + compatible = "fixed-partitions"; + #address-cells = <1>; + #size-cells = <1>; + + cfe@0 { + reg = <0x0 0x10000>; + read-only; + }; + + firmware@10000 { + reg = <0x10000 0x7d0000>; + compatible = "brcm,bcm963xx-imagetag"; + }; + + caldata@7e0000 { + reg = <0x7e0000 0x10000>; + read-only; + }; + + nvram@7f0000 { + reg = <0x7f0000 0x10000>; + }; + }; +}; -- cgit v1.2.3 From 6e9314dc051f9a5e9120954f2d6de9c8e5d8c522 Mon Sep 17 00:00:00 2001 From: Chris Packham Date: Fri, 29 Mar 2019 15:13:22 +1300 Subject: dt-binding: mtd: physmap: Add example using addr-gpios property Add an example showing how to use the addr-gpios property to deal with a system with limited IO space. Cc: devicetree@vger.kernel.org Signed-off-by: Chris Packham Reviewed-by: Rob Herring Signed-off-by: Richard Weinberger --- Documentation/devicetree/bindings/mtd/mtd-physmap.txt | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mtd/mtd-physmap.txt b/Documentation/devicetree/bindings/mtd/mtd-physmap.txt index 7df0dcaccb7d..c69f4f065d23 100644 --- a/Documentation/devicetree/bindings/mtd/mtd-physmap.txt +++ b/Documentation/devicetree/bindings/mtd/mtd-physmap.txt @@ -96,3 +96,19 @@ An example using SRAM: bank-width = <2>; }; +An example using gpio-addrs + + flash@20000000 { + #address-cells = <1>; + #size-cells = <1>; + compatible = "cfi-flash", "jedec-flash"; + reg = <0x20000000 0x02000000>; + ranges = <0 0x00000000 0x02000000 + 1 0x02000000 0x02000000>; + bank-width = <2>; + addr-gpios = <&gpio1 2 GPIO_ACTIVE_HIGH>; + partition@0 { + label = "test-part1"; + reg = <0 0x04000000>; + }; + }; -- cgit v1.2.3 From 2485fa5323316968e73a2b46ea0bc554c37b7e83 Mon Sep 17 00:00:00 2001 From: Linus Walleij Date: Thu, 2 May 2019 16:30:27 +0200 Subject: mtd: partitions: Add AFS partitions DT bindings This adds device tree bindings for ARM Firmware Suite flash partitioning used in NOR flashes on ARM reference designs. Cc: devicetree@vger.kernel.org Reviewed-by: Rob Herring Signed-off-by: Linus Walleij Signed-off-by: Richard Weinberger --- .../bindings/mtd/partitions/arm,arm-firmware-suite.txt | 17 +++++++++++++++++ 1 file changed, 17 insertions(+) create mode 100644 Documentation/devicetree/bindings/mtd/partitions/arm,arm-firmware-suite.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mtd/partitions/arm,arm-firmware-suite.txt b/Documentation/devicetree/bindings/mtd/partitions/arm,arm-firmware-suite.txt new file mode 100644 index 000000000000..d5c5616f6db5 --- /dev/null +++ b/Documentation/devicetree/bindings/mtd/partitions/arm,arm-firmware-suite.txt @@ -0,0 +1,17 @@ +ARM AFS - ARM Firmware Suite Partitions +======================================= + +The ARM Firmware Suite is a flash partitioning system found on the +ARM reference designs: Integrator AP, Integrator CP, Versatile AB, +Versatile PB, the RealView family, Versatile Express and Juno. + +Required properties: +- compatible : (required) must be "arm,arm-firmware-suite" + +Example: + +flash@0 { + partitions { + compatible = "arm,arm-firmware-suite"; + }; +}; -- cgit v1.2.3 From 898490c010b5d2e499e03b7e815fc214209ac583 Mon Sep 17 00:00:00 2001 From: Alexey Gladkov Date: Mon, 29 Apr 2019 18:11:14 +0200 Subject: moduleparam: Save information about built-in modules in separate file Problem: When a kernel module is compiled as a separate module, some important information about the kernel module is available via .modinfo section of the module. In contrast, when the kernel module is compiled into the kernel, that information is not available. Information about built-in modules is necessary in the following cases: 1. When it is necessary to find out what additional parameters can be passed to the kernel at boot time. 2. When you need to know which module names and their aliases are in the kernel. This is very useful for creating an initrd image. Proposal: The proposed patch does not remove .modinfo section with module information from the vmlinux at the build time and saves it into a separate file after kernel linking. So, the kernel does not increase in size and no additional information remains in it. Information is stored in the same format as in the separate modules (null-terminated string array). Because the .modinfo section is already exported with a separate modules, we are not creating a new API. It can be easily read in the userspace: $ tr '\0' '\n' < modules.builtin.modinfo ext4.softdep=pre: crc32c ext4.license=GPL ext4.description=Fourth Extended Filesystem ext4.author=Remy Card, Stephen Tweedie, Andrew Morton, Andreas Dilger, Theodore Ts'o and others ext4.alias=fs-ext4 ext4.alias=ext3 ext4.alias=fs-ext3 ext4.alias=ext2 ext4.alias=fs-ext2 md_mod.alias=block-major-9-* md_mod.alias=md md_mod.description=MD RAID framework md_mod.license=GPL md_mod.parmtype=create_on_open:bool md_mod.parmtype=start_dirty_degraded:int ... Co-Developed-by: Gleb Fotengauer-Malinovskiy Signed-off-by: Gleb Fotengauer-Malinovskiy Signed-off-by: Alexey Gladkov Acked-by: Jessica Yu Signed-off-by: Masahiro Yamada --- .gitignore | 1 + Documentation/dontdiff | 1 + Documentation/kbuild/kbuild.txt | 5 +++++ Makefile | 2 ++ include/asm-generic/vmlinux.lds.h | 1 + include/linux/module.h | 1 + include/linux/moduleparam.h | 12 +++++------- scripts/link-vmlinux.sh | 3 +++ 8 files changed, 19 insertions(+), 7 deletions(-) (limited to 'Documentation') diff --git a/.gitignore b/.gitignore index e7bb6c6edbae..2fb1765c33b0 100644 --- a/.gitignore +++ b/.gitignore @@ -58,6 +58,7 @@ modules.builtin /vmlinuz /System.map /Module.markers +/modules.builtin.modinfo # # RPM spec file (make rpm-pkg) diff --git a/Documentation/dontdiff b/Documentation/dontdiff index ef25a066d952..512fa0239ebf 100644 --- a/Documentation/dontdiff +++ b/Documentation/dontdiff @@ -178,6 +178,7 @@ mktables mktree modpost modules.builtin +modules.builtin.modinfo modules.order modversions.h* nconf diff --git a/Documentation/kbuild/kbuild.txt b/Documentation/kbuild/kbuild.txt index 8a3830b39c7d..9c230ea71963 100644 --- a/Documentation/kbuild/kbuild.txt +++ b/Documentation/kbuild/kbuild.txt @@ -11,6 +11,11 @@ modules.builtin This file lists all modules that are built into the kernel. This is used by modprobe to not fail when trying to load something builtin. +modules.builtin.modinfo +-------------------------------------------------- +This file contains modinfo from all modules that are built into the kernel. +Unlike modinfo of a separate module, all fields are prefixed with module name. + Environment variables diff --git a/Makefile b/Makefile index 85dd977f4232..9a8b3f94633d 100644 --- a/Makefile +++ b/Makefile @@ -1308,6 +1308,7 @@ _modinst_: fi @cp -f $(objtree)/modules.order $(MODLIB)/ @cp -f $(objtree)/modules.builtin $(MODLIB)/ + @cp -f $(objtree)/modules.builtin.modinfo $(MODLIB)/ $(Q)$(MAKE) -f $(srctree)/scripts/Makefile.modinst # This depmod is only for convenience to give the initial @@ -1348,6 +1349,7 @@ endif # CONFIG_MODULES # Directories & files removed with 'make clean' CLEAN_DIRS += $(MODVERDIR) include/ksym +CLEAN_FILES += modules.builtin.modinfo # Directories & files removed with 'make mrproper' MRPROPER_DIRS += include/config usr/include include/generated \ diff --git a/include/asm-generic/vmlinux.lds.h b/include/asm-generic/vmlinux.lds.h index f8f6f04c4453..bbb9e332f2fe 100644 --- a/include/asm-generic/vmlinux.lds.h +++ b/include/asm-generic/vmlinux.lds.h @@ -844,6 +844,7 @@ EXIT_CALL \ *(.discard) \ *(.discard.*) \ + *(.modinfo) \ } /** diff --git a/include/linux/module.h b/include/linux/module.h index 5bf5dcd91009..5f7007430d35 100644 --- a/include/linux/module.h +++ b/include/linux/module.h @@ -253,6 +253,7 @@ extern typeof(name) __mod_##type##__##name##_device_table \ #define MODULE_VERSION(_version) MODULE_INFO(version, _version) #else #define MODULE_VERSION(_version) \ + MODULE_INFO(version, _version); \ static struct module_version_attribute ___modver_attr = { \ .mattr = { \ .attr = { \ diff --git a/include/linux/moduleparam.h b/include/linux/moduleparam.h index ba36506db4fb..5ba250d9172a 100644 --- a/include/linux/moduleparam.h +++ b/include/linux/moduleparam.h @@ -10,23 +10,21 @@ module name. */ #ifdef MODULE #define MODULE_PARAM_PREFIX /* empty */ +#define __MODULE_INFO_PREFIX /* empty */ #else #define MODULE_PARAM_PREFIX KBUILD_MODNAME "." +/* We cannot use MODULE_PARAM_PREFIX because some modules override it. */ +#define __MODULE_INFO_PREFIX KBUILD_MODNAME "." #endif /* Chosen so that structs with an unsigned long line up. */ #define MAX_PARAM_PREFIX_LEN (64 - sizeof(unsigned long)) -#ifdef MODULE #define __MODULE_INFO(tag, name, info) \ static const char __UNIQUE_ID(name)[] \ __used __attribute__((section(".modinfo"), unused, aligned(1))) \ - = __stringify(tag) "=" info -#else /* !MODULE */ -/* This struct is here for syntactic coherency, it is not used */ -#define __MODULE_INFO(tag, name, info) \ - struct __UNIQUE_ID(name) {} -#endif + = __MODULE_INFO_PREFIX __stringify(tag) "=" info + #define __MODULE_PARM_TYPE(name, _type) \ __MODULE_INFO(parmtype, name##type, #name ":" _type) diff --git a/scripts/link-vmlinux.sh b/scripts/link-vmlinux.sh index dc0e8c5a1402..e4383e0f476e 100755 --- a/scripts/link-vmlinux.sh +++ b/scripts/link-vmlinux.sh @@ -193,6 +193,9 @@ modpost_link vmlinux.o # modpost vmlinux.o to check for section mismatches ${MAKE} -f "${srctree}/scripts/Makefile.modpost" vmlinux.o +info MODINFO modules.builtin.modinfo +${OBJCOPY} -j .modinfo -O binary vmlinux.o modules.builtin.modinfo + kallsymso="" kallsyms_vmlinux="" if [ -n "${CONFIG_KALLSYMS}" ]; then -- cgit v1.2.3 From 0fbee1df2078fa1f61e2da14f51ceb357c79ae69 Mon Sep 17 00:00:00 2001 From: Linus Walleij Date: Sat, 20 Apr 2019 13:03:34 +0200 Subject: gpio: Update documentation Strictify the language a bit, move things around, make proper headings, mention pull-up and pull-down, expand unreadable acronyms etc. Signed-off-by: Linus Walleij --- Documentation/driver-api/gpio/driver.rst | 361 ++++++++++++++++++++----------- 1 file changed, 229 insertions(+), 132 deletions(-) (limited to 'Documentation') diff --git a/Documentation/driver-api/gpio/driver.rst b/Documentation/driver-api/gpio/driver.rst index 3043167fc557..1ce7fcd0f989 100644 --- a/Documentation/driver-api/gpio/driver.rst +++ b/Documentation/driver-api/gpio/driver.rst @@ -1,10 +1,8 @@ -================================ -GPIO Descriptor Driver Interface -================================ +===================== +GPIO Driver Interface +===================== -This document serves as a guide for GPIO chip drivers writers. Note that it -describes the new descriptor-based interface. For a description of the -deprecated integer-based GPIO interface please refer to gpio-legacy.txt. +This document serves as a guide for writers of GPIO chip drivers. Each GPIO controller driver needs to include the following header, which defines the structures used to define a GPIO driver: @@ -15,32 +13,49 @@ the structures used to define a GPIO driver: Internal Representation of GPIOs ================================ -Inside a GPIO driver, individual GPIOs are identified by their hardware number, -which is a unique number between 0 and n, n being the number of GPIOs managed by -the chip. This number is purely internal: the hardware number of a particular -GPIO descriptor is never made visible outside of the driver. - -On top of this internal number, each GPIO also need to have a global number in -the integer GPIO namespace so that it can be used with the legacy GPIO +A GPIO chip handles one or more GPIO lines. To be considered a GPIO chip, the +lines must conform to the definition: General Purpose Input/Output. If the +line is not general purpose, it is not GPIO and should not be handled by a +GPIO chip. The use case is the indicative: certain lines in a system may be +called GPIO but serve a very particular purpose thus not meeting the criteria +of a general purpose I/O. On the other hand a LED driver line may be used as a +GPIO and should therefore still be handled by a GPIO chip driver. + +Inside a GPIO driver, individual GPIO lines are identified by their hardware +number, sometime also referred to as ``offset``, which is a unique number +between 0 and n-1, n being the number of GPIOs managed by the chip. + +The hardware GPIO number should be something intuitive to the hardware, for +example if a system uses a memory-mapped set of I/O-registers where 32 GPIO +lines are handled by one bit per line in a 32-bit register, it makes sense to +use hardware offsets 0..31 for these, corresponding to bits 0..31 in the +register. + +This number is purely internal: the hardware number of a particular GPIO +line is never made visible outside of the driver. + +On top of this internal number, each GPIO line also needs to have a global +number in the integer GPIO namespace so that it can be used with the legacy GPIO interface. Each chip must thus have a "base" number (which can be automatically -assigned), and for each GPIO the global number will be (base + hardware number). -Although the integer representation is considered deprecated, it still has many -users and thus needs to be maintained. +assigned), and for each GPIO line the global number will be (base + hardware +number). Although the integer representation is considered deprecated, it still +has many users and thus needs to be maintained. -So for example one platform could use numbers 32-159 for GPIOs, with a +So for example one platform could use global numbers 32-159 for GPIOs, with a controller defining 128 GPIOs at a "base" of 32 ; while another platform uses -numbers 0..63 with one set of GPIO controllers, 64-79 with another type of GPIO -controller, and on one particular board 80-95 with an FPGA. The numbers need not -be contiguous; either of those platforms could also use numbers 2000-2063 to -identify GPIOs in a bank of I2C GPIO expanders. +global numbers 0..63 with one set of GPIO controllers, 64-79 with another type +of GPIO controller, and on one particular board 80-95 with an FPGA. The legacy +numbers need not be contiguous; either of those platforms could also use numbers +2000-2063 to identify GPIO lines in a bank of I2C GPIO expanders. Controller Drivers: gpio_chip ============================= In the gpiolib framework each GPIO controller is packaged as a "struct -gpio_chip" (see linux/gpio/driver.h for its complete definition) with members -common to each controller of that type: +gpio_chip" (see for its complete definition) with members +common to each controller of that type, these should be assigned by the +driver code: - methods to establish GPIO line direction - methods used to access GPIO line values @@ -48,12 +63,12 @@ common to each controller of that type: - method to return the IRQ number associated to a given GPIO line - flag saying whether calls to its methods may sleep - optional line names array to identify lines - - optional debugfs dump method (showing extra state like pullup config) + - optional debugfs dump method (showing extra state information) - optional base number (will be automatically assigned if omitted) - optional label for diagnostics and GPIO chip mapping using platform data The code implementing a gpio_chip should support multiple instances of the -controller, possibly using the driver model. That code will configure each +controller, preferably using the driver model. That code will configure each gpio_chip and issue ``gpiochip_add[_data]()`` or ``devm_gpiochip_add_data()``. Removing a GPIO controller should be rare; use ``[devm_]gpiochip_remove()`` when it is unavoidable. @@ -62,24 +77,28 @@ Often a gpio_chip is part of an instance-specific structure with states not exposed by the GPIO interfaces, such as addressing, power management, and more. Chips such as audio codecs will have complex non-GPIO states. -Any debugfs dump method should normally ignore signals which haven't been -requested as GPIOs. They can use gpiochip_is_requested(), which returns either -NULL or the label associated with that GPIO when it was requested. +Any debugfs dump method should normally ignore lines which haven't been +requested. They can use gpiochip_is_requested(), which returns either +NULL or the label associated with that GPIO line when it was requested. -RT_FULL: the GPIO driver should not use spinlock_t or any sleepable APIs -(like PM runtime) in its gpio_chip implementation (.get/.set and direction -control callbacks) if it is expected to call GPIO APIs from atomic context -on -RT (inside hard IRQ handlers and similar contexts). Normally this should -not be required. +Realtime considerations: the GPIO driver should not use spinlock_t or any +sleepable APIs (like PM runtime) in its gpio_chip implementation (.get/.set +and direction control callbacks) if it is expected to call GPIO APIs from +atomic context on realtime kernels (inside hard IRQ handlers and similar +contexts). Normally this should not be required. GPIO electrical configuration ----------------------------- -GPIOs can be configured for several electrical modes of operation by using the -.set_config() callback. Currently this API supports setting debouncing and -single-ended modes (open drain/open source). These settings are described -below. +GPIO lines can be configured for several electrical modes of operation by using +the .set_config() callback. Currently this API supports setting: + +- Debouncing +- Single-ended modes (open drain/open source) +- Pull up and pull down resistor enablement + +These settings are described below. The .set_config() callback uses the same enumerators and configuration semantics as the generic pin control drivers. This is not a coincidence: it is @@ -94,8 +113,8 @@ description needs to provide "GPIO ranges" mapping the GPIO line offsets to pin numbers on the pin controller so they can properly cross-reference each other. -GPIOs with debounce support ---------------------------- +GPIO lines with debounce support +-------------------------------- Debouncing is a configuration set to a pin indicating that it is connected to a mechanical switch or button, or similar that may bounce. Bouncing means the @@ -111,8 +130,8 @@ a certain number of milliseconds for debouncing, or just "on/off" if that time is not configurable. -GPIOs with open drain/source support ------------------------------------- +GPIO lines with open drain/source support +----------------------------------------- Open drain (CMOS) or open collector (TTL) means the line is not actively driven high: instead you provide the drain/collector as output, so when the transistor @@ -132,13 +151,13 @@ This configuration is normally used as a way to achieve one of two things: - Level-shifting: to reach a logical level higher than that of the silicon where the output resides. -- inverse wire-OR on an I/O line, for example a GPIO line, making it possible +- Inverse wire-OR on an I/O line, for example a GPIO line, making it possible for any driving stage on the line to drive it low even if any other output to the same line is simultaneously driving it high. A special case of this is driving the SCL and SDA lines of an I2C bus, which is by definition a wire-OR bus. -Both usecases require that the line be equipped with a pull-up resistor. This +Both use cases require that the line be equipped with a pull-up resistor. This resistor will make the line tend to high level unless one of the transistors on the rail actively pulls it down. @@ -208,27 +227,91 @@ For open source configuration the same principle is used, just that instead of actively driving the line low, it is set to input. +GPIO lines with pull up/down resistor support +--------------------------------------------- + +A GPIO line can support pull-up/down using the .set_config() callback. This +means that a pull up or pull-down resistor is available on the output of the +GPIO line, and this resistor is software controlled. + +In discrete designs, a pull-up or pull-down resistor is simply soldered on +the circuit board. This is not something we deal or model in software. The +most you will think about these lines is that they will very likely be +configured as open drain or open source (see the section above). + +The .set_config() callback can only turn pull up or down on and off, and will +no have any semantic knowledge about the resistance used. It will only say +switch a bit in a register enabling or disabling pull-up or pull-down. + +If the GPIO line supports shunting in different resistance values for the +pull-up or pull-down resistor, the GPIO chip callback .set_config() will not +suffice. For these complex use cases, a combined GPIO chip and pin controller +need to be implemented, as the pin config interface of a pin controller +supports more versatile control over electrical properties and can handle +different pull-up or pull-down resistance values. + + GPIO drivers providing IRQs ---------------------------- +=========================== + It is custom that GPIO drivers (GPIO chips) are also providing interrupts, most often cascaded off a parent interrupt controller, and in some special cases the GPIO logic is melded with a SoC's primary interrupt controller. -The IRQ portions of the GPIO block are implemented using an irqchip, using +The IRQ portions of the GPIO block are implemented using an irq_chip, using the header . So basically such a driver is utilizing two sub- systems simultaneously: gpio and irq. -RT_FULL: a realtime compliant GPIO driver should not use spinlock_t or any -sleepable APIs (like PM runtime) as part of its irq_chip implementation. +It is legal for any IRQ consumer to request an IRQ from any irqchip even if it +is a combined GPIO+IRQ driver. The basic premise is that gpio_chip and +irq_chip are orthogonal, and offering their services independent of each +other. -* spinlock_t should be replaced with raw_spinlock_t [1]. -* If sleepable APIs have to be used, these can be done from the .irq_bus_lock() +gpiod_to_irq() is just a convenience function to figure out the IRQ for a +certain GPIO line and should not be relied upon to have been called before +the IRQ is used. + +Always prepare the hardware and make it ready for action in respective +callbacks from the GPIO and irq_chip APIs. Do not rely on gpiod_to_irq() having +been called first. + +We can divide GPIO irqchips in two broad categories: + +- CASCADED INTERRUPT CHIPS: this means that the GPIO chip has one common + interrupt output line, which is triggered by any enabled GPIO line on that + chip. The interrupt output line will then be routed to an parent interrupt + controller one level up, in the most simple case the systems primary + interrupt controller. This is modeled by an irqchip that will inspect bits + inside the GPIO controller to figure out which line fired it. The irqchip + part of the driver needs to inspect registers to figure this out and it + will likely also need to acknowledge that it is handling the interrupt + by clearing some bit (sometime implicitly, by just reading a status + register) and it will often need to set up the configuration such as + edge sensitivity (rising or falling edge, or high/low level interrupt for + example). + +- HIERARCHICAL INTERRUPT CHIPS: this means that each GPIO line has a dedicated + irq line to a parent interrupt controller one level up. There is no need + to inquire the GPIO hardware to figure out which line has figured, but it + may still be necessary to acknowledge the interrupt and set up the + configuration such as edge sensitivity. + +Realtime considerations: a realtime compliant GPIO driver should not use +spinlock_t or any sleepable APIs (like PM runtime) as part of its irqchip +implementation. + +- spinlock_t should be replaced with raw_spinlock_t [1]. +- If sleepable APIs have to be used, these can be done from the .irq_bus_lock() and .irq_bus_unlock() callbacks, as these are the only slowpath callbacks on an irqchip. Create the callbacks if needed [2]. -GPIO irqchips usually fall in one of two categories: -* CHAINED GPIO irqchips: these are usually the type that is embedded on +Cascaded GPIO irqchips +---------------------- + +Cascaded GPIO irqchips usually fall in one of three categories: + +- CHAINED CASCADED GPIO IRQCHIPS: these are usually the type that is embedded on an SoC. This means that there is a fast IRQ flow handler for the GPIOs that gets called in a chain from the parent IRQ handler, most typically the system interrupt controller. This means that the GPIO irqchip handler will @@ -245,16 +328,19 @@ GPIO irqchips usually fall in one of two categories: struct gpio_chip, as everything happens directly in the callbacks: no slow bus traffic like I2C can be used. - RT_FULL: Note, chained IRQ handlers will not be forced threaded on -RT. - As result, spinlock_t or any sleepable APIs (like PM runtime) can't be used - in chained IRQ handler. - If required (and if it can't be converted to the nested threaded GPIO irqchip) - a chained IRQ handler can be converted to generic irq handler and this way - it will be a threaded IRQ handler on -RT and a hard IRQ handler on non-RT - (for example, see [3]). - Know W/A: The generic_handle_irq() is expected to be called with IRQ disabled, + Realtime considerations: Note that chained IRQ handlers will not be forced + threaded on -RT. As a result, spinlock_t or any sleepable APIs (like PM + runtime) can't be used in a chained IRQ handler. + + If required (and if it can't be converted to the nested threaded GPIO irqchip, + see below) a chained IRQ handler can be converted to generic irq handler and + this way it will become a threaded IRQ handler on -RT and a hard IRQ handler + on non-RT (for example, see [3]). + + The generic_handle_irq() is expected to be called with IRQ disabled, so the IRQ core will complain if it is called from an IRQ handler which is - forced to a thread. The "fake?" raw lock can be used to W/A this problem:: + forced to a thread. The "fake?" raw lock can be used to work around this + problem:: raw_spinlock_t wa_lock; static irqreturn_t omap_gpio_irq_handler(int irq, void *gpiobank) @@ -263,7 +349,7 @@ GPIO irqchips usually fall in one of two categories: generic_handle_irq(irq_find_mapping(bank->chip.irq.domain, bit)); raw_spin_unlock_irqrestore(&bank->wa_lock, wa_lock_flags); -* GENERIC CHAINED GPIO irqchips: these are the same as "CHAINED GPIO irqchips", +- GENERIC CHAINED GPIO IRQCHIPS: these are the same as "CHAINED GPIO irqchips", but chained IRQ handlers are not used. Instead GPIO IRQs dispatching is performed by generic IRQ handler which is configured using request_irq(). The GPIO irqchip will then end up calling something like this sequence in @@ -273,16 +359,19 @@ GPIO irqchips usually fall in one of two categories: for each detected GPIO IRQ generic_handle_irq(...); - RT_FULL: Such kind of handlers will be forced threaded on -RT, as result IRQ - core will complain that generic_handle_irq() is called with IRQ enabled and - the same W/A as for "CHAINED GPIO irqchips" can be applied. + Realtime considerations: this kind of handlers will be forced threaded on -RT, + and as result the IRQ core will complain that generic_handle_irq() is called + with IRQ enabled and the same work around as for "CHAINED GPIO irqchips" can + be applied. + +- NESTED THREADED GPIO IRQCHIPS: these are off-chip GPIO expanders and any + other GPIO irqchip residing on the other side of a sleeping bus such as I2C + or SPI. -* NESTED THREADED GPIO irqchips: these are off-chip GPIO expanders and any - other GPIO irqchip residing on the other side of a sleeping bus. Of course - such drivers that need slow bus traffic to read out IRQ status and similar, - traffic which may in turn incur other IRQs to happen, cannot be handled - in a quick IRQ handler with IRQs disabled. Instead they need to spawn a - thread and then mask the parent IRQ line until the interrupt is handled + Of course such drivers that need slow bus traffic to read out IRQ status and + similar, traffic which may in turn incur other IRQs to happen, cannot be + handled in a quick IRQ handler with IRQs disabled. Instead they need to spawn + a thread and then mask the parent IRQ line until the interrupt is handled by the driver. The hallmark of this driver is to call something like this in its interrupt handler:: @@ -294,36 +383,46 @@ GPIO irqchips usually fall in one of two categories: flag on struct gpio_chip to true, indicating that this chip may sleep when accessing the GPIOs. + These kinds of irqchips are inherently realtime tolerant as they are + already set up to handle sleeping contexts. + + +Infrastructure helpers for GPIO irqchips +---------------------------------------- + To help out in handling the set-up and management of GPIO irqchips and the associated irqdomain and resource allocation callbacks, the gpiolib has some helpers that can be enabled by selecting the GPIOLIB_IRQCHIP Kconfig symbol: -* gpiochip_irqchip_add(): adds a chained irqchip to a gpiochip. It will pass - the struct gpio_chip* for the chip to all IRQ callbacks, so the callbacks - need to embed the gpio_chip in its state container and obtain a pointer - to the container using container_of(). +- gpiochip_irqchip_add(): adds a chained cascaded irqchip to a gpiochip. It + will pass the struct gpio_chip* for the chip to all IRQ callbacks, so the + callbacks need to embed the gpio_chip in its state container and obtain a + pointer to the container using container_of(). (See Documentation/driver-model/design-patterns.txt) -* gpiochip_irqchip_add_nested(): adds a nested irqchip to a gpiochip. +- gpiochip_irqchip_add_nested(): adds a nested cascaded irqchip to a gpiochip, + as discussed above regarding different types of cascaded irqchips. The + cascaded irq has to be handled by a threaded interrupt handler. Apart from that it works exactly like the chained irqchip. -* gpiochip_set_chained_irqchip(): sets up a chained irq handler for a +- gpiochip_set_chained_irqchip(): sets up a chained cascaded irq handler for a gpio_chip from a parent IRQ and passes the struct gpio_chip* as handler - data. (Notice handler data, since the irqchip data is likely used by the - parent irqchip!). + data. Notice that we pass is as the handler data, since the irqchip data is + likely used by the parent irqchip. -* gpiochip_set_nested_irqchip(): sets up a nested irq handler for a +- gpiochip_set_nested_irqchip(): sets up a nested cascaded irq handler for a gpio_chip from a parent IRQ. As the parent IRQ has usually been explicitly requested by the driver, this does very little more than mark all the child IRQs as having the other IRQ as parent. -If there is a need to exclude certain GPIOs from the IRQ domain, you can -set .irq.need_valid_mask of the gpiochip before gpiochip_add_data() is -called. This allocates an .irq.valid_mask with as many bits set as there -are GPIOs in the chip. Drivers can exclude GPIOs by clearing bits from this -mask. The mask must be filled in before gpiochip_irqchip_add() or -gpiochip_irqchip_add_nested() is called. +If there is a need to exclude certain GPIO lines from the IRQ domain handled by +these helpers, we can set .irq.need_valid_mask of the gpiochip before +[devm_]gpiochip_add_data() is called. This allocates an .irq.valid_mask with as +many bits set as there are GPIO lines in the chip, each bit representing line +0..n-1. Drivers can exclude GPIO lines by clearing bits from this mask. The mask +must be filled in before gpiochip_irqchip_add() or gpiochip_irqchip_add_nested() +is called. To use the helpers please keep the following in mind: @@ -333,33 +432,24 @@ To use the helpers please keep the following in mind: - Nominally set all handlers to handle_bad_irq() in the setup call and pass handle_bad_irq() as flow handler parameter in gpiochip_irqchip_add() if it is - expected for GPIO driver that irqchip .set_type() callback have to be called - before using/enabling GPIO IRQ. Then set the handler to handle_level_irq() - and/or handle_edge_irq() in the irqchip .set_type() callback depending on - what your controller supports. + expected for GPIO driver that irqchip .set_type() callback will be called + before using/enabling each GPIO IRQ. Then set the handler to + handle_level_irq() and/or handle_edge_irq() in the irqchip .set_type() + callback depending on what your controller supports and what is requested + by the consumer. -It is legal for any IRQ consumer to request an IRQ from any irqchip no matter -if that is a combined GPIO+IRQ driver. The basic premise is that gpio_chip and -irq_chip are orthogonal, and offering their services independent of each -other. - -gpiod_to_irq() is just a convenience function to figure out the IRQ for a -certain GPIO line and should not be relied upon to have been called before -the IRQ is used. -So always prepare the hardware and make it ready for action in respective -callbacks from the GPIO and irqchip APIs. Do not rely on gpiod_to_irq() having -been called first. +Locking IRQ usage +----------------- -This orthogonality leads to ambiguities that we need to solve: if there is -competition inside the subsystem which side is using the resource (a certain -GPIO line and register for example) it needs to deny certain operations and -keep track of usage inside of the gpiolib subsystem. This is why the API -below exists. +Since GPIO and irq_chip are orthogonal, we can get conflicts between different +use cases. For example a GPIO line used for IRQs should be an input line, +it does not make sense to fire interrupts on an output GPIO. +If there is competition inside the subsystem which side is using the +resource (a certain GPIO line and register for example) it needs to deny +certain operations and keep track of usage inside of the gpiolib subsystem. -Locking IRQ usage ------------------ Input GPIOs can be used as IRQ signals. When this happens, a driver is requested to mark the GPIO as being used as an IRQ:: @@ -380,9 +470,15 @@ assigned. Disabling and enabling IRQs --------------------------- + +In some (fringe) use cases, a driver may be using a GPIO line as input for IRQs, +but occasionally switch that line over to drive output and then back to being +an input with interrupts again. This happens on things like CEC (Consumer +Electronics Control). + When a GPIO is used as an IRQ signal, then gpiolib also needs to know if the IRQ is enabled or disabled. In order to inform gpiolib about this, -a driver should call:: +the irqchip driver should call:: void gpiochip_disable_irq(struct gpio_chip *chip, unsigned int offset) @@ -398,40 +494,45 @@ irqchip. When using the gpiolib irqchip helpers, these callbacks are automatically assigned. + Real-Time compliance for GPIO IRQ chips --------------------------------------- -Any provider of irqchips needs to be carefully tailored to support Real Time +Any provider of irqchips needs to be carefully tailored to support Real-Time preemption. It is desirable that all irqchips in the GPIO subsystem keep this in mind and do the proper testing to assure they are real time-enabled. -So, pay attention on above " RT_FULL:" notes, please. -The following is a checklist to follow when preparing a driver for real -time-compliance: -- ensure spinlock_t is not used as part irq_chip implementation; -- ensure that sleepable APIs are not used as part irq_chip implementation. +So, pay attention on above realtime considerations in the documentation. + +The following is a checklist to follow when preparing a driver for real-time +compliance: + +- ensure spinlock_t is not used as part irq_chip implementation +- ensure that sleepable APIs are not used as part irq_chip implementation If sleepable APIs have to be used, these can be done from the .irq_bus_lock() - and .irq_bus_unlock() callbacks; + and .irq_bus_unlock() callbacks - Chained GPIO irqchips: ensure spinlock_t or any sleepable APIs are not used - from chained IRQ handler; + from the chained IRQ handler - Generic chained GPIO irqchips: take care about generic_handle_irq() calls and - apply corresponding W/A; -- Chained GPIO irqchips: get rid of chained IRQ handler and use generic irq - handler if possible :) -- regmap_mmio: Sry, but you are in trouble :( if MMIO regmap is used as for - GPIO IRQ chip implementation; -- Test your driver with the appropriate in-kernel real time test cases for both - level and edge IRQs. + apply corresponding work-around +- Chained GPIO irqchips: get rid of the chained IRQ handler and use generic irq + handler if possible +- regmap_mmio: it is possible to disable internal locking in regmap by setting + .disable_locking and handling the locking in the GPIO driver +- Test your driver with the appropriate in-kernel real-time test cases for both + level and edge IRQs + +* [1] http://www.spinics.net/lists/linux-omap/msg120425.html +* [2] https://lkml.org/lkml/2015/9/25/494 +* [3] https://lkml.org/lkml/2015/9/25/495 Requesting self-owned GPIO pins -------------------------------- +=============================== Sometimes it is useful to allow a GPIO chip driver to request its own GPIO -descriptors through the gpiolib API. Using gpio_request() for this purpose -does not help since it pins the module to the kernel forever (it calls -try_module_get()). A GPIO driver can use the following functions instead -to request and free descriptors without being pinned to the kernel forever:: +descriptors through the gpiolib API. A GPIO driver can use the following +functions to request and free descriptors:: struct gpio_desc *gpiochip_request_own_desc(struct gpio_desc *desc, u16 hwnum, @@ -446,7 +547,3 @@ gpiochip_free_own_desc(). These functions must be used with care since they do not affect module use count. Do not use the functions to request gpio descriptors not owned by the calling driver. - -* [1] http://www.spinics.net/lists/linux-omap/msg120425.html -* [2] https://lkml.org/lkml/2015/9/25/494 -* [3] https://lkml.org/lkml/2015/9/25/495 -- cgit v1.2.3 From 822dd046d7e22a8d01728200a003da230e4c6f7f Mon Sep 17 00:00:00 2001 From: Maxime Chevallier Date: Tue, 7 May 2019 17:35:55 +0200 Subject: dt-bindings: net: Fix a typo in the phy-mode list for ethernet bindings The phy_mode "2000base-x" is actually supposed to be "1000base-x", even though the commit title of the original patch says otherwise. Fixes: 55601a880690 ("net: phy: Add 2000base-x, 2500base-x and rxaui modes") Signed-off-by: Maxime Chevallier Reviewed-by: Andrew Lunn Signed-off-by: David S. Miller --- Documentation/devicetree/bindings/net/ethernet.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/net/ethernet.txt b/Documentation/devicetree/bindings/net/ethernet.txt index a68621580584..d45b5b56fa39 100644 --- a/Documentation/devicetree/bindings/net/ethernet.txt +++ b/Documentation/devicetree/bindings/net/ethernet.txt @@ -36,7 +36,7 @@ Documentation/devicetree/bindings/phy/phy-bindings.txt. * "smii" * "xgmii" * "trgmii" - * "2000base-x", + * "1000base-x", * "2500base-x", * "rxaui" * "xaui" -- cgit v1.2.3 From 88ad5d1eb147a73ad000c658dff0e5166819e6f2 Mon Sep 17 00:00:00 2001 From: Mikulas Patocka Date: Mon, 29 Apr 2019 14:57:23 +0200 Subject: dm integrity: update documentation Update documentation with the "meta_device" parameter and flags. Signed-off-by: Mikulas Patocka Signed-off-by: Mike Snitzer --- Documentation/device-mapper/dm-integrity.txt | 10 +++++++++- drivers/md/dm-integrity.c | 4 +++- 2 files changed, 12 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/device-mapper/dm-integrity.txt b/Documentation/device-mapper/dm-integrity.txt index 297251b0d2d5..7dc9180cdeac 100644 --- a/Documentation/device-mapper/dm-integrity.txt +++ b/Documentation/device-mapper/dm-integrity.txt @@ -79,6 +79,10 @@ interleave_sectors:number a power of two. If the device is already formatted, the value from the superblock is used. +meta_device:device + Don't interleave the data and metadata on on device. Use a + separate device for metadata. + buffer_sectors:number The number of sectors in one buffer. The value is rounded down to a power of two. @@ -167,7 +171,11 @@ The layout of the formatted block device: provides (i.e. the size of the device minus the size of all metadata and padding). The user of this target should not send bios that access data beyond the "provided data sectors" limit. - * flags - a flag is set if journal_mac is used + * flags + SB_FLAG_HAVE_JOURNAL_MAC - a flag is set if journal_mac is used + SB_FLAG_RECALCULATING - recalculating is in progress + * log2(sectors per block) + * a position where recalculating finished * journal The journal is divided into sections, each section contains: * metadata area (4kiB), it contains journal entries diff --git a/drivers/md/dm-integrity.c b/drivers/md/dm-integrity.c index 1ff02683f6ec..4c3bc16d3750 100644 --- a/drivers/md/dm-integrity.c +++ b/drivers/md/dm-integrity.c @@ -3081,10 +3081,12 @@ bad: * buffer_sectors * journal_watermark * commit_time + * meta_device + * block_size * internal_hash * journal_crypt * journal_mac - * block_size + * recalculate */ static int dm_integrity_ctr(struct dm_target *ti, unsigned argc, char **argv) { -- cgit v1.2.3 From cbebf5addec1a7c46b67868de031fca97e36995b Mon Sep 17 00:00:00 2001 From: Marco Felsch Date: Sat, 4 May 2019 09:49:23 -0700 Subject: Input: qt1050 - add Microchip AT42QT1050 support Add initial support for the AT42QT1050 (QT1050) device. The device supports up to five input keys, dependent on the mode. Since it adds only the initial support, the "1 to 4 keys plus Guard Channel" mode isn't supported. Signed-off-by: Marco Felsch Reviewed-by: Rob Herring Signed-off-by: Dmitry Torokhov --- .../devicetree/bindings/input/microchip,qt1050.txt | 78 +++ drivers/input/keyboard/Kconfig | 11 + drivers/input/keyboard/Makefile | 1 + drivers/input/keyboard/qt1050.c | 598 +++++++++++++++++++++ 4 files changed, 688 insertions(+) create mode 100644 Documentation/devicetree/bindings/input/microchip,qt1050.txt create mode 100644 drivers/input/keyboard/qt1050.c (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/input/microchip,qt1050.txt b/Documentation/devicetree/bindings/input/microchip,qt1050.txt new file mode 100644 index 000000000000..80e75f96252b --- /dev/null +++ b/Documentation/devicetree/bindings/input/microchip,qt1050.txt @@ -0,0 +1,78 @@ +Microchip AT42QT1050 Five-channel Touch Sensor IC + +The AT42QT1050 (QT1050) is a QTouchADC sensor device. The device can sense from +one to five keys, dependent on mode. The QT1050 includes all signal processing +functions necessary to provide stable sensing under a wide variety of changing +conditions, and the outputs are fully debounced. + +The touchkey device node should be placed inside an I2C bus node. + +Required properties: +- compatible: Must be "microchip,qt1050" +- reg: The I2C address of the device +- interrupts: The sink for the touchpad's IRQ output, + see ../interrupt-controller/interrupts.txt + +Optional properties: +- wakeup-source: touch keys can be used as a wakeup source + +Each button (key) is represented as a sub-node: + +Each not specified key or key with linux,code set to KEY_RESERVED gets disabled +in HW. + +Subnode properties: +- linux,code: Keycode to emit. +- reg: The key number. Valid values: 0, 1, 2, 3, 4. + +Optional subnode-properties: + +If a optional property is missing or has a invalid value the default value is +taken. + +- microchip,pre-charge-time-ns: + Each touchpad need some time to precharge. The value depends on the mechanical + layout. + Valid value range: 0 - 637500; values must be a multiple of 2500; + default is 0. +- microchip,average-samples: + Number of data samples which are averaged for each read. + Valid values: 1, 4, 16, 64, 256, 1024, 4096, 16384; default is 1. +- microchip,average-scaling: + The scaling factor which is used to scale the average-samples. + Valid values: 1, 2, 4, 8, 16, 32, 64, 128; default is 1. +- microchip,threshold: + Number of counts to register a touch detection. + Valid value range: 0 - 255; default is 20. + +Example: +QT1050 with 3 non continuous keys, key2 and key4 are disabled. + +touchkeys@41 { + compatible = "microchip,qt1050"; + reg = <0x41>; + interrupt-parent = <&gpio0>; + interrupts = <17 IRQ_TYPE_EDGE_FALLING>; + + up@0 { + reg = <0>; + linux,code = ; + microchip,average-samples = <64>; + microchip,average-scaling = <16>; + microchip,pre-charge-time-ns = <10000>; + }; + + right@1 { + reg = <1>; + linux,code = ; + microchip,average-samples = <64>; + microchip,average-scaling = <8>; + }; + + down@3 { + reg = <3>; + linux,code = ; + microchip,average-samples = <256>; + microchip,average-scaling = <16>; + }; +}; diff --git a/drivers/input/keyboard/Kconfig b/drivers/input/keyboard/Kconfig index 4713957b0cbb..08aba5e7cd93 100644 --- a/drivers/input/keyboard/Kconfig +++ b/drivers/input/keyboard/Kconfig @@ -137,6 +137,17 @@ config KEYBOARD_ATKBD_RDI_KEYCODES right-hand column will be interpreted as the key shown in the left-hand column. +config KEYBOARD_QT1050 + tristate "Microchip AT42QT1050 Touch Sensor Chip" + depends on I2C + select REGMAP_I2C + help + Say Y here if you want to use Microchip AT42QT1050 QTouch + Sensor chip as input device. + + To compile this driver as a module, choose M here: + the module will be called qt1050 + config KEYBOARD_QT1070 tristate "Atmel AT42QT1070 Touch Sensor Chip" depends on I2C diff --git a/drivers/input/keyboard/Makefile b/drivers/input/keyboard/Makefile index 182e92985dbf..f0291ca39f62 100644 --- a/drivers/input/keyboard/Makefile +++ b/drivers/input/keyboard/Makefile @@ -50,6 +50,7 @@ obj-$(CONFIG_KEYBOARD_OPENCORES) += opencores-kbd.o obj-$(CONFIG_KEYBOARD_PMIC8XXX) += pmic8xxx-keypad.o obj-$(CONFIG_KEYBOARD_PXA27x) += pxa27x_keypad.o obj-$(CONFIG_KEYBOARD_PXA930_ROTARY) += pxa930_rotary.o +obj-$(CONFIG_KEYBOARD_QT1050) += qt1050.o obj-$(CONFIG_KEYBOARD_QT1070) += qt1070.o obj-$(CONFIG_KEYBOARD_QT2160) += qt2160.o obj-$(CONFIG_KEYBOARD_SAMSUNG) += samsung-keypad.o diff --git a/drivers/input/keyboard/qt1050.c b/drivers/input/keyboard/qt1050.c new file mode 100644 index 000000000000..403060d05c3b --- /dev/null +++ b/drivers/input/keyboard/qt1050.c @@ -0,0 +1,598 @@ +// SPDX-License-Identifier: GPL-2.0 +/* + * Microchip AT42QT1050 QTouch Sensor Controller + * + * Copyright (C) 2019 Pengutronix, Marco Felsch + * + * Base on AT42QT1070 driver by: + * Bo Shen + * Copyright (C) 2011 Atmel + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include + +/* Chip ID */ +#define QT1050_CHIP_ID 0x00 +#define QT1050_CHIP_ID_VER 0x46 + +/* Firmware version */ +#define QT1050_FW_VERSION 0x01 + +/* Detection status */ +#define QT1050_DET_STATUS 0x02 + +/* Key status */ +#define QT1050_KEY_STATUS 0x03 + +/* Key Signals */ +#define QT1050_KEY_SIGNAL_0_MSB 0x06 +#define QT1050_KEY_SIGNAL_0_LSB 0x07 +#define QT1050_KEY_SIGNAL_1_MSB 0x08 +#define QT1050_KEY_SIGNAL_1_LSB 0x09 +#define QT1050_KEY_SIGNAL_2_MSB 0x0c +#define QT1050_KEY_SIGNAL_2_LSB 0x0d +#define QT1050_KEY_SIGNAL_3_MSB 0x0e +#define QT1050_KEY_SIGNAL_3_LSB 0x0f +#define QT1050_KEY_SIGNAL_4_MSB 0x10 +#define QT1050_KEY_SIGNAL_4_LSB 0x11 + +/* Reference data */ +#define QT1050_REF_DATA_0_MSB 0x14 +#define QT1050_REF_DATA_0_LSB 0x15 +#define QT1050_REF_DATA_1_MSB 0x16 +#define QT1050_REF_DATA_1_LSB 0x17 +#define QT1050_REF_DATA_2_MSB 0x1a +#define QT1050_REF_DATA_2_LSB 0x1b +#define QT1050_REF_DATA_3_MSB 0x1c +#define QT1050_REF_DATA_3_LSB 0x1d +#define QT1050_REF_DATA_4_MSB 0x1e +#define QT1050_REF_DATA_4_LSB 0x1f + +/* Negative threshold level */ +#define QT1050_NTHR_0 0x21 +#define QT1050_NTHR_1 0x22 +#define QT1050_NTHR_2 0x24 +#define QT1050_NTHR_3 0x25 +#define QT1050_NTHR_4 0x26 + +/* Pulse / Scale */ +#define QT1050_PULSE_SCALE_0 0x28 +#define QT1050_PULSE_SCALE_1 0x29 +#define QT1050_PULSE_SCALE_2 0x2b +#define QT1050_PULSE_SCALE_3 0x2c +#define QT1050_PULSE_SCALE_4 0x2d + +/* Detection integrator counter / AKS */ +#define QT1050_DI_AKS_0 0x2f +#define QT1050_DI_AKS_1 0x30 +#define QT1050_DI_AKS_2 0x32 +#define QT1050_DI_AKS_3 0x33 +#define QT1050_DI_AKS_4 0x34 + +/* Charge Share Delay */ +#define QT1050_CSD_0 0x36 +#define QT1050_CSD_1 0x37 +#define QT1050_CSD_2 0x39 +#define QT1050_CSD_3 0x3a +#define QT1050_CSD_4 0x3b + +/* Low Power Mode */ +#define QT1050_LPMODE 0x3d + +/* Calibration and Reset */ +#define QT1050_RES_CAL 0x3f +#define QT1050_RES_CAL_RESET BIT(7) +#define QT1050_RES_CAL_CALIBRATE BIT(1) + +#define QT1050_MAX_KEYS 5 +#define QT1050_RESET_TIME 255 + +struct qt1050_key_regs { + unsigned int nthr; + unsigned int pulse_scale; + unsigned int di_aks; + unsigned int csd; +}; + +struct qt1050_key { + u32 num; + u32 charge_delay; + u32 thr_cnt; + u32 samples; + u32 scale; + u32 keycode; +}; + +struct qt1050_priv { + struct i2c_client *client; + struct input_dev *input; + struct regmap *regmap; + struct qt1050_key keys[QT1050_MAX_KEYS]; + unsigned short keycodes[QT1050_MAX_KEYS]; + u8 reg_keys; + u8 last_keys; +}; + +static const struct qt1050_key_regs qt1050_key_regs_data[] = { + { + .nthr = QT1050_NTHR_0, + .pulse_scale = QT1050_PULSE_SCALE_0, + .di_aks = QT1050_DI_AKS_0, + .csd = QT1050_CSD_0, + }, { + .nthr = QT1050_NTHR_1, + .pulse_scale = QT1050_PULSE_SCALE_1, + .di_aks = QT1050_DI_AKS_1, + .csd = QT1050_CSD_1, + }, { + .nthr = QT1050_NTHR_2, + .pulse_scale = QT1050_PULSE_SCALE_2, + .di_aks = QT1050_DI_AKS_2, + .csd = QT1050_CSD_2, + }, { + .nthr = QT1050_NTHR_3, + .pulse_scale = QT1050_PULSE_SCALE_3, + .di_aks = QT1050_DI_AKS_3, + .csd = QT1050_CSD_3, + }, { + .nthr = QT1050_NTHR_4, + .pulse_scale = QT1050_PULSE_SCALE_4, + .di_aks = QT1050_DI_AKS_4, + .csd = QT1050_CSD_4, + } +}; + +static bool qt1050_volatile_reg(struct device *dev, unsigned int reg) +{ + switch (reg) { + case QT1050_DET_STATUS: + case QT1050_KEY_STATUS: + case QT1050_KEY_SIGNAL_0_MSB: + case QT1050_KEY_SIGNAL_0_LSB: + case QT1050_KEY_SIGNAL_1_MSB: + case QT1050_KEY_SIGNAL_1_LSB: + case QT1050_KEY_SIGNAL_2_MSB: + case QT1050_KEY_SIGNAL_2_LSB: + case QT1050_KEY_SIGNAL_3_MSB: + case QT1050_KEY_SIGNAL_3_LSB: + case QT1050_KEY_SIGNAL_4_MSB: + case QT1050_KEY_SIGNAL_4_LSB: + return true; + default: + return false; + } +} + +static const struct regmap_range qt1050_readable_ranges[] = { + regmap_reg_range(QT1050_CHIP_ID, QT1050_KEY_STATUS), + regmap_reg_range(QT1050_KEY_SIGNAL_0_MSB, QT1050_KEY_SIGNAL_1_LSB), + regmap_reg_range(QT1050_KEY_SIGNAL_2_MSB, QT1050_KEY_SIGNAL_4_LSB), + regmap_reg_range(QT1050_REF_DATA_0_MSB, QT1050_REF_DATA_1_LSB), + regmap_reg_range(QT1050_REF_DATA_2_MSB, QT1050_REF_DATA_4_LSB), + regmap_reg_range(QT1050_NTHR_0, QT1050_NTHR_1), + regmap_reg_range(QT1050_NTHR_2, QT1050_NTHR_4), + regmap_reg_range(QT1050_PULSE_SCALE_0, QT1050_PULSE_SCALE_1), + regmap_reg_range(QT1050_PULSE_SCALE_2, QT1050_PULSE_SCALE_4), + regmap_reg_range(QT1050_DI_AKS_0, QT1050_DI_AKS_1), + regmap_reg_range(QT1050_DI_AKS_2, QT1050_DI_AKS_4), + regmap_reg_range(QT1050_CSD_0, QT1050_CSD_1), + regmap_reg_range(QT1050_CSD_2, QT1050_RES_CAL), +}; + +static const struct regmap_access_table qt1050_readable_table = { + .yes_ranges = qt1050_readable_ranges, + .n_yes_ranges = ARRAY_SIZE(qt1050_readable_ranges), +}; + +static const struct regmap_range qt1050_writeable_ranges[] = { + regmap_reg_range(QT1050_NTHR_0, QT1050_NTHR_1), + regmap_reg_range(QT1050_NTHR_2, QT1050_NTHR_4), + regmap_reg_range(QT1050_PULSE_SCALE_0, QT1050_PULSE_SCALE_1), + regmap_reg_range(QT1050_PULSE_SCALE_2, QT1050_PULSE_SCALE_4), + regmap_reg_range(QT1050_DI_AKS_0, QT1050_DI_AKS_1), + regmap_reg_range(QT1050_DI_AKS_2, QT1050_DI_AKS_4), + regmap_reg_range(QT1050_CSD_0, QT1050_CSD_1), + regmap_reg_range(QT1050_CSD_2, QT1050_RES_CAL), +}; + +static const struct regmap_access_table qt1050_writeable_table = { + .yes_ranges = qt1050_writeable_ranges, + .n_yes_ranges = ARRAY_SIZE(qt1050_writeable_ranges), +}; + +static struct regmap_config qt1050_regmap_config = { + .reg_bits = 8, + .val_bits = 8, + .max_register = QT1050_RES_CAL, + + .cache_type = REGCACHE_RBTREE, + + .wr_table = &qt1050_writeable_table, + .rd_table = &qt1050_readable_table, + .volatile_reg = qt1050_volatile_reg, +}; + +static bool qt1050_identify(struct qt1050_priv *ts) +{ + unsigned int val; + int err; + + /* Read Chip ID */ + regmap_read(ts->regmap, QT1050_CHIP_ID, &val); + if (val != QT1050_CHIP_ID_VER) { + dev_err(&ts->client->dev, "ID %d not supported\n", val); + return false; + } + + /* Read firmware version */ + err = regmap_read(ts->regmap, QT1050_FW_VERSION, &val); + if (err) { + dev_err(&ts->client->dev, "could not read the firmware version\n"); + return false; + } + + dev_info(&ts->client->dev, "AT42QT1050 firmware version %1d.%1d\n", + val >> 4, val & 0xf); + + return true; +} + +static irqreturn_t qt1050_irq_threaded(int irq, void *dev_id) +{ + struct qt1050_priv *ts = dev_id; + struct input_dev *input = ts->input; + unsigned long new_keys, changed; + unsigned int val; + int i, err; + + /* Read the detected status register, thus clearing interrupt */ + err = regmap_read(ts->regmap, QT1050_DET_STATUS, &val); + if (err) { + dev_err(&ts->client->dev, "Fail to read detection status: %d\n", + err); + return IRQ_NONE; + } + + /* Read which key changed, keys are not continuous */ + err = regmap_read(ts->regmap, QT1050_KEY_STATUS, &val); + if (err) { + dev_err(&ts->client->dev, + "Fail to determine the key status: %d\n", err); + return IRQ_NONE; + } + new_keys = (val & 0x70) >> 2 | (val & 0x6) >> 1; + changed = ts->last_keys ^ new_keys; + /* Report registered keys only */ + changed &= ts->reg_keys; + + for_each_set_bit(i, &changed, QT1050_MAX_KEYS) + input_report_key(input, ts->keys[i].keycode, + test_bit(i, &new_keys)); + + ts->last_keys = new_keys; + input_sync(input); + + return IRQ_HANDLED; +} + +static const struct qt1050_key_regs *qt1050_get_key_regs(int key_num) +{ + return &qt1050_key_regs_data[key_num]; +} + +static int qt1050_set_key(struct regmap *map, int number, int on) +{ + const struct qt1050_key_regs *key_regs; + + key_regs = qt1050_get_key_regs(number); + + return regmap_update_bits(map, key_regs->di_aks, 0xfc, + on ? BIT(4) : 0x00); +} + +static int qt1050_apply_fw_data(struct qt1050_priv *ts) +{ + struct regmap *map = ts->regmap; + struct qt1050_key *button = &ts->keys[0]; + const struct qt1050_key_regs *key_regs; + int i, err; + + /* Disable all keys and enable only the specified ones */ + for (i = 0; i < QT1050_MAX_KEYS; i++) { + err = qt1050_set_key(map, i, 0); + if (err) + return err; + } + + for (i = 0; i < QT1050_MAX_KEYS; i++, button++) { + /* Keep KEY_RESERVED keys off */ + if (button->keycode == KEY_RESERVED) + continue; + + err = qt1050_set_key(map, button->num, 1); + if (err) + return err; + + key_regs = qt1050_get_key_regs(button->num); + + err = regmap_write(map, key_regs->pulse_scale, + (button->samples << 4) | (button->scale)); + if (err) + return err; + err = regmap_write(map, key_regs->csd, button->charge_delay); + if (err) + return err; + err = regmap_write(map, key_regs->nthr, button->thr_cnt); + if (err) + return err; + } + + return 0; +} + +static int qt1050_parse_fw(struct qt1050_priv *ts) +{ + struct device *dev = &ts->client->dev; + struct fwnode_handle *child; + int nbuttons; + + nbuttons = device_get_child_node_count(dev); + if (nbuttons == 0 || nbuttons > QT1050_MAX_KEYS) + return -ENODEV; + + device_for_each_child_node(dev, child) { + struct qt1050_key button; + + /* Required properties */ + if (fwnode_property_read_u32(child, "linux,code", + &button.keycode)) { + dev_err(dev, "Button without keycode\n"); + goto err; + } + if (button.keycode >= KEY_MAX) { + dev_err(dev, "Invalid keycode 0x%x\n", + button.keycode); + goto err; + } + + if (fwnode_property_read_u32(child, "reg", + &button.num)) { + dev_err(dev, "Button without pad number\n"); + goto err; + } + if (button.num < 0 || button.num > QT1050_MAX_KEYS - 1) + goto err; + + ts->reg_keys |= BIT(button.num); + + /* Optional properties */ + if (fwnode_property_read_u32(child, + "microchip,pre-charge-time-ns", + &button.charge_delay)) { + button.charge_delay = 0; + } else { + if (button.charge_delay % 2500 == 0) + button.charge_delay = + button.charge_delay / 2500; + else + button.charge_delay = 0; + } + + if (fwnode_property_read_u32(child, "microchip,average-samples", + &button.samples)) { + button.samples = 0; + } else { + if (is_power_of_2(button.samples)) + button.samples = ilog2(button.samples); + else + button.samples = 0; + } + + if (fwnode_property_read_u32(child, "microchip,average-scaling", + &button.scale)) { + button.scale = 0; + } else { + if (is_power_of_2(button.scale)) + button.scale = ilog2(button.scale); + else + button.scale = 0; + + } + + if (fwnode_property_read_u32(child, "microchip,threshold", + &button.thr_cnt)) { + button.thr_cnt = 20; + } else { + if (button.thr_cnt > 255) + button.thr_cnt = 20; + } + + ts->keys[button.num] = button; + } + + return 0; + +err: + fwnode_handle_put(child); + return -EINVAL; +} + +static int qt1050_probe(struct i2c_client *client) +{ + struct qt1050_priv *ts; + struct input_dev *input; + struct device *dev = &client->dev; + struct regmap *map; + unsigned int status, i; + int err; + + /* Check basic functionality */ + err = i2c_check_functionality(client->adapter, I2C_FUNC_SMBUS_BYTE); + if (!err) { + dev_err(&client->dev, "%s adapter not supported\n", + dev_driver_string(&client->adapter->dev)); + return -ENODEV; + } + + if (!client->irq) { + dev_err(dev, "assign a irq line to this device\n"); + return -EINVAL; + } + + ts = devm_kzalloc(dev, sizeof(*ts), GFP_KERNEL); + if (!ts) + return -ENOMEM; + + input = devm_input_allocate_device(dev); + if (!input) + return -ENOMEM; + + map = devm_regmap_init_i2c(client, &qt1050_regmap_config); + if (IS_ERR(map)) + return PTR_ERR(map); + + ts->client = client; + ts->input = input; + ts->regmap = map; + + i2c_set_clientdata(client, ts); + + /* Identify the qt1050 chip */ + if (!qt1050_identify(ts)) + return -ENODEV; + + /* Get pdata */ + err = qt1050_parse_fw(ts); + if (err) { + dev_err(dev, "Failed to parse firmware: %d\n", err); + return err; + } + + input->name = "AT42QT1050 QTouch Sensor"; + input->dev.parent = &client->dev; + input->id.bustype = BUS_I2C; + + /* Add the keycode */ + input->keycode = ts->keycodes; + input->keycodesize = sizeof(ts->keycodes[0]); + input->keycodemax = QT1050_MAX_KEYS; + + __set_bit(EV_KEY, input->evbit); + for (i = 0; i < QT1050_MAX_KEYS; i++) { + ts->keycodes[i] = ts->keys[i].keycode; + __set_bit(ts->keycodes[i], input->keybit); + } + + /* Trigger re-calibration */ + err = regmap_update_bits(ts->regmap, QT1050_RES_CAL, 0x7f, + QT1050_RES_CAL_CALIBRATE); + if (err) { + dev_err(dev, "Trigger calibration failed: %d\n", err); + return err; + } + err = regmap_read_poll_timeout(ts->regmap, QT1050_DET_STATUS, status, + status >> 7 == 1, 10000, 200000); + if (err) { + dev_err(dev, "Calibration failed: %d\n", err); + return err; + } + + /* Soft reset to set defaults */ + err = regmap_update_bits(ts->regmap, QT1050_RES_CAL, + QT1050_RES_CAL_RESET, QT1050_RES_CAL_RESET); + if (err) { + dev_err(dev, "Trigger soft reset failed: %d\n", err); + return err; + } + msleep(QT1050_RESET_TIME); + + /* Set pdata */ + err = qt1050_apply_fw_data(ts); + if (err) { + dev_err(dev, "Failed to set firmware data: %d\n", err); + return err; + } + + err = devm_request_threaded_irq(dev, client->irq, NULL, + qt1050_irq_threaded, IRQF_ONESHOT, + "qt1050", ts); + if (err) { + dev_err(&client->dev, "Failed to request irq: %d\n", err); + return err; + } + + /* Clear #CHANGE line */ + err = regmap_read(ts->regmap, QT1050_DET_STATUS, &status); + if (err) { + dev_err(dev, "Failed to clear #CHANGE line level: %d\n", err); + return err; + } + + /* Register the input device */ + err = input_register_device(ts->input); + if (err) { + dev_err(&client->dev, "Failed to register input device: %d\n", + err); + return err; + } + + return 0; +} + +static int __maybe_unused qt1050_suspend(struct device *dev) +{ + struct i2c_client *client = to_i2c_client(dev); + struct qt1050_priv *ts = i2c_get_clientdata(client); + + disable_irq(client->irq); + + /* + * Set measurement interval to 1s (125 x 8ms) if wakeup is allowed + * else turn off. The 1s interval seems to be a good compromise between + * low power and response time. + */ + return regmap_write(ts->regmap, QT1050_LPMODE, + device_may_wakeup(dev) ? 125 : 0); +} + +static int __maybe_unused qt1050_resume(struct device *dev) +{ + struct i2c_client *client = to_i2c_client(dev); + struct qt1050_priv *ts = i2c_get_clientdata(client); + + enable_irq(client->irq); + + /* Set measurement interval back to 16ms (2 x 8ms) */ + return regmap_write(ts->regmap, QT1050_LPMODE, 2); +} + +static SIMPLE_DEV_PM_OPS(qt1050_pm_ops, qt1050_suspend, qt1050_resume); + +static const struct of_device_id __maybe_unused qt1050_of_match[] = { + { .compatible = "microchip,qt1050", }, + { }, +}; +MODULE_DEVICE_TABLE(of, qt1050_of_match); + +static struct i2c_driver qt1050_driver = { + .driver = { + .name = "qt1050", + .of_match_table = of_match_ptr(qt1050_of_match), + .pm = &qt1050_pm_ops, + }, + .probe_new = qt1050_probe, +}; + +module_i2c_driver(qt1050_driver); + +MODULE_AUTHOR("Marco Felsch Date: Fri, 3 May 2019 16:30:23 +0200 Subject: docs: livepatch: convert docs to ReST and rename to *.rst Convert livepatch documentation to ReST format. The changes are mostly trivial, as the documents are already on a good shape. Just a few markup changes are needed for Sphinx to properly parse the docs. The conversion is actually: - add blank lines and identation in order to identify paragraphs; - fix tables markups; - add some lists markups; - mark literal blocks; - The in-file TOC becomes a comment, in order to skip it from the output, as Sphinx already generates an index there. - adjust title markups. At its new index.rst, let's add a :orphan: while this is not linked to the main index.rst file, in order to avoid build warnings. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Petr Mladek Acked-by: Miroslav Benes Acked-by: Josh Poimboeuf Acked-by: Joe Lawrence Reviewed-by: Kamalesh Babulal Signed-off-by: Jonathan Corbet --- Documentation/ABI/testing/sysfs-kernel-livepatch | 2 +- Documentation/livepatch/callbacks.rst | 130 +++++++ Documentation/livepatch/callbacks.txt | 126 ------- Documentation/livepatch/cumulative-patches.rst | 102 +++++ Documentation/livepatch/cumulative-patches.txt | 102 ----- Documentation/livepatch/index.rst | 21 ++ Documentation/livepatch/livepatch.rst | 461 +++++++++++++++++++++++ Documentation/livepatch/livepatch.txt | 459 ---------------------- Documentation/livepatch/module-elf-format.rst | 340 +++++++++++++++++ Documentation/livepatch/module-elf-format.txt | 323 ---------------- Documentation/livepatch/shadow-vars.rst | 226 +++++++++++ Documentation/livepatch/shadow-vars.txt | 209 ---------- tools/objtool/Documentation/stack-validation.txt | 2 +- 13 files changed, 1282 insertions(+), 1221 deletions(-) create mode 100644 Documentation/livepatch/callbacks.rst delete mode 100644 Documentation/livepatch/callbacks.txt create mode 100644 Documentation/livepatch/cumulative-patches.rst delete mode 100644 Documentation/livepatch/cumulative-patches.txt create mode 100644 Documentation/livepatch/index.rst create mode 100644 Documentation/livepatch/livepatch.rst delete mode 100644 Documentation/livepatch/livepatch.txt create mode 100644 Documentation/livepatch/module-elf-format.rst delete mode 100644 Documentation/livepatch/module-elf-format.txt create mode 100644 Documentation/livepatch/shadow-vars.rst delete mode 100644 Documentation/livepatch/shadow-vars.txt (limited to 'Documentation') diff --git a/Documentation/ABI/testing/sysfs-kernel-livepatch b/Documentation/ABI/testing/sysfs-kernel-livepatch index 85db352f68f9..bea7bd5a1d5f 100644 --- a/Documentation/ABI/testing/sysfs-kernel-livepatch +++ b/Documentation/ABI/testing/sysfs-kernel-livepatch @@ -45,7 +45,7 @@ Description: use this feature without a clearance from a patch distributor. Removal (rmmod) of patch modules is permanently disabled when the feature is used. See - Documentation/livepatch/livepatch.txt for more information. + Documentation/livepatch/livepatch.rst for more information. What: /sys/kernel/livepatch// Date: Nov 2014 diff --git a/Documentation/livepatch/callbacks.rst b/Documentation/livepatch/callbacks.rst new file mode 100644 index 000000000000..d76d1f0d9fcf --- /dev/null +++ b/Documentation/livepatch/callbacks.rst @@ -0,0 +1,130 @@ +====================== +(Un)patching Callbacks +====================== + +Livepatch (un)patch-callbacks provide a mechanism for livepatch modules +to execute callback functions when a kernel object is (un)patched. They +can be considered a "power feature" that extends livepatching abilities +to include: + + - Safe updates to global data + + - "Patches" to init and probe functions + + - Patching otherwise unpatchable code (i.e. assembly) + +In most cases, (un)patch callbacks will need to be used in conjunction +with memory barriers and kernel synchronization primitives, like +mutexes/spinlocks, or even stop_machine(), to avoid concurrency issues. + +Callbacks differ from existing kernel facilities: + + - Module init/exit code doesn't run when disabling and re-enabling a + patch. + + - A module notifier can't stop a to-be-patched module from loading. + +Callbacks are part of the klp_object structure and their implementation +is specific to that klp_object. Other livepatch objects may or may not +be patched, irrespective of the target klp_object's current state. + +Callbacks can be registered for the following livepatch actions: + + * Pre-patch + - before a klp_object is patched + + * Post-patch + - after a klp_object has been patched and is active + across all tasks + + * Pre-unpatch + - before a klp_object is unpatched (ie, patched code is + active), used to clean up post-patch callback + resources + + * Post-unpatch + - after a klp_object has been patched, all code has + been restored and no tasks are running patched code, + used to cleanup pre-patch callback resources + +Each callback is optional, omitting one does not preclude specifying any +other. However, the livepatching core executes the handlers in +symmetry: pre-patch callbacks have a post-unpatch counterpart and +post-patch callbacks have a pre-unpatch counterpart. An unpatch +callback will only be executed if its corresponding patch callback was +executed. Typical use cases pair a patch handler that acquires and +configures resources with an unpatch handler tears down and releases +those same resources. + +A callback is only executed if its host klp_object is loaded. For +in-kernel vmlinux targets, this means that callbacks will always execute +when a livepatch is enabled/disabled. For patch target kernel modules, +callbacks will only execute if the target module is loaded. When a +module target is (un)loaded, its callbacks will execute only if the +livepatch module is enabled. + +The pre-patch callback, if specified, is expected to return a status +code (0 for success, -ERRNO on error). An error status code indicates +to the livepatching core that patching of the current klp_object is not +safe and to stop the current patching request. (When no pre-patch +callback is provided, the transition is assumed to be safe.) If a +pre-patch callback returns failure, the kernel's module loader will: + + - Refuse to load a livepatch, if the livepatch is loaded after + targeted code. + + or: + + - Refuse to load a module, if the livepatch was already successfully + loaded. + +No post-patch, pre-unpatch, or post-unpatch callbacks will be executed +for a given klp_object if the object failed to patch, due to a failed +pre_patch callback or for any other reason. + +If a patch transition is reversed, no pre-unpatch handlers will be run +(this follows the previously mentioned symmetry -- pre-unpatch callbacks +will only occur if their corresponding post-patch callback executed). + +If the object did successfully patch, but the patch transition never +started for some reason (e.g., if another object failed to patch), +only the post-unpatch callback will be called. + + +Example Use-cases +================= + +Update global data +------------------ + +A pre-patch callback can be useful to update a global variable. For +example, 75ff39ccc1bd ("tcp: make challenge acks less predictable") +changes a global sysctl, as well as patches the tcp_send_challenge_ack() +function. + +In this case, if we're being super paranoid, it might make sense to +patch the data *after* patching is complete with a post-patch callback, +so that tcp_send_challenge_ack() could first be changed to read +sysctl_tcp_challenge_ack_limit with READ_ONCE. + + +Support __init and probe function patches +----------------------------------------- + +Although __init and probe functions are not directly livepatch-able, it +may be possible to implement similar updates via pre/post-patch +callbacks. + +48900cb6af42 ("virtio-net: drop NETIF_F_FRAGLIST") change the way that +virtnet_probe() initialized its driver's net_device features. A +pre/post-patch callback could iterate over all such devices, making a +similar change to their hw_features value. (Client functions of the +value may need to be updated accordingly.) + + +Other Examples +============== + +Sample livepatch modules demonstrating the callback API can be found in +samples/livepatch/ directory. These samples were modified for use in +kselftests and can be found in the lib/livepatch directory. diff --git a/Documentation/livepatch/callbacks.txt b/Documentation/livepatch/callbacks.txt deleted file mode 100644 index 182e31d4abce..000000000000 --- a/Documentation/livepatch/callbacks.txt +++ /dev/null @@ -1,126 +0,0 @@ -====================== -(Un)patching Callbacks -====================== - -Livepatch (un)patch-callbacks provide a mechanism for livepatch modules -to execute callback functions when a kernel object is (un)patched. They -can be considered a "power feature" that extends livepatching abilities -to include: - - - Safe updates to global data - - - "Patches" to init and probe functions - - - Patching otherwise unpatchable code (i.e. assembly) - -In most cases, (un)patch callbacks will need to be used in conjunction -with memory barriers and kernel synchronization primitives, like -mutexes/spinlocks, or even stop_machine(), to avoid concurrency issues. - -Callbacks differ from existing kernel facilities: - - - Module init/exit code doesn't run when disabling and re-enabling a - patch. - - - A module notifier can't stop a to-be-patched module from loading. - -Callbacks are part of the klp_object structure and their implementation -is specific to that klp_object. Other livepatch objects may or may not -be patched, irrespective of the target klp_object's current state. - -Callbacks can be registered for the following livepatch actions: - - * Pre-patch - before a klp_object is patched - - * Post-patch - after a klp_object has been patched and is active - across all tasks - - * Pre-unpatch - before a klp_object is unpatched (ie, patched code is - active), used to clean up post-patch callback - resources - - * Post-unpatch - after a klp_object has been patched, all code has - been restored and no tasks are running patched code, - used to cleanup pre-patch callback resources - -Each callback is optional, omitting one does not preclude specifying any -other. However, the livepatching core executes the handlers in -symmetry: pre-patch callbacks have a post-unpatch counterpart and -post-patch callbacks have a pre-unpatch counterpart. An unpatch -callback will only be executed if its corresponding patch callback was -executed. Typical use cases pair a patch handler that acquires and -configures resources with an unpatch handler tears down and releases -those same resources. - -A callback is only executed if its host klp_object is loaded. For -in-kernel vmlinux targets, this means that callbacks will always execute -when a livepatch is enabled/disabled. For patch target kernel modules, -callbacks will only execute if the target module is loaded. When a -module target is (un)loaded, its callbacks will execute only if the -livepatch module is enabled. - -The pre-patch callback, if specified, is expected to return a status -code (0 for success, -ERRNO on error). An error status code indicates -to the livepatching core that patching of the current klp_object is not -safe and to stop the current patching request. (When no pre-patch -callback is provided, the transition is assumed to be safe.) If a -pre-patch callback returns failure, the kernel's module loader will: - - - Refuse to load a livepatch, if the livepatch is loaded after - targeted code. - - or: - - - Refuse to load a module, if the livepatch was already successfully - loaded. - -No post-patch, pre-unpatch, or post-unpatch callbacks will be executed -for a given klp_object if the object failed to patch, due to a failed -pre_patch callback or for any other reason. - -If a patch transition is reversed, no pre-unpatch handlers will be run -(this follows the previously mentioned symmetry -- pre-unpatch callbacks -will only occur if their corresponding post-patch callback executed). - -If the object did successfully patch, but the patch transition never -started for some reason (e.g., if another object failed to patch), -only the post-unpatch callback will be called. - - -Example Use-cases -================= - -Update global data ------------------- - -A pre-patch callback can be useful to update a global variable. For -example, 75ff39ccc1bd ("tcp: make challenge acks less predictable") -changes a global sysctl, as well as patches the tcp_send_challenge_ack() -function. - -In this case, if we're being super paranoid, it might make sense to -patch the data *after* patching is complete with a post-patch callback, -so that tcp_send_challenge_ack() could first be changed to read -sysctl_tcp_challenge_ack_limit with READ_ONCE. - - -Support __init and probe function patches ------------------------------------------ - -Although __init and probe functions are not directly livepatch-able, it -may be possible to implement similar updates via pre/post-patch -callbacks. - -48900cb6af42 ("virtio-net: drop NETIF_F_FRAGLIST") change the way that -virtnet_probe() initialized its driver's net_device features. A -pre/post-patch callback could iterate over all such devices, making a -similar change to their hw_features value. (Client functions of the -value may need to be updated accordingly.) - - -Other Examples -============== - -Sample livepatch modules demonstrating the callback API can be found in -samples/livepatch/ directory. These samples were modified for use in -kselftests and can be found in the lib/livepatch directory. diff --git a/Documentation/livepatch/cumulative-patches.rst b/Documentation/livepatch/cumulative-patches.rst new file mode 100644 index 000000000000..1931f318976a --- /dev/null +++ b/Documentation/livepatch/cumulative-patches.rst @@ -0,0 +1,102 @@ +=================================== +Atomic Replace & Cumulative Patches +=================================== + +There might be dependencies between livepatches. If multiple patches need +to do different changes to the same function(s) then we need to define +an order in which the patches will be installed. And function implementations +from any newer livepatch must be done on top of the older ones. + +This might become a maintenance nightmare. Especially when more patches +modified the same function in different ways. + +An elegant solution comes with the feature called "Atomic Replace". It allows +creation of so called "Cumulative Patches". They include all wanted changes +from all older livepatches and completely replace them in one transition. + +Usage +----- + +The atomic replace can be enabled by setting "replace" flag in struct klp_patch, +for example:: + + static struct klp_patch patch = { + .mod = THIS_MODULE, + .objs = objs, + .replace = true, + }; + +All processes are then migrated to use the code only from the new patch. +Once the transition is finished, all older patches are automatically +disabled. + +Ftrace handlers are transparently removed from functions that are no +longer modified by the new cumulative patch. + +As a result, the livepatch authors might maintain sources only for one +cumulative patch. It helps to keep the patch consistent while adding or +removing various fixes or features. + +Users could keep only the last patch installed on the system after +the transition to has finished. It helps to clearly see what code is +actually in use. Also the livepatch might then be seen as a "normal" +module that modifies the kernel behavior. The only difference is that +it can be updated at runtime without breaking its functionality. + + +Features +-------- + +The atomic replace allows: + + - Atomically revert some functions in a previous patch while + upgrading other functions. + + - Remove eventual performance impact caused by core redirection + for functions that are no longer patched. + + - Decrease user confusion about dependencies between livepatches. + + +Limitations: +------------ + + - Once the operation finishes, there is no straightforward way + to reverse it and restore the replaced patches atomically. + + A good practice is to set .replace flag in any released livepatch. + Then re-adding an older livepatch is equivalent to downgrading + to that patch. This is safe as long as the livepatches do _not_ do + extra modifications in (un)patching callbacks or in the module_init() + or module_exit() functions, see below. + + Also note that the replaced patch can be removed and loaded again + only when the transition was not forced. + + + - Only the (un)patching callbacks from the _new_ cumulative livepatch are + executed. Any callbacks from the replaced patches are ignored. + + In other words, the cumulative patch is responsible for doing any actions + that are necessary to properly replace any older patch. + + As a result, it might be dangerous to replace newer cumulative patches by + older ones. The old livepatches might not provide the necessary callbacks. + + This might be seen as a limitation in some scenarios. But it makes life + easier in many others. Only the new cumulative livepatch knows what + fixes/features are added/removed and what special actions are necessary + for a smooth transition. + + In any case, it would be a nightmare to think about the order of + the various callbacks and their interactions if the callbacks from all + enabled patches were called. + + + - There is no special handling of shadow variables. Livepatch authors + must create their own rules how to pass them from one cumulative + patch to the other. Especially that they should not blindly remove + them in module_exit() functions. + + A good practice might be to remove shadow variables in the post-unpatch + callback. It is called only when the livepatch is properly disabled. diff --git a/Documentation/livepatch/cumulative-patches.txt b/Documentation/livepatch/cumulative-patches.txt deleted file mode 100644 index 0012808e8d44..000000000000 --- a/Documentation/livepatch/cumulative-patches.txt +++ /dev/null @@ -1,102 +0,0 @@ -=================================== -Atomic Replace & Cumulative Patches -=================================== - -There might be dependencies between livepatches. If multiple patches need -to do different changes to the same function(s) then we need to define -an order in which the patches will be installed. And function implementations -from any newer livepatch must be done on top of the older ones. - -This might become a maintenance nightmare. Especially when more patches -modified the same function in different ways. - -An elegant solution comes with the feature called "Atomic Replace". It allows -creation of so called "Cumulative Patches". They include all wanted changes -from all older livepatches and completely replace them in one transition. - -Usage ------ - -The atomic replace can be enabled by setting "replace" flag in struct klp_patch, -for example: - - static struct klp_patch patch = { - .mod = THIS_MODULE, - .objs = objs, - .replace = true, - }; - -All processes are then migrated to use the code only from the new patch. -Once the transition is finished, all older patches are automatically -disabled. - -Ftrace handlers are transparently removed from functions that are no -longer modified by the new cumulative patch. - -As a result, the livepatch authors might maintain sources only for one -cumulative patch. It helps to keep the patch consistent while adding or -removing various fixes or features. - -Users could keep only the last patch installed on the system after -the transition to has finished. It helps to clearly see what code is -actually in use. Also the livepatch might then be seen as a "normal" -module that modifies the kernel behavior. The only difference is that -it can be updated at runtime without breaking its functionality. - - -Features --------- - -The atomic replace allows: - - + Atomically revert some functions in a previous patch while - upgrading other functions. - - + Remove eventual performance impact caused by core redirection - for functions that are no longer patched. - - + Decrease user confusion about dependencies between livepatches. - - -Limitations: ------------- - - + Once the operation finishes, there is no straightforward way - to reverse it and restore the replaced patches atomically. - - A good practice is to set .replace flag in any released livepatch. - Then re-adding an older livepatch is equivalent to downgrading - to that patch. This is safe as long as the livepatches do _not_ do - extra modifications in (un)patching callbacks or in the module_init() - or module_exit() functions, see below. - - Also note that the replaced patch can be removed and loaded again - only when the transition was not forced. - - - + Only the (un)patching callbacks from the _new_ cumulative livepatch are - executed. Any callbacks from the replaced patches are ignored. - - In other words, the cumulative patch is responsible for doing any actions - that are necessary to properly replace any older patch. - - As a result, it might be dangerous to replace newer cumulative patches by - older ones. The old livepatches might not provide the necessary callbacks. - - This might be seen as a limitation in some scenarios. But it makes life - easier in many others. Only the new cumulative livepatch knows what - fixes/features are added/removed and what special actions are necessary - for a smooth transition. - - In any case, it would be a nightmare to think about the order of - the various callbacks and their interactions if the callbacks from all - enabled patches were called. - - - + There is no special handling of shadow variables. Livepatch authors - must create their own rules how to pass them from one cumulative - patch to the other. Especially that they should not blindly remove - them in module_exit() functions. - - A good practice might be to remove shadow variables in the post-unpatch - callback. It is called only when the livepatch is properly disabled. diff --git a/Documentation/livepatch/index.rst b/Documentation/livepatch/index.rst new file mode 100644 index 000000000000..edd291d51847 --- /dev/null +++ b/Documentation/livepatch/index.rst @@ -0,0 +1,21 @@ +:orphan: + +=================== +Kernel Livepatching +=================== + +.. toctree:: + :maxdepth: 1 + + livepatch + callbacks + cumulative-patches + module-elf-format + shadow-vars + +.. only:: subproject and html + + Indices + ======= + + * :ref:`genindex` diff --git a/Documentation/livepatch/livepatch.rst b/Documentation/livepatch/livepatch.rst new file mode 100644 index 000000000000..c2c598c4ead8 --- /dev/null +++ b/Documentation/livepatch/livepatch.rst @@ -0,0 +1,461 @@ +========= +Livepatch +========= + +This document outlines basic information about kernel livepatching. + +.. Table of Contents: + + 1. Motivation + 2. Kprobes, Ftrace, Livepatching + 3. Consistency model + 4. Livepatch module + 4.1. New functions + 4.2. Metadata + 5. Livepatch life-cycle + 5.1. Loading + 5.2. Enabling + 5.3. Replacing + 5.4. Disabling + 5.5. Removing + 6. Sysfs + 7. Limitations + + +1. Motivation +============= + +There are many situations where users are reluctant to reboot a system. It may +be because their system is performing complex scientific computations or under +heavy load during peak usage. In addition to keeping systems up and running, +users want to also have a stable and secure system. Livepatching gives users +both by allowing for function calls to be redirected; thus, fixing critical +functions without a system reboot. + + +2. Kprobes, Ftrace, Livepatching +================================ + +There are multiple mechanisms in the Linux kernel that are directly related +to redirection of code execution; namely: kernel probes, function tracing, +and livepatching: + + - The kernel probes are the most generic. The code can be redirected by + putting a breakpoint instruction instead of any instruction. + + - The function tracer calls the code from a predefined location that is + close to the function entry point. This location is generated by the + compiler using the '-pg' gcc option. + + - Livepatching typically needs to redirect the code at the very beginning + of the function entry before the function parameters or the stack + are in any way modified. + +All three approaches need to modify the existing code at runtime. Therefore +they need to be aware of each other and not step over each other's toes. +Most of these problems are solved by using the dynamic ftrace framework as +a base. A Kprobe is registered as a ftrace handler when the function entry +is probed, see CONFIG_KPROBES_ON_FTRACE. Also an alternative function from +a live patch is called with the help of a custom ftrace handler. But there are +some limitations, see below. + + +3. Consistency model +==================== + +Functions are there for a reason. They take some input parameters, get or +release locks, read, process, and even write some data in a defined way, +have return values. In other words, each function has a defined semantic. + +Many fixes do not change the semantic of the modified functions. For +example, they add a NULL pointer or a boundary check, fix a race by adding +a missing memory barrier, or add some locking around a critical section. +Most of these changes are self contained and the function presents itself +the same way to the rest of the system. In this case, the functions might +be updated independently one by one. + +But there are more complex fixes. For example, a patch might change +ordering of locking in multiple functions at the same time. Or a patch +might exchange meaning of some temporary structures and update +all the relevant functions. In this case, the affected unit +(thread, whole kernel) need to start using all new versions of +the functions at the same time. Also the switch must happen only +when it is safe to do so, e.g. when the affected locks are released +or no data are stored in the modified structures at the moment. + +The theory about how to apply functions a safe way is rather complex. +The aim is to define a so-called consistency model. It attempts to define +conditions when the new implementation could be used so that the system +stays consistent. + +Livepatch has a consistency model which is a hybrid of kGraft and +kpatch: it uses kGraft's per-task consistency and syscall barrier +switching combined with kpatch's stack trace switching. There are also +a number of fallback options which make it quite flexible. + +Patches are applied on a per-task basis, when the task is deemed safe to +switch over. When a patch is enabled, livepatch enters into a +transition state where tasks are converging to the patched state. +Usually this transition state can complete in a few seconds. The same +sequence occurs when a patch is disabled, except the tasks converge from +the patched state to the unpatched state. + +An interrupt handler inherits the patched state of the task it +interrupts. The same is true for forked tasks: the child inherits the +patched state of the parent. + +Livepatch uses several complementary approaches to determine when it's +safe to patch tasks: + +1. The first and most effective approach is stack checking of sleeping + tasks. If no affected functions are on the stack of a given task, + the task is patched. In most cases this will patch most or all of + the tasks on the first try. Otherwise it'll keep trying + periodically. This option is only available if the architecture has + reliable stacks (HAVE_RELIABLE_STACKTRACE). + +2. The second approach, if needed, is kernel exit switching. A + task is switched when it returns to user space from a system call, a + user space IRQ, or a signal. It's useful in the following cases: + + a) Patching I/O-bound user tasks which are sleeping on an affected + function. In this case you have to send SIGSTOP and SIGCONT to + force it to exit the kernel and be patched. + b) Patching CPU-bound user tasks. If the task is highly CPU-bound + then it will get patched the next time it gets interrupted by an + IRQ. + +3. For idle "swapper" tasks, since they don't ever exit the kernel, they + instead have a klp_update_patch_state() call in the idle loop which + allows them to be patched before the CPU enters the idle state. + + (Note there's not yet such an approach for kthreads.) + +Architectures which don't have HAVE_RELIABLE_STACKTRACE solely rely on +the second approach. It's highly likely that some tasks may still be +running with an old version of the function, until that function +returns. In this case you would have to signal the tasks. This +especially applies to kthreads. They may not be woken up and would need +to be forced. See below for more information. + +Unless we can come up with another way to patch kthreads, architectures +without HAVE_RELIABLE_STACKTRACE are not considered fully supported by +the kernel livepatching. + +The /sys/kernel/livepatch//transition file shows whether a patch +is in transition. Only a single patch can be in transition at a given +time. A patch can remain in transition indefinitely, if any of the tasks +are stuck in the initial patch state. + +A transition can be reversed and effectively canceled by writing the +opposite value to the /sys/kernel/livepatch//enabled file while +the transition is in progress. Then all the tasks will attempt to +converge back to the original patch state. + +There's also a /proc//patch_state file which can be used to +determine which tasks are blocking completion of a patching operation. +If a patch is in transition, this file shows 0 to indicate the task is +unpatched and 1 to indicate it's patched. Otherwise, if no patch is in +transition, it shows -1. Any tasks which are blocking the transition +can be signaled with SIGSTOP and SIGCONT to force them to change their +patched state. This may be harmful to the system though. Sending a fake signal +to all remaining blocking tasks is a better alternative. No proper signal is +actually delivered (there is no data in signal pending structures). Tasks are +interrupted or woken up, and forced to change their patched state. The fake +signal is automatically sent every 15 seconds. + +Administrator can also affect a transition through +/sys/kernel/livepatch//force attribute. Writing 1 there clears +TIF_PATCH_PENDING flag of all tasks and thus forces the tasks to the patched +state. Important note! The force attribute is intended for cases when the +transition gets stuck for a long time because of a blocking task. Administrator +is expected to collect all necessary data (namely stack traces of such blocking +tasks) and request a clearance from a patch distributor to force the transition. +Unauthorized usage may cause harm to the system. It depends on the nature of the +patch, which functions are (un)patched, and which functions the blocking tasks +are sleeping in (/proc//stack may help here). Removal (rmmod) of patch +modules is permanently disabled when the force feature is used. It cannot be +guaranteed there is no task sleeping in such module. It implies unbounded +reference count if a patch module is disabled and enabled in a loop. + +Moreover, the usage of force may also affect future applications of live +patches and cause even more harm to the system. Administrator should first +consider to simply cancel a transition (see above). If force is used, reboot +should be planned and no more live patches applied. + +3.1 Adding consistency model support to new architectures +--------------------------------------------------------- + +For adding consistency model support to new architectures, there are a +few options: + +1) Add CONFIG_HAVE_RELIABLE_STACKTRACE. This means porting objtool, and + for non-DWARF unwinders, also making sure there's a way for the stack + tracing code to detect interrupts on the stack. + +2) Alternatively, ensure that every kthread has a call to + klp_update_patch_state() in a safe location. Kthreads are typically + in an infinite loop which does some action repeatedly. The safe + location to switch the kthread's patch state would be at a designated + point in the loop where there are no locks taken and all data + structures are in a well-defined state. + + The location is clear when using workqueues or the kthread worker + API. These kthreads process independent actions in a generic loop. + + It's much more complicated with kthreads which have a custom loop. + There the safe location must be carefully selected on a case-by-case + basis. + + In that case, arches without HAVE_RELIABLE_STACKTRACE would still be + able to use the non-stack-checking parts of the consistency model: + + a) patching user tasks when they cross the kernel/user space + boundary; and + + b) patching kthreads and idle tasks at their designated patch points. + + This option isn't as good as option 1 because it requires signaling + user tasks and waking kthreads to patch them. But it could still be + a good backup option for those architectures which don't have + reliable stack traces yet. + + +4. Livepatch module +=================== + +Livepatches are distributed using kernel modules, see +samples/livepatch/livepatch-sample.c. + +The module includes a new implementation of functions that we want +to replace. In addition, it defines some structures describing the +relation between the original and the new implementation. Then there +is code that makes the kernel start using the new code when the livepatch +module is loaded. Also there is code that cleans up before the +livepatch module is removed. All this is explained in more details in +the next sections. + + +4.1. New functions +------------------ + +New versions of functions are typically just copied from the original +sources. A good practice is to add a prefix to the names so that they +can be distinguished from the original ones, e.g. in a backtrace. Also +they can be declared as static because they are not called directly +and do not need the global visibility. + +The patch contains only functions that are really modified. But they +might want to access functions or data from the original source file +that may only be locally accessible. This can be solved by a special +relocation section in the generated livepatch module, see +Documentation/livepatch/module-elf-format.rst for more details. + + +4.2. Metadata +------------- + +The patch is described by several structures that split the information +into three levels: + + - struct klp_func is defined for each patched function. It describes + the relation between the original and the new implementation of a + particular function. + + The structure includes the name, as a string, of the original function. + The function address is found via kallsyms at runtime. + + Then it includes the address of the new function. It is defined + directly by assigning the function pointer. Note that the new + function is typically defined in the same source file. + + As an optional parameter, the symbol position in the kallsyms database can + be used to disambiguate functions of the same name. This is not the + absolute position in the database, but rather the order it has been found + only for a particular object ( vmlinux or a kernel module ). Note that + kallsyms allows for searching symbols according to the object name. + + - struct klp_object defines an array of patched functions (struct + klp_func) in the same object. Where the object is either vmlinux + (NULL) or a module name. + + The structure helps to group and handle functions for each object + together. Note that patched modules might be loaded later than + the patch itself and the relevant functions might be patched + only when they are available. + + + - struct klp_patch defines an array of patched objects (struct + klp_object). + + This structure handles all patched functions consistently and eventually, + synchronously. The whole patch is applied only when all patched + symbols are found. The only exception are symbols from objects + (kernel modules) that have not been loaded yet. + + For more details on how the patch is applied on a per-task basis, + see the "Consistency model" section. + + +5. Livepatch life-cycle +======================= + +Livepatching can be described by five basic operations: +loading, enabling, replacing, disabling, removing. + +Where the replacing and the disabling operations are mutually +exclusive. They have the same result for the given patch but +not for the system. + + +5.1. Loading +------------ + +The only reasonable way is to enable the patch when the livepatch kernel +module is being loaded. For this, klp_enable_patch() has to be called +in the module_init() callback. There are two main reasons: + +First, only the module has an easy access to the related struct klp_patch. + +Second, the error code might be used to refuse loading the module when +the patch cannot get enabled. + + +5.2. Enabling +------------- + +The livepatch gets enabled by calling klp_enable_patch() from +the module_init() callback. The system will start using the new +implementation of the patched functions at this stage. + +First, the addresses of the patched functions are found according to their +names. The special relocations, mentioned in the section "New functions", +are applied. The relevant entries are created under +/sys/kernel/livepatch/. The patch is rejected when any above +operation fails. + +Second, livepatch enters into a transition state where tasks are converging +to the patched state. If an original function is patched for the first +time, a function specific struct klp_ops is created and an universal +ftrace handler is registered\ [#]_. This stage is indicated by a value of '1' +in /sys/kernel/livepatch//transition. For more information about +this process, see the "Consistency model" section. + +Finally, once all tasks have been patched, the 'transition' value changes +to '0'. + +.. [#] + + Note that functions might be patched multiple times. The ftrace handler + is registered only once for a given function. Further patches just add + an entry to the list (see field `func_stack`) of the struct klp_ops. + The right implementation is selected by the ftrace handler, see + the "Consistency model" section. + + That said, it is highly recommended to use cumulative livepatches + because they help keeping the consistency of all changes. In this case, + functions might be patched two times only during the transition period. + + +5.3. Replacing +-------------- + +All enabled patches might get replaced by a cumulative patch that +has the .replace flag set. + +Once the new patch is enabled and the 'transition' finishes then +all the functions (struct klp_func) associated with the replaced +patches are removed from the corresponding struct klp_ops. Also +the ftrace handler is unregistered and the struct klp_ops is +freed when the related function is not modified by the new patch +and func_stack list becomes empty. + +See Documentation/livepatch/cumulative-patches.rst for more details. + + +5.4. Disabling +-------------- + +Enabled patches might get disabled by writing '0' to +/sys/kernel/livepatch//enabled. + +First, livepatch enters into a transition state where tasks are converging +to the unpatched state. The system starts using either the code from +the previously enabled patch or even the original one. This stage is +indicated by a value of '1' in /sys/kernel/livepatch//transition. +For more information about this process, see the "Consistency model" +section. + +Second, once all tasks have been unpatched, the 'transition' value changes +to '0'. All the functions (struct klp_func) associated with the to-be-disabled +patch are removed from the corresponding struct klp_ops. The ftrace handler +is unregistered and the struct klp_ops is freed when the func_stack list +becomes empty. + +Third, the sysfs interface is destroyed. + + +5.5. Removing +------------- + +Module removal is only safe when there are no users of functions provided +by the module. This is the reason why the force feature permanently +disables the removal. Only when the system is successfully transitioned +to a new patch state (patched/unpatched) without being forced it is +guaranteed that no task sleeps or runs in the old code. + + +6. Sysfs +======== + +Information about the registered patches can be found under +/sys/kernel/livepatch. The patches could be enabled and disabled +by writing there. + +/sys/kernel/livepatch//force attributes allow administrator to affect a +patching operation. + +See Documentation/ABI/testing/sysfs-kernel-livepatch for more details. + + +7. Limitations +============== + +The current Livepatch implementation has several limitations: + + - Only functions that can be traced could be patched. + + Livepatch is based on the dynamic ftrace. In particular, functions + implementing ftrace or the livepatch ftrace handler could not be + patched. Otherwise, the code would end up in an infinite loop. A + potential mistake is prevented by marking the problematic functions + by "notrace". + + + + - Livepatch works reliably only when the dynamic ftrace is located at + the very beginning of the function. + + The function need to be redirected before the stack or the function + parameters are modified in any way. For example, livepatch requires + using -fentry gcc compiler option on x86_64. + + One exception is the PPC port. It uses relative addressing and TOC. + Each function has to handle TOC and save LR before it could call + the ftrace handler. This operation has to be reverted on return. + Fortunately, the generic ftrace code has the same problem and all + this is handled on the ftrace level. + + + - Kretprobes using the ftrace framework conflict with the patched + functions. + + Both kretprobes and livepatches use a ftrace handler that modifies + the return address. The first user wins. Either the probe or the patch + is rejected when the handler is already in use by the other. + + + - Kprobes in the original function are ignored when the code is + redirected to the new implementation. + + There is a work in progress to add warnings about this situation. diff --git a/Documentation/livepatch/livepatch.txt b/Documentation/livepatch/livepatch.txt deleted file mode 100644 index 4627b41ff02e..000000000000 --- a/Documentation/livepatch/livepatch.txt +++ /dev/null @@ -1,459 +0,0 @@ -========= -Livepatch -========= - -This document outlines basic information about kernel livepatching. - -Table of Contents: - -1. Motivation -2. Kprobes, Ftrace, Livepatching -3. Consistency model -4. Livepatch module - 4.1. New functions - 4.2. Metadata -5. Livepatch life-cycle - 5.1. Loading - 5.2. Enabling - 5.3. Replacing - 5.4. Disabling - 5.5. Removing -6. Sysfs -7. Limitations - - -1. Motivation -============= - -There are many situations where users are reluctant to reboot a system. It may -be because their system is performing complex scientific computations or under -heavy load during peak usage. In addition to keeping systems up and running, -users want to also have a stable and secure system. Livepatching gives users -both by allowing for function calls to be redirected; thus, fixing critical -functions without a system reboot. - - -2. Kprobes, Ftrace, Livepatching -================================ - -There are multiple mechanisms in the Linux kernel that are directly related -to redirection of code execution; namely: kernel probes, function tracing, -and livepatching: - - + The kernel probes are the most generic. The code can be redirected by - putting a breakpoint instruction instead of any instruction. - - + The function tracer calls the code from a predefined location that is - close to the function entry point. This location is generated by the - compiler using the '-pg' gcc option. - - + Livepatching typically needs to redirect the code at the very beginning - of the function entry before the function parameters or the stack - are in any way modified. - -All three approaches need to modify the existing code at runtime. Therefore -they need to be aware of each other and not step over each other's toes. -Most of these problems are solved by using the dynamic ftrace framework as -a base. A Kprobe is registered as a ftrace handler when the function entry -is probed, see CONFIG_KPROBES_ON_FTRACE. Also an alternative function from -a live patch is called with the help of a custom ftrace handler. But there are -some limitations, see below. - - -3. Consistency model -==================== - -Functions are there for a reason. They take some input parameters, get or -release locks, read, process, and even write some data in a defined way, -have return values. In other words, each function has a defined semantic. - -Many fixes do not change the semantic of the modified functions. For -example, they add a NULL pointer or a boundary check, fix a race by adding -a missing memory barrier, or add some locking around a critical section. -Most of these changes are self contained and the function presents itself -the same way to the rest of the system. In this case, the functions might -be updated independently one by one. - -But there are more complex fixes. For example, a patch might change -ordering of locking in multiple functions at the same time. Or a patch -might exchange meaning of some temporary structures and update -all the relevant functions. In this case, the affected unit -(thread, whole kernel) need to start using all new versions of -the functions at the same time. Also the switch must happen only -when it is safe to do so, e.g. when the affected locks are released -or no data are stored in the modified structures at the moment. - -The theory about how to apply functions a safe way is rather complex. -The aim is to define a so-called consistency model. It attempts to define -conditions when the new implementation could be used so that the system -stays consistent. - -Livepatch has a consistency model which is a hybrid of kGraft and -kpatch: it uses kGraft's per-task consistency and syscall barrier -switching combined with kpatch's stack trace switching. There are also -a number of fallback options which make it quite flexible. - -Patches are applied on a per-task basis, when the task is deemed safe to -switch over. When a patch is enabled, livepatch enters into a -transition state where tasks are converging to the patched state. -Usually this transition state can complete in a few seconds. The same -sequence occurs when a patch is disabled, except the tasks converge from -the patched state to the unpatched state. - -An interrupt handler inherits the patched state of the task it -interrupts. The same is true for forked tasks: the child inherits the -patched state of the parent. - -Livepatch uses several complementary approaches to determine when it's -safe to patch tasks: - -1. The first and most effective approach is stack checking of sleeping - tasks. If no affected functions are on the stack of a given task, - the task is patched. In most cases this will patch most or all of - the tasks on the first try. Otherwise it'll keep trying - periodically. This option is only available if the architecture has - reliable stacks (HAVE_RELIABLE_STACKTRACE). - -2. The second approach, if needed, is kernel exit switching. A - task is switched when it returns to user space from a system call, a - user space IRQ, or a signal. It's useful in the following cases: - - a) Patching I/O-bound user tasks which are sleeping on an affected - function. In this case you have to send SIGSTOP and SIGCONT to - force it to exit the kernel and be patched. - b) Patching CPU-bound user tasks. If the task is highly CPU-bound - then it will get patched the next time it gets interrupted by an - IRQ. - -3. For idle "swapper" tasks, since they don't ever exit the kernel, they - instead have a klp_update_patch_state() call in the idle loop which - allows them to be patched before the CPU enters the idle state. - - (Note there's not yet such an approach for kthreads.) - -Architectures which don't have HAVE_RELIABLE_STACKTRACE solely rely on -the second approach. It's highly likely that some tasks may still be -running with an old version of the function, until that function -returns. In this case you would have to signal the tasks. This -especially applies to kthreads. They may not be woken up and would need -to be forced. See below for more information. - -Unless we can come up with another way to patch kthreads, architectures -without HAVE_RELIABLE_STACKTRACE are not considered fully supported by -the kernel livepatching. - -The /sys/kernel/livepatch//transition file shows whether a patch -is in transition. Only a single patch can be in transition at a given -time. A patch can remain in transition indefinitely, if any of the tasks -are stuck in the initial patch state. - -A transition can be reversed and effectively canceled by writing the -opposite value to the /sys/kernel/livepatch//enabled file while -the transition is in progress. Then all the tasks will attempt to -converge back to the original patch state. - -There's also a /proc//patch_state file which can be used to -determine which tasks are blocking completion of a patching operation. -If a patch is in transition, this file shows 0 to indicate the task is -unpatched and 1 to indicate it's patched. Otherwise, if no patch is in -transition, it shows -1. Any tasks which are blocking the transition -can be signaled with SIGSTOP and SIGCONT to force them to change their -patched state. This may be harmful to the system though. Sending a fake signal -to all remaining blocking tasks is a better alternative. No proper signal is -actually delivered (there is no data in signal pending structures). Tasks are -interrupted or woken up, and forced to change their patched state. The fake -signal is automatically sent every 15 seconds. - -Administrator can also affect a transition through -/sys/kernel/livepatch//force attribute. Writing 1 there clears -TIF_PATCH_PENDING flag of all tasks and thus forces the tasks to the patched -state. Important note! The force attribute is intended for cases when the -transition gets stuck for a long time because of a blocking task. Administrator -is expected to collect all necessary data (namely stack traces of such blocking -tasks) and request a clearance from a patch distributor to force the transition. -Unauthorized usage may cause harm to the system. It depends on the nature of the -patch, which functions are (un)patched, and which functions the blocking tasks -are sleeping in (/proc//stack may help here). Removal (rmmod) of patch -modules is permanently disabled when the force feature is used. It cannot be -guaranteed there is no task sleeping in such module. It implies unbounded -reference count if a patch module is disabled and enabled in a loop. - -Moreover, the usage of force may also affect future applications of live -patches and cause even more harm to the system. Administrator should first -consider to simply cancel a transition (see above). If force is used, reboot -should be planned and no more live patches applied. - -3.1 Adding consistency model support to new architectures ---------------------------------------------------------- - -For adding consistency model support to new architectures, there are a -few options: - -1) Add CONFIG_HAVE_RELIABLE_STACKTRACE. This means porting objtool, and - for non-DWARF unwinders, also making sure there's a way for the stack - tracing code to detect interrupts on the stack. - -2) Alternatively, ensure that every kthread has a call to - klp_update_patch_state() in a safe location. Kthreads are typically - in an infinite loop which does some action repeatedly. The safe - location to switch the kthread's patch state would be at a designated - point in the loop where there are no locks taken and all data - structures are in a well-defined state. - - The location is clear when using workqueues or the kthread worker - API. These kthreads process independent actions in a generic loop. - - It's much more complicated with kthreads which have a custom loop. - There the safe location must be carefully selected on a case-by-case - basis. - - In that case, arches without HAVE_RELIABLE_STACKTRACE would still be - able to use the non-stack-checking parts of the consistency model: - - a) patching user tasks when they cross the kernel/user space - boundary; and - - b) patching kthreads and idle tasks at their designated patch points. - - This option isn't as good as option 1 because it requires signaling - user tasks and waking kthreads to patch them. But it could still be - a good backup option for those architectures which don't have - reliable stack traces yet. - - -4. Livepatch module -=================== - -Livepatches are distributed using kernel modules, see -samples/livepatch/livepatch-sample.c. - -The module includes a new implementation of functions that we want -to replace. In addition, it defines some structures describing the -relation between the original and the new implementation. Then there -is code that makes the kernel start using the new code when the livepatch -module is loaded. Also there is code that cleans up before the -livepatch module is removed. All this is explained in more details in -the next sections. - - -4.1. New functions ------------------- - -New versions of functions are typically just copied from the original -sources. A good practice is to add a prefix to the names so that they -can be distinguished from the original ones, e.g. in a backtrace. Also -they can be declared as static because they are not called directly -and do not need the global visibility. - -The patch contains only functions that are really modified. But they -might want to access functions or data from the original source file -that may only be locally accessible. This can be solved by a special -relocation section in the generated livepatch module, see -Documentation/livepatch/module-elf-format.txt for more details. - - -4.2. Metadata -------------- - -The patch is described by several structures that split the information -into three levels: - - + struct klp_func is defined for each patched function. It describes - the relation between the original and the new implementation of a - particular function. - - The structure includes the name, as a string, of the original function. - The function address is found via kallsyms at runtime. - - Then it includes the address of the new function. It is defined - directly by assigning the function pointer. Note that the new - function is typically defined in the same source file. - - As an optional parameter, the symbol position in the kallsyms database can - be used to disambiguate functions of the same name. This is not the - absolute position in the database, but rather the order it has been found - only for a particular object ( vmlinux or a kernel module ). Note that - kallsyms allows for searching symbols according to the object name. - - + struct klp_object defines an array of patched functions (struct - klp_func) in the same object. Where the object is either vmlinux - (NULL) or a module name. - - The structure helps to group and handle functions for each object - together. Note that patched modules might be loaded later than - the patch itself and the relevant functions might be patched - only when they are available. - - - + struct klp_patch defines an array of patched objects (struct - klp_object). - - This structure handles all patched functions consistently and eventually, - synchronously. The whole patch is applied only when all patched - symbols are found. The only exception are symbols from objects - (kernel modules) that have not been loaded yet. - - For more details on how the patch is applied on a per-task basis, - see the "Consistency model" section. - - -5. Livepatch life-cycle -======================= - -Livepatching can be described by five basic operations: -loading, enabling, replacing, disabling, removing. - -Where the replacing and the disabling operations are mutually -exclusive. They have the same result for the given patch but -not for the system. - - -5.1. Loading ------------- - -The only reasonable way is to enable the patch when the livepatch kernel -module is being loaded. For this, klp_enable_patch() has to be called -in the module_init() callback. There are two main reasons: - -First, only the module has an easy access to the related struct klp_patch. - -Second, the error code might be used to refuse loading the module when -the patch cannot get enabled. - - -5.2. Enabling -------------- - -The livepatch gets enabled by calling klp_enable_patch() from -the module_init() callback. The system will start using the new -implementation of the patched functions at this stage. - -First, the addresses of the patched functions are found according to their -names. The special relocations, mentioned in the section "New functions", -are applied. The relevant entries are created under -/sys/kernel/livepatch/. The patch is rejected when any above -operation fails. - -Second, livepatch enters into a transition state where tasks are converging -to the patched state. If an original function is patched for the first -time, a function specific struct klp_ops is created and an universal -ftrace handler is registered[*]. This stage is indicated by a value of '1' -in /sys/kernel/livepatch//transition. For more information about -this process, see the "Consistency model" section. - -Finally, once all tasks have been patched, the 'transition' value changes -to '0'. - -[*] Note that functions might be patched multiple times. The ftrace handler - is registered only once for a given function. Further patches just add - an entry to the list (see field `func_stack`) of the struct klp_ops. - The right implementation is selected by the ftrace handler, see - the "Consistency model" section. - - That said, it is highly recommended to use cumulative livepatches - because they help keeping the consistency of all changes. In this case, - functions might be patched two times only during the transition period. - - -5.3. Replacing --------------- - -All enabled patches might get replaced by a cumulative patch that -has the .replace flag set. - -Once the new patch is enabled and the 'transition' finishes then -all the functions (struct klp_func) associated with the replaced -patches are removed from the corresponding struct klp_ops. Also -the ftrace handler is unregistered and the struct klp_ops is -freed when the related function is not modified by the new patch -and func_stack list becomes empty. - -See Documentation/livepatch/cumulative-patches.txt for more details. - - -5.4. Disabling --------------- - -Enabled patches might get disabled by writing '0' to -/sys/kernel/livepatch//enabled. - -First, livepatch enters into a transition state where tasks are converging -to the unpatched state. The system starts using either the code from -the previously enabled patch or even the original one. This stage is -indicated by a value of '1' in /sys/kernel/livepatch//transition. -For more information about this process, see the "Consistency model" -section. - -Second, once all tasks have been unpatched, the 'transition' value changes -to '0'. All the functions (struct klp_func) associated with the to-be-disabled -patch are removed from the corresponding struct klp_ops. The ftrace handler -is unregistered and the struct klp_ops is freed when the func_stack list -becomes empty. - -Third, the sysfs interface is destroyed. - - -5.5. Removing -------------- - -Module removal is only safe when there are no users of functions provided -by the module. This is the reason why the force feature permanently -disables the removal. Only when the system is successfully transitioned -to a new patch state (patched/unpatched) without being forced it is -guaranteed that no task sleeps or runs in the old code. - - -6. Sysfs -======== - -Information about the registered patches can be found under -/sys/kernel/livepatch. The patches could be enabled and disabled -by writing there. - -/sys/kernel/livepatch//force attributes allow administrator to affect a -patching operation. - -See Documentation/ABI/testing/sysfs-kernel-livepatch for more details. - - -7. Limitations -============== - -The current Livepatch implementation has several limitations: - - + Only functions that can be traced could be patched. - - Livepatch is based on the dynamic ftrace. In particular, functions - implementing ftrace or the livepatch ftrace handler could not be - patched. Otherwise, the code would end up in an infinite loop. A - potential mistake is prevented by marking the problematic functions - by "notrace". - - - - + Livepatch works reliably only when the dynamic ftrace is located at - the very beginning of the function. - - The function need to be redirected before the stack or the function - parameters are modified in any way. For example, livepatch requires - using -fentry gcc compiler option on x86_64. - - One exception is the PPC port. It uses relative addressing and TOC. - Each function has to handle TOC and save LR before it could call - the ftrace handler. This operation has to be reverted on return. - Fortunately, the generic ftrace code has the same problem and all - this is handled on the ftrace level. - - - + Kretprobes using the ftrace framework conflict with the patched - functions. - - Both kretprobes and livepatches use a ftrace handler that modifies - the return address. The first user wins. Either the probe or the patch - is rejected when the handler is already in use by the other. - - - + Kprobes in the original function are ignored when the code is - redirected to the new implementation. - - There is a work in progress to add warnings about this situation. diff --git a/Documentation/livepatch/module-elf-format.rst b/Documentation/livepatch/module-elf-format.rst new file mode 100644 index 000000000000..7f557c6f6deb --- /dev/null +++ b/Documentation/livepatch/module-elf-format.rst @@ -0,0 +1,340 @@ +=========================== +Livepatch module Elf format +=========================== + +This document outlines the Elf format requirements that livepatch modules must follow. + + +.. Table of Contents + + 0. Background and motivation + 1. Livepatch modinfo field + 2. Livepatch relocation sections + 2.1 What are livepatch relocation sections? + 2.2 Livepatch relocation section format + 2.2.1 Required flags + 2.2.2 Required name format + 2.2.3 Example livepatch relocation section names + 2.2.4 Example `readelf --sections` output + 2.2.5 Example `readelf --relocs` output + 3. Livepatch symbols + 3.1 What are livepatch symbols? + 3.2 A livepatch module's symbol table + 3.3 Livepatch symbol format + 3.3.1 Required flags + 3.3.2 Required name format + 3.3.3 Example livepatch symbol names + 3.3.4 Example `readelf --symbols` output + 4. Architecture-specific sections + 5. Symbol table and Elf section access + +---------------------------- +0. Background and motivation +---------------------------- + +Formerly, livepatch required separate architecture-specific code to write +relocations. However, arch-specific code to write relocations already +exists in the module loader, so this former approach produced redundant +code. So, instead of duplicating code and re-implementing what the module +loader can already do, livepatch leverages existing code in the module +loader to perform the all the arch-specific relocation work. Specifically, +livepatch reuses the apply_relocate_add() function in the module loader to +write relocations. The patch module Elf format described in this document +enables livepatch to be able to do this. The hope is that this will make +livepatch more easily portable to other architectures and reduce the amount +of arch-specific code required to port livepatch to a particular +architecture. + +Since apply_relocate_add() requires access to a module's section header +table, symbol table, and relocation section indices, Elf information is +preserved for livepatch modules (see section 5). Livepatch manages its own +relocation sections and symbols, which are described in this document. The +Elf constants used to mark livepatch symbols and relocation sections were +selected from OS-specific ranges according to the definitions from glibc. + +0.1 Why does livepatch need to write its own relocations? +--------------------------------------------------------- +A typical livepatch module contains patched versions of functions that can +reference non-exported global symbols and non-included local symbols. +Relocations referencing these types of symbols cannot be left in as-is +since the kernel module loader cannot resolve them and will therefore +reject the livepatch module. Furthermore, we cannot apply relocations that +affect modules not yet loaded at patch module load time (e.g. a patch to a +driver that is not loaded). Formerly, livepatch solved this problem by +embedding special "dynrela" (dynamic rela) sections in the resulting patch +module Elf output. Using these dynrela sections, livepatch could resolve +symbols while taking into account its scope and what module the symbol +belongs to, and then manually apply the dynamic relocations. However this +approach required livepatch to supply arch-specific code in order to write +these relocations. In the new format, livepatch manages its own SHT_RELA +relocation sections in place of dynrela sections, and the symbols that the +relas reference are special livepatch symbols (see section 2 and 3). The +arch-specific livepatch relocation code is replaced by a call to +apply_relocate_add(). + +================================ +PATCH MODULE FORMAT REQUIREMENTS +================================ + +-------------------------- +1. Livepatch modinfo field +-------------------------- + +Livepatch modules are required to have the "livepatch" modinfo attribute. +See the sample livepatch module in samples/livepatch/ for how this is done. + +Livepatch modules can be identified by users by using the 'modinfo' command +and looking for the presence of the "livepatch" field. This field is also +used by the kernel module loader to identify livepatch modules. + +Example modinfo output: +----------------------- + +:: + + % modinfo livepatch-meminfo.ko + filename: livepatch-meminfo.ko + livepatch: Y + license: GPL + depends: + vermagic: 4.3.0+ SMP mod_unload + +-------------------------------- +2. Livepatch relocation sections +-------------------------------- + +------------------------------------------- +2.1 What are livepatch relocation sections? +------------------------------------------- +A livepatch module manages its own Elf relocation sections to apply +relocations to modules as well as to the kernel (vmlinux) at the +appropriate time. For example, if a patch module patches a driver that is +not currently loaded, livepatch will apply the corresponding livepatch +relocation section(s) to the driver once it loads. + +Each "object" (e.g. vmlinux, or a module) within a patch module may have +multiple livepatch relocation sections associated with it (e.g. patches to +multiple functions within the same object). There is a 1-1 correspondence +between a livepatch relocation section and the target section (usually the +text section of a function) to which the relocation(s) apply. It is +also possible for a livepatch module to have no livepatch relocation +sections, as in the case of the sample livepatch module (see +samples/livepatch). + +Since Elf information is preserved for livepatch modules (see Section 5), a +livepatch relocation section can be applied simply by passing in the +appropriate section index to apply_relocate_add(), which then uses it to +access the relocation section and apply the relocations. + +Every symbol referenced by a rela in a livepatch relocation section is a +livepatch symbol. These must be resolved before livepatch can call +apply_relocate_add(). See Section 3 for more information. + +--------------------------------------- +2.2 Livepatch relocation section format +--------------------------------------- + +2.2.1 Required flags +-------------------- +Livepatch relocation sections must be marked with the SHF_RELA_LIVEPATCH +section flag. See include/uapi/linux/elf.h for the definition. The module +loader recognizes this flag and will avoid applying those relocation sections +at patch module load time. These sections must also be marked with SHF_ALLOC, +so that the module loader doesn't discard them on module load (i.e. they will +be copied into memory along with the other SHF_ALLOC sections). + +2.2.2 Required name format +-------------------------- +The name of a livepatch relocation section must conform to the following +format:: + + .klp.rela.objname.section_name + ^ ^^ ^ ^ ^ + |________||_____| |__________| + [A] [B] [C] + + [A] The relocation section name is prefixed with the string ".klp.rela." + [B] The name of the object (i.e. "vmlinux" or name of module) to + which the relocation section belongs follows immediately after the prefix. + [C] The actual name of the section to which this relocation section applies. + +2.2.3 Example livepatch relocation section names: +------------------------------------------------- +.klp.rela.ext4.text.ext4_attr_store +.klp.rela.vmlinux.text.cmdline_proc_show + +2.2.4 Example `readelf --sections` output for a patch +module that patches vmlinux and modules 9p, btrfs, ext4: +-------------------------------------------------------- + +:: + + Section Headers: + [Nr] Name Type Address Off Size ES Flg Lk Inf Al + [ snip ] + [29] .klp.rela.9p.text.caches.show RELA 0000000000000000 002d58 0000c0 18 AIo 64 9 8 + [30] .klp.rela.btrfs.text.btrfs.feature.attr.show RELA 0000000000000000 002e18 000060 18 AIo 64 11 8 + [ snip ] + [34] .klp.rela.ext4.text.ext4.attr.store RELA 0000000000000000 002fd8 0000d8 18 AIo 64 13 8 + [35] .klp.rela.ext4.text.ext4.attr.show RELA 0000000000000000 0030b0 000150 18 AIo 64 15 8 + [36] .klp.rela.vmlinux.text.cmdline.proc.show RELA 0000000000000000 003200 000018 18 AIo 64 17 8 + [37] .klp.rela.vmlinux.text.meminfo.proc.show RELA 0000000000000000 003218 0000f0 18 AIo 64 19 8 + [ snip ] ^ ^ + | | + [*] [*] + [*] Livepatch relocation sections are SHT_RELA sections but with a few special + characteristics. Notice that they are marked SHF_ALLOC ("A") so that they will + not be discarded when the module is loaded into memory, as well as with the + SHF_RELA_LIVEPATCH flag ("o" - for OS-specific). + +2.2.5 Example `readelf --relocs` output for a patch module: +----------------------------------------------------------- + +:: + + Relocation section '.klp.rela.btrfs.text.btrfs_feature_attr_show' at offset 0x2ba0 contains 4 entries: + Offset Info Type Symbol's Value Symbol's Name + Addend + 000000000000001f 0000005e00000002 R_X86_64_PC32 0000000000000000 .klp.sym.vmlinux.printk,0 - 4 + 0000000000000028 0000003d0000000b R_X86_64_32S 0000000000000000 .klp.sym.btrfs.btrfs_ktype,0 + 0 + 0000000000000036 0000003b00000002 R_X86_64_PC32 0000000000000000 .klp.sym.btrfs.can_modify_feature.isra.3,0 - 4 + 000000000000004c 0000004900000002 R_X86_64_PC32 0000000000000000 .klp.sym.vmlinux.snprintf,0 - 4 + [ snip ] ^ + | + [*] + [*] Every symbol referenced by a relocation is a livepatch symbol. + +-------------------- +3. Livepatch symbols +-------------------- + +------------------------------- +3.1 What are livepatch symbols? +------------------------------- +Livepatch symbols are symbols referred to by livepatch relocation sections. +These are symbols accessed from new versions of functions for patched +objects, whose addresses cannot be resolved by the module loader (because +they are local or unexported global syms). Since the module loader only +resolves exported syms, and not every symbol referenced by the new patched +functions is exported, livepatch symbols were introduced. They are used +also in cases where we cannot immediately know the address of a symbol when +a patch module loads. For example, this is the case when livepatch patches +a module that is not loaded yet. In this case, the relevant livepatch +symbols are resolved simply when the target module loads. In any case, for +any livepatch relocation section, all livepatch symbols referenced by that +section must be resolved before livepatch can call apply_relocate_add() for +that reloc section. + +Livepatch symbols must be marked with SHN_LIVEPATCH so that the module +loader can identify and ignore them. Livepatch modules keep these symbols +in their symbol tables, and the symbol table is made accessible through +module->symtab. + +------------------------------------- +3.2 A livepatch module's symbol table +------------------------------------- +Normally, a stripped down copy of a module's symbol table (containing only +"core" symbols) is made available through module->symtab (See layout_symtab() +in kernel/module.c). For livepatch modules, the symbol table copied into memory +on module load must be exactly the same as the symbol table produced when the +patch module was compiled. This is because the relocations in each livepatch +relocation section refer to their respective symbols with their symbol indices, +and the original symbol indices (and thus the symtab ordering) must be +preserved in order for apply_relocate_add() to find the right symbol. + +For example, take this particular rela from a livepatch module::: + + Relocation section '.klp.rela.btrfs.text.btrfs_feature_attr_show' at offset 0x2ba0 contains 4 entries: + Offset Info Type Symbol's Value Symbol's Name + Addend + 000000000000001f 0000005e00000002 R_X86_64_PC32 0000000000000000 .klp.sym.vmlinux.printk,0 - 4 + + This rela refers to the symbol '.klp.sym.vmlinux.printk,0', and the symbol index is encoded + in 'Info'. Here its symbol index is 0x5e, which is 94 in decimal, which refers to the + symbol index 94. + And in this patch module's corresponding symbol table, symbol index 94 refers to that very symbol: + [ snip ] + 94: 0000000000000000 0 NOTYPE GLOBAL DEFAULT OS [0xff20] .klp.sym.vmlinux.printk,0 + [ snip ] + +--------------------------- +3.3 Livepatch symbol format +--------------------------- + +3.3.1 Required flags +-------------------- +Livepatch symbols must have their section index marked as SHN_LIVEPATCH, so +that the module loader can identify them and not attempt to resolve them. +See include/uapi/linux/elf.h for the actual definitions. + +3.3.2 Required name format +-------------------------- +Livepatch symbol names must conform to the following format:: + + .klp.sym.objname.symbol_name,sympos + ^ ^^ ^ ^ ^ ^ + |_______||_____| |_________| | + [A] [B] [C] [D] + + [A] The symbol name is prefixed with the string ".klp.sym." + [B] The name of the object (i.e. "vmlinux" or name of module) to + which the symbol belongs follows immediately after the prefix. + [C] The actual name of the symbol. + [D] The position of the symbol in the object (as according to kallsyms) + This is used to differentiate duplicate symbols within the same + object. The symbol position is expressed numerically (0, 1, 2...). + The symbol position of a unique symbol is 0. + +3.3.3 Example livepatch symbol names: +------------------------------------- + +:: + + .klp.sym.vmlinux.snprintf,0 + .klp.sym.vmlinux.printk,0 + .klp.sym.btrfs.btrfs_ktype,0 + +3.3.4 Example `readelf --symbols` output for a patch module: +------------------------------------------------------------ + +:: + + Symbol table '.symtab' contains 127 entries: + Num: Value Size Type Bind Vis Ndx Name + [ snip ] + 73: 0000000000000000 0 NOTYPE GLOBAL DEFAULT OS [0xff20] .klp.sym.vmlinux.snprintf,0 + 74: 0000000000000000 0 NOTYPE GLOBAL DEFAULT OS [0xff20] .klp.sym.vmlinux.capable,0 + 75: 0000000000000000 0 NOTYPE GLOBAL DEFAULT OS [0xff20] .klp.sym.vmlinux.find_next_bit,0 + 76: 0000000000000000 0 NOTYPE GLOBAL DEFAULT OS [0xff20] .klp.sym.vmlinux.si_swapinfo,0 + [ snip ] ^ + | + [*] + [*] Note that the 'Ndx' (Section index) for these symbols is SHN_LIVEPATCH (0xff20). + "OS" means OS-specific. + +--------------------------------- +4. Architecture-specific sections +--------------------------------- +Architectures may override arch_klp_init_object_loaded() to perform +additional arch-specific tasks when a target module loads, such as applying +arch-specific sections. On x86 for example, we must apply per-object +.altinstructions and .parainstructions sections when a target module loads. +These sections must be prefixed with ".klp.arch.$objname." so that they can +be easily identified when iterating through a patch module's Elf sections +(See arch/x86/kernel/livepatch.c for a complete example). + +-------------------------------------- +5. Symbol table and Elf section access +-------------------------------------- +A livepatch module's symbol table is accessible through module->symtab. + +Since apply_relocate_add() requires access to a module's section headers, +symbol table, and relocation section indices, Elf information is preserved for +livepatch modules and is made accessible by the module loader through +module->klp_info, which is a klp_modinfo struct. When a livepatch module loads, +this struct is filled in by the module loader. Its fields are documented below:: + + struct klp_modinfo { + Elf_Ehdr hdr; /* Elf header */ + Elf_Shdr *sechdrs; /* Section header table */ + char *secstrings; /* String table for the section headers */ + unsigned int symndx; /* The symbol table section index */ + }; diff --git a/Documentation/livepatch/module-elf-format.txt b/Documentation/livepatch/module-elf-format.txt deleted file mode 100644 index f21a5289a09c..000000000000 --- a/Documentation/livepatch/module-elf-format.txt +++ /dev/null @@ -1,323 +0,0 @@ -=========================== -Livepatch module Elf format -=========================== - -This document outlines the Elf format requirements that livepatch modules must follow. - ------------------ -Table of Contents ------------------ -0. Background and motivation -1. Livepatch modinfo field -2. Livepatch relocation sections - 2.1 What are livepatch relocation sections? - 2.2 Livepatch relocation section format - 2.2.1 Required flags - 2.2.2 Required name format - 2.2.3 Example livepatch relocation section names - 2.2.4 Example `readelf --sections` output - 2.2.5 Example `readelf --relocs` output -3. Livepatch symbols - 3.1 What are livepatch symbols? - 3.2 A livepatch module's symbol table - 3.3 Livepatch symbol format - 3.3.1 Required flags - 3.3.2 Required name format - 3.3.3 Example livepatch symbol names - 3.3.4 Example `readelf --symbols` output -4. Architecture-specific sections -5. Symbol table and Elf section access - ----------------------------- -0. Background and motivation ----------------------------- - -Formerly, livepatch required separate architecture-specific code to write -relocations. However, arch-specific code to write relocations already -exists in the module loader, so this former approach produced redundant -code. So, instead of duplicating code and re-implementing what the module -loader can already do, livepatch leverages existing code in the module -loader to perform the all the arch-specific relocation work. Specifically, -livepatch reuses the apply_relocate_add() function in the module loader to -write relocations. The patch module Elf format described in this document -enables livepatch to be able to do this. The hope is that this will make -livepatch more easily portable to other architectures and reduce the amount -of arch-specific code required to port livepatch to a particular -architecture. - -Since apply_relocate_add() requires access to a module's section header -table, symbol table, and relocation section indices, Elf information is -preserved for livepatch modules (see section 5). Livepatch manages its own -relocation sections and symbols, which are described in this document. The -Elf constants used to mark livepatch symbols and relocation sections were -selected from OS-specific ranges according to the definitions from glibc. - -0.1 Why does livepatch need to write its own relocations? ---------------------------------------------------------- -A typical livepatch module contains patched versions of functions that can -reference non-exported global symbols and non-included local symbols. -Relocations referencing these types of symbols cannot be left in as-is -since the kernel module loader cannot resolve them and will therefore -reject the livepatch module. Furthermore, we cannot apply relocations that -affect modules not yet loaded at patch module load time (e.g. a patch to a -driver that is not loaded). Formerly, livepatch solved this problem by -embedding special "dynrela" (dynamic rela) sections in the resulting patch -module Elf output. Using these dynrela sections, livepatch could resolve -symbols while taking into account its scope and what module the symbol -belongs to, and then manually apply the dynamic relocations. However this -approach required livepatch to supply arch-specific code in order to write -these relocations. In the new format, livepatch manages its own SHT_RELA -relocation sections in place of dynrela sections, and the symbols that the -relas reference are special livepatch symbols (see section 2 and 3). The -arch-specific livepatch relocation code is replaced by a call to -apply_relocate_add(). - -================================ -PATCH MODULE FORMAT REQUIREMENTS -================================ - --------------------------- -1. Livepatch modinfo field --------------------------- - -Livepatch modules are required to have the "livepatch" modinfo attribute. -See the sample livepatch module in samples/livepatch/ for how this is done. - -Livepatch modules can be identified by users by using the 'modinfo' command -and looking for the presence of the "livepatch" field. This field is also -used by the kernel module loader to identify livepatch modules. - -Example modinfo output: ------------------------ -% modinfo livepatch-meminfo.ko -filename: livepatch-meminfo.ko -livepatch: Y -license: GPL -depends: -vermagic: 4.3.0+ SMP mod_unload - --------------------------------- -2. Livepatch relocation sections --------------------------------- - -------------------------------------------- -2.1 What are livepatch relocation sections? -------------------------------------------- -A livepatch module manages its own Elf relocation sections to apply -relocations to modules as well as to the kernel (vmlinux) at the -appropriate time. For example, if a patch module patches a driver that is -not currently loaded, livepatch will apply the corresponding livepatch -relocation section(s) to the driver once it loads. - -Each "object" (e.g. vmlinux, or a module) within a patch module may have -multiple livepatch relocation sections associated with it (e.g. patches to -multiple functions within the same object). There is a 1-1 correspondence -between a livepatch relocation section and the target section (usually the -text section of a function) to which the relocation(s) apply. It is -also possible for a livepatch module to have no livepatch relocation -sections, as in the case of the sample livepatch module (see -samples/livepatch). - -Since Elf information is preserved for livepatch modules (see Section 5), a -livepatch relocation section can be applied simply by passing in the -appropriate section index to apply_relocate_add(), which then uses it to -access the relocation section and apply the relocations. - -Every symbol referenced by a rela in a livepatch relocation section is a -livepatch symbol. These must be resolved before livepatch can call -apply_relocate_add(). See Section 3 for more information. - ---------------------------------------- -2.2 Livepatch relocation section format ---------------------------------------- - -2.2.1 Required flags --------------------- -Livepatch relocation sections must be marked with the SHF_RELA_LIVEPATCH -section flag. See include/uapi/linux/elf.h for the definition. The module -loader recognizes this flag and will avoid applying those relocation sections -at patch module load time. These sections must also be marked with SHF_ALLOC, -so that the module loader doesn't discard them on module load (i.e. they will -be copied into memory along with the other SHF_ALLOC sections). - -2.2.2 Required name format --------------------------- -The name of a livepatch relocation section must conform to the following format: - -.klp.rela.objname.section_name -^ ^^ ^ ^ ^ -|________||_____| |__________| - [A] [B] [C] - -[A] The relocation section name is prefixed with the string ".klp.rela." -[B] The name of the object (i.e. "vmlinux" or name of module) to - which the relocation section belongs follows immediately after the prefix. -[C] The actual name of the section to which this relocation section applies. - -2.2.3 Example livepatch relocation section names: -------------------------------------------------- -.klp.rela.ext4.text.ext4_attr_store -.klp.rela.vmlinux.text.cmdline_proc_show - -2.2.4 Example `readelf --sections` output for a patch -module that patches vmlinux and modules 9p, btrfs, ext4: --------------------------------------------------------- - Section Headers: - [Nr] Name Type Address Off Size ES Flg Lk Inf Al - [ snip ] - [29] .klp.rela.9p.text.caches.show RELA 0000000000000000 002d58 0000c0 18 AIo 64 9 8 - [30] .klp.rela.btrfs.text.btrfs.feature.attr.show RELA 0000000000000000 002e18 000060 18 AIo 64 11 8 - [ snip ] - [34] .klp.rela.ext4.text.ext4.attr.store RELA 0000000000000000 002fd8 0000d8 18 AIo 64 13 8 - [35] .klp.rela.ext4.text.ext4.attr.show RELA 0000000000000000 0030b0 000150 18 AIo 64 15 8 - [36] .klp.rela.vmlinux.text.cmdline.proc.show RELA 0000000000000000 003200 000018 18 AIo 64 17 8 - [37] .klp.rela.vmlinux.text.meminfo.proc.show RELA 0000000000000000 003218 0000f0 18 AIo 64 19 8 - [ snip ] ^ ^ - | | - [*] [*] -[*] Livepatch relocation sections are SHT_RELA sections but with a few special -characteristics. Notice that they are marked SHF_ALLOC ("A") so that they will -not be discarded when the module is loaded into memory, as well as with the -SHF_RELA_LIVEPATCH flag ("o" - for OS-specific). - -2.2.5 Example `readelf --relocs` output for a patch module: ------------------------------------------------------------ -Relocation section '.klp.rela.btrfs.text.btrfs_feature_attr_show' at offset 0x2ba0 contains 4 entries: - Offset Info Type Symbol's Value Symbol's Name + Addend -000000000000001f 0000005e00000002 R_X86_64_PC32 0000000000000000 .klp.sym.vmlinux.printk,0 - 4 -0000000000000028 0000003d0000000b R_X86_64_32S 0000000000000000 .klp.sym.btrfs.btrfs_ktype,0 + 0 -0000000000000036 0000003b00000002 R_X86_64_PC32 0000000000000000 .klp.sym.btrfs.can_modify_feature.isra.3,0 - 4 -000000000000004c 0000004900000002 R_X86_64_PC32 0000000000000000 .klp.sym.vmlinux.snprintf,0 - 4 -[ snip ] ^ - | - [*] -[*] Every symbol referenced by a relocation is a livepatch symbol. - --------------------- -3. Livepatch symbols --------------------- - -------------------------------- -3.1 What are livepatch symbols? -------------------------------- -Livepatch symbols are symbols referred to by livepatch relocation sections. -These are symbols accessed from new versions of functions for patched -objects, whose addresses cannot be resolved by the module loader (because -they are local or unexported global syms). Since the module loader only -resolves exported syms, and not every symbol referenced by the new patched -functions is exported, livepatch symbols were introduced. They are used -also in cases where we cannot immediately know the address of a symbol when -a patch module loads. For example, this is the case when livepatch patches -a module that is not loaded yet. In this case, the relevant livepatch -symbols are resolved simply when the target module loads. In any case, for -any livepatch relocation section, all livepatch symbols referenced by that -section must be resolved before livepatch can call apply_relocate_add() for -that reloc section. - -Livepatch symbols must be marked with SHN_LIVEPATCH so that the module -loader can identify and ignore them. Livepatch modules keep these symbols -in their symbol tables, and the symbol table is made accessible through -module->symtab. - -------------------------------------- -3.2 A livepatch module's symbol table -------------------------------------- -Normally, a stripped down copy of a module's symbol table (containing only -"core" symbols) is made available through module->symtab (See layout_symtab() -in kernel/module.c). For livepatch modules, the symbol table copied into memory -on module load must be exactly the same as the symbol table produced when the -patch module was compiled. This is because the relocations in each livepatch -relocation section refer to their respective symbols with their symbol indices, -and the original symbol indices (and thus the symtab ordering) must be -preserved in order for apply_relocate_add() to find the right symbol. - -For example, take this particular rela from a livepatch module: -Relocation section '.klp.rela.btrfs.text.btrfs_feature_attr_show' at offset 0x2ba0 contains 4 entries: - Offset Info Type Symbol's Value Symbol's Name + Addend -000000000000001f 0000005e00000002 R_X86_64_PC32 0000000000000000 .klp.sym.vmlinux.printk,0 - 4 - -This rela refers to the symbol '.klp.sym.vmlinux.printk,0', and the symbol index is encoded -in 'Info'. Here its symbol index is 0x5e, which is 94 in decimal, which refers to the -symbol index 94. -And in this patch module's corresponding symbol table, symbol index 94 refers to that very symbol: -[ snip ] -94: 0000000000000000 0 NOTYPE GLOBAL DEFAULT OS [0xff20] .klp.sym.vmlinux.printk,0 -[ snip ] - ---------------------------- -3.3 Livepatch symbol format ---------------------------- - -3.3.1 Required flags --------------------- -Livepatch symbols must have their section index marked as SHN_LIVEPATCH, so -that the module loader can identify them and not attempt to resolve them. -See include/uapi/linux/elf.h for the actual definitions. - -3.3.2 Required name format --------------------------- -Livepatch symbol names must conform to the following format: - -.klp.sym.objname.symbol_name,sympos -^ ^^ ^ ^ ^ ^ -|_______||_____| |_________| | - [A] [B] [C] [D] - -[A] The symbol name is prefixed with the string ".klp.sym." -[B] The name of the object (i.e. "vmlinux" or name of module) to - which the symbol belongs follows immediately after the prefix. -[C] The actual name of the symbol. -[D] The position of the symbol in the object (as according to kallsyms) - This is used to differentiate duplicate symbols within the same - object. The symbol position is expressed numerically (0, 1, 2...). - The symbol position of a unique symbol is 0. - -3.3.3 Example livepatch symbol names: -------------------------------------- -.klp.sym.vmlinux.snprintf,0 -.klp.sym.vmlinux.printk,0 -.klp.sym.btrfs.btrfs_ktype,0 - -3.3.4 Example `readelf --symbols` output for a patch module: ------------------------------------------------------------- -Symbol table '.symtab' contains 127 entries: - Num: Value Size Type Bind Vis Ndx Name - [ snip ] - 73: 0000000000000000 0 NOTYPE GLOBAL DEFAULT OS [0xff20] .klp.sym.vmlinux.snprintf,0 - 74: 0000000000000000 0 NOTYPE GLOBAL DEFAULT OS [0xff20] .klp.sym.vmlinux.capable,0 - 75: 0000000000000000 0 NOTYPE GLOBAL DEFAULT OS [0xff20] .klp.sym.vmlinux.find_next_bit,0 - 76: 0000000000000000 0 NOTYPE GLOBAL DEFAULT OS [0xff20] .klp.sym.vmlinux.si_swapinfo,0 - [ snip ] ^ - | - [*] -[*] Note that the 'Ndx' (Section index) for these symbols is SHN_LIVEPATCH (0xff20). - "OS" means OS-specific. - ---------------------------------- -4. Architecture-specific sections ---------------------------------- -Architectures may override arch_klp_init_object_loaded() to perform -additional arch-specific tasks when a target module loads, such as applying -arch-specific sections. On x86 for example, we must apply per-object -.altinstructions and .parainstructions sections when a target module loads. -These sections must be prefixed with ".klp.arch.$objname." so that they can -be easily identified when iterating through a patch module's Elf sections -(See arch/x86/kernel/livepatch.c for a complete example). - --------------------------------------- -5. Symbol table and Elf section access --------------------------------------- -A livepatch module's symbol table is accessible through module->symtab. - -Since apply_relocate_add() requires access to a module's section headers, -symbol table, and relocation section indices, Elf information is preserved for -livepatch modules and is made accessible by the module loader through -module->klp_info, which is a klp_modinfo struct. When a livepatch module loads, -this struct is filled in by the module loader. Its fields are documented below: - -struct klp_modinfo { - Elf_Ehdr hdr; /* Elf header */ - Elf_Shdr *sechdrs; /* Section header table */ - char *secstrings; /* String table for the section headers */ - unsigned int symndx; /* The symbol table section index */ -}; diff --git a/Documentation/livepatch/shadow-vars.rst b/Documentation/livepatch/shadow-vars.rst new file mode 100644 index 000000000000..c05715aeafa4 --- /dev/null +++ b/Documentation/livepatch/shadow-vars.rst @@ -0,0 +1,226 @@ +================ +Shadow Variables +================ + +Shadow variables are a simple way for livepatch modules to associate +additional "shadow" data with existing data structures. Shadow data is +allocated separately from parent data structures, which are left +unmodified. The shadow variable API described in this document is used +to allocate/add and remove/free shadow variables to/from their parents. + +The implementation introduces a global, in-kernel hashtable that +associates pointers to parent objects and a numeric identifier of the +shadow data. The numeric identifier is a simple enumeration that may be +used to describe shadow variable version, class or type, etc. More +specifically, the parent pointer serves as the hashtable key while the +numeric id subsequently filters hashtable queries. Multiple shadow +variables may attach to the same parent object, but their numeric +identifier distinguishes between them. + + +1. Brief API summary +==================== + +(See the full API usage docbook notes in livepatch/shadow.c.) + +A hashtable references all shadow variables. These references are +stored and retrieved through a pair. + +* The klp_shadow variable data structure encapsulates both tracking + meta-data and shadow-data: + + - meta-data + + - obj - pointer to parent object + - id - data identifier + + - data[] - storage for shadow data + +It is important to note that the klp_shadow_alloc() and +klp_shadow_get_or_alloc() are zeroing the variable by default. +They also allow to call a custom constructor function when a non-zero +value is needed. Callers should provide whatever mutual exclusion +is required. + +Note that the constructor is called under klp_shadow_lock spinlock. It allows +to do actions that can be done only once when a new variable is allocated. + +* klp_shadow_get() - retrieve a shadow variable data pointer + - search hashtable for pair + +* klp_shadow_alloc() - allocate and add a new shadow variable + - search hashtable for pair + + - if exists + + - WARN and return NULL + + - if doesn't already exist + + - allocate a new shadow variable + - initialize the variable using a custom constructor and data when provided + - add to the global hashtable + +* klp_shadow_get_or_alloc() - get existing or alloc a new shadow variable + - search hashtable for pair + + - if exists + + - return existing shadow variable + + - if doesn't already exist + + - allocate a new shadow variable + - initialize the variable using a custom constructor and data when provided + - add pair to the global hashtable + +* klp_shadow_free() - detach and free a shadow variable + - find and remove a reference from global hashtable + + - if found + + - call destructor function if defined + - free shadow variable + +* klp_shadow_free_all() - detach and free all <*, id> shadow variables + - find and remove any <*, id> references from global hashtable + + - if found + + - call destructor function if defined + - free shadow variable + + +2. Use cases +============ + +(See the example shadow variable livepatch modules in samples/livepatch/ +for full working demonstrations.) + +For the following use-case examples, consider commit 1d147bfa6429 +("mac80211: fix AP powersave TX vs. wakeup race"), which added a +spinlock to net/mac80211/sta_info.h :: struct sta_info. Each use-case +example can be considered a stand-alone livepatch implementation of this +fix. + + +Matching parent's lifecycle +--------------------------- + +If parent data structures are frequently created and destroyed, it may +be easiest to align their shadow variables lifetimes to the same +allocation and release functions. In this case, the parent data +structure is typically allocated, initialized, then registered in some +manner. Shadow variable allocation and setup can then be considered +part of the parent's initialization and should be completed before the +parent "goes live" (ie, any shadow variable get-API requests are made +for this pair.) + +For commit 1d147bfa6429, when a parent sta_info structure is allocated, +allocate a shadow copy of the ps_lock pointer, then initialize it:: + + #define PS_LOCK 1 + struct sta_info *sta_info_alloc(struct ieee80211_sub_if_data *sdata, + const u8 *addr, gfp_t gfp) + { + struct sta_info *sta; + spinlock_t *ps_lock; + + /* Parent structure is created */ + sta = kzalloc(sizeof(*sta) + hw->sta_data_size, gfp); + + /* Attach a corresponding shadow variable, then initialize it */ + ps_lock = klp_shadow_alloc(sta, PS_LOCK, sizeof(*ps_lock), gfp, + NULL, NULL); + if (!ps_lock) + goto shadow_fail; + spin_lock_init(ps_lock); + ... + +When requiring a ps_lock, query the shadow variable API to retrieve one +for a specific struct sta_info::: + + void ieee80211_sta_ps_deliver_wakeup(struct sta_info *sta) + { + spinlock_t *ps_lock; + + /* sync with ieee80211_tx_h_unicast_ps_buf */ + ps_lock = klp_shadow_get(sta, PS_LOCK); + if (ps_lock) + spin_lock(ps_lock); + ... + +When the parent sta_info structure is freed, first free the shadow +variable:: + + void sta_info_free(struct ieee80211_local *local, struct sta_info *sta) + { + klp_shadow_free(sta, PS_LOCK, NULL); + kfree(sta); + ... + + +In-flight parent objects +------------------------ + +Sometimes it may not be convenient or possible to allocate shadow +variables alongside their parent objects. Or a livepatch fix may +require shadow varibles to only a subset of parent object instances. In +these cases, the klp_shadow_get_or_alloc() call can be used to attach +shadow variables to parents already in-flight. + +For commit 1d147bfa6429, a good spot to allocate a shadow spinlock is +inside ieee80211_sta_ps_deliver_wakeup():: + + int ps_lock_shadow_ctor(void *obj, void *shadow_data, void *ctor_data) + { + spinlock_t *lock = shadow_data; + + spin_lock_init(lock); + return 0; + } + + #define PS_LOCK 1 + void ieee80211_sta_ps_deliver_wakeup(struct sta_info *sta) + { + spinlock_t *ps_lock; + + /* sync with ieee80211_tx_h_unicast_ps_buf */ + ps_lock = klp_shadow_get_or_alloc(sta, PS_LOCK, + sizeof(*ps_lock), GFP_ATOMIC, + ps_lock_shadow_ctor, NULL); + + if (ps_lock) + spin_lock(ps_lock); + ... + +This usage will create a shadow variable, only if needed, otherwise it +will use one that was already created for this pair. + +Like the previous use-case, the shadow spinlock needs to be cleaned up. +A shadow variable can be freed just before its parent object is freed, +or even when the shadow variable itself is no longer required. + + +Other use-cases +--------------- + +Shadow variables can also be used as a flag indicating that a data +structure was allocated by new, livepatched code. In this case, it +doesn't matter what data value the shadow variable holds, its existence +suggests how to handle the parent object. + + +3. References +============= + +* https://github.com/dynup/kpatch + + The livepatch implementation is based on the kpatch version of shadow + variables. + +* http://files.mkgnu.net/files/dynamos/doc/papers/dynamos_eurosys_07.pdf + + Dynamic and Adaptive Updates of Non-Quiescent Subsystems in Commodity + Operating System Kernels (Kritis Makris, Kyung Dong Ryu 2007) presented + a datatype update technique called "shadow data structures". diff --git a/Documentation/livepatch/shadow-vars.txt b/Documentation/livepatch/shadow-vars.txt deleted file mode 100644 index ecc09a7be5dd..000000000000 --- a/Documentation/livepatch/shadow-vars.txt +++ /dev/null @@ -1,209 +0,0 @@ -================ -Shadow Variables -================ - -Shadow variables are a simple way for livepatch modules to associate -additional "shadow" data with existing data structures. Shadow data is -allocated separately from parent data structures, which are left -unmodified. The shadow variable API described in this document is used -to allocate/add and remove/free shadow variables to/from their parents. - -The implementation introduces a global, in-kernel hashtable that -associates pointers to parent objects and a numeric identifier of the -shadow data. The numeric identifier is a simple enumeration that may be -used to describe shadow variable version, class or type, etc. More -specifically, the parent pointer serves as the hashtable key while the -numeric id subsequently filters hashtable queries. Multiple shadow -variables may attach to the same parent object, but their numeric -identifier distinguishes between them. - - -1. Brief API summary -==================== - -(See the full API usage docbook notes in livepatch/shadow.c.) - -A hashtable references all shadow variables. These references are -stored and retrieved through a pair. - -* The klp_shadow variable data structure encapsulates both tracking -meta-data and shadow-data: - - meta-data - - obj - pointer to parent object - - id - data identifier - - data[] - storage for shadow data - -It is important to note that the klp_shadow_alloc() and -klp_shadow_get_or_alloc() are zeroing the variable by default. -They also allow to call a custom constructor function when a non-zero -value is needed. Callers should provide whatever mutual exclusion -is required. - -Note that the constructor is called under klp_shadow_lock spinlock. It allows -to do actions that can be done only once when a new variable is allocated. - -* klp_shadow_get() - retrieve a shadow variable data pointer - - search hashtable for pair - -* klp_shadow_alloc() - allocate and add a new shadow variable - - search hashtable for pair - - if exists - - WARN and return NULL - - if doesn't already exist - - allocate a new shadow variable - - initialize the variable using a custom constructor and data when provided - - add to the global hashtable - -* klp_shadow_get_or_alloc() - get existing or alloc a new shadow variable - - search hashtable for pair - - if exists - - return existing shadow variable - - if doesn't already exist - - allocate a new shadow variable - - initialize the variable using a custom constructor and data when provided - - add pair to the global hashtable - -* klp_shadow_free() - detach and free a shadow variable - - find and remove a reference from global hashtable - - if found - - call destructor function if defined - - free shadow variable - -* klp_shadow_free_all() - detach and free all <*, id> shadow variables - - find and remove any <*, id> references from global hashtable - - if found - - call destructor function if defined - - free shadow variable - - -2. Use cases -============ - -(See the example shadow variable livepatch modules in samples/livepatch/ -for full working demonstrations.) - -For the following use-case examples, consider commit 1d147bfa6429 -("mac80211: fix AP powersave TX vs. wakeup race"), which added a -spinlock to net/mac80211/sta_info.h :: struct sta_info. Each use-case -example can be considered a stand-alone livepatch implementation of this -fix. - - -Matching parent's lifecycle ---------------------------- - -If parent data structures are frequently created and destroyed, it may -be easiest to align their shadow variables lifetimes to the same -allocation and release functions. In this case, the parent data -structure is typically allocated, initialized, then registered in some -manner. Shadow variable allocation and setup can then be considered -part of the parent's initialization and should be completed before the -parent "goes live" (ie, any shadow variable get-API requests are made -for this pair.) - -For commit 1d147bfa6429, when a parent sta_info structure is allocated, -allocate a shadow copy of the ps_lock pointer, then initialize it: - -#define PS_LOCK 1 -struct sta_info *sta_info_alloc(struct ieee80211_sub_if_data *sdata, - const u8 *addr, gfp_t gfp) -{ - struct sta_info *sta; - spinlock_t *ps_lock; - - /* Parent structure is created */ - sta = kzalloc(sizeof(*sta) + hw->sta_data_size, gfp); - - /* Attach a corresponding shadow variable, then initialize it */ - ps_lock = klp_shadow_alloc(sta, PS_LOCK, sizeof(*ps_lock), gfp, - NULL, NULL); - if (!ps_lock) - goto shadow_fail; - spin_lock_init(ps_lock); - ... - -When requiring a ps_lock, query the shadow variable API to retrieve one -for a specific struct sta_info: - -void ieee80211_sta_ps_deliver_wakeup(struct sta_info *sta) -{ - spinlock_t *ps_lock; - - /* sync with ieee80211_tx_h_unicast_ps_buf */ - ps_lock = klp_shadow_get(sta, PS_LOCK); - if (ps_lock) - spin_lock(ps_lock); - ... - -When the parent sta_info structure is freed, first free the shadow -variable: - -void sta_info_free(struct ieee80211_local *local, struct sta_info *sta) -{ - klp_shadow_free(sta, PS_LOCK, NULL); - kfree(sta); - ... - - -In-flight parent objects ------------------------- - -Sometimes it may not be convenient or possible to allocate shadow -variables alongside their parent objects. Or a livepatch fix may -require shadow varibles to only a subset of parent object instances. In -these cases, the klp_shadow_get_or_alloc() call can be used to attach -shadow variables to parents already in-flight. - -For commit 1d147bfa6429, a good spot to allocate a shadow spinlock is -inside ieee80211_sta_ps_deliver_wakeup(): - -int ps_lock_shadow_ctor(void *obj, void *shadow_data, void *ctor_data) -{ - spinlock_t *lock = shadow_data; - - spin_lock_init(lock); - return 0; -} - -#define PS_LOCK 1 -void ieee80211_sta_ps_deliver_wakeup(struct sta_info *sta) -{ - spinlock_t *ps_lock; - - /* sync with ieee80211_tx_h_unicast_ps_buf */ - ps_lock = klp_shadow_get_or_alloc(sta, PS_LOCK, - sizeof(*ps_lock), GFP_ATOMIC, - ps_lock_shadow_ctor, NULL); - - if (ps_lock) - spin_lock(ps_lock); - ... - -This usage will create a shadow variable, only if needed, otherwise it -will use one that was already created for this pair. - -Like the previous use-case, the shadow spinlock needs to be cleaned up. -A shadow variable can be freed just before its parent object is freed, -or even when the shadow variable itself is no longer required. - - -Other use-cases ---------------- - -Shadow variables can also be used as a flag indicating that a data -structure was allocated by new, livepatched code. In this case, it -doesn't matter what data value the shadow variable holds, its existence -suggests how to handle the parent object. - - -3. References -============= - -* https://github.com/dynup/kpatch -The livepatch implementation is based on the kpatch version of shadow -variables. - -* http://files.mkgnu.net/files/dynamos/doc/papers/dynamos_eurosys_07.pdf -Dynamic and Adaptive Updates of Non-Quiescent Subsystems in Commodity -Operating System Kernels (Kritis Makris, Kyung Dong Ryu 2007) presented -a datatype update technique called "shadow data structures". diff --git a/tools/objtool/Documentation/stack-validation.txt b/tools/objtool/Documentation/stack-validation.txt index 3995735a878f..8df526c80b65 100644 --- a/tools/objtool/Documentation/stack-validation.txt +++ b/tools/objtool/Documentation/stack-validation.txt @@ -111,7 +111,7 @@ c) Higher live patching compatibility rate be detectable). Objtool makes that possible. For more details, see the livepatch documentation in the Linux kernel - source tree at Documentation/livepatch/livepatch.txt. + source tree at Documentation/livepatch/livepatch.rst. Rules ----- -- cgit v1.2.3 From d9defe448f4c7b88ca2ae636a321ef8970fa718d Mon Sep 17 00:00:00 2001 From: Petr Mladek Date: Fri, 3 May 2019 16:30:24 +0200 Subject: docs/livepatch: Unify style of livepatch documentation in the ReST format Make the structure of "Livepatch module Elf format" document similar to the main "Livepatch" document. Also make the structure of "(Un)patching Callbacks" document similar to the "Shadow Variables" document. It fixes the most visible inconsistencies of the documentation generated from the ReST format. Signed-off-by: Petr Mladek Acked-by: Joe Lawrence Acked-by: Josh Poimboeuf Acked-by: Miroslav Benes Reviewed-by: Mauro Carvalho Chehab Reviewed-by: Kamalesh Babulal Signed-off-by: Jonathan Corbet --- Documentation/livepatch/callbacks.rst | 33 ++--- Documentation/livepatch/module-elf-format.rst | 186 ++++++++++++-------------- 2 files changed, 104 insertions(+), 115 deletions(-) (limited to 'Documentation') diff --git a/Documentation/livepatch/callbacks.rst b/Documentation/livepatch/callbacks.rst index d76d1f0d9fcf..470944aa8658 100644 --- a/Documentation/livepatch/callbacks.rst +++ b/Documentation/livepatch/callbacks.rst @@ -4,7 +4,7 @@ Livepatch (un)patch-callbacks provide a mechanism for livepatch modules to execute callback functions when a kernel object is (un)patched. They -can be considered a "power feature" that extends livepatching abilities +can be considered a **power feature** that **extends livepatching abilities** to include: - Safe updates to global data @@ -17,6 +17,9 @@ In most cases, (un)patch callbacks will need to be used in conjunction with memory barriers and kernel synchronization primitives, like mutexes/spinlocks, or even stop_machine(), to avoid concurrency issues. +1. Motivation +============= + Callbacks differ from existing kernel facilities: - Module init/exit code doesn't run when disabling and re-enabling a @@ -28,6 +31,9 @@ Callbacks are part of the klp_object structure and their implementation is specific to that klp_object. Other livepatch objects may or may not be patched, irrespective of the target klp_object's current state. +2. Callback types +================= + Callbacks can be registered for the following livepatch actions: * Pre-patch @@ -47,6 +53,9 @@ Callbacks can be registered for the following livepatch actions: been restored and no tasks are running patched code, used to cleanup pre-patch callback resources +3. How it works +=============== + Each callback is optional, omitting one does not preclude specifying any other. However, the livepatching core executes the handlers in symmetry: pre-patch callbacks have a post-unpatch counterpart and @@ -90,11 +99,14 @@ If the object did successfully patch, but the patch transition never started for some reason (e.g., if another object failed to patch), only the post-unpatch callback will be called. +4. Use cases +============ -Example Use-cases -================= +Sample livepatch modules demonstrating the callback API can be found in +samples/livepatch/ directory. These samples were modified for use in +kselftests and can be found in the lib/livepatch directory. -Update global data +Global data update ------------------ A pre-patch callback can be useful to update a global variable. For @@ -107,24 +119,15 @@ patch the data *after* patching is complete with a post-patch callback, so that tcp_send_challenge_ack() could first be changed to read sysctl_tcp_challenge_ack_limit with READ_ONCE. - -Support __init and probe function patches +__init and probe function patches support ----------------------------------------- Although __init and probe functions are not directly livepatch-able, it may be possible to implement similar updates via pre/post-patch callbacks. -48900cb6af42 ("virtio-net: drop NETIF_F_FRAGLIST") change the way that +The commit ``48900cb6af42 ("virtio-net: drop NETIF_F_FRAGLIST")`` change the way that virtnet_probe() initialized its driver's net_device features. A pre/post-patch callback could iterate over all such devices, making a similar change to their hw_features value. (Client functions of the value may need to be updated accordingly.) - - -Other Examples -============== - -Sample livepatch modules demonstrating the callback API can be found in -samples/livepatch/ directory. These samples were modified for use in -kselftests and can be found in the lib/livepatch directory. diff --git a/Documentation/livepatch/module-elf-format.rst b/Documentation/livepatch/module-elf-format.rst index 7f557c6f6deb..2a591e6f8e6c 100644 --- a/Documentation/livepatch/module-elf-format.rst +++ b/Documentation/livepatch/module-elf-format.rst @@ -7,30 +7,18 @@ This document outlines the Elf format requirements that livepatch modules must f .. Table of Contents - 0. Background and motivation - 1. Livepatch modinfo field - 2. Livepatch relocation sections - 2.1 What are livepatch relocation sections? - 2.2 Livepatch relocation section format - 2.2.1 Required flags - 2.2.2 Required name format - 2.2.3 Example livepatch relocation section names - 2.2.4 Example `readelf --sections` output - 2.2.5 Example `readelf --relocs` output - 3. Livepatch symbols - 3.1 What are livepatch symbols? - 3.2 A livepatch module's symbol table - 3.3 Livepatch symbol format - 3.3.1 Required flags - 3.3.2 Required name format - 3.3.3 Example livepatch symbol names - 3.3.4 Example `readelf --symbols` output - 4. Architecture-specific sections - 5. Symbol table and Elf section access - ----------------------------- -0. Background and motivation ----------------------------- + 1. Background and motivation + 2. Livepatch modinfo field + 3. Livepatch relocation sections + 3.1 Livepatch relocation section format + 4. Livepatch symbols + 4.1 A livepatch module's symbol table + 4.2 Livepatch symbol format + 5. Architecture-specific sections + 6. Symbol table and Elf section access + +1. Background and motivation +============================ Formerly, livepatch required separate architecture-specific code to write relocations. However, arch-specific code to write relocations already @@ -52,8 +40,8 @@ relocation sections and symbols, which are described in this document. The Elf constants used to mark livepatch symbols and relocation sections were selected from OS-specific ranges according to the definitions from glibc. -0.1 Why does livepatch need to write its own relocations? ---------------------------------------------------------- +Why does livepatch need to write its own relocations? +----------------------------------------------------- A typical livepatch module contains patched versions of functions that can reference non-exported global symbols and non-included local symbols. Relocations referencing these types of symbols cannot be left in as-is @@ -72,13 +60,8 @@ relas reference are special livepatch symbols (see section 2 and 3). The arch-specific livepatch relocation code is replaced by a call to apply_relocate_add(). -================================ -PATCH MODULE FORMAT REQUIREMENTS -================================ - --------------------------- -1. Livepatch modinfo field --------------------------- +2. Livepatch modinfo field +========================== Livepatch modules are required to have the "livepatch" modinfo attribute. See the sample livepatch module in samples/livepatch/ for how this is done. @@ -87,8 +70,10 @@ Livepatch modules can be identified by users by using the 'modinfo' command and looking for the presence of the "livepatch" field. This field is also used by the kernel module loader to identify livepatch modules. -Example modinfo output: ------------------------ +Example: +-------- + +**Modinfo output:** :: @@ -99,13 +84,9 @@ Example modinfo output: depends: vermagic: 4.3.0+ SMP mod_unload --------------------------------- -2. Livepatch relocation sections --------------------------------- +3. Livepatch relocation sections +================================ -------------------------------------------- -2.1 What are livepatch relocation sections? -------------------------------------------- A livepatch module manages its own Elf relocation sections to apply relocations to modules as well as to the kernel (vmlinux) at the appropriate time. For example, if a patch module patches a driver that is @@ -130,12 +111,9 @@ Every symbol referenced by a rela in a livepatch relocation section is a livepatch symbol. These must be resolved before livepatch can call apply_relocate_add(). See Section 3 for more information. ---------------------------------------- -2.2 Livepatch relocation section format ---------------------------------------- +3.1 Livepatch relocation section format +======================================= -2.2.1 Required flags --------------------- Livepatch relocation sections must be marked with the SHF_RELA_LIVEPATCH section flag. See include/uapi/linux/elf.h for the definition. The module loader recognizes this flag and will avoid applying those relocation sections @@ -143,8 +121,6 @@ at patch module load time. These sections must also be marked with SHF_ALLOC, so that the module loader doesn't discard them on module load (i.e. they will be copied into memory along with the other SHF_ALLOC sections). -2.2.2 Required name format --------------------------- The name of a livepatch relocation section must conform to the following format:: @@ -153,19 +129,28 @@ format:: |________||_____| |__________| [A] [B] [C] - [A] The relocation section name is prefixed with the string ".klp.rela." - [B] The name of the object (i.e. "vmlinux" or name of module) to - which the relocation section belongs follows immediately after the prefix. - [C] The actual name of the section to which this relocation section applies. +[A] + The relocation section name is prefixed with the string ".klp.rela." -2.2.3 Example livepatch relocation section names: -------------------------------------------------- -.klp.rela.ext4.text.ext4_attr_store -.klp.rela.vmlinux.text.cmdline_proc_show +[B] + The name of the object (i.e. "vmlinux" or name of module) to + which the relocation section belongs follows immediately after the prefix. -2.2.4 Example `readelf --sections` output for a patch -module that patches vmlinux and modules 9p, btrfs, ext4: --------------------------------------------------------- +[C] + The actual name of the section to which this relocation section applies. + +Examples: +--------- + +**Livepatch relocation section names:** + +:: + + .klp.rela.ext4.text.ext4_attr_store + .klp.rela.vmlinux.text.cmdline_proc_show + +**`readelf --sections` output for a patch +module that patches vmlinux and modules 9p, btrfs, ext4:** :: @@ -182,13 +167,14 @@ module that patches vmlinux and modules 9p, btrfs, ext4: [ snip ] ^ ^ | | [*] [*] - [*] Livepatch relocation sections are SHT_RELA sections but with a few special + +[*] + Livepatch relocation sections are SHT_RELA sections but with a few special characteristics. Notice that they are marked SHF_ALLOC ("A") so that they will not be discarded when the module is loaded into memory, as well as with the SHF_RELA_LIVEPATCH flag ("o" - for OS-specific). -2.2.5 Example `readelf --relocs` output for a patch module: ------------------------------------------------------------ +**`readelf --relocs` output for a patch module:** :: @@ -200,16 +186,14 @@ module that patches vmlinux and modules 9p, btrfs, ext4: 000000000000004c 0000004900000002 R_X86_64_PC32 0000000000000000 .klp.sym.vmlinux.snprintf,0 - 4 [ snip ] ^ | - [*] - [*] Every symbol referenced by a relocation is a livepatch symbol. + [*] + +[*] + Every symbol referenced by a relocation is a livepatch symbol. --------------------- -3. Livepatch symbols --------------------- +4. Livepatch symbols +==================== -------------------------------- -3.1 What are livepatch symbols? -------------------------------- Livepatch symbols are symbols referred to by livepatch relocation sections. These are symbols accessed from new versions of functions for patched objects, whose addresses cannot be resolved by the module loader (because @@ -229,9 +213,8 @@ loader can identify and ignore them. Livepatch modules keep these symbols in their symbol tables, and the symbol table is made accessible through module->symtab. -------------------------------------- -3.2 A livepatch module's symbol table -------------------------------------- +4.1 A livepatch module's symbol table +===================================== Normally, a stripped down copy of a module's symbol table (containing only "core" symbols) is made available through module->symtab (See layout_symtab() in kernel/module.c). For livepatch modules, the symbol table copied into memory @@ -255,18 +238,13 @@ For example, take this particular rela from a livepatch module::: 94: 0000000000000000 0 NOTYPE GLOBAL DEFAULT OS [0xff20] .klp.sym.vmlinux.printk,0 [ snip ] ---------------------------- -3.3 Livepatch symbol format ---------------------------- +4.2 Livepatch symbol format +=========================== -3.3.1 Required flags --------------------- Livepatch symbols must have their section index marked as SHN_LIVEPATCH, so that the module loader can identify them and not attempt to resolve them. See include/uapi/linux/elf.h for the actual definitions. -3.3.2 Required name format --------------------------- Livepatch symbol names must conform to the following format:: .klp.sym.objname.symbol_name,sympos @@ -274,17 +252,26 @@ Livepatch symbol names must conform to the following format:: |_______||_____| |_________| | [A] [B] [C] [D] - [A] The symbol name is prefixed with the string ".klp.sym." - [B] The name of the object (i.e. "vmlinux" or name of module) to - which the symbol belongs follows immediately after the prefix. - [C] The actual name of the symbol. - [D] The position of the symbol in the object (as according to kallsyms) - This is used to differentiate duplicate symbols within the same - object. The symbol position is expressed numerically (0, 1, 2...). - The symbol position of a unique symbol is 0. +[A] + The symbol name is prefixed with the string ".klp.sym." + +[B] + The name of the object (i.e. "vmlinux" or name of module) to + which the symbol belongs follows immediately after the prefix. -3.3.3 Example livepatch symbol names: -------------------------------------- +[C] + The actual name of the symbol. + +[D] + The position of the symbol in the object (as according to kallsyms) + This is used to differentiate duplicate symbols within the same + object. The symbol position is expressed numerically (0, 1, 2...). + The symbol position of a unique symbol is 0. + +Examples: +--------- + +**Livepatch symbol names:** :: @@ -292,8 +279,7 @@ Livepatch symbol names must conform to the following format:: .klp.sym.vmlinux.printk,0 .klp.sym.btrfs.btrfs_ktype,0 -3.3.4 Example `readelf --symbols` output for a patch module: ------------------------------------------------------------- +**`readelf --symbols` output for a patch module:** :: @@ -307,12 +293,13 @@ Livepatch symbol names must conform to the following format:: [ snip ] ^ | [*] - [*] Note that the 'Ndx' (Section index) for these symbols is SHN_LIVEPATCH (0xff20). - "OS" means OS-specific. ---------------------------------- -4. Architecture-specific sections ---------------------------------- +[*] + Note that the 'Ndx' (Section index) for these symbols is SHN_LIVEPATCH (0xff20). + "OS" means OS-specific. + +5. Architecture-specific sections +================================= Architectures may override arch_klp_init_object_loaded() to perform additional arch-specific tasks when a target module loads, such as applying arch-specific sections. On x86 for example, we must apply per-object @@ -321,9 +308,8 @@ These sections must be prefixed with ".klp.arch.$objname." so that they can be easily identified when iterating through a patch module's Elf sections (See arch/x86/kernel/livepatch.c for a complete example). --------------------------------------- -5. Symbol table and Elf section access --------------------------------------- +6. Symbol table and Elf section access +====================================== A livepatch module's symbol table is accessible through module->symtab. Since apply_relocate_add() requires access to a module's section headers, -- cgit v1.2.3 From e672f8bf71c66253197e503f75c771dd28ada4a0 Mon Sep 17 00:00:00 2001 From: speck for Pawan Gupta Date: Mon, 6 May 2019 12:23:50 -0700 Subject: x86/mds: Add MDSUM variant to the MDS documentation Updated the documentation for a new CVE-2019-11091 Microarchitectural Data Sampling Uncacheable Memory (MDSUM) which is a variant of Microarchitectural Data Sampling (MDS). MDS is a family of side channel attacks on internal buffers in Intel CPUs. MDSUM is a special case of MSBDS, MFBDS and MLPDS. An uncacheable load from memory that takes a fault or assist can leave data in a microarchitectural structure that may later be observed using one of the same methods used by MSBDS, MFBDS or MLPDS. There are no new code changes expected for MDSUM. The existing mitigation for MDS applies to MDSUM as well. Signed-off-by: Pawan Gupta Signed-off-by: Thomas Gleixner Reviewed-by: Tyler Hicks Reviewed-by: Jon Masters --- Documentation/admin-guide/hw-vuln/mds.rst | 5 +++-- Documentation/x86/mds.rst | 5 +++++ 2 files changed, 8 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/admin-guide/hw-vuln/mds.rst b/Documentation/admin-guide/hw-vuln/mds.rst index 244ab47d1fb3..e0dccf414eca 100644 --- a/Documentation/admin-guide/hw-vuln/mds.rst +++ b/Documentation/admin-guide/hw-vuln/mds.rst @@ -32,11 +32,12 @@ Related CVEs The following CVE entries are related to the MDS vulnerability: - ============== ===== ============================================== + ============== ===== =================================================== CVE-2018-12126 MSBDS Microarchitectural Store Buffer Data Sampling CVE-2018-12130 MFBDS Microarchitectural Fill Buffer Data Sampling CVE-2018-12127 MLPDS Microarchitectural Load Port Data Sampling - ============== ===== ============================================== + CVE-2019-11091 MDSUM Microarchitectural Data Sampling Uncacheable Memory + ============== ===== =================================================== Problem ------- diff --git a/Documentation/x86/mds.rst b/Documentation/x86/mds.rst index 3d6f943f1afb..979945be257a 100644 --- a/Documentation/x86/mds.rst +++ b/Documentation/x86/mds.rst @@ -12,6 +12,7 @@ on internal buffers in Intel CPUs. The variants are: - Microarchitectural Store Buffer Data Sampling (MSBDS) (CVE-2018-12126) - Microarchitectural Fill Buffer Data Sampling (MFBDS) (CVE-2018-12130) - Microarchitectural Load Port Data Sampling (MLPDS) (CVE-2018-12127) + - Microarchitectural Data Sampling Uncacheable Memory (MDSUM) (CVE-2019-11091) MSBDS leaks Store Buffer Entries which can be speculatively forwarded to a dependent load (store-to-load forwarding) as an optimization. The forward @@ -38,6 +39,10 @@ faulting or assisting loads under certain conditions, which again can be exploited eventually. Load ports are shared between Hyper-Threads so cross thread leakage is possible. +MDSUM is a special case of MSBDS, MFBDS and MLPDS. An uncacheable load from +memory that takes a fault or assist can leave data in a microarchitectural +structure that may later be observed using one of the same methods used by +MSBDS, MFBDS or MLPDS. Exposure assumptions -------------------- -- cgit v1.2.3 From ea01668f9f43021b28b3f4d5ffad50106a1e1301 Mon Sep 17 00:00:00 2001 From: Tyler Hicks Date: Mon, 6 May 2019 23:52:58 +0000 Subject: Documentation: Correct the possible MDS sysfs values Adjust the last two rows in the table that display possible values when MDS mitigation is enabled. They both were slightly innacurate. In addition, convert the table of possible values and their descriptions to a list-table. The simple table format uses the top border of equals signs to determine cell width which resulted in the first column being far too wide in comparison to the second column that contained the majority of the text. Signed-off-by: Tyler Hicks Signed-off-by: Thomas Gleixner --- Documentation/admin-guide/hw-vuln/mds.rst | 29 +++++++++++++---------------- 1 file changed, 13 insertions(+), 16 deletions(-) (limited to 'Documentation') diff --git a/Documentation/admin-guide/hw-vuln/mds.rst b/Documentation/admin-guide/hw-vuln/mds.rst index e0dccf414eca..e3a796c0d3a2 100644 --- a/Documentation/admin-guide/hw-vuln/mds.rst +++ b/Documentation/admin-guide/hw-vuln/mds.rst @@ -95,22 +95,19 @@ mitigations are active. The relevant sysfs file is: The possible values in this file are: - ========================================= ================================= - 'Not affected' The processor is not vulnerable - - 'Vulnerable' The processor is vulnerable, - but no mitigation enabled - - 'Vulnerable: Clear CPU buffers attempted' The processor is vulnerable but - microcode is not updated. - The mitigation is enabled on a - best effort basis. - See :ref:`vmwerv` - - 'Mitigation: CPU buffer clear' The processor is vulnerable and the - CPU buffer clearing mitigation is - enabled. - ========================================= ================================= + .. list-table:: + + * - 'Not affected' + - The processor is not vulnerable + * - 'Vulnerable' + - The processor is vulnerable, but no mitigation enabled + * - 'Vulnerable: Clear CPU buffers attempted, no microcode' + - The processor is vulnerable but microcode is not updated. + + The mitigation is enabled on a best effort basis. See :ref:`vmwerv` + * - 'Mitigation: Clear CPU buffers' + - The processor is vulnerable and the CPU buffer clearing mitigation is + enabled. If the processor is vulnerable then the following information is appended to the above information: -- cgit v1.2.3 From 95310e348a321b45fb746c176961d4da72344282 Mon Sep 17 00:00:00 2001 From: Josh Poimboeuf Date: Tue, 7 May 2019 15:05:22 -0500 Subject: x86/speculation/mds: Fix documentation typo Fix a minor typo in the MDS documentation: "eanbled" -> "enabled". Reported-by: Jeff Bastian Signed-off-by: Josh Poimboeuf Signed-off-by: Thomas Gleixner --- Documentation/x86/mds.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/x86/mds.rst b/Documentation/x86/mds.rst index 979945be257a..534e9baa4e1d 100644 --- a/Documentation/x86/mds.rst +++ b/Documentation/x86/mds.rst @@ -116,7 +116,7 @@ Kernel internal mitigation modes off Mitigation is disabled. Either the CPU is not affected or mds=off is supplied on the kernel command line - full Mitigation is eanbled. CPU is affected and MD_CLEAR is + full Mitigation is enabled. CPU is affected and MD_CLEAR is advertised in CPUID. vmwerv Mitigation is enabled. CPU is affected and MD_CLEAR is not -- cgit v1.2.3 From 13a22f73319c75511bd6b49cc77afb15fed0a91e Mon Sep 17 00:00:00 2001 From: Bartosz Golaszewski Date: Tue, 23 Apr 2019 11:04:41 +0200 Subject: dt-bindings: mfd: Add DT bindings for max77650 Add a DT binding document for max77650 ultra-low power PMIC. This describes the core mfd device and the GPIO module. Signed-off-by: Bartosz Golaszewski Reviewed-by: Rob Herring Acked-by: Pavel Machek Signed-off-by: Lee Jones --- Documentation/devicetree/bindings/mfd/max77650.txt | 46 ++++++++++++++++++++++ 1 file changed, 46 insertions(+) create mode 100644 Documentation/devicetree/bindings/mfd/max77650.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mfd/max77650.txt b/Documentation/devicetree/bindings/mfd/max77650.txt new file mode 100644 index 000000000000..b529d8d19335 --- /dev/null +++ b/Documentation/devicetree/bindings/mfd/max77650.txt @@ -0,0 +1,46 @@ +MAX77650 ultra low-power PMIC from Maxim Integrated. + +Required properties: +------------------- +- compatible: Must be "maxim,max77650" +- reg: I2C device address. +- interrupts: The interrupt on the parent the controller is + connected to. +- interrupt-controller: Marks the device node as an interrupt controller. +- #interrupt-cells: Must be <2>. + +- gpio-controller: Marks the device node as a gpio controller. +- #gpio-cells: Must be <2>. The first cell is the pin number and + the second cell is used to specify the gpio active + state. + +Optional properties: +-------------------- +gpio-line-names: Single string containing the name of the GPIO line. + +The GPIO-controller module is represented as part of the top-level PMIC +node. The device exposes a single GPIO line. + +For device-tree bindings of other sub-modules (regulator, power supply, +LEDs and onkey) refer to the binding documents under the respective +sub-system directories. + +For more details on GPIO bindings, please refer to the generic GPIO DT +binding document . + +Example: +-------- + + pmic@48 { + compatible = "maxim,max77650"; + reg = <0x48>; + + interrupt-controller; + interrupt-parent = <&gpio2>; + #interrupt-cells = <2>; + interrupts = <3 IRQ_TYPE_LEVEL_LOW>; + + gpio-controller; + #gpio-cells = <2>; + gpio-line-names = "max77650-charger"; + }; -- cgit v1.2.3 From 424ece627cd9e61ecd35ddd306b6bbda5e17ec24 Mon Sep 17 00:00:00 2001 From: Bartosz Golaszewski Date: Tue, 23 Apr 2019 11:04:42 +0200 Subject: dt-bindings: power: supply: Add DT bindings for max77650 Add the DT binding document for the battery charger module of max77650. Signed-off-by: Bartosz Golaszewski Reviewed-by: Sebastian Reichel Signed-off-by: Lee Jones --- .../bindings/power/supply/max77650-charger.txt | 28 ++++++++++++++++++++++ 1 file changed, 28 insertions(+) create mode 100644 Documentation/devicetree/bindings/power/supply/max77650-charger.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/power/supply/max77650-charger.txt b/Documentation/devicetree/bindings/power/supply/max77650-charger.txt new file mode 100644 index 000000000000..e6d0fb6ff94e --- /dev/null +++ b/Documentation/devicetree/bindings/power/supply/max77650-charger.txt @@ -0,0 +1,28 @@ +Battery charger driver for MAX77650 PMIC from Maxim Integrated. + +This module is part of the MAX77650 MFD device. For more details +see Documentation/devicetree/bindings/mfd/max77650.txt. + +The charger is represented as a sub-node of the PMIC node on the device tree. + +Required properties: +-------------------- +- compatible: Must be "maxim,max77650-charger" + +Optional properties: +-------------------- +- input-voltage-min-microvolt: Minimum CHGIN regulation voltage. Must be one + of: 4000000, 4100000, 4200000, 4300000, + 4400000, 4500000, 4600000, 4700000. +- input-current-limit-microamp: CHGIN input current limit (in microamps). Must + be one of: 95000, 190000, 285000, 380000, + 475000. + +Example: +-------- + + charger { + compatible = "maxim,max77650-charger"; + input-voltage-min-microvolt = <4200000>; + input-current-limit-microamp = <285000>; + }; -- cgit v1.2.3 From 5a032b0697c79d7499ba955b40fa9a7756f08dad Mon Sep 17 00:00:00 2001 From: Bartosz Golaszewski Date: Tue, 23 Apr 2019 11:04:43 +0200 Subject: dt-bindings: leds: Add DT bindings for max77650 Add the DT binding document for the LEDs module of max77650. Signed-off-by: Bartosz Golaszewski Reviewed-by: Rob Herring Acked-by: Pavel Machek Signed-off-by: Lee Jones --- .../devicetree/bindings/leds/leds-max77650.txt | 57 ++++++++++++++++++++++ 1 file changed, 57 insertions(+) create mode 100644 Documentation/devicetree/bindings/leds/leds-max77650.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/leds/leds-max77650.txt b/Documentation/devicetree/bindings/leds/leds-max77650.txt new file mode 100644 index 000000000000..3a67115cc1da --- /dev/null +++ b/Documentation/devicetree/bindings/leds/leds-max77650.txt @@ -0,0 +1,57 @@ +LED driver for MAX77650 PMIC from Maxim Integrated. + +This module is part of the MAX77650 MFD device. For more details +see Documentation/devicetree/bindings/mfd/max77650.txt. + +The LED controller is represented as a sub-node of the PMIC node on +the device tree. + +This device has three current sinks. + +Required properties: +-------------------- +- compatible: Must be "maxim,max77650-led" +- #address-cells: Must be <1>. +- #size-cells: Must be <0>. + +Each LED is represented as a sub-node of the LED-controller node. Up to +three sub-nodes can be defined. + +Required properties of the sub-node: +------------------------------------ + +- reg: Must be <0>, <1> or <2>. + +Optional properties of the sub-node: +------------------------------------ + +- label: See Documentation/devicetree/bindings/leds/common.txt +- linux,default-trigger: See Documentation/devicetree/bindings/leds/common.txt + +For more details, please refer to the generic GPIO DT binding document +. + +Example: +-------- + + leds { + compatible = "maxim,max77650-led"; + #address-cells = <1>; + #size-cells = <0>; + + led@0 { + reg = <0>; + label = "blue:usr0"; + }; + + led@1 { + reg = <1>; + label = "red:usr1"; + linux,default-trigger = "heartbeat"; + }; + + led@2 { + reg = <2>; + label = "green:usr2"; + }; + }; -- cgit v1.2.3 From 93fb61e2c3defc6fe89cdf041f7f6a659b64ec56 Mon Sep 17 00:00:00 2001 From: Bartosz Golaszewski Date: Tue, 23 Apr 2019 11:04:44 +0200 Subject: dt-bindings: input: Add DT bindings for max77650 Add the DT binding document for the onkey module of max77650. Signed-off-by: Bartosz Golaszewski Reviewed-by: Rob Herring Signed-off-by: Lee Jones --- .../devicetree/bindings/input/max77650-onkey.txt | 26 ++++++++++++++++++++++ 1 file changed, 26 insertions(+) create mode 100644 Documentation/devicetree/bindings/input/max77650-onkey.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/input/max77650-onkey.txt b/Documentation/devicetree/bindings/input/max77650-onkey.txt new file mode 100644 index 000000000000..477dc74f452a --- /dev/null +++ b/Documentation/devicetree/bindings/input/max77650-onkey.txt @@ -0,0 +1,26 @@ +Onkey driver for MAX77650 PMIC from Maxim Integrated. + +This module is part of the MAX77650 MFD device. For more details +see Documentation/devicetree/bindings/mfd/max77650.txt. + +The onkey controller is represented as a sub-node of the PMIC node on +the device tree. + +Required properties: +-------------------- +- compatible: Must be "maxim,max77650-onkey". + +Optional properties: +- linux,code: The key-code to be reported when the key is pressed. + Defaults to KEY_POWER. +- maxim,onkey-slide: The system's button is a slide switch, not the default + push button. + +Example: +-------- + + onkey { + compatible = "maxim,max77650-onkey"; + linux,code = ; + maxim,onkey-slide; + }; -- cgit v1.2.3 From d7547c55cbe7471255ca51f14bcd4699f5eaabe5 Mon Sep 17 00:00:00 2001 From: Peter Xu Date: Wed, 8 May 2019 17:15:47 +0800 Subject: KVM: Introduce KVM_CAP_MANUAL_DIRTY_LOG_PROTECT2 The previous KVM_CAP_MANUAL_DIRTY_LOG_PROTECT has some problem which blocks the correct usage from userspace. Obsolete the old one and introduce a new capability bit for it. Suggested-by: Paolo Bonzini Signed-off-by: Peter Xu Signed-off-by: Paolo Bonzini --- Documentation/virtual/kvm/api.txt | 15 ++++++++++----- include/uapi/linux/kvm.h | 5 +++-- tools/testing/selftests/kvm/dirty_log_test.c | 4 ++-- virt/kvm/kvm_main.c | 4 ++-- 4 files changed, 17 insertions(+), 11 deletions(-) (limited to 'Documentation') diff --git a/Documentation/virtual/kvm/api.txt b/Documentation/virtual/kvm/api.txt index 675cb0bea903..47a5eb00bc53 100644 --- a/Documentation/virtual/kvm/api.txt +++ b/Documentation/virtual/kvm/api.txt @@ -330,7 +330,7 @@ They must be less than the value that KVM_CHECK_EXTENSION returns for the KVM_CAP_MULTI_ADDRESS_SPACE capability. The bits in the dirty bitmap are cleared before the ioctl returns, unless -KVM_CAP_MANUAL_DIRTY_LOG_PROTECT is enabled. For more information, +KVM_CAP_MANUAL_DIRTY_LOG_PROTECT2 is enabled. For more information, see the description of the capability. 4.9 KVM_SET_MEMORY_ALIAS @@ -3791,7 +3791,7 @@ to I/O ports. 4.117 KVM_CLEAR_DIRTY_LOG (vm ioctl) -Capability: KVM_CAP_MANUAL_DIRTY_LOG_PROTECT +Capability: KVM_CAP_MANUAL_DIRTY_LOG_PROTECT2 Architectures: x86 Type: vm ioctl Parameters: struct kvm_dirty_log (in) @@ -3824,10 +3824,10 @@ the address space for which you want to return the dirty bitmap. They must be less than the value that KVM_CHECK_EXTENSION returns for the KVM_CAP_MULTI_ADDRESS_SPACE capability. -This ioctl is mostly useful when KVM_CAP_MANUAL_DIRTY_LOG_PROTECT +This ioctl is mostly useful when KVM_CAP_MANUAL_DIRTY_LOG_PROTECT2 is enabled; for more information, see the description of the capability. However, it can always be used as long as KVM_CHECK_EXTENSION confirms -that KVM_CAP_MANUAL_DIRTY_LOG_PROTECT is present. +that KVM_CAP_MANUAL_DIRTY_LOG_PROTECT2 is present. 4.118 KVM_GET_SUPPORTED_HV_CPUID @@ -4780,7 +4780,7 @@ and injected exceptions. * For the new DR6 bits, note that bit 16 is set iff the #DB exception will clear DR6.RTM. -7.18 KVM_CAP_MANUAL_DIRTY_LOG_PROTECT +7.18 KVM_CAP_MANUAL_DIRTY_LOG_PROTECT2 Architectures: all Parameters: args[0] whether feature should be enabled or not @@ -4803,6 +4803,11 @@ while userspace can see false reports of dirty pages. Manual reprotection helps reducing this time, improving guest performance and reducing the number of dirty log false positives. +KVM_CAP_MANUAL_DIRTY_LOG_PROTECT2 was previously available under the name +KVM_CAP_MANUAL_DIRTY_LOG_PROTECT, but the implementation had bugs that make +it hard or impossible to use it correctly. The availability of +KVM_CAP_MANUAL_DIRTY_LOG_PROTECT2 signals that those bugs are fixed. +Userspace should not try to use KVM_CAP_MANUAL_DIRTY_LOG_PROTECT. 8. Other capabilities. ---------------------- diff --git a/include/uapi/linux/kvm.h b/include/uapi/linux/kvm.h index 6d4ea4b6c922..d673734c46cb 100644 --- a/include/uapi/linux/kvm.h +++ b/include/uapi/linux/kvm.h @@ -986,8 +986,9 @@ struct kvm_ppc_resize_hpt { #define KVM_CAP_HYPERV_ENLIGHTENED_VMCS 163 #define KVM_CAP_EXCEPTION_PAYLOAD 164 #define KVM_CAP_ARM_VM_IPA_SIZE 165 -#define KVM_CAP_MANUAL_DIRTY_LOG_PROTECT 166 +#define KVM_CAP_MANUAL_DIRTY_LOG_PROTECT 166 /* Obsolete */ #define KVM_CAP_HYPERV_CPUID 167 +#define KVM_CAP_MANUAL_DIRTY_LOG_PROTECT2 168 #ifdef KVM_CAP_IRQ_ROUTING @@ -1434,7 +1435,7 @@ struct kvm_enc_region { #define KVM_GET_NESTED_STATE _IOWR(KVMIO, 0xbe, struct kvm_nested_state) #define KVM_SET_NESTED_STATE _IOW(KVMIO, 0xbf, struct kvm_nested_state) -/* Available with KVM_CAP_MANUAL_DIRTY_LOG_PROTECT */ +/* Available with KVM_CAP_MANUAL_DIRTY_LOG_PROTECT_2 */ #define KVM_CLEAR_DIRTY_LOG _IOWR(KVMIO, 0xc0, struct kvm_clear_dirty_log) /* Available with KVM_CAP_HYPERV_CPUID */ diff --git a/tools/testing/selftests/kvm/dirty_log_test.c b/tools/testing/selftests/kvm/dirty_log_test.c index 052fb5856df4..a29d1119ccb3 100644 --- a/tools/testing/selftests/kvm/dirty_log_test.c +++ b/tools/testing/selftests/kvm/dirty_log_test.c @@ -311,7 +311,7 @@ static void run_test(enum vm_guest_mode mode, unsigned long iterations, #ifdef USE_CLEAR_DIRTY_LOG struct kvm_enable_cap cap = {}; - cap.cap = KVM_CAP_MANUAL_DIRTY_LOG_PROTECT; + cap.cap = KVM_CAP_MANUAL_DIRTY_LOG_PROTECT2; cap.args[0] = 1; vm_enable_cap(vm, &cap); #endif @@ -427,7 +427,7 @@ int main(int argc, char *argv[]) int opt, i; #ifdef USE_CLEAR_DIRTY_LOG - if (!kvm_check_cap(KVM_CAP_MANUAL_DIRTY_LOG_PROTECT)) { + if (!kvm_check_cap(KVM_CAP_MANUAL_DIRTY_LOG_PROTECT2)) { fprintf(stderr, "KVM_CLEAR_DIRTY_LOG not available, skipping tests\n"); exit(KSFT_SKIP); } diff --git a/virt/kvm/kvm_main.c b/virt/kvm/kvm_main.c index 7883e0ad07fe..f4e02cd8fa43 100644 --- a/virt/kvm/kvm_main.c +++ b/virt/kvm/kvm_main.c @@ -3110,7 +3110,7 @@ static long kvm_vm_ioctl_check_extension_generic(struct kvm *kvm, long arg) case KVM_CAP_CHECK_EXTENSION_VM: case KVM_CAP_ENABLE_CAP_VM: #ifdef CONFIG_KVM_GENERIC_DIRTYLOG_READ_PROTECT - case KVM_CAP_MANUAL_DIRTY_LOG_PROTECT: + case KVM_CAP_MANUAL_DIRTY_LOG_PROTECT2: #endif return 1; #ifdef CONFIG_KVM_MMIO @@ -3148,7 +3148,7 @@ static int kvm_vm_ioctl_enable_cap_generic(struct kvm *kvm, { switch (cap->cap) { #ifdef CONFIG_KVM_GENERIC_DIRTYLOG_READ_PROTECT - case KVM_CAP_MANUAL_DIRTY_LOG_PROTECT: + case KVM_CAP_MANUAL_DIRTY_LOG_PROTECT2: if (cap->flags || (cap->args[0] & ~1)) return -EINVAL; kvm->manual_dirty_log_protect = cap->args[0]; -- cgit v1.2.3 From 56076a538536ace0ac4965771acd7c62fdd4c3dd Mon Sep 17 00:00:00 2001 From: Dmitry Osipenko Date: Sun, 5 May 2019 18:43:20 +0300 Subject: dt-bindings: mfd: max77620: Add compatible for Maxim 77663 Maxim 77663 has a few minor differences in regards to hardware interface and available capabilities by comparing it with 77620 and 20024 models, hence re-use 77620 device-tree binding for the 77663. Signed-off-by: Dmitry Osipenko Reviewed-by: Rob Herring Signed-off-by: Lee Jones --- Documentation/devicetree/bindings/mfd/max77620.txt | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mfd/max77620.txt b/Documentation/devicetree/bindings/mfd/max77620.txt index 9c16d51cc15b..b75283787ba1 100644 --- a/Documentation/devicetree/bindings/mfd/max77620.txt +++ b/Documentation/devicetree/bindings/mfd/max77620.txt @@ -4,7 +4,8 @@ Required properties: ------------------- - compatible: Must be one of "maxim,max77620" - "maxim,max20024". + "maxim,max20024" + "maxim,max77663" - reg: I2C device address. Optional properties: @@ -105,6 +106,7 @@ Optional properties: Here supported time periods by device in microseconds are as follows: MAX77620 supports 40, 80, 160, 320, 640, 1280, 2560 and 5120 microseconds. MAX20024 supports 20, 40, 80, 160, 320, 640, 1280 and 2540 microseconds. +MAX77663 supports 20, 40, 80, 160, 320, 640, 1280 and 2540 microseconds. -maxim,power-ok-control: configure map power ok bit 1: Enables POK(Power OK) to control nRST_IO and GPIO1 -- cgit v1.2.3 From c63217a462fe655eff329abc6a552fba5452c46f Mon Sep 17 00:00:00 2001 From: Dmitry Osipenko Date: Sun, 5 May 2019 18:43:21 +0300 Subject: dt-bindings: mfd: max77620: Add system-power-controller property Document new generic property that designates the PMIC as the system's power controller. Signed-off-by: Dmitry Osipenko Reviewed-by: Rob Herring Signed-off-by: Lee Jones --- Documentation/devicetree/bindings/mfd/max77620.txt | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mfd/max77620.txt b/Documentation/devicetree/bindings/mfd/max77620.txt index b75283787ba1..5a642a51d58e 100644 --- a/Documentation/devicetree/bindings/mfd/max77620.txt +++ b/Documentation/devicetree/bindings/mfd/max77620.txt @@ -18,6 +18,11 @@ Optional properties: IRQ numbers for different interrupt source of MAX77620 are defined at dt-bindings/mfd/max77620.h. +- system-power-controller: Indicates that this PMIC is controlling the + system power, see [1] for more details. + +[1] Documentation/devicetree/bindings/power/power-controller.txt + Optional subnodes and their properties: ======================================= -- cgit v1.2.3 From 468dfca38b1a6fbdccd195d875599cb7c8875cd9 Mon Sep 17 00:00:00 2001 From: Mikulas Patocka Date: Mon, 29 Apr 2019 14:57:24 +0200 Subject: dm integrity: add a bitmap mode Introduce an alternate mode of operation where dm-integrity uses a bitmap instead of a journal. If a bit in the bitmap is 1, the corresponding region's data and integrity tags are not synchronized - if the machine crashes, the unsynchronized regions will be recalculated. The bitmap mode is faster than the journal mode, because we don't have to write the data twice, but it is also less reliable, because if data corruption happens when the machine crashes, it may not be detected. Benchmark results for an SSD connected to a SATA300 port, when doing large linear writes with dd: buffered I/O: raw device throughput - 245MB/s dm-integrity with journaling - 120MB/s dm-integrity with bitmap - 238MB/s direct I/O with 1MB block size: raw device throughput - 248MB/s dm-integrity with journaling - 123MB/s dm-integrity with bitmap - 223MB/s For more info see dm-integrity in Documentation/device-mapper/ Signed-off-by: Mikulas Patocka Signed-off-by: Mike Snitzer --- Documentation/device-mapper/dm-integrity.txt | 22 ++ drivers/md/dm-integrity.c | 536 +++++++++++++++++++++++++-- 2 files changed, 525 insertions(+), 33 deletions(-) (limited to 'Documentation') diff --git a/Documentation/device-mapper/dm-integrity.txt b/Documentation/device-mapper/dm-integrity.txt index 7dc9180cdeac..d63d78ffeb73 100644 --- a/Documentation/device-mapper/dm-integrity.txt +++ b/Documentation/device-mapper/dm-integrity.txt @@ -21,6 +21,13 @@ mode it calculates and verifies the integrity tag internally. In this mode, the dm-integrity target can be used to detect silent data corruption on the disk or in the I/O path. +There's an alternate mode of operation where dm-integrity uses bitmap +instead of a journal. If a bit in the bitmap is 1, the corresponding +region's data and integrity tags are not synchronized - if the machine +crashes, the unsynchronized regions will be recalculated. The bitmap mode +is faster than the journal mode, because we don't have to write the data +twice, but it is also less reliable, because if data corruption happens +when the machine crashes, it may not be detected. When loading the target for the first time, the kernel driver will format the device. But it will only format the device if the superblock contains @@ -59,6 +66,10 @@ Target arguments: either both data and tag or none of them are written. The journaled mode degrades write throughput twice because the data have to be written twice. + B - bitmap mode - data and metadata are written without any + synchronization, the driver maintains a bitmap of dirty + regions where data and metadata don't match. This mode can + only be used with internal hash. R - recovery mode - in this mode, journal is not replayed, checksums are not checked and writes to the device are not allowed. This mode is useful for data recovery if the @@ -150,6 +161,15 @@ block_size:number Supported values are 512, 1024, 2048 and 4096 bytes. If not specified the default block size is 512 bytes. +sectors_per_bit:number + In the bitmap mode, this parameter specifies the number of + 512-byte sectors that corresponds to one bitmap bit. + +bitmap_flush_interval:number + The bitmap flush interval in milliseconds. The metadata buffers + are synchronized when this interval expires. + + The journal mode (D/J), buffer_sectors, journal_watermark, commit_time can be changed when reloading the target (load an inactive table and swap the tables with suspend and resume). The other arguments should not be changed @@ -174,6 +194,8 @@ The layout of the formatted block device: * flags SB_FLAG_HAVE_JOURNAL_MAC - a flag is set if journal_mac is used SB_FLAG_RECALCULATING - recalculating is in progress + SB_FLAG_DIRTY_BITMAP - journal area contains the bitmap of dirty + blocks * log2(sectors per block) * a position where recalculating finished * journal diff --git a/drivers/md/dm-integrity.c b/drivers/md/dm-integrity.c index fb8935d80842..54b3fe1403a8 100644 --- a/drivers/md/dm-integrity.c +++ b/drivers/md/dm-integrity.c @@ -24,6 +24,7 @@ #define DEFAULT_INTERLEAVE_SECTORS 32768 #define DEFAULT_JOURNAL_SIZE_FACTOR 7 +#define DEFAULT_SECTORS_PER_BITMAP_BIT 32768 #define DEFAULT_BUFFER_SECTORS 128 #define DEFAULT_JOURNAL_WATERMARK 50 #define DEFAULT_SYNC_MSEC 10000 @@ -33,6 +34,8 @@ #define METADATA_WORKQUEUE_MAX_ACTIVE 16 #define RECALC_SECTORS 8192 #define RECALC_WRITE_SUPER 16 +#define BITMAP_BLOCK_SIZE 4096 /* don't change it */ +#define BITMAP_FLUSH_INTERVAL (10 * HZ) /* * Warning - DEBUG_PRINT prints security-sensitive data to the log, @@ -48,6 +51,7 @@ #define SB_MAGIC "integrt" #define SB_VERSION_1 1 #define SB_VERSION_2 2 +#define SB_VERSION_3 3 #define SB_SECTORS 8 #define MAX_SECTORS_PER_BLOCK 8 @@ -60,12 +64,14 @@ struct superblock { __u64 provided_data_sectors; /* userspace uses this value */ __u32 flags; __u8 log2_sectors_per_block; - __u8 pad[3]; + __u8 log2_blocks_per_bitmap_bit; + __u8 pad[2]; __u64 recalc_sector; }; #define SB_FLAG_HAVE_JOURNAL_MAC 0x1 #define SB_FLAG_RECALCULATING 0x2 +#define SB_FLAG_DIRTY_BITMAP 0x4 #define JOURNAL_ENTRY_ROUNDUP 8 @@ -155,9 +161,16 @@ struct dm_integrity_c { struct workqueue_struct *metadata_wq; struct superblock *sb; unsigned journal_pages; + unsigned n_bitmap_blocks; + struct page_list *journal; struct page_list *journal_io; struct page_list *journal_xor; + struct page_list *recalc_bitmap; + struct page_list *may_write_bitmap; + struct bitmap_block_status *bbs; + unsigned bitmap_flush_interval; + struct delayed_work bitmap_flush_work; struct crypto_skcipher *journal_crypt; struct scatterlist **journal_scatterlist; @@ -184,6 +197,7 @@ struct dm_integrity_c { __s8 log2_metadata_run; __u8 log2_buffer_sectors; __u8 sectors_per_block; + __u8 log2_blocks_per_bitmap_bit; unsigned char mode; int suspending; @@ -236,6 +250,7 @@ struct dm_integrity_c { bool journal_uptodate; bool just_formatted; + bool recalculate_flag; struct alg_spec internal_hash_alg; struct alg_spec journal_crypt_alg; @@ -292,6 +307,16 @@ struct journal_io { struct journal_completion *comp; }; +struct bitmap_block_status { + struct work_struct work; + struct dm_integrity_c *ic; + unsigned idx; + unsigned long *bitmap; + struct bio_list bio_queue; + spinlock_t bio_queue_lock; + +}; + static struct kmem_cache *journal_io_cache; #define JOURNAL_IO_MEMPOOL 32 @@ -427,7 +452,9 @@ static void wraparound_section(struct dm_integrity_c *ic, unsigned *sec_ptr) static void sb_set_version(struct dm_integrity_c *ic) { - if (ic->meta_dev || ic->sb->flags & cpu_to_le32(SB_FLAG_RECALCULATING)) + if (ic->mode == 'B' || ic->sb->flags & cpu_to_le32(SB_FLAG_DIRTY_BITMAP)) + ic->sb->version = SB_VERSION_3; + else if (ic->meta_dev || ic->sb->flags & cpu_to_le32(SB_FLAG_RECALCULATING)) ic->sb->version = SB_VERSION_2; else ic->sb->version = SB_VERSION_1; @@ -451,6 +478,135 @@ static int sync_rw_sb(struct dm_integrity_c *ic, int op, int op_flags) return dm_io(&io_req, 1, &io_loc, NULL); } +#define BITMAP_OP_TEST_ALL_SET 0 +#define BITMAP_OP_TEST_ALL_CLEAR 1 +#define BITMAP_OP_SET 2 +#define BITMAP_OP_CLEAR 3 + +static bool block_bitmap_op(struct dm_integrity_c *ic, struct page_list *bitmap, sector_t sector, sector_t n_sectors, int mode) +{ + unsigned long bit, end_bit, this_end_bit, page, end_page; + unsigned long *data; + + if (unlikely(((sector | n_sectors) & ((1 << ic->sb->log2_sectors_per_block) - 1)) != 0)) { + DMCRIT("invalid bitmap access (%llx,%llx,%d,%d,%d)\n", + (unsigned long long)sector, + (unsigned long long)n_sectors, + ic->sb->log2_sectors_per_block, + ic->log2_blocks_per_bitmap_bit, + mode); + BUG(); + } + + if (unlikely(!n_sectors)) + return true; + + bit = sector >> (ic->sb->log2_sectors_per_block + ic->log2_blocks_per_bitmap_bit); + end_bit = (sector + n_sectors - 1) >> (ic->sb->log2_sectors_per_block + ic->log2_blocks_per_bitmap_bit); + + page = bit / (PAGE_SIZE * 8); + bit %= PAGE_SIZE * 8; + + end_page = end_bit / (PAGE_SIZE * 8); + end_bit %= PAGE_SIZE * 8; + +repeat: + if (page < end_page) { + this_end_bit = PAGE_SIZE * 8 - 1; + } else { + this_end_bit = end_bit; + } + + data = lowmem_page_address(bitmap[page].page); + + if (mode == BITMAP_OP_TEST_ALL_SET) { + while (bit <= this_end_bit) { + if (!(bit % BITS_PER_LONG) && this_end_bit >= bit + BITS_PER_LONG - 1) { + do { + if (data[bit / BITS_PER_LONG] != -1) + return false; + bit += BITS_PER_LONG; + } while (this_end_bit >= bit + BITS_PER_LONG - 1); + continue; + } + if (!test_bit(bit, data)) + return false; + bit++; + } + } else if (mode == BITMAP_OP_TEST_ALL_CLEAR) { + while (bit <= this_end_bit) { + if (!(bit % BITS_PER_LONG) && this_end_bit >= bit + BITS_PER_LONG - 1) { + do { + if (data[bit / BITS_PER_LONG] != 0) + return false; + bit += BITS_PER_LONG; + } while (this_end_bit >= bit + BITS_PER_LONG - 1); + continue; + } + if (test_bit(bit, data)) + return false; + bit++; + } + } else if (mode == BITMAP_OP_SET) { + while (bit <= this_end_bit) { + if (!(bit % BITS_PER_LONG) && this_end_bit >= bit + BITS_PER_LONG - 1) { + do { + data[bit / BITS_PER_LONG] = -1; + bit += BITS_PER_LONG; + } while (this_end_bit >= bit + BITS_PER_LONG - 1); + continue; + } + __set_bit(bit, data); + bit++; + } + } else if (mode == BITMAP_OP_CLEAR) { + if (!bit && this_end_bit == PAGE_SIZE * 8 - 1) + clear_page(data); + else while (bit <= this_end_bit) { + if (!(bit % BITS_PER_LONG) && this_end_bit >= bit + BITS_PER_LONG - 1) { + do { + data[bit / BITS_PER_LONG] = 0; + bit += BITS_PER_LONG; + } while (this_end_bit >= bit + BITS_PER_LONG - 1); + continue; + } + __clear_bit(bit, data); + bit++; + } + } else { + BUG(); + } + + if (unlikely(page < end_page)) { + bit = 0; + page++; + goto repeat; + } + + return true; +} + +static void block_bitmap_copy(struct dm_integrity_c *ic, struct page_list *dst, struct page_list *src) +{ + unsigned n_bitmap_pages = DIV_ROUND_UP(ic->n_bitmap_blocks, PAGE_SIZE / BITMAP_BLOCK_SIZE); + unsigned i; + + for (i = 0; i < n_bitmap_pages; i++) { + unsigned long *dst_data = lowmem_page_address(dst[i].page); + unsigned long *src_data = lowmem_page_address(src[i].page); + copy_page(dst_data, src_data); + } +} + +static struct bitmap_block_status *sector_to_bitmap_block(struct dm_integrity_c *ic, sector_t sector) +{ + unsigned bit = sector >> (ic->sb->log2_sectors_per_block + ic->log2_blocks_per_bitmap_bit); + unsigned bitmap_block = bit / (BITMAP_BLOCK_SIZE * 8); + + BUG_ON(bitmap_block >= ic->n_bitmap_blocks); + return &ic->bbs[bitmap_block]; +} + static void access_journal_check(struct dm_integrity_c *ic, unsigned section, unsigned offset, bool e, const char *function) { @@ -1784,6 +1940,20 @@ offload_to_thread: goto journal_read_write; } + if (ic->mode == 'B' && dio->write) { + if (!block_bitmap_op(ic, ic->may_write_bitmap, dio->range.logical_sector, dio->range.n_sectors, BITMAP_OP_TEST_ALL_SET)) { + struct bitmap_block_status *bbs = sector_to_bitmap_block(ic, dio->range.logical_sector); + + spin_lock(&bbs->bio_queue_lock); + bio_list_add(&bbs->bio_queue, bio); + spin_unlock(&bbs->bio_queue_lock); + + queue_work(ic->writer_wq, &bbs->work); + + return; + } + } + dio->in_flight = (atomic_t)ATOMIC_INIT(2); if (need_sync_io) { @@ -1810,10 +1980,14 @@ offload_to_thread: if (need_sync_io) { wait_for_completion_io(&read_comp); - if (unlikely(ic->recalc_wq != NULL) && - ic->sb->flags & cpu_to_le32(SB_FLAG_RECALCULATING) && + if (ic->sb->flags & cpu_to_le32(SB_FLAG_RECALCULATING) && dio->range.logical_sector + dio->range.n_sectors > le64_to_cpu(ic->sb->recalc_sector)) goto skip_check; + if (ic->mode == 'B') { + if (!block_bitmap_op(ic, ic->recalc_bitmap, dio->range.logical_sector, dio->range.n_sectors, BITMAP_OP_TEST_ALL_CLEAR)) + goto skip_check; + } + if (likely(!bio->bi_status)) integrity_metadata(&dio->work); else @@ -1851,8 +2025,22 @@ static void pad_uncommitted(struct dm_integrity_c *ic) wraparound_section(ic, &ic->free_section); ic->n_uncommitted_sections++; } - WARN_ON(ic->journal_sections * ic->journal_section_entries != - (ic->n_uncommitted_sections + ic->n_committed_sections) * ic->journal_section_entries + ic->free_sectors); + if (WARN_ON(ic->journal_sections * ic->journal_section_entries != + (ic->n_uncommitted_sections + ic->n_committed_sections) * ic->journal_section_entries + ic->free_sectors)) { + printk(KERN_CRIT "dm-integrity: " + "journal_sections %u, " + "journal_section_entries %u, " + "n_uncommitted_sections %u, " + "n_committed_sections %u, " + "journal_section_entries %u, " + "free_sectors %u\n", + ic->journal_sections, + ic->journal_section_entries, + ic->n_uncommitted_sections, + ic->n_committed_sections, + ic->journal_section_entries, + ic->free_sectors); + } } static void integrity_commit(struct work_struct *w) @@ -2139,11 +2327,14 @@ static void integrity_recalc(struct work_struct *w) sector_t area, offset; sector_t metadata_block; unsigned metadata_offset; + sector_t logical_sector, n_sectors; __u8 *t; unsigned i; int r; unsigned super_counter = 0; + DEBUG_print("start recalculation... (position %llx)\n", le64_to_cpu(ic->sb->recalc_sector)); + spin_lock_irq(&ic->endio_wait.lock); next_chunk: @@ -2152,8 +2343,13 @@ next_chunk: goto unlock_ret; range.logical_sector = le64_to_cpu(ic->sb->recalc_sector); - if (unlikely(range.logical_sector >= ic->provided_data_sectors)) + if (unlikely(range.logical_sector >= ic->provided_data_sectors)) { + if (ic->mode == 'B') { + DEBUG_print("queue_delayed_work: bitmap_flush_work\n"); + queue_delayed_work(ic->commit_wq, &ic->bitmap_flush_work, 0); + } goto unlock_ret; + } get_area_and_offset(ic, range.logical_sector, &area, &offset); range.n_sectors = min((sector_t)RECALC_SECTORS, ic->provided_data_sectors - range.logical_sector); @@ -2161,11 +2357,33 @@ next_chunk: range.n_sectors = min(range.n_sectors, ((sector_t)1U << ic->sb->log2_interleave_sectors) - (unsigned)offset); add_new_range_and_wait(ic, &range); - spin_unlock_irq(&ic->endio_wait.lock); + logical_sector = range.logical_sector; + n_sectors = range.n_sectors; + + if (ic->mode == 'B') { + if (block_bitmap_op(ic, ic->recalc_bitmap, logical_sector, n_sectors, BITMAP_OP_TEST_ALL_CLEAR)) { + goto advance_and_next; + } + while (block_bitmap_op(ic, ic->recalc_bitmap, logical_sector, ic->sectors_per_block, BITMAP_OP_TEST_ALL_CLEAR)) { + logical_sector += ic->sectors_per_block; + n_sectors -= ic->sectors_per_block; + cond_resched(); + } + while (block_bitmap_op(ic, ic->recalc_bitmap, logical_sector + n_sectors - ic->sectors_per_block, ic->sectors_per_block, BITMAP_OP_TEST_ALL_CLEAR)) { + n_sectors -= ic->sectors_per_block; + cond_resched(); + } + get_area_and_offset(ic, logical_sector, &area, &offset); + } + + DEBUG_print("recalculating: %lx, %lx\n", logical_sector, n_sectors); if (unlikely(++super_counter == RECALC_WRITE_SUPER)) { recalc_write_super(ic); + if (ic->mode == 'B') { + queue_delayed_work(ic->commit_wq, &ic->bitmap_flush_work, ic->bitmap_flush_interval); + } super_counter = 0; } @@ -2180,7 +2398,7 @@ next_chunk: io_req.client = ic->io; io_loc.bdev = ic->dev->bdev; io_loc.sector = get_data_sector(ic, area, offset); - io_loc.count = range.n_sectors; + io_loc.count = n_sectors; r = dm_io(&io_req, 1, &io_loc, NULL); if (unlikely(r)) { @@ -2189,8 +2407,8 @@ next_chunk: } t = ic->recalc_tags; - for (i = 0; i < range.n_sectors; i += ic->sectors_per_block) { - integrity_sector_checksum(ic, range.logical_sector + i, ic->recalc_buffer + (i << SECTOR_SHIFT), t); + for (i = 0; i < n_sectors; i += ic->sectors_per_block) { + integrity_sector_checksum(ic, logical_sector + i, ic->recalc_buffer + (i << SECTOR_SHIFT), t); t += ic->tag_size; } @@ -2202,6 +2420,9 @@ next_chunk: goto err; } +advance_and_next: + cond_resched(); + spin_lock_irq(&ic->endio_wait.lock); remove_range_unlocked(ic, &range); ic->sb->recalc_sector = cpu_to_le64(range.logical_sector + range.n_sectors); @@ -2217,6 +2438,89 @@ unlock_ret: recalc_write_super(ic); } +static void bitmap_block_work(struct work_struct *w) +{ + struct bitmap_block_status *bbs = container_of(w, struct bitmap_block_status, work); + struct dm_integrity_c *ic = bbs->ic; + struct bio *bio; + struct bio_list bio_queue; + struct bio_list waiting; + + bio_list_init(&waiting); + + spin_lock(&bbs->bio_queue_lock); + bio_queue = bbs->bio_queue; + bio_list_init(&bbs->bio_queue); + spin_unlock(&bbs->bio_queue_lock); + + while ((bio = bio_list_pop(&bio_queue))) { + struct dm_integrity_io *dio; + + dio = dm_per_bio_data(bio, sizeof(struct dm_integrity_io)); + + if (block_bitmap_op(ic, ic->may_write_bitmap, dio->range.logical_sector, dio->range.n_sectors, BITMAP_OP_TEST_ALL_SET)) { + remove_range(ic, &dio->range); + INIT_WORK(&dio->work, integrity_bio_wait); + queue_work(ic->wait_wq, &dio->work); + } else { + block_bitmap_op(ic, ic->journal, dio->range.logical_sector, dio->range.n_sectors, BITMAP_OP_SET); + bio_list_add(&waiting, bio); + } + } + + if (bio_list_empty(&waiting)) + return; + + rw_journal_sectors(ic, REQ_OP_WRITE, REQ_FUA | REQ_SYNC, bbs->idx * (BITMAP_BLOCK_SIZE >> SECTOR_SHIFT), BITMAP_BLOCK_SIZE >> SECTOR_SHIFT, NULL); + + while ((bio = bio_list_pop(&waiting))) { + struct dm_integrity_io *dio = dm_per_bio_data(bio, sizeof(struct dm_integrity_io)); + + block_bitmap_op(ic, ic->may_write_bitmap, dio->range.logical_sector, dio->range.n_sectors, BITMAP_OP_SET); + + remove_range(ic, &dio->range); + INIT_WORK(&dio->work, integrity_bio_wait); + queue_work(ic->wait_wq, &dio->work); + } + + queue_delayed_work(ic->commit_wq, &ic->bitmap_flush_work, ic->bitmap_flush_interval); +} + +static void bitmap_flush_work(struct work_struct *work) +{ + struct dm_integrity_c *ic = container_of(work, struct dm_integrity_c, bitmap_flush_work.work); + struct dm_integrity_range range; + unsigned long limit; + + dm_integrity_flush_buffers(ic); + + range.logical_sector = 0; + range.n_sectors = ic->provided_data_sectors; + + spin_lock_irq(&ic->endio_wait.lock); + add_new_range_and_wait(ic, &range); + spin_unlock_irq(&ic->endio_wait.lock); + + dm_integrity_flush_buffers(ic); + if (ic->meta_dev) + blkdev_issue_flush(ic->dev->bdev, GFP_NOIO, NULL); + + limit = ic->provided_data_sectors; + if (ic->sb->flags & cpu_to_le32(SB_FLAG_RECALCULATING)) { + limit = le64_to_cpu(ic->sb->recalc_sector) + >> (ic->sb->log2_sectors_per_block + ic->log2_blocks_per_bitmap_bit) + << (ic->sb->log2_sectors_per_block + ic->log2_blocks_per_bitmap_bit); + } + DEBUG_print("zeroing journal\n"); + block_bitmap_op(ic, ic->journal, 0, limit, BITMAP_OP_CLEAR); + block_bitmap_op(ic, ic->may_write_bitmap, 0, limit, BITMAP_OP_CLEAR); + + rw_journal_sectors(ic, REQ_OP_WRITE, REQ_FUA | REQ_SYNC, 0, ic->n_bitmap_blocks * (BITMAP_BLOCK_SIZE >> SECTOR_SHIFT), NULL); + + remove_range(ic, &range); +} + + static void init_journal(struct dm_integrity_c *ic, unsigned start_section, unsigned n_sections, unsigned char commit_seq) { @@ -2416,6 +2720,7 @@ clear_journal: static void dm_integrity_postsuspend(struct dm_target *ti) { struct dm_integrity_c *ic = (struct dm_integrity_c *)ti->private; + int r; del_timer_sync(&ic->autocommit_timer); @@ -2424,6 +2729,9 @@ static void dm_integrity_postsuspend(struct dm_target *ti) if (ic->recalc_wq) drain_workqueue(ic->recalc_wq); + if (ic->mode == 'B') + cancel_delayed_work_sync(&ic->bitmap_flush_work); + queue_work(ic->commit_wq, &ic->commit_work); drain_workqueue(ic->commit_wq); @@ -2434,6 +2742,17 @@ static void dm_integrity_postsuspend(struct dm_target *ti) dm_integrity_flush_buffers(ic); } + if (ic->mode == 'B') { + dm_integrity_flush_buffers(ic); +#if 1 + init_journal(ic, 0, ic->journal_sections, 0); + ic->sb->flags &= ~cpu_to_le32(SB_FLAG_DIRTY_BITMAP); + r = sync_rw_sb(ic, REQ_OP_WRITE, REQ_FUA); + if (unlikely(r)) + dm_integrity_io_error(ic, "writing superblock", r); +#endif + } + WRITE_ONCE(ic->suspending, 0); BUG_ON(!RB_EMPTY_ROOT(&ic->in_progress)); @@ -2444,11 +2763,65 @@ static void dm_integrity_postsuspend(struct dm_target *ti) static void dm_integrity_resume(struct dm_target *ti) { struct dm_integrity_c *ic = (struct dm_integrity_c *)ti->private; + int r; + DEBUG_print("resume\n"); + + if (ic->sb->flags & cpu_to_le32(SB_FLAG_DIRTY_BITMAP)) { + DEBUG_print("resume dirty_bitmap\n"); + rw_journal_sectors(ic, REQ_OP_READ, 0, 0, ic->n_bitmap_blocks * (BITMAP_BLOCK_SIZE >> SECTOR_SHIFT), NULL); + if (ic->mode == 'B') { + if (ic->sb->log2_blocks_per_bitmap_bit == ic->log2_blocks_per_bitmap_bit) { + block_bitmap_copy(ic, ic->recalc_bitmap, ic->journal); + block_bitmap_copy(ic, ic->may_write_bitmap, ic->journal); + if (!block_bitmap_op(ic, ic->journal, 0, ic->provided_data_sectors, BITMAP_OP_TEST_ALL_CLEAR)) { + ic->sb->flags |= cpu_to_le32(SB_FLAG_RECALCULATING); + ic->sb->recalc_sector = cpu_to_le64(0); + } + } else { + DEBUG_print("non-matching blocks_per_bitmap_bit: %u, %u\n", ic->sb->log2_blocks_per_bitmap_bit, ic->log2_blocks_per_bitmap_bit); + ic->sb->log2_blocks_per_bitmap_bit = ic->log2_blocks_per_bitmap_bit; + block_bitmap_op(ic, ic->recalc_bitmap, 0, ic->provided_data_sectors, BITMAP_OP_SET); + block_bitmap_op(ic, ic->may_write_bitmap, 0, ic->provided_data_sectors, BITMAP_OP_SET); + block_bitmap_op(ic, ic->journal, 0, ic->provided_data_sectors, BITMAP_OP_SET); + rw_journal_sectors(ic, REQ_OP_WRITE, REQ_FUA | REQ_SYNC, 0, ic->n_bitmap_blocks * (BITMAP_BLOCK_SIZE >> SECTOR_SHIFT), NULL); + ic->sb->flags |= cpu_to_le32(SB_FLAG_RECALCULATING); + ic->sb->recalc_sector = cpu_to_le64(0); + } + } else { + if (!(ic->sb->log2_blocks_per_bitmap_bit == ic->log2_blocks_per_bitmap_bit && + block_bitmap_op(ic, ic->journal, 0, ic->provided_data_sectors, BITMAP_OP_TEST_ALL_CLEAR))) { + ic->sb->flags |= cpu_to_le32(SB_FLAG_RECALCULATING); + ic->sb->recalc_sector = cpu_to_le64(0); + } + init_journal(ic, 0, ic->journal_sections, 0); + replay_journal(ic); + ic->sb->flags &= ~cpu_to_le32(SB_FLAG_DIRTY_BITMAP); + } + r = sync_rw_sb(ic, REQ_OP_WRITE, REQ_FUA); + if (unlikely(r)) + dm_integrity_io_error(ic, "writing superblock", r); + } else { + replay_journal(ic); + if (ic->mode == 'B') { + int mode; + ic->sb->flags |= cpu_to_le32(SB_FLAG_DIRTY_BITMAP); + ic->sb->log2_blocks_per_bitmap_bit = ic->log2_blocks_per_bitmap_bit; + r = sync_rw_sb(ic, REQ_OP_WRITE, REQ_FUA); + if (unlikely(r)) + dm_integrity_io_error(ic, "writing superblock", r); + + mode = ic->recalculate_flag ? BITMAP_OP_SET : BITMAP_OP_CLEAR; + block_bitmap_op(ic, ic->journal, 0, ic->provided_data_sectors, mode); + block_bitmap_op(ic, ic->recalc_bitmap, 0, ic->provided_data_sectors, mode); + block_bitmap_op(ic, ic->may_write_bitmap, 0, ic->provided_data_sectors, mode); + rw_journal_sectors(ic, REQ_OP_WRITE, REQ_FUA | REQ_SYNC, 0, ic->n_bitmap_blocks * (BITMAP_BLOCK_SIZE >> SECTOR_SHIFT), NULL); + } + } - replay_journal(ic); - - if (ic->recalc_wq && ic->sb->flags & cpu_to_le32(SB_FLAG_RECALCULATING)) { + DEBUG_print("testing recalc: %x\n", ic->sb->flags); + if (ic->sb->flags & cpu_to_le32(SB_FLAG_RECALCULATING)) { __u64 recalc_pos = le64_to_cpu(ic->sb->recalc_sector); + DEBUG_print("recalc pos: %lx / %lx\n", (long)recalc_pos, ic->provided_data_sectors); if (recalc_pos < ic->provided_data_sectors) { queue_work(ic->recalc_wq, &ic->recalc_work); } else if (recalc_pos > ic->provided_data_sectors) { @@ -2486,6 +2859,8 @@ static void dm_integrity_status(struct dm_target *ti, status_type_t type, arg_count += !!(ic->sb->flags & cpu_to_le32(SB_FLAG_RECALCULATING)); arg_count += ic->mode == 'J'; arg_count += ic->mode == 'J'; + arg_count += ic->mode == 'B'; + arg_count += ic->mode == 'B'; arg_count += !!ic->internal_hash_alg.alg_string; arg_count += !!ic->journal_crypt_alg.alg_string; arg_count += !!ic->journal_mac_alg.alg_string; @@ -2495,7 +2870,7 @@ static void dm_integrity_status(struct dm_target *ti, status_type_t type, DMEMIT(" meta_device:%s", ic->meta_dev->name); if (ic->sectors_per_block != 1) DMEMIT(" block_size:%u", ic->sectors_per_block << SECTOR_SHIFT); - if (ic->sb->flags & cpu_to_le32(SB_FLAG_RECALCULATING)) + if (ic->recalculate_flag) DMEMIT(" recalculate"); DMEMIT(" journal_sectors:%u", ic->initial_sectors - SB_SECTORS); DMEMIT(" interleave_sectors:%u", 1U << ic->sb->log2_interleave_sectors); @@ -2504,6 +2879,10 @@ static void dm_integrity_status(struct dm_target *ti, status_type_t type, DMEMIT(" journal_watermark:%u", (unsigned)watermark_percentage); DMEMIT(" commit_time:%u", ic->autocommit_msec); } + if (ic->mode == 'B') { + DMEMIT(" sectors_per_bit:%llu", (unsigned long long)ic->sectors_per_block << ic->log2_blocks_per_bitmap_bit); + DMEMIT(" bitmap_flush_interval:%u", jiffies_to_msecs(ic->bitmap_flush_interval)); + } #define EMIT_ALG(a, n) \ do { \ @@ -3085,7 +3464,7 @@ bad: * device * offset from the start of the device * tag size - * D - direct writes, J - journal writes, R - recovery mode + * D - direct writes, J - journal writes, B - bitmap mode, R - recovery mode * number of optional arguments * optional arguments: * journal_sectors @@ -3095,6 +3474,8 @@ bad: * commit_time * meta_device * block_size + * sectors_per_bit + * bitmap_flush_interval * internal_hash * journal_crypt * journal_mac @@ -3111,10 +3492,13 @@ static int dm_integrity_ctr(struct dm_target *ti, unsigned argc, char **argv) {0, 9, "Invalid number of feature args"}, }; unsigned journal_sectors, interleave_sectors, buffer_sectors, journal_watermark, sync_msec; - bool recalculate; bool should_write_sb; __u64 threshold; unsigned long long start; + __s8 log2_sectors_per_bitmap_bit = -1; + __s8 log2_blocks_per_bitmap_bit; + __u64 bits_in_journal; + __u64 n_bitmap_bits; #define DIRECT_ARGUMENTS 4 @@ -3138,6 +3522,7 @@ static int dm_integrity_ctr(struct dm_target *ti, unsigned argc, char **argv) init_waitqueue_head(&ic->copy_to_journal_wait); init_completion(&ic->crypto_backoff); atomic64_set(&ic->number_of_mismatches, 0); + ic->bitmap_flush_interval = BITMAP_FLUSH_INTERVAL; r = dm_get_device(ti, argv[0], dm_table_get_mode(ti->table), &ic->dev); if (r) { @@ -3160,10 +3545,10 @@ static int dm_integrity_ctr(struct dm_target *ti, unsigned argc, char **argv) } } - if (!strcmp(argv[3], "J") || !strcmp(argv[3], "D") || !strcmp(argv[3], "R")) + if (!strcmp(argv[3], "J") || !strcmp(argv[3], "B") || !strcmp(argv[3], "D") || !strcmp(argv[3], "R")) { ic->mode = argv[3][0]; - else { - ti->error = "Invalid mode (expecting J, D, R)"; + } else { + ti->error = "Invalid mode (expecting J, B, D, R)"; r = -EINVAL; goto bad; } @@ -3173,7 +3558,6 @@ static int dm_integrity_ctr(struct dm_target *ti, unsigned argc, char **argv) buffer_sectors = DEFAULT_BUFFER_SECTORS; journal_watermark = DEFAULT_JOURNAL_WATERMARK; sync_msec = DEFAULT_SYNC_MSEC; - recalculate = false; ic->sectors_per_block = 1; as.argc = argc - DIRECT_ARGUMENTS; @@ -3185,6 +3569,7 @@ static int dm_integrity_ctr(struct dm_target *ti, unsigned argc, char **argv) while (extra_args--) { const char *opt_string; unsigned val; + unsigned long long llval; opt_string = dm_shift_arg(&as); if (!opt_string) { r = -EINVAL; @@ -3220,6 +3605,14 @@ static int dm_integrity_ctr(struct dm_target *ti, unsigned argc, char **argv) goto bad; } ic->sectors_per_block = val >> SECTOR_SHIFT; + } else if (sscanf(opt_string, "sectors_per_bit:%llu%c", &llval, &dummy) == 1) { + log2_sectors_per_bitmap_bit = !llval ? 0 : __ilog2_u64(llval); + } else if (sscanf(opt_string, "bitmap_flush_interval:%u%c", &val, &dummy) == 1) { + if (val >= (uint64_t)UINT_MAX * 1000 / HZ) { + r = -EINVAL; + ti->error = "Invalid bitmap_flush_interval argument"; + } + ic->bitmap_flush_interval = msecs_to_jiffies(val); } else if (!strncmp(opt_string, "internal_hash:", strlen("internal_hash:"))) { r = get_alg_and_key(opt_string, &ic->internal_hash_alg, &ti->error, "Invalid internal_hash argument"); @@ -3236,7 +3629,7 @@ static int dm_integrity_ctr(struct dm_target *ti, unsigned argc, char **argv) if (r) goto bad; } else if (!strcmp(opt_string, "recalculate")) { - recalculate = true; + ic->recalculate_flag = true; } else { r = -EINVAL; ti->error = "Invalid argument"; @@ -3287,6 +3680,12 @@ static int dm_integrity_ctr(struct dm_target *ti, unsigned argc, char **argv) else ic->log2_tag_size = -1; + if (ic->mode == 'B' && !ic->internal_hash) { + r = -EINVAL; + ti->error = "Bitmap mode can be only used with internal hash"; + goto bad; + } + ic->autocommit_jiffies = msecs_to_jiffies(sync_msec); ic->autocommit_msec = sync_msec; timer_setup(&ic->autocommit_timer, autocommit_fn, 0); @@ -3332,7 +3731,7 @@ static int dm_integrity_ctr(struct dm_target *ti, unsigned argc, char **argv) } INIT_WORK(&ic->commit_work, integrity_commit); - if (ic->mode == 'J') { + if (ic->mode == 'J' || ic->mode == 'B') { ic->writer_wq = alloc_workqueue("dm-integrity-writer", WQ_MEM_RECLAIM, 1); if (!ic->writer_wq) { ti->error = "Cannot allocate workqueue"; @@ -3373,7 +3772,7 @@ static int dm_integrity_ctr(struct dm_target *ti, unsigned argc, char **argv) should_write_sb = true; } - if (!ic->sb->version || ic->sb->version > SB_VERSION_2) { + if (!ic->sb->version || ic->sb->version > SB_VERSION_3) { r = -EINVAL; ti->error = "Unknown version"; goto bad; @@ -3433,6 +3832,27 @@ try_smaller_buffer: ti->error = "The device is too small"; goto bad; } + + if (log2_sectors_per_bitmap_bit < 0) + log2_sectors_per_bitmap_bit = __fls(DEFAULT_SECTORS_PER_BITMAP_BIT); + if (log2_sectors_per_bitmap_bit < ic->sb->log2_sectors_per_block) + log2_sectors_per_bitmap_bit = ic->sb->log2_sectors_per_block; + + bits_in_journal = ((__u64)ic->journal_section_sectors * ic->journal_sections) << (SECTOR_SHIFT + 3); + if (bits_in_journal > UINT_MAX) + bits_in_journal = UINT_MAX; + while (bits_in_journal < (ic->provided_data_sectors + ((sector_t)1 << log2_sectors_per_bitmap_bit) - 1) >> log2_sectors_per_bitmap_bit) + log2_sectors_per_bitmap_bit++; + + log2_blocks_per_bitmap_bit = log2_sectors_per_bitmap_bit - ic->sb->log2_sectors_per_block; + ic->log2_blocks_per_bitmap_bit = log2_blocks_per_bitmap_bit; + if (should_write_sb) { + ic->sb->log2_blocks_per_bitmap_bit = log2_blocks_per_bitmap_bit; + } + n_bitmap_bits = ((ic->provided_data_sectors >> ic->sb->log2_sectors_per_block) + + (((sector_t)1 << log2_blocks_per_bitmap_bit) - 1)) >> log2_blocks_per_bitmap_bit; + ic->n_bitmap_blocks = DIV_ROUND_UP(n_bitmap_bits, BITMAP_BLOCK_SIZE * 8); + if (!ic->meta_dev) ic->log2_buffer_sectors = min(ic->log2_buffer_sectors, (__u8)__ffs(ic->metadata_run)); @@ -3457,25 +3877,21 @@ try_smaller_buffer: DEBUG_print(" journal_sections %u\n", (unsigned)le32_to_cpu(ic->sb->journal_sections)); DEBUG_print(" journal_entries %u\n", ic->journal_entries); DEBUG_print(" log2_interleave_sectors %d\n", ic->sb->log2_interleave_sectors); - DEBUG_print(" data_device_sectors 0x%llx\n", (unsigned long long)ic->data_device_sectors); + DEBUG_print(" data_device_sectors 0x%llx\n", i_size_read(ic->dev->bdev->bd_inode) >> SECTOR_SHIFT); DEBUG_print(" initial_sectors 0x%x\n", ic->initial_sectors); DEBUG_print(" metadata_run 0x%x\n", ic->metadata_run); DEBUG_print(" log2_metadata_run %d\n", ic->log2_metadata_run); DEBUG_print(" provided_data_sectors 0x%llx (%llu)\n", (unsigned long long)ic->provided_data_sectors, (unsigned long long)ic->provided_data_sectors); DEBUG_print(" log2_buffer_sectors %u\n", ic->log2_buffer_sectors); + DEBUG_print(" bits_in_journal %llu\n", (unsigned long long)bits_in_journal); - if (recalculate && !(ic->sb->flags & cpu_to_le32(SB_FLAG_RECALCULATING))) { + if (ic->recalculate_flag && !(ic->sb->flags & cpu_to_le32(SB_FLAG_RECALCULATING))) { ic->sb->flags |= cpu_to_le32(SB_FLAG_RECALCULATING); ic->sb->recalc_sector = cpu_to_le64(0); } - if (ic->sb->flags & cpu_to_le32(SB_FLAG_RECALCULATING)) { - if (!ic->internal_hash) { - r = -EINVAL; - ti->error = "Recalculate is only valid with internal hash"; - goto bad; - } + if (ic->internal_hash) { ic->recalc_wq = alloc_workqueue("dm-integrity-recalc", WQ_MEM_RECLAIM, 1); if (!ic->recalc_wq ) { ti->error = "Cannot allocate workqueue"; @@ -3512,6 +3928,45 @@ try_smaller_buffer: r = create_journal(ic, &ti->error); if (r) goto bad; + + } + + if (ic->mode == 'B') { + unsigned i; + unsigned n_bitmap_pages = DIV_ROUND_UP(ic->n_bitmap_blocks, PAGE_SIZE / BITMAP_BLOCK_SIZE); + + ic->recalc_bitmap = dm_integrity_alloc_page_list(n_bitmap_pages); + if (!ic->recalc_bitmap) { + r = -ENOMEM; + goto bad; + } + ic->may_write_bitmap = dm_integrity_alloc_page_list(n_bitmap_pages); + if (!ic->may_write_bitmap) { + r = -ENOMEM; + goto bad; + } + ic->bbs = kvmalloc_array(ic->n_bitmap_blocks, sizeof(struct bitmap_block_status), GFP_KERNEL); + if (!ic->bbs) { + r = -ENOMEM; + goto bad; + } + INIT_DELAYED_WORK(&ic->bitmap_flush_work, bitmap_flush_work); + for (i = 0; i < ic->n_bitmap_blocks; i++) { + struct bitmap_block_status *bbs = &ic->bbs[i]; + unsigned sector, pl_index, pl_offset; + + INIT_WORK(&bbs->work, bitmap_block_work); + bbs->ic = ic; + bbs->idx = i; + bio_list_init(&bbs->bio_queue); + spin_lock_init(&bbs->bio_queue_lock); + + sector = i * (BITMAP_BLOCK_SIZE >> SECTOR_SHIFT); + pl_index = sector >> (PAGE_SHIFT - SECTOR_SHIFT); + pl_offset = (sector << SECTOR_SHIFT) & (PAGE_SIZE - 1); + + bbs->bitmap = lowmem_page_address(ic->journal[pl_index].page) + pl_offset; + } } if (should_write_sb) { @@ -3536,6 +3991,17 @@ try_smaller_buffer: if (r) goto bad; } + if (ic->mode == 'B') { + unsigned max_io_len = ((sector_t)ic->sectors_per_block << ic->log2_blocks_per_bitmap_bit) * (BITMAP_BLOCK_SIZE * 8); + if (!max_io_len) + max_io_len = 1U << 31; + DEBUG_print("max_io_len: old %u, new %u\n", ti->max_io_len, max_io_len); + if (!ti->max_io_len || ti->max_io_len > max_io_len) { + r = dm_set_target_max_io_len(ti, max_io_len); + if (r) + goto bad; + } + } if (!ic->internal_hash) dm_integrity_set(ti, ic); @@ -3544,6 +4010,7 @@ try_smaller_buffer: ti->flush_supported = true; return 0; + bad: dm_integrity_dtr(ti); return r; @@ -3568,6 +4035,7 @@ static void dm_integrity_dtr(struct dm_target *ti) destroy_workqueue(ic->recalc_wq); vfree(ic->recalc_buffer); kvfree(ic->recalc_tags); + kvfree(ic->bbs); if (ic->bufio) dm_bufio_client_destroy(ic->bufio); mempool_exit(&ic->journal_io_mempool); @@ -3580,6 +4048,8 @@ static void dm_integrity_dtr(struct dm_target *ti) dm_integrity_free_page_list(ic->journal); dm_integrity_free_page_list(ic->journal_io); dm_integrity_free_page_list(ic->journal_xor); + dm_integrity_free_page_list(ic->recalc_bitmap); + dm_integrity_free_page_list(ic->may_write_bitmap); if (ic->journal_scatterlist) dm_integrity_free_journal_scatterlist(ic, ic->journal_scatterlist); if (ic->journal_io_scatterlist) @@ -3617,7 +4087,7 @@ static void dm_integrity_dtr(struct dm_target *ti) static struct target_type integrity_target = { .name = "integrity", - .version = {1, 2, 0}, + .version = {1, 3, 0}, .module = THIS_MODULE, .features = DM_TARGET_SINGLETON | DM_TARGET_INTEGRITY, .ctr = dm_integrity_ctr, -- cgit v1.2.3 From 823a633eeb7775171cbb9f423401316504745dc7 Mon Sep 17 00:00:00 2001 From: Hans Verkuil Date: Tue, 23 Apr 2019 10:05:09 -0400 Subject: media: field-order.rst: clarify FIELD_ANY and FIELD_NONE Rephrased the FIELD_ANY description: rather than explicitly list field values, just say 'when any field format is acceptable'. The list of FIELD values was outdated, so it was a bit confusing. The FIELD_NONE description said that 'The driver may also indicate this order when it cannot distinguish between V4L2_FIELD_TOP and V4L2_FIELD_BOTTOM'. This is false, NONE really means a full frame and userspace depends on that. So drop this line completely. There are no drivers that do this anyway. FIELD_TOP/BOTTOM/ALTERNATE indicate that the number of lines in the buffer are that of a field, not frame, so returning NONE here would cause huge problems. Finally attempt to clarify 'progressive' and 'interlaced' a little bit. Signed-off-by: Hans Verkuil Signed-off-by: Mauro Carvalho Chehab --- Documentation/media/uapi/v4l/field-order.rst | 16 +++++++--------- 1 file changed, 7 insertions(+), 9 deletions(-) (limited to 'Documentation') diff --git a/Documentation/media/uapi/v4l/field-order.rst b/Documentation/media/uapi/v4l/field-order.rst index 3fb473e3b8e2..d640e922a974 100644 --- a/Documentation/media/uapi/v4l/field-order.rst +++ b/Documentation/media/uapi/v4l/field-order.rst @@ -75,12 +75,11 @@ enum v4l2_field * - ``V4L2_FIELD_ANY`` - 0 - - Applications request this field order when any one of the - ``V4L2_FIELD_NONE``, ``V4L2_FIELD_TOP``, ``V4L2_FIELD_BOTTOM``, or - ``V4L2_FIELD_INTERLACED`` formats is acceptable. Drivers choose - depending on hardware capabilities or e. g. the requested image - size, and return the actual field order. Drivers must never return - ``V4L2_FIELD_ANY``. If multiple field orders are possible the + - Applications request this field order when any field format + is acceptable. Drivers choose depending on hardware capabilities or + e.g. the requested image size, and return the actual field order. + Drivers must never return ``V4L2_FIELD_ANY``. + If multiple field orders are possible the driver must choose one of the possible field orders during :ref:`VIDIOC_S_FMT ` or :ref:`VIDIOC_TRY_FMT `. struct @@ -88,9 +87,8 @@ enum v4l2_field ``V4L2_FIELD_ANY``. * - ``V4L2_FIELD_NONE`` - 1 - - Images are in progressive format, not interlaced. The driver may - also indicate this order when it cannot distinguish between - ``V4L2_FIELD_TOP`` and ``V4L2_FIELD_BOTTOM``. + - Images are in progressive (frame-based) format, not interlaced + (field-based). * - ``V4L2_FIELD_TOP`` - 2 - Images consist of the top (aka odd) field only. -- cgit v1.2.3 From f15be33aa3f9d4e17b8e35e18d7f9577187960c2 Mon Sep 17 00:00:00 2001 From: Federico Vaga Date: Wed, 8 May 2019 00:05:25 +0200 Subject: doc:it_IT: align documentation after licenses patches This patch translates in Italian the following updates 62be257e986d LICENSES: Rename other to deprecated 8ea8814fcdcb LICENSES: Clearly mark dual license only licenses 6132c37ca543 docs: Don't reference the ZLib license in license-rules.rst Signed-off-by: Federico Vaga Signed-off-by: Jonathan Corbet --- .../translations/it_IT/process/license-rules.rst | 60 +++++++++++++++++++--- 1 file changed, 54 insertions(+), 6 deletions(-) (limited to 'Documentation') diff --git a/Documentation/translations/it_IT/process/license-rules.rst b/Documentation/translations/it_IT/process/license-rules.rst index 91a8794ffd79..f058e06996dc 100644 --- a/Documentation/translations/it_IT/process/license-rules.rst +++ b/Documentation/translations/it_IT/process/license-rules.rst @@ -249,13 +249,13 @@ essere categorizzate in: | -2. Licenze non raccomandate: +2. Licenze deprecate: Questo tipo di licenze dovrebbero essere usate solo per codice già esistente o quando si prende codice da altri progetti. Le licenze sono disponibili nei sorgenti del kernel nella cartella:: - LICENSES/other/ + LICENSES/deprecated/ I file in questa cartella contengono il testo completo della licenza e i `Metatag`_. Il nome di questi file è lo stesso usato come identificatore @@ -263,14 +263,14 @@ essere categorizzate in: Esempi:: - LICENSES/other/ISC + LICENSES/deprecated/ISC Contiene il testo della licenza Internet System Consortium e i suoi metatag:: - LICENSES/other/ZLib + LICENSES/deprecated/GPL-1.0 - Contiene il testo della licenza ZLIB e i suoi metatag. + Contiene il testo della versione 1 della licenza GPL e i suoi metatag. Metatag: @@ -294,7 +294,55 @@ essere categorizzate in: | -3. _`Eccezioni`: +3. Solo per doppie licenze + + Queste licenze dovrebbero essere usate solamente per codice licenziato in + combinazione con un'altra licenza che solitamente è quella preferita. + Queste licenze sono disponibili nei sorgenti del kernel nella cartella:: + + LICENSES/dual + + I file in questa cartella contengono il testo completo della rispettiva + licenza e i suoi `Metatags`_. I nomi dei file sono identici agli + identificatori di licenza SPDX che dovrebbero essere usati nei file + sorgenti. + + Esempi:: + + LICENSES/dual/MPL-1.1 + + Questo file contiene il testo della versione 1.1 della licenza *Mozilla + Pulic License* e i metatag necessari:: + + LICENSES/dual/Apache-2.0 + + Questo file contiene il testo della versione 2.0 della licenza Apache e i + metatag necessari. + + Metatag: + + I requisiti per le 'altre' ('*other*') licenze sono identici a quelli per le + `Licenze raccomandate`_. + + Esempio del formato del file:: + + Valid-License-Identifier: MPL-1.1 + SPDX-URL: https://spdx.org/licenses/MPL-1.1.html + Usage-Guide: + Do NOT use. The MPL-1.1 is not GPL2 compatible. It may only be used for + dual-licensed files where the other license is GPL2 compatible. + If you end up using this it MUST be used together with a GPL2 compatible + license using "OR". + To use the Mozilla Public License version 1.1 put the following SPDX + tag/value pair into a comment according to the placement guidelines in + the licensing rules documentation: + SPDX-License-Identifier: MPL-1.1 + License-Text: + Full license text + +| + +4. _`Eccezioni`: Alcune licenze possono essere corrette con delle eccezioni che forniscono diritti aggiuntivi. Queste eccezioni sono disponibili nei sorgenti del -- cgit v1.2.3 From 39a39d5b6bc0f1f6dd6eaa44916f19edfe003377 Mon Sep 17 00:00:00 2001 From: Tzvetomir Stoyanov Date: Fri, 3 May 2019 17:35:37 +0300 Subject: Documentation/trace: Add clarification how histogram onmatch works The current trace documentation, the section describing histogram's "onmatch" is not straightforward enough about how this action is applied. It is not clear what criteria are used to "match" both events. A short note is added, describing what exactly is compared in order to match the events. Signed-off-by: Tzvetomir Stoyanov Reviewed-by: Steven Rostedt (VMware) Reviewed-by: Tom Zanussi [jc: fixed trivial conflict with docs-next] Signed-off-by: Jonathan Corbet --- Documentation/trace/histogram.rst | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) (limited to 'Documentation') diff --git a/Documentation/trace/histogram.rst b/Documentation/trace/histogram.rst index f95d94d19c22..ddbaffa530f9 100644 --- a/Documentation/trace/histogram.rst +++ b/Documentation/trace/histogram.rst @@ -1915,7 +1915,10 @@ The following commonly-used handler.action pairs are available: The 'matching.event' specification is simply the fully qualified event name of the event that matches the target event for the - onmatch() functionality, in the form 'system.event_name'. + onmatch() functionality, in the form 'system.event_name'. Histogram + keys of both events are compared to find if events match. In case + multiple histogram keys are used, they all must match in the specified + order. Finally, the number and type of variables/fields in the 'param list' must match the number and types of the fields in the @@ -1978,9 +1981,9 @@ The following commonly-used handler.action pairs are available: /sys/kernel/debug/tracing/events/sched/sched_waking/trigger Then, when the corresponding thread is actually scheduled onto the - CPU by a sched_switch event, calculate the latency and use that - along with another variable and an event field to generate a - wakeup_latency synthetic event:: + CPU by a sched_switch event (saved_pid matches next_pid), calculate + the latency and use that along with another variable and an event field + to generate a wakeup_latency synthetic event:: # echo 'hist:keys=next_pid:wakeup_lat=common_timestamp.usecs-$ts0:\ onmatch(sched.sched_waking).wakeup_latency($wakeup_lat,\ -- cgit v1.2.3 From e5def4c6039e9b7bb158c6ec6d8fedda9265b7ef Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:15 +0800 Subject: Documentation: add Linux x86 docs to Sphinx TOC tree Add a index.rst for x86 support. More docs will be added later. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/index.rst | 1 + Documentation/x86/index.rst | 9 +++++++++ 2 files changed, 10 insertions(+) create mode 100644 Documentation/x86/index.rst (limited to 'Documentation') diff --git a/Documentation/index.rst b/Documentation/index.rst index 80a421cb935e..d65dd4934a1a 100644 --- a/Documentation/index.rst +++ b/Documentation/index.rst @@ -101,6 +101,7 @@ implementation. .. toctree:: :maxdepth: 2 + x86/index sh/index Filesystem Documentation diff --git a/Documentation/x86/index.rst b/Documentation/x86/index.rst new file mode 100644 index 000000000000..9f34545a9c52 --- /dev/null +++ b/Documentation/x86/index.rst @@ -0,0 +1,9 @@ +.. SPDX-License-Identifier: GPL-2.0 + +========================== +x86-specific Documentation +========================== + +.. toctree:: + :maxdepth: 2 + :numbered: -- cgit v1.2.3 From f1f238a9f1ca1f1c7f53ebb7d5517066bf40c471 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:16 +0800 Subject: Documentation: x86: convert boot.txt to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Cc: Mauro Carvalho Chehab Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/boot.rst | 1256 +++++++++++++++++++++++++++++++++++++++++++ Documentation/x86/boot.txt | 1134 -------------------------------------- Documentation/x86/index.rst | 2 + 3 files changed, 1258 insertions(+), 1134 deletions(-) create mode 100644 Documentation/x86/boot.rst delete mode 100644 Documentation/x86/boot.txt (limited to 'Documentation') diff --git a/Documentation/x86/boot.rst b/Documentation/x86/boot.rst new file mode 100644 index 000000000000..08a2f100c0e6 --- /dev/null +++ b/Documentation/x86/boot.rst @@ -0,0 +1,1256 @@ +.. SPDX-License-Identifier: GPL-2.0 + +=========================== +The Linux/x86 Boot Protocol +=========================== + +On the x86 platform, the Linux kernel uses a rather complicated boot +convention. This has evolved partially due to historical aspects, as +well as the desire in the early days to have the kernel itself be a +bootable image, the complicated PC memory model and due to changed +expectations in the PC industry caused by the effective demise of +real-mode DOS as a mainstream operating system. + +Currently, the following versions of the Linux/x86 boot protocol exist. + +============= ============================================================ +Old kernels zImage/Image support only. Some very early kernels + may not even support a command line. + +Protocol 2.00 (Kernel 1.3.73) Added bzImage and initrd support, as + well as a formalized way to communicate between the + boot loader and the kernel. setup.S made relocatable, + although the traditional setup area still assumed + writable. + +Protocol 2.01 (Kernel 1.3.76) Added a heap overrun warning. + +Protocol 2.02 (Kernel 2.4.0-test3-pre3) New command line protocol. + Lower the conventional memory ceiling. No overwrite + of the traditional setup area, thus making booting + safe for systems which use the EBDA from SMM or 32-bit + BIOS entry points. zImage deprecated but still + supported. + +Protocol 2.03 (Kernel 2.4.18-pre1) Explicitly makes the highest possible + initrd address available to the bootloader. + +Protocol 2.04 (Kernel 2.6.14) Extend the syssize field to four bytes. + +Protocol 2.05 (Kernel 2.6.20) Make protected mode kernel relocatable. + Introduce relocatable_kernel and kernel_alignment fields. + +Protocol 2.06 (Kernel 2.6.22) Added a field that contains the size of + the boot command line. + +Protocol 2.07 (Kernel 2.6.24) Added paravirtualised boot protocol. + Introduced hardware_subarch and hardware_subarch_data + and KEEP_SEGMENTS flag in load_flags. + +Protocol 2.08 (Kernel 2.6.26) Added crc32 checksum and ELF format + payload. Introduced payload_offset and payload_length + fields to aid in locating the payload. + +Protocol 2.09 (Kernel 2.6.26) Added a field of 64-bit physical + pointer to single linked list of struct setup_data. + +Protocol 2.10 (Kernel 2.6.31) Added a protocol for relaxed alignment + beyond the kernel_alignment added, new init_size and + pref_address fields. Added extended boot loader IDs. + +Protocol 2.11 (Kernel 3.6) Added a field for offset of EFI handover + protocol entry point. + +Protocol 2.12 (Kernel 3.8) Added the xloadflags field and extension fields + to struct boot_params for loading bzImage and ramdisk + above 4G in 64bit. + +Protocol 2.13 (Kernel 3.14) Support 32- and 64-bit flags being set in + xloadflags to support booting a 64-bit kernel from 32-bit + EFI +============= ============================================================ + + +Memory Layout +============= + +The traditional memory map for the kernel loader, used for Image or +zImage kernels, typically looks like:: + + | | + 0A0000 +------------------------+ + | Reserved for BIOS | Do not use. Reserved for BIOS EBDA. + 09A000 +------------------------+ + | Command line | + | Stack/heap | For use by the kernel real-mode code. + 098000 +------------------------+ + | Kernel setup | The kernel real-mode code. + 090200 +------------------------+ + | Kernel boot sector | The kernel legacy boot sector. + 090000 +------------------------+ + | Protected-mode kernel | The bulk of the kernel image. + 010000 +------------------------+ + | Boot loader | <- Boot sector entry point 0000:7C00 + 001000 +------------------------+ + | Reserved for MBR/BIOS | + 000800 +------------------------+ + | Typically used by MBR | + 000600 +------------------------+ + | BIOS use only | + 000000 +------------------------+ + +When using bzImage, the protected-mode kernel was relocated to +0x100000 ("high memory"), and the kernel real-mode block (boot sector, +setup, and stack/heap) was made relocatable to any address between +0x10000 and end of low memory. Unfortunately, in protocols 2.00 and +2.01 the 0x90000+ memory range is still used internally by the kernel; +the 2.02 protocol resolves that problem. + +It is desirable to keep the "memory ceiling" -- the highest point in +low memory touched by the boot loader -- as low as possible, since +some newer BIOSes have begun to allocate some rather large amounts of +memory, called the Extended BIOS Data Area, near the top of low +memory. The boot loader should use the "INT 12h" BIOS call to verify +how much low memory is available. + +Unfortunately, if INT 12h reports that the amount of memory is too +low, there is usually nothing the boot loader can do but to report an +error to the user. The boot loader should therefore be designed to +take up as little space in low memory as it reasonably can. For +zImage or old bzImage kernels, which need data written into the +0x90000 segment, the boot loader should make sure not to use memory +above the 0x9A000 point; too many BIOSes will break above that point. + +For a modern bzImage kernel with boot protocol version >= 2.02, a +memory layout like the following is suggested:: + + ~ ~ + | Protected-mode kernel | + 100000 +------------------------+ + | I/O memory hole | + 0A0000 +------------------------+ + | Reserved for BIOS | Leave as much as possible unused + ~ ~ + | Command line | (Can also be below the X+10000 mark) + X+10000 +------------------------+ + | Stack/heap | For use by the kernel real-mode code. + X+08000 +------------------------+ + | Kernel setup | The kernel real-mode code. + | Kernel boot sector | The kernel legacy boot sector. + X +------------------------+ + | Boot loader | <- Boot sector entry point 0000:7C00 + 001000 +------------------------+ + | Reserved for MBR/BIOS | + 000800 +------------------------+ + | Typically used by MBR | + 000600 +------------------------+ + | BIOS use only | + 000000 +------------------------+ + + ... where the address X is as low as the design of the boot loader permits. + + +The Real-Mode Kernel Header +=========================== + +In the following text, and anywhere in the kernel boot sequence, "a +sector" refers to 512 bytes. It is independent of the actual sector +size of the underlying medium. + +The first step in loading a Linux kernel should be to load the +real-mode code (boot sector and setup code) and then examine the +following header at offset 0x01f1. The real-mode code can total up to +32K, although the boot loader may choose to load only the first two +sectors (1K) and then examine the bootup sector size. + +The header looks like: + +=========== ======== ===================== ============================================ +Offset/Size Proto Name Meaning +=========== ======== ===================== ============================================ +01F1/1 ALL(1) setup_sects The size of the setup in sectors +01F2/2 ALL root_flags If set, the root is mounted readonly +01F4/4 2.04+(2) syssize The size of the 32-bit code in 16-byte paras +01F8/2 ALL ram_size DO NOT USE - for bootsect.S use only +01FA/2 ALL vid_mode Video mode control +01FC/2 ALL root_dev Default root device number +01FE/2 ALL boot_flag 0xAA55 magic number +0200/2 2.00+ jump Jump instruction +0202/4 2.00+ header Magic signature "HdrS" +0206/2 2.00+ version Boot protocol version supported +0208/4 2.00+ realmode_swtch Boot loader hook (see below) +020C/2 2.00+ start_sys_seg The load-low segment (0x1000) (obsolete) +020E/2 2.00+ kernel_version Pointer to kernel version string +0210/1 2.00+ type_of_loader Boot loader identifier +0211/1 2.00+ loadflags Boot protocol option flags +0212/2 2.00+ setup_move_size Move to high memory size (used with hooks) +0214/4 2.00+ code32_start Boot loader hook (see below) +0218/4 2.00+ ramdisk_image initrd load address (set by boot loader) +021C/4 2.00+ ramdisk_size initrd size (set by boot loader) +0220/4 2.00+ bootsect_kludge DO NOT USE - for bootsect.S use only +0224/2 2.01+ heap_end_ptr Free memory after setup end +0226/1 2.02+(3) ext_loader_ver Extended boot loader version +0227/1 2.02+(3) ext_loader_type Extended boot loader ID +0228/4 2.02+ cmd_line_ptr 32-bit pointer to the kernel command line +022C/4 2.03+ initrd_addr_max Highest legal initrd address +0230/4 2.05+ kernel_alignment Physical addr alignment required for kernel +0234/1 2.05+ relocatable_kernel Whether kernel is relocatable or not +0235/1 2.10+ min_alignment Minimum alignment, as a power of two +0236/2 2.12+ xloadflags Boot protocol option flags +0238/4 2.06+ cmdline_size Maximum size of the kernel command line +023C/4 2.07+ hardware_subarch Hardware subarchitecture +0240/8 2.07+ hardware_subarch_data Subarchitecture-specific data +0248/4 2.08+ payload_offset Offset of kernel payload +024C/4 2.08+ payload_length Length of kernel payload +0250/8 2.09+ setup_data 64-bit physical pointer to linked list + of struct setup_data +0258/8 2.10+ pref_address Preferred loading address +0260/4 2.10+ init_size Linear memory required during initialization +0264/4 2.11+ handover_offset Offset of handover entry point +=========== ======== ===================== ============================================ + +.. note:: + (1) For backwards compatibility, if the setup_sects field contains 0, the + real value is 4. + + (2) For boot protocol prior to 2.04, the upper two bytes of the syssize + field are unusable, which means the size of a bzImage kernel + cannot be determined. + + (3) Ignored, but safe to set, for boot protocols 2.02-2.09. + +If the "HdrS" (0x53726448) magic number is not found at offset 0x202, +the boot protocol version is "old". Loading an old kernel, the +following parameters should be assumed:: + + Image type = zImage + initrd not supported + Real-mode kernel must be located at 0x90000. + +Otherwise, the "version" field contains the protocol version, +e.g. protocol version 2.01 will contain 0x0201 in this field. When +setting fields in the header, you must make sure only to set fields +supported by the protocol version in use. + + +Details of Harder Fileds +======================== + +For each field, some are information from the kernel to the bootloader +("read"), some are expected to be filled out by the bootloader +("write"), and some are expected to be read and modified by the +bootloader ("modify"). + +All general purpose boot loaders should write the fields marked +(obligatory). Boot loaders who want to load the kernel at a +nonstandard address should fill in the fields marked (reloc); other +boot loaders can ignore those fields. + +The byte order of all fields is littleendian (this is x86, after all.) + +============ =========== +Field name: setup_sects +Type: read +Offset/size: 0x1f1/1 +Protocol: ALL +============ =========== + + The size of the setup code in 512-byte sectors. If this field is + 0, the real value is 4. The real-mode code consists of the boot + sector (always one 512-byte sector) plus the setup code. + +============ ================= +Field name: root_flags +Type: modify (optional) +Offset/size: 0x1f2/2 +Protocol: ALL +============ ================= + + If this field is nonzero, the root defaults to readonly. The use of + this field is deprecated; use the "ro" or "rw" options on the + command line instead. + +============ =============================================== +Field name: syssize +Type: read +Offset/size: 0x1f4/4 (protocol 2.04+) 0x1f4/2 (protocol ALL) +Protocol: 2.04+ +============ =============================================== + + The size of the protected-mode code in units of 16-byte paragraphs. + For protocol versions older than 2.04 this field is only two bytes + wide, and therefore cannot be trusted for the size of a kernel if + the LOAD_HIGH flag is set. + +============ =============== +Field name: ram_size +Type: kernel internal +Offset/size: 0x1f8/2 +Protocol: ALL +============ =============== + + This field is obsolete. + +============ =================== +Field name: vid_mode +Type: modify (obligatory) +Offset/size: 0x1fa/2 +============ =================== + + Please see the section on SPECIAL COMMAND LINE OPTIONS. + +============ ================= +Field name: root_dev +Type: modify (optional) +Offset/size: 0x1fc/2 +Protocol: ALL +============ ================= + + The default root device device number. The use of this field is + deprecated, use the "root=" option on the command line instead. + +============ ========= +Field name: boot_flag +Type: read +Offset/size: 0x1fe/2 +Protocol: ALL +============ ========= + + Contains 0xAA55. This is the closest thing old Linux kernels have + to a magic number. + +============ ======= +Field name: jump +Type: read +Offset/size: 0x200/2 +Protocol: 2.00+ +============ ======= + + Contains an x86 jump instruction, 0xEB followed by a signed offset + relative to byte 0x202. This can be used to determine the size of + the header. + +============ ======= +Field name: header +Type: read +Offset/size: 0x202/4 +Protocol: 2.00+ +============ ======= + + Contains the magic number "HdrS" (0x53726448). + +============ ======= +Field name: version +Type: read +Offset/size: 0x206/2 +Protocol: 2.00+ +============ ======= + + Contains the boot protocol version, in (major << 8)+minor format, + e.g. 0x0204 for version 2.04, and 0x0a11 for a hypothetical version + 10.17. + +============ ================= +Field name: realmode_swtch +Type: modify (optional) +Offset/size: 0x208/4 +Protocol: 2.00+ +============ ================= + + Boot loader hook (see ADVANCED BOOT LOADER HOOKS below.) + +============ ============= +Field name: start_sys_seg +Type: read +Offset/size: 0x20c/2 +Protocol: 2.00+ +============ ============= + + The load low segment (0x1000). Obsolete. + +============ ============== +Field name: kernel_version +Type: read +Offset/size: 0x20e/2 +Protocol: 2.00+ +============ ============== + + If set to a nonzero value, contains a pointer to a NUL-terminated + human-readable kernel version number string, less 0x200. This can + be used to display the kernel version to the user. This value + should be less than (0x200*setup_sects). + + For example, if this value is set to 0x1c00, the kernel version + number string can be found at offset 0x1e00 in the kernel file. + This is a valid value if and only if the "setup_sects" field + contains the value 15 or higher, as:: + + 0x1c00 < 15*0x200 (= 0x1e00) but + 0x1c00 >= 14*0x200 (= 0x1c00) + + 0x1c00 >> 9 = 14, So the minimum value for setup_secs is 15. + +============ ================== +Field name: type_of_loader +Type: write (obligatory) +Offset/size: 0x210/1 +Protocol: 2.00+ +============ ================== + + If your boot loader has an assigned id (see table below), enter + 0xTV here, where T is an identifier for the boot loader and V is + a version number. Otherwise, enter 0xFF here. + + For boot loader IDs above T = 0xD, write T = 0xE to this field and + write the extended ID minus 0x10 to the ext_loader_type field. + Similarly, the ext_loader_ver field can be used to provide more than + four bits for the bootloader version. + + For example, for T = 0x15, V = 0x234, write:: + + type_of_loader <- 0xE4 + ext_loader_type <- 0x05 + ext_loader_ver <- 0x23 + + Assigned boot loader ids (hexadecimal): + + == ======================================= + 0 LILO + (0x00 reserved for pre-2.00 bootloader) + 1 Loadlin + 2 bootsect-loader + (0x20, all other values reserved) + 3 Syslinux + 4 Etherboot/gPXE/iPXE + 5 ELILO + 7 GRUB + 8 U-Boot + 9 Xen + A Gujin + B Qemu + C Arcturus Networks uCbootloader + D kexec-tools + E Extended (see ext_loader_type) + F Special (0xFF = undefined) + 10 Reserved + 11 Minimal Linux Bootloader + + 12 OVMF UEFI virtualization stack + == ======================================= + + Please contact if you need a bootloader ID value assigned. + +============ =================== +Field name: loadflags +Type: modify (obligatory) +Offset/size: 0x211/1 +Protocol: 2.00+ +============ =================== + + This field is a bitmask. + + Bit 0 (read): LOADED_HIGH + + - If 0, the protected-mode code is loaded at 0x10000. + - If 1, the protected-mode code is loaded at 0x100000. + + Bit 1 (kernel internal): KASLR_FLAG + + - Used internally by the compressed kernel to communicate + KASLR status to kernel proper. + + - If 1, KASLR enabled. + - If 0, KASLR disabled. + + Bit 5 (write): QUIET_FLAG + + - If 0, print early messages. + - If 1, suppress early messages. + + This requests to the kernel (decompressor and early + kernel) to not write early messages that require + accessing the display hardware directly. + + Bit 6 (write): KEEP_SEGMENTS + + Protocol: 2.07+ + + - If 0, reload the segment registers in the 32bit entry point. + - If 1, do not reload the segment registers in the 32bit entry point. + + Assume that %cs %ds %ss %es are all set to flat segments with + a base of 0 (or the equivalent for their environment). + + Bit 7 (write): CAN_USE_HEAP + + Set this bit to 1 to indicate that the value entered in the + heap_end_ptr is valid. If this field is clear, some setup code + functionality will be disabled. + + +============ =================== +Field name: setup_move_size +Type: modify (obligatory) +Offset/size: 0x212/2 +Protocol: 2.00-2.01 +============ =================== + + When using protocol 2.00 or 2.01, if the real mode kernel is not + loaded at 0x90000, it gets moved there later in the loading + sequence. Fill in this field if you want additional data (such as + the kernel command line) moved in addition to the real-mode kernel + itself. + + The unit is bytes starting with the beginning of the boot sector. + + This field is can be ignored when the protocol is 2.02 or higher, or + if the real-mode code is loaded at 0x90000. + +============ ======================== +Field name: code32_start +Type: modify (optional, reloc) +Offset/size: 0x214/4 +Protocol: 2.00+ +============ ======================== + + The address to jump to in protected mode. This defaults to the load + address of the kernel, and can be used by the boot loader to + determine the proper load address. + + This field can be modified for two purposes: + + 1. as a boot loader hook (see Advanced Boot Loader Hooks below.) + + 2. if a bootloader which does not install a hook loads a + relocatable kernel at a nonstandard address it will have to modify + this field to point to the load address. + +============ ================== +Field name: ramdisk_image +Type: write (obligatory) +Offset/size: 0x218/4 +Protocol: 2.00+ +============ ================== + + The 32-bit linear address of the initial ramdisk or ramfs. Leave at + zero if there is no initial ramdisk/ramfs. + +============ ================== +Field name: ramdisk_size +Type: write (obligatory) +Offset/size: 0x21c/4 +Protocol: 2.00+ +============ ================== + + Size of the initial ramdisk or ramfs. Leave at zero if there is no + initial ramdisk/ramfs. + +============ =============== +Field name: bootsect_kludge +Type: kernel internal +Offset/size: 0x220/4 +Protocol: 2.00+ +============ =============== + + This field is obsolete. + +============ ================== +Field name: heap_end_ptr +Type: write (obligatory) +Offset/size: 0x224/2 +Protocol: 2.01+ +============ ================== + + Set this field to the offset (from the beginning of the real-mode + code) of the end of the setup stack/heap, minus 0x0200. + +============ ================ +Field name: ext_loader_ver +Type: write (optional) +Offset/size: 0x226/1 +Protocol: 2.02+ +============ ================ + + This field is used as an extension of the version number in the + type_of_loader field. The total version number is considered to be + (type_of_loader & 0x0f) + (ext_loader_ver << 4). + + The use of this field is boot loader specific. If not written, it + is zero. + + Kernels prior to 2.6.31 did not recognize this field, but it is safe + to write for protocol version 2.02 or higher. + +============ ===================================================== +Field name: ext_loader_type +Type: write (obligatory if (type_of_loader & 0xf0) == 0xe0) +Offset/size: 0x227/1 +Protocol: 2.02+ +============ ===================================================== + + This field is used as an extension of the type number in + type_of_loader field. If the type in type_of_loader is 0xE, then + the actual type is (ext_loader_type + 0x10). + + This field is ignored if the type in type_of_loader is not 0xE. + + Kernels prior to 2.6.31 did not recognize this field, but it is safe + to write for protocol version 2.02 or higher. + +============ ================== +Field name: cmd_line_ptr +Type: write (obligatory) +Offset/size: 0x228/4 +Protocol: 2.02+ +============ ================== + + Set this field to the linear address of the kernel command line. + The kernel command line can be located anywhere between the end of + the setup heap and 0xA0000; it does not have to be located in the + same 64K segment as the real-mode code itself. + + Fill in this field even if your boot loader does not support a + command line, in which case you can point this to an empty string + (or better yet, to the string "auto".) If this field is left at + zero, the kernel will assume that your boot loader does not support + the 2.02+ protocol. + +============ =============== +Field name: initrd_addr_max +Type: read +Offset/size: 0x22c/4 +Protocol: 2.03+ +============ =============== + + The maximum address that may be occupied by the initial + ramdisk/ramfs contents. For boot protocols 2.02 or earlier, this + field is not present, and the maximum address is 0x37FFFFFF. (This + address is defined as the address of the highest safe byte, so if + your ramdisk is exactly 131072 bytes long and this field is + 0x37FFFFFF, you can start your ramdisk at 0x37FE0000.) + +============ ============================ +Field name: kernel_alignment +Type: read/modify (reloc) +Offset/size: 0x230/4 +Protocol: 2.05+ (read), 2.10+ (modify) +============ ============================ + + Alignment unit required by the kernel (if relocatable_kernel is + true.) A relocatable kernel that is loaded at an alignment + incompatible with the value in this field will be realigned during + kernel initialization. + + Starting with protocol version 2.10, this reflects the kernel + alignment preferred for optimal performance; it is possible for the + loader to modify this field to permit a lesser alignment. See the + min_alignment and pref_address field below. + +============ ================== +Field name: relocatable_kernel +Type: read (reloc) +Offset/size: 0x234/1 +Protocol: 2.05+ +============ ================== + + If this field is nonzero, the protected-mode part of the kernel can + be loaded at any address that satisfies the kernel_alignment field. + After loading, the boot loader must set the code32_start field to + point to the loaded code, or to a boot loader hook. + +============ ============= +Field name: min_alignment +Type: read (reloc) +Offset/size: 0x235/1 +Protocol: 2.10+ +============ ============= + + This field, if nonzero, indicates as a power of two the minimum + alignment required, as opposed to preferred, by the kernel to boot. + If a boot loader makes use of this field, it should update the + kernel_alignment field with the alignment unit desired; typically:: + + kernel_alignment = 1 << min_alignment + + There may be a considerable performance cost with an excessively + misaligned kernel. Therefore, a loader should typically try each + power-of-two alignment from kernel_alignment down to this alignment. + +============ ========== +Field name: xloadflags +Type: read +Offset/size: 0x236/2 +Protocol: 2.12+ +============ ========== + + This field is a bitmask. + + Bit 0 (read): XLF_KERNEL_64 + + - If 1, this kernel has the legacy 64-bit entry point at 0x200. + + Bit 1 (read): XLF_CAN_BE_LOADED_ABOVE_4G + + - If 1, kernel/boot_params/cmdline/ramdisk can be above 4G. + + Bit 2 (read): XLF_EFI_HANDOVER_32 + + - If 1, the kernel supports the 32-bit EFI handoff entry point + given at handover_offset. + + Bit 3 (read): XLF_EFI_HANDOVER_64 + + - If 1, the kernel supports the 64-bit EFI handoff entry point + given at handover_offset + 0x200. + + Bit 4 (read): XLF_EFI_KEXEC + + - If 1, the kernel supports kexec EFI boot with EFI runtime support. + + +============ ============ +Field name: cmdline_size +Type: read +Offset/size: 0x238/4 +Protocol: 2.06+ +============ ============ + + The maximum size of the command line without the terminating + zero. This means that the command line can contain at most + cmdline_size characters. With protocol version 2.05 and earlier, the + maximum size was 255. + +============ ==================================== +Field name: hardware_subarch +Type: write (optional, defaults to x86/PC) +Offset/size: 0x23c/4 +Protocol: 2.07+ +============ ==================================== + + In a paravirtualized environment the hardware low level architectural + pieces such as interrupt handling, page table handling, and + accessing process control registers needs to be done differently. + + This field allows the bootloader to inform the kernel we are in one + one of those environments. + + ========== ============================== + 0x00000000 The default x86/PC environment + 0x00000001 lguest + 0x00000002 Xen + 0x00000003 Moorestown MID + 0x00000004 CE4100 TV Platform + ========== ============================== + +============ ========================= +Field name: hardware_subarch_data +Type: write (subarch-dependent) +Offset/size: 0x240/8 +Protocol: 2.07+ +============ ========================= + + A pointer to data that is specific to hardware subarch + This field is currently unused for the default x86/PC environment, + do not modify. + +============ ============== +Field name: payload_offset +Type: read +Offset/size: 0x248/4 +Protocol: 2.08+ +============ ============== + + If non-zero then this field contains the offset from the beginning + of the protected-mode code to the payload. + + The payload may be compressed. The format of both the compressed and + uncompressed data should be determined using the standard magic + numbers. The currently supported compression formats are gzip + (magic numbers 1F 8B or 1F 9E), bzip2 (magic number 42 5A), LZMA + (magic number 5D 00), XZ (magic number FD 37), and LZ4 (magic number + 02 21). The uncompressed payload is currently always ELF (magic + number 7F 45 4C 46). + +============ ============== +Field name: payload_length +Type: read +Offset/size: 0x24c/4 +Protocol: 2.08+ +============ ============== + + The length of the payload. + +============ =============== +Field name: setup_data +Type: write (special) +Offset/size: 0x250/8 +Protocol: 2.09+ +============ =============== + + The 64-bit physical pointer to NULL terminated single linked list of + struct setup_data. This is used to define a more extensible boot + parameters passing mechanism. The definition of struct setup_data is + as follow:: + + struct setup_data { + u64 next; + u32 type; + u32 len; + u8 data[0]; + }; + + Where, the next is a 64-bit physical pointer to the next node of + linked list, the next field of the last node is 0; the type is used + to identify the contents of data; the len is the length of data + field; the data holds the real payload. + + This list may be modified at a number of points during the bootup + process. Therefore, when modifying this list one should always make + sure to consider the case where the linked list already contains + entries. + +============ ============ +Field name: pref_address +Type: read (reloc) +Offset/size: 0x258/8 +Protocol: 2.10+ +============ ============ + + This field, if nonzero, represents a preferred load address for the + kernel. A relocating bootloader should attempt to load at this + address if possible. + + A non-relocatable kernel will unconditionally move itself and to run + at this address. + +============ ======= +Field name: init_size +Type: read +Offset/size: 0x260/4 +============ ======= + + This field indicates the amount of linear contiguous memory starting + at the kernel runtime start address that the kernel needs before it + is capable of examining its memory map. This is not the same thing + as the total amount of memory the kernel needs to boot, but it can + be used by a relocating boot loader to help select a safe load + address for the kernel. + + The kernel runtime start address is determined by the following algorithm:: + + if (relocatable_kernel) + runtime_start = align_up(load_address, kernel_alignment) + else + runtime_start = pref_address + +============ =============== +Field name: handover_offset +Type: read +Offset/size: 0x264/4 +============ =============== + + This field is the offset from the beginning of the kernel image to + the EFI handover protocol entry point. Boot loaders using the EFI + handover protocol to boot the kernel should jump to this offset. + + See EFI HANDOVER PROTOCOL below for more details. + + +The Image Checksum +================== + +From boot protocol version 2.08 onwards the CRC-32 is calculated over +the entire file using the characteristic polynomial 0x04C11DB7 and an +initial remainder of 0xffffffff. The checksum is appended to the +file; therefore the CRC of the file up to the limit specified in the +syssize field of the header is always 0. + + +The Kernel Command Line +======================= + +The kernel command line has become an important way for the boot +loader to communicate with the kernel. Some of its options are also +relevant to the boot loader itself, see "special command line options" +below. + +The kernel command line is a null-terminated string. The maximum +length can be retrieved from the field cmdline_size. Before protocol +version 2.06, the maximum was 255 characters. A string that is too +long will be automatically truncated by the kernel. + +If the boot protocol version is 2.02 or later, the address of the +kernel command line is given by the header field cmd_line_ptr (see +above.) This address can be anywhere between the end of the setup +heap and 0xA0000. + +If the protocol version is *not* 2.02 or higher, the kernel +command line is entered using the following protocol: + + - At offset 0x0020 (word), "cmd_line_magic", enter the magic + number 0xA33F. + + - At offset 0x0022 (word), "cmd_line_offset", enter the offset + of the kernel command line (relative to the start of the + real-mode kernel). + + - The kernel command line *must* be within the memory region + covered by setup_move_size, so you may need to adjust this + field. + + +Memory Layout of The Real-Mode Code +=================================== + +The real-mode code requires a stack/heap to be set up, as well as +memory allocated for the kernel command line. This needs to be done +in the real-mode accessible memory in bottom megabyte. + +It should be noted that modern machines often have a sizable Extended +BIOS Data Area (EBDA). As a result, it is advisable to use as little +of the low megabyte as possible. + +Unfortunately, under the following circumstances the 0x90000 memory +segment has to be used: + + - When loading a zImage kernel ((loadflags & 0x01) == 0). + - When loading a 2.01 or earlier boot protocol kernel. + +.. note:: + For the 2.00 and 2.01 boot protocols, the real-mode code + can be loaded at another address, but it is internally + relocated to 0x90000. For the "old" protocol, the + real-mode code must be loaded at 0x90000. + +When loading at 0x90000, avoid using memory above 0x9a000. + +For boot protocol 2.02 or higher, the command line does not have to be +located in the same 64K segment as the real-mode setup code; it is +thus permitted to give the stack/heap the full 64K segment and locate +the command line above it. + +The kernel command line should not be located below the real-mode +code, nor should it be located in high memory. + + +Sample Boot Configuartion +========================= + +As a sample configuration, assume the following layout of the real +mode segment. + + When loading below 0x90000, use the entire segment: + + ============= =================== + 0x0000-0x7fff Real mode kernel + 0x8000-0xdfff Stack and heap + 0xe000-0xffff Kernel command line + ============= =================== + + When loading at 0x90000 OR the protocol version is 2.01 or earlier: + + ============= =================== + 0x0000-0x7fff Real mode kernel + 0x8000-0x97ff Stack and heap + 0x9800-0x9fff Kernel command line + ============= =================== + +Such a boot loader should enter the following fields in the header:: + + unsigned long base_ptr; /* base address for real-mode segment */ + + if ( setup_sects == 0 ) { + setup_sects = 4; + } + + if ( protocol >= 0x0200 ) { + type_of_loader = ; + if ( loading_initrd ) { + ramdisk_image = ; + ramdisk_size = ; + } + + if ( protocol >= 0x0202 && loadflags & 0x01 ) + heap_end = 0xe000; + else + heap_end = 0x9800; + + if ( protocol >= 0x0201 ) { + heap_end_ptr = heap_end - 0x200; + loadflags |= 0x80; /* CAN_USE_HEAP */ + } + + if ( protocol >= 0x0202 ) { + cmd_line_ptr = base_ptr + heap_end; + strcpy(cmd_line_ptr, cmdline); + } else { + cmd_line_magic = 0xA33F; + cmd_line_offset = heap_end; + setup_move_size = heap_end + strlen(cmdline)+1; + strcpy(base_ptr+cmd_line_offset, cmdline); + } + } else { + /* Very old kernel */ + + heap_end = 0x9800; + + cmd_line_magic = 0xA33F; + cmd_line_offset = heap_end; + + /* A very old kernel MUST have its real-mode code + loaded at 0x90000 */ + + if ( base_ptr != 0x90000 ) { + /* Copy the real-mode kernel */ + memcpy(0x90000, base_ptr, (setup_sects+1)*512); + base_ptr = 0x90000; /* Relocated */ + } + + strcpy(0x90000+cmd_line_offset, cmdline); + + /* It is recommended to clear memory up to the 32K mark */ + memset(0x90000 + (setup_sects+1)*512, 0, + (64-(setup_sects+1))*512); + } + + +Loading The Rest of The Kernel +============================== + +The 32-bit (non-real-mode) kernel starts at offset (setup_sects+1)*512 +in the kernel file (again, if setup_sects == 0 the real value is 4.) +It should be loaded at address 0x10000 for Image/zImage kernels and +0x100000 for bzImage kernels. + +The kernel is a bzImage kernel if the protocol >= 2.00 and the 0x01 +bit (LOAD_HIGH) in the loadflags field is set:: + + is_bzImage = (protocol >= 0x0200) && (loadflags & 0x01); + load_address = is_bzImage ? 0x100000 : 0x10000; + +Note that Image/zImage kernels can be up to 512K in size, and thus use +the entire 0x10000-0x90000 range of memory. This means it is pretty +much a requirement for these kernels to load the real-mode part at +0x90000. bzImage kernels allow much more flexibility. + +Special Command Line Options +============================ + +If the command line provided by the boot loader is entered by the +user, the user may expect the following command line options to work. +They should normally not be deleted from the kernel command line even +though not all of them are actually meaningful to the kernel. Boot +loader authors who need additional command line options for the boot +loader itself should get them registered in +Documentation/admin-guide/kernel-parameters.rst to make sure they will not +conflict with actual kernel options now or in the future. + + vga= + here is either an integer (in C notation, either + decimal, octal, or hexadecimal) or one of the strings + "normal" (meaning 0xFFFF), "ext" (meaning 0xFFFE) or "ask" + (meaning 0xFFFD). This value should be entered into the + vid_mode field, as it is used by the kernel before the command + line is parsed. + + mem= + is an integer in C notation optionally followed by + (case insensitive) K, M, G, T, P or E (meaning << 10, << 20, + << 30, << 40, << 50 or << 60). This specifies the end of + memory to the kernel. This affects the possible placement of + an initrd, since an initrd should be placed near end of + memory. Note that this is an option to *both* the kernel and + the bootloader! + + initrd= + An initrd should be loaded. The meaning of is + obviously bootloader-dependent, and some boot loaders + (e.g. LILO) do not have such a command. + +In addition, some boot loaders add the following options to the +user-specified command line: + + BOOT_IMAGE= + The boot image which was loaded. Again, the meaning of + is obviously bootloader-dependent. + + auto + The kernel was booted without explicit user intervention. + +If these options are added by the boot loader, it is highly +recommended that they are located *first*, before the user-specified +or configuration-specified command line. Otherwise, "init=/bin/sh" +gets confused by the "auto" option. + + +Running the Kernel +================== + +The kernel is started by jumping to the kernel entry point, which is +located at *segment* offset 0x20 from the start of the real mode +kernel. This means that if you loaded your real-mode kernel code at +0x90000, the kernel entry point is 9020:0000. + +At entry, ds = es = ss should point to the start of the real-mode +kernel code (0x9000 if the code is loaded at 0x90000), sp should be +set up properly, normally pointing to the top of the heap, and +interrupts should be disabled. Furthermore, to guard against bugs in +the kernel, it is recommended that the boot loader sets fs = gs = ds = +es = ss. + +In our example from above, we would do:: + + /* Note: in the case of the "old" kernel protocol, base_ptr must + be == 0x90000 at this point; see the previous sample code */ + + seg = base_ptr >> 4; + + cli(); /* Enter with interrupts disabled! */ + + /* Set up the real-mode kernel stack */ + _SS = seg; + _SP = heap_end; + + _DS = _ES = _FS = _GS = seg; + jmp_far(seg+0x20, 0); /* Run the kernel */ + +If your boot sector accesses a floppy drive, it is recommended to +switch off the floppy motor before running the kernel, since the +kernel boot leaves interrupts off and thus the motor will not be +switched off, especially if the loaded kernel has the floppy driver as +a demand-loaded module! + + +Advanced Boot Loader Hooks +========================== + +If the boot loader runs in a particularly hostile environment (such as +LOADLIN, which runs under DOS) it may be impossible to follow the +standard memory location requirements. Such a boot loader may use the +following hooks that, if set, are invoked by the kernel at the +appropriate time. The use of these hooks should probably be +considered an absolutely last resort! + +IMPORTANT: All the hooks are required to preserve %esp, %ebp, %esi and +%edi across invocation. + + realmode_swtch: + A 16-bit real mode far subroutine invoked immediately before + entering protected mode. The default routine disables NMI, so + your routine should probably do so, too. + + code32_start: + A 32-bit flat-mode routine *jumped* to immediately after the + transition to protected mode, but before the kernel is + uncompressed. No segments, except CS, are guaranteed to be + set up (current kernels do, but older ones do not); you should + set them up to BOOT_DS (0x18) yourself. + + After completing your hook, you should jump to the address + that was in this field before your boot loader overwrote it + (relocated, if appropriate.) + + +32-bit Boot Protocol +==================== + +For machine with some new BIOS other than legacy BIOS, such as EFI, +LinuxBIOS, etc, and kexec, the 16-bit real mode setup code in kernel +based on legacy BIOS can not be used, so a 32-bit boot protocol needs +to be defined. + +In 32-bit boot protocol, the first step in loading a Linux kernel +should be to setup the boot parameters (struct boot_params, +traditionally known as "zero page"). The memory for struct boot_params +should be allocated and initialized to all zero. Then the setup header +from offset 0x01f1 of kernel image on should be loaded into struct +boot_params and examined. The end of setup header can be calculated as +follow:: + + 0x0202 + byte value at offset 0x0201 + +In addition to read/modify/write the setup header of the struct +boot_params as that of 16-bit boot protocol, the boot loader should +also fill the additional fields of the struct boot_params as that +described in zero-page.txt. + +After setting up the struct boot_params, the boot loader can load the +32/64-bit kernel in the same way as that of 16-bit boot protocol. + +In 32-bit boot protocol, the kernel is started by jumping to the +32-bit kernel entry point, which is the start address of loaded +32/64-bit kernel. + +At entry, the CPU must be in 32-bit protected mode with paging +disabled; a GDT must be loaded with the descriptors for selectors +__BOOT_CS(0x10) and __BOOT_DS(0x18); both descriptors must be 4G flat +segment; __BOOT_CS must have execute/read permission, and __BOOT_DS +must have read/write permission; CS must be __BOOT_CS and DS, ES, SS +must be __BOOT_DS; interrupt must be disabled; %esi must hold the base +address of the struct boot_params; %ebp, %edi and %ebx must be zero. + +64-bit Boot Protocol +==================== + +For machine with 64bit cpus and 64bit kernel, we could use 64bit bootloader +and we need a 64-bit boot protocol. + +In 64-bit boot protocol, the first step in loading a Linux kernel +should be to setup the boot parameters (struct boot_params, +traditionally known as "zero page"). The memory for struct boot_params +could be allocated anywhere (even above 4G) and initialized to all zero. +Then, the setup header at offset 0x01f1 of kernel image on should be +loaded into struct boot_params and examined. The end of setup header +can be calculated as follows:: + + 0x0202 + byte value at offset 0x0201 + +In addition to read/modify/write the setup header of the struct +boot_params as that of 16-bit boot protocol, the boot loader should +also fill the additional fields of the struct boot_params as described +in zero-page.txt. + +After setting up the struct boot_params, the boot loader can load +64-bit kernel in the same way as that of 16-bit boot protocol, but +kernel could be loaded above 4G. + +In 64-bit boot protocol, the kernel is started by jumping to the +64-bit kernel entry point, which is the start address of loaded +64-bit kernel plus 0x200. + +At entry, the CPU must be in 64-bit mode with paging enabled. +The range with setup_header.init_size from start address of loaded +kernel and zero page and command line buffer get ident mapping; +a GDT must be loaded with the descriptors for selectors +__BOOT_CS(0x10) and __BOOT_DS(0x18); both descriptors must be 4G flat +segment; __BOOT_CS must have execute/read permission, and __BOOT_DS +must have read/write permission; CS must be __BOOT_CS and DS, ES, SS +must be __BOOT_DS; interrupt must be disabled; %rsi must hold the base +address of the struct boot_params. + +EFI Handover Protocol +===================== + +This protocol allows boot loaders to defer initialisation to the EFI +boot stub. The boot loader is required to load the kernel/initrd(s) +from the boot media and jump to the EFI handover protocol entry point +which is hdr->handover_offset bytes from the beginning of +startup_{32,64}. + +The function prototype for the handover entry point looks like this:: + + efi_main(void *handle, efi_system_table_t *table, struct boot_params *bp) + +'handle' is the EFI image handle passed to the boot loader by the EFI +firmware, 'table' is the EFI system table - these are the first two +arguments of the "handoff state" as described in section 2.3 of the +UEFI specification. 'bp' is the boot loader-allocated boot params. + +The boot loader *must* fill out the following fields in bp:: + + - hdr.code32_start + - hdr.cmd_line_ptr + - hdr.ramdisk_image (if applicable) + - hdr.ramdisk_size (if applicable) + +All other fields should be zero. diff --git a/Documentation/x86/boot.txt b/Documentation/x86/boot.txt deleted file mode 100644 index 223e484a1304..000000000000 --- a/Documentation/x86/boot.txt +++ /dev/null @@ -1,1134 +0,0 @@ - THE LINUX/x86 BOOT PROTOCOL - --------------------------- - -On the x86 platform, the Linux kernel uses a rather complicated boot -convention. This has evolved partially due to historical aspects, as -well as the desire in the early days to have the kernel itself be a -bootable image, the complicated PC memory model and due to changed -expectations in the PC industry caused by the effective demise of -real-mode DOS as a mainstream operating system. - -Currently, the following versions of the Linux/x86 boot protocol exist. - -Old kernels: zImage/Image support only. Some very early kernels - may not even support a command line. - -Protocol 2.00: (Kernel 1.3.73) Added bzImage and initrd support, as - well as a formalized way to communicate between the - boot loader and the kernel. setup.S made relocatable, - although the traditional setup area still assumed - writable. - -Protocol 2.01: (Kernel 1.3.76) Added a heap overrun warning. - -Protocol 2.02: (Kernel 2.4.0-test3-pre3) New command line protocol. - Lower the conventional memory ceiling. No overwrite - of the traditional setup area, thus making booting - safe for systems which use the EBDA from SMM or 32-bit - BIOS entry points. zImage deprecated but still - supported. - -Protocol 2.03: (Kernel 2.4.18-pre1) Explicitly makes the highest possible - initrd address available to the bootloader. - -Protocol 2.04: (Kernel 2.6.14) Extend the syssize field to four bytes. - -Protocol 2.05: (Kernel 2.6.20) Make protected mode kernel relocatable. - Introduce relocatable_kernel and kernel_alignment fields. - -Protocol 2.06: (Kernel 2.6.22) Added a field that contains the size of - the boot command line. - -Protocol 2.07: (Kernel 2.6.24) Added paravirtualised boot protocol. - Introduced hardware_subarch and hardware_subarch_data - and KEEP_SEGMENTS flag in load_flags. - -Protocol 2.08: (Kernel 2.6.26) Added crc32 checksum and ELF format - payload. Introduced payload_offset and payload_length - fields to aid in locating the payload. - -Protocol 2.09: (Kernel 2.6.26) Added a field of 64-bit physical - pointer to single linked list of struct setup_data. - -Protocol 2.10: (Kernel 2.6.31) Added a protocol for relaxed alignment - beyond the kernel_alignment added, new init_size and - pref_address fields. Added extended boot loader IDs. - -Protocol 2.11: (Kernel 3.6) Added a field for offset of EFI handover - protocol entry point. - -Protocol 2.12: (Kernel 3.8) Added the xloadflags field and extension fields - to struct boot_params for loading bzImage and ramdisk - above 4G in 64bit. - -Protocol 2.13: (Kernel 3.14) Support 32- and 64-bit flags being set in - xloadflags to support booting a 64-bit kernel from 32-bit - EFI - -**** MEMORY LAYOUT - -The traditional memory map for the kernel loader, used for Image or -zImage kernels, typically looks like: - - | | -0A0000 +------------------------+ - | Reserved for BIOS | Do not use. Reserved for BIOS EBDA. -09A000 +------------------------+ - | Command line | - | Stack/heap | For use by the kernel real-mode code. -098000 +------------------------+ - | Kernel setup | The kernel real-mode code. -090200 +------------------------+ - | Kernel boot sector | The kernel legacy boot sector. -090000 +------------------------+ - | Protected-mode kernel | The bulk of the kernel image. -010000 +------------------------+ - | Boot loader | <- Boot sector entry point 0000:7C00 -001000 +------------------------+ - | Reserved for MBR/BIOS | -000800 +------------------------+ - | Typically used by MBR | -000600 +------------------------+ - | BIOS use only | -000000 +------------------------+ - - -When using bzImage, the protected-mode kernel was relocated to -0x100000 ("high memory"), and the kernel real-mode block (boot sector, -setup, and stack/heap) was made relocatable to any address between -0x10000 and end of low memory. Unfortunately, in protocols 2.00 and -2.01 the 0x90000+ memory range is still used internally by the kernel; -the 2.02 protocol resolves that problem. - -It is desirable to keep the "memory ceiling" -- the highest point in -low memory touched by the boot loader -- as low as possible, since -some newer BIOSes have begun to allocate some rather large amounts of -memory, called the Extended BIOS Data Area, near the top of low -memory. The boot loader should use the "INT 12h" BIOS call to verify -how much low memory is available. - -Unfortunately, if INT 12h reports that the amount of memory is too -low, there is usually nothing the boot loader can do but to report an -error to the user. The boot loader should therefore be designed to -take up as little space in low memory as it reasonably can. For -zImage or old bzImage kernels, which need data written into the -0x90000 segment, the boot loader should make sure not to use memory -above the 0x9A000 point; too many BIOSes will break above that point. - -For a modern bzImage kernel with boot protocol version >= 2.02, a -memory layout like the following is suggested: - - ~ ~ - | Protected-mode kernel | -100000 +------------------------+ - | I/O memory hole | -0A0000 +------------------------+ - | Reserved for BIOS | Leave as much as possible unused - ~ ~ - | Command line | (Can also be below the X+10000 mark) -X+10000 +------------------------+ - | Stack/heap | For use by the kernel real-mode code. -X+08000 +------------------------+ - | Kernel setup | The kernel real-mode code. - | Kernel boot sector | The kernel legacy boot sector. -X +------------------------+ - | Boot loader | <- Boot sector entry point 0000:7C00 -001000 +------------------------+ - | Reserved for MBR/BIOS | -000800 +------------------------+ - | Typically used by MBR | -000600 +------------------------+ - | BIOS use only | -000000 +------------------------+ - -... where the address X is as low as the design of the boot loader -permits. - - -**** THE REAL-MODE KERNEL HEADER - -In the following text, and anywhere in the kernel boot sequence, "a -sector" refers to 512 bytes. It is independent of the actual sector -size of the underlying medium. - -The first step in loading a Linux kernel should be to load the -real-mode code (boot sector and setup code) and then examine the -following header at offset 0x01f1. The real-mode code can total up to -32K, although the boot loader may choose to load only the first two -sectors (1K) and then examine the bootup sector size. - -The header looks like: - -Offset Proto Name Meaning -/Size - -01F1/1 ALL(1 setup_sects The size of the setup in sectors -01F2/2 ALL root_flags If set, the root is mounted readonly -01F4/4 2.04+(2 syssize The size of the 32-bit code in 16-byte paras -01F8/2 ALL ram_size DO NOT USE - for bootsect.S use only -01FA/2 ALL vid_mode Video mode control -01FC/2 ALL root_dev Default root device number -01FE/2 ALL boot_flag 0xAA55 magic number -0200/2 2.00+ jump Jump instruction -0202/4 2.00+ header Magic signature "HdrS" -0206/2 2.00+ version Boot protocol version supported -0208/4 2.00+ realmode_swtch Boot loader hook (see below) -020C/2 2.00+ start_sys_seg The load-low segment (0x1000) (obsolete) -020E/2 2.00+ kernel_version Pointer to kernel version string -0210/1 2.00+ type_of_loader Boot loader identifier -0211/1 2.00+ loadflags Boot protocol option flags -0212/2 2.00+ setup_move_size Move to high memory size (used with hooks) -0214/4 2.00+ code32_start Boot loader hook (see below) -0218/4 2.00+ ramdisk_image initrd load address (set by boot loader) -021C/4 2.00+ ramdisk_size initrd size (set by boot loader) -0220/4 2.00+ bootsect_kludge DO NOT USE - for bootsect.S use only -0224/2 2.01+ heap_end_ptr Free memory after setup end -0226/1 2.02+(3 ext_loader_ver Extended boot loader version -0227/1 2.02+(3 ext_loader_type Extended boot loader ID -0228/4 2.02+ cmd_line_ptr 32-bit pointer to the kernel command line -022C/4 2.03+ initrd_addr_max Highest legal initrd address -0230/4 2.05+ kernel_alignment Physical addr alignment required for kernel -0234/1 2.05+ relocatable_kernel Whether kernel is relocatable or not -0235/1 2.10+ min_alignment Minimum alignment, as a power of two -0236/2 2.12+ xloadflags Boot protocol option flags -0238/4 2.06+ cmdline_size Maximum size of the kernel command line -023C/4 2.07+ hardware_subarch Hardware subarchitecture -0240/8 2.07+ hardware_subarch_data Subarchitecture-specific data -0248/4 2.08+ payload_offset Offset of kernel payload -024C/4 2.08+ payload_length Length of kernel payload -0250/8 2.09+ setup_data 64-bit physical pointer to linked list - of struct setup_data -0258/8 2.10+ pref_address Preferred loading address -0260/4 2.10+ init_size Linear memory required during initialization -0264/4 2.11+ handover_offset Offset of handover entry point - -(1) For backwards compatibility, if the setup_sects field contains 0, the - real value is 4. - -(2) For boot protocol prior to 2.04, the upper two bytes of the syssize - field are unusable, which means the size of a bzImage kernel - cannot be determined. - -(3) Ignored, but safe to set, for boot protocols 2.02-2.09. - -If the "HdrS" (0x53726448) magic number is not found at offset 0x202, -the boot protocol version is "old". Loading an old kernel, the -following parameters should be assumed: - - Image type = zImage - initrd not supported - Real-mode kernel must be located at 0x90000. - -Otherwise, the "version" field contains the protocol version, -e.g. protocol version 2.01 will contain 0x0201 in this field. When -setting fields in the header, you must make sure only to set fields -supported by the protocol version in use. - - -**** DETAILS OF HEADER FIELDS - -For each field, some are information from the kernel to the bootloader -("read"), some are expected to be filled out by the bootloader -("write"), and some are expected to be read and modified by the -bootloader ("modify"). - -All general purpose boot loaders should write the fields marked -(obligatory). Boot loaders who want to load the kernel at a -nonstandard address should fill in the fields marked (reloc); other -boot loaders can ignore those fields. - -The byte order of all fields is littleendian (this is x86, after all.) - -Field name: setup_sects -Type: read -Offset/size: 0x1f1/1 -Protocol: ALL - - The size of the setup code in 512-byte sectors. If this field is - 0, the real value is 4. The real-mode code consists of the boot - sector (always one 512-byte sector) plus the setup code. - -Field name: root_flags -Type: modify (optional) -Offset/size: 0x1f2/2 -Protocol: ALL - - If this field is nonzero, the root defaults to readonly. The use of - this field is deprecated; use the "ro" or "rw" options on the - command line instead. - -Field name: syssize -Type: read -Offset/size: 0x1f4/4 (protocol 2.04+) 0x1f4/2 (protocol ALL) -Protocol: 2.04+ - - The size of the protected-mode code in units of 16-byte paragraphs. - For protocol versions older than 2.04 this field is only two bytes - wide, and therefore cannot be trusted for the size of a kernel if - the LOAD_HIGH flag is set. - -Field name: ram_size -Type: kernel internal -Offset/size: 0x1f8/2 -Protocol: ALL - - This field is obsolete. - -Field name: vid_mode -Type: modify (obligatory) -Offset/size: 0x1fa/2 - - Please see the section on SPECIAL COMMAND LINE OPTIONS. - -Field name: root_dev -Type: modify (optional) -Offset/size: 0x1fc/2 -Protocol: ALL - - The default root device device number. The use of this field is - deprecated, use the "root=" option on the command line instead. - -Field name: boot_flag -Type: read -Offset/size: 0x1fe/2 -Protocol: ALL - - Contains 0xAA55. This is the closest thing old Linux kernels have - to a magic number. - -Field name: jump -Type: read -Offset/size: 0x200/2 -Protocol: 2.00+ - - Contains an x86 jump instruction, 0xEB followed by a signed offset - relative to byte 0x202. This can be used to determine the size of - the header. - -Field name: header -Type: read -Offset/size: 0x202/4 -Protocol: 2.00+ - - Contains the magic number "HdrS" (0x53726448). - -Field name: version -Type: read -Offset/size: 0x206/2 -Protocol: 2.00+ - - Contains the boot protocol version, in (major << 8)+minor format, - e.g. 0x0204 for version 2.04, and 0x0a11 for a hypothetical version - 10.17. - -Field name: realmode_swtch -Type: modify (optional) -Offset/size: 0x208/4 -Protocol: 2.00+ - - Boot loader hook (see ADVANCED BOOT LOADER HOOKS below.) - -Field name: start_sys_seg -Type: read -Offset/size: 0x20c/2 -Protocol: 2.00+ - - The load low segment (0x1000). Obsolete. - -Field name: kernel_version -Type: read -Offset/size: 0x20e/2 -Protocol: 2.00+ - - If set to a nonzero value, contains a pointer to a NUL-terminated - human-readable kernel version number string, less 0x200. This can - be used to display the kernel version to the user. This value - should be less than (0x200*setup_sects). - - For example, if this value is set to 0x1c00, the kernel version - number string can be found at offset 0x1e00 in the kernel file. - This is a valid value if and only if the "setup_sects" field - contains the value 15 or higher, as: - - 0x1c00 < 15*0x200 (= 0x1e00) but - 0x1c00 >= 14*0x200 (= 0x1c00) - - 0x1c00 >> 9 = 14, so the minimum value for setup_secs is 15. - -Field name: type_of_loader -Type: write (obligatory) -Offset/size: 0x210/1 -Protocol: 2.00+ - - If your boot loader has an assigned id (see table below), enter - 0xTV here, where T is an identifier for the boot loader and V is - a version number. Otherwise, enter 0xFF here. - - For boot loader IDs above T = 0xD, write T = 0xE to this field and - write the extended ID minus 0x10 to the ext_loader_type field. - Similarly, the ext_loader_ver field can be used to provide more than - four bits for the bootloader version. - - For example, for T = 0x15, V = 0x234, write: - - type_of_loader <- 0xE4 - ext_loader_type <- 0x05 - ext_loader_ver <- 0x23 - - Assigned boot loader ids (hexadecimal): - - 0 LILO (0x00 reserved for pre-2.00 bootloader) - 1 Loadlin - 2 bootsect-loader (0x20, all other values reserved) - 3 Syslinux - 4 Etherboot/gPXE/iPXE - 5 ELILO - 7 GRUB - 8 U-Boot - 9 Xen - A Gujin - B Qemu - C Arcturus Networks uCbootloader - D kexec-tools - E Extended (see ext_loader_type) - F Special (0xFF = undefined) - 10 Reserved - 11 Minimal Linux Bootloader - 12 OVMF UEFI virtualization stack - - Please contact if you need a bootloader ID - value assigned. - -Field name: loadflags -Type: modify (obligatory) -Offset/size: 0x211/1 -Protocol: 2.00+ - - This field is a bitmask. - - Bit 0 (read): LOADED_HIGH - - If 0, the protected-mode code is loaded at 0x10000. - - If 1, the protected-mode code is loaded at 0x100000. - - Bit 1 (kernel internal): KASLR_FLAG - - Used internally by the compressed kernel to communicate - KASLR status to kernel proper. - If 1, KASLR enabled. - If 0, KASLR disabled. - - Bit 5 (write): QUIET_FLAG - - If 0, print early messages. - - If 1, suppress early messages. - This requests to the kernel (decompressor and early - kernel) to not write early messages that require - accessing the display hardware directly. - - Bit 6 (write): KEEP_SEGMENTS - Protocol: 2.07+ - - If 0, reload the segment registers in the 32bit entry point. - - If 1, do not reload the segment registers in the 32bit entry point. - Assume that %cs %ds %ss %es are all set to flat segments with - a base of 0 (or the equivalent for their environment). - - Bit 7 (write): CAN_USE_HEAP - Set this bit to 1 to indicate that the value entered in the - heap_end_ptr is valid. If this field is clear, some setup code - functionality will be disabled. - -Field name: setup_move_size -Type: modify (obligatory) -Offset/size: 0x212/2 -Protocol: 2.00-2.01 - - When using protocol 2.00 or 2.01, if the real mode kernel is not - loaded at 0x90000, it gets moved there later in the loading - sequence. Fill in this field if you want additional data (such as - the kernel command line) moved in addition to the real-mode kernel - itself. - - The unit is bytes starting with the beginning of the boot sector. - - This field is can be ignored when the protocol is 2.02 or higher, or - if the real-mode code is loaded at 0x90000. - -Field name: code32_start -Type: modify (optional, reloc) -Offset/size: 0x214/4 -Protocol: 2.00+ - - The address to jump to in protected mode. This defaults to the load - address of the kernel, and can be used by the boot loader to - determine the proper load address. - - This field can be modified for two purposes: - - 1. as a boot loader hook (see ADVANCED BOOT LOADER HOOKS below.) - - 2. if a bootloader which does not install a hook loads a - relocatable kernel at a nonstandard address it will have to modify - this field to point to the load address. - -Field name: ramdisk_image -Type: write (obligatory) -Offset/size: 0x218/4 -Protocol: 2.00+ - - The 32-bit linear address of the initial ramdisk or ramfs. Leave at - zero if there is no initial ramdisk/ramfs. - -Field name: ramdisk_size -Type: write (obligatory) -Offset/size: 0x21c/4 -Protocol: 2.00+ - - Size of the initial ramdisk or ramfs. Leave at zero if there is no - initial ramdisk/ramfs. - -Field name: bootsect_kludge -Type: kernel internal -Offset/size: 0x220/4 -Protocol: 2.00+ - - This field is obsolete. - -Field name: heap_end_ptr -Type: write (obligatory) -Offset/size: 0x224/2 -Protocol: 2.01+ - - Set this field to the offset (from the beginning of the real-mode - code) of the end of the setup stack/heap, minus 0x0200. - -Field name: ext_loader_ver -Type: write (optional) -Offset/size: 0x226/1 -Protocol: 2.02+ - - This field is used as an extension of the version number in the - type_of_loader field. The total version number is considered to be - (type_of_loader & 0x0f) + (ext_loader_ver << 4). - - The use of this field is boot loader specific. If not written, it - is zero. - - Kernels prior to 2.6.31 did not recognize this field, but it is safe - to write for protocol version 2.02 or higher. - -Field name: ext_loader_type -Type: write (obligatory if (type_of_loader & 0xf0) == 0xe0) -Offset/size: 0x227/1 -Protocol: 2.02+ - - This field is used as an extension of the type number in - type_of_loader field. If the type in type_of_loader is 0xE, then - the actual type is (ext_loader_type + 0x10). - - This field is ignored if the type in type_of_loader is not 0xE. - - Kernels prior to 2.6.31 did not recognize this field, but it is safe - to write for protocol version 2.02 or higher. - -Field name: cmd_line_ptr -Type: write (obligatory) -Offset/size: 0x228/4 -Protocol: 2.02+ - - Set this field to the linear address of the kernel command line. - The kernel command line can be located anywhere between the end of - the setup heap and 0xA0000; it does not have to be located in the - same 64K segment as the real-mode code itself. - - Fill in this field even if your boot loader does not support a - command line, in which case you can point this to an empty string - (or better yet, to the string "auto".) If this field is left at - zero, the kernel will assume that your boot loader does not support - the 2.02+ protocol. - -Field name: initrd_addr_max -Type: read -Offset/size: 0x22c/4 -Protocol: 2.03+ - - The maximum address that may be occupied by the initial - ramdisk/ramfs contents. For boot protocols 2.02 or earlier, this - field is not present, and the maximum address is 0x37FFFFFF. (This - address is defined as the address of the highest safe byte, so if - your ramdisk is exactly 131072 bytes long and this field is - 0x37FFFFFF, you can start your ramdisk at 0x37FE0000.) - -Field name: kernel_alignment -Type: read/modify (reloc) -Offset/size: 0x230/4 -Protocol: 2.05+ (read), 2.10+ (modify) - - Alignment unit required by the kernel (if relocatable_kernel is - true.) A relocatable kernel that is loaded at an alignment - incompatible with the value in this field will be realigned during - kernel initialization. - - Starting with protocol version 2.10, this reflects the kernel - alignment preferred for optimal performance; it is possible for the - loader to modify this field to permit a lesser alignment. See the - min_alignment and pref_address field below. - -Field name: relocatable_kernel -Type: read (reloc) -Offset/size: 0x234/1 -Protocol: 2.05+ - - If this field is nonzero, the protected-mode part of the kernel can - be loaded at any address that satisfies the kernel_alignment field. - After loading, the boot loader must set the code32_start field to - point to the loaded code, or to a boot loader hook. - -Field name: min_alignment -Type: read (reloc) -Offset/size: 0x235/1 -Protocol: 2.10+ - - This field, if nonzero, indicates as a power of two the minimum - alignment required, as opposed to preferred, by the kernel to boot. - If a boot loader makes use of this field, it should update the - kernel_alignment field with the alignment unit desired; typically: - - kernel_alignment = 1 << min_alignment - - There may be a considerable performance cost with an excessively - misaligned kernel. Therefore, a loader should typically try each - power-of-two alignment from kernel_alignment down to this alignment. - -Field name: xloadflags -Type: read -Offset/size: 0x236/2 -Protocol: 2.12+ - - This field is a bitmask. - - Bit 0 (read): XLF_KERNEL_64 - - If 1, this kernel has the legacy 64-bit entry point at 0x200. - - Bit 1 (read): XLF_CAN_BE_LOADED_ABOVE_4G - - If 1, kernel/boot_params/cmdline/ramdisk can be above 4G. - - Bit 2 (read): XLF_EFI_HANDOVER_32 - - If 1, the kernel supports the 32-bit EFI handoff entry point - given at handover_offset. - - Bit 3 (read): XLF_EFI_HANDOVER_64 - - If 1, the kernel supports the 64-bit EFI handoff entry point - given at handover_offset + 0x200. - - Bit 4 (read): XLF_EFI_KEXEC - - If 1, the kernel supports kexec EFI boot with EFI runtime support. - -Field name: cmdline_size -Type: read -Offset/size: 0x238/4 -Protocol: 2.06+ - - The maximum size of the command line without the terminating - zero. This means that the command line can contain at most - cmdline_size characters. With protocol version 2.05 and earlier, the - maximum size was 255. - -Field name: hardware_subarch -Type: write (optional, defaults to x86/PC) -Offset/size: 0x23c/4 -Protocol: 2.07+ - - In a paravirtualized environment the hardware low level architectural - pieces such as interrupt handling, page table handling, and - accessing process control registers needs to be done differently. - - This field allows the bootloader to inform the kernel we are in one - one of those environments. - - 0x00000000 The default x86/PC environment - 0x00000001 lguest - 0x00000002 Xen - 0x00000003 Moorestown MID - 0x00000004 CE4100 TV Platform - -Field name: hardware_subarch_data -Type: write (subarch-dependent) -Offset/size: 0x240/8 -Protocol: 2.07+ - - A pointer to data that is specific to hardware subarch - This field is currently unused for the default x86/PC environment, - do not modify. - -Field name: payload_offset -Type: read -Offset/size: 0x248/4 -Protocol: 2.08+ - - If non-zero then this field contains the offset from the beginning - of the protected-mode code to the payload. - - The payload may be compressed. The format of both the compressed and - uncompressed data should be determined using the standard magic - numbers. The currently supported compression formats are gzip - (magic numbers 1F 8B or 1F 9E), bzip2 (magic number 42 5A), LZMA - (magic number 5D 00), XZ (magic number FD 37), and LZ4 (magic number - 02 21). The uncompressed payload is currently always ELF (magic - number 7F 45 4C 46). - -Field name: payload_length -Type: read -Offset/size: 0x24c/4 -Protocol: 2.08+ - - The length of the payload. - -Field name: setup_data -Type: write (special) -Offset/size: 0x250/8 -Protocol: 2.09+ - - The 64-bit physical pointer to NULL terminated single linked list of - struct setup_data. This is used to define a more extensible boot - parameters passing mechanism. The definition of struct setup_data is - as follow: - - struct setup_data { - u64 next; - u32 type; - u32 len; - u8 data[0]; - }; - - Where, the next is a 64-bit physical pointer to the next node of - linked list, the next field of the last node is 0; the type is used - to identify the contents of data; the len is the length of data - field; the data holds the real payload. - - This list may be modified at a number of points during the bootup - process. Therefore, when modifying this list one should always make - sure to consider the case where the linked list already contains - entries. - -Field name: pref_address -Type: read (reloc) -Offset/size: 0x258/8 -Protocol: 2.10+ - - This field, if nonzero, represents a preferred load address for the - kernel. A relocating bootloader should attempt to load at this - address if possible. - - A non-relocatable kernel will unconditionally move itself and to run - at this address. - -Field name: init_size -Type: read -Offset/size: 0x260/4 - - This field indicates the amount of linear contiguous memory starting - at the kernel runtime start address that the kernel needs before it - is capable of examining its memory map. This is not the same thing - as the total amount of memory the kernel needs to boot, but it can - be used by a relocating boot loader to help select a safe load - address for the kernel. - - The kernel runtime start address is determined by the following algorithm: - - if (relocatable_kernel) - runtime_start = align_up(load_address, kernel_alignment) - else - runtime_start = pref_address - -Field name: handover_offset -Type: read -Offset/size: 0x264/4 - - This field is the offset from the beginning of the kernel image to - the EFI handover protocol entry point. Boot loaders using the EFI - handover protocol to boot the kernel should jump to this offset. - - See EFI HANDOVER PROTOCOL below for more details. - - -**** THE IMAGE CHECKSUM - -From boot protocol version 2.08 onwards the CRC-32 is calculated over -the entire file using the characteristic polynomial 0x04C11DB7 and an -initial remainder of 0xffffffff. The checksum is appended to the -file; therefore the CRC of the file up to the limit specified in the -syssize field of the header is always 0. - - -**** THE KERNEL COMMAND LINE - -The kernel command line has become an important way for the boot -loader to communicate with the kernel. Some of its options are also -relevant to the boot loader itself, see "special command line options" -below. - -The kernel command line is a null-terminated string. The maximum -length can be retrieved from the field cmdline_size. Before protocol -version 2.06, the maximum was 255 characters. A string that is too -long will be automatically truncated by the kernel. - -If the boot protocol version is 2.02 or later, the address of the -kernel command line is given by the header field cmd_line_ptr (see -above.) This address can be anywhere between the end of the setup -heap and 0xA0000. - -If the protocol version is *not* 2.02 or higher, the kernel -command line is entered using the following protocol: - - At offset 0x0020 (word), "cmd_line_magic", enter the magic - number 0xA33F. - - At offset 0x0022 (word), "cmd_line_offset", enter the offset - of the kernel command line (relative to the start of the - real-mode kernel). - - The kernel command line *must* be within the memory region - covered by setup_move_size, so you may need to adjust this - field. - - -**** MEMORY LAYOUT OF THE REAL-MODE CODE - -The real-mode code requires a stack/heap to be set up, as well as -memory allocated for the kernel command line. This needs to be done -in the real-mode accessible memory in bottom megabyte. - -It should be noted that modern machines often have a sizable Extended -BIOS Data Area (EBDA). As a result, it is advisable to use as little -of the low megabyte as possible. - -Unfortunately, under the following circumstances the 0x90000 memory -segment has to be used: - - - When loading a zImage kernel ((loadflags & 0x01) == 0). - - When loading a 2.01 or earlier boot protocol kernel. - - -> For the 2.00 and 2.01 boot protocols, the real-mode code - can be loaded at another address, but it is internally - relocated to 0x90000. For the "old" protocol, the - real-mode code must be loaded at 0x90000. - -When loading at 0x90000, avoid using memory above 0x9a000. - -For boot protocol 2.02 or higher, the command line does not have to be -located in the same 64K segment as the real-mode setup code; it is -thus permitted to give the stack/heap the full 64K segment and locate -the command line above it. - -The kernel command line should not be located below the real-mode -code, nor should it be located in high memory. - - -**** SAMPLE BOOT CONFIGURATION - -As a sample configuration, assume the following layout of the real -mode segment: - - When loading below 0x90000, use the entire segment: - - 0x0000-0x7fff Real mode kernel - 0x8000-0xdfff Stack and heap - 0xe000-0xffff Kernel command line - - When loading at 0x90000 OR the protocol version is 2.01 or earlier: - - 0x0000-0x7fff Real mode kernel - 0x8000-0x97ff Stack and heap - 0x9800-0x9fff Kernel command line - -Such a boot loader should enter the following fields in the header: - - unsigned long base_ptr; /* base address for real-mode segment */ - - if ( setup_sects == 0 ) { - setup_sects = 4; - } - - if ( protocol >= 0x0200 ) { - type_of_loader = ; - if ( loading_initrd ) { - ramdisk_image = ; - ramdisk_size = ; - } - - if ( protocol >= 0x0202 && loadflags & 0x01 ) - heap_end = 0xe000; - else - heap_end = 0x9800; - - if ( protocol >= 0x0201 ) { - heap_end_ptr = heap_end - 0x200; - loadflags |= 0x80; /* CAN_USE_HEAP */ - } - - if ( protocol >= 0x0202 ) { - cmd_line_ptr = base_ptr + heap_end; - strcpy(cmd_line_ptr, cmdline); - } else { - cmd_line_magic = 0xA33F; - cmd_line_offset = heap_end; - setup_move_size = heap_end + strlen(cmdline)+1; - strcpy(base_ptr+cmd_line_offset, cmdline); - } - } else { - /* Very old kernel */ - - heap_end = 0x9800; - - cmd_line_magic = 0xA33F; - cmd_line_offset = heap_end; - - /* A very old kernel MUST have its real-mode code - loaded at 0x90000 */ - - if ( base_ptr != 0x90000 ) { - /* Copy the real-mode kernel */ - memcpy(0x90000, base_ptr, (setup_sects+1)*512); - base_ptr = 0x90000; /* Relocated */ - } - - strcpy(0x90000+cmd_line_offset, cmdline); - - /* It is recommended to clear memory up to the 32K mark */ - memset(0x90000 + (setup_sects+1)*512, 0, - (64-(setup_sects+1))*512); - } - - -**** LOADING THE REST OF THE KERNEL - -The 32-bit (non-real-mode) kernel starts at offset (setup_sects+1)*512 -in the kernel file (again, if setup_sects == 0 the real value is 4.) -It should be loaded at address 0x10000 for Image/zImage kernels and -0x100000 for bzImage kernels. - -The kernel is a bzImage kernel if the protocol >= 2.00 and the 0x01 -bit (LOAD_HIGH) in the loadflags field is set: - - is_bzImage = (protocol >= 0x0200) && (loadflags & 0x01); - load_address = is_bzImage ? 0x100000 : 0x10000; - -Note that Image/zImage kernels can be up to 512K in size, and thus use -the entire 0x10000-0x90000 range of memory. This means it is pretty -much a requirement for these kernels to load the real-mode part at -0x90000. bzImage kernels allow much more flexibility. - - -**** SPECIAL COMMAND LINE OPTIONS - -If the command line provided by the boot loader is entered by the -user, the user may expect the following command line options to work. -They should normally not be deleted from the kernel command line even -though not all of them are actually meaningful to the kernel. Boot -loader authors who need additional command line options for the boot -loader itself should get them registered in -Documentation/admin-guide/kernel-parameters.rst to make sure they will not -conflict with actual kernel options now or in the future. - - vga= - here is either an integer (in C notation, either - decimal, octal, or hexadecimal) or one of the strings - "normal" (meaning 0xFFFF), "ext" (meaning 0xFFFE) or "ask" - (meaning 0xFFFD). This value should be entered into the - vid_mode field, as it is used by the kernel before the command - line is parsed. - - mem= - is an integer in C notation optionally followed by - (case insensitive) K, M, G, T, P or E (meaning << 10, << 20, - << 30, << 40, << 50 or << 60). This specifies the end of - memory to the kernel. This affects the possible placement of - an initrd, since an initrd should be placed near end of - memory. Note that this is an option to *both* the kernel and - the bootloader! - - initrd= - An initrd should be loaded. The meaning of is - obviously bootloader-dependent, and some boot loaders - (e.g. LILO) do not have such a command. - -In addition, some boot loaders add the following options to the -user-specified command line: - - BOOT_IMAGE= - The boot image which was loaded. Again, the meaning of - is obviously bootloader-dependent. - - auto - The kernel was booted without explicit user intervention. - -If these options are added by the boot loader, it is highly -recommended that they are located *first*, before the user-specified -or configuration-specified command line. Otherwise, "init=/bin/sh" -gets confused by the "auto" option. - - -**** RUNNING THE KERNEL - -The kernel is started by jumping to the kernel entry point, which is -located at *segment* offset 0x20 from the start of the real mode -kernel. This means that if you loaded your real-mode kernel code at -0x90000, the kernel entry point is 9020:0000. - -At entry, ds = es = ss should point to the start of the real-mode -kernel code (0x9000 if the code is loaded at 0x90000), sp should be -set up properly, normally pointing to the top of the heap, and -interrupts should be disabled. Furthermore, to guard against bugs in -the kernel, it is recommended that the boot loader sets fs = gs = ds = -es = ss. - -In our example from above, we would do: - - /* Note: in the case of the "old" kernel protocol, base_ptr must - be == 0x90000 at this point; see the previous sample code */ - - seg = base_ptr >> 4; - - cli(); /* Enter with interrupts disabled! */ - - /* Set up the real-mode kernel stack */ - _SS = seg; - _SP = heap_end; - - _DS = _ES = _FS = _GS = seg; - jmp_far(seg+0x20, 0); /* Run the kernel */ - -If your boot sector accesses a floppy drive, it is recommended to -switch off the floppy motor before running the kernel, since the -kernel boot leaves interrupts off and thus the motor will not be -switched off, especially if the loaded kernel has the floppy driver as -a demand-loaded module! - - -**** ADVANCED BOOT LOADER HOOKS - -If the boot loader runs in a particularly hostile environment (such as -LOADLIN, which runs under DOS) it may be impossible to follow the -standard memory location requirements. Such a boot loader may use the -following hooks that, if set, are invoked by the kernel at the -appropriate time. The use of these hooks should probably be -considered an absolutely last resort! - -IMPORTANT: All the hooks are required to preserve %esp, %ebp, %esi and -%edi across invocation. - - realmode_swtch: - A 16-bit real mode far subroutine invoked immediately before - entering protected mode. The default routine disables NMI, so - your routine should probably do so, too. - - code32_start: - A 32-bit flat-mode routine *jumped* to immediately after the - transition to protected mode, but before the kernel is - uncompressed. No segments, except CS, are guaranteed to be - set up (current kernels do, but older ones do not); you should - set them up to BOOT_DS (0x18) yourself. - - After completing your hook, you should jump to the address - that was in this field before your boot loader overwrote it - (relocated, if appropriate.) - - -**** 32-bit BOOT PROTOCOL - -For machine with some new BIOS other than legacy BIOS, such as EFI, -LinuxBIOS, etc, and kexec, the 16-bit real mode setup code in kernel -based on legacy BIOS can not be used, so a 32-bit boot protocol needs -to be defined. - -In 32-bit boot protocol, the first step in loading a Linux kernel -should be to setup the boot parameters (struct boot_params, -traditionally known as "zero page"). The memory for struct boot_params -should be allocated and initialized to all zero. Then the setup header -from offset 0x01f1 of kernel image on should be loaded into struct -boot_params and examined. The end of setup header can be calculated as -follow: - - 0x0202 + byte value at offset 0x0201 - -In addition to read/modify/write the setup header of the struct -boot_params as that of 16-bit boot protocol, the boot loader should -also fill the additional fields of the struct boot_params as that -described in zero-page.txt. - -After setting up the struct boot_params, the boot loader can load the -32/64-bit kernel in the same way as that of 16-bit boot protocol. - -In 32-bit boot protocol, the kernel is started by jumping to the -32-bit kernel entry point, which is the start address of loaded -32/64-bit kernel. - -At entry, the CPU must be in 32-bit protected mode with paging -disabled; a GDT must be loaded with the descriptors for selectors -__BOOT_CS(0x10) and __BOOT_DS(0x18); both descriptors must be 4G flat -segment; __BOOT_CS must have execute/read permission, and __BOOT_DS -must have read/write permission; CS must be __BOOT_CS and DS, ES, SS -must be __BOOT_DS; interrupt must be disabled; %esi must hold the base -address of the struct boot_params; %ebp, %edi and %ebx must be zero. - -**** 64-bit BOOT PROTOCOL - -For machine with 64bit cpus and 64bit kernel, we could use 64bit bootloader -and we need a 64-bit boot protocol. - -In 64-bit boot protocol, the first step in loading a Linux kernel -should be to setup the boot parameters (struct boot_params, -traditionally known as "zero page"). The memory for struct boot_params -could be allocated anywhere (even above 4G) and initialized to all zero. -Then, the setup header at offset 0x01f1 of kernel image on should be -loaded into struct boot_params and examined. The end of setup header -can be calculated as follows: - - 0x0202 + byte value at offset 0x0201 - -In addition to read/modify/write the setup header of the struct -boot_params as that of 16-bit boot protocol, the boot loader should -also fill the additional fields of the struct boot_params as described -in zero-page.txt. - -After setting up the struct boot_params, the boot loader can load -64-bit kernel in the same way as that of 16-bit boot protocol, but -kernel could be loaded above 4G. - -In 64-bit boot protocol, the kernel is started by jumping to the -64-bit kernel entry point, which is the start address of loaded -64-bit kernel plus 0x200. - -At entry, the CPU must be in 64-bit mode with paging enabled. -The range with setup_header.init_size from start address of loaded -kernel and zero page and command line buffer get ident mapping; -a GDT must be loaded with the descriptors for selectors -__BOOT_CS(0x10) and __BOOT_DS(0x18); both descriptors must be 4G flat -segment; __BOOT_CS must have execute/read permission, and __BOOT_DS -must have read/write permission; CS must be __BOOT_CS and DS, ES, SS -must be __BOOT_DS; interrupt must be disabled; %rsi must hold the base -address of the struct boot_params. - -**** EFI HANDOVER PROTOCOL - -This protocol allows boot loaders to defer initialisation to the EFI -boot stub. The boot loader is required to load the kernel/initrd(s) -from the boot media and jump to the EFI handover protocol entry point -which is hdr->handover_offset bytes from the beginning of -startup_{32,64}. - -The function prototype for the handover entry point looks like this, - - efi_main(void *handle, efi_system_table_t *table, struct boot_params *bp) - -'handle' is the EFI image handle passed to the boot loader by the EFI -firmware, 'table' is the EFI system table - these are the first two -arguments of the "handoff state" as described in section 2.3 of the -UEFI specification. 'bp' is the boot loader-allocated boot params. - -The boot loader *must* fill out the following fields in bp, - - o hdr.code32_start - o hdr.cmd_line_ptr - o hdr.ramdisk_image (if applicable) - o hdr.ramdisk_size (if applicable) - -All other fields should be zero. diff --git a/Documentation/x86/index.rst b/Documentation/x86/index.rst index 9f34545a9c52..d7fc8efac192 100644 --- a/Documentation/x86/index.rst +++ b/Documentation/x86/index.rst @@ -7,3 +7,5 @@ x86-specific Documentation .. toctree:: :maxdepth: 2 :numbered: + + boot -- cgit v1.2.3 From 848942cb2ef584752d7c41594b2cc91229fe7f01 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:17 +0800 Subject: Documentation: x86: convert topology.txt to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/index.rst | 1 + Documentation/x86/topology.rst | 221 +++++++++++++++++++++++++++++++++++++++++ Documentation/x86/topology.txt | 217 ---------------------------------------- 3 files changed, 222 insertions(+), 217 deletions(-) create mode 100644 Documentation/x86/topology.rst delete mode 100644 Documentation/x86/topology.txt (limited to 'Documentation') diff --git a/Documentation/x86/index.rst b/Documentation/x86/index.rst index d7fc8efac192..da89bf0ad69f 100644 --- a/Documentation/x86/index.rst +++ b/Documentation/x86/index.rst @@ -9,3 +9,4 @@ x86-specific Documentation :numbered: boot + topology diff --git a/Documentation/x86/topology.rst b/Documentation/x86/topology.rst new file mode 100644 index 000000000000..5176e5315faa --- /dev/null +++ b/Documentation/x86/topology.rst @@ -0,0 +1,221 @@ +.. SPDX-License-Identifier: GPL-2.0 + +============ +x86 Topology +============ + +This documents and clarifies the main aspects of x86 topology modelling and +representation in the kernel. Update/change when doing changes to the +respective code. + +The architecture-agnostic topology definitions are in +Documentation/cputopology.txt. This file holds x86-specific +differences/specialities which must not necessarily apply to the generic +definitions. Thus, the way to read up on Linux topology on x86 is to start +with the generic one and look at this one in parallel for the x86 specifics. + +Needless to say, code should use the generic functions - this file is *only* +here to *document* the inner workings of x86 topology. + +Started by Thomas Gleixner and Borislav Petkov . + +The main aim of the topology facilities is to present adequate interfaces to +code which needs to know/query/use the structure of the running system wrt +threads, cores, packages, etc. + +The kernel does not care about the concept of physical sockets because a +socket has no relevance to software. It's an electromechanical component. In +the past a socket always contained a single package (see below), but with the +advent of Multi Chip Modules (MCM) a socket can hold more than one package. So +there might be still references to sockets in the code, but they are of +historical nature and should be cleaned up. + +The topology of a system is described in the units of: + + - packages + - cores + - threads + +Package +======= +Packages contain a number of cores plus shared resources, e.g. DRAM +controller, shared caches etc. + +AMD nomenclature for package is 'Node'. + +Package-related topology information in the kernel: + + - cpuinfo_x86.x86_max_cores: + + The number of cores in a package. This information is retrieved via CPUID. + + - cpuinfo_x86.phys_proc_id: + + The physical ID of the package. This information is retrieved via CPUID + and deduced from the APIC IDs of the cores in the package. + + - cpuinfo_x86.logical_id: + + The logical ID of the package. As we do not trust BIOSes to enumerate the + packages in a consistent way, we introduced the concept of logical package + ID so we can sanely calculate the number of maximum possible packages in + the system and have the packages enumerated linearly. + + - topology_max_packages(): + + The maximum possible number of packages in the system. Helpful for per + package facilities to preallocate per package information. + + - cpu_llc_id: + + A per-CPU variable containing: + + - On Intel, the first APIC ID of the list of CPUs sharing the Last Level + Cache + + - On AMD, the Node ID or Core Complex ID containing the Last Level + Cache. In general, it is a number identifying an LLC uniquely on the + system. + +Cores +===== +A core consists of 1 or more threads. It does not matter whether the threads +are SMT- or CMT-type threads. + +AMDs nomenclature for a CMT core is "Compute Unit". The kernel always uses +"core". + +Core-related topology information in the kernel: + + - smp_num_siblings: + + The number of threads in a core. The number of threads in a package can be + calculated by:: + + threads_per_package = cpuinfo_x86.x86_max_cores * smp_num_siblings + + +Threads +======= +A thread is a single scheduling unit. It's the equivalent to a logical Linux +CPU. + +AMDs nomenclature for CMT threads is "Compute Unit Core". The kernel always +uses "thread". + +Thread-related topology information in the kernel: + + - topology_core_cpumask(): + + The cpumask contains all online threads in the package to which a thread + belongs. + + The number of online threads is also printed in /proc/cpuinfo "siblings." + + - topology_sibling_cpumask(): + + The cpumask contains all online threads in the core to which a thread + belongs. + + - topology_logical_package_id(): + + The logical package ID to which a thread belongs. + + - topology_physical_package_id(): + + The physical package ID to which a thread belongs. + + - topology_core_id(); + + The ID of the core to which a thread belongs. It is also printed in /proc/cpuinfo + "core_id." + + + +System topology examples +======================== + +.. note:: + The alternative Linux CPU enumeration depends on how the BIOS enumerates the + threads. Many BIOSes enumerate all threads 0 first and then all threads 1. + That has the "advantage" that the logical Linux CPU numbers of threads 0 stay + the same whether threads are enabled or not. That's merely an implementation + detail and has no practical impact. + +1) Single Package, Single Core:: + + [package 0] -> [core 0] -> [thread 0] -> Linux CPU 0 + +2) Single Package, Dual Core + + a) One thread per core:: + + [package 0] -> [core 0] -> [thread 0] -> Linux CPU 0 + -> [core 1] -> [thread 0] -> Linux CPU 1 + + b) Two threads per core:: + + [package 0] -> [core 0] -> [thread 0] -> Linux CPU 0 + -> [thread 1] -> Linux CPU 1 + -> [core 1] -> [thread 0] -> Linux CPU 2 + -> [thread 1] -> Linux CPU 3 + + Alternative enumeration:: + + [package 0] -> [core 0] -> [thread 0] -> Linux CPU 0 + -> [thread 1] -> Linux CPU 2 + -> [core 1] -> [thread 0] -> Linux CPU 1 + -> [thread 1] -> Linux CPU 3 + + AMD nomenclature for CMT systems:: + + [node 0] -> [Compute Unit 0] -> [Compute Unit Core 0] -> Linux CPU 0 + -> [Compute Unit Core 1] -> Linux CPU 1 + -> [Compute Unit 1] -> [Compute Unit Core 0] -> Linux CPU 2 + -> [Compute Unit Core 1] -> Linux CPU 3 + +4) Dual Package, Dual Core + + a) One thread per core:: + + [package 0] -> [core 0] -> [thread 0] -> Linux CPU 0 + -> [core 1] -> [thread 0] -> Linux CPU 1 + + [package 1] -> [core 0] -> [thread 0] -> Linux CPU 2 + -> [core 1] -> [thread 0] -> Linux CPU 3 + + b) Two threads per core:: + + [package 0] -> [core 0] -> [thread 0] -> Linux CPU 0 + -> [thread 1] -> Linux CPU 1 + -> [core 1] -> [thread 0] -> Linux CPU 2 + -> [thread 1] -> Linux CPU 3 + + [package 1] -> [core 0] -> [thread 0] -> Linux CPU 4 + -> [thread 1] -> Linux CPU 5 + -> [core 1] -> [thread 0] -> Linux CPU 6 + -> [thread 1] -> Linux CPU 7 + + Alternative enumeration:: + + [package 0] -> [core 0] -> [thread 0] -> Linux CPU 0 + -> [thread 1] -> Linux CPU 4 + -> [core 1] -> [thread 0] -> Linux CPU 1 + -> [thread 1] -> Linux CPU 5 + + [package 1] -> [core 0] -> [thread 0] -> Linux CPU 2 + -> [thread 1] -> Linux CPU 6 + -> [core 1] -> [thread 0] -> Linux CPU 3 + -> [thread 1] -> Linux CPU 7 + + AMD nomenclature for CMT systems:: + + [node 0] -> [Compute Unit 0] -> [Compute Unit Core 0] -> Linux CPU 0 + -> [Compute Unit Core 1] -> Linux CPU 1 + -> [Compute Unit 1] -> [Compute Unit Core 0] -> Linux CPU 2 + -> [Compute Unit Core 1] -> Linux CPU 3 + + [node 1] -> [Compute Unit 0] -> [Compute Unit Core 0] -> Linux CPU 4 + -> [Compute Unit Core 1] -> Linux CPU 5 + -> [Compute Unit 1] -> [Compute Unit Core 0] -> Linux CPU 6 + -> [Compute Unit Core 1] -> Linux CPU 7 diff --git a/Documentation/x86/topology.txt b/Documentation/x86/topology.txt deleted file mode 100644 index 2953e3ec9a02..000000000000 --- a/Documentation/x86/topology.txt +++ /dev/null @@ -1,217 +0,0 @@ -x86 Topology -============ - -This documents and clarifies the main aspects of x86 topology modelling and -representation in the kernel. Update/change when doing changes to the -respective code. - -The architecture-agnostic topology definitions are in -Documentation/cputopology.txt. This file holds x86-specific -differences/specialities which must not necessarily apply to the generic -definitions. Thus, the way to read up on Linux topology on x86 is to start -with the generic one and look at this one in parallel for the x86 specifics. - -Needless to say, code should use the generic functions - this file is *only* -here to *document* the inner workings of x86 topology. - -Started by Thomas Gleixner and Borislav Petkov . - -The main aim of the topology facilities is to present adequate interfaces to -code which needs to know/query/use the structure of the running system wrt -threads, cores, packages, etc. - -The kernel does not care about the concept of physical sockets because a -socket has no relevance to software. It's an electromechanical component. In -the past a socket always contained a single package (see below), but with the -advent of Multi Chip Modules (MCM) a socket can hold more than one package. So -there might be still references to sockets in the code, but they are of -historical nature and should be cleaned up. - -The topology of a system is described in the units of: - - - packages - - cores - - threads - -* Package: - - Packages contain a number of cores plus shared resources, e.g. DRAM - controller, shared caches etc. - - AMD nomenclature for package is 'Node'. - - Package-related topology information in the kernel: - - - cpuinfo_x86.x86_max_cores: - - The number of cores in a package. This information is retrieved via CPUID. - - - cpuinfo_x86.phys_proc_id: - - The physical ID of the package. This information is retrieved via CPUID - and deduced from the APIC IDs of the cores in the package. - - - cpuinfo_x86.logical_id: - - The logical ID of the package. As we do not trust BIOSes to enumerate the - packages in a consistent way, we introduced the concept of logical package - ID so we can sanely calculate the number of maximum possible packages in - the system and have the packages enumerated linearly. - - - topology_max_packages(): - - The maximum possible number of packages in the system. Helpful for per - package facilities to preallocate per package information. - - - cpu_llc_id: - - A per-CPU variable containing: - - On Intel, the first APIC ID of the list of CPUs sharing the Last Level - Cache - - - On AMD, the Node ID or Core Complex ID containing the Last Level - Cache. In general, it is a number identifying an LLC uniquely on the - system. - -* Cores: - - A core consists of 1 or more threads. It does not matter whether the threads - are SMT- or CMT-type threads. - - AMDs nomenclature for a CMT core is "Compute Unit". The kernel always uses - "core". - - Core-related topology information in the kernel: - - - smp_num_siblings: - - The number of threads in a core. The number of threads in a package can be - calculated by: - - threads_per_package = cpuinfo_x86.x86_max_cores * smp_num_siblings - - -* Threads: - - A thread is a single scheduling unit. It's the equivalent to a logical Linux - CPU. - - AMDs nomenclature for CMT threads is "Compute Unit Core". The kernel always - uses "thread". - - Thread-related topology information in the kernel: - - - topology_core_cpumask(): - - The cpumask contains all online threads in the package to which a thread - belongs. - - The number of online threads is also printed in /proc/cpuinfo "siblings." - - - topology_sibling_cpumask(): - - The cpumask contains all online threads in the core to which a thread - belongs. - - - topology_logical_package_id(): - - The logical package ID to which a thread belongs. - - - topology_physical_package_id(): - - The physical package ID to which a thread belongs. - - - topology_core_id(); - - The ID of the core to which a thread belongs. It is also printed in /proc/cpuinfo - "core_id." - - - -System topology examples - -Note: - -The alternative Linux CPU enumeration depends on how the BIOS enumerates the -threads. Many BIOSes enumerate all threads 0 first and then all threads 1. -That has the "advantage" that the logical Linux CPU numbers of threads 0 stay -the same whether threads are enabled or not. That's merely an implementation -detail and has no practical impact. - -1) Single Package, Single Core - - [package 0] -> [core 0] -> [thread 0] -> Linux CPU 0 - -2) Single Package, Dual Core - - a) One thread per core - - [package 0] -> [core 0] -> [thread 0] -> Linux CPU 0 - -> [core 1] -> [thread 0] -> Linux CPU 1 - - b) Two threads per core - - [package 0] -> [core 0] -> [thread 0] -> Linux CPU 0 - -> [thread 1] -> Linux CPU 1 - -> [core 1] -> [thread 0] -> Linux CPU 2 - -> [thread 1] -> Linux CPU 3 - - Alternative enumeration: - - [package 0] -> [core 0] -> [thread 0] -> Linux CPU 0 - -> [thread 1] -> Linux CPU 2 - -> [core 1] -> [thread 0] -> Linux CPU 1 - -> [thread 1] -> Linux CPU 3 - - AMD nomenclature for CMT systems: - - [node 0] -> [Compute Unit 0] -> [Compute Unit Core 0] -> Linux CPU 0 - -> [Compute Unit Core 1] -> Linux CPU 1 - -> [Compute Unit 1] -> [Compute Unit Core 0] -> Linux CPU 2 - -> [Compute Unit Core 1] -> Linux CPU 3 - -4) Dual Package, Dual Core - - a) One thread per core - - [package 0] -> [core 0] -> [thread 0] -> Linux CPU 0 - -> [core 1] -> [thread 0] -> Linux CPU 1 - - [package 1] -> [core 0] -> [thread 0] -> Linux CPU 2 - -> [core 1] -> [thread 0] -> Linux CPU 3 - - b) Two threads per core - - [package 0] -> [core 0] -> [thread 0] -> Linux CPU 0 - -> [thread 1] -> Linux CPU 1 - -> [core 1] -> [thread 0] -> Linux CPU 2 - -> [thread 1] -> Linux CPU 3 - - [package 1] -> [core 0] -> [thread 0] -> Linux CPU 4 - -> [thread 1] -> Linux CPU 5 - -> [core 1] -> [thread 0] -> Linux CPU 6 - -> [thread 1] -> Linux CPU 7 - - Alternative enumeration: - - [package 0] -> [core 0] -> [thread 0] -> Linux CPU 0 - -> [thread 1] -> Linux CPU 4 - -> [core 1] -> [thread 0] -> Linux CPU 1 - -> [thread 1] -> Linux CPU 5 - - [package 1] -> [core 0] -> [thread 0] -> Linux CPU 2 - -> [thread 1] -> Linux CPU 6 - -> [core 1] -> [thread 0] -> Linux CPU 3 - -> [thread 1] -> Linux CPU 7 - - AMD nomenclature for CMT systems: - - [node 0] -> [Compute Unit 0] -> [Compute Unit Core 0] -> Linux CPU 0 - -> [Compute Unit Core 1] -> Linux CPU 1 - -> [Compute Unit 1] -> [Compute Unit Core 0] -> Linux CPU 2 - -> [Compute Unit Core 1] -> Linux CPU 3 - - [node 1] -> [Compute Unit 0] -> [Compute Unit Core 0] -> Linux CPU 4 - -> [Compute Unit Core 1] -> Linux CPU 5 - -> [Compute Unit 1] -> [Compute Unit Core 0] -> Linux CPU 6 - -> [Compute Unit Core 1] -> Linux CPU 7 -- cgit v1.2.3 From 06955392a95cc2918c7881eddabe30e5d8cd0a53 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:18 +0800 Subject: Documentation: x86: convert exception-tables.txt to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/exception-tables.rst | 346 +++++++++++++++++++++++++++++++++ Documentation/x86/exception-tables.txt | 327 ------------------------------- Documentation/x86/index.rst | 1 + 3 files changed, 347 insertions(+), 327 deletions(-) create mode 100644 Documentation/x86/exception-tables.rst delete mode 100644 Documentation/x86/exception-tables.txt (limited to 'Documentation') diff --git a/Documentation/x86/exception-tables.rst b/Documentation/x86/exception-tables.rst new file mode 100644 index 000000000000..24596c8210b5 --- /dev/null +++ b/Documentation/x86/exception-tables.rst @@ -0,0 +1,346 @@ +.. SPDX-License-Identifier: GPL-2.0 + +=============================== +Kernel level exception handling +=============================== + +Commentary by Joerg Pommnitz + +When a process runs in kernel mode, it often has to access user +mode memory whose address has been passed by an untrusted program. +To protect itself the kernel has to verify this address. + +In older versions of Linux this was done with the +int verify_area(int type, const void * addr, unsigned long size) +function (which has since been replaced by access_ok()). + +This function verified that the memory area starting at address +'addr' and of size 'size' was accessible for the operation specified +in type (read or write). To do this, verify_read had to look up the +virtual memory area (vma) that contained the address addr. In the +normal case (correctly working program), this test was successful. +It only failed for a few buggy programs. In some kernel profiling +tests, this normally unneeded verification used up a considerable +amount of time. + +To overcome this situation, Linus decided to let the virtual memory +hardware present in every Linux-capable CPU handle this test. + +How does this work? + +Whenever the kernel tries to access an address that is currently not +accessible, the CPU generates a page fault exception and calls the +page fault handler:: + + void do_page_fault(struct pt_regs *regs, unsigned long error_code) + +in arch/x86/mm/fault.c. The parameters on the stack are set up by +the low level assembly glue in arch/x86/kernel/entry_32.S. The parameter +regs is a pointer to the saved registers on the stack, error_code +contains a reason code for the exception. + +do_page_fault first obtains the unaccessible address from the CPU +control register CR2. If the address is within the virtual address +space of the process, the fault probably occurred, because the page +was not swapped in, write protected or something similar. However, +we are interested in the other case: the address is not valid, there +is no vma that contains this address. In this case, the kernel jumps +to the bad_area label. + +There it uses the address of the instruction that caused the exception +(i.e. regs->eip) to find an address where the execution can continue +(fixup). If this search is successful, the fault handler modifies the +return address (again regs->eip) and returns. The execution will +continue at the address in fixup. + +Where does fixup point to? + +Since we jump to the contents of fixup, fixup obviously points +to executable code. This code is hidden inside the user access macros. +I have picked the get_user macro defined in arch/x86/include/asm/uaccess.h +as an example. The definition is somewhat hard to follow, so let's peek at +the code generated by the preprocessor and the compiler. I selected +the get_user call in drivers/char/sysrq.c for a detailed examination. + +The original code in sysrq.c line 587:: + + get_user(c, buf); + +The preprocessor output (edited to become somewhat readable):: + + ( + { + long __gu_err = - 14 , __gu_val = 0; + const __typeof__(*( ( buf ) )) *__gu_addr = ((buf)); + if (((((0 + current_set[0])->tss.segment) == 0x18 ) || + (((sizeof(*(buf))) <= 0xC0000000UL) && + ((unsigned long)(__gu_addr ) <= 0xC0000000UL - (sizeof(*(buf))))))) + do { + __gu_err = 0; + switch ((sizeof(*(buf)))) { + case 1: + __asm__ __volatile__( + "1: mov" "b" " %2,%" "b" "1\n" + "2:\n" + ".section .fixup,\"ax\"\n" + "3: movl %3,%0\n" + " xor" "b" " %" "b" "1,%" "b" "1\n" + " jmp 2b\n" + ".section __ex_table,\"a\"\n" + " .align 4\n" + " .long 1b,3b\n" + ".text" : "=r"(__gu_err), "=q" (__gu_val): "m"((*(struct __large_struct *) + ( __gu_addr )) ), "i"(- 14 ), "0"( __gu_err )) ; + break; + case 2: + __asm__ __volatile__( + "1: mov" "w" " %2,%" "w" "1\n" + "2:\n" + ".section .fixup,\"ax\"\n" + "3: movl %3,%0\n" + " xor" "w" " %" "w" "1,%" "w" "1\n" + " jmp 2b\n" + ".section __ex_table,\"a\"\n" + " .align 4\n" + " .long 1b,3b\n" + ".text" : "=r"(__gu_err), "=r" (__gu_val) : "m"((*(struct __large_struct *) + ( __gu_addr )) ), "i"(- 14 ), "0"( __gu_err )); + break; + case 4: + __asm__ __volatile__( + "1: mov" "l" " %2,%" "" "1\n" + "2:\n" + ".section .fixup,\"ax\"\n" + "3: movl %3,%0\n" + " xor" "l" " %" "" "1,%" "" "1\n" + " jmp 2b\n" + ".section __ex_table,\"a\"\n" + " .align 4\n" " .long 1b,3b\n" + ".text" : "=r"(__gu_err), "=r" (__gu_val) : "m"((*(struct __large_struct *) + ( __gu_addr )) ), "i"(- 14 ), "0"(__gu_err)); + break; + default: + (__gu_val) = __get_user_bad(); + } + } while (0) ; + ((c)) = (__typeof__(*((buf))))__gu_val; + __gu_err; + } + ); + +WOW! Black GCC/assembly magic. This is impossible to follow, so let's +see what code gcc generates:: + + > xorl %edx,%edx + > movl current_set,%eax + > cmpl $24,788(%eax) + > je .L1424 + > cmpl $-1073741825,64(%esp) + > ja .L1423 + > .L1424: + > movl %edx,%eax + > movl 64(%esp),%ebx + > #APP + > 1: movb (%ebx),%dl /* this is the actual user access */ + > 2: + > .section .fixup,"ax" + > 3: movl $-14,%eax + > xorb %dl,%dl + > jmp 2b + > .section __ex_table,"a" + > .align 4 + > .long 1b,3b + > .text + > #NO_APP + > .L1423: + > movzbl %dl,%esi + +The optimizer does a good job and gives us something we can actually +understand. Can we? The actual user access is quite obvious. Thanks +to the unified address space we can just access the address in user +memory. But what does the .section stuff do????? + +To understand this we have to look at the final kernel:: + + > objdump --section-headers vmlinux + > + > vmlinux: file format elf32-i386 + > + > Sections: + > Idx Name Size VMA LMA File off Algn + > 0 .text 00098f40 c0100000 c0100000 00001000 2**4 + > CONTENTS, ALLOC, LOAD, READONLY, CODE + > 1 .fixup 000016bc c0198f40 c0198f40 00099f40 2**0 + > CONTENTS, ALLOC, LOAD, READONLY, CODE + > 2 .rodata 0000f127 c019a5fc c019a5fc 0009b5fc 2**2 + > CONTENTS, ALLOC, LOAD, READONLY, DATA + > 3 __ex_table 000015c0 c01a9724 c01a9724 000aa724 2**2 + > CONTENTS, ALLOC, LOAD, READONLY, DATA + > 4 .data 0000ea58 c01abcf0 c01abcf0 000abcf0 2**4 + > CONTENTS, ALLOC, LOAD, DATA + > 5 .bss 00018e21 c01ba748 c01ba748 000ba748 2**2 + > ALLOC + > 6 .comment 00000ec4 00000000 00000000 000ba748 2**0 + > CONTENTS, READONLY + > 7 .note 00001068 00000ec4 00000ec4 000bb60c 2**0 + > CONTENTS, READONLY + +There are obviously 2 non standard ELF sections in the generated object +file. But first we want to find out what happened to our code in the +final kernel executable:: + + > objdump --disassemble --section=.text vmlinux + > + > c017e785 xorl %edx,%edx + > c017e787 movl 0xc01c7bec,%eax + > c017e78c cmpl $0x18,0x314(%eax) + > c017e793 je c017e79f + > c017e795 cmpl $0xbfffffff,0x40(%esp,1) + > c017e79d ja c017e7a7 + > c017e79f movl %edx,%eax + > c017e7a1 movl 0x40(%esp,1),%ebx + > c017e7a5 movb (%ebx),%dl + > c017e7a7 movzbl %dl,%esi + +The whole user memory access is reduced to 10 x86 machine instructions. +The instructions bracketed in the .section directives are no longer +in the normal execution path. They are located in a different section +of the executable file:: + + > objdump --disassemble --section=.fixup vmlinux + > + > c0199ff5 <.fixup+10b5> movl $0xfffffff2,%eax + > c0199ffa <.fixup+10ba> xorb %dl,%dl + > c0199ffc <.fixup+10bc> jmp c017e7a7 + +And finally:: + + > objdump --full-contents --section=__ex_table vmlinux + > + > c01aa7c4 93c017c0 e09f19c0 97c017c0 99c017c0 ................ + > c01aa7d4 f6c217c0 e99f19c0 a5e717c0 f59f19c0 ................ + > c01aa7e4 080a18c0 01a019c0 0a0a18c0 04a019c0 ................ + +or in human readable byte order:: + + > c01aa7c4 c017c093 c0199fe0 c017c097 c017c099 ................ + > c01aa7d4 c017c2f6 c0199fe9 c017e7a5 c0199ff5 ................ + ^^^^^^^^^^^^^^^^^ + this is the interesting part! + > c01aa7e4 c0180a08 c019a001 c0180a0a c019a004 ................ + +What happened? The assembly directives:: + + .section .fixup,"ax" + .section __ex_table,"a" + +told the assembler to move the following code to the specified +sections in the ELF object file. So the instructions:: + + 3: movl $-14,%eax + xorb %dl,%dl + jmp 2b + +ended up in the .fixup section of the object file and the addresses:: + + .long 1b,3b + +ended up in the __ex_table section of the object file. 1b and 3b +are local labels. The local label 1b (1b stands for next label 1 +backward) is the address of the instruction that might fault, i.e. +in our case the address of the label 1 is c017e7a5: +the original assembly code: > 1: movb (%ebx),%dl +and linked in vmlinux : > c017e7a5 movb (%ebx),%dl + +The local label 3 (backwards again) is the address of the code to handle +the fault, in our case the actual value is c0199ff5: +the original assembly code: > 3: movl $-14,%eax +and linked in vmlinux : > c0199ff5 <.fixup+10b5> movl $0xfffffff2,%eax + +The assembly code:: + + > .section __ex_table,"a" + > .align 4 + > .long 1b,3b + +becomes the value pair:: + + > c01aa7d4 c017c2f6 c0199fe9 c017e7a5 c0199ff5 ................ + ^this is ^this is + 1b 3b + +c017e7a5,c0199ff5 in the exception table of the kernel. + +So, what actually happens if a fault from kernel mode with no suitable +vma occurs? + +#. access to invalid address:: + + > c017e7a5 movb (%ebx),%dl +#. MMU generates exception +#. CPU calls do_page_fault +#. do page fault calls search_exception_table (regs->eip == c017e7a5); +#. search_exception_table looks up the address c017e7a5 in the + exception table (i.e. the contents of the ELF section __ex_table) + and returns the address of the associated fault handle code c0199ff5. +#. do_page_fault modifies its own return address to point to the fault + handle code and returns. +#. execution continues in the fault handling code. +#. a) EAX becomes -EFAULT (== -14) + b) DL becomes zero (the value we "read" from user space) + c) execution continues at local label 2 (address of the + instruction immediately after the faulting user access). + +The steps 8a to 8c in a certain way emulate the faulting instruction. + +That's it, mostly. If you look at our example, you might ask why +we set EAX to -EFAULT in the exception handler code. Well, the +get_user macro actually returns a value: 0, if the user access was +successful, -EFAULT on failure. Our original code did not test this +return value, however the inline assembly code in get_user tries to +return -EFAULT. GCC selected EAX to return this value. + +NOTE: +Due to the way that the exception table is built and needs to be ordered, +only use exceptions for code in the .text section. Any other section +will cause the exception table to not be sorted correctly, and the +exceptions will fail. + +Things changed when 64-bit support was added to x86 Linux. Rather than +double the size of the exception table by expanding the two entries +from 32-bits to 64 bits, a clever trick was used to store addresses +as relative offsets from the table itself. The assembly code changed +from:: + + .long 1b,3b + to: + .long (from) - . + .long (to) - . + +and the C-code that uses these values converts back to absolute addresses +like this:: + + ex_insn_addr(const struct exception_table_entry *x) + { + return (unsigned long)&x->insn + x->insn; + } + +In v4.6 the exception table entry was expanded with a new field "handler". +This is also 32-bits wide and contains a third relative function +pointer which points to one of: + +1) ``int ex_handler_default(const struct exception_table_entry *fixup)`` + This is legacy case that just jumps to the fixup code + +2) ``int ex_handler_fault(const struct exception_table_entry *fixup)`` + This case provides the fault number of the trap that occurred at + entry->insn. It is used to distinguish page faults from machine + check. + +3) ``int ex_handler_ext(const struct exception_table_entry *fixup)`` + This case is used for uaccess_err ... we need to set a flag + in the task structure. Before the handler functions existed this + case was handled by adding a large offset to the fixup to tag + it as special. + +More functions can easily be added. diff --git a/Documentation/x86/exception-tables.txt b/Documentation/x86/exception-tables.txt deleted file mode 100644 index e396bcd8d830..000000000000 --- a/Documentation/x86/exception-tables.txt +++ /dev/null @@ -1,327 +0,0 @@ - Kernel level exception handling in Linux - Commentary by Joerg Pommnitz - -When a process runs in kernel mode, it often has to access user -mode memory whose address has been passed by an untrusted program. -To protect itself the kernel has to verify this address. - -In older versions of Linux this was done with the -int verify_area(int type, const void * addr, unsigned long size) -function (which has since been replaced by access_ok()). - -This function verified that the memory area starting at address -'addr' and of size 'size' was accessible for the operation specified -in type (read or write). To do this, verify_read had to look up the -virtual memory area (vma) that contained the address addr. In the -normal case (correctly working program), this test was successful. -It only failed for a few buggy programs. In some kernel profiling -tests, this normally unneeded verification used up a considerable -amount of time. - -To overcome this situation, Linus decided to let the virtual memory -hardware present in every Linux-capable CPU handle this test. - -How does this work? - -Whenever the kernel tries to access an address that is currently not -accessible, the CPU generates a page fault exception and calls the -page fault handler - -void do_page_fault(struct pt_regs *regs, unsigned long error_code) - -in arch/x86/mm/fault.c. The parameters on the stack are set up by -the low level assembly glue in arch/x86/kernel/entry_32.S. The parameter -regs is a pointer to the saved registers on the stack, error_code -contains a reason code for the exception. - -do_page_fault first obtains the unaccessible address from the CPU -control register CR2. If the address is within the virtual address -space of the process, the fault probably occurred, because the page -was not swapped in, write protected or something similar. However, -we are interested in the other case: the address is not valid, there -is no vma that contains this address. In this case, the kernel jumps -to the bad_area label. - -There it uses the address of the instruction that caused the exception -(i.e. regs->eip) to find an address where the execution can continue -(fixup). If this search is successful, the fault handler modifies the -return address (again regs->eip) and returns. The execution will -continue at the address in fixup. - -Where does fixup point to? - -Since we jump to the contents of fixup, fixup obviously points -to executable code. This code is hidden inside the user access macros. -I have picked the get_user macro defined in arch/x86/include/asm/uaccess.h -as an example. The definition is somewhat hard to follow, so let's peek at -the code generated by the preprocessor and the compiler. I selected -the get_user call in drivers/char/sysrq.c for a detailed examination. - -The original code in sysrq.c line 587: - get_user(c, buf); - -The preprocessor output (edited to become somewhat readable): - -( - { - long __gu_err = - 14 , __gu_val = 0; - const __typeof__(*( ( buf ) )) *__gu_addr = ((buf)); - if (((((0 + current_set[0])->tss.segment) == 0x18 ) || - (((sizeof(*(buf))) <= 0xC0000000UL) && - ((unsigned long)(__gu_addr ) <= 0xC0000000UL - (sizeof(*(buf))))))) - do { - __gu_err = 0; - switch ((sizeof(*(buf)))) { - case 1: - __asm__ __volatile__( - "1: mov" "b" " %2,%" "b" "1\n" - "2:\n" - ".section .fixup,\"ax\"\n" - "3: movl %3,%0\n" - " xor" "b" " %" "b" "1,%" "b" "1\n" - " jmp 2b\n" - ".section __ex_table,\"a\"\n" - " .align 4\n" - " .long 1b,3b\n" - ".text" : "=r"(__gu_err), "=q" (__gu_val): "m"((*(struct __large_struct *) - ( __gu_addr )) ), "i"(- 14 ), "0"( __gu_err )) ; - break; - case 2: - __asm__ __volatile__( - "1: mov" "w" " %2,%" "w" "1\n" - "2:\n" - ".section .fixup,\"ax\"\n" - "3: movl %3,%0\n" - " xor" "w" " %" "w" "1,%" "w" "1\n" - " jmp 2b\n" - ".section __ex_table,\"a\"\n" - " .align 4\n" - " .long 1b,3b\n" - ".text" : "=r"(__gu_err), "=r" (__gu_val) : "m"((*(struct __large_struct *) - ( __gu_addr )) ), "i"(- 14 ), "0"( __gu_err )); - break; - case 4: - __asm__ __volatile__( - "1: mov" "l" " %2,%" "" "1\n" - "2:\n" - ".section .fixup,\"ax\"\n" - "3: movl %3,%0\n" - " xor" "l" " %" "" "1,%" "" "1\n" - " jmp 2b\n" - ".section __ex_table,\"a\"\n" - " .align 4\n" " .long 1b,3b\n" - ".text" : "=r"(__gu_err), "=r" (__gu_val) : "m"((*(struct __large_struct *) - ( __gu_addr )) ), "i"(- 14 ), "0"(__gu_err)); - break; - default: - (__gu_val) = __get_user_bad(); - } - } while (0) ; - ((c)) = (__typeof__(*((buf))))__gu_val; - __gu_err; - } -); - -WOW! Black GCC/assembly magic. This is impossible to follow, so let's -see what code gcc generates: - - > xorl %edx,%edx - > movl current_set,%eax - > cmpl $24,788(%eax) - > je .L1424 - > cmpl $-1073741825,64(%esp) - > ja .L1423 - > .L1424: - > movl %edx,%eax - > movl 64(%esp),%ebx - > #APP - > 1: movb (%ebx),%dl /* this is the actual user access */ - > 2: - > .section .fixup,"ax" - > 3: movl $-14,%eax - > xorb %dl,%dl - > jmp 2b - > .section __ex_table,"a" - > .align 4 - > .long 1b,3b - > .text - > #NO_APP - > .L1423: - > movzbl %dl,%esi - -The optimizer does a good job and gives us something we can actually -understand. Can we? The actual user access is quite obvious. Thanks -to the unified address space we can just access the address in user -memory. But what does the .section stuff do????? - -To understand this we have to look at the final kernel: - - > objdump --section-headers vmlinux - > - > vmlinux: file format elf32-i386 - > - > Sections: - > Idx Name Size VMA LMA File off Algn - > 0 .text 00098f40 c0100000 c0100000 00001000 2**4 - > CONTENTS, ALLOC, LOAD, READONLY, CODE - > 1 .fixup 000016bc c0198f40 c0198f40 00099f40 2**0 - > CONTENTS, ALLOC, LOAD, READONLY, CODE - > 2 .rodata 0000f127 c019a5fc c019a5fc 0009b5fc 2**2 - > CONTENTS, ALLOC, LOAD, READONLY, DATA - > 3 __ex_table 000015c0 c01a9724 c01a9724 000aa724 2**2 - > CONTENTS, ALLOC, LOAD, READONLY, DATA - > 4 .data 0000ea58 c01abcf0 c01abcf0 000abcf0 2**4 - > CONTENTS, ALLOC, LOAD, DATA - > 5 .bss 00018e21 c01ba748 c01ba748 000ba748 2**2 - > ALLOC - > 6 .comment 00000ec4 00000000 00000000 000ba748 2**0 - > CONTENTS, READONLY - > 7 .note 00001068 00000ec4 00000ec4 000bb60c 2**0 - > CONTENTS, READONLY - -There are obviously 2 non standard ELF sections in the generated object -file. But first we want to find out what happened to our code in the -final kernel executable: - - > objdump --disassemble --section=.text vmlinux - > - > c017e785 xorl %edx,%edx - > c017e787 movl 0xc01c7bec,%eax - > c017e78c cmpl $0x18,0x314(%eax) - > c017e793 je c017e79f - > c017e795 cmpl $0xbfffffff,0x40(%esp,1) - > c017e79d ja c017e7a7 - > c017e79f movl %edx,%eax - > c017e7a1 movl 0x40(%esp,1),%ebx - > c017e7a5 movb (%ebx),%dl - > c017e7a7 movzbl %dl,%esi - -The whole user memory access is reduced to 10 x86 machine instructions. -The instructions bracketed in the .section directives are no longer -in the normal execution path. They are located in a different section -of the executable file: - - > objdump --disassemble --section=.fixup vmlinux - > - > c0199ff5 <.fixup+10b5> movl $0xfffffff2,%eax - > c0199ffa <.fixup+10ba> xorb %dl,%dl - > c0199ffc <.fixup+10bc> jmp c017e7a7 - -And finally: - > objdump --full-contents --section=__ex_table vmlinux - > - > c01aa7c4 93c017c0 e09f19c0 97c017c0 99c017c0 ................ - > c01aa7d4 f6c217c0 e99f19c0 a5e717c0 f59f19c0 ................ - > c01aa7e4 080a18c0 01a019c0 0a0a18c0 04a019c0 ................ - -or in human readable byte order: - - > c01aa7c4 c017c093 c0199fe0 c017c097 c017c099 ................ - > c01aa7d4 c017c2f6 c0199fe9 c017e7a5 c0199ff5 ................ - ^^^^^^^^^^^^^^^^^ - this is the interesting part! - > c01aa7e4 c0180a08 c019a001 c0180a0a c019a004 ................ - -What happened? The assembly directives - -.section .fixup,"ax" -.section __ex_table,"a" - -told the assembler to move the following code to the specified -sections in the ELF object file. So the instructions -3: movl $-14,%eax - xorb %dl,%dl - jmp 2b -ended up in the .fixup section of the object file and the addresses - .long 1b,3b -ended up in the __ex_table section of the object file. 1b and 3b -are local labels. The local label 1b (1b stands for next label 1 -backward) is the address of the instruction that might fault, i.e. -in our case the address of the label 1 is c017e7a5: -the original assembly code: > 1: movb (%ebx),%dl -and linked in vmlinux : > c017e7a5 movb (%ebx),%dl - -The local label 3 (backwards again) is the address of the code to handle -the fault, in our case the actual value is c0199ff5: -the original assembly code: > 3: movl $-14,%eax -and linked in vmlinux : > c0199ff5 <.fixup+10b5> movl $0xfffffff2,%eax - -The assembly code - > .section __ex_table,"a" - > .align 4 - > .long 1b,3b - -becomes the value pair - > c01aa7d4 c017c2f6 c0199fe9 c017e7a5 c0199ff5 ................ - ^this is ^this is - 1b 3b -c017e7a5,c0199ff5 in the exception table of the kernel. - -So, what actually happens if a fault from kernel mode with no suitable -vma occurs? - -1.) access to invalid address: - > c017e7a5 movb (%ebx),%dl -2.) MMU generates exception -3.) CPU calls do_page_fault -4.) do page fault calls search_exception_table (regs->eip == c017e7a5); -5.) search_exception_table looks up the address c017e7a5 in the - exception table (i.e. the contents of the ELF section __ex_table) - and returns the address of the associated fault handle code c0199ff5. -6.) do_page_fault modifies its own return address to point to the fault - handle code and returns. -7.) execution continues in the fault handling code. -8.) 8a) EAX becomes -EFAULT (== -14) - 8b) DL becomes zero (the value we "read" from user space) - 8c) execution continues at local label 2 (address of the - instruction immediately after the faulting user access). - -The steps 8a to 8c in a certain way emulate the faulting instruction. - -That's it, mostly. If you look at our example, you might ask why -we set EAX to -EFAULT in the exception handler code. Well, the -get_user macro actually returns a value: 0, if the user access was -successful, -EFAULT on failure. Our original code did not test this -return value, however the inline assembly code in get_user tries to -return -EFAULT. GCC selected EAX to return this value. - -NOTE: -Due to the way that the exception table is built and needs to be ordered, -only use exceptions for code in the .text section. Any other section -will cause the exception table to not be sorted correctly, and the -exceptions will fail. - -Things changed when 64-bit support was added to x86 Linux. Rather than -double the size of the exception table by expanding the two entries -from 32-bits to 64 bits, a clever trick was used to store addresses -as relative offsets from the table itself. The assembly code changed -from: - .long 1b,3b -to: - .long (from) - . - .long (to) - . - -and the C-code that uses these values converts back to absolute addresses -like this: - - ex_insn_addr(const struct exception_table_entry *x) - { - return (unsigned long)&x->insn + x->insn; - } - -In v4.6 the exception table entry was expanded with a new field "handler". -This is also 32-bits wide and contains a third relative function -pointer which points to one of: - -1) int ex_handler_default(const struct exception_table_entry *fixup) - This is legacy case that just jumps to the fixup code -2) int ex_handler_fault(const struct exception_table_entry *fixup) - This case provides the fault number of the trap that occurred at - entry->insn. It is used to distinguish page faults from machine - check. -3) int ex_handler_ext(const struct exception_table_entry *fixup) - This case is used for uaccess_err ... we need to set a flag - in the task structure. Before the handler functions existed this - case was handled by adding a large offset to the fixup to tag - it as special. -More functions can easily be added. diff --git a/Documentation/x86/index.rst b/Documentation/x86/index.rst index da89bf0ad69f..c855b730bab4 100644 --- a/Documentation/x86/index.rst +++ b/Documentation/x86/index.rst @@ -10,3 +10,4 @@ x86-specific Documentation boot topology + exception-tables -- cgit v1.2.3 From ac2b4687dadd4e7703c0e985f5a5a0fdaab53316 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:19 +0800 Subject: Documentation: x86: convert kernel-stacks to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/index.rst | 1 + Documentation/x86/kernel-stacks | 141 ---------------------------------- Documentation/x86/kernel-stacks.rst | 147 ++++++++++++++++++++++++++++++++++++ 3 files changed, 148 insertions(+), 141 deletions(-) delete mode 100644 Documentation/x86/kernel-stacks create mode 100644 Documentation/x86/kernel-stacks.rst (limited to 'Documentation') diff --git a/Documentation/x86/index.rst b/Documentation/x86/index.rst index c855b730bab4..f6f4e0fc79f2 100644 --- a/Documentation/x86/index.rst +++ b/Documentation/x86/index.rst @@ -11,3 +11,4 @@ x86-specific Documentation boot topology exception-tables + kernel-stacks diff --git a/Documentation/x86/kernel-stacks b/Documentation/x86/kernel-stacks deleted file mode 100644 index 9a0aa4d3a866..000000000000 --- a/Documentation/x86/kernel-stacks +++ /dev/null @@ -1,141 +0,0 @@ -Kernel stacks on x86-64 bit ---------------------------- - -Most of the text from Keith Owens, hacked by AK - -x86_64 page size (PAGE_SIZE) is 4K. - -Like all other architectures, x86_64 has a kernel stack for every -active thread. These thread stacks are THREAD_SIZE (2*PAGE_SIZE) big. -These stacks contain useful data as long as a thread is alive or a -zombie. While the thread is in user space the kernel stack is empty -except for the thread_info structure at the bottom. - -In addition to the per thread stacks, there are specialized stacks -associated with each CPU. These stacks are only used while the kernel -is in control on that CPU; when a CPU returns to user space the -specialized stacks contain no useful data. The main CPU stacks are: - -* Interrupt stack. IRQ_STACK_SIZE - - Used for external hardware interrupts. If this is the first external - hardware interrupt (i.e. not a nested hardware interrupt) then the - kernel switches from the current task to the interrupt stack. Like - the split thread and interrupt stacks on i386, this gives more room - for kernel interrupt processing without having to increase the size - of every per thread stack. - - The interrupt stack is also used when processing a softirq. - -Switching to the kernel interrupt stack is done by software based on a -per CPU interrupt nest counter. This is needed because x86-64 "IST" -hardware stacks cannot nest without races. - -x86_64 also has a feature which is not available on i386, the ability -to automatically switch to a new stack for designated events such as -double fault or NMI, which makes it easier to handle these unusual -events on x86_64. This feature is called the Interrupt Stack Table -(IST). There can be up to 7 IST entries per CPU. The IST code is an -index into the Task State Segment (TSS). The IST entries in the TSS -point to dedicated stacks; each stack can be a different size. - -An IST is selected by a non-zero value in the IST field of an -interrupt-gate descriptor. When an interrupt occurs and the hardware -loads such a descriptor, the hardware automatically sets the new stack -pointer based on the IST value, then invokes the interrupt handler. If -the interrupt came from user mode, then the interrupt handler prologue -will switch back to the per-thread stack. If software wants to allow -nested IST interrupts then the handler must adjust the IST values on -entry to and exit from the interrupt handler. (This is occasionally -done, e.g. for debug exceptions.) - -Events with different IST codes (i.e. with different stacks) can be -nested. For example, a debug interrupt can safely be interrupted by an -NMI. arch/x86_64/kernel/entry.S::paranoidentry adjusts the stack -pointers on entry to and exit from all IST events, in theory allowing -IST events with the same code to be nested. However in most cases, the -stack size allocated to an IST assumes no nesting for the same code. -If that assumption is ever broken then the stacks will become corrupt. - -The currently assigned IST stacks are :- - -* DOUBLEFAULT_STACK. EXCEPTION_STKSZ (PAGE_SIZE). - - Used for interrupt 8 - Double Fault Exception (#DF). - - Invoked when handling one exception causes another exception. Happens - when the kernel is very confused (e.g. kernel stack pointer corrupt). - Using a separate stack allows the kernel to recover from it well enough - in many cases to still output an oops. - -* NMI_STACK. EXCEPTION_STKSZ (PAGE_SIZE). - - Used for non-maskable interrupts (NMI). - - NMI can be delivered at any time, including when the kernel is in the - middle of switching stacks. Using IST for NMI events avoids making - assumptions about the previous state of the kernel stack. - -* DEBUG_STACK. DEBUG_STKSZ - - Used for hardware debug interrupts (interrupt 1) and for software - debug interrupts (INT3). - - When debugging a kernel, debug interrupts (both hardware and - software) can occur at any time. Using IST for these interrupts - avoids making assumptions about the previous state of the kernel - stack. - -* MCE_STACK. EXCEPTION_STKSZ (PAGE_SIZE). - - Used for interrupt 18 - Machine Check Exception (#MC). - - MCE can be delivered at any time, including when the kernel is in the - middle of switching stacks. Using IST for MCE events avoids making - assumptions about the previous state of the kernel stack. - -For more details see the Intel IA32 or AMD AMD64 architecture manuals. - - -Printing backtraces on x86 --------------------------- - -The question about the '?' preceding function names in an x86 stacktrace -keeps popping up, here's an indepth explanation. It helps if the reader -stares at print_context_stack() and the whole machinery in and around -arch/x86/kernel/dumpstack.c. - -Adapted from Ingo's mail, Message-ID: <20150521101614.GA10889@gmail.com>: - -We always scan the full kernel stack for return addresses stored on -the kernel stack(s) [*], from stack top to stack bottom, and print out -anything that 'looks like' a kernel text address. - -If it fits into the frame pointer chain, we print it without a question -mark, knowing that it's part of the real backtrace. - -If the address does not fit into our expected frame pointer chain we -still print it, but we print a '?'. It can mean two things: - - - either the address is not part of the call chain: it's just stale - values on the kernel stack, from earlier function calls. This is - the common case. - - - or it is part of the call chain, but the frame pointer was not set - up properly within the function, so we don't recognize it. - -This way we will always print out the real call chain (plus a few more -entries), regardless of whether the frame pointer was set up correctly -or not - but in most cases we'll get the call chain right as well. The -entries printed are strictly in stack order, so you can deduce more -information from that as well. - -The most important property of this method is that we _never_ lose -information: we always strive to print _all_ addresses on the stack(s) -that look like kernel text addresses, so if debug information is wrong, -we still print out the real call chain as well - just with more question -marks than ideal. - -[*] For things like IRQ and IST stacks, we also scan those stacks, in - the right order, and try to cross from one stack into another - reconstructing the call chain. This works most of the time. diff --git a/Documentation/x86/kernel-stacks.rst b/Documentation/x86/kernel-stacks.rst new file mode 100644 index 000000000000..c7c7afce086f --- /dev/null +++ b/Documentation/x86/kernel-stacks.rst @@ -0,0 +1,147 @@ +.. SPDX-License-Identifier: GPL-2.0 + +============= +Kernel Stacks +============= + +Kernel stacks on x86-64 bit +=========================== + +Most of the text from Keith Owens, hacked by AK + +x86_64 page size (PAGE_SIZE) is 4K. + +Like all other architectures, x86_64 has a kernel stack for every +active thread. These thread stacks are THREAD_SIZE (2*PAGE_SIZE) big. +These stacks contain useful data as long as a thread is alive or a +zombie. While the thread is in user space the kernel stack is empty +except for the thread_info structure at the bottom. + +In addition to the per thread stacks, there are specialized stacks +associated with each CPU. These stacks are only used while the kernel +is in control on that CPU; when a CPU returns to user space the +specialized stacks contain no useful data. The main CPU stacks are: + +* Interrupt stack. IRQ_STACK_SIZE + + Used for external hardware interrupts. If this is the first external + hardware interrupt (i.e. not a nested hardware interrupt) then the + kernel switches from the current task to the interrupt stack. Like + the split thread and interrupt stacks on i386, this gives more room + for kernel interrupt processing without having to increase the size + of every per thread stack. + + The interrupt stack is also used when processing a softirq. + +Switching to the kernel interrupt stack is done by software based on a +per CPU interrupt nest counter. This is needed because x86-64 "IST" +hardware stacks cannot nest without races. + +x86_64 also has a feature which is not available on i386, the ability +to automatically switch to a new stack for designated events such as +double fault or NMI, which makes it easier to handle these unusual +events on x86_64. This feature is called the Interrupt Stack Table +(IST). There can be up to 7 IST entries per CPU. The IST code is an +index into the Task State Segment (TSS). The IST entries in the TSS +point to dedicated stacks; each stack can be a different size. + +An IST is selected by a non-zero value in the IST field of an +interrupt-gate descriptor. When an interrupt occurs and the hardware +loads such a descriptor, the hardware automatically sets the new stack +pointer based on the IST value, then invokes the interrupt handler. If +the interrupt came from user mode, then the interrupt handler prologue +will switch back to the per-thread stack. If software wants to allow +nested IST interrupts then the handler must adjust the IST values on +entry to and exit from the interrupt handler. (This is occasionally +done, e.g. for debug exceptions.) + +Events with different IST codes (i.e. with different stacks) can be +nested. For example, a debug interrupt can safely be interrupted by an +NMI. arch/x86_64/kernel/entry.S::paranoidentry adjusts the stack +pointers on entry to and exit from all IST events, in theory allowing +IST events with the same code to be nested. However in most cases, the +stack size allocated to an IST assumes no nesting for the same code. +If that assumption is ever broken then the stacks will become corrupt. + +The currently assigned IST stacks are: + +* DOUBLEFAULT_STACK. EXCEPTION_STKSZ (PAGE_SIZE). + + Used for interrupt 8 - Double Fault Exception (#DF). + + Invoked when handling one exception causes another exception. Happens + when the kernel is very confused (e.g. kernel stack pointer corrupt). + Using a separate stack allows the kernel to recover from it well enough + in many cases to still output an oops. + +* NMI_STACK. EXCEPTION_STKSZ (PAGE_SIZE). + + Used for non-maskable interrupts (NMI). + + NMI can be delivered at any time, including when the kernel is in the + middle of switching stacks. Using IST for NMI events avoids making + assumptions about the previous state of the kernel stack. + +* DEBUG_STACK. DEBUG_STKSZ + + Used for hardware debug interrupts (interrupt 1) and for software + debug interrupts (INT3). + + When debugging a kernel, debug interrupts (both hardware and + software) can occur at any time. Using IST for these interrupts + avoids making assumptions about the previous state of the kernel + stack. + +* MCE_STACK. EXCEPTION_STKSZ (PAGE_SIZE). + + Used for interrupt 18 - Machine Check Exception (#MC). + + MCE can be delivered at any time, including when the kernel is in the + middle of switching stacks. Using IST for MCE events avoids making + assumptions about the previous state of the kernel stack. + +For more details see the Intel IA32 or AMD AMD64 architecture manuals. + + +Printing backtraces on x86 +========================== + +The question about the '?' preceding function names in an x86 stacktrace +keeps popping up, here's an indepth explanation. It helps if the reader +stares at print_context_stack() and the whole machinery in and around +arch/x86/kernel/dumpstack.c. + +Adapted from Ingo's mail, Message-ID: <20150521101614.GA10889@gmail.com>: + +We always scan the full kernel stack for return addresses stored on +the kernel stack(s) [1]_, from stack top to stack bottom, and print out +anything that 'looks like' a kernel text address. + +If it fits into the frame pointer chain, we print it without a question +mark, knowing that it's part of the real backtrace. + +If the address does not fit into our expected frame pointer chain we +still print it, but we print a '?'. It can mean two things: + + - either the address is not part of the call chain: it's just stale + values on the kernel stack, from earlier function calls. This is + the common case. + + - or it is part of the call chain, but the frame pointer was not set + up properly within the function, so we don't recognize it. + +This way we will always print out the real call chain (plus a few more +entries), regardless of whether the frame pointer was set up correctly +or not - but in most cases we'll get the call chain right as well. The +entries printed are strictly in stack order, so you can deduce more +information from that as well. + +The most important property of this method is that we _never_ lose +information: we always strive to print _all_ addresses on the stack(s) +that look like kernel text addresses, so if debug information is wrong, +we still print out the real call chain as well - just with more question +marks than ideal. + +.. [1] For things like IRQ and IST stacks, we also scan those stacks, in + the right order, and try to cross from one stack into another + reconstructing the call chain. This works most of the time. -- cgit v1.2.3 From c2dea5cda0729fdd91760cdad6bb1166037be74a Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:20 +0800 Subject: Documentation: x86: convert entry_64.txt to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/entry_64.rst | 110 +++++++++++++++++++++++++++++++++++++++++ Documentation/x86/entry_64.txt | 104 -------------------------------------- Documentation/x86/index.rst | 1 + 3 files changed, 111 insertions(+), 104 deletions(-) create mode 100644 Documentation/x86/entry_64.rst delete mode 100644 Documentation/x86/entry_64.txt (limited to 'Documentation') diff --git a/Documentation/x86/entry_64.rst b/Documentation/x86/entry_64.rst new file mode 100644 index 000000000000..a48b3f6ebbe8 --- /dev/null +++ b/Documentation/x86/entry_64.rst @@ -0,0 +1,110 @@ +.. SPDX-License-Identifier: GPL-2.0 + +============== +Kernel Entries +============== + +This file documents some of the kernel entries in +arch/x86/entry/entry_64.S. A lot of this explanation is adapted from +an email from Ingo Molnar: + +http://lkml.kernel.org/r/<20110529191055.GC9835%40elte.hu> + +The x86 architecture has quite a few different ways to jump into +kernel code. Most of these entry points are registered in +arch/x86/kernel/traps.c and implemented in arch/x86/entry/entry_64.S +for 64-bit, arch/x86/entry/entry_32.S for 32-bit and finally +arch/x86/entry/entry_64_compat.S which implements the 32-bit compatibility +syscall entry points and thus provides for 32-bit processes the +ability to execute syscalls when running on 64-bit kernels. + +The IDT vector assignments are listed in arch/x86/include/asm/irq_vectors.h. + +Some of these entries are: + + - system_call: syscall instruction from 64-bit code. + + - entry_INT80_compat: int 0x80 from 32-bit or 64-bit code; compat syscall + either way. + + - entry_INT80_compat, ia32_sysenter: syscall and sysenter from 32-bit + code + + - interrupt: An array of entries. Every IDT vector that doesn't + explicitly point somewhere else gets set to the corresponding + value in interrupts. These point to a whole array of + magically-generated functions that make their way to do_IRQ with + the interrupt number as a parameter. + + - APIC interrupts: Various special-purpose interrupts for things + like TLB shootdown. + + - Architecturally-defined exceptions like divide_error. + +There are a few complexities here. The different x86-64 entries +have different calling conventions. The syscall and sysenter +instructions have their own peculiar calling conventions. Some of +the IDT entries push an error code onto the stack; others don't. +IDT entries using the IST alternative stack mechanism need their own +magic to get the stack frames right. (You can find some +documentation in the AMD APM, Volume 2, Chapter 8 and the Intel SDM, +Volume 3, Chapter 6.) + +Dealing with the swapgs instruction is especially tricky. Swapgs +toggles whether gs is the kernel gs or the user gs. The swapgs +instruction is rather fragile: it must nest perfectly and only in +single depth, it should only be used if entering from user mode to +kernel mode and then when returning to user-space, and precisely +so. If we mess that up even slightly, we crash. + +So when we have a secondary entry, already in kernel mode, we *must +not* use SWAPGS blindly - nor must we forget doing a SWAPGS when it's +not switched/swapped yet. + +Now, there's a secondary complication: there's a cheap way to test +which mode the CPU is in and an expensive way. + +The cheap way is to pick this info off the entry frame on the kernel +stack, from the CS of the ptregs area of the kernel stack:: + + xorl %ebx,%ebx + testl $3,CS+8(%rsp) + je error_kernelspace + SWAPGS + +The expensive (paranoid) way is to read back the MSR_GS_BASE value +(which is what SWAPGS modifies):: + + movl $1,%ebx + movl $MSR_GS_BASE,%ecx + rdmsr + testl %edx,%edx + js 1f /* negative -> in kernel */ + SWAPGS + xorl %ebx,%ebx + 1: ret + +If we are at an interrupt or user-trap/gate-alike boundary then we can +use the faster check: the stack will be a reliable indicator of +whether SWAPGS was already done: if we see that we are a secondary +entry interrupting kernel mode execution, then we know that the GS +base has already been switched. If it says that we interrupted +user-space execution then we must do the SWAPGS. + +But if we are in an NMI/MCE/DEBUG/whatever super-atomic entry context, +which might have triggered right after a normal entry wrote CS to the +stack but before we executed SWAPGS, then the only safe way to check +for GS is the slower method: the RDMSR. + +Therefore, super-atomic entries (except NMI, which is handled separately) +must use idtentry with paranoid=1 to handle gsbase correctly. This +triggers three main behavior changes: + + - Interrupt entry will use the slower gsbase check. + - Interrupt entry from user mode will switch off the IST stack. + - Interrupt exit to kernel mode will not attempt to reschedule. + +We try to only use IST entries and the paranoid entry code for vectors +that absolutely need the more expensive check for the GS base - and we +generate all 'normal' entry points with the regular (faster) paranoid=0 +variant. diff --git a/Documentation/x86/entry_64.txt b/Documentation/x86/entry_64.txt deleted file mode 100644 index c1df8eba9dfd..000000000000 --- a/Documentation/x86/entry_64.txt +++ /dev/null @@ -1,104 +0,0 @@ -This file documents some of the kernel entries in -arch/x86/entry/entry_64.S. A lot of this explanation is adapted from -an email from Ingo Molnar: - -http://lkml.kernel.org/r/<20110529191055.GC9835%40elte.hu> - -The x86 architecture has quite a few different ways to jump into -kernel code. Most of these entry points are registered in -arch/x86/kernel/traps.c and implemented in arch/x86/entry/entry_64.S -for 64-bit, arch/x86/entry/entry_32.S for 32-bit and finally -arch/x86/entry/entry_64_compat.S which implements the 32-bit compatibility -syscall entry points and thus provides for 32-bit processes the -ability to execute syscalls when running on 64-bit kernels. - -The IDT vector assignments are listed in arch/x86/include/asm/irq_vectors.h. - -Some of these entries are: - - - system_call: syscall instruction from 64-bit code. - - - entry_INT80_compat: int 0x80 from 32-bit or 64-bit code; compat syscall - either way. - - - entry_INT80_compat, ia32_sysenter: syscall and sysenter from 32-bit - code - - - interrupt: An array of entries. Every IDT vector that doesn't - explicitly point somewhere else gets set to the corresponding - value in interrupts. These point to a whole array of - magically-generated functions that make their way to do_IRQ with - the interrupt number as a parameter. - - - APIC interrupts: Various special-purpose interrupts for things - like TLB shootdown. - - - Architecturally-defined exceptions like divide_error. - -There are a few complexities here. The different x86-64 entries -have different calling conventions. The syscall and sysenter -instructions have their own peculiar calling conventions. Some of -the IDT entries push an error code onto the stack; others don't. -IDT entries using the IST alternative stack mechanism need their own -magic to get the stack frames right. (You can find some -documentation in the AMD APM, Volume 2, Chapter 8 and the Intel SDM, -Volume 3, Chapter 6.) - -Dealing with the swapgs instruction is especially tricky. Swapgs -toggles whether gs is the kernel gs or the user gs. The swapgs -instruction is rather fragile: it must nest perfectly and only in -single depth, it should only be used if entering from user mode to -kernel mode and then when returning to user-space, and precisely -so. If we mess that up even slightly, we crash. - -So when we have a secondary entry, already in kernel mode, we *must -not* use SWAPGS blindly - nor must we forget doing a SWAPGS when it's -not switched/swapped yet. - -Now, there's a secondary complication: there's a cheap way to test -which mode the CPU is in and an expensive way. - -The cheap way is to pick this info off the entry frame on the kernel -stack, from the CS of the ptregs area of the kernel stack: - - xorl %ebx,%ebx - testl $3,CS+8(%rsp) - je error_kernelspace - SWAPGS - -The expensive (paranoid) way is to read back the MSR_GS_BASE value -(which is what SWAPGS modifies): - - movl $1,%ebx - movl $MSR_GS_BASE,%ecx - rdmsr - testl %edx,%edx - js 1f /* negative -> in kernel */ - SWAPGS - xorl %ebx,%ebx -1: ret - -If we are at an interrupt or user-trap/gate-alike boundary then we can -use the faster check: the stack will be a reliable indicator of -whether SWAPGS was already done: if we see that we are a secondary -entry interrupting kernel mode execution, then we know that the GS -base has already been switched. If it says that we interrupted -user-space execution then we must do the SWAPGS. - -But if we are in an NMI/MCE/DEBUG/whatever super-atomic entry context, -which might have triggered right after a normal entry wrote CS to the -stack but before we executed SWAPGS, then the only safe way to check -for GS is the slower method: the RDMSR. - -Therefore, super-atomic entries (except NMI, which is handled separately) -must use idtentry with paranoid=1 to handle gsbase correctly. This -triggers three main behavior changes: - - - Interrupt entry will use the slower gsbase check. - - Interrupt entry from user mode will switch off the IST stack. - - Interrupt exit to kernel mode will not attempt to reschedule. - -We try to only use IST entries and the paranoid entry code for vectors -that absolutely need the more expensive check for the GS base - and we -generate all 'normal' entry points with the regular (faster) paranoid=0 -variant. diff --git a/Documentation/x86/index.rst b/Documentation/x86/index.rst index f6f4e0fc79f2..0e3e73458738 100644 --- a/Documentation/x86/index.rst +++ b/Documentation/x86/index.rst @@ -12,3 +12,4 @@ x86-specific Documentation topology exception-tables kernel-stacks + entry_64 -- cgit v1.2.3 From 4b1357600200cd2b56ecc6fb452d50d4079b42ed Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:21 +0800 Subject: Documentation: x86: convert earlyprintk.txt to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/earlyprintk.rst | 151 ++++++++++++++++++++++++++++++++++++++ Documentation/x86/earlyprintk.txt | 141 ----------------------------------- Documentation/x86/index.rst | 1 + 3 files changed, 152 insertions(+), 141 deletions(-) create mode 100644 Documentation/x86/earlyprintk.rst delete mode 100644 Documentation/x86/earlyprintk.txt (limited to 'Documentation') diff --git a/Documentation/x86/earlyprintk.rst b/Documentation/x86/earlyprintk.rst new file mode 100644 index 000000000000..11307378acf0 --- /dev/null +++ b/Documentation/x86/earlyprintk.rst @@ -0,0 +1,151 @@ +.. SPDX-License-Identifier: GPL-2.0 + +============ +Early Printk +============ + +Mini-HOWTO for using the earlyprintk=dbgp boot option with a +USB2 Debug port key and a debug cable, on x86 systems. + +You need two computers, the 'USB debug key' special gadget and +and two USB cables, connected like this:: + + [host/target] <-------> [USB debug key] <-------> [client/console] + +Hardware requirements +===================== + + a) Host/target system needs to have USB debug port capability. + + You can check this capability by looking at a 'Debug port' bit in + the lspci -vvv output:: + + # lspci -vvv + ... + 00:1d.7 USB Controller: Intel Corporation 82801H (ICH8 Family) USB2 EHCI Controller #1 (rev 03) (prog-if 20 [EHCI]) + Subsystem: Lenovo ThinkPad T61 + Control: I/O- Mem+ BusMaster+ SpecCycle- MemWINV- VGASnoop- ParErr- Stepping- SERR+ FastB2B- DisINTx- + Status: Cap+ 66MHz- UDF- FastB2B+ ParErr- DEVSEL=medium >TAbort- SERR- /grub.cfg. + + On systems with more than one EHCI debug controller you must + specify the correct EHCI debug controller number. The ordering + comes from the PCI bus enumeration of the EHCI controllers. The + default with no number argument is "0" or the first EHCI debug + controller. To use the second EHCI debug controller, you would + use the command line: "earlyprintk=dbgp1" + + .. note:: + normally earlyprintk console gets turned off once the + regular console is alive - use "earlyprintk=dbgp,keep" to keep + this channel open beyond early bootup. This can be useful for + debugging crashes under Xorg, etc. + + b) On the client/console system: + + You should enable the following kernel config option:: + + CONFIG_USB_SERIAL_DEBUG=y + + On the next bootup with the modified kernel you should + get a /dev/ttyUSBx device(s). + + Now this channel of kernel messages is ready to be used: start + your favorite terminal emulator (minicom, etc.) and set + it up to use /dev/ttyUSB0 - or use a raw 'cat /dev/ttyUSBx' to + see the raw output. + + c) On Nvidia Southbridge based systems: the kernel will try to probe + and find out which port has a debug device connected. + +Testing +======= + +You can test the output by using earlyprintk=dbgp,keep and provoking +kernel messages on the host/target system. You can provoke a harmless +kernel message by for example doing:: + + echo h > /proc/sysrq-trigger + +On the host/target system you should see this help line in "dmesg" output:: + + SysRq : HELP : loglevel(0-9) reBoot Crashdump terminate-all-tasks(E) memory-full-oom-kill(F) kill-all-tasks(I) saK show-backtrace-all-active-cpus(L) show-memory-usage(M) nice-all-RT-tasks(N) powerOff show-registers(P) show-all-timers(Q) unRaw Sync show-task-states(T) Unmount show-blocked-tasks(W) dump-ftrace-buffer(Z) + +On the client/console system do:: + + cat /dev/ttyUSB0 + +And you should see the help line above displayed shortly after you've +provoked it on the host system. + +If it does not work then please ask about it on the linux-kernel@vger.kernel.org +mailing list or contact the x86 maintainers. diff --git a/Documentation/x86/earlyprintk.txt b/Documentation/x86/earlyprintk.txt deleted file mode 100644 index 46933e06c972..000000000000 --- a/Documentation/x86/earlyprintk.txt +++ /dev/null @@ -1,141 +0,0 @@ - -Mini-HOWTO for using the earlyprintk=dbgp boot option with a -USB2 Debug port key and a debug cable, on x86 systems. - -You need two computers, the 'USB debug key' special gadget and -and two USB cables, connected like this: - - [host/target] <-------> [USB debug key] <-------> [client/console] - -1. There are a number of specific hardware requirements: - - a.) Host/target system needs to have USB debug port capability. - - You can check this capability by looking at a 'Debug port' bit in - the lspci -vvv output: - - # lspci -vvv - ... - 00:1d.7 USB Controller: Intel Corporation 82801H (ICH8 Family) USB2 EHCI Controller #1 (rev 03) (prog-if 20 [EHCI]) - Subsystem: Lenovo ThinkPad T61 - Control: I/O- Mem+ BusMaster+ SpecCycle- MemWINV- VGASnoop- ParErr- Stepping- SERR+ FastB2B- DisINTx- - Status: Cap+ 66MHz- UDF- FastB2B+ ParErr- DEVSEL=medium >TAbort- SERR- /grub.cfg.) - - On systems with more than one EHCI debug controller you must - specify the correct EHCI debug controller number. The ordering - comes from the PCI bus enumeration of the EHCI controllers. The - default with no number argument is "0" or the first EHCI debug - controller. To use the second EHCI debug controller, you would - use the command line: "earlyprintk=dbgp1" - - NOTE: normally earlyprintk console gets turned off once the - regular console is alive - use "earlyprintk=dbgp,keep" to keep - this channel open beyond early bootup. This can be useful for - debugging crashes under Xorg, etc. - - b.) On the client/console system: - - You should enable the following kernel config option: - - CONFIG_USB_SERIAL_DEBUG=y - - On the next bootup with the modified kernel you should - get a /dev/ttyUSBx device(s). - - Now this channel of kernel messages is ready to be used: start - your favorite terminal emulator (minicom, etc.) and set - it up to use /dev/ttyUSB0 - or use a raw 'cat /dev/ttyUSBx' to - see the raw output. - - c.) On Nvidia Southbridge based systems: the kernel will try to probe - and find out which port has a debug device connected. - -3. Testing that it works fine: - - You can test the output by using earlyprintk=dbgp,keep and provoking - kernel messages on the host/target system. You can provoke a harmless - kernel message by for example doing: - - echo h > /proc/sysrq-trigger - - On the host/target system you should see this help line in "dmesg" output: - - SysRq : HELP : loglevel(0-9) reBoot Crashdump terminate-all-tasks(E) memory-full-oom-kill(F) kill-all-tasks(I) saK show-backtrace-all-active-cpus(L) show-memory-usage(M) nice-all-RT-tasks(N) powerOff show-registers(P) show-all-timers(Q) unRaw Sync show-task-states(T) Unmount show-blocked-tasks(W) dump-ftrace-buffer(Z) - - On the client/console system do: - - cat /dev/ttyUSB0 - - And you should see the help line above displayed shortly after you've - provoked it on the host system. - -If it does not work then please ask about it on the linux-kernel@vger.kernel.org -mailing list or contact the x86 maintainers. diff --git a/Documentation/x86/index.rst b/Documentation/x86/index.rst index 0e3e73458738..d9ccc0f39279 100644 --- a/Documentation/x86/index.rst +++ b/Documentation/x86/index.rst @@ -13,3 +13,4 @@ x86-specific Documentation exception-tables kernel-stacks entry_64 + earlyprintk -- cgit v1.2.3 From 0c2d3639a81b1033f3cb5d3c5ae4d9e7e1313cc4 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:22 +0800 Subject: Documentation: x86: convert zero-page.txt to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/index.rst | 1 + Documentation/x86/zero-page.rst | 45 +++++++++++++++++++++++++++++++++++++++++ Documentation/x86/zero-page.txt | 40 ------------------------------------ 3 files changed, 46 insertions(+), 40 deletions(-) create mode 100644 Documentation/x86/zero-page.rst delete mode 100644 Documentation/x86/zero-page.txt (limited to 'Documentation') diff --git a/Documentation/x86/index.rst b/Documentation/x86/index.rst index d9ccc0f39279..e43aa9b31976 100644 --- a/Documentation/x86/index.rst +++ b/Documentation/x86/index.rst @@ -14,3 +14,4 @@ x86-specific Documentation kernel-stacks entry_64 earlyprintk + zero-page diff --git a/Documentation/x86/zero-page.rst b/Documentation/x86/zero-page.rst new file mode 100644 index 000000000000..f088f5881666 --- /dev/null +++ b/Documentation/x86/zero-page.rst @@ -0,0 +1,45 @@ +.. SPDX-License-Identifier: GPL-2.0 + +========= +Zero Page +========= +The additional fields in struct boot_params as a part of 32-bit boot +protocol of kernel. These should be filled by bootloader or 16-bit +real-mode setup code of the kernel. References/settings to it mainly +are in:: + + arch/x86/include/uapi/asm/bootparam.h + +=========== ===== ======================= ================================================= +Offset/Size Proto Name Meaning + +000/040 ALL screen_info Text mode or frame buffer information + (struct screen_info) +040/014 ALL apm_bios_info APM BIOS information (struct apm_bios_info) +058/008 ALL tboot_addr Physical address of tboot shared page +060/010 ALL ist_info Intel SpeedStep (IST) BIOS support information + (struct ist_info) +080/010 ALL hd0_info hd0 disk parameter, OBSOLETE!! +090/010 ALL hd1_info hd1 disk parameter, OBSOLETE!! +0A0/010 ALL sys_desc_table System description table (struct sys_desc_table), + OBSOLETE!! +0B0/010 ALL olpc_ofw_header OLPC's OpenFirmware CIF and friends +0C0/004 ALL ext_ramdisk_image ramdisk_image high 32bits +0C4/004 ALL ext_ramdisk_size ramdisk_size high 32bits +0C8/004 ALL ext_cmd_line_ptr cmd_line_ptr high 32bits +140/080 ALL edid_info Video mode setup (struct edid_info) +1C0/020 ALL efi_info EFI 32 information (struct efi_info) +1E0/004 ALL alt_mem_k Alternative mem check, in KB +1E4/004 ALL scratch Scratch field for the kernel setup code +1E8/001 ALL e820_entries Number of entries in e820_table (below) +1E9/001 ALL eddbuf_entries Number of entries in eddbuf (below) +1EA/001 ALL edd_mbr_sig_buf_entries Number of entries in edd_mbr_sig_buffer + (below) +1EB/001 ALL kbd_status Numlock is enabled +1EC/001 ALL secure_boot Secure boot is enabled in the firmware +1EF/001 ALL sentinel Used to detect broken bootloaders +290/040 ALL edd_mbr_sig_buffer EDD MBR signatures +2D0/A00 ALL e820_table E820 memory map table + (array of struct e820_entry) +D00/1EC ALL eddbuf EDD data (array of struct edd_info) +=========== ===== ======================= ================================================= diff --git a/Documentation/x86/zero-page.txt b/Documentation/x86/zero-page.txt deleted file mode 100644 index 68aed077f7b6..000000000000 --- a/Documentation/x86/zero-page.txt +++ /dev/null @@ -1,40 +0,0 @@ -The additional fields in struct boot_params as a part of 32-bit boot -protocol of kernel. These should be filled by bootloader or 16-bit -real-mode setup code of the kernel. References/settings to it mainly -are in: - - arch/x86/include/uapi/asm/bootparam.h - - -Offset Proto Name Meaning -/Size - -000/040 ALL screen_info Text mode or frame buffer information - (struct screen_info) -040/014 ALL apm_bios_info APM BIOS information (struct apm_bios_info) -058/008 ALL tboot_addr Physical address of tboot shared page -060/010 ALL ist_info Intel SpeedStep (IST) BIOS support information - (struct ist_info) -080/010 ALL hd0_info hd0 disk parameter, OBSOLETE!! -090/010 ALL hd1_info hd1 disk parameter, OBSOLETE!! -0A0/010 ALL sys_desc_table System description table (struct sys_desc_table), - OBSOLETE!! -0B0/010 ALL olpc_ofw_header OLPC's OpenFirmware CIF and friends -0C0/004 ALL ext_ramdisk_image ramdisk_image high 32bits -0C4/004 ALL ext_ramdisk_size ramdisk_size high 32bits -0C8/004 ALL ext_cmd_line_ptr cmd_line_ptr high 32bits -140/080 ALL edid_info Video mode setup (struct edid_info) -1C0/020 ALL efi_info EFI 32 information (struct efi_info) -1E0/004 ALL alt_mem_k Alternative mem check, in KB -1E4/004 ALL scratch Scratch field for the kernel setup code -1E8/001 ALL e820_entries Number of entries in e820_table (below) -1E9/001 ALL eddbuf_entries Number of entries in eddbuf (below) -1EA/001 ALL edd_mbr_sig_buf_entries Number of entries in edd_mbr_sig_buffer - (below) -1EB/001 ALL kbd_status Numlock is enabled -1EC/001 ALL secure_boot Secure boot is enabled in the firmware -1EF/001 ALL sentinel Used to detect broken bootloaders -290/040 ALL edd_mbr_sig_buffer EDD MBR signatures -2D0/A00 ALL e820_table E820 memory map table - (array of struct e820_entry) -D00/1EC ALL eddbuf EDD data (array of struct edd_info) -- cgit v1.2.3 From 17156044b11c878a9fdd8326cf47bc0cbd1aa918 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:23 +0800 Subject: Documentation: x86: convert tlb.txt to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/index.rst | 1 + Documentation/x86/tlb.rst | 83 +++++++++++++++++++++++++++++++++++++++++++++ Documentation/x86/tlb.txt | 75 ---------------------------------------- 3 files changed, 84 insertions(+), 75 deletions(-) create mode 100644 Documentation/x86/tlb.rst delete mode 100644 Documentation/x86/tlb.txt (limited to 'Documentation') diff --git a/Documentation/x86/index.rst b/Documentation/x86/index.rst index e43aa9b31976..c4ea25350221 100644 --- a/Documentation/x86/index.rst +++ b/Documentation/x86/index.rst @@ -15,3 +15,4 @@ x86-specific Documentation entry_64 earlyprintk zero-page + tlb diff --git a/Documentation/x86/tlb.rst b/Documentation/x86/tlb.rst new file mode 100644 index 000000000000..82ec58ae63a8 --- /dev/null +++ b/Documentation/x86/tlb.rst @@ -0,0 +1,83 @@ +.. SPDX-License-Identifier: GPL-2.0 + +======= +The TLB +======= + +When the kernel unmaps or modified the attributes of a range of +memory, it has two choices: + + 1. Flush the entire TLB with a two-instruction sequence. This is + a quick operation, but it causes collateral damage: TLB entries + from areas other than the one we are trying to flush will be + destroyed and must be refilled later, at some cost. + 2. Use the invlpg instruction to invalidate a single page at a + time. This could potentially cost many more instructions, but + it is a much more precise operation, causing no collateral + damage to other TLB entries. + +Which method to do depends on a few things: + + 1. The size of the flush being performed. A flush of the entire + address space is obviously better performed by flushing the + entire TLB than doing 2^48/PAGE_SIZE individual flushes. + 2. The contents of the TLB. If the TLB is empty, then there will + be no collateral damage caused by doing the global flush, and + all of the individual flush will have ended up being wasted + work. + 3. The size of the TLB. The larger the TLB, the more collateral + damage we do with a full flush. So, the larger the TLB, the + more attractive an individual flush looks. Data and + instructions have separate TLBs, as do different page sizes. + 4. The microarchitecture. The TLB has become a multi-level + cache on modern CPUs, and the global flushes have become more + expensive relative to single-page flushes. + +There is obviously no way the kernel can know all these things, +especially the contents of the TLB during a given flush. The +sizes of the flush will vary greatly depending on the workload as +well. There is essentially no "right" point to choose. + +You may be doing too many individual invalidations if you see the +invlpg instruction (or instructions _near_ it) show up high in +profiles. If you believe that individual invalidations being +called too often, you can lower the tunable:: + + /sys/kernel/debug/x86/tlb_single_page_flush_ceiling + +This will cause us to do the global flush for more cases. +Lowering it to 0 will disable the use of the individual flushes. +Setting it to 1 is a very conservative setting and it should +never need to be 0 under normal circumstances. + +Despite the fact that a single individual flush on x86 is +guaranteed to flush a full 2MB [1]_, hugetlbfs always uses the full +flushes. THP is treated exactly the same as normal memory. + +You might see invlpg inside of flush_tlb_mm_range() show up in +profiles, or you can use the trace_tlb_flush() tracepoints. to +determine how long the flush operations are taking. + +Essentially, you are balancing the cycles you spend doing invlpg +with the cycles that you spend refilling the TLB later. + +You can measure how expensive TLB refills are by using +performance counters and 'perf stat', like this:: + + perf stat -e + cpu/event=0x8,umask=0x84,name=dtlb_load_misses_walk_duration/, + cpu/event=0x8,umask=0x82,name=dtlb_load_misses_walk_completed/, + cpu/event=0x49,umask=0x4,name=dtlb_store_misses_walk_duration/, + cpu/event=0x49,umask=0x2,name=dtlb_store_misses_walk_completed/, + cpu/event=0x85,umask=0x4,name=itlb_misses_walk_duration/, + cpu/event=0x85,umask=0x2,name=itlb_misses_walk_completed/ + +That works on an IvyBridge-era CPU (i5-3320M). Different CPUs +may have differently-named counters, but they should at least +be there in some form. You can use pmu-tools 'ocperf list' +(https://github.com/andikleen/pmu-tools) to find the right +counters for a given CPU. + +.. [1] A footnote in Intel's SDM "4.10.4.2 Recommended Invalidation" + says: "One execution of INVLPG is sufficient even for a page + with size greater than 4 KBytes." diff --git a/Documentation/x86/tlb.txt b/Documentation/x86/tlb.txt deleted file mode 100644 index 6a0607b99ed8..000000000000 --- a/Documentation/x86/tlb.txt +++ /dev/null @@ -1,75 +0,0 @@ -When the kernel unmaps or modified the attributes of a range of -memory, it has two choices: - 1. Flush the entire TLB with a two-instruction sequence. This is - a quick operation, but it causes collateral damage: TLB entries - from areas other than the one we are trying to flush will be - destroyed and must be refilled later, at some cost. - 2. Use the invlpg instruction to invalidate a single page at a - time. This could potentially cost many more instructions, but - it is a much more precise operation, causing no collateral - damage to other TLB entries. - -Which method to do depends on a few things: - 1. The size of the flush being performed. A flush of the entire - address space is obviously better performed by flushing the - entire TLB than doing 2^48/PAGE_SIZE individual flushes. - 2. The contents of the TLB. If the TLB is empty, then there will - be no collateral damage caused by doing the global flush, and - all of the individual flush will have ended up being wasted - work. - 3. The size of the TLB. The larger the TLB, the more collateral - damage we do with a full flush. So, the larger the TLB, the - more attractive an individual flush looks. Data and - instructions have separate TLBs, as do different page sizes. - 4. The microarchitecture. The TLB has become a multi-level - cache on modern CPUs, and the global flushes have become more - expensive relative to single-page flushes. - -There is obviously no way the kernel can know all these things, -especially the contents of the TLB during a given flush. The -sizes of the flush will vary greatly depending on the workload as -well. There is essentially no "right" point to choose. - -You may be doing too many individual invalidations if you see the -invlpg instruction (or instructions _near_ it) show up high in -profiles. If you believe that individual invalidations being -called too often, you can lower the tunable: - - /sys/kernel/debug/x86/tlb_single_page_flush_ceiling - -This will cause us to do the global flush for more cases. -Lowering it to 0 will disable the use of the individual flushes. -Setting it to 1 is a very conservative setting and it should -never need to be 0 under normal circumstances. - -Despite the fact that a single individual flush on x86 is -guaranteed to flush a full 2MB [1], hugetlbfs always uses the full -flushes. THP is treated exactly the same as normal memory. - -You might see invlpg inside of flush_tlb_mm_range() show up in -profiles, or you can use the trace_tlb_flush() tracepoints. to -determine how long the flush operations are taking. - -Essentially, you are balancing the cycles you spend doing invlpg -with the cycles that you spend refilling the TLB later. - -You can measure how expensive TLB refills are by using -performance counters and 'perf stat', like this: - -perf stat -e - cpu/event=0x8,umask=0x84,name=dtlb_load_misses_walk_duration/, - cpu/event=0x8,umask=0x82,name=dtlb_load_misses_walk_completed/, - cpu/event=0x49,umask=0x4,name=dtlb_store_misses_walk_duration/, - cpu/event=0x49,umask=0x2,name=dtlb_store_misses_walk_completed/, - cpu/event=0x85,umask=0x4,name=itlb_misses_walk_duration/, - cpu/event=0x85,umask=0x2,name=itlb_misses_walk_completed/ - -That works on an IvyBridge-era CPU (i5-3320M). Different CPUs -may have differently-named counters, but they should at least -be there in some form. You can use pmu-tools 'ocperf list' -(https://github.com/andikleen/pmu-tools) to find the right -counters for a given CPU. - -1. A footnote in Intel's SDM "4.10.4.2 Recommended Invalidation" - says: "One execution of INVLPG is sufficient even for a page - with size greater than 4 KBytes." -- cgit v1.2.3 From 26d14a2025f4e0d0aa3c157e1421e27fcc2d2bb3 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:24 +0800 Subject: Documentation: x86: convert mtrr.txt to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Signed-off-by: Jonathan Corbet --- Documentation/x86/index.rst | 1 + Documentation/x86/mtrr.rst | 354 ++++++++++++++++++++++++++++++++++++++++++++ Documentation/x86/mtrr.txt | 329 ---------------------------------------- 3 files changed, 355 insertions(+), 329 deletions(-) create mode 100644 Documentation/x86/mtrr.rst delete mode 100644 Documentation/x86/mtrr.txt (limited to 'Documentation') diff --git a/Documentation/x86/index.rst b/Documentation/x86/index.rst index c4ea25350221..769c4491e9cb 100644 --- a/Documentation/x86/index.rst +++ b/Documentation/x86/index.rst @@ -16,3 +16,4 @@ x86-specific Documentation earlyprintk zero-page tlb + mtrr diff --git a/Documentation/x86/mtrr.rst b/Documentation/x86/mtrr.rst new file mode 100644 index 000000000000..c5b695d75349 --- /dev/null +++ b/Documentation/x86/mtrr.rst @@ -0,0 +1,354 @@ +.. SPDX-License-Identifier: GPL-2.0 + +========================================= +MTRR (Memory Type Range Register) control +========================================= + +:Authors: - Richard Gooch - 3 Jun 1999 + - Luis R. Rodriguez - April 9, 2015 + + +Phasing out MTRR use +==================== + +MTRR use is replaced on modern x86 hardware with PAT. Direct MTRR use by +drivers on Linux is now completely phased out, device drivers should use +arch_phys_wc_add() in combination with ioremap_wc() to make MTRR effective on +non-PAT systems while a no-op but equally effective on PAT enabled systems. + +Even if Linux does not use MTRRs directly, some x86 platform firmware may still +set up MTRRs early before booting the OS. They do this as some platform +firmware may still have implemented access to MTRRs which would be controlled +and handled by the platform firmware directly. An example of platform use of +MTRRs is through the use of SMI handlers, one case could be for fan control, +the platform code would need uncachable access to some of its fan control +registers. Such platform access does not need any Operating System MTRR code in +place other than mtrr_type_lookup() to ensure any OS specific mapping requests +are aligned with platform MTRR setup. If MTRRs are only set up by the platform +firmware code though and the OS does not make any specific MTRR mapping +requests mtrr_type_lookup() should always return MTRR_TYPE_INVALID. + +For details refer to :doc:`pat`. + +.. tip:: + On Intel P6 family processors (Pentium Pro, Pentium II and later) + the Memory Type Range Registers (MTRRs) may be used to control + processor access to memory ranges. This is most useful when you have + a video (VGA) card on a PCI or AGP bus. Enabling write-combining + allows bus write transfers to be combined into a larger transfer + before bursting over the PCI/AGP bus. This can increase performance + of image write operations 2.5 times or more. + + The Cyrix 6x86, 6x86MX and M II processors have Address Range + Registers (ARRs) which provide a similar functionality to MTRRs. For + these, the ARRs are used to emulate the MTRRs. + + The AMD K6-2 (stepping 8 and above) and K6-3 processors have two + MTRRs. These are supported. The AMD Athlon family provide 8 Intel + style MTRRs. + + The Centaur C6 (WinChip) has 8 MCRs, allowing write-combining. These + are supported. + + The VIA Cyrix III and VIA C3 CPUs offer 8 Intel style MTRRs. + + The CONFIG_MTRR option creates a /proc/mtrr file which may be used + to manipulate your MTRRs. Typically the X server should use + this. This should have a reasonably generic interface so that + similar control registers on other processors can be easily + supported. + +There are two interfaces to /proc/mtrr: one is an ASCII interface +which allows you to read and write. The other is an ioctl() +interface. The ASCII interface is meant for administration. The +ioctl() interface is meant for C programs (i.e. the X server). The +interfaces are described below, with sample commands and C code. + + +Reading MTRRs from the shell +============================ +:: + + % cat /proc/mtrr + reg00: base=0x00000000 ( 0MB), size= 128MB: write-back, count=1 + reg01: base=0x08000000 ( 128MB), size= 64MB: write-back, count=1 + +Creating MTRRs from the C-shell:: + + # echo "base=0xf8000000 size=0x400000 type=write-combining" >! /proc/mtrr + +or if you use bash:: + + # echo "base=0xf8000000 size=0x400000 type=write-combining" >| /proc/mtrr + +And the result thereof:: + + % cat /proc/mtrr + reg00: base=0x00000000 ( 0MB), size= 128MB: write-back, count=1 + reg01: base=0x08000000 ( 128MB), size= 64MB: write-back, count=1 + reg02: base=0xf8000000 (3968MB), size= 4MB: write-combining, count=1 + +This is for video RAM at base address 0xf8000000 and size 4 megabytes. To +find out your base address, you need to look at the output of your X +server, which tells you where the linear framebuffer address is. A +typical line that you may get is:: + + (--) S3: PCI: 968 rev 0, Linear FB @ 0xf8000000 + +Note that you should only use the value from the X server, as it may +move the framebuffer base address, so the only value you can trust is +that reported by the X server. + +To find out the size of your framebuffer (what, you don't actually +know?), the following line will tell you:: + + (--) S3: videoram: 4096k + +That's 4 megabytes, which is 0x400000 bytes (in hexadecimal). +A patch is being written for XFree86 which will make this automatic: +in other words the X server will manipulate /proc/mtrr using the +ioctl() interface, so users won't have to do anything. If you use a +commercial X server, lobby your vendor to add support for MTRRs. + + +Creating overlapping MTRRs +========================== +:: + + %echo "base=0xfb000000 size=0x1000000 type=write-combining" >/proc/mtrr + %echo "base=0xfb000000 size=0x1000 type=uncachable" >/proc/mtrr + +And the results:: + + % cat /proc/mtrr + reg00: base=0x00000000 ( 0MB), size= 64MB: write-back, count=1 + reg01: base=0xfb000000 (4016MB), size= 16MB: write-combining, count=1 + reg02: base=0xfb000000 (4016MB), size= 4kB: uncachable, count=1 + +Some cards (especially Voodoo Graphics boards) need this 4 kB area +excluded from the beginning of the region because it is used for +registers. + +NOTE: You can only create type=uncachable region, if the first +region that you created is type=write-combining. + + +Removing MTRRs from the C-shel +============================== +:: + + % echo "disable=2" >! /proc/mtrr + +or using bash:: + + % echo "disable=2" >| /proc/mtrr + + +Reading MTRRs from a C program using ioctl()'s +============================================== +:: + + /* mtrr-show.c + + Source file for mtrr-show (example program to show MTRRs using ioctl()'s) + + Copyright (C) 1997-1998 Richard Gooch + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + + Richard Gooch may be reached by email at rgooch@atnf.csiro.au + The postal address is: + Richard Gooch, c/o ATNF, P. O. Box 76, Epping, N.S.W., 2121, Australia. + */ + + /* + This program will use an ioctl() on /proc/mtrr to show the current MTRR + settings. This is an alternative to reading /proc/mtrr. + + + Written by Richard Gooch 17-DEC-1997 + + Last updated by Richard Gooch 2-MAY-1998 + + + */ + #include + #include + #include + #include + #include + #include + #include + #include + #include + + #define TRUE 1 + #define FALSE 0 + #define ERRSTRING strerror (errno) + + static char *mtrr_strings[MTRR_NUM_TYPES] = + { + "uncachable", /* 0 */ + "write-combining", /* 1 */ + "?", /* 2 */ + "?", /* 3 */ + "write-through", /* 4 */ + "write-protect", /* 5 */ + "write-back", /* 6 */ + }; + + int main () + { + int fd; + struct mtrr_gentry gentry; + + if ( ( fd = open ("/proc/mtrr", O_RDONLY, 0) ) == -1 ) + { + if (errno == ENOENT) + { + fputs ("/proc/mtrr not found: not supported or you don't have a PPro?\n", + stderr); + exit (1); + } + fprintf (stderr, "Error opening /proc/mtrr\t%s\n", ERRSTRING); + exit (2); + } + for (gentry.regnum = 0; ioctl (fd, MTRRIOC_GET_ENTRY, &gentry) == 0; + ++gentry.regnum) + { + if (gentry.size < 1) + { + fprintf (stderr, "Register: %u disabled\n", gentry.regnum); + continue; + } + fprintf (stderr, "Register: %u base: 0x%lx size: 0x%lx type: %s\n", + gentry.regnum, gentry.base, gentry.size, + mtrr_strings[gentry.type]); + } + if (errno == EINVAL) exit (0); + fprintf (stderr, "Error doing ioctl(2) on /dev/mtrr\t%s\n", ERRSTRING); + exit (3); + } /* End Function main */ + + +Creating MTRRs from a C programme using ioctl()'s +================================================= +:: + + /* mtrr-add.c + + Source file for mtrr-add (example programme to add an MTRRs using ioctl()) + + Copyright (C) 1997-1998 Richard Gooch + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + + Richard Gooch may be reached by email at rgooch@atnf.csiro.au + The postal address is: + Richard Gooch, c/o ATNF, P. O. Box 76, Epping, N.S.W., 2121, Australia. + */ + + /* + This programme will use an ioctl() on /proc/mtrr to add an entry. The first + available mtrr is used. This is an alternative to writing /proc/mtrr. + + + Written by Richard Gooch 17-DEC-1997 + + Last updated by Richard Gooch 2-MAY-1998 + + + */ + #include + #include + #include + #include + #include + #include + #include + #include + #include + #include + + #define TRUE 1 + #define FALSE 0 + #define ERRSTRING strerror (errno) + + static char *mtrr_strings[MTRR_NUM_TYPES] = + { + "uncachable", /* 0 */ + "write-combining", /* 1 */ + "?", /* 2 */ + "?", /* 3 */ + "write-through", /* 4 */ + "write-protect", /* 5 */ + "write-back", /* 6 */ + }; + + int main (int argc, char **argv) + { + int fd; + struct mtrr_sentry sentry; + + if (argc != 4) + { + fprintf (stderr, "Usage:\tmtrr-add base size type\n"); + exit (1); + } + sentry.base = strtoul (argv[1], NULL, 0); + sentry.size = strtoul (argv[2], NULL, 0); + for (sentry.type = 0; sentry.type < MTRR_NUM_TYPES; ++sentry.type) + { + if (strcmp (argv[3], mtrr_strings[sentry.type]) == 0) break; + } + if (sentry.type >= MTRR_NUM_TYPES) + { + fprintf (stderr, "Illegal type: \"%s\"\n", argv[3]); + exit (2); + } + if ( ( fd = open ("/proc/mtrr", O_WRONLY, 0) ) == -1 ) + { + if (errno == ENOENT) + { + fputs ("/proc/mtrr not found: not supported or you don't have a PPro?\n", + stderr); + exit (3); + } + fprintf (stderr, "Error opening /proc/mtrr\t%s\n", ERRSTRING); + exit (4); + } + if (ioctl (fd, MTRRIOC_ADD_ENTRY, &sentry) == -1) + { + fprintf (stderr, "Error doing ioctl(2) on /dev/mtrr\t%s\n", ERRSTRING); + exit (5); + } + fprintf (stderr, "Sleeping for 5 seconds so you can see the new entry\n"); + sleep (5); + close (fd); + fputs ("I've just closed /proc/mtrr so now the new entry should be gone\n", + stderr); + } /* End Function main */ diff --git a/Documentation/x86/mtrr.txt b/Documentation/x86/mtrr.txt deleted file mode 100644 index dc3e703913ac..000000000000 --- a/Documentation/x86/mtrr.txt +++ /dev/null @@ -1,329 +0,0 @@ -MTRR (Memory Type Range Register) control - -Richard Gooch - 3 Jun 1999 -Luis R. Rodriguez - April 9, 2015 - -=============================================================================== -Phasing out MTRR use - -MTRR use is replaced on modern x86 hardware with PAT. Direct MTRR use by -drivers on Linux is now completely phased out, device drivers should use -arch_phys_wc_add() in combination with ioremap_wc() to make MTRR effective on -non-PAT systems while a no-op but equally effective on PAT enabled systems. - -Even if Linux does not use MTRRs directly, some x86 platform firmware may still -set up MTRRs early before booting the OS. They do this as some platform -firmware may still have implemented access to MTRRs which would be controlled -and handled by the platform firmware directly. An example of platform use of -MTRRs is through the use of SMI handlers, one case could be for fan control, -the platform code would need uncachable access to some of its fan control -registers. Such platform access does not need any Operating System MTRR code in -place other than mtrr_type_lookup() to ensure any OS specific mapping requests -are aligned with platform MTRR setup. If MTRRs are only set up by the platform -firmware code though and the OS does not make any specific MTRR mapping -requests mtrr_type_lookup() should always return MTRR_TYPE_INVALID. - -For details refer to Documentation/x86/pat.txt. - -=============================================================================== - - On Intel P6 family processors (Pentium Pro, Pentium II and later) - the Memory Type Range Registers (MTRRs) may be used to control - processor access to memory ranges. This is most useful when you have - a video (VGA) card on a PCI or AGP bus. Enabling write-combining - allows bus write transfers to be combined into a larger transfer - before bursting over the PCI/AGP bus. This can increase performance - of image write operations 2.5 times or more. - - The Cyrix 6x86, 6x86MX and M II processors have Address Range - Registers (ARRs) which provide a similar functionality to MTRRs. For - these, the ARRs are used to emulate the MTRRs. - - The AMD K6-2 (stepping 8 and above) and K6-3 processors have two - MTRRs. These are supported. The AMD Athlon family provide 8 Intel - style MTRRs. - - The Centaur C6 (WinChip) has 8 MCRs, allowing write-combining. These - are supported. - - The VIA Cyrix III and VIA C3 CPUs offer 8 Intel style MTRRs. - - The CONFIG_MTRR option creates a /proc/mtrr file which may be used - to manipulate your MTRRs. Typically the X server should use - this. This should have a reasonably generic interface so that - similar control registers on other processors can be easily - supported. - - -There are two interfaces to /proc/mtrr: one is an ASCII interface -which allows you to read and write. The other is an ioctl() -interface. The ASCII interface is meant for administration. The -ioctl() interface is meant for C programs (i.e. the X server). The -interfaces are described below, with sample commands and C code. - -=============================================================================== -Reading MTRRs from the shell: - -% cat /proc/mtrr -reg00: base=0x00000000 ( 0MB), size= 128MB: write-back, count=1 -reg01: base=0x08000000 ( 128MB), size= 64MB: write-back, count=1 -=============================================================================== -Creating MTRRs from the C-shell: -# echo "base=0xf8000000 size=0x400000 type=write-combining" >! /proc/mtrr -or if you use bash: -# echo "base=0xf8000000 size=0x400000 type=write-combining" >| /proc/mtrr - -And the result thereof: -% cat /proc/mtrr -reg00: base=0x00000000 ( 0MB), size= 128MB: write-back, count=1 -reg01: base=0x08000000 ( 128MB), size= 64MB: write-back, count=1 -reg02: base=0xf8000000 (3968MB), size= 4MB: write-combining, count=1 - -This is for video RAM at base address 0xf8000000 and size 4 megabytes. To -find out your base address, you need to look at the output of your X -server, which tells you where the linear framebuffer address is. A -typical line that you may get is: - -(--) S3: PCI: 968 rev 0, Linear FB @ 0xf8000000 - -Note that you should only use the value from the X server, as it may -move the framebuffer base address, so the only value you can trust is -that reported by the X server. - -To find out the size of your framebuffer (what, you don't actually -know?), the following line will tell you: - -(--) S3: videoram: 4096k - -That's 4 megabytes, which is 0x400000 bytes (in hexadecimal). -A patch is being written for XFree86 which will make this automatic: -in other words the X server will manipulate /proc/mtrr using the -ioctl() interface, so users won't have to do anything. If you use a -commercial X server, lobby your vendor to add support for MTRRs. -=============================================================================== -Creating overlapping MTRRs: - -%echo "base=0xfb000000 size=0x1000000 type=write-combining" >/proc/mtrr -%echo "base=0xfb000000 size=0x1000 type=uncachable" >/proc/mtrr - -And the results: cat /proc/mtrr -reg00: base=0x00000000 ( 0MB), size= 64MB: write-back, count=1 -reg01: base=0xfb000000 (4016MB), size= 16MB: write-combining, count=1 -reg02: base=0xfb000000 (4016MB), size= 4kB: uncachable, count=1 - -Some cards (especially Voodoo Graphics boards) need this 4 kB area -excluded from the beginning of the region because it is used for -registers. - -NOTE: You can only create type=uncachable region, if the first -region that you created is type=write-combining. -=============================================================================== -Removing MTRRs from the C-shell: -% echo "disable=2" >! /proc/mtrr -or using bash: -% echo "disable=2" >| /proc/mtrr -=============================================================================== -Reading MTRRs from a C program using ioctl()'s: - -/* mtrr-show.c - - Source file for mtrr-show (example program to show MTRRs using ioctl()'s) - - Copyright (C) 1997-1998 Richard Gooch - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Richard Gooch may be reached by email at rgooch@atnf.csiro.au - The postal address is: - Richard Gooch, c/o ATNF, P. O. Box 76, Epping, N.S.W., 2121, Australia. -*/ - -/* - This program will use an ioctl() on /proc/mtrr to show the current MTRR - settings. This is an alternative to reading /proc/mtrr. - - - Written by Richard Gooch 17-DEC-1997 - - Last updated by Richard Gooch 2-MAY-1998 - - -*/ -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#define TRUE 1 -#define FALSE 0 -#define ERRSTRING strerror (errno) - -static char *mtrr_strings[MTRR_NUM_TYPES] = -{ - "uncachable", /* 0 */ - "write-combining", /* 1 */ - "?", /* 2 */ - "?", /* 3 */ - "write-through", /* 4 */ - "write-protect", /* 5 */ - "write-back", /* 6 */ -}; - -int main () -{ - int fd; - struct mtrr_gentry gentry; - - if ( ( fd = open ("/proc/mtrr", O_RDONLY, 0) ) == -1 ) - { - if (errno == ENOENT) - { - fputs ("/proc/mtrr not found: not supported or you don't have a PPro?\n", - stderr); - exit (1); - } - fprintf (stderr, "Error opening /proc/mtrr\t%s\n", ERRSTRING); - exit (2); - } - for (gentry.regnum = 0; ioctl (fd, MTRRIOC_GET_ENTRY, &gentry) == 0; - ++gentry.regnum) - { - if (gentry.size < 1) - { - fprintf (stderr, "Register: %u disabled\n", gentry.regnum); - continue; - } - fprintf (stderr, "Register: %u base: 0x%lx size: 0x%lx type: %s\n", - gentry.regnum, gentry.base, gentry.size, - mtrr_strings[gentry.type]); - } - if (errno == EINVAL) exit (0); - fprintf (stderr, "Error doing ioctl(2) on /dev/mtrr\t%s\n", ERRSTRING); - exit (3); -} /* End Function main */ -=============================================================================== -Creating MTRRs from a C programme using ioctl()'s: - -/* mtrr-add.c - - Source file for mtrr-add (example programme to add an MTRRs using ioctl()) - - Copyright (C) 1997-1998 Richard Gooch - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. - - Richard Gooch may be reached by email at rgooch@atnf.csiro.au - The postal address is: - Richard Gooch, c/o ATNF, P. O. Box 76, Epping, N.S.W., 2121, Australia. -*/ - -/* - This programme will use an ioctl() on /proc/mtrr to add an entry. The first - available mtrr is used. This is an alternative to writing /proc/mtrr. - - - Written by Richard Gooch 17-DEC-1997 - - Last updated by Richard Gooch 2-MAY-1998 - - -*/ -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#define TRUE 1 -#define FALSE 0 -#define ERRSTRING strerror (errno) - -static char *mtrr_strings[MTRR_NUM_TYPES] = -{ - "uncachable", /* 0 */ - "write-combining", /* 1 */ - "?", /* 2 */ - "?", /* 3 */ - "write-through", /* 4 */ - "write-protect", /* 5 */ - "write-back", /* 6 */ -}; - -int main (int argc, char **argv) -{ - int fd; - struct mtrr_sentry sentry; - - if (argc != 4) - { - fprintf (stderr, "Usage:\tmtrr-add base size type\n"); - exit (1); - } - sentry.base = strtoul (argv[1], NULL, 0); - sentry.size = strtoul (argv[2], NULL, 0); - for (sentry.type = 0; sentry.type < MTRR_NUM_TYPES; ++sentry.type) - { - if (strcmp (argv[3], mtrr_strings[sentry.type]) == 0) break; - } - if (sentry.type >= MTRR_NUM_TYPES) - { - fprintf (stderr, "Illegal type: \"%s\"\n", argv[3]); - exit (2); - } - if ( ( fd = open ("/proc/mtrr", O_WRONLY, 0) ) == -1 ) - { - if (errno == ENOENT) - { - fputs ("/proc/mtrr not found: not supported or you don't have a PPro?\n", - stderr); - exit (3); - } - fprintf (stderr, "Error opening /proc/mtrr\t%s\n", ERRSTRING); - exit (4); - } - if (ioctl (fd, MTRRIOC_ADD_ENTRY, &sentry) == -1) - { - fprintf (stderr, "Error doing ioctl(2) on /dev/mtrr\t%s\n", ERRSTRING); - exit (5); - } - fprintf (stderr, "Sleeping for 5 seconds so you can see the new entry\n"); - sleep (5); - close (fd); - fputs ("I've just closed /proc/mtrr so now the new entry should be gone\n", - stderr); -} /* End Function main */ -=============================================================================== -- cgit v1.2.3 From 2f6eae4730120fd6459f55e47b750cd3570e9349 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:25 +0800 Subject: Documentation: x86: convert pat.txt to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Cc: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/index.rst | 1 + Documentation/x86/pat.rst | 242 ++++++++++++++++++++++++++++++++++++++++++++ Documentation/x86/pat.txt | 230 ----------------------------------------- 3 files changed, 243 insertions(+), 230 deletions(-) create mode 100644 Documentation/x86/pat.rst delete mode 100644 Documentation/x86/pat.txt (limited to 'Documentation') diff --git a/Documentation/x86/index.rst b/Documentation/x86/index.rst index 769c4491e9cb..f7012e4afacd 100644 --- a/Documentation/x86/index.rst +++ b/Documentation/x86/index.rst @@ -17,3 +17,4 @@ x86-specific Documentation zero-page tlb mtrr + pat diff --git a/Documentation/x86/pat.rst b/Documentation/x86/pat.rst new file mode 100644 index 000000000000..9a298fd97d74 --- /dev/null +++ b/Documentation/x86/pat.rst @@ -0,0 +1,242 @@ +.. SPDX-License-Identifier: GPL-2.0 + +========================== +PAT (Page Attribute Table) +========================== + +x86 Page Attribute Table (PAT) allows for setting the memory attribute at the +page level granularity. PAT is complementary to the MTRR settings which allows +for setting of memory types over physical address ranges. However, PAT is +more flexible than MTRR due to its capability to set attributes at page level +and also due to the fact that there are no hardware limitations on number of +such attribute settings allowed. Added flexibility comes with guidelines for +not having memory type aliasing for the same physical memory with multiple +virtual addresses. + +PAT allows for different types of memory attributes. The most commonly used +ones that will be supported at this time are: + +=== ============== +WB Write-back +UC Uncached +WC Write-combined +WT Write-through +UC- Uncached Minus +=== ============== + + +PAT APIs +======== + +There are many different APIs in the kernel that allows setting of memory +attributes at the page level. In order to avoid aliasing, these interfaces +should be used thoughtfully. Below is a table of interfaces available, +their intended usage and their memory attribute relationships. Internally, +these APIs use a reserve_memtype()/free_memtype() interface on the physical +address range to avoid any aliasing. + ++------------------------+----------+--------------+------------------+ +| API | RAM | ACPI,... | Reserved/Holes | ++------------------------+----------+--------------+------------------+ +| ioremap | -- | UC- | UC- | ++------------------------+----------+--------------+------------------+ +| ioremap_cache | -- | WB | WB | ++------------------------+----------+--------------+------------------+ +| ioremap_uc | -- | UC | UC | ++------------------------+----------+--------------+------------------+ +| ioremap_nocache | -- | UC- | UC- | ++------------------------+----------+--------------+------------------+ +| ioremap_wc | -- | -- | WC | ++------------------------+----------+--------------+------------------+ +| ioremap_wt | -- | -- | WT | ++------------------------+----------+--------------+------------------+ +| set_memory_uc, | UC- | -- | -- | +| set_memory_wb | | | | ++------------------------+----------+--------------+------------------+ +| set_memory_wc, | WC | -- | -- | +| set_memory_wb | | | | ++------------------------+----------+--------------+------------------+ +| set_memory_wt, | WT | -- | -- | +| set_memory_wb | | | | ++------------------------+----------+--------------+------------------+ +| pci sysfs resource | -- | -- | UC- | ++------------------------+----------+--------------+------------------+ +| pci sysfs resource_wc | -- | -- | WC | +| is IORESOURCE_PREFETCH | | | | ++------------------------+----------+--------------+------------------+ +| pci proc | -- | -- | UC- | +| !PCIIOC_WRITE_COMBINE | | | | ++------------------------+----------+--------------+------------------+ +| pci proc | -- | -- | WC | +| PCIIOC_WRITE_COMBINE | | | | ++------------------------+----------+--------------+------------------+ +| /dev/mem | -- | WB/WC/UC- | WB/WC/UC- | +| read-write | | | | ++------------------------+----------+--------------+------------------+ +| /dev/mem | -- | UC- | UC- | +| mmap SYNC flag | | | | ++------------------------+----------+--------------+------------------+ +| /dev/mem | -- | WB/WC/UC- | WB/WC/UC- | +| mmap !SYNC flag | | | | +| and | |(from existing| (from existing | +| any alias to this area | |alias) | alias) | ++------------------------+----------+--------------+------------------+ +| /dev/mem | -- | WB | WB | +| mmap !SYNC flag | | | | +| no alias to this area | | | | +| and | | | | +| MTRR says WB | | | | ++------------------------+----------+--------------+------------------+ +| /dev/mem | -- | -- | UC- | +| mmap !SYNC flag | | | | +| no alias to this area | | | | +| and | | | | +| MTRR says !WB | | | | ++------------------------+----------+--------------+------------------+ + + +Advanced APIs for drivers +========================= + +A. Exporting pages to users with remap_pfn_range, io_remap_pfn_range, +vmf_insert_pfn. + +Drivers wanting to export some pages to userspace do it by using mmap +interface and a combination of: + + 1) pgprot_noncached() + 2) io_remap_pfn_range() or remap_pfn_range() or vmf_insert_pfn() + +With PAT support, a new API pgprot_writecombine is being added. So, drivers can +continue to use the above sequence, with either pgprot_noncached() or +pgprot_writecombine() in step 1, followed by step 2. + +In addition, step 2 internally tracks the region as UC or WC in memtype +list in order to ensure no conflicting mapping. + +Note that this set of APIs only works with IO (non RAM) regions. If driver +wants to export a RAM region, it has to do set_memory_uc() or set_memory_wc() +as step 0 above and also track the usage of those pages and use set_memory_wb() +before the page is freed to free pool. + +MTRR effects on PAT / non-PAT systems +===================================== + +The following table provides the effects of using write-combining MTRRs when +using ioremap*() calls on x86 for both non-PAT and PAT systems. Ideally +mtrr_add() usage will be phased out in favor of arch_phys_wc_add() which will +be a no-op on PAT enabled systems. The region over which a arch_phys_wc_add() +is made, should already have been ioremapped with WC attributes or PAT entries, +this can be done by using ioremap_wc() / set_memory_wc(). Devices which +combine areas of IO memory desired to remain uncacheable with areas where +write-combining is desirable should consider use of ioremap_uc() followed by +set_memory_wc() to white-list effective write-combined areas. Such use is +nevertheless discouraged as the effective memory type is considered +implementation defined, yet this strategy can be used as last resort on devices +with size-constrained regions where otherwise MTRR write-combining would +otherwise not be effective. +:: + + ==== ======= === ========================= ===================== + MTRR Non-PAT PAT Linux ioremap value Effective memory type + ==== ======= === ========================= ===================== + PAT Non-PAT | PAT + |PCD | + ||PWT | + ||| | + WC 000 WB _PAGE_CACHE_MODE_WB WC | WC + WC 001 WC _PAGE_CACHE_MODE_WC WC* | WC + WC 010 UC- _PAGE_CACHE_MODE_UC_MINUS WC* | UC + WC 011 UC _PAGE_CACHE_MODE_UC UC | UC + ==== ======= === ========================= ===================== + + (*) denotes implementation defined and is discouraged + +.. note:: -- in the above table mean "Not suggested usage for the API". Some + of the --'s are strictly enforced by the kernel. Some others are not really + enforced today, but may be enforced in future. + +For ioremap and pci access through /sys or /proc - The actual type returned +can be more restrictive, in case of any existing aliasing for that address. +For example: If there is an existing uncached mapping, a new ioremap_wc can +return uncached mapping in place of write-combine requested. + +set_memory_[uc|wc|wt] and set_memory_wb should be used in pairs, where driver +will first make a region uc, wc or wt and switch it back to wb after use. + +Over time writes to /proc/mtrr will be deprecated in favor of using PAT based +interfaces. Users writing to /proc/mtrr are suggested to use above interfaces. + +Drivers should use ioremap_[uc|wc] to access PCI BARs with [uc|wc] access +types. + +Drivers should use set_memory_[uc|wc|wt] to set access type for RAM ranges. + + +PAT debugging +============= + +With CONFIG_DEBUG_FS enabled, PAT memtype list can be examined by:: + + # mount -t debugfs debugfs /sys/kernel/debug + # cat /sys/kernel/debug/x86/pat_memtype_list + PAT memtype list: + uncached-minus @ 0x7fadf000-0x7fae0000 + uncached-minus @ 0x7fb19000-0x7fb1a000 + uncached-minus @ 0x7fb1a000-0x7fb1b000 + uncached-minus @ 0x7fb1b000-0x7fb1c000 + uncached-minus @ 0x7fb1c000-0x7fb1d000 + uncached-minus @ 0x7fb1d000-0x7fb1e000 + uncached-minus @ 0x7fb1e000-0x7fb25000 + uncached-minus @ 0x7fb25000-0x7fb26000 + uncached-minus @ 0x7fb26000-0x7fb27000 + uncached-minus @ 0x7fb27000-0x7fb28000 + uncached-minus @ 0x7fb28000-0x7fb2e000 + uncached-minus @ 0x7fb2e000-0x7fb2f000 + uncached-minus @ 0x7fb2f000-0x7fb30000 + uncached-minus @ 0x7fb31000-0x7fb32000 + uncached-minus @ 0x80000000-0x90000000 + +This list shows physical address ranges and various PAT settings used to +access those physical address ranges. + +Another, more verbose way of getting PAT related debug messages is with +"debugpat" boot parameter. With this parameter, various debug messages are +printed to dmesg log. + +PAT Initialization +================== + +The following table describes how PAT is initialized under various +configurations. The PAT MSR must be updated by Linux in order to support WC +and WT attributes. Otherwise, the PAT MSR has the value programmed in it +by the firmware. Note, Xen enables WC attribute in the PAT MSR for guests. + + ==== ===== ========================== ========= ======= + MTRR PAT Call Sequence PAT State PAT MSR + ==== ===== ========================== ========= ======= + E E MTRR -> PAT init Enabled OS + E D MTRR -> PAT init Disabled - + D E MTRR -> PAT disable Disabled BIOS + D D MTRR -> PAT disable Disabled - + - np/E PAT -> PAT disable Disabled BIOS + - np/D PAT -> PAT disable Disabled - + E !P/E MTRR -> PAT init Disabled BIOS + D !P/E MTRR -> PAT disable Disabled BIOS + !M !P/E MTRR stub -> PAT disable Disabled BIOS + ==== ===== ========================== ========= ======= + + Legend + + ========= ======================================= + E Feature enabled in CPU + D Feature disabled/unsupported in CPU + np "nopat" boot option specified + !P CONFIG_X86_PAT option unset + !M CONFIG_MTRR option unset + Enabled PAT state set to enabled + Disabled PAT state set to disabled + OS PAT initializes PAT MSR with OS setting + BIOS PAT keeps PAT MSR with BIOS setting + ========= ======================================= + diff --git a/Documentation/x86/pat.txt b/Documentation/x86/pat.txt deleted file mode 100644 index 481d8d8536ac..000000000000 --- a/Documentation/x86/pat.txt +++ /dev/null @@ -1,230 +0,0 @@ - -PAT (Page Attribute Table) - -x86 Page Attribute Table (PAT) allows for setting the memory attribute at the -page level granularity. PAT is complementary to the MTRR settings which allows -for setting of memory types over physical address ranges. However, PAT is -more flexible than MTRR due to its capability to set attributes at page level -and also due to the fact that there are no hardware limitations on number of -such attribute settings allowed. Added flexibility comes with guidelines for -not having memory type aliasing for the same physical memory with multiple -virtual addresses. - -PAT allows for different types of memory attributes. The most commonly used -ones that will be supported at this time are Write-back, Uncached, -Write-combined, Write-through and Uncached Minus. - - -PAT APIs --------- - -There are many different APIs in the kernel that allows setting of memory -attributes at the page level. In order to avoid aliasing, these interfaces -should be used thoughtfully. Below is a table of interfaces available, -their intended usage and their memory attribute relationships. Internally, -these APIs use a reserve_memtype()/free_memtype() interface on the physical -address range to avoid any aliasing. - - -------------------------------------------------------------------- -API | RAM | ACPI,... | Reserved/Holes | ------------------------|----------|------------|------------------| - | | | | -ioremap | -- | UC- | UC- | - | | | | -ioremap_cache | -- | WB | WB | - | | | | -ioremap_uc | -- | UC | UC | - | | | | -ioremap_nocache | -- | UC- | UC- | - | | | | -ioremap_wc | -- | -- | WC | - | | | | -ioremap_wt | -- | -- | WT | - | | | | -set_memory_uc | UC- | -- | -- | - set_memory_wb | | | | - | | | | -set_memory_wc | WC | -- | -- | - set_memory_wb | | | | - | | | | -set_memory_wt | WT | -- | -- | - set_memory_wb | | | | - | | | | -pci sysfs resource | -- | -- | UC- | - | | | | -pci sysfs resource_wc | -- | -- | WC | - is IORESOURCE_PREFETCH| | | | - | | | | -pci proc | -- | -- | UC- | - !PCIIOC_WRITE_COMBINE | | | | - | | | | -pci proc | -- | -- | WC | - PCIIOC_WRITE_COMBINE | | | | - | | | | -/dev/mem | -- | WB/WC/UC- | WB/WC/UC- | - read-write | | | | - | | | | -/dev/mem | -- | UC- | UC- | - mmap SYNC flag | | | | - | | | | -/dev/mem | -- | WB/WC/UC- | WB/WC/UC- | - mmap !SYNC flag | |(from exist-| (from exist- | - and | | ing alias)| ing alias) | - any alias to this area| | | | - | | | | -/dev/mem | -- | WB | WB | - mmap !SYNC flag | | | | - no alias to this area | | | | - and | | | | - MTRR says WB | | | | - | | | | -/dev/mem | -- | -- | UC- | - mmap !SYNC flag | | | | - no alias to this area | | | | - and | | | | - MTRR says !WB | | | | - | | | | -------------------------------------------------------------------- - -Advanced APIs for drivers -------------------------- -A. Exporting pages to users with remap_pfn_range, io_remap_pfn_range, -vmf_insert_pfn - -Drivers wanting to export some pages to userspace do it by using mmap -interface and a combination of -1) pgprot_noncached() -2) io_remap_pfn_range() or remap_pfn_range() or vmf_insert_pfn() - -With PAT support, a new API pgprot_writecombine is being added. So, drivers can -continue to use the above sequence, with either pgprot_noncached() or -pgprot_writecombine() in step 1, followed by step 2. - -In addition, step 2 internally tracks the region as UC or WC in memtype -list in order to ensure no conflicting mapping. - -Note that this set of APIs only works with IO (non RAM) regions. If driver -wants to export a RAM region, it has to do set_memory_uc() or set_memory_wc() -as step 0 above and also track the usage of those pages and use set_memory_wb() -before the page is freed to free pool. - -MTRR effects on PAT / non-PAT systems -------------------------------------- - -The following table provides the effects of using write-combining MTRRs when -using ioremap*() calls on x86 for both non-PAT and PAT systems. Ideally -mtrr_add() usage will be phased out in favor of arch_phys_wc_add() which will -be a no-op on PAT enabled systems. The region over which a arch_phys_wc_add() -is made, should already have been ioremapped with WC attributes or PAT entries, -this can be done by using ioremap_wc() / set_memory_wc(). Devices which -combine areas of IO memory desired to remain uncacheable with areas where -write-combining is desirable should consider use of ioremap_uc() followed by -set_memory_wc() to white-list effective write-combined areas. Such use is -nevertheless discouraged as the effective memory type is considered -implementation defined, yet this strategy can be used as last resort on devices -with size-constrained regions where otherwise MTRR write-combining would -otherwise not be effective. - ----------------------------------------------------------------------- -MTRR Non-PAT PAT Linux ioremap value Effective memory type ----------------------------------------------------------------------- - Non-PAT | PAT - PAT - |PCD - ||PWT - ||| -WC 000 WB _PAGE_CACHE_MODE_WB WC | WC -WC 001 WC _PAGE_CACHE_MODE_WC WC* | WC -WC 010 UC- _PAGE_CACHE_MODE_UC_MINUS WC* | UC -WC 011 UC _PAGE_CACHE_MODE_UC UC | UC ----------------------------------------------------------------------- - -(*) denotes implementation defined and is discouraged - -Notes: - --- in the above table mean "Not suggested usage for the API". Some of the --'s -are strictly enforced by the kernel. Some others are not really enforced -today, but may be enforced in future. - -For ioremap and pci access through /sys or /proc - The actual type returned -can be more restrictive, in case of any existing aliasing for that address. -For example: If there is an existing uncached mapping, a new ioremap_wc can -return uncached mapping in place of write-combine requested. - -set_memory_[uc|wc|wt] and set_memory_wb should be used in pairs, where driver -will first make a region uc, wc or wt and switch it back to wb after use. - -Over time writes to /proc/mtrr will be deprecated in favor of using PAT based -interfaces. Users writing to /proc/mtrr are suggested to use above interfaces. - -Drivers should use ioremap_[uc|wc] to access PCI BARs with [uc|wc] access -types. - -Drivers should use set_memory_[uc|wc|wt] to set access type for RAM ranges. - - -PAT debugging -------------- - -With CONFIG_DEBUG_FS enabled, PAT memtype list can be examined by - -# mount -t debugfs debugfs /sys/kernel/debug -# cat /sys/kernel/debug/x86/pat_memtype_list -PAT memtype list: -uncached-minus @ 0x7fadf000-0x7fae0000 -uncached-minus @ 0x7fb19000-0x7fb1a000 -uncached-minus @ 0x7fb1a000-0x7fb1b000 -uncached-minus @ 0x7fb1b000-0x7fb1c000 -uncached-minus @ 0x7fb1c000-0x7fb1d000 -uncached-minus @ 0x7fb1d000-0x7fb1e000 -uncached-minus @ 0x7fb1e000-0x7fb25000 -uncached-minus @ 0x7fb25000-0x7fb26000 -uncached-minus @ 0x7fb26000-0x7fb27000 -uncached-minus @ 0x7fb27000-0x7fb28000 -uncached-minus @ 0x7fb28000-0x7fb2e000 -uncached-minus @ 0x7fb2e000-0x7fb2f000 -uncached-minus @ 0x7fb2f000-0x7fb30000 -uncached-minus @ 0x7fb31000-0x7fb32000 -uncached-minus @ 0x80000000-0x90000000 - -This list shows physical address ranges and various PAT settings used to -access those physical address ranges. - -Another, more verbose way of getting PAT related debug messages is with -"debugpat" boot parameter. With this parameter, various debug messages are -printed to dmesg log. - -PAT Initialization ------------------- - -The following table describes how PAT is initialized under various -configurations. The PAT MSR must be updated by Linux in order to support WC -and WT attributes. Otherwise, the PAT MSR has the value programmed in it -by the firmware. Note, Xen enables WC attribute in the PAT MSR for guests. - - MTRR PAT Call Sequence PAT State PAT MSR - ========================================================= - E E MTRR -> PAT init Enabled OS - E D MTRR -> PAT init Disabled - - D E MTRR -> PAT disable Disabled BIOS - D D MTRR -> PAT disable Disabled - - - np/E PAT -> PAT disable Disabled BIOS - - np/D PAT -> PAT disable Disabled - - E !P/E MTRR -> PAT init Disabled BIOS - D !P/E MTRR -> PAT disable Disabled BIOS - !M !P/E MTRR stub -> PAT disable Disabled BIOS - - Legend - ------------------------------------------------ - E Feature enabled in CPU - D Feature disabled/unsupported in CPU - np "nopat" boot option specified - !P CONFIG_X86_PAT option unset - !M CONFIG_MTRR option unset - Enabled PAT state set to enabled - Disabled PAT state set to disabled - OS PAT initializes PAT MSR with OS setting - BIOS PAT keeps PAT MSR with BIOS setting - -- cgit v1.2.3 From 28e21eac94a2ee2512ae6c21f04a0b41fb26cb0b Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:26 +0800 Subject: Documentation: x86: convert protection-keys.txt to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/index.rst | 1 + Documentation/x86/protection-keys.rst | 99 +++++++++++++++++++++++++++++++++++ Documentation/x86/protection-keys.txt | 90 ------------------------------- 3 files changed, 100 insertions(+), 90 deletions(-) create mode 100644 Documentation/x86/protection-keys.rst delete mode 100644 Documentation/x86/protection-keys.txt (limited to 'Documentation') diff --git a/Documentation/x86/index.rst b/Documentation/x86/index.rst index f7012e4afacd..e2c0db9fcd4e 100644 --- a/Documentation/x86/index.rst +++ b/Documentation/x86/index.rst @@ -18,3 +18,4 @@ x86-specific Documentation tlb mtrr pat + protection-keys diff --git a/Documentation/x86/protection-keys.rst b/Documentation/x86/protection-keys.rst new file mode 100644 index 000000000000..49d9833af871 --- /dev/null +++ b/Documentation/x86/protection-keys.rst @@ -0,0 +1,99 @@ +.. SPDX-License-Identifier: GPL-2.0 + +====================== +Memory Protection Keys +====================== + +Memory Protection Keys for Userspace (PKU aka PKEYs) is a feature +which is found on Intel's Skylake "Scalable Processor" Server CPUs. +It will be avalable in future non-server parts. + +For anyone wishing to test or use this feature, it is available in +Amazon's EC2 C5 instances and is known to work there using an Ubuntu +17.04 image. + +Memory Protection Keys provides a mechanism for enforcing page-based +protections, but without requiring modification of the page tables +when an application changes protection domains. It works by +dedicating 4 previously ignored bits in each page table entry to a +"protection key", giving 16 possible keys. + +There is also a new user-accessible register (PKRU) with two separate +bits (Access Disable and Write Disable) for each key. Being a CPU +register, PKRU is inherently thread-local, potentially giving each +thread a different set of protections from every other thread. + +There are two new instructions (RDPKRU/WRPKRU) for reading and writing +to the new register. The feature is only available in 64-bit mode, +even though there is theoretically space in the PAE PTEs. These +permissions are enforced on data access only and have no effect on +instruction fetches. + +Syscalls +======== + +There are 3 system calls which directly interact with pkeys:: + + int pkey_alloc(unsigned long flags, unsigned long init_access_rights) + int pkey_free(int pkey); + int pkey_mprotect(unsigned long start, size_t len, + unsigned long prot, int pkey); + +Before a pkey can be used, it must first be allocated with +pkey_alloc(). An application calls the WRPKRU instruction +directly in order to change access permissions to memory covered +with a key. In this example WRPKRU is wrapped by a C function +called pkey_set(). +:: + + int real_prot = PROT_READ|PROT_WRITE; + pkey = pkey_alloc(0, PKEY_DISABLE_WRITE); + ptr = mmap(NULL, PAGE_SIZE, PROT_NONE, MAP_ANONYMOUS|MAP_PRIVATE, -1, 0); + ret = pkey_mprotect(ptr, PAGE_SIZE, real_prot, pkey); + ... application runs here + +Now, if the application needs to update the data at 'ptr', it can +gain access, do the update, then remove its write access:: + + pkey_set(pkey, 0); // clear PKEY_DISABLE_WRITE + *ptr = foo; // assign something + pkey_set(pkey, PKEY_DISABLE_WRITE); // set PKEY_DISABLE_WRITE again + +Now when it frees the memory, it will also free the pkey since it +is no longer in use:: + + munmap(ptr, PAGE_SIZE); + pkey_free(pkey); + +.. note:: pkey_set() is a wrapper for the RDPKRU and WRPKRU instructions. + An example implementation can be found in + tools/testing/selftests/x86/protection_keys.c. + +Behavior +======== + +The kernel attempts to make protection keys consistent with the +behavior of a plain mprotect(). For instance if you do this:: + + mprotect(ptr, size, PROT_NONE); + something(ptr); + +you can expect the same effects with protection keys when doing this:: + + pkey = pkey_alloc(0, PKEY_DISABLE_WRITE | PKEY_DISABLE_READ); + pkey_mprotect(ptr, size, PROT_READ|PROT_WRITE, pkey); + something(ptr); + +That should be true whether something() is a direct access to 'ptr' +like:: + + *ptr = foo; + +or when the kernel does the access on the application's behalf like +with a read():: + + read(fd, ptr, 1); + +The kernel will send a SIGSEGV in both cases, but si_code will be set +to SEGV_PKERR when violating protection keys versus SEGV_ACCERR when +the plain mprotect() permissions are violated. diff --git a/Documentation/x86/protection-keys.txt b/Documentation/x86/protection-keys.txt deleted file mode 100644 index ecb0d2dadfb7..000000000000 --- a/Documentation/x86/protection-keys.txt +++ /dev/null @@ -1,90 +0,0 @@ -Memory Protection Keys for Userspace (PKU aka PKEYs) is a feature -which is found on Intel's Skylake "Scalable Processor" Server CPUs. -It will be avalable in future non-server parts. - -For anyone wishing to test or use this feature, it is available in -Amazon's EC2 C5 instances and is known to work there using an Ubuntu -17.04 image. - -Memory Protection Keys provides a mechanism for enforcing page-based -protections, but without requiring modification of the page tables -when an application changes protection domains. It works by -dedicating 4 previously ignored bits in each page table entry to a -"protection key", giving 16 possible keys. - -There is also a new user-accessible register (PKRU) with two separate -bits (Access Disable and Write Disable) for each key. Being a CPU -register, PKRU is inherently thread-local, potentially giving each -thread a different set of protections from every other thread. - -There are two new instructions (RDPKRU/WRPKRU) for reading and writing -to the new register. The feature is only available in 64-bit mode, -even though there is theoretically space in the PAE PTEs. These -permissions are enforced on data access only and have no effect on -instruction fetches. - -=========================== Syscalls =========================== - -There are 3 system calls which directly interact with pkeys: - - int pkey_alloc(unsigned long flags, unsigned long init_access_rights) - int pkey_free(int pkey); - int pkey_mprotect(unsigned long start, size_t len, - unsigned long prot, int pkey); - -Before a pkey can be used, it must first be allocated with -pkey_alloc(). An application calls the WRPKRU instruction -directly in order to change access permissions to memory covered -with a key. In this example WRPKRU is wrapped by a C function -called pkey_set(). - - int real_prot = PROT_READ|PROT_WRITE; - pkey = pkey_alloc(0, PKEY_DISABLE_WRITE); - ptr = mmap(NULL, PAGE_SIZE, PROT_NONE, MAP_ANONYMOUS|MAP_PRIVATE, -1, 0); - ret = pkey_mprotect(ptr, PAGE_SIZE, real_prot, pkey); - ... application runs here - -Now, if the application needs to update the data at 'ptr', it can -gain access, do the update, then remove its write access: - - pkey_set(pkey, 0); // clear PKEY_DISABLE_WRITE - *ptr = foo; // assign something - pkey_set(pkey, PKEY_DISABLE_WRITE); // set PKEY_DISABLE_WRITE again - -Now when it frees the memory, it will also free the pkey since it -is no longer in use: - - munmap(ptr, PAGE_SIZE); - pkey_free(pkey); - -(Note: pkey_set() is a wrapper for the RDPKRU and WRPKRU instructions. - An example implementation can be found in - tools/testing/selftests/x86/protection_keys.c) - -=========================== Behavior =========================== - -The kernel attempts to make protection keys consistent with the -behavior of a plain mprotect(). For instance if you do this: - - mprotect(ptr, size, PROT_NONE); - something(ptr); - -you can expect the same effects with protection keys when doing this: - - pkey = pkey_alloc(0, PKEY_DISABLE_WRITE | PKEY_DISABLE_READ); - pkey_mprotect(ptr, size, PROT_READ|PROT_WRITE, pkey); - something(ptr); - -That should be true whether something() is a direct access to 'ptr' -like: - - *ptr = foo; - -or when the kernel does the access on the application's behalf like -with a read(): - - read(fd, ptr, 1); - -The kernel will send a SIGSEGV in both cases, but si_code will be set -to SEGV_PKERR when violating protection keys versus SEGV_ACCERR when -the plain mprotect() permissions are violated. -- cgit v1.2.3 From f10b07a01a48d0584fa9815005e04c54058e2e47 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:27 +0800 Subject: Documentation: x86: convert intel_mpx.txt to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/index.rst | 1 + Documentation/x86/intel_mpx.rst | 252 ++++++++++++++++++++++++++++++++++++++++ Documentation/x86/intel_mpx.txt | 244 -------------------------------------- 3 files changed, 253 insertions(+), 244 deletions(-) create mode 100644 Documentation/x86/intel_mpx.rst delete mode 100644 Documentation/x86/intel_mpx.txt (limited to 'Documentation') diff --git a/Documentation/x86/index.rst b/Documentation/x86/index.rst index e2c0db9fcd4e..b5cdc0d889b3 100644 --- a/Documentation/x86/index.rst +++ b/Documentation/x86/index.rst @@ -19,3 +19,4 @@ x86-specific Documentation mtrr pat protection-keys + intel_mpx diff --git a/Documentation/x86/intel_mpx.rst b/Documentation/x86/intel_mpx.rst new file mode 100644 index 000000000000..387a640941a6 --- /dev/null +++ b/Documentation/x86/intel_mpx.rst @@ -0,0 +1,252 @@ +.. SPDX-License-Identifier: GPL-2.0 + +=========================================== +Intel(R) Memory Protection Extensions (MPX) +=========================================== + +Intel(R) MPX Overview +===================== + +Intel(R) Memory Protection Extensions (Intel(R) MPX) is a new capability +introduced into Intel Architecture. Intel MPX provides hardware features +that can be used in conjunction with compiler changes to check memory +references, for those references whose compile-time normal intentions are +usurped at runtime due to buffer overflow or underflow. + +You can tell if your CPU supports MPX by looking in /proc/cpuinfo:: + + cat /proc/cpuinfo | grep ' mpx ' + +For more information, please refer to Intel(R) Architecture Instruction +Set Extensions Programming Reference, Chapter 9: Intel(R) Memory Protection +Extensions. + +Note: As of December 2014, no hardware with MPX is available but it is +possible to use SDE (Intel(R) Software Development Emulator) instead, which +can be downloaded from +http://software.intel.com/en-us/articles/intel-software-development-emulator + + +How to get the advantage of MPX +=============================== + +For MPX to work, changes are required in the kernel, binutils and compiler. +No source changes are required for applications, just a recompile. + +There are a lot of moving parts of this to all work right. The following +is how we expect the compiler, application and kernel to work together. + +1) Application developer compiles with -fmpx. The compiler will add the + instrumentation as well as some setup code called early after the app + starts. New instruction prefixes are noops for old CPUs. +2) That setup code allocates (virtual) space for the "bounds directory", + points the "bndcfgu" register to the directory (must also set the valid + bit) and notifies the kernel (via the new prctl(PR_MPX_ENABLE_MANAGEMENT)) + that the app will be using MPX. The app must be careful not to access + the bounds tables between the time when it populates "bndcfgu" and + when it calls the prctl(). This might be hard to guarantee if the app + is compiled with MPX. You can add "__attribute__((bnd_legacy))" to + the function to disable MPX instrumentation to help guarantee this. + Also be careful not to call out to any other code which might be + MPX-instrumented. +3) The kernel detects that the CPU has MPX, allows the new prctl() to + succeed, and notes the location of the bounds directory. Userspace is + expected to keep the bounds directory at that location. We note it + instead of reading it each time because the 'xsave' operation needed + to access the bounds directory register is an expensive operation. +4) If the application needs to spill bounds out of the 4 registers, it + issues a bndstx instruction. Since the bounds directory is empty at + this point, a bounds fault (#BR) is raised, the kernel allocates a + bounds table (in the user address space) and makes the relevant entry + in the bounds directory point to the new table. +5) If the application violates the bounds specified in the bounds registers, + a separate kind of #BR is raised which will deliver a signal with + information about the violation in the 'struct siginfo'. +6) Whenever memory is freed, we know that it can no longer contain valid + pointers, and we attempt to free the associated space in the bounds + tables. If an entire table becomes unused, we will attempt to free + the table and remove the entry in the directory. + +To summarize, there are essentially three things interacting here: + +GCC with -fmpx: + * enables annotation of code with MPX instructions and prefixes + * inserts code early in the application to call in to the "gcc runtime" +GCC MPX Runtime: + * Checks for hardware MPX support in cpuid leaf + * allocates virtual space for the bounds directory (malloc() essentially) + * points the hardware BNDCFGU register at the directory + * calls a new prctl(PR_MPX_ENABLE_MANAGEMENT) to notify the kernel to + start managing the bounds directories +Kernel MPX Code: + * Checks for hardware MPX support in cpuid leaf + * Handles #BR exceptions and sends SIGSEGV to the app when it violates + bounds, like during a buffer overflow. + * When bounds are spilled in to an unallocated bounds table, the kernel + notices in the #BR exception, allocates the virtual space, then + updates the bounds directory to point to the new table. It keeps + special track of the memory with a VM_MPX flag. + * Frees unused bounds tables at the time that the memory they described + is unmapped. + + +How does MPX kernel code work +============================= + +Handling #BR faults caused by MPX +--------------------------------- + +When MPX is enabled, there are 2 new situations that can generate +#BR faults. + + * new bounds tables (BT) need to be allocated to save bounds. + * bounds violation caused by MPX instructions. + +We hook #BR handler to handle these two new situations. + +On-demand kernel allocation of bounds tables +-------------------------------------------- + +MPX only has 4 hardware registers for storing bounds information. If +MPX-enabled code needs more than these 4 registers, it needs to spill +them somewhere. It has two special instructions for this which allow +the bounds to be moved between the bounds registers and some new "bounds +tables". + +#BR exceptions are a new class of exceptions just for MPX. They are +similar conceptually to a page fault and will be raised by the MPX +hardware during both bounds violations or when the tables are not +present. The kernel handles those #BR exceptions for not-present tables +by carving the space out of the normal processes address space and then +pointing the bounds-directory over to it. + +The tables need to be accessed and controlled by userspace because +the instructions for moving bounds in and out of them are extremely +frequent. They potentially happen every time a register points to +memory. Any direct kernel involvement (like a syscall) to access the +tables would obviously destroy performance. + +Why not do this in userspace? MPX does not strictly require anything in +the kernel. It can theoretically be done completely from userspace. Here +are a few ways this could be done. We don't think any of them are practical +in the real-world, but here they are. + +:Q: Can virtual space simply be reserved for the bounds tables so that we + never have to allocate them? +:A: MPX-enabled application will possibly create a lot of bounds tables in + process address space to save bounds information. These tables can take + up huge swaths of memory (as much as 80% of the memory on the system) + even if we clean them up aggressively. In the worst-case scenario, the + tables can be 4x the size of the data structure being tracked. IOW, a + 1-page structure can require 4 bounds-table pages. An X-GB virtual + area needs 4*X GB of virtual space, plus 2GB for the bounds directory. + If we were to preallocate them for the 128TB of user virtual address + space, we would need to reserve 512TB+2GB, which is larger than the + entire virtual address space today. This means they can not be reserved + ahead of time. Also, a single process's pre-populated bounds directory + consumes 2GB of virtual *AND* physical memory. IOW, it's completely + infeasible to prepopulate bounds directories. + +:Q: Can we preallocate bounds table space at the same time memory is + allocated which might contain pointers that might eventually need + bounds tables? +:A: This would work if we could hook the site of each and every memory + allocation syscall. This can be done for small, constrained applications. + But, it isn't practical at a larger scale since a given app has no + way of controlling how all the parts of the app might allocate memory + (think libraries). The kernel is really the only place to intercept + these calls. + +:Q: Could a bounds fault be handed to userspace and the tables allocated + there in a signal handler instead of in the kernel? +:A: mmap() is not on the list of safe async handler functions and even + if mmap() would work it still requires locking or nasty tricks to + keep track of the allocation state there. + +Having ruled out all of the userspace-only approaches for managing +bounds tables that we could think of, we create them on demand in +the kernel. + +Decoding MPX instructions +------------------------- + +If a #BR is generated due to a bounds violation caused by MPX. +We need to decode MPX instructions to get violation address and +set this address into extended struct siginfo. + +The _sigfault field of struct siginfo is extended as follow:: + + 87 /* SIGILL, SIGFPE, SIGSEGV, SIGBUS */ + 88 struct { + 89 void __user *_addr; /* faulting insn/memory ref. */ + 90 #ifdef __ARCH_SI_TRAPNO + 91 int _trapno; /* TRAP # which caused the signal */ + 92 #endif + 93 short _addr_lsb; /* LSB of the reported address */ + 94 struct { + 95 void __user *_lower; + 96 void __user *_upper; + 97 } _addr_bnd; + 98 } _sigfault; + +The '_addr' field refers to violation address, and new '_addr_and' +field refers to the upper/lower bounds when a #BR is caused. + +Glibc will be also updated to support this new siginfo. So user +can get violation address and bounds when bounds violations occur. + +Cleanup unused bounds tables +---------------------------- + +When a BNDSTX instruction attempts to save bounds to a bounds directory +entry marked as invalid, a #BR is generated. This is an indication that +no bounds table exists for this entry. In this case the fault handler +will allocate a new bounds table on demand. + +Since the kernel allocated those tables on-demand without userspace +knowledge, it is also responsible for freeing them when the associated +mappings go away. + +Here, the solution for this issue is to hook do_munmap() to check +whether one process is MPX enabled. If yes, those bounds tables covered +in the virtual address region which is being unmapped will be freed also. + +Adding new prctl commands +------------------------- + +Two new prctl commands are added to enable and disable MPX bounds tables +management in kernel. +:: + + 155 #define PR_MPX_ENABLE_MANAGEMENT 43 + 156 #define PR_MPX_DISABLE_MANAGEMENT 44 + +Runtime library in userspace is responsible for allocation of bounds +directory. So kernel have to use XSAVE instruction to get the base +of bounds directory from BNDCFG register. + +But XSAVE is expected to be very expensive. In order to do performance +optimization, we have to get the base of bounds directory and save it +into struct mm_struct to be used in future during PR_MPX_ENABLE_MANAGEMENT +command execution. + + +Special rules +============= + +1) If userspace is requesting help from the kernel to do the management +of bounds tables, it may not create or modify entries in the bounds directory. + +Certainly users can allocate bounds tables and forcibly point the bounds +directory at them through XSAVE instruction, and then set valid bit +of bounds entry to have this entry valid. But, the kernel will decline +to assist in managing these tables. + +2) Userspace may not take multiple bounds directory entries and point +them at the same bounds table. + +This is allowed architecturally. See more information "Intel(R) Architecture +Instruction Set Extensions Programming Reference" (9.3.4). + +However, if users did this, the kernel might be fooled in to unmapping an +in-use bounds table since it does not recognize sharing. diff --git a/Documentation/x86/intel_mpx.txt b/Documentation/x86/intel_mpx.txt deleted file mode 100644 index 85d0549ad846..000000000000 --- a/Documentation/x86/intel_mpx.txt +++ /dev/null @@ -1,244 +0,0 @@ -1. Intel(R) MPX Overview -======================== - -Intel(R) Memory Protection Extensions (Intel(R) MPX) is a new capability -introduced into Intel Architecture. Intel MPX provides hardware features -that can be used in conjunction with compiler changes to check memory -references, for those references whose compile-time normal intentions are -usurped at runtime due to buffer overflow or underflow. - -You can tell if your CPU supports MPX by looking in /proc/cpuinfo: - - cat /proc/cpuinfo | grep ' mpx ' - -For more information, please refer to Intel(R) Architecture Instruction -Set Extensions Programming Reference, Chapter 9: Intel(R) Memory Protection -Extensions. - -Note: As of December 2014, no hardware with MPX is available but it is -possible to use SDE (Intel(R) Software Development Emulator) instead, which -can be downloaded from -http://software.intel.com/en-us/articles/intel-software-development-emulator - - -2. How to get the advantage of MPX -================================== - -For MPX to work, changes are required in the kernel, binutils and compiler. -No source changes are required for applications, just a recompile. - -There are a lot of moving parts of this to all work right. The following -is how we expect the compiler, application and kernel to work together. - -1) Application developer compiles with -fmpx. The compiler will add the - instrumentation as well as some setup code called early after the app - starts. New instruction prefixes are noops for old CPUs. -2) That setup code allocates (virtual) space for the "bounds directory", - points the "bndcfgu" register to the directory (must also set the valid - bit) and notifies the kernel (via the new prctl(PR_MPX_ENABLE_MANAGEMENT)) - that the app will be using MPX. The app must be careful not to access - the bounds tables between the time when it populates "bndcfgu" and - when it calls the prctl(). This might be hard to guarantee if the app - is compiled with MPX. You can add "__attribute__((bnd_legacy))" to - the function to disable MPX instrumentation to help guarantee this. - Also be careful not to call out to any other code which might be - MPX-instrumented. -3) The kernel detects that the CPU has MPX, allows the new prctl() to - succeed, and notes the location of the bounds directory. Userspace is - expected to keep the bounds directory at that location. We note it - instead of reading it each time because the 'xsave' operation needed - to access the bounds directory register is an expensive operation. -4) If the application needs to spill bounds out of the 4 registers, it - issues a bndstx instruction. Since the bounds directory is empty at - this point, a bounds fault (#BR) is raised, the kernel allocates a - bounds table (in the user address space) and makes the relevant entry - in the bounds directory point to the new table. -5) If the application violates the bounds specified in the bounds registers, - a separate kind of #BR is raised which will deliver a signal with - information about the violation in the 'struct siginfo'. -6) Whenever memory is freed, we know that it can no longer contain valid - pointers, and we attempt to free the associated space in the bounds - tables. If an entire table becomes unused, we will attempt to free - the table and remove the entry in the directory. - -To summarize, there are essentially three things interacting here: - -GCC with -fmpx: - * enables annotation of code with MPX instructions and prefixes - * inserts code early in the application to call in to the "gcc runtime" -GCC MPX Runtime: - * Checks for hardware MPX support in cpuid leaf - * allocates virtual space for the bounds directory (malloc() essentially) - * points the hardware BNDCFGU register at the directory - * calls a new prctl(PR_MPX_ENABLE_MANAGEMENT) to notify the kernel to - start managing the bounds directories -Kernel MPX Code: - * Checks for hardware MPX support in cpuid leaf - * Handles #BR exceptions and sends SIGSEGV to the app when it violates - bounds, like during a buffer overflow. - * When bounds are spilled in to an unallocated bounds table, the kernel - notices in the #BR exception, allocates the virtual space, then - updates the bounds directory to point to the new table. It keeps - special track of the memory with a VM_MPX flag. - * Frees unused bounds tables at the time that the memory they described - is unmapped. - - -3. How does MPX kernel code work -================================ - -Handling #BR faults caused by MPX ---------------------------------- - -When MPX is enabled, there are 2 new situations that can generate -#BR faults. - * new bounds tables (BT) need to be allocated to save bounds. - * bounds violation caused by MPX instructions. - -We hook #BR handler to handle these two new situations. - -On-demand kernel allocation of bounds tables --------------------------------------------- - -MPX only has 4 hardware registers for storing bounds information. If -MPX-enabled code needs more than these 4 registers, it needs to spill -them somewhere. It has two special instructions for this which allow -the bounds to be moved between the bounds registers and some new "bounds -tables". - -#BR exceptions are a new class of exceptions just for MPX. They are -similar conceptually to a page fault and will be raised by the MPX -hardware during both bounds violations or when the tables are not -present. The kernel handles those #BR exceptions for not-present tables -by carving the space out of the normal processes address space and then -pointing the bounds-directory over to it. - -The tables need to be accessed and controlled by userspace because -the instructions for moving bounds in and out of them are extremely -frequent. They potentially happen every time a register points to -memory. Any direct kernel involvement (like a syscall) to access the -tables would obviously destroy performance. - -Why not do this in userspace? MPX does not strictly require anything in -the kernel. It can theoretically be done completely from userspace. Here -are a few ways this could be done. We don't think any of them are practical -in the real-world, but here they are. - -Q: Can virtual space simply be reserved for the bounds tables so that we - never have to allocate them? -A: MPX-enabled application will possibly create a lot of bounds tables in - process address space to save bounds information. These tables can take - up huge swaths of memory (as much as 80% of the memory on the system) - even if we clean them up aggressively. In the worst-case scenario, the - tables can be 4x the size of the data structure being tracked. IOW, a - 1-page structure can require 4 bounds-table pages. An X-GB virtual - area needs 4*X GB of virtual space, plus 2GB for the bounds directory. - If we were to preallocate them for the 128TB of user virtual address - space, we would need to reserve 512TB+2GB, which is larger than the - entire virtual address space today. This means they can not be reserved - ahead of time. Also, a single process's pre-populated bounds directory - consumes 2GB of virtual *AND* physical memory. IOW, it's completely - infeasible to prepopulate bounds directories. - -Q: Can we preallocate bounds table space at the same time memory is - allocated which might contain pointers that might eventually need - bounds tables? -A: This would work if we could hook the site of each and every memory - allocation syscall. This can be done for small, constrained applications. - But, it isn't practical at a larger scale since a given app has no - way of controlling how all the parts of the app might allocate memory - (think libraries). The kernel is really the only place to intercept - these calls. - -Q: Could a bounds fault be handed to userspace and the tables allocated - there in a signal handler instead of in the kernel? -A: mmap() is not on the list of safe async handler functions and even - if mmap() would work it still requires locking or nasty tricks to - keep track of the allocation state there. - -Having ruled out all of the userspace-only approaches for managing -bounds tables that we could think of, we create them on demand in -the kernel. - -Decoding MPX instructions -------------------------- - -If a #BR is generated due to a bounds violation caused by MPX. -We need to decode MPX instructions to get violation address and -set this address into extended struct siginfo. - -The _sigfault field of struct siginfo is extended as follow: - -87 /* SIGILL, SIGFPE, SIGSEGV, SIGBUS */ -88 struct { -89 void __user *_addr; /* faulting insn/memory ref. */ -90 #ifdef __ARCH_SI_TRAPNO -91 int _trapno; /* TRAP # which caused the signal */ -92 #endif -93 short _addr_lsb; /* LSB of the reported address */ -94 struct { -95 void __user *_lower; -96 void __user *_upper; -97 } _addr_bnd; -98 } _sigfault; - -The '_addr' field refers to violation address, and new '_addr_and' -field refers to the upper/lower bounds when a #BR is caused. - -Glibc will be also updated to support this new siginfo. So user -can get violation address and bounds when bounds violations occur. - -Cleanup unused bounds tables ----------------------------- - -When a BNDSTX instruction attempts to save bounds to a bounds directory -entry marked as invalid, a #BR is generated. This is an indication that -no bounds table exists for this entry. In this case the fault handler -will allocate a new bounds table on demand. - -Since the kernel allocated those tables on-demand without userspace -knowledge, it is also responsible for freeing them when the associated -mappings go away. - -Here, the solution for this issue is to hook do_munmap() to check -whether one process is MPX enabled. If yes, those bounds tables covered -in the virtual address region which is being unmapped will be freed also. - -Adding new prctl commands -------------------------- - -Two new prctl commands are added to enable and disable MPX bounds tables -management in kernel. - -155 #define PR_MPX_ENABLE_MANAGEMENT 43 -156 #define PR_MPX_DISABLE_MANAGEMENT 44 - -Runtime library in userspace is responsible for allocation of bounds -directory. So kernel have to use XSAVE instruction to get the base -of bounds directory from BNDCFG register. - -But XSAVE is expected to be very expensive. In order to do performance -optimization, we have to get the base of bounds directory and save it -into struct mm_struct to be used in future during PR_MPX_ENABLE_MANAGEMENT -command execution. - - -4. Special rules -================ - -1) If userspace is requesting help from the kernel to do the management -of bounds tables, it may not create or modify entries in the bounds directory. - -Certainly users can allocate bounds tables and forcibly point the bounds -directory at them through XSAVE instruction, and then set valid bit -of bounds entry to have this entry valid. But, the kernel will decline -to assist in managing these tables. - -2) Userspace may not take multiple bounds directory entries and point -them at the same bounds table. - -This is allowed architecturally. See more information "Intel(R) Architecture -Instruction Set Extensions Programming Reference" (9.3.4). - -However, if users did this, the kernel might be fooled in to unmapping an -in-use bounds table since it does not recognize sharing. -- cgit v1.2.3 From 0c7180f2e4e6fc02f268e18c4f753d9f9cdfb5ad Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:28 +0800 Subject: Documentation: x86: convert amd-memory-encryption.txt to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/amd-memory-encryption.rst | 97 +++++++++++++++++++++++++++++ Documentation/x86/amd-memory-encryption.txt | 90 -------------------------- Documentation/x86/index.rst | 1 + 3 files changed, 98 insertions(+), 90 deletions(-) create mode 100644 Documentation/x86/amd-memory-encryption.rst delete mode 100644 Documentation/x86/amd-memory-encryption.txt (limited to 'Documentation') diff --git a/Documentation/x86/amd-memory-encryption.rst b/Documentation/x86/amd-memory-encryption.rst new file mode 100644 index 000000000000..c48d452d0718 --- /dev/null +++ b/Documentation/x86/amd-memory-encryption.rst @@ -0,0 +1,97 @@ +.. SPDX-License-Identifier: GPL-2.0 + +===================== +AMD Memory Encryption +===================== + +Secure Memory Encryption (SME) and Secure Encrypted Virtualization (SEV) are +features found on AMD processors. + +SME provides the ability to mark individual pages of memory as encrypted using +the standard x86 page tables. A page that is marked encrypted will be +automatically decrypted when read from DRAM and encrypted when written to +DRAM. SME can therefore be used to protect the contents of DRAM from physical +attacks on the system. + +SEV enables running encrypted virtual machines (VMs) in which the code and data +of the guest VM are secured so that a decrypted version is available only +within the VM itself. SEV guest VMs have the concept of private and shared +memory. Private memory is encrypted with the guest-specific key, while shared +memory may be encrypted with hypervisor key. When SME is enabled, the hypervisor +key is the same key which is used in SME. + +A page is encrypted when a page table entry has the encryption bit set (see +below on how to determine its position). The encryption bit can also be +specified in the cr3 register, allowing the PGD table to be encrypted. Each +successive level of page tables can also be encrypted by setting the encryption +bit in the page table entry that points to the next table. This allows the full +page table hierarchy to be encrypted. Note, this means that just because the +encryption bit is set in cr3, doesn't imply the full hierarchy is encrypted. +Each page table entry in the hierarchy needs to have the encryption bit set to +achieve that. So, theoretically, you could have the encryption bit set in cr3 +so that the PGD is encrypted, but not set the encryption bit in the PGD entry +for a PUD which results in the PUD pointed to by that entry to not be +encrypted. + +When SEV is enabled, instruction pages and guest page tables are always treated +as private. All the DMA operations inside the guest must be performed on shared +memory. Since the memory encryption bit is controlled by the guest OS when it +is operating in 64-bit or 32-bit PAE mode, in all other modes the SEV hardware +forces the memory encryption bit to 1. + +Support for SME and SEV can be determined through the CPUID instruction. The +CPUID function 0x8000001f reports information related to SME:: + + 0x8000001f[eax]: + Bit[0] indicates support for SME + Bit[1] indicates support for SEV + 0x8000001f[ebx]: + Bits[5:0] pagetable bit number used to activate memory + encryption + Bits[11:6] reduction in physical address space, in bits, when + memory encryption is enabled (this only affects + system physical addresses, not guest physical + addresses) + +If support for SME is present, MSR 0xc00100010 (MSR_K8_SYSCFG) can be used to +determine if SME is enabled and/or to enable memory encryption:: + + 0xc0010010: + Bit[23] 0 = memory encryption features are disabled + 1 = memory encryption features are enabled + +If SEV is supported, MSR 0xc0010131 (MSR_AMD64_SEV) can be used to determine if +SEV is active:: + + 0xc0010131: + Bit[0] 0 = memory encryption is not active + 1 = memory encryption is active + +Linux relies on BIOS to set this bit if BIOS has determined that the reduction +in the physical address space as a result of enabling memory encryption (see +CPUID information above) will not conflict with the address space resource +requirements for the system. If this bit is not set upon Linux startup then +Linux itself will not set it and memory encryption will not be possible. + +The state of SME in the Linux kernel can be documented as follows: + + - Supported: + The CPU supports SME (determined through CPUID instruction). + + - Enabled: + Supported and bit 23 of MSR_K8_SYSCFG is set. + + - Active: + Supported, Enabled and the Linux kernel is actively applying + the encryption bit to page table entries (the SME mask in the + kernel is non-zero). + +SME can also be enabled and activated in the BIOS. If SME is enabled and +activated in the BIOS, then all memory accesses will be encrypted and it will +not be necessary to activate the Linux memory encryption support. If the BIOS +merely enables SME (sets bit 23 of the MSR_K8_SYSCFG), then Linux can activate +memory encryption by default (CONFIG_AMD_MEM_ENCRYPT_ACTIVE_BY_DEFAULT=y) or +by supplying mem_encrypt=on on the kernel command line. However, if BIOS does +not enable SME, then Linux will not be able to activate memory encryption, even +if configured to do so by default or the mem_encrypt=on command line parameter +is specified. diff --git a/Documentation/x86/amd-memory-encryption.txt b/Documentation/x86/amd-memory-encryption.txt deleted file mode 100644 index afc41f544dab..000000000000 --- a/Documentation/x86/amd-memory-encryption.txt +++ /dev/null @@ -1,90 +0,0 @@ -Secure Memory Encryption (SME) and Secure Encrypted Virtualization (SEV) are -features found on AMD processors. - -SME provides the ability to mark individual pages of memory as encrypted using -the standard x86 page tables. A page that is marked encrypted will be -automatically decrypted when read from DRAM and encrypted when written to -DRAM. SME can therefore be used to protect the contents of DRAM from physical -attacks on the system. - -SEV enables running encrypted virtual machines (VMs) in which the code and data -of the guest VM are secured so that a decrypted version is available only -within the VM itself. SEV guest VMs have the concept of private and shared -memory. Private memory is encrypted with the guest-specific key, while shared -memory may be encrypted with hypervisor key. When SME is enabled, the hypervisor -key is the same key which is used in SME. - -A page is encrypted when a page table entry has the encryption bit set (see -below on how to determine its position). The encryption bit can also be -specified in the cr3 register, allowing the PGD table to be encrypted. Each -successive level of page tables can also be encrypted by setting the encryption -bit in the page table entry that points to the next table. This allows the full -page table hierarchy to be encrypted. Note, this means that just because the -encryption bit is set in cr3, doesn't imply the full hierarchy is encrypted. -Each page table entry in the hierarchy needs to have the encryption bit set to -achieve that. So, theoretically, you could have the encryption bit set in cr3 -so that the PGD is encrypted, but not set the encryption bit in the PGD entry -for a PUD which results in the PUD pointed to by that entry to not be -encrypted. - -When SEV is enabled, instruction pages and guest page tables are always treated -as private. All the DMA operations inside the guest must be performed on shared -memory. Since the memory encryption bit is controlled by the guest OS when it -is operating in 64-bit or 32-bit PAE mode, in all other modes the SEV hardware -forces the memory encryption bit to 1. - -Support for SME and SEV can be determined through the CPUID instruction. The -CPUID function 0x8000001f reports information related to SME: - - 0x8000001f[eax]: - Bit[0] indicates support for SME - Bit[1] indicates support for SEV - 0x8000001f[ebx]: - Bits[5:0] pagetable bit number used to activate memory - encryption - Bits[11:6] reduction in physical address space, in bits, when - memory encryption is enabled (this only affects - system physical addresses, not guest physical - addresses) - -If support for SME is present, MSR 0xc00100010 (MSR_K8_SYSCFG) can be used to -determine if SME is enabled and/or to enable memory encryption: - - 0xc0010010: - Bit[23] 0 = memory encryption features are disabled - 1 = memory encryption features are enabled - -If SEV is supported, MSR 0xc0010131 (MSR_AMD64_SEV) can be used to determine if -SEV is active: - - 0xc0010131: - Bit[0] 0 = memory encryption is not active - 1 = memory encryption is active - -Linux relies on BIOS to set this bit if BIOS has determined that the reduction -in the physical address space as a result of enabling memory encryption (see -CPUID information above) will not conflict with the address space resource -requirements for the system. If this bit is not set upon Linux startup then -Linux itself will not set it and memory encryption will not be possible. - -The state of SME in the Linux kernel can be documented as follows: - - Supported: - The CPU supports SME (determined through CPUID instruction). - - - Enabled: - Supported and bit 23 of MSR_K8_SYSCFG is set. - - - Active: - Supported, Enabled and the Linux kernel is actively applying - the encryption bit to page table entries (the SME mask in the - kernel is non-zero). - -SME can also be enabled and activated in the BIOS. If SME is enabled and -activated in the BIOS, then all memory accesses will be encrypted and it will -not be necessary to activate the Linux memory encryption support. If the BIOS -merely enables SME (sets bit 23 of the MSR_K8_SYSCFG), then Linux can activate -memory encryption by default (CONFIG_AMD_MEM_ENCRYPT_ACTIVE_BY_DEFAULT=y) or -by supplying mem_encrypt=on on the kernel command line. However, if BIOS does -not enable SME, then Linux will not be able to activate memory encryption, even -if configured to do so by default or the mem_encrypt=on command line parameter -is specified. diff --git a/Documentation/x86/index.rst b/Documentation/x86/index.rst index b5cdc0d889b3..85f1f44cc8ac 100644 --- a/Documentation/x86/index.rst +++ b/Documentation/x86/index.rst @@ -20,3 +20,4 @@ x86-specific Documentation pat protection-keys intel_mpx + amd-memory-encryption -- cgit v1.2.3 From ea0765e835e084707abb7e14d84b572f5ffe4242 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:29 +0800 Subject: Documentation: x86: convert pti.txt to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/index.rst | 1 + Documentation/x86/pti.rst | 195 ++++++++++++++++++++++++++++++++++++++++++++ Documentation/x86/pti.txt | 186 ------------------------------------------ 3 files changed, 196 insertions(+), 186 deletions(-) create mode 100644 Documentation/x86/pti.rst delete mode 100644 Documentation/x86/pti.txt (limited to 'Documentation') diff --git a/Documentation/x86/index.rst b/Documentation/x86/index.rst index 85f1f44cc8ac..6719defc16f8 100644 --- a/Documentation/x86/index.rst +++ b/Documentation/x86/index.rst @@ -21,3 +21,4 @@ x86-specific Documentation protection-keys intel_mpx amd-memory-encryption + pti diff --git a/Documentation/x86/pti.rst b/Documentation/x86/pti.rst new file mode 100644 index 000000000000..4b858a9bad8d --- /dev/null +++ b/Documentation/x86/pti.rst @@ -0,0 +1,195 @@ +.. SPDX-License-Identifier: GPL-2.0 + +========================== +Page Table Isolation (PTI) +========================== + +Overview +======== + +Page Table Isolation (pti, previously known as KAISER [1]_) is a +countermeasure against attacks on the shared user/kernel address +space such as the "Meltdown" approach [2]_. + +To mitigate this class of attacks, we create an independent set of +page tables for use only when running userspace applications. When +the kernel is entered via syscalls, interrupts or exceptions, the +page tables are switched to the full "kernel" copy. When the system +switches back to user mode, the user copy is used again. + +The userspace page tables contain only a minimal amount of kernel +data: only what is needed to enter/exit the kernel such as the +entry/exit functions themselves and the interrupt descriptor table +(IDT). There are a few strictly unnecessary things that get mapped +such as the first C function when entering an interrupt (see +comments in pti.c). + +This approach helps to ensure that side-channel attacks leveraging +the paging structures do not function when PTI is enabled. It can be +enabled by setting CONFIG_PAGE_TABLE_ISOLATION=y at compile time. +Once enabled at compile-time, it can be disabled at boot with the +'nopti' or 'pti=' kernel parameters (see kernel-parameters.txt). + +Page Table Management +===================== + +When PTI is enabled, the kernel manages two sets of page tables. +The first set is very similar to the single set which is present in +kernels without PTI. This includes a complete mapping of userspace +that the kernel can use for things like copy_to_user(). + +Although _complete_, the user portion of the kernel page tables is +crippled by setting the NX bit in the top level. This ensures +that any missed kernel->user CR3 switch will immediately crash +userspace upon executing its first instruction. + +The userspace page tables map only the kernel data needed to enter +and exit the kernel. This data is entirely contained in the 'struct +cpu_entry_area' structure which is placed in the fixmap which gives +each CPU's copy of the area a compile-time-fixed virtual address. + +For new userspace mappings, the kernel makes the entries in its +page tables like normal. The only difference is when the kernel +makes entries in the top (PGD) level. In addition to setting the +entry in the main kernel PGD, a copy of the entry is made in the +userspace page tables' PGD. + +This sharing at the PGD level also inherently shares all the lower +layers of the page tables. This leaves a single, shared set of +userspace page tables to manage. One PTE to lock, one set of +accessed bits, dirty bits, etc... + +Overhead +======== + +Protection against side-channel attacks is important. But, +this protection comes at a cost: + +1. Increased Memory Use + + a. Each process now needs an order-1 PGD instead of order-0. + (Consumes an additional 4k per process). + b. The 'cpu_entry_area' structure must be 2MB in size and 2MB + aligned so that it can be mapped by setting a single PMD + entry. This consumes nearly 2MB of RAM once the kernel + is decompressed, but no space in the kernel image itself. + +2. Runtime Cost + + a. CR3 manipulation to switch between the page table copies + must be done at interrupt, syscall, and exception entry + and exit (it can be skipped when the kernel is interrupted, + though.) Moves to CR3 are on the order of a hundred + cycles, and are required at every entry and exit. + b. A "trampoline" must be used for SYSCALL entry. This + trampoline depends on a smaller set of resources than the + non-PTI SYSCALL entry code, so requires mapping fewer + things into the userspace page tables. The downside is + that stacks must be switched at entry time. + c. Global pages are disabled for all kernel structures not + mapped into both kernel and userspace page tables. This + feature of the MMU allows different processes to share TLB + entries mapping the kernel. Losing the feature means more + TLB misses after a context switch. The actual loss of + performance is very small, however, never exceeding 1%. + d. Process Context IDentifiers (PCID) is a CPU feature that + allows us to skip flushing the entire TLB when switching page + tables by setting a special bit in CR3 when the page tables + are changed. This makes switching the page tables (at context + switch, or kernel entry/exit) cheaper. But, on systems with + PCID support, the context switch code must flush both the user + and kernel entries out of the TLB. The user PCID TLB flush is + deferred until the exit to userspace, minimizing the cost. + See intel.com/sdm for the gory PCID/INVPCID details. + e. The userspace page tables must be populated for each new + process. Even without PTI, the shared kernel mappings + are created by copying top-level (PGD) entries into each + new process. But, with PTI, there are now *two* kernel + mappings: one in the kernel page tables that maps everything + and one for the entry/exit structures. At fork(), we need to + copy both. + f. In addition to the fork()-time copying, there must also + be an update to the userspace PGD any time a set_pgd() is done + on a PGD used to map userspace. This ensures that the kernel + and userspace copies always map the same userspace + memory. + g. On systems without PCID support, each CR3 write flushes + the entire TLB. That means that each syscall, interrupt + or exception flushes the TLB. + h. INVPCID is a TLB-flushing instruction which allows flushing + of TLB entries for non-current PCIDs. Some systems support + PCIDs, but do not support INVPCID. On these systems, addresses + can only be flushed from the TLB for the current PCID. When + flushing a kernel address, we need to flush all PCIDs, so a + single kernel address flush will require a TLB-flushing CR3 + write upon the next use of every PCID. + +Possible Future Work +==================== +1. We can be more careful about not actually writing to CR3 + unless its value is actually changed. +2. Allow PTI to be enabled/disabled at runtime in addition to the + boot-time switching. + +Testing +======== + +To test stability of PTI, the following test procedure is recommended, +ideally doing all of these in parallel: + +1. Set CONFIG_DEBUG_ENTRY=y +2. Run several copies of all of the tools/testing/selftests/x86/ tests + (excluding MPX and protection_keys) in a loop on multiple CPUs for + several minutes. These tests frequently uncover corner cases in the + kernel entry code. In general, old kernels might cause these tests + themselves to crash, but they should never crash the kernel. +3. Run the 'perf' tool in a mode (top or record) that generates many + frequent performance monitoring non-maskable interrupts (see "NMI" + in /proc/interrupts). This exercises the NMI entry/exit code which + is known to trigger bugs in code paths that did not expect to be + interrupted, including nested NMIs. Using "-c" boosts the rate of + NMIs, and using two -c with separate counters encourages nested NMIs + and less deterministic behavior. + :: + + while true; do perf record -c 10000 -e instructions,cycles -a sleep 10; done + +4. Launch a KVM virtual machine. +5. Run 32-bit binaries on systems supporting the SYSCALL instruction. + This has been a lightly-tested code path and needs extra scrutiny. + +Debugging +========= + +Bugs in PTI cause a few different signatures of crashes +that are worth noting here. + + * Failures of the selftests/x86 code. Usually a bug in one of the + more obscure corners of entry_64.S + * Crashes in early boot, especially around CPU bringup. Bugs + in the trampoline code or mappings cause these. + * Crashes at the first interrupt. Caused by bugs in entry_64.S, + like screwing up a page table switch. Also caused by + incorrectly mapping the IRQ handler entry code. + * Crashes at the first NMI. The NMI code is separate from main + interrupt handlers and can have bugs that do not affect + normal interrupts. Also caused by incorrectly mapping NMI + code. NMIs that interrupt the entry code must be very + careful and can be the cause of crashes that show up when + running perf. + * Kernel crashes at the first exit to userspace. entry_64.S + bugs, or failing to map some of the exit code. + * Crashes at first interrupt that interrupts userspace. The paths + in entry_64.S that return to userspace are sometimes separate + from the ones that return to the kernel. + * Double faults: overflowing the kernel stack because of page + faults upon page faults. Caused by touching non-pti-mapped + data in the entry code, or forgetting to switch to kernel + CR3 before calling into C functions which are not pti-mapped. + * Userspace segfaults early in boot, sometimes manifesting + as mount(8) failing to mount the rootfs. These have + tended to be TLB invalidation issues. Usually invalidating + the wrong PCID, or otherwise missing an invalidation. + +.. [1] https://gruss.cc/files/kaiser.pdf +.. [2] https://meltdownattack.com/meltdown.pdf diff --git a/Documentation/x86/pti.txt b/Documentation/x86/pti.txt deleted file mode 100644 index 5cd58439ad2d..000000000000 --- a/Documentation/x86/pti.txt +++ /dev/null @@ -1,186 +0,0 @@ -Overview -======== - -Page Table Isolation (pti, previously known as KAISER[1]) is a -countermeasure against attacks on the shared user/kernel address -space such as the "Meltdown" approach[2]. - -To mitigate this class of attacks, we create an independent set of -page tables for use only when running userspace applications. When -the kernel is entered via syscalls, interrupts or exceptions, the -page tables are switched to the full "kernel" copy. When the system -switches back to user mode, the user copy is used again. - -The userspace page tables contain only a minimal amount of kernel -data: only what is needed to enter/exit the kernel such as the -entry/exit functions themselves and the interrupt descriptor table -(IDT). There are a few strictly unnecessary things that get mapped -such as the first C function when entering an interrupt (see -comments in pti.c). - -This approach helps to ensure that side-channel attacks leveraging -the paging structures do not function when PTI is enabled. It can be -enabled by setting CONFIG_PAGE_TABLE_ISOLATION=y at compile time. -Once enabled at compile-time, it can be disabled at boot with the -'nopti' or 'pti=' kernel parameters (see kernel-parameters.txt). - -Page Table Management -===================== - -When PTI is enabled, the kernel manages two sets of page tables. -The first set is very similar to the single set which is present in -kernels without PTI. This includes a complete mapping of userspace -that the kernel can use for things like copy_to_user(). - -Although _complete_, the user portion of the kernel page tables is -crippled by setting the NX bit in the top level. This ensures -that any missed kernel->user CR3 switch will immediately crash -userspace upon executing its first instruction. - -The userspace page tables map only the kernel data needed to enter -and exit the kernel. This data is entirely contained in the 'struct -cpu_entry_area' structure which is placed in the fixmap which gives -each CPU's copy of the area a compile-time-fixed virtual address. - -For new userspace mappings, the kernel makes the entries in its -page tables like normal. The only difference is when the kernel -makes entries in the top (PGD) level. In addition to setting the -entry in the main kernel PGD, a copy of the entry is made in the -userspace page tables' PGD. - -This sharing at the PGD level also inherently shares all the lower -layers of the page tables. This leaves a single, shared set of -userspace page tables to manage. One PTE to lock, one set of -accessed bits, dirty bits, etc... - -Overhead -======== - -Protection against side-channel attacks is important. But, -this protection comes at a cost: - -1. Increased Memory Use - a. Each process now needs an order-1 PGD instead of order-0. - (Consumes an additional 4k per process). - b. The 'cpu_entry_area' structure must be 2MB in size and 2MB - aligned so that it can be mapped by setting a single PMD - entry. This consumes nearly 2MB of RAM once the kernel - is decompressed, but no space in the kernel image itself. - -2. Runtime Cost - a. CR3 manipulation to switch between the page table copies - must be done at interrupt, syscall, and exception entry - and exit (it can be skipped when the kernel is interrupted, - though.) Moves to CR3 are on the order of a hundred - cycles, and are required at every entry and exit. - b. A "trampoline" must be used for SYSCALL entry. This - trampoline depends on a smaller set of resources than the - non-PTI SYSCALL entry code, so requires mapping fewer - things into the userspace page tables. The downside is - that stacks must be switched at entry time. - c. Global pages are disabled for all kernel structures not - mapped into both kernel and userspace page tables. This - feature of the MMU allows different processes to share TLB - entries mapping the kernel. Losing the feature means more - TLB misses after a context switch. The actual loss of - performance is very small, however, never exceeding 1%. - d. Process Context IDentifiers (PCID) is a CPU feature that - allows us to skip flushing the entire TLB when switching page - tables by setting a special bit in CR3 when the page tables - are changed. This makes switching the page tables (at context - switch, or kernel entry/exit) cheaper. But, on systems with - PCID support, the context switch code must flush both the user - and kernel entries out of the TLB. The user PCID TLB flush is - deferred until the exit to userspace, minimizing the cost. - See intel.com/sdm for the gory PCID/INVPCID details. - e. The userspace page tables must be populated for each new - process. Even without PTI, the shared kernel mappings - are created by copying top-level (PGD) entries into each - new process. But, with PTI, there are now *two* kernel - mappings: one in the kernel page tables that maps everything - and one for the entry/exit structures. At fork(), we need to - copy both. - f. In addition to the fork()-time copying, there must also - be an update to the userspace PGD any time a set_pgd() is done - on a PGD used to map userspace. This ensures that the kernel - and userspace copies always map the same userspace - memory. - g. On systems without PCID support, each CR3 write flushes - the entire TLB. That means that each syscall, interrupt - or exception flushes the TLB. - h. INVPCID is a TLB-flushing instruction which allows flushing - of TLB entries for non-current PCIDs. Some systems support - PCIDs, but do not support INVPCID. On these systems, addresses - can only be flushed from the TLB for the current PCID. When - flushing a kernel address, we need to flush all PCIDs, so a - single kernel address flush will require a TLB-flushing CR3 - write upon the next use of every PCID. - -Possible Future Work -==================== -1. We can be more careful about not actually writing to CR3 - unless its value is actually changed. -2. Allow PTI to be enabled/disabled at runtime in addition to the - boot-time switching. - -Testing -======== - -To test stability of PTI, the following test procedure is recommended, -ideally doing all of these in parallel: - -1. Set CONFIG_DEBUG_ENTRY=y -2. Run several copies of all of the tools/testing/selftests/x86/ tests - (excluding MPX and protection_keys) in a loop on multiple CPUs for - several minutes. These tests frequently uncover corner cases in the - kernel entry code. In general, old kernels might cause these tests - themselves to crash, but they should never crash the kernel. -3. Run the 'perf' tool in a mode (top or record) that generates many - frequent performance monitoring non-maskable interrupts (see "NMI" - in /proc/interrupts). This exercises the NMI entry/exit code which - is known to trigger bugs in code paths that did not expect to be - interrupted, including nested NMIs. Using "-c" boosts the rate of - NMIs, and using two -c with separate counters encourages nested NMIs - and less deterministic behavior. - - while true; do perf record -c 10000 -e instructions,cycles -a sleep 10; done - -4. Launch a KVM virtual machine. -5. Run 32-bit binaries on systems supporting the SYSCALL instruction. - This has been a lightly-tested code path and needs extra scrutiny. - -Debugging -========= - -Bugs in PTI cause a few different signatures of crashes -that are worth noting here. - - * Failures of the selftests/x86 code. Usually a bug in one of the - more obscure corners of entry_64.S - * Crashes in early boot, especially around CPU bringup. Bugs - in the trampoline code or mappings cause these. - * Crashes at the first interrupt. Caused by bugs in entry_64.S, - like screwing up a page table switch. Also caused by - incorrectly mapping the IRQ handler entry code. - * Crashes at the first NMI. The NMI code is separate from main - interrupt handlers and can have bugs that do not affect - normal interrupts. Also caused by incorrectly mapping NMI - code. NMIs that interrupt the entry code must be very - careful and can be the cause of crashes that show up when - running perf. - * Kernel crashes at the first exit to userspace. entry_64.S - bugs, or failing to map some of the exit code. - * Crashes at first interrupt that interrupts userspace. The paths - in entry_64.S that return to userspace are sometimes separate - from the ones that return to the kernel. - * Double faults: overflowing the kernel stack because of page - faults upon page faults. Caused by touching non-pti-mapped - data in the entry code, or forgetting to switch to kernel - CR3 before calling into C functions which are not pti-mapped. - * Userspace segfaults early in boot, sometimes manifesting - as mount(8) failing to mount the rootfs. These have - tended to be TLB invalidation issues. Usually invalidating - the wrong PCID, or otherwise missing an invalidation. - -1. https://gruss.cc/files/kaiser.pdf -2. https://meltdownattack.com/meltdown.pdf -- cgit v1.2.3 From 3d07bc393f9b63ca4c6f9953922f9122a11f29c3 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:30 +0800 Subject: Documentation: x86: convert microcode.txt to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/index.rst | 1 + Documentation/x86/microcode.rst | 142 ++++++++++++++++++++++++++++++++++++++++ Documentation/x86/microcode.txt | 136 -------------------------------------- 3 files changed, 143 insertions(+), 136 deletions(-) create mode 100644 Documentation/x86/microcode.rst delete mode 100644 Documentation/x86/microcode.txt (limited to 'Documentation') diff --git a/Documentation/x86/index.rst b/Documentation/x86/index.rst index 6719defc16f8..ae29c026be72 100644 --- a/Documentation/x86/index.rst +++ b/Documentation/x86/index.rst @@ -22,3 +22,4 @@ x86-specific Documentation intel_mpx amd-memory-encryption pti + microcode diff --git a/Documentation/x86/microcode.rst b/Documentation/x86/microcode.rst new file mode 100644 index 000000000000..a320d37982ed --- /dev/null +++ b/Documentation/x86/microcode.rst @@ -0,0 +1,142 @@ +.. SPDX-License-Identifier: GPL-2.0 + +========================== +The Linux Microcode Loader +========================== + +:Authors: - Fenghua Yu + - Borislav Petkov + +The kernel has a x86 microcode loading facility which is supposed to +provide microcode loading methods in the OS. Potential use cases are +updating the microcode on platforms beyond the OEM End-Of-Life support, +and updating the microcode on long-running systems without rebooting. + +The loader supports three loading methods: + +Early load microcode +==================== + +The kernel can update microcode very early during boot. Loading +microcode early can fix CPU issues before they are observed during +kernel boot time. + +The microcode is stored in an initrd file. During boot, it is read from +it and loaded into the CPU cores. + +The format of the combined initrd image is microcode in (uncompressed) +cpio format followed by the (possibly compressed) initrd image. The +loader parses the combined initrd image during boot. + +The microcode files in cpio name space are: + +on Intel: + kernel/x86/microcode/GenuineIntel.bin +on AMD : + kernel/x86/microcode/AuthenticAMD.bin + +During BSP (BootStrapping Processor) boot (pre-SMP), the kernel +scans the microcode file in the initrd. If microcode matching the +CPU is found, it will be applied in the BSP and later on in all APs +(Application Processors). + +The loader also saves the matching microcode for the CPU in memory. +Thus, the cached microcode patch is applied when CPUs resume from a +sleep state. + +Here's a crude example how to prepare an initrd with microcode (this is +normally done automatically by the distribution, when recreating the +initrd, so you don't really have to do it yourself. It is documented +here for future reference only). +:: + + #!/bin/bash + + if [ -z "$1" ]; then + echo "You need to supply an initrd file" + exit 1 + fi + + INITRD="$1" + + DSTDIR=kernel/x86/microcode + TMPDIR=/tmp/initrd + + rm -rf $TMPDIR + + mkdir $TMPDIR + cd $TMPDIR + mkdir -p $DSTDIR + + if [ -d /lib/firmware/amd-ucode ]; then + cat /lib/firmware/amd-ucode/microcode_amd*.bin > $DSTDIR/AuthenticAMD.bin + fi + + if [ -d /lib/firmware/intel-ucode ]; then + cat /lib/firmware/intel-ucode/* > $DSTDIR/GenuineIntel.bin + fi + + find . | cpio -o -H newc >../ucode.cpio + cd .. + mv $INITRD $INITRD.orig + cat ucode.cpio $INITRD.orig > $INITRD + + rm -rf $TMPDIR + + +The system needs to have the microcode packages installed into +/lib/firmware or you need to fixup the paths above if yours are +somewhere else and/or you've downloaded them directly from the processor +vendor's site. + +Late loading +============ + +There are two legacy user space interfaces to load microcode, either through +/dev/cpu/microcode or through /sys/devices/system/cpu/microcode/reload file +in sysfs. + +The /dev/cpu/microcode method is deprecated because it needs a special +userspace tool for that. + +The easier method is simply installing the microcode packages your distro +supplies and running:: + + # echo 1 > /sys/devices/system/cpu/microcode/reload + +as root. + +The loading mechanism looks for microcode blobs in +/lib/firmware/{intel-ucode,amd-ucode}. The default distro installation +packages already put them there. + +Builtin microcode +================= + +The loader supports also loading of a builtin microcode supplied through +the regular builtin firmware method CONFIG_EXTRA_FIRMWARE. Only 64-bit is +currently supported. + +Here's an example:: + + CONFIG_EXTRA_FIRMWARE="intel-ucode/06-3a-09 amd-ucode/microcode_amd_fam15h.bin" + CONFIG_EXTRA_FIRMWARE_DIR="/lib/firmware" + +This basically means, you have the following tree structure locally:: + + /lib/firmware/ + |-- amd-ucode + ... + | |-- microcode_amd_fam15h.bin + ... + |-- intel-ucode + ... + | |-- 06-3a-09 + ... + +so that the build system can find those files and integrate them into +the final kernel image. The early loader finds them and applies them. + +Needless to say, this method is not the most flexible one because it +requires rebuilding the kernel each time updated microcode from the CPU +vendor is available. diff --git a/Documentation/x86/microcode.txt b/Documentation/x86/microcode.txt deleted file mode 100644 index 79fdb4a8148a..000000000000 --- a/Documentation/x86/microcode.txt +++ /dev/null @@ -1,136 +0,0 @@ - The Linux Microcode Loader - -Authors: Fenghua Yu - Borislav Petkov - -The kernel has a x86 microcode loading facility which is supposed to -provide microcode loading methods in the OS. Potential use cases are -updating the microcode on platforms beyond the OEM End-Of-Life support, -and updating the microcode on long-running systems without rebooting. - -The loader supports three loading methods: - -1. Early load microcode -======================= - -The kernel can update microcode very early during boot. Loading -microcode early can fix CPU issues before they are observed during -kernel boot time. - -The microcode is stored in an initrd file. During boot, it is read from -it and loaded into the CPU cores. - -The format of the combined initrd image is microcode in (uncompressed) -cpio format followed by the (possibly compressed) initrd image. The -loader parses the combined initrd image during boot. - -The microcode files in cpio name space are: - -on Intel: kernel/x86/microcode/GenuineIntel.bin -on AMD : kernel/x86/microcode/AuthenticAMD.bin - -During BSP (BootStrapping Processor) boot (pre-SMP), the kernel -scans the microcode file in the initrd. If microcode matching the -CPU is found, it will be applied in the BSP and later on in all APs -(Application Processors). - -The loader also saves the matching microcode for the CPU in memory. -Thus, the cached microcode patch is applied when CPUs resume from a -sleep state. - -Here's a crude example how to prepare an initrd with microcode (this is -normally done automatically by the distribution, when recreating the -initrd, so you don't really have to do it yourself. It is documented -here for future reference only). - ---- - #!/bin/bash - - if [ -z "$1" ]; then - echo "You need to supply an initrd file" - exit 1 - fi - - INITRD="$1" - - DSTDIR=kernel/x86/microcode - TMPDIR=/tmp/initrd - - rm -rf $TMPDIR - - mkdir $TMPDIR - cd $TMPDIR - mkdir -p $DSTDIR - - if [ -d /lib/firmware/amd-ucode ]; then - cat /lib/firmware/amd-ucode/microcode_amd*.bin > $DSTDIR/AuthenticAMD.bin - fi - - if [ -d /lib/firmware/intel-ucode ]; then - cat /lib/firmware/intel-ucode/* > $DSTDIR/GenuineIntel.bin - fi - - find . | cpio -o -H newc >../ucode.cpio - cd .. - mv $INITRD $INITRD.orig - cat ucode.cpio $INITRD.orig > $INITRD - - rm -rf $TMPDIR ---- - -The system needs to have the microcode packages installed into -/lib/firmware or you need to fixup the paths above if yours are -somewhere else and/or you've downloaded them directly from the processor -vendor's site. - -2. Late loading -=============== - -There are two legacy user space interfaces to load microcode, either through -/dev/cpu/microcode or through /sys/devices/system/cpu/microcode/reload file -in sysfs. - -The /dev/cpu/microcode method is deprecated because it needs a special -userspace tool for that. - -The easier method is simply installing the microcode packages your distro -supplies and running: - -# echo 1 > /sys/devices/system/cpu/microcode/reload - -as root. - -The loading mechanism looks for microcode blobs in -/lib/firmware/{intel-ucode,amd-ucode}. The default distro installation -packages already put them there. - -3. Builtin microcode -==================== - -The loader supports also loading of a builtin microcode supplied through -the regular builtin firmware method CONFIG_EXTRA_FIRMWARE. Only 64-bit is -currently supported. - -Here's an example: - -CONFIG_EXTRA_FIRMWARE="intel-ucode/06-3a-09 amd-ucode/microcode_amd_fam15h.bin" -CONFIG_EXTRA_FIRMWARE_DIR="/lib/firmware" - -This basically means, you have the following tree structure locally: - -/lib/firmware/ -|-- amd-ucode -... -| |-- microcode_amd_fam15h.bin -... -|-- intel-ucode -... -| |-- 06-3a-09 -... - -so that the build system can find those files and integrate them into -the final kernel image. The early loader finds them and applies them. - -Needless to say, this method is not the most flexible one because it -requires rebuilding the kernel each time updated microcode from the CPU -vendor is available. -- cgit v1.2.3 From 1cd7af509dc223905dce622c07ec62e26044e3c0 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:31 +0800 Subject: Documentation: x86: convert resctrl_ui.txt to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/index.rst | 1 + Documentation/x86/resctrl_ui.rst | 1191 ++++++++++++++++++++++++++++++++++++++ Documentation/x86/resctrl_ui.txt | 1121 ----------------------------------- 3 files changed, 1192 insertions(+), 1121 deletions(-) create mode 100644 Documentation/x86/resctrl_ui.rst delete mode 100644 Documentation/x86/resctrl_ui.txt (limited to 'Documentation') diff --git a/Documentation/x86/index.rst b/Documentation/x86/index.rst index ae29c026be72..6e3c887a0c3b 100644 --- a/Documentation/x86/index.rst +++ b/Documentation/x86/index.rst @@ -23,3 +23,4 @@ x86-specific Documentation amd-memory-encryption pti microcode + resctrl_ui diff --git a/Documentation/x86/resctrl_ui.rst b/Documentation/x86/resctrl_ui.rst new file mode 100644 index 000000000000..225cfd4daaee --- /dev/null +++ b/Documentation/x86/resctrl_ui.rst @@ -0,0 +1,1191 @@ +.. SPDX-License-Identifier: GPL-2.0 +.. include:: + +=========================================== +User Interface for Resource Control feature +=========================================== + +:Copyright: |copy| 2016 Intel Corporation +:Authors: - Fenghua Yu + - Tony Luck + - Vikas Shivappa + + +Intel refers to this feature as Intel Resource Director Technology(Intel(R) RDT). +AMD refers to this feature as AMD Platform Quality of Service(AMD QoS). + +This feature is enabled by the CONFIG_X86_CPU_RESCTRL and the x86 /proc/cpuinfo +flag bits: + +============================================= ================================ +RDT (Resource Director Technology) Allocation "rdt_a" +CAT (Cache Allocation Technology) "cat_l3", "cat_l2" +CDP (Code and Data Prioritization) "cdp_l3", "cdp_l2" +CQM (Cache QoS Monitoring) "cqm_llc", "cqm_occup_llc" +MBM (Memory Bandwidth Monitoring) "cqm_mbm_total", "cqm_mbm_local" +MBA (Memory Bandwidth Allocation) "mba" +============================================= ================================ + +To use the feature mount the file system:: + + # mount -t resctrl resctrl [-o cdp[,cdpl2][,mba_MBps]] /sys/fs/resctrl + +mount options are: + +"cdp": + Enable code/data prioritization in L3 cache allocations. +"cdpl2": + Enable code/data prioritization in L2 cache allocations. +"mba_MBps": + Enable the MBA Software Controller(mba_sc) to specify MBA + bandwidth in MBps + +L2 and L3 CDP are controlled seperately. + +RDT features are orthogonal. A particular system may support only +monitoring, only control, or both monitoring and control. Cache +pseudo-locking is a unique way of using cache control to "pin" or +"lock" data in the cache. Details can be found in +"Cache Pseudo-Locking". + + +The mount succeeds if either of allocation or monitoring is present, but +only those files and directories supported by the system will be created. +For more details on the behavior of the interface during monitoring +and allocation, see the "Resource alloc and monitor groups" section. + +Info directory +============== + +The 'info' directory contains information about the enabled +resources. Each resource has its own subdirectory. The subdirectory +names reflect the resource names. + +Each subdirectory contains the following files with respect to +allocation: + +Cache resource(L3/L2) subdirectory contains the following files +related to allocation: + +"num_closids": + The number of CLOSIDs which are valid for this + resource. The kernel uses the smallest number of + CLOSIDs of all enabled resources as limit. +"cbm_mask": + The bitmask which is valid for this resource. + This mask is equivalent to 100%. +"min_cbm_bits": + The minimum number of consecutive bits which + must be set when writing a mask. + +"shareable_bits": + Bitmask of shareable resource with other executing + entities (e.g. I/O). User can use this when + setting up exclusive cache partitions. Note that + some platforms support devices that have their + own settings for cache use which can over-ride + these bits. +"bit_usage": + Annotated capacity bitmasks showing how all + instances of the resource are used. The legend is: + + "0": + Corresponding region is unused. When the system's + resources have been allocated and a "0" is found + in "bit_usage" it is a sign that resources are + wasted. + + "H": + Corresponding region is used by hardware only + but available for software use. If a resource + has bits set in "shareable_bits" but not all + of these bits appear in the resource groups' + schematas then the bits appearing in + "shareable_bits" but no resource group will + be marked as "H". + "X": + Corresponding region is available for sharing and + used by hardware and software. These are the + bits that appear in "shareable_bits" as + well as a resource group's allocation. + "S": + Corresponding region is used by software + and available for sharing. + "E": + Corresponding region is used exclusively by + one resource group. No sharing allowed. + "P": + Corresponding region is pseudo-locked. No + sharing allowed. + +Memory bandwitdh(MB) subdirectory contains the following files +with respect to allocation: + +"min_bandwidth": + The minimum memory bandwidth percentage which + user can request. + +"bandwidth_gran": + The granularity in which the memory bandwidth + percentage is allocated. The allocated + b/w percentage is rounded off to the next + control step available on the hardware. The + available bandwidth control steps are: + min_bandwidth + N * bandwidth_gran. + +"delay_linear": + Indicates if the delay scale is linear or + non-linear. This field is purely informational + only. + +If RDT monitoring is available there will be an "L3_MON" directory +with the following files: + +"num_rmids": + The number of RMIDs available. This is the + upper bound for how many "CTRL_MON" + "MON" + groups can be created. + +"mon_features": + Lists the monitoring events if + monitoring is enabled for the resource. + +"max_threshold_occupancy": + Read/write file provides the largest value (in + bytes) at which a previously used LLC_occupancy + counter can be considered for re-use. + +Finally, in the top level of the "info" directory there is a file +named "last_cmd_status". This is reset with every "command" issued +via the file system (making new directories or writing to any of the +control files). If the command was successful, it will read as "ok". +If the command failed, it will provide more information that can be +conveyed in the error returns from file operations. E.g. +:: + + # echo L3:0=f7 > schemata + bash: echo: write error: Invalid argument + # cat info/last_cmd_status + mask f7 has non-consecutive 1-bits + +Resource alloc and monitor groups +================================= + +Resource groups are represented as directories in the resctrl file +system. The default group is the root directory which, immediately +after mounting, owns all the tasks and cpus in the system and can make +full use of all resources. + +On a system with RDT control features additional directories can be +created in the root directory that specify different amounts of each +resource (see "schemata" below). The root and these additional top level +directories are referred to as "CTRL_MON" groups below. + +On a system with RDT monitoring the root directory and other top level +directories contain a directory named "mon_groups" in which additional +directories can be created to monitor subsets of tasks in the CTRL_MON +group that is their ancestor. These are called "MON" groups in the rest +of this document. + +Removing a directory will move all tasks and cpus owned by the group it +represents to the parent. Removing one of the created CTRL_MON groups +will automatically remove all MON groups below it. + +All groups contain the following files: + +"tasks": + Reading this file shows the list of all tasks that belong to + this group. Writing a task id to the file will add a task to the + group. If the group is a CTRL_MON group the task is removed from + whichever previous CTRL_MON group owned the task and also from + any MON group that owned the task. If the group is a MON group, + then the task must already belong to the CTRL_MON parent of this + group. The task is removed from any previous MON group. + + +"cpus": + Reading this file shows a bitmask of the logical CPUs owned by + this group. Writing a mask to this file will add and remove + CPUs to/from this group. As with the tasks file a hierarchy is + maintained where MON groups may only include CPUs owned by the + parent CTRL_MON group. + When the resouce group is in pseudo-locked mode this file will + only be readable, reflecting the CPUs associated with the + pseudo-locked region. + + +"cpus_list": + Just like "cpus", only using ranges of CPUs instead of bitmasks. + + +When control is enabled all CTRL_MON groups will also contain: + +"schemata": + A list of all the resources available to this group. + Each resource has its own line and format - see below for details. + +"size": + Mirrors the display of the "schemata" file to display the size in + bytes of each allocation instead of the bits representing the + allocation. + +"mode": + The "mode" of the resource group dictates the sharing of its + allocations. A "shareable" resource group allows sharing of its + allocations while an "exclusive" resource group does not. A + cache pseudo-locked region is created by first writing + "pseudo-locksetup" to the "mode" file before writing the cache + pseudo-locked region's schemata to the resource group's "schemata" + file. On successful pseudo-locked region creation the mode will + automatically change to "pseudo-locked". + +When monitoring is enabled all MON groups will also contain: + +"mon_data": + This contains a set of files organized by L3 domain and by + RDT event. E.g. on a system with two L3 domains there will + be subdirectories "mon_L3_00" and "mon_L3_01". Each of these + directories have one file per event (e.g. "llc_occupancy", + "mbm_total_bytes", and "mbm_local_bytes"). In a MON group these + files provide a read out of the current value of the event for + all tasks in the group. In CTRL_MON groups these files provide + the sum for all tasks in the CTRL_MON group and all tasks in + MON groups. Please see example section for more details on usage. + +Resource allocation rules +------------------------- + +When a task is running the following rules define which resources are +available to it: + +1) If the task is a member of a non-default group, then the schemata + for that group is used. + +2) Else if the task belongs to the default group, but is running on a + CPU that is assigned to some specific group, then the schemata for the + CPU's group is used. + +3) Otherwise the schemata for the default group is used. + +Resource monitoring rules +------------------------- +1) If a task is a member of a MON group, or non-default CTRL_MON group + then RDT events for the task will be reported in that group. + +2) If a task is a member of the default CTRL_MON group, but is running + on a CPU that is assigned to some specific group, then the RDT events + for the task will be reported in that group. + +3) Otherwise RDT events for the task will be reported in the root level + "mon_data" group. + + +Notes on cache occupancy monitoring and control +=============================================== +When moving a task from one group to another you should remember that +this only affects *new* cache allocations by the task. E.g. you may have +a task in a monitor group showing 3 MB of cache occupancy. If you move +to a new group and immediately check the occupancy of the old and new +groups you will likely see that the old group is still showing 3 MB and +the new group zero. When the task accesses locations still in cache from +before the move, the h/w does not update any counters. On a busy system +you will likely see the occupancy in the old group go down as cache lines +are evicted and re-used while the occupancy in the new group rises as +the task accesses memory and loads into the cache are counted based on +membership in the new group. + +The same applies to cache allocation control. Moving a task to a group +with a smaller cache partition will not evict any cache lines. The +process may continue to use them from the old partition. + +Hardware uses CLOSid(Class of service ID) and an RMID(Resource monitoring ID) +to identify a control group and a monitoring group respectively. Each of +the resource groups are mapped to these IDs based on the kind of group. The +number of CLOSid and RMID are limited by the hardware and hence the creation of +a "CTRL_MON" directory may fail if we run out of either CLOSID or RMID +and creation of "MON" group may fail if we run out of RMIDs. + +max_threshold_occupancy - generic concepts +------------------------------------------ + +Note that an RMID once freed may not be immediately available for use as +the RMID is still tagged the cache lines of the previous user of RMID. +Hence such RMIDs are placed on limbo list and checked back if the cache +occupancy has gone down. If there is a time when system has a lot of +limbo RMIDs but which are not ready to be used, user may see an -EBUSY +during mkdir. + +max_threshold_occupancy is a user configurable value to determine the +occupancy at which an RMID can be freed. + +Schemata files - general concepts +--------------------------------- +Each line in the file describes one resource. The line starts with +the name of the resource, followed by specific values to be applied +in each of the instances of that resource on the system. + +Cache IDs +--------- +On current generation systems there is one L3 cache per socket and L2 +caches are generally just shared by the hyperthreads on a core, but this +isn't an architectural requirement. We could have multiple separate L3 +caches on a socket, multiple cores could share an L2 cache. So instead +of using "socket" or "core" to define the set of logical cpus sharing +a resource we use a "Cache ID". At a given cache level this will be a +unique number across the whole system (but it isn't guaranteed to be a +contiguous sequence, there may be gaps). To find the ID for each logical +CPU look in /sys/devices/system/cpu/cpu*/cache/index*/id + +Cache Bit Masks (CBM) +--------------------- +For cache resources we describe the portion of the cache that is available +for allocation using a bitmask. The maximum value of the mask is defined +by each cpu model (and may be different for different cache levels). It +is found using CPUID, but is also provided in the "info" directory of +the resctrl file system in "info/{resource}/cbm_mask". X86 hardware +requires that these masks have all the '1' bits in a contiguous block. So +0x3, 0x6 and 0xC are legal 4-bit masks with two bits set, but 0x5, 0x9 +and 0xA are not. On a system with a 20-bit mask each bit represents 5% +of the capacity of the cache. You could partition the cache into four +equal parts with masks: 0x1f, 0x3e0, 0x7c00, 0xf8000. + +Memory bandwidth Allocation and monitoring +========================================== + +For Memory bandwidth resource, by default the user controls the resource +by indicating the percentage of total memory bandwidth. + +The minimum bandwidth percentage value for each cpu model is predefined +and can be looked up through "info/MB/min_bandwidth". The bandwidth +granularity that is allocated is also dependent on the cpu model and can +be looked up at "info/MB/bandwidth_gran". The available bandwidth +control steps are: min_bw + N * bw_gran. Intermediate values are rounded +to the next control step available on the hardware. + +The bandwidth throttling is a core specific mechanism on some of Intel +SKUs. Using a high bandwidth and a low bandwidth setting on two threads +sharing a core will result in both threads being throttled to use the +low bandwidth. The fact that Memory bandwidth allocation(MBA) is a core +specific mechanism where as memory bandwidth monitoring(MBM) is done at +the package level may lead to confusion when users try to apply control +via the MBA and then monitor the bandwidth to see if the controls are +effective. Below are such scenarios: + +1. User may *not* see increase in actual bandwidth when percentage + values are increased: + +This can occur when aggregate L2 external bandwidth is more than L3 +external bandwidth. Consider an SKL SKU with 24 cores on a package and +where L2 external is 10GBps (hence aggregate L2 external bandwidth is +240GBps) and L3 external bandwidth is 100GBps. Now a workload with '20 +threads, having 50% bandwidth, each consuming 5GBps' consumes the max L3 +bandwidth of 100GBps although the percentage value specified is only 50% +<< 100%. Hence increasing the bandwidth percentage will not yeild any +more bandwidth. This is because although the L2 external bandwidth still +has capacity, the L3 external bandwidth is fully used. Also note that +this would be dependent on number of cores the benchmark is run on. + +2. Same bandwidth percentage may mean different actual bandwidth + depending on # of threads: + +For the same SKU in #1, a 'single thread, with 10% bandwidth' and '4 +thread, with 10% bandwidth' can consume upto 10GBps and 40GBps although +they have same percentage bandwidth of 10%. This is simply because as +threads start using more cores in an rdtgroup, the actual bandwidth may +increase or vary although user specified bandwidth percentage is same. + +In order to mitigate this and make the interface more user friendly, +resctrl added support for specifying the bandwidth in MBps as well. The +kernel underneath would use a software feedback mechanism or a "Software +Controller(mba_sc)" which reads the actual bandwidth using MBM counters +and adjust the memowy bandwidth percentages to ensure:: + + "actual bandwidth < user specified bandwidth". + +By default, the schemata would take the bandwidth percentage values +where as user can switch to the "MBA software controller" mode using +a mount option 'mba_MBps'. The schemata format is specified in the below +sections. + +L3 schemata file details (code and data prioritization disabled) +---------------------------------------------------------------- +With CDP disabled the L3 schemata format is:: + + L3:=;=;... + +L3 schemata file details (CDP enabled via mount option to resctrl) +------------------------------------------------------------------ +When CDP is enabled L3 control is split into two separate resources +so you can specify independent masks for code and data like this:: + + L3data:=;=;... + L3code:=;=;... + +L2 schemata file details +------------------------ +L2 cache does not support code and data prioritization, so the +schemata format is always:: + + L2:=;=;... + +Memory bandwidth Allocation (default mode) +------------------------------------------ + +Memory b/w domain is L3 cache. +:: + + MB:=bandwidth0;=bandwidth1;... + +Memory bandwidth Allocation specified in MBps +--------------------------------------------- + +Memory bandwidth domain is L3 cache. +:: + + MB:=bw_MBps0;=bw_MBps1;... + +Reading/writing the schemata file +--------------------------------- +Reading the schemata file will show the state of all resources +on all domains. When writing you only need to specify those values +which you wish to change. E.g. +:: + + # cat schemata + L3DATA:0=fffff;1=fffff;2=fffff;3=fffff + L3CODE:0=fffff;1=fffff;2=fffff;3=fffff + # echo "L3DATA:2=3c0;" > schemata + # cat schemata + L3DATA:0=fffff;1=fffff;2=3c0;3=fffff + L3CODE:0=fffff;1=fffff;2=fffff;3=fffff + +Cache Pseudo-Locking +==================== +CAT enables a user to specify the amount of cache space that an +application can fill. Cache pseudo-locking builds on the fact that a +CPU can still read and write data pre-allocated outside its current +allocated area on a cache hit. With cache pseudo-locking, data can be +preloaded into a reserved portion of cache that no application can +fill, and from that point on will only serve cache hits. The cache +pseudo-locked memory is made accessible to user space where an +application can map it into its virtual address space and thus have +a region of memory with reduced average read latency. + +The creation of a cache pseudo-locked region is triggered by a request +from the user to do so that is accompanied by a schemata of the region +to be pseudo-locked. The cache pseudo-locked region is created as follows: + +- Create a CAT allocation CLOSNEW with a CBM matching the schemata + from the user of the cache region that will contain the pseudo-locked + memory. This region must not overlap with any current CAT allocation/CLOS + on the system and no future overlap with this cache region is allowed + while the pseudo-locked region exists. +- Create a contiguous region of memory of the same size as the cache + region. +- Flush the cache, disable hardware prefetchers, disable preemption. +- Make CLOSNEW the active CLOS and touch the allocated memory to load + it into the cache. +- Set the previous CLOS as active. +- At this point the closid CLOSNEW can be released - the cache + pseudo-locked region is protected as long as its CBM does not appear in + any CAT allocation. Even though the cache pseudo-locked region will from + this point on not appear in any CBM of any CLOS an application running with + any CLOS will be able to access the memory in the pseudo-locked region since + the region continues to serve cache hits. +- The contiguous region of memory loaded into the cache is exposed to + user-space as a character device. + +Cache pseudo-locking increases the probability that data will remain +in the cache via carefully configuring the CAT feature and controlling +application behavior. There is no guarantee that data is placed in +cache. Instructions like INVD, WBINVD, CLFLUSH, etc. can still evict +“locked” data from cache. Power management C-states may shrink or +power off cache. Deeper C-states will automatically be restricted on +pseudo-locked region creation. + +It is required that an application using a pseudo-locked region runs +with affinity to the cores (or a subset of the cores) associated +with the cache on which the pseudo-locked region resides. A sanity check +within the code will not allow an application to map pseudo-locked memory +unless it runs with affinity to cores associated with the cache on which the +pseudo-locked region resides. The sanity check is only done during the +initial mmap() handling, there is no enforcement afterwards and the +application self needs to ensure it remains affine to the correct cores. + +Pseudo-locking is accomplished in two stages: + +1) During the first stage the system administrator allocates a portion + of cache that should be dedicated to pseudo-locking. At this time an + equivalent portion of memory is allocated, loaded into allocated + cache portion, and exposed as a character device. +2) During the second stage a user-space application maps (mmap()) the + pseudo-locked memory into its address space. + +Cache Pseudo-Locking Interface +------------------------------ +A pseudo-locked region is created using the resctrl interface as follows: + +1) Create a new resource group by creating a new directory in /sys/fs/resctrl. +2) Change the new resource group's mode to "pseudo-locksetup" by writing + "pseudo-locksetup" to the "mode" file. +3) Write the schemata of the pseudo-locked region to the "schemata" file. All + bits within the schemata should be "unused" according to the "bit_usage" + file. + +On successful pseudo-locked region creation the "mode" file will contain +"pseudo-locked" and a new character device with the same name as the resource +group will exist in /dev/pseudo_lock. This character device can be mmap()'ed +by user space in order to obtain access to the pseudo-locked memory region. + +An example of cache pseudo-locked region creation and usage can be found below. + +Cache Pseudo-Locking Debugging Interface +---------------------------------------- +The pseudo-locking debugging interface is enabled by default (if +CONFIG_DEBUG_FS is enabled) and can be found in /sys/kernel/debug/resctrl. + +There is no explicit way for the kernel to test if a provided memory +location is present in the cache. The pseudo-locking debugging interface uses +the tracing infrastructure to provide two ways to measure cache residency of +the pseudo-locked region: + +1) Memory access latency using the pseudo_lock_mem_latency tracepoint. Data + from these measurements are best visualized using a hist trigger (see + example below). In this test the pseudo-locked region is traversed at + a stride of 32 bytes while hardware prefetchers and preemption + are disabled. This also provides a substitute visualization of cache + hits and misses. +2) Cache hit and miss measurements using model specific precision counters if + available. Depending on the levels of cache on the system the pseudo_lock_l2 + and pseudo_lock_l3 tracepoints are available. + +When a pseudo-locked region is created a new debugfs directory is created for +it in debugfs as /sys/kernel/debug/resctrl/. A single +write-only file, pseudo_lock_measure, is present in this directory. The +measurement of the pseudo-locked region depends on the number written to this +debugfs file: + +1: + writing "1" to the pseudo_lock_measure file will trigger the latency + measurement captured in the pseudo_lock_mem_latency tracepoint. See + example below. +2: + writing "2" to the pseudo_lock_measure file will trigger the L2 cache + residency (cache hits and misses) measurement captured in the + pseudo_lock_l2 tracepoint. See example below. +3: + writing "3" to the pseudo_lock_measure file will trigger the L3 cache + residency (cache hits and misses) measurement captured in the + pseudo_lock_l3 tracepoint. + +All measurements are recorded with the tracing infrastructure. This requires +the relevant tracepoints to be enabled before the measurement is triggered. + +Example of latency debugging interface +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +In this example a pseudo-locked region named "newlock" was created. Here is +how we can measure the latency in cycles of reading from this region and +visualize this data with a histogram that is available if CONFIG_HIST_TRIGGERS +is set:: + + # :> /sys/kernel/debug/tracing/trace + # echo 'hist:keys=latency' > /sys/kernel/debug/tracing/events/resctrl/pseudo_lock_mem_latency/trigger + # echo 1 > /sys/kernel/debug/tracing/events/resctrl/pseudo_lock_mem_latency/enable + # echo 1 > /sys/kernel/debug/resctrl/newlock/pseudo_lock_measure + # echo 0 > /sys/kernel/debug/tracing/events/resctrl/pseudo_lock_mem_latency/enable + # cat /sys/kernel/debug/tracing/events/resctrl/pseudo_lock_mem_latency/hist + + # event histogram + # + # trigger info: hist:keys=latency:vals=hitcount:sort=hitcount:size=2048 [active] + # + + { latency: 456 } hitcount: 1 + { latency: 50 } hitcount: 83 + { latency: 36 } hitcount: 96 + { latency: 44 } hitcount: 174 + { latency: 48 } hitcount: 195 + { latency: 46 } hitcount: 262 + { latency: 42 } hitcount: 693 + { latency: 40 } hitcount: 3204 + { latency: 38 } hitcount: 3484 + + Totals: + Hits: 8192 + Entries: 9 + Dropped: 0 + +Example of cache hits/misses debugging +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +In this example a pseudo-locked region named "newlock" was created on the L2 +cache of a platform. Here is how we can obtain details of the cache hits +and misses using the platform's precision counters. +:: + + # :> /sys/kernel/debug/tracing/trace + # echo 1 > /sys/kernel/debug/tracing/events/resctrl/pseudo_lock_l2/enable + # echo 2 > /sys/kernel/debug/resctrl/newlock/pseudo_lock_measure + # echo 0 > /sys/kernel/debug/tracing/events/resctrl/pseudo_lock_l2/enable + # cat /sys/kernel/debug/tracing/trace + + # tracer: nop + # + # _-----=> irqs-off + # / _----=> need-resched + # | / _---=> hardirq/softirq + # || / _--=> preempt-depth + # ||| / delay + # TASK-PID CPU# |||| TIMESTAMP FUNCTION + # | | | |||| | | + pseudo_lock_mea-1672 [002] .... 3132.860500: pseudo_lock_l2: hits=4097 miss=0 + + +Examples for RDT allocation usage +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +1) Example 1 + +On a two socket machine (one L3 cache per socket) with just four bits +for cache bit masks, minimum b/w of 10% with a memory bandwidth +granularity of 10%. +:: + + # mount -t resctrl resctrl /sys/fs/resctrl + # cd /sys/fs/resctrl + # mkdir p0 p1 + # echo "L3:0=3;1=c\nMB:0=50;1=50" > /sys/fs/resctrl/p0/schemata + # echo "L3:0=3;1=3\nMB:0=50;1=50" > /sys/fs/resctrl/p1/schemata + +The default resource group is unmodified, so we have access to all parts +of all caches (its schemata file reads "L3:0=f;1=f"). + +Tasks that are under the control of group "p0" may only allocate from the +"lower" 50% on cache ID 0, and the "upper" 50% of cache ID 1. +Tasks in group "p1" use the "lower" 50% of cache on both sockets. + +Similarly, tasks that are under the control of group "p0" may use a +maximum memory b/w of 50% on socket0 and 50% on socket 1. +Tasks in group "p1" may also use 50% memory b/w on both sockets. +Note that unlike cache masks, memory b/w cannot specify whether these +allocations can overlap or not. The allocations specifies the maximum +b/w that the group may be able to use and the system admin can configure +the b/w accordingly. + +If the MBA is specified in MB(megabytes) then user can enter the max b/w in MB +rather than the percentage values. +:: + + # echo "L3:0=3;1=c\nMB:0=1024;1=500" > /sys/fs/resctrl/p0/schemata + # echo "L3:0=3;1=3\nMB:0=1024;1=500" > /sys/fs/resctrl/p1/schemata + +In the above example the tasks in "p1" and "p0" on socket 0 would use a max b/w +of 1024MB where as on socket 1 they would use 500MB. + +2) Example 2 + +Again two sockets, but this time with a more realistic 20-bit mask. + +Two real time tasks pid=1234 running on processor 0 and pid=5678 running on +processor 1 on socket 0 on a 2-socket and dual core machine. To avoid noisy +neighbors, each of the two real-time tasks exclusively occupies one quarter +of L3 cache on socket 0. +:: + + # mount -t resctrl resctrl /sys/fs/resctrl + # cd /sys/fs/resctrl + +First we reset the schemata for the default group so that the "upper" +50% of the L3 cache on socket 0 and 50% of memory b/w cannot be used by +ordinary tasks:: + + # echo "L3:0=3ff;1=fffff\nMB:0=50;1=100" > schemata + +Next we make a resource group for our first real time task and give +it access to the "top" 25% of the cache on socket 0. +:: + + # mkdir p0 + # echo "L3:0=f8000;1=fffff" > p0/schemata + +Finally we move our first real time task into this resource group. We +also use taskset(1) to ensure the task always runs on a dedicated CPU +on socket 0. Most uses of resource groups will also constrain which +processors tasks run on. +:: + + # echo 1234 > p0/tasks + # taskset -cp 1 1234 + +Ditto for the second real time task (with the remaining 25% of cache):: + + # mkdir p1 + # echo "L3:0=7c00;1=fffff" > p1/schemata + # echo 5678 > p1/tasks + # taskset -cp 2 5678 + +For the same 2 socket system with memory b/w resource and CAT L3 the +schemata would look like(Assume min_bandwidth 10 and bandwidth_gran is +10): + +For our first real time task this would request 20% memory b/w on socket 0. +:: + + # echo -e "L3:0=f8000;1=fffff\nMB:0=20;1=100" > p0/schemata + +For our second real time task this would request an other 20% memory b/w +on socket 0. +:: + + # echo -e "L3:0=f8000;1=fffff\nMB:0=20;1=100" > p0/schemata + +3) Example 3 + +A single socket system which has real-time tasks running on core 4-7 and +non real-time workload assigned to core 0-3. The real-time tasks share text +and data, so a per task association is not required and due to interaction +with the kernel it's desired that the kernel on these cores shares L3 with +the tasks. +:: + + # mount -t resctrl resctrl /sys/fs/resctrl + # cd /sys/fs/resctrl + +First we reset the schemata for the default group so that the "upper" +50% of the L3 cache on socket 0, and 50% of memory bandwidth on socket 0 +cannot be used by ordinary tasks:: + + # echo "L3:0=3ff\nMB:0=50" > schemata + +Next we make a resource group for our real time cores and give it access +to the "top" 50% of the cache on socket 0 and 50% of memory bandwidth on +socket 0. +:: + + # mkdir p0 + # echo "L3:0=ffc00\nMB:0=50" > p0/schemata + +Finally we move core 4-7 over to the new group and make sure that the +kernel and the tasks running there get 50% of the cache. They should +also get 50% of memory bandwidth assuming that the cores 4-7 are SMT +siblings and only the real time threads are scheduled on the cores 4-7. +:: + + # echo F0 > p0/cpus + +4) Example 4 + +The resource groups in previous examples were all in the default "shareable" +mode allowing sharing of their cache allocations. If one resource group +configures a cache allocation then nothing prevents another resource group +to overlap with that allocation. + +In this example a new exclusive resource group will be created on a L2 CAT +system with two L2 cache instances that can be configured with an 8-bit +capacity bitmask. The new exclusive resource group will be configured to use +25% of each cache instance. +:: + + # mount -t resctrl resctrl /sys/fs/resctrl/ + # cd /sys/fs/resctrl + +First, we observe that the default group is configured to allocate to all L2 +cache:: + + # cat schemata + L2:0=ff;1=ff + +We could attempt to create the new resource group at this point, but it will +fail because of the overlap with the schemata of the default group:: + + # mkdir p0 + # echo 'L2:0=0x3;1=0x3' > p0/schemata + # cat p0/mode + shareable + # echo exclusive > p0/mode + -sh: echo: write error: Invalid argument + # cat info/last_cmd_status + schemata overlaps + +To ensure that there is no overlap with another resource group the default +resource group's schemata has to change, making it possible for the new +resource group to become exclusive. +:: + + # echo 'L2:0=0xfc;1=0xfc' > schemata + # echo exclusive > p0/mode + # grep . p0/* + p0/cpus:0 + p0/mode:exclusive + p0/schemata:L2:0=03;1=03 + p0/size:L2:0=262144;1=262144 + +A new resource group will on creation not overlap with an exclusive resource +group:: + + # mkdir p1 + # grep . p1/* + p1/cpus:0 + p1/mode:shareable + p1/schemata:L2:0=fc;1=fc + p1/size:L2:0=786432;1=786432 + +The bit_usage will reflect how the cache is used:: + + # cat info/L2/bit_usage + 0=SSSSSSEE;1=SSSSSSEE + +A resource group cannot be forced to overlap with an exclusive resource group:: + + # echo 'L2:0=0x1;1=0x1' > p1/schemata + -sh: echo: write error: Invalid argument + # cat info/last_cmd_status + overlaps with exclusive group + +Example of Cache Pseudo-Locking +~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ +Lock portion of L2 cache from cache id 1 using CBM 0x3. Pseudo-locked +region is exposed at /dev/pseudo_lock/newlock that can be provided to +application for argument to mmap(). +:: + + # mount -t resctrl resctrl /sys/fs/resctrl/ + # cd /sys/fs/resctrl + +Ensure that there are bits available that can be pseudo-locked, since only +unused bits can be pseudo-locked the bits to be pseudo-locked needs to be +removed from the default resource group's schemata:: + + # cat info/L2/bit_usage + 0=SSSSSSSS;1=SSSSSSSS + # echo 'L2:1=0xfc' > schemata + # cat info/L2/bit_usage + 0=SSSSSSSS;1=SSSSSS00 + +Create a new resource group that will be associated with the pseudo-locked +region, indicate that it will be used for a pseudo-locked region, and +configure the requested pseudo-locked region capacity bitmask:: + + # mkdir newlock + # echo pseudo-locksetup > newlock/mode + # echo 'L2:1=0x3' > newlock/schemata + +On success the resource group's mode will change to pseudo-locked, the +bit_usage will reflect the pseudo-locked region, and the character device +exposing the pseudo-locked region will exist:: + + # cat newlock/mode + pseudo-locked + # cat info/L2/bit_usage + 0=SSSSSSSS;1=SSSSSSPP + # ls -l /dev/pseudo_lock/newlock + crw------- 1 root root 243, 0 Apr 3 05:01 /dev/pseudo_lock/newlock + +:: + + /* + * Example code to access one page of pseudo-locked cache region + * from user space. + */ + #define _GNU_SOURCE + #include + #include + #include + #include + #include + #include + + /* + * It is required that the application runs with affinity to only + * cores associated with the pseudo-locked region. Here the cpu + * is hardcoded for convenience of example. + */ + static int cpuid = 2; + + int main(int argc, char *argv[]) + { + cpu_set_t cpuset; + long page_size; + void *mapping; + int dev_fd; + int ret; + + page_size = sysconf(_SC_PAGESIZE); + + CPU_ZERO(&cpuset); + CPU_SET(cpuid, &cpuset); + ret = sched_setaffinity(0, sizeof(cpuset), &cpuset); + if (ret < 0) { + perror("sched_setaffinity"); + exit(EXIT_FAILURE); + } + + dev_fd = open("/dev/pseudo_lock/newlock", O_RDWR); + if (dev_fd < 0) { + perror("open"); + exit(EXIT_FAILURE); + } + + mapping = mmap(0, page_size, PROT_READ | PROT_WRITE, MAP_SHARED, + dev_fd, 0); + if (mapping == MAP_FAILED) { + perror("mmap"); + close(dev_fd); + exit(EXIT_FAILURE); + } + + /* Application interacts with pseudo-locked memory @mapping */ + + ret = munmap(mapping, page_size); + if (ret < 0) { + perror("munmap"); + close(dev_fd); + exit(EXIT_FAILURE); + } + + close(dev_fd); + exit(EXIT_SUCCESS); + } + +Locking between applications +---------------------------- + +Certain operations on the resctrl filesystem, composed of read/writes +to/from multiple files, must be atomic. + +As an example, the allocation of an exclusive reservation of L3 cache +involves: + + 1. Read the cbmmasks from each directory or the per-resource "bit_usage" + 2. Find a contiguous set of bits in the global CBM bitmask that is clear + in any of the directory cbmmasks + 3. Create a new directory + 4. Set the bits found in step 2 to the new directory "schemata" file + +If two applications attempt to allocate space concurrently then they can +end up allocating the same bits so the reservations are shared instead of +exclusive. + +To coordinate atomic operations on the resctrlfs and to avoid the problem +above, the following locking procedure is recommended: + +Locking is based on flock, which is available in libc and also as a shell +script command + +Write lock: + + A) Take flock(LOCK_EX) on /sys/fs/resctrl + B) Read/write the directory structure. + C) funlock + +Read lock: + + A) Take flock(LOCK_SH) on /sys/fs/resctrl + B) If success read the directory structure. + C) funlock + +Example with bash:: + + # Atomically read directory structure + $ flock -s /sys/fs/resctrl/ find /sys/fs/resctrl + + # Read directory contents and create new subdirectory + + $ cat create-dir.sh + find /sys/fs/resctrl/ > output.txt + mask = function-of(output.txt) + mkdir /sys/fs/resctrl/newres/ + echo mask > /sys/fs/resctrl/newres/schemata + + $ flock /sys/fs/resctrl/ ./create-dir.sh + +Example with C:: + + /* + * Example code do take advisory locks + * before accessing resctrl filesystem + */ + #include + #include + + void resctrl_take_shared_lock(int fd) + { + int ret; + + /* take shared lock on resctrl filesystem */ + ret = flock(fd, LOCK_SH); + if (ret) { + perror("flock"); + exit(-1); + } + } + + void resctrl_take_exclusive_lock(int fd) + { + int ret; + + /* release lock on resctrl filesystem */ + ret = flock(fd, LOCK_EX); + if (ret) { + perror("flock"); + exit(-1); + } + } + + void resctrl_release_lock(int fd) + { + int ret; + + /* take shared lock on resctrl filesystem */ + ret = flock(fd, LOCK_UN); + if (ret) { + perror("flock"); + exit(-1); + } + } + + void main(void) + { + int fd, ret; + + fd = open("/sys/fs/resctrl", O_DIRECTORY); + if (fd == -1) { + perror("open"); + exit(-1); + } + resctrl_take_shared_lock(fd); + /* code to read directory contents */ + resctrl_release_lock(fd); + + resctrl_take_exclusive_lock(fd); + /* code to read and write directory contents */ + resctrl_release_lock(fd); + } + +Examples for RDT Monitoring along with allocation usage +======================================================= +Reading monitored data +---------------------- +Reading an event file (for ex: mon_data/mon_L3_00/llc_occupancy) would +show the current snapshot of LLC occupancy of the corresponding MON +group or CTRL_MON group. + + +Example 1 (Monitor CTRL_MON group and subset of tasks in CTRL_MON group) +------------------------------------------------------------------------ +On a two socket machine (one L3 cache per socket) with just four bits +for cache bit masks:: + + # mount -t resctrl resctrl /sys/fs/resctrl + # cd /sys/fs/resctrl + # mkdir p0 p1 + # echo "L3:0=3;1=c" > /sys/fs/resctrl/p0/schemata + # echo "L3:0=3;1=3" > /sys/fs/resctrl/p1/schemata + # echo 5678 > p1/tasks + # echo 5679 > p1/tasks + +The default resource group is unmodified, so we have access to all parts +of all caches (its schemata file reads "L3:0=f;1=f"). + +Tasks that are under the control of group "p0" may only allocate from the +"lower" 50% on cache ID 0, and the "upper" 50% of cache ID 1. +Tasks in group "p1" use the "lower" 50% of cache on both sockets. + +Create monitor groups and assign a subset of tasks to each monitor group. +:: + + # cd /sys/fs/resctrl/p1/mon_groups + # mkdir m11 m12 + # echo 5678 > m11/tasks + # echo 5679 > m12/tasks + +fetch data (data shown in bytes) +:: + + # cat m11/mon_data/mon_L3_00/llc_occupancy + 16234000 + # cat m11/mon_data/mon_L3_01/llc_occupancy + 14789000 + # cat m12/mon_data/mon_L3_00/llc_occupancy + 16789000 + +The parent ctrl_mon group shows the aggregated data. +:: + + # cat /sys/fs/resctrl/p1/mon_data/mon_l3_00/llc_occupancy + 31234000 + +Example 2 (Monitor a task from its creation) +-------------------------------------------- +On a two socket machine (one L3 cache per socket):: + + # mount -t resctrl resctrl /sys/fs/resctrl + # cd /sys/fs/resctrl + # mkdir p0 p1 + +An RMID is allocated to the group once its created and hence the +below is monitored from its creation. +:: + + # echo $$ > /sys/fs/resctrl/p1/tasks + # + +Fetch the data:: + + # cat /sys/fs/resctrl/p1/mon_data/mon_l3_00/llc_occupancy + 31789000 + +Example 3 (Monitor without CAT support or before creating CAT groups) +--------------------------------------------------------------------- + +Assume a system like HSW has only CQM and no CAT support. In this case +the resctrl will still mount but cannot create CTRL_MON directories. +But user can create different MON groups within the root group thereby +able to monitor all tasks including kernel threads. + +This can also be used to profile jobs cache size footprint before being +able to allocate them to different allocation groups. +:: + + # mount -t resctrl resctrl /sys/fs/resctrl + # cd /sys/fs/resctrl + # mkdir mon_groups/m01 + # mkdir mon_groups/m02 + + # echo 3478 > /sys/fs/resctrl/mon_groups/m01/tasks + # echo 2467 > /sys/fs/resctrl/mon_groups/m02/tasks + +Monitor the groups separately and also get per domain data. From the +below its apparent that the tasks are mostly doing work on +domain(socket) 0. +:: + + # cat /sys/fs/resctrl/mon_groups/m01/mon_L3_00/llc_occupancy + 31234000 + # cat /sys/fs/resctrl/mon_groups/m01/mon_L3_01/llc_occupancy + 34555 + # cat /sys/fs/resctrl/mon_groups/m02/mon_L3_00/llc_occupancy + 31234000 + # cat /sys/fs/resctrl/mon_groups/m02/mon_L3_01/llc_occupancy + 32789 + + +Example 4 (Monitor real time tasks) +----------------------------------- + +A single socket system which has real time tasks running on cores 4-7 +and non real time tasks on other cpus. We want to monitor the cache +occupancy of the real time threads on these cores. +:: + + # mount -t resctrl resctrl /sys/fs/resctrl + # cd /sys/fs/resctrl + # mkdir p1 + +Move the cpus 4-7 over to p1:: + + # echo f0 > p1/cpus + +View the llc occupancy snapshot:: + + # cat /sys/fs/resctrl/p1/mon_data/mon_L3_00/llc_occupancy + 11234000 diff --git a/Documentation/x86/resctrl_ui.txt b/Documentation/x86/resctrl_ui.txt deleted file mode 100644 index c1f95b59e14d..000000000000 --- a/Documentation/x86/resctrl_ui.txt +++ /dev/null @@ -1,1121 +0,0 @@ -User Interface for Resource Control feature - -Intel refers to this feature as Intel Resource Director Technology(Intel(R) RDT). -AMD refers to this feature as AMD Platform Quality of Service(AMD QoS). - -Copyright (C) 2016 Intel Corporation - -Fenghua Yu -Tony Luck -Vikas Shivappa - -This feature is enabled by the CONFIG_X86_CPU_RESCTRL and the x86 /proc/cpuinfo -flag bits: -RDT (Resource Director Technology) Allocation - "rdt_a" -CAT (Cache Allocation Technology) - "cat_l3", "cat_l2" -CDP (Code and Data Prioritization ) - "cdp_l3", "cdp_l2" -CQM (Cache QoS Monitoring) - "cqm_llc", "cqm_occup_llc" -MBM (Memory Bandwidth Monitoring) - "cqm_mbm_total", "cqm_mbm_local" -MBA (Memory Bandwidth Allocation) - "mba" - -To use the feature mount the file system: - - # mount -t resctrl resctrl [-o cdp[,cdpl2][,mba_MBps]] /sys/fs/resctrl - -mount options are: - -"cdp": Enable code/data prioritization in L3 cache allocations. -"cdpl2": Enable code/data prioritization in L2 cache allocations. -"mba_MBps": Enable the MBA Software Controller(mba_sc) to specify MBA - bandwidth in MBps - -L2 and L3 CDP are controlled seperately. - -RDT features are orthogonal. A particular system may support only -monitoring, only control, or both monitoring and control. Cache -pseudo-locking is a unique way of using cache control to "pin" or -"lock" data in the cache. Details can be found in -"Cache Pseudo-Locking". - - -The mount succeeds if either of allocation or monitoring is present, but -only those files and directories supported by the system will be created. -For more details on the behavior of the interface during monitoring -and allocation, see the "Resource alloc and monitor groups" section. - -Info directory --------------- - -The 'info' directory contains information about the enabled -resources. Each resource has its own subdirectory. The subdirectory -names reflect the resource names. - -Each subdirectory contains the following files with respect to -allocation: - -Cache resource(L3/L2) subdirectory contains the following files -related to allocation: - -"num_closids": The number of CLOSIDs which are valid for this - resource. The kernel uses the smallest number of - CLOSIDs of all enabled resources as limit. - -"cbm_mask": The bitmask which is valid for this resource. - This mask is equivalent to 100%. - -"min_cbm_bits": The minimum number of consecutive bits which - must be set when writing a mask. - -"shareable_bits": Bitmask of shareable resource with other executing - entities (e.g. I/O). User can use this when - setting up exclusive cache partitions. Note that - some platforms support devices that have their - own settings for cache use which can over-ride - these bits. -"bit_usage": Annotated capacity bitmasks showing how all - instances of the resource are used. The legend is: - "0" - Corresponding region is unused. When the system's - resources have been allocated and a "0" is found - in "bit_usage" it is a sign that resources are - wasted. - "H" - Corresponding region is used by hardware only - but available for software use. If a resource - has bits set in "shareable_bits" but not all - of these bits appear in the resource groups' - schematas then the bits appearing in - "shareable_bits" but no resource group will - be marked as "H". - "X" - Corresponding region is available for sharing and - used by hardware and software. These are the - bits that appear in "shareable_bits" as - well as a resource group's allocation. - "S" - Corresponding region is used by software - and available for sharing. - "E" - Corresponding region is used exclusively by - one resource group. No sharing allowed. - "P" - Corresponding region is pseudo-locked. No - sharing allowed. - -Memory bandwitdh(MB) subdirectory contains the following files -with respect to allocation: - -"min_bandwidth": The minimum memory bandwidth percentage which - user can request. - -"bandwidth_gran": The granularity in which the memory bandwidth - percentage is allocated. The allocated - b/w percentage is rounded off to the next - control step available on the hardware. The - available bandwidth control steps are: - min_bandwidth + N * bandwidth_gran. - -"delay_linear": Indicates if the delay scale is linear or - non-linear. This field is purely informational - only. - -If RDT monitoring is available there will be an "L3_MON" directory -with the following files: - -"num_rmids": The number of RMIDs available. This is the - upper bound for how many "CTRL_MON" + "MON" - groups can be created. - -"mon_features": Lists the monitoring events if - monitoring is enabled for the resource. - -"max_threshold_occupancy": - Read/write file provides the largest value (in - bytes) at which a previously used LLC_occupancy - counter can be considered for re-use. - -Finally, in the top level of the "info" directory there is a file -named "last_cmd_status". This is reset with every "command" issued -via the file system (making new directories or writing to any of the -control files). If the command was successful, it will read as "ok". -If the command failed, it will provide more information that can be -conveyed in the error returns from file operations. E.g. - - # echo L3:0=f7 > schemata - bash: echo: write error: Invalid argument - # cat info/last_cmd_status - mask f7 has non-consecutive 1-bits - -Resource alloc and monitor groups ---------------------------------- - -Resource groups are represented as directories in the resctrl file -system. The default group is the root directory which, immediately -after mounting, owns all the tasks and cpus in the system and can make -full use of all resources. - -On a system with RDT control features additional directories can be -created in the root directory that specify different amounts of each -resource (see "schemata" below). The root and these additional top level -directories are referred to as "CTRL_MON" groups below. - -On a system with RDT monitoring the root directory and other top level -directories contain a directory named "mon_groups" in which additional -directories can be created to monitor subsets of tasks in the CTRL_MON -group that is their ancestor. These are called "MON" groups in the rest -of this document. - -Removing a directory will move all tasks and cpus owned by the group it -represents to the parent. Removing one of the created CTRL_MON groups -will automatically remove all MON groups below it. - -All groups contain the following files: - -"tasks": - Reading this file shows the list of all tasks that belong to - this group. Writing a task id to the file will add a task to the - group. If the group is a CTRL_MON group the task is removed from - whichever previous CTRL_MON group owned the task and also from - any MON group that owned the task. If the group is a MON group, - then the task must already belong to the CTRL_MON parent of this - group. The task is removed from any previous MON group. - - -"cpus": - Reading this file shows a bitmask of the logical CPUs owned by - this group. Writing a mask to this file will add and remove - CPUs to/from this group. As with the tasks file a hierarchy is - maintained where MON groups may only include CPUs owned by the - parent CTRL_MON group. - When the resouce group is in pseudo-locked mode this file will - only be readable, reflecting the CPUs associated with the - pseudo-locked region. - - -"cpus_list": - Just like "cpus", only using ranges of CPUs instead of bitmasks. - - -When control is enabled all CTRL_MON groups will also contain: - -"schemata": - A list of all the resources available to this group. - Each resource has its own line and format - see below for details. - -"size": - Mirrors the display of the "schemata" file to display the size in - bytes of each allocation instead of the bits representing the - allocation. - -"mode": - The "mode" of the resource group dictates the sharing of its - allocations. A "shareable" resource group allows sharing of its - allocations while an "exclusive" resource group does not. A - cache pseudo-locked region is created by first writing - "pseudo-locksetup" to the "mode" file before writing the cache - pseudo-locked region's schemata to the resource group's "schemata" - file. On successful pseudo-locked region creation the mode will - automatically change to "pseudo-locked". - -When monitoring is enabled all MON groups will also contain: - -"mon_data": - This contains a set of files organized by L3 domain and by - RDT event. E.g. on a system with two L3 domains there will - be subdirectories "mon_L3_00" and "mon_L3_01". Each of these - directories have one file per event (e.g. "llc_occupancy", - "mbm_total_bytes", and "mbm_local_bytes"). In a MON group these - files provide a read out of the current value of the event for - all tasks in the group. In CTRL_MON groups these files provide - the sum for all tasks in the CTRL_MON group and all tasks in - MON groups. Please see example section for more details on usage. - -Resource allocation rules -------------------------- -When a task is running the following rules define which resources are -available to it: - -1) If the task is a member of a non-default group, then the schemata - for that group is used. - -2) Else if the task belongs to the default group, but is running on a - CPU that is assigned to some specific group, then the schemata for the - CPU's group is used. - -3) Otherwise the schemata for the default group is used. - -Resource monitoring rules -------------------------- -1) If a task is a member of a MON group, or non-default CTRL_MON group - then RDT events for the task will be reported in that group. - -2) If a task is a member of the default CTRL_MON group, but is running - on a CPU that is assigned to some specific group, then the RDT events - for the task will be reported in that group. - -3) Otherwise RDT events for the task will be reported in the root level - "mon_data" group. - - -Notes on cache occupancy monitoring and control ------------------------------------------------ -When moving a task from one group to another you should remember that -this only affects *new* cache allocations by the task. E.g. you may have -a task in a monitor group showing 3 MB of cache occupancy. If you move -to a new group and immediately check the occupancy of the old and new -groups you will likely see that the old group is still showing 3 MB and -the new group zero. When the task accesses locations still in cache from -before the move, the h/w does not update any counters. On a busy system -you will likely see the occupancy in the old group go down as cache lines -are evicted and re-used while the occupancy in the new group rises as -the task accesses memory and loads into the cache are counted based on -membership in the new group. - -The same applies to cache allocation control. Moving a task to a group -with a smaller cache partition will not evict any cache lines. The -process may continue to use them from the old partition. - -Hardware uses CLOSid(Class of service ID) and an RMID(Resource monitoring ID) -to identify a control group and a monitoring group respectively. Each of -the resource groups are mapped to these IDs based on the kind of group. The -number of CLOSid and RMID are limited by the hardware and hence the creation of -a "CTRL_MON" directory may fail if we run out of either CLOSID or RMID -and creation of "MON" group may fail if we run out of RMIDs. - -max_threshold_occupancy - generic concepts ------------------------------------------- - -Note that an RMID once freed may not be immediately available for use as -the RMID is still tagged the cache lines of the previous user of RMID. -Hence such RMIDs are placed on limbo list and checked back if the cache -occupancy has gone down. If there is a time when system has a lot of -limbo RMIDs but which are not ready to be used, user may see an -EBUSY -during mkdir. - -max_threshold_occupancy is a user configurable value to determine the -occupancy at which an RMID can be freed. - -Schemata files - general concepts ---------------------------------- -Each line in the file describes one resource. The line starts with -the name of the resource, followed by specific values to be applied -in each of the instances of that resource on the system. - -Cache IDs ---------- -On current generation systems there is one L3 cache per socket and L2 -caches are generally just shared by the hyperthreads on a core, but this -isn't an architectural requirement. We could have multiple separate L3 -caches on a socket, multiple cores could share an L2 cache. So instead -of using "socket" or "core" to define the set of logical cpus sharing -a resource we use a "Cache ID". At a given cache level this will be a -unique number across the whole system (but it isn't guaranteed to be a -contiguous sequence, there may be gaps). To find the ID for each logical -CPU look in /sys/devices/system/cpu/cpu*/cache/index*/id - -Cache Bit Masks (CBM) ---------------------- -For cache resources we describe the portion of the cache that is available -for allocation using a bitmask. The maximum value of the mask is defined -by each cpu model (and may be different for different cache levels). It -is found using CPUID, but is also provided in the "info" directory of -the resctrl file system in "info/{resource}/cbm_mask". X86 hardware -requires that these masks have all the '1' bits in a contiguous block. So -0x3, 0x6 and 0xC are legal 4-bit masks with two bits set, but 0x5, 0x9 -and 0xA are not. On a system with a 20-bit mask each bit represents 5% -of the capacity of the cache. You could partition the cache into four -equal parts with masks: 0x1f, 0x3e0, 0x7c00, 0xf8000. - -Memory bandwidth Allocation and monitoring ------------------------------------------- - -For Memory bandwidth resource, by default the user controls the resource -by indicating the percentage of total memory bandwidth. - -The minimum bandwidth percentage value for each cpu model is predefined -and can be looked up through "info/MB/min_bandwidth". The bandwidth -granularity that is allocated is also dependent on the cpu model and can -be looked up at "info/MB/bandwidth_gran". The available bandwidth -control steps are: min_bw + N * bw_gran. Intermediate values are rounded -to the next control step available on the hardware. - -The bandwidth throttling is a core specific mechanism on some of Intel -SKUs. Using a high bandwidth and a low bandwidth setting on two threads -sharing a core will result in both threads being throttled to use the -low bandwidth. The fact that Memory bandwidth allocation(MBA) is a core -specific mechanism where as memory bandwidth monitoring(MBM) is done at -the package level may lead to confusion when users try to apply control -via the MBA and then monitor the bandwidth to see if the controls are -effective. Below are such scenarios: - -1. User may *not* see increase in actual bandwidth when percentage - values are increased: - -This can occur when aggregate L2 external bandwidth is more than L3 -external bandwidth. Consider an SKL SKU with 24 cores on a package and -where L2 external is 10GBps (hence aggregate L2 external bandwidth is -240GBps) and L3 external bandwidth is 100GBps. Now a workload with '20 -threads, having 50% bandwidth, each consuming 5GBps' consumes the max L3 -bandwidth of 100GBps although the percentage value specified is only 50% -<< 100%. Hence increasing the bandwidth percentage will not yeild any -more bandwidth. This is because although the L2 external bandwidth still -has capacity, the L3 external bandwidth is fully used. Also note that -this would be dependent on number of cores the benchmark is run on. - -2. Same bandwidth percentage may mean different actual bandwidth - depending on # of threads: - -For the same SKU in #1, a 'single thread, with 10% bandwidth' and '4 -thread, with 10% bandwidth' can consume upto 10GBps and 40GBps although -they have same percentage bandwidth of 10%. This is simply because as -threads start using more cores in an rdtgroup, the actual bandwidth may -increase or vary although user specified bandwidth percentage is same. - -In order to mitigate this and make the interface more user friendly, -resctrl added support for specifying the bandwidth in MBps as well. The -kernel underneath would use a software feedback mechanism or a "Software -Controller(mba_sc)" which reads the actual bandwidth using MBM counters -and adjust the memowy bandwidth percentages to ensure - - "actual bandwidth < user specified bandwidth". - -By default, the schemata would take the bandwidth percentage values -where as user can switch to the "MBA software controller" mode using -a mount option 'mba_MBps'. The schemata format is specified in the below -sections. - -L3 schemata file details (code and data prioritization disabled) ----------------------------------------------------------------- -With CDP disabled the L3 schemata format is: - - L3:=;=;... - -L3 schemata file details (CDP enabled via mount option to resctrl) ------------------------------------------------------------------- -When CDP is enabled L3 control is split into two separate resources -so you can specify independent masks for code and data like this: - - L3data:=;=;... - L3code:=;=;... - -L2 schemata file details ------------------------- -L2 cache does not support code and data prioritization, so the -schemata format is always: - - L2:=;=;... - -Memory bandwidth Allocation (default mode) ------------------------------------------- - -Memory b/w domain is L3 cache. - - MB:=bandwidth0;=bandwidth1;... - -Memory bandwidth Allocation specified in MBps ---------------------------------------------- - -Memory bandwidth domain is L3 cache. - - MB:=bw_MBps0;=bw_MBps1;... - -Reading/writing the schemata file ---------------------------------- -Reading the schemata file will show the state of all resources -on all domains. When writing you only need to specify those values -which you wish to change. E.g. - -# cat schemata -L3DATA:0=fffff;1=fffff;2=fffff;3=fffff -L3CODE:0=fffff;1=fffff;2=fffff;3=fffff -# echo "L3DATA:2=3c0;" > schemata -# cat schemata -L3DATA:0=fffff;1=fffff;2=3c0;3=fffff -L3CODE:0=fffff;1=fffff;2=fffff;3=fffff - -Cache Pseudo-Locking --------------------- -CAT enables a user to specify the amount of cache space that an -application can fill. Cache pseudo-locking builds on the fact that a -CPU can still read and write data pre-allocated outside its current -allocated area on a cache hit. With cache pseudo-locking, data can be -preloaded into a reserved portion of cache that no application can -fill, and from that point on will only serve cache hits. The cache -pseudo-locked memory is made accessible to user space where an -application can map it into its virtual address space and thus have -a region of memory with reduced average read latency. - -The creation of a cache pseudo-locked region is triggered by a request -from the user to do so that is accompanied by a schemata of the region -to be pseudo-locked. The cache pseudo-locked region is created as follows: -- Create a CAT allocation CLOSNEW with a CBM matching the schemata - from the user of the cache region that will contain the pseudo-locked - memory. This region must not overlap with any current CAT allocation/CLOS - on the system and no future overlap with this cache region is allowed - while the pseudo-locked region exists. -- Create a contiguous region of memory of the same size as the cache - region. -- Flush the cache, disable hardware prefetchers, disable preemption. -- Make CLOSNEW the active CLOS and touch the allocated memory to load - it into the cache. -- Set the previous CLOS as active. -- At this point the closid CLOSNEW can be released - the cache - pseudo-locked region is protected as long as its CBM does not appear in - any CAT allocation. Even though the cache pseudo-locked region will from - this point on not appear in any CBM of any CLOS an application running with - any CLOS will be able to access the memory in the pseudo-locked region since - the region continues to serve cache hits. -- The contiguous region of memory loaded into the cache is exposed to - user-space as a character device. - -Cache pseudo-locking increases the probability that data will remain -in the cache via carefully configuring the CAT feature and controlling -application behavior. There is no guarantee that data is placed in -cache. Instructions like INVD, WBINVD, CLFLUSH, etc. can still evict -“locked” data from cache. Power management C-states may shrink or -power off cache. Deeper C-states will automatically be restricted on -pseudo-locked region creation. - -It is required that an application using a pseudo-locked region runs -with affinity to the cores (or a subset of the cores) associated -with the cache on which the pseudo-locked region resides. A sanity check -within the code will not allow an application to map pseudo-locked memory -unless it runs with affinity to cores associated with the cache on which the -pseudo-locked region resides. The sanity check is only done during the -initial mmap() handling, there is no enforcement afterwards and the -application self needs to ensure it remains affine to the correct cores. - -Pseudo-locking is accomplished in two stages: -1) During the first stage the system administrator allocates a portion - of cache that should be dedicated to pseudo-locking. At this time an - equivalent portion of memory is allocated, loaded into allocated - cache portion, and exposed as a character device. -2) During the second stage a user-space application maps (mmap()) the - pseudo-locked memory into its address space. - -Cache Pseudo-Locking Interface ------------------------------- -A pseudo-locked region is created using the resctrl interface as follows: - -1) Create a new resource group by creating a new directory in /sys/fs/resctrl. -2) Change the new resource group's mode to "pseudo-locksetup" by writing - "pseudo-locksetup" to the "mode" file. -3) Write the schemata of the pseudo-locked region to the "schemata" file. All - bits within the schemata should be "unused" according to the "bit_usage" - file. - -On successful pseudo-locked region creation the "mode" file will contain -"pseudo-locked" and a new character device with the same name as the resource -group will exist in /dev/pseudo_lock. This character device can be mmap()'ed -by user space in order to obtain access to the pseudo-locked memory region. - -An example of cache pseudo-locked region creation and usage can be found below. - -Cache Pseudo-Locking Debugging Interface ---------------------------------------- -The pseudo-locking debugging interface is enabled by default (if -CONFIG_DEBUG_FS is enabled) and can be found in /sys/kernel/debug/resctrl. - -There is no explicit way for the kernel to test if a provided memory -location is present in the cache. The pseudo-locking debugging interface uses -the tracing infrastructure to provide two ways to measure cache residency of -the pseudo-locked region: -1) Memory access latency using the pseudo_lock_mem_latency tracepoint. Data - from these measurements are best visualized using a hist trigger (see - example below). In this test the pseudo-locked region is traversed at - a stride of 32 bytes while hardware prefetchers and preemption - are disabled. This also provides a substitute visualization of cache - hits and misses. -2) Cache hit and miss measurements using model specific precision counters if - available. Depending on the levels of cache on the system the pseudo_lock_l2 - and pseudo_lock_l3 tracepoints are available. - -When a pseudo-locked region is created a new debugfs directory is created for -it in debugfs as /sys/kernel/debug/resctrl/. A single -write-only file, pseudo_lock_measure, is present in this directory. The -measurement of the pseudo-locked region depends on the number written to this -debugfs file: -1 - writing "1" to the pseudo_lock_measure file will trigger the latency - measurement captured in the pseudo_lock_mem_latency tracepoint. See - example below. -2 - writing "2" to the pseudo_lock_measure file will trigger the L2 cache - residency (cache hits and misses) measurement captured in the - pseudo_lock_l2 tracepoint. See example below. -3 - writing "3" to the pseudo_lock_measure file will trigger the L3 cache - residency (cache hits and misses) measurement captured in the - pseudo_lock_l3 tracepoint. - -All measurements are recorded with the tracing infrastructure. This requires -the relevant tracepoints to be enabled before the measurement is triggered. - -Example of latency debugging interface: -In this example a pseudo-locked region named "newlock" was created. Here is -how we can measure the latency in cycles of reading from this region and -visualize this data with a histogram that is available if CONFIG_HIST_TRIGGERS -is set: -# :> /sys/kernel/debug/tracing/trace -# echo 'hist:keys=latency' > /sys/kernel/debug/tracing/events/resctrl/pseudo_lock_mem_latency/trigger -# echo 1 > /sys/kernel/debug/tracing/events/resctrl/pseudo_lock_mem_latency/enable -# echo 1 > /sys/kernel/debug/resctrl/newlock/pseudo_lock_measure -# echo 0 > /sys/kernel/debug/tracing/events/resctrl/pseudo_lock_mem_latency/enable -# cat /sys/kernel/debug/tracing/events/resctrl/pseudo_lock_mem_latency/hist - -# event histogram -# -# trigger info: hist:keys=latency:vals=hitcount:sort=hitcount:size=2048 [active] -# - -{ latency: 456 } hitcount: 1 -{ latency: 50 } hitcount: 83 -{ latency: 36 } hitcount: 96 -{ latency: 44 } hitcount: 174 -{ latency: 48 } hitcount: 195 -{ latency: 46 } hitcount: 262 -{ latency: 42 } hitcount: 693 -{ latency: 40 } hitcount: 3204 -{ latency: 38 } hitcount: 3484 - -Totals: - Hits: 8192 - Entries: 9 - Dropped: 0 - -Example of cache hits/misses debugging: -In this example a pseudo-locked region named "newlock" was created on the L2 -cache of a platform. Here is how we can obtain details of the cache hits -and misses using the platform's precision counters. - -# :> /sys/kernel/debug/tracing/trace -# echo 1 > /sys/kernel/debug/tracing/events/resctrl/pseudo_lock_l2/enable -# echo 2 > /sys/kernel/debug/resctrl/newlock/pseudo_lock_measure -# echo 0 > /sys/kernel/debug/tracing/events/resctrl/pseudo_lock_l2/enable -# cat /sys/kernel/debug/tracing/trace - -# tracer: nop -# -# _-----=> irqs-off -# / _----=> need-resched -# | / _---=> hardirq/softirq -# || / _--=> preempt-depth -# ||| / delay -# TASK-PID CPU# |||| TIMESTAMP FUNCTION -# | | | |||| | | - pseudo_lock_mea-1672 [002] .... 3132.860500: pseudo_lock_l2: hits=4097 miss=0 - - -Examples for RDT allocation usage: - -Example 1 ---------- -On a two socket machine (one L3 cache per socket) with just four bits -for cache bit masks, minimum b/w of 10% with a memory bandwidth -granularity of 10% - -# mount -t resctrl resctrl /sys/fs/resctrl -# cd /sys/fs/resctrl -# mkdir p0 p1 -# echo "L3:0=3;1=c\nMB:0=50;1=50" > /sys/fs/resctrl/p0/schemata -# echo "L3:0=3;1=3\nMB:0=50;1=50" > /sys/fs/resctrl/p1/schemata - -The default resource group is unmodified, so we have access to all parts -of all caches (its schemata file reads "L3:0=f;1=f"). - -Tasks that are under the control of group "p0" may only allocate from the -"lower" 50% on cache ID 0, and the "upper" 50% of cache ID 1. -Tasks in group "p1" use the "lower" 50% of cache on both sockets. - -Similarly, tasks that are under the control of group "p0" may use a -maximum memory b/w of 50% on socket0 and 50% on socket 1. -Tasks in group "p1" may also use 50% memory b/w on both sockets. -Note that unlike cache masks, memory b/w cannot specify whether these -allocations can overlap or not. The allocations specifies the maximum -b/w that the group may be able to use and the system admin can configure -the b/w accordingly. - -If the MBA is specified in MB(megabytes) then user can enter the max b/w in MB -rather than the percentage values. - -# echo "L3:0=3;1=c\nMB:0=1024;1=500" > /sys/fs/resctrl/p0/schemata -# echo "L3:0=3;1=3\nMB:0=1024;1=500" > /sys/fs/resctrl/p1/schemata - -In the above example the tasks in "p1" and "p0" on socket 0 would use a max b/w -of 1024MB where as on socket 1 they would use 500MB. - -Example 2 ---------- -Again two sockets, but this time with a more realistic 20-bit mask. - -Two real time tasks pid=1234 running on processor 0 and pid=5678 running on -processor 1 on socket 0 on a 2-socket and dual core machine. To avoid noisy -neighbors, each of the two real-time tasks exclusively occupies one quarter -of L3 cache on socket 0. - -# mount -t resctrl resctrl /sys/fs/resctrl -# cd /sys/fs/resctrl - -First we reset the schemata for the default group so that the "upper" -50% of the L3 cache on socket 0 and 50% of memory b/w cannot be used by -ordinary tasks: - -# echo "L3:0=3ff;1=fffff\nMB:0=50;1=100" > schemata - -Next we make a resource group for our first real time task and give -it access to the "top" 25% of the cache on socket 0. - -# mkdir p0 -# echo "L3:0=f8000;1=fffff" > p0/schemata - -Finally we move our first real time task into this resource group. We -also use taskset(1) to ensure the task always runs on a dedicated CPU -on socket 0. Most uses of resource groups will also constrain which -processors tasks run on. - -# echo 1234 > p0/tasks -# taskset -cp 1 1234 - -Ditto for the second real time task (with the remaining 25% of cache): - -# mkdir p1 -# echo "L3:0=7c00;1=fffff" > p1/schemata -# echo 5678 > p1/tasks -# taskset -cp 2 5678 - -For the same 2 socket system with memory b/w resource and CAT L3 the -schemata would look like(Assume min_bandwidth 10 and bandwidth_gran is -10): - -For our first real time task this would request 20% memory b/w on socket -0. - -# echo -e "L3:0=f8000;1=fffff\nMB:0=20;1=100" > p0/schemata - -For our second real time task this would request an other 20% memory b/w -on socket 0. - -# echo -e "L3:0=f8000;1=fffff\nMB:0=20;1=100" > p0/schemata - -Example 3 ---------- - -A single socket system which has real-time tasks running on core 4-7 and -non real-time workload assigned to core 0-3. The real-time tasks share text -and data, so a per task association is not required and due to interaction -with the kernel it's desired that the kernel on these cores shares L3 with -the tasks. - -# mount -t resctrl resctrl /sys/fs/resctrl -# cd /sys/fs/resctrl - -First we reset the schemata for the default group so that the "upper" -50% of the L3 cache on socket 0, and 50% of memory bandwidth on socket 0 -cannot be used by ordinary tasks: - -# echo "L3:0=3ff\nMB:0=50" > schemata - -Next we make a resource group for our real time cores and give it access -to the "top" 50% of the cache on socket 0 and 50% of memory bandwidth on -socket 0. - -# mkdir p0 -# echo "L3:0=ffc00\nMB:0=50" > p0/schemata - -Finally we move core 4-7 over to the new group and make sure that the -kernel and the tasks running there get 50% of the cache. They should -also get 50% of memory bandwidth assuming that the cores 4-7 are SMT -siblings and only the real time threads are scheduled on the cores 4-7. - -# echo F0 > p0/cpus - -Example 4 ---------- - -The resource groups in previous examples were all in the default "shareable" -mode allowing sharing of their cache allocations. If one resource group -configures a cache allocation then nothing prevents another resource group -to overlap with that allocation. - -In this example a new exclusive resource group will be created on a L2 CAT -system with two L2 cache instances that can be configured with an 8-bit -capacity bitmask. The new exclusive resource group will be configured to use -25% of each cache instance. - -# mount -t resctrl resctrl /sys/fs/resctrl/ -# cd /sys/fs/resctrl - -First, we observe that the default group is configured to allocate to all L2 -cache: - -# cat schemata -L2:0=ff;1=ff - -We could attempt to create the new resource group at this point, but it will -fail because of the overlap with the schemata of the default group: -# mkdir p0 -# echo 'L2:0=0x3;1=0x3' > p0/schemata -# cat p0/mode -shareable -# echo exclusive > p0/mode --sh: echo: write error: Invalid argument -# cat info/last_cmd_status -schemata overlaps - -To ensure that there is no overlap with another resource group the default -resource group's schemata has to change, making it possible for the new -resource group to become exclusive. -# echo 'L2:0=0xfc;1=0xfc' > schemata -# echo exclusive > p0/mode -# grep . p0/* -p0/cpus:0 -p0/mode:exclusive -p0/schemata:L2:0=03;1=03 -p0/size:L2:0=262144;1=262144 - -A new resource group will on creation not overlap with an exclusive resource -group: -# mkdir p1 -# grep . p1/* -p1/cpus:0 -p1/mode:shareable -p1/schemata:L2:0=fc;1=fc -p1/size:L2:0=786432;1=786432 - -The bit_usage will reflect how the cache is used: -# cat info/L2/bit_usage -0=SSSSSSEE;1=SSSSSSEE - -A resource group cannot be forced to overlap with an exclusive resource group: -# echo 'L2:0=0x1;1=0x1' > p1/schemata --sh: echo: write error: Invalid argument -# cat info/last_cmd_status -overlaps with exclusive group - -Example of Cache Pseudo-Locking -------------------------------- -Lock portion of L2 cache from cache id 1 using CBM 0x3. Pseudo-locked -region is exposed at /dev/pseudo_lock/newlock that can be provided to -application for argument to mmap(). - -# mount -t resctrl resctrl /sys/fs/resctrl/ -# cd /sys/fs/resctrl - -Ensure that there are bits available that can be pseudo-locked, since only -unused bits can be pseudo-locked the bits to be pseudo-locked needs to be -removed from the default resource group's schemata: -# cat info/L2/bit_usage -0=SSSSSSSS;1=SSSSSSSS -# echo 'L2:1=0xfc' > schemata -# cat info/L2/bit_usage -0=SSSSSSSS;1=SSSSSS00 - -Create a new resource group that will be associated with the pseudo-locked -region, indicate that it will be used for a pseudo-locked region, and -configure the requested pseudo-locked region capacity bitmask: - -# mkdir newlock -# echo pseudo-locksetup > newlock/mode -# echo 'L2:1=0x3' > newlock/schemata - -On success the resource group's mode will change to pseudo-locked, the -bit_usage will reflect the pseudo-locked region, and the character device -exposing the pseudo-locked region will exist: - -# cat newlock/mode -pseudo-locked -# cat info/L2/bit_usage -0=SSSSSSSS;1=SSSSSSPP -# ls -l /dev/pseudo_lock/newlock -crw------- 1 root root 243, 0 Apr 3 05:01 /dev/pseudo_lock/newlock - -/* - * Example code to access one page of pseudo-locked cache region - * from user space. - */ -#define _GNU_SOURCE -#include -#include -#include -#include -#include -#include - -/* - * It is required that the application runs with affinity to only - * cores associated with the pseudo-locked region. Here the cpu - * is hardcoded for convenience of example. - */ -static int cpuid = 2; - -int main(int argc, char *argv[]) -{ - cpu_set_t cpuset; - long page_size; - void *mapping; - int dev_fd; - int ret; - - page_size = sysconf(_SC_PAGESIZE); - - CPU_ZERO(&cpuset); - CPU_SET(cpuid, &cpuset); - ret = sched_setaffinity(0, sizeof(cpuset), &cpuset); - if (ret < 0) { - perror("sched_setaffinity"); - exit(EXIT_FAILURE); - } - - dev_fd = open("/dev/pseudo_lock/newlock", O_RDWR); - if (dev_fd < 0) { - perror("open"); - exit(EXIT_FAILURE); - } - - mapping = mmap(0, page_size, PROT_READ | PROT_WRITE, MAP_SHARED, - dev_fd, 0); - if (mapping == MAP_FAILED) { - perror("mmap"); - close(dev_fd); - exit(EXIT_FAILURE); - } - - /* Application interacts with pseudo-locked memory @mapping */ - - ret = munmap(mapping, page_size); - if (ret < 0) { - perror("munmap"); - close(dev_fd); - exit(EXIT_FAILURE); - } - - close(dev_fd); - exit(EXIT_SUCCESS); -} - -Locking between applications ----------------------------- - -Certain operations on the resctrl filesystem, composed of read/writes -to/from multiple files, must be atomic. - -As an example, the allocation of an exclusive reservation of L3 cache -involves: - - 1. Read the cbmmasks from each directory or the per-resource "bit_usage" - 2. Find a contiguous set of bits in the global CBM bitmask that is clear - in any of the directory cbmmasks - 3. Create a new directory - 4. Set the bits found in step 2 to the new directory "schemata" file - -If two applications attempt to allocate space concurrently then they can -end up allocating the same bits so the reservations are shared instead of -exclusive. - -To coordinate atomic operations on the resctrlfs and to avoid the problem -above, the following locking procedure is recommended: - -Locking is based on flock, which is available in libc and also as a shell -script command - -Write lock: - - A) Take flock(LOCK_EX) on /sys/fs/resctrl - B) Read/write the directory structure. - C) funlock - -Read lock: - - A) Take flock(LOCK_SH) on /sys/fs/resctrl - B) If success read the directory structure. - C) funlock - -Example with bash: - -# Atomically read directory structure -$ flock -s /sys/fs/resctrl/ find /sys/fs/resctrl - -# Read directory contents and create new subdirectory - -$ cat create-dir.sh -find /sys/fs/resctrl/ > output.txt -mask = function-of(output.txt) -mkdir /sys/fs/resctrl/newres/ -echo mask > /sys/fs/resctrl/newres/schemata - -$ flock /sys/fs/resctrl/ ./create-dir.sh - -Example with C: - -/* - * Example code do take advisory locks - * before accessing resctrl filesystem - */ -#include -#include - -void resctrl_take_shared_lock(int fd) -{ - int ret; - - /* take shared lock on resctrl filesystem */ - ret = flock(fd, LOCK_SH); - if (ret) { - perror("flock"); - exit(-1); - } -} - -void resctrl_take_exclusive_lock(int fd) -{ - int ret; - - /* release lock on resctrl filesystem */ - ret = flock(fd, LOCK_EX); - if (ret) { - perror("flock"); - exit(-1); - } -} - -void resctrl_release_lock(int fd) -{ - int ret; - - /* take shared lock on resctrl filesystem */ - ret = flock(fd, LOCK_UN); - if (ret) { - perror("flock"); - exit(-1); - } -} - -void main(void) -{ - int fd, ret; - - fd = open("/sys/fs/resctrl", O_DIRECTORY); - if (fd == -1) { - perror("open"); - exit(-1); - } - resctrl_take_shared_lock(fd); - /* code to read directory contents */ - resctrl_release_lock(fd); - - resctrl_take_exclusive_lock(fd); - /* code to read and write directory contents */ - resctrl_release_lock(fd); -} - -Examples for RDT Monitoring along with allocation usage: - -Reading monitored data ----------------------- -Reading an event file (for ex: mon_data/mon_L3_00/llc_occupancy) would -show the current snapshot of LLC occupancy of the corresponding MON -group or CTRL_MON group. - - -Example 1 (Monitor CTRL_MON group and subset of tasks in CTRL_MON group) ---------- -On a two socket machine (one L3 cache per socket) with just four bits -for cache bit masks - -# mount -t resctrl resctrl /sys/fs/resctrl -# cd /sys/fs/resctrl -# mkdir p0 p1 -# echo "L3:0=3;1=c" > /sys/fs/resctrl/p0/schemata -# echo "L3:0=3;1=3" > /sys/fs/resctrl/p1/schemata -# echo 5678 > p1/tasks -# echo 5679 > p1/tasks - -The default resource group is unmodified, so we have access to all parts -of all caches (its schemata file reads "L3:0=f;1=f"). - -Tasks that are under the control of group "p0" may only allocate from the -"lower" 50% on cache ID 0, and the "upper" 50% of cache ID 1. -Tasks in group "p1" use the "lower" 50% of cache on both sockets. - -Create monitor groups and assign a subset of tasks to each monitor group. - -# cd /sys/fs/resctrl/p1/mon_groups -# mkdir m11 m12 -# echo 5678 > m11/tasks -# echo 5679 > m12/tasks - -fetch data (data shown in bytes) - -# cat m11/mon_data/mon_L3_00/llc_occupancy -16234000 -# cat m11/mon_data/mon_L3_01/llc_occupancy -14789000 -# cat m12/mon_data/mon_L3_00/llc_occupancy -16789000 - -The parent ctrl_mon group shows the aggregated data. - -# cat /sys/fs/resctrl/p1/mon_data/mon_l3_00/llc_occupancy -31234000 - -Example 2 (Monitor a task from its creation) ---------- -On a two socket machine (one L3 cache per socket) - -# mount -t resctrl resctrl /sys/fs/resctrl -# cd /sys/fs/resctrl -# mkdir p0 p1 - -An RMID is allocated to the group once its created and hence the -below is monitored from its creation. - -# echo $$ > /sys/fs/resctrl/p1/tasks -# - -Fetch the data - -# cat /sys/fs/resctrl/p1/mon_data/mon_l3_00/llc_occupancy -31789000 - -Example 3 (Monitor without CAT support or before creating CAT groups) ---------- - -Assume a system like HSW has only CQM and no CAT support. In this case -the resctrl will still mount but cannot create CTRL_MON directories. -But user can create different MON groups within the root group thereby -able to monitor all tasks including kernel threads. - -This can also be used to profile jobs cache size footprint before being -able to allocate them to different allocation groups. - -# mount -t resctrl resctrl /sys/fs/resctrl -# cd /sys/fs/resctrl -# mkdir mon_groups/m01 -# mkdir mon_groups/m02 - -# echo 3478 > /sys/fs/resctrl/mon_groups/m01/tasks -# echo 2467 > /sys/fs/resctrl/mon_groups/m02/tasks - -Monitor the groups separately and also get per domain data. From the -below its apparent that the tasks are mostly doing work on -domain(socket) 0. - -# cat /sys/fs/resctrl/mon_groups/m01/mon_L3_00/llc_occupancy -31234000 -# cat /sys/fs/resctrl/mon_groups/m01/mon_L3_01/llc_occupancy -34555 -# cat /sys/fs/resctrl/mon_groups/m02/mon_L3_00/llc_occupancy -31234000 -# cat /sys/fs/resctrl/mon_groups/m02/mon_L3_01/llc_occupancy -32789 - - -Example 4 (Monitor real time tasks) ------------------------------------ - -A single socket system which has real time tasks running on cores 4-7 -and non real time tasks on other cpus. We want to monitor the cache -occupancy of the real time threads on these cores. - -# mount -t resctrl resctrl /sys/fs/resctrl -# cd /sys/fs/resctrl -# mkdir p1 - -Move the cpus 4-7 over to p1 -# echo f0 > p1/cpus - -View the llc occupancy snapshot - -# cat /sys/fs/resctrl/p1/mon_data/mon_L3_00/llc_occupancy -11234000 -- cgit v1.2.3 From 9d12f58fe91e5e72ef08afe9e3e66d1c755fc085 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:32 +0800 Subject: Documentation: x86: convert orc-unwinder.txt to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/index.rst | 1 + Documentation/x86/orc-unwinder.rst | 182 +++++++++++++++++++++++++++++++++++++ Documentation/x86/orc-unwinder.txt | 179 ------------------------------------ 3 files changed, 183 insertions(+), 179 deletions(-) create mode 100644 Documentation/x86/orc-unwinder.rst delete mode 100644 Documentation/x86/orc-unwinder.txt (limited to 'Documentation') diff --git a/Documentation/x86/index.rst b/Documentation/x86/index.rst index 6e3c887a0c3b..453557097743 100644 --- a/Documentation/x86/index.rst +++ b/Documentation/x86/index.rst @@ -14,6 +14,7 @@ x86-specific Documentation kernel-stacks entry_64 earlyprintk + orc-unwinder zero-page tlb mtrr diff --git a/Documentation/x86/orc-unwinder.rst b/Documentation/x86/orc-unwinder.rst new file mode 100644 index 000000000000..d811576c1f3e --- /dev/null +++ b/Documentation/x86/orc-unwinder.rst @@ -0,0 +1,182 @@ +.. SPDX-License-Identifier: GPL-2.0 + +============ +ORC unwinder +============ + +Overview +======== + +The kernel CONFIG_UNWINDER_ORC option enables the ORC unwinder, which is +similar in concept to a DWARF unwinder. The difference is that the +format of the ORC data is much simpler than DWARF, which in turn allows +the ORC unwinder to be much simpler and faster. + +The ORC data consists of unwind tables which are generated by objtool. +They contain out-of-band data which is used by the in-kernel ORC +unwinder. Objtool generates the ORC data by first doing compile-time +stack metadata validation (CONFIG_STACK_VALIDATION). After analyzing +all the code paths of a .o file, it determines information about the +stack state at each instruction address in the file and outputs that +information to the .orc_unwind and .orc_unwind_ip sections. + +The per-object ORC sections are combined at link time and are sorted and +post-processed at boot time. The unwinder uses the resulting data to +correlate instruction addresses with their stack states at run time. + + +ORC vs frame pointers +===================== + +With frame pointers enabled, GCC adds instrumentation code to every +function in the kernel. The kernel's .text size increases by about +3.2%, resulting in a broad kernel-wide slowdown. Measurements by Mel +Gorman [1]_ have shown a slowdown of 5-10% for some workloads. + +In contrast, the ORC unwinder has no effect on text size or runtime +performance, because the debuginfo is out of band. So if you disable +frame pointers and enable the ORC unwinder, you get a nice performance +improvement across the board, and still have reliable stack traces. + +Ingo Molnar says: + + "Note that it's not just a performance improvement, but also an + instruction cache locality improvement: 3.2% .text savings almost + directly transform into a similarly sized reduction in cache + footprint. That can transform to even higher speedups for workloads + whose cache locality is borderline." + +Another benefit of ORC compared to frame pointers is that it can +reliably unwind across interrupts and exceptions. Frame pointer based +unwinds can sometimes skip the caller of the interrupted function, if it +was a leaf function or if the interrupt hit before the frame pointer was +saved. + +The main disadvantage of the ORC unwinder compared to frame pointers is +that it needs more memory to store the ORC unwind tables: roughly 2-4MB +depending on the kernel config. + + +ORC vs DWARF +============ + +ORC debuginfo's advantage over DWARF itself is that it's much simpler. +It gets rid of the complex DWARF CFI state machine and also gets rid of +the tracking of unnecessary registers. This allows the unwinder to be +much simpler, meaning fewer bugs, which is especially important for +mission critical oops code. + +The simpler debuginfo format also enables the unwinder to be much faster +than DWARF, which is important for perf and lockdep. In a basic +performance test by Jiri Slaby [2]_, the ORC unwinder was about 20x +faster than an out-of-tree DWARF unwinder. (Note: That measurement was +taken before some performance tweaks were added, which doubled +performance, so the speedup over DWARF may be closer to 40x.) + +The ORC data format does have a few downsides compared to DWARF. ORC +unwind tables take up ~50% more RAM (+1.3MB on an x86 defconfig kernel) +than DWARF-based eh_frame tables. + +Another potential downside is that, as GCC evolves, it's conceivable +that the ORC data may end up being *too* simple to describe the state of +the stack for certain optimizations. But IMO this is unlikely because +GCC saves the frame pointer for any unusual stack adjustments it does, +so I suspect we'll really only ever need to keep track of the stack +pointer and the frame pointer between call frames. But even if we do +end up having to track all the registers DWARF tracks, at least we will +still be able to control the format, e.g. no complex state machines. + + +ORC unwind table generation +=========================== + +The ORC data is generated by objtool. With the existing compile-time +stack metadata validation feature, objtool already follows all code +paths, and so it already has all the information it needs to be able to +generate ORC data from scratch. So it's an easy step to go from stack +validation to ORC data generation. + +It should be possible to instead generate the ORC data with a simple +tool which converts DWARF to ORC data. However, such a solution would +be incomplete due to the kernel's extensive use of asm, inline asm, and +special sections like exception tables. + +That could be rectified by manually annotating those special code paths +using GNU assembler .cfi annotations in .S files, and homegrown +annotations for inline asm in .c files. But asm annotations were tried +in the past and were found to be unmaintainable. They were often +incorrect/incomplete and made the code harder to read and keep updated. +And based on looking at glibc code, annotating inline asm in .c files +might be even worse. + +Objtool still needs a few annotations, but only in code which does +unusual things to the stack like entry code. And even then, far fewer +annotations are needed than what DWARF would need, so they're much more +maintainable than DWARF CFI annotations. + +So the advantages of using objtool to generate ORC data are that it +gives more accurate debuginfo, with very few annotations. It also +insulates the kernel from toolchain bugs which can be very painful to +deal with in the kernel since we often have to workaround issues in +older versions of the toolchain for years. + +The downside is that the unwinder now becomes dependent on objtool's +ability to reverse engineer GCC code flow. If GCC optimizations become +too complicated for objtool to follow, the ORC data generation might +stop working or become incomplete. (It's worth noting that livepatch +already has such a dependency on objtool's ability to follow GCC code +flow.) + +If newer versions of GCC come up with some optimizations which break +objtool, we may need to revisit the current implementation. Some +possible solutions would be asking GCC to make the optimizations more +palatable, or having objtool use DWARF as an additional input, or +creating a GCC plugin to assist objtool with its analysis. But for now, +objtool follows GCC code quite well. + + +Unwinder implementation details +=============================== + +Objtool generates the ORC data by integrating with the compile-time +stack metadata validation feature, which is described in detail in +tools/objtool/Documentation/stack-validation.txt. After analyzing all +the code paths of a .o file, it creates an array of orc_entry structs, +and a parallel array of instruction addresses associated with those +structs, and writes them to the .orc_unwind and .orc_unwind_ip sections +respectively. + +The ORC data is split into the two arrays for performance reasons, to +make the searchable part of the data (.orc_unwind_ip) more compact. The +arrays are sorted in parallel at boot time. + +Performance is further improved by the use of a fast lookup table which +is created at runtime. The fast lookup table associates a given address +with a range of indices for the .orc_unwind table, so that only a small +subset of the table needs to be searched. + + +Etymology +========= + +Orcs, fearsome creatures of medieval folklore, are the Dwarves' natural +enemies. Similarly, the ORC unwinder was created in opposition to the +complexity and slowness of DWARF. + +"Although Orcs rarely consider multiple solutions to a problem, they do +excel at getting things done because they are creatures of action, not +thought." [3]_ Similarly, unlike the esoteric DWARF unwinder, the +veracious ORC unwinder wastes no time or siloconic effort decoding +variable-length zero-extended unsigned-integer byte-coded +state-machine-based debug information entries. + +Similar to how Orcs frequently unravel the well-intentioned plans of +their adversaries, the ORC unwinder frequently unravels stacks with +brutal, unyielding efficiency. + +ORC stands for Oops Rewind Capability. + + +.. [1] https://lkml.kernel.org/r/20170602104048.jkkzssljsompjdwy@suse.de +.. [2] https://lkml.kernel.org/r/d2ca5435-6386-29b8-db87-7f227c2b713a@suse.cz +.. [3] http://dustin.wikidot.com/half-orcs-and-orcs diff --git a/Documentation/x86/orc-unwinder.txt b/Documentation/x86/orc-unwinder.txt deleted file mode 100644 index cd4b29be29af..000000000000 --- a/Documentation/x86/orc-unwinder.txt +++ /dev/null @@ -1,179 +0,0 @@ -ORC unwinder -============ - -Overview --------- - -The kernel CONFIG_UNWINDER_ORC option enables the ORC unwinder, which is -similar in concept to a DWARF unwinder. The difference is that the -format of the ORC data is much simpler than DWARF, which in turn allows -the ORC unwinder to be much simpler and faster. - -The ORC data consists of unwind tables which are generated by objtool. -They contain out-of-band data which is used by the in-kernel ORC -unwinder. Objtool generates the ORC data by first doing compile-time -stack metadata validation (CONFIG_STACK_VALIDATION). After analyzing -all the code paths of a .o file, it determines information about the -stack state at each instruction address in the file and outputs that -information to the .orc_unwind and .orc_unwind_ip sections. - -The per-object ORC sections are combined at link time and are sorted and -post-processed at boot time. The unwinder uses the resulting data to -correlate instruction addresses with their stack states at run time. - - -ORC vs frame pointers ---------------------- - -With frame pointers enabled, GCC adds instrumentation code to every -function in the kernel. The kernel's .text size increases by about -3.2%, resulting in a broad kernel-wide slowdown. Measurements by Mel -Gorman [1] have shown a slowdown of 5-10% for some workloads. - -In contrast, the ORC unwinder has no effect on text size or runtime -performance, because the debuginfo is out of band. So if you disable -frame pointers and enable the ORC unwinder, you get a nice performance -improvement across the board, and still have reliable stack traces. - -Ingo Molnar says: - - "Note that it's not just a performance improvement, but also an - instruction cache locality improvement: 3.2% .text savings almost - directly transform into a similarly sized reduction in cache - footprint. That can transform to even higher speedups for workloads - whose cache locality is borderline." - -Another benefit of ORC compared to frame pointers is that it can -reliably unwind across interrupts and exceptions. Frame pointer based -unwinds can sometimes skip the caller of the interrupted function, if it -was a leaf function or if the interrupt hit before the frame pointer was -saved. - -The main disadvantage of the ORC unwinder compared to frame pointers is -that it needs more memory to store the ORC unwind tables: roughly 2-4MB -depending on the kernel config. - - -ORC vs DWARF ------------- - -ORC debuginfo's advantage over DWARF itself is that it's much simpler. -It gets rid of the complex DWARF CFI state machine and also gets rid of -the tracking of unnecessary registers. This allows the unwinder to be -much simpler, meaning fewer bugs, which is especially important for -mission critical oops code. - -The simpler debuginfo format also enables the unwinder to be much faster -than DWARF, which is important for perf and lockdep. In a basic -performance test by Jiri Slaby [2], the ORC unwinder was about 20x -faster than an out-of-tree DWARF unwinder. (Note: That measurement was -taken before some performance tweaks were added, which doubled -performance, so the speedup over DWARF may be closer to 40x.) - -The ORC data format does have a few downsides compared to DWARF. ORC -unwind tables take up ~50% more RAM (+1.3MB on an x86 defconfig kernel) -than DWARF-based eh_frame tables. - -Another potential downside is that, as GCC evolves, it's conceivable -that the ORC data may end up being *too* simple to describe the state of -the stack for certain optimizations. But IMO this is unlikely because -GCC saves the frame pointer for any unusual stack adjustments it does, -so I suspect we'll really only ever need to keep track of the stack -pointer and the frame pointer between call frames. But even if we do -end up having to track all the registers DWARF tracks, at least we will -still be able to control the format, e.g. no complex state machines. - - -ORC unwind table generation ---------------------------- - -The ORC data is generated by objtool. With the existing compile-time -stack metadata validation feature, objtool already follows all code -paths, and so it already has all the information it needs to be able to -generate ORC data from scratch. So it's an easy step to go from stack -validation to ORC data generation. - -It should be possible to instead generate the ORC data with a simple -tool which converts DWARF to ORC data. However, such a solution would -be incomplete due to the kernel's extensive use of asm, inline asm, and -special sections like exception tables. - -That could be rectified by manually annotating those special code paths -using GNU assembler .cfi annotations in .S files, and homegrown -annotations for inline asm in .c files. But asm annotations were tried -in the past and were found to be unmaintainable. They were often -incorrect/incomplete and made the code harder to read and keep updated. -And based on looking at glibc code, annotating inline asm in .c files -might be even worse. - -Objtool still needs a few annotations, but only in code which does -unusual things to the stack like entry code. And even then, far fewer -annotations are needed than what DWARF would need, so they're much more -maintainable than DWARF CFI annotations. - -So the advantages of using objtool to generate ORC data are that it -gives more accurate debuginfo, with very few annotations. It also -insulates the kernel from toolchain bugs which can be very painful to -deal with in the kernel since we often have to workaround issues in -older versions of the toolchain for years. - -The downside is that the unwinder now becomes dependent on objtool's -ability to reverse engineer GCC code flow. If GCC optimizations become -too complicated for objtool to follow, the ORC data generation might -stop working or become incomplete. (It's worth noting that livepatch -already has such a dependency on objtool's ability to follow GCC code -flow.) - -If newer versions of GCC come up with some optimizations which break -objtool, we may need to revisit the current implementation. Some -possible solutions would be asking GCC to make the optimizations more -palatable, or having objtool use DWARF as an additional input, or -creating a GCC plugin to assist objtool with its analysis. But for now, -objtool follows GCC code quite well. - - -Unwinder implementation details -------------------------------- - -Objtool generates the ORC data by integrating with the compile-time -stack metadata validation feature, which is described in detail in -tools/objtool/Documentation/stack-validation.txt. After analyzing all -the code paths of a .o file, it creates an array of orc_entry structs, -and a parallel array of instruction addresses associated with those -structs, and writes them to the .orc_unwind and .orc_unwind_ip sections -respectively. - -The ORC data is split into the two arrays for performance reasons, to -make the searchable part of the data (.orc_unwind_ip) more compact. The -arrays are sorted in parallel at boot time. - -Performance is further improved by the use of a fast lookup table which -is created at runtime. The fast lookup table associates a given address -with a range of indices for the .orc_unwind table, so that only a small -subset of the table needs to be searched. - - -Etymology ---------- - -Orcs, fearsome creatures of medieval folklore, are the Dwarves' natural -enemies. Similarly, the ORC unwinder was created in opposition to the -complexity and slowness of DWARF. - -"Although Orcs rarely consider multiple solutions to a problem, they do -excel at getting things done because they are creatures of action, not -thought." [3] Similarly, unlike the esoteric DWARF unwinder, the -veracious ORC unwinder wastes no time or siloconic effort decoding -variable-length zero-extended unsigned-integer byte-coded -state-machine-based debug information entries. - -Similar to how Orcs frequently unravel the well-intentioned plans of -their adversaries, the ORC unwinder frequently unravels stacks with -brutal, unyielding efficiency. - -ORC stands for Oops Rewind Capability. - - -[1] https://lkml.kernel.org/r/20170602104048.jkkzssljsompjdwy@suse.de -[2] https://lkml.kernel.org/r/d2ca5435-6386-29b8-db87-7f227c2b713a@suse.cz -[3] http://dustin.wikidot.com/half-orcs-and-orcs -- cgit v1.2.3 From 71892b25fc49999071472f6bce589c18468a85a8 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:33 +0800 Subject: Documentation: x86: convert usb-legacy-support.txt to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/index.rst | 1 + Documentation/x86/usb-legacy-support.rst | 50 ++++++++++++++++++++++++++++++++ Documentation/x86/usb-legacy-support.txt | 44 ---------------------------- 3 files changed, 51 insertions(+), 44 deletions(-) create mode 100644 Documentation/x86/usb-legacy-support.rst delete mode 100644 Documentation/x86/usb-legacy-support.txt (limited to 'Documentation') diff --git a/Documentation/x86/index.rst b/Documentation/x86/index.rst index 453557097743..3eb0334ae2d4 100644 --- a/Documentation/x86/index.rst +++ b/Documentation/x86/index.rst @@ -25,3 +25,4 @@ x86-specific Documentation pti microcode resctrl_ui + usb-legacy-support diff --git a/Documentation/x86/usb-legacy-support.rst b/Documentation/x86/usb-legacy-support.rst new file mode 100644 index 000000000000..e01c08b7c981 --- /dev/null +++ b/Documentation/x86/usb-legacy-support.rst @@ -0,0 +1,50 @@ + +.. SPDX-License-Identifier: GPL-2.0 + +================== +USB Legacy support +================== + +:Author: Vojtech Pavlik , January 2004 + + +Also known as "USB Keyboard" or "USB Mouse support" in the BIOS Setup is a +feature that allows one to use the USB mouse and keyboard as if they were +their classic PS/2 counterparts. This means one can use an USB keyboard to +type in LILO for example. + +It has several drawbacks, though: + +1) On some machines, the emulated PS/2 mouse takes over even when no USB + mouse is present and a real PS/2 mouse is present. In that case the extra + features (wheel, extra buttons, touchpad mode) of the real PS/2 mouse may + not be available. + +2) If CONFIG_HIGHMEM64G is enabled, the PS/2 mouse emulation can cause + system crashes, because the SMM BIOS is not expecting to be in PAE mode. + The Intel E7505 is a typical machine where this happens. + +3) If AMD64 64-bit mode is enabled, again system crashes often happen, + because the SMM BIOS isn't expecting the CPU to be in 64-bit mode. The + BIOS manufacturers only test with Windows, and Windows doesn't do 64-bit + yet. + +Solutions: + +Problem 1) + can be solved by loading the USB drivers prior to loading the + PS/2 mouse driver. Since the PS/2 mouse driver is in 2.6 compiled into + the kernel unconditionally, this means the USB drivers need to be + compiled-in, too. + +Problem 2) + can currently only be solved by either disabling HIGHMEM64G + in the kernel config or USB Legacy support in the BIOS. A BIOS update + could help, but so far no such update exists. + +Problem 3) + is usually fixed by a BIOS update. Check the board + manufacturers web site. If an update is not available, disable USB + Legacy support in the BIOS. If this alone doesn't help, try also adding + idle=poll on the kernel command line. The BIOS may be entering the SMM + on the HLT instruction as well. diff --git a/Documentation/x86/usb-legacy-support.txt b/Documentation/x86/usb-legacy-support.txt deleted file mode 100644 index 1894cdfc69d9..000000000000 --- a/Documentation/x86/usb-legacy-support.txt +++ /dev/null @@ -1,44 +0,0 @@ -USB Legacy support -~~~~~~~~~~~~~~~~~~ - -Vojtech Pavlik , January 2004 - - -Also known as "USB Keyboard" or "USB Mouse support" in the BIOS Setup is a -feature that allows one to use the USB mouse and keyboard as if they were -their classic PS/2 counterparts. This means one can use an USB keyboard to -type in LILO for example. - -It has several drawbacks, though: - -1) On some machines, the emulated PS/2 mouse takes over even when no USB - mouse is present and a real PS/2 mouse is present. In that case the extra - features (wheel, extra buttons, touchpad mode) of the real PS/2 mouse may - not be available. - -2) If CONFIG_HIGHMEM64G is enabled, the PS/2 mouse emulation can cause - system crashes, because the SMM BIOS is not expecting to be in PAE mode. - The Intel E7505 is a typical machine where this happens. - -3) If AMD64 64-bit mode is enabled, again system crashes often happen, - because the SMM BIOS isn't expecting the CPU to be in 64-bit mode. The - BIOS manufacturers only test with Windows, and Windows doesn't do 64-bit - yet. - -Solutions: - -Problem 1) can be solved by loading the USB drivers prior to loading the -PS/2 mouse driver. Since the PS/2 mouse driver is in 2.6 compiled into -the kernel unconditionally, this means the USB drivers need to be -compiled-in, too. - -Problem 2) can currently only be solved by either disabling HIGHMEM64G -in the kernel config or USB Legacy support in the BIOS. A BIOS update -could help, but so far no such update exists. - -Problem 3) is usually fixed by a BIOS update. Check the board -manufacturers web site. If an update is not available, disable USB -Legacy support in the BIOS. If this alone doesn't help, try also adding -idle=poll on the kernel command line. The BIOS may be entering the SMM -on the HLT instruction as well. - -- cgit v1.2.3 From 8fffdc9353d64f7ceef5c4589249759561aa1b39 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:34 +0800 Subject: Documentation: x86: convert i386/IO-APIC.txt to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/i386/IO-APIC.rst | 123 +++++++++++++++++++++++++++++++++++++ Documentation/x86/i386/IO-APIC.txt | 119 ----------------------------------- Documentation/x86/i386/index.rst | 10 +++ Documentation/x86/index.rst | 1 + 4 files changed, 134 insertions(+), 119 deletions(-) create mode 100644 Documentation/x86/i386/IO-APIC.rst delete mode 100644 Documentation/x86/i386/IO-APIC.txt create mode 100644 Documentation/x86/i386/index.rst (limited to 'Documentation') diff --git a/Documentation/x86/i386/IO-APIC.rst b/Documentation/x86/i386/IO-APIC.rst new file mode 100644 index 000000000000..ce4d8df15e7c --- /dev/null +++ b/Documentation/x86/i386/IO-APIC.rst @@ -0,0 +1,123 @@ +.. SPDX-License-Identifier: GPL-2.0 + +======= +IO-APIC +======= + +:Author: Ingo Molnar + +Most (all) Intel-MP compliant SMP boards have the so-called 'IO-APIC', +which is an enhanced interrupt controller. It enables us to route +hardware interrupts to multiple CPUs, or to CPU groups. Without an +IO-APIC, interrupts from hardware will be delivered only to the +CPU which boots the operating system (usually CPU#0). + +Linux supports all variants of compliant SMP boards, including ones with +multiple IO-APICs. Multiple IO-APICs are used in high-end servers to +distribute IRQ load further. + +There are (a few) known breakages in certain older boards, such bugs are +usually worked around by the kernel. If your MP-compliant SMP board does +not boot Linux, then consult the linux-smp mailing list archives first. + +If your box boots fine with enabled IO-APIC IRQs, then your +/proc/interrupts will look like this one:: + + hell:~> cat /proc/interrupts + CPU0 + 0: 1360293 IO-APIC-edge timer + 1: 4 IO-APIC-edge keyboard + 2: 0 XT-PIC cascade + 13: 1 XT-PIC fpu + 14: 1448 IO-APIC-edge ide0 + 16: 28232 IO-APIC-level Intel EtherExpress Pro 10/100 Ethernet + 17: 51304 IO-APIC-level eth0 + NMI: 0 + ERR: 0 + hell:~> + +Some interrupts are still listed as 'XT PIC', but this is not a problem; +none of those IRQ sources is performance-critical. + + +In the unlikely case that your board does not create a working mp-table, +you can use the pirq= boot parameter to 'hand-construct' IRQ entries. This +is non-trivial though and cannot be automated. One sample /etc/lilo.conf +entry:: + + append="pirq=15,11,10" + +The actual numbers depend on your system, on your PCI cards and on their +PCI slot position. Usually PCI slots are 'daisy chained' before they are +connected to the PCI chipset IRQ routing facility (the incoming PIRQ1-4 +lines):: + + ,-. ,-. ,-. ,-. ,-. + PIRQ4 ----| |-. ,-| |-. ,-| |-. ,-| |--------| | + |S| \ / |S| \ / |S| \ / |S| |S| + PIRQ3 ----|l|-. `/---|l|-. `/---|l|-. `/---|l|--------|l| + |o| \/ |o| \/ |o| \/ |o| |o| + PIRQ2 ----|t|-./`----|t|-./`----|t|-./`----|t|--------|t| + |1| /\ |2| /\ |3| /\ |4| |5| + PIRQ1 ----| |- `----| |- `----| |- `----| |--------| | + `-' `-' `-' `-' `-' + +Every PCI card emits a PCI IRQ, which can be INTA, INTB, INTC or INTD:: + + ,-. + INTD--| | + |S| + INTC--|l| + |o| + INTB--|t| + |x| + INTA--| | + `-' + +These INTA-D PCI IRQs are always 'local to the card', their real meaning +depends on which slot they are in. If you look at the daisy chaining diagram, +a card in slot4, issuing INTA IRQ, it will end up as a signal on PIRQ4 of +the PCI chipset. Most cards issue INTA, this creates optimal distribution +between the PIRQ lines. (distributing IRQ sources properly is not a +necessity, PCI IRQs can be shared at will, but it's a good for performance +to have non shared interrupts). Slot5 should be used for videocards, they +do not use interrupts normally, thus they are not daisy chained either. + +so if you have your SCSI card (IRQ11) in Slot1, Tulip card (IRQ9) in +Slot2, then you'll have to specify this pirq= line:: + + append="pirq=11,9" + +the following script tries to figure out such a default pirq= line from +your PCI configuration:: + + echo -n pirq=; echo `scanpci | grep T_L | cut -c56-` | sed 's/ /,/g' + +note that this script won't work if you have skipped a few slots or if your +board does not do default daisy-chaining. (or the IO-APIC has the PIRQ pins +connected in some strange way). E.g. if in the above case you have your SCSI +card (IRQ11) in Slot3, and have Slot1 empty:: + + append="pirq=0,9,11" + +[value '0' is a generic 'placeholder', reserved for empty (or non-IRQ emitting) +slots.] + +Generally, it's always possible to find out the correct pirq= settings, just +permute all IRQ numbers properly ... it will take some time though. An +'incorrect' pirq line will cause the booting process to hang, or a device +won't function properly (e.g. if it's inserted as a module). + +If you have 2 PCI buses, then you can use up to 8 pirq values, although such +boards tend to have a good configuration. + +Be prepared that it might happen that you need some strange pirq line:: + + append="pirq=0,0,0,0,0,0,9,11" + +Use smart trial-and-error techniques to find out the correct pirq line ... + +Good luck and mail to linux-smp@vger.kernel.org or +linux-kernel@vger.kernel.org if you have any problems that are not covered +by this document. + diff --git a/Documentation/x86/i386/IO-APIC.txt b/Documentation/x86/i386/IO-APIC.txt deleted file mode 100644 index 15f5baf7e1b6..000000000000 --- a/Documentation/x86/i386/IO-APIC.txt +++ /dev/null @@ -1,119 +0,0 @@ -Most (all) Intel-MP compliant SMP boards have the so-called 'IO-APIC', -which is an enhanced interrupt controller. It enables us to route -hardware interrupts to multiple CPUs, or to CPU groups. Without an -IO-APIC, interrupts from hardware will be delivered only to the -CPU which boots the operating system (usually CPU#0). - -Linux supports all variants of compliant SMP boards, including ones with -multiple IO-APICs. Multiple IO-APICs are used in high-end servers to -distribute IRQ load further. - -There are (a few) known breakages in certain older boards, such bugs are -usually worked around by the kernel. If your MP-compliant SMP board does -not boot Linux, then consult the linux-smp mailing list archives first. - -If your box boots fine with enabled IO-APIC IRQs, then your -/proc/interrupts will look like this one: - - ----------------------------> - hell:~> cat /proc/interrupts - CPU0 - 0: 1360293 IO-APIC-edge timer - 1: 4 IO-APIC-edge keyboard - 2: 0 XT-PIC cascade - 13: 1 XT-PIC fpu - 14: 1448 IO-APIC-edge ide0 - 16: 28232 IO-APIC-level Intel EtherExpress Pro 10/100 Ethernet - 17: 51304 IO-APIC-level eth0 - NMI: 0 - ERR: 0 - hell:~> - <---------------------------- - -Some interrupts are still listed as 'XT PIC', but this is not a problem; -none of those IRQ sources is performance-critical. - - -In the unlikely case that your board does not create a working mp-table, -you can use the pirq= boot parameter to 'hand-construct' IRQ entries. This -is non-trivial though and cannot be automated. One sample /etc/lilo.conf -entry: - - append="pirq=15,11,10" - -The actual numbers depend on your system, on your PCI cards and on their -PCI slot position. Usually PCI slots are 'daisy chained' before they are -connected to the PCI chipset IRQ routing facility (the incoming PIRQ1-4 -lines): - - ,-. ,-. ,-. ,-. ,-. - PIRQ4 ----| |-. ,-| |-. ,-| |-. ,-| |--------| | - |S| \ / |S| \ / |S| \ / |S| |S| - PIRQ3 ----|l|-. `/---|l|-. `/---|l|-. `/---|l|--------|l| - |o| \/ |o| \/ |o| \/ |o| |o| - PIRQ2 ----|t|-./`----|t|-./`----|t|-./`----|t|--------|t| - |1| /\ |2| /\ |3| /\ |4| |5| - PIRQ1 ----| |- `----| |- `----| |- `----| |--------| | - `-' `-' `-' `-' `-' - -Every PCI card emits a PCI IRQ, which can be INTA, INTB, INTC or INTD: - - ,-. - INTD--| | - |S| - INTC--|l| - |o| - INTB--|t| - |x| - INTA--| | - `-' - -These INTA-D PCI IRQs are always 'local to the card', their real meaning -depends on which slot they are in. If you look at the daisy chaining diagram, -a card in slot4, issuing INTA IRQ, it will end up as a signal on PIRQ4 of -the PCI chipset. Most cards issue INTA, this creates optimal distribution -between the PIRQ lines. (distributing IRQ sources properly is not a -necessity, PCI IRQs can be shared at will, but it's a good for performance -to have non shared interrupts). Slot5 should be used for videocards, they -do not use interrupts normally, thus they are not daisy chained either. - -so if you have your SCSI card (IRQ11) in Slot1, Tulip card (IRQ9) in -Slot2, then you'll have to specify this pirq= line: - - append="pirq=11,9" - -the following script tries to figure out such a default pirq= line from -your PCI configuration: - - echo -n pirq=; echo `scanpci | grep T_L | cut -c56-` | sed 's/ /,/g' - -note that this script won't work if you have skipped a few slots or if your -board does not do default daisy-chaining. (or the IO-APIC has the PIRQ pins -connected in some strange way). E.g. if in the above case you have your SCSI -card (IRQ11) in Slot3, and have Slot1 empty: - - append="pirq=0,9,11" - -[value '0' is a generic 'placeholder', reserved for empty (or non-IRQ emitting) -slots.] - -Generally, it's always possible to find out the correct pirq= settings, just -permute all IRQ numbers properly ... it will take some time though. An -'incorrect' pirq line will cause the booting process to hang, or a device -won't function properly (e.g. if it's inserted as a module). - -If you have 2 PCI buses, then you can use up to 8 pirq values, although such -boards tend to have a good configuration. - -Be prepared that it might happen that you need some strange pirq line: - - append="pirq=0,0,0,0,0,0,9,11" - -Use smart trial-and-error techniques to find out the correct pirq line ... - -Good luck and mail to linux-smp@vger.kernel.org or -linux-kernel@vger.kernel.org if you have any problems that are not covered -by this document. - --- mingo - diff --git a/Documentation/x86/i386/index.rst b/Documentation/x86/i386/index.rst new file mode 100644 index 000000000000..8747cf5bbd49 --- /dev/null +++ b/Documentation/x86/i386/index.rst @@ -0,0 +1,10 @@ +.. SPDX-License-Identifier: GPL-2.0 + +============ +i386 Support +============ + +.. toctree:: + :maxdepth: 2 + + IO-APIC diff --git a/Documentation/x86/index.rst b/Documentation/x86/index.rst index 3eb0334ae2d4..4e15bcc6456c 100644 --- a/Documentation/x86/index.rst +++ b/Documentation/x86/index.rst @@ -26,3 +26,4 @@ x86-specific Documentation microcode resctrl_ui usb-legacy-support + i386/index -- cgit v1.2.3 From bbea90bbb6c849b62b80ec4a83d10e64dd901bd9 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:35 +0800 Subject: Documentation: x86: convert x86_64/boot-options.txt to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/index.rst | 1 + Documentation/x86/x86_64/boot-options.rst | 335 ++++++++++++++++++++++++++++++ Documentation/x86/x86_64/boot-options.txt | 278 ------------------------- Documentation/x86/x86_64/index.rst | 10 + 4 files changed, 346 insertions(+), 278 deletions(-) create mode 100644 Documentation/x86/x86_64/boot-options.rst delete mode 100644 Documentation/x86/x86_64/boot-options.txt create mode 100644 Documentation/x86/x86_64/index.rst (limited to 'Documentation') diff --git a/Documentation/x86/index.rst b/Documentation/x86/index.rst index 4e15bcc6456c..73a487957fd4 100644 --- a/Documentation/x86/index.rst +++ b/Documentation/x86/index.rst @@ -27,3 +27,4 @@ x86-specific Documentation resctrl_ui usb-legacy-support i386/index + x86_64/index diff --git a/Documentation/x86/x86_64/boot-options.rst b/Documentation/x86/x86_64/boot-options.rst new file mode 100644 index 000000000000..2f69836b8445 --- /dev/null +++ b/Documentation/x86/x86_64/boot-options.rst @@ -0,0 +1,335 @@ +.. SPDX-License-Identifier: GPL-2.0 + +=========================== +AMD64 Specific Boot Options +=========================== + +There are many others (usually documented in driver documentation), but +only the AMD64 specific ones are listed here. + +Machine check +============= +Please see Documentation/x86/x86_64/machinecheck for sysfs runtime tunables. + + mce=off + Disable machine check + mce=no_cmci + Disable CMCI(Corrected Machine Check Interrupt) that + Intel processor supports. Usually this disablement is + not recommended, but it might be handy if your hardware + is misbehaving. + Note that you'll get more problems without CMCI than with + due to the shared banks, i.e. you might get duplicated + error logs. + mce=dont_log_ce + Don't make logs for corrected errors. All events reported + as corrected are silently cleared by OS. + This option will be useful if you have no interest in any + of corrected errors. + mce=ignore_ce + Disable features for corrected errors, e.g. polling timer + and CMCI. All events reported as corrected are not cleared + by OS and remained in its error banks. + Usually this disablement is not recommended, however if + there is an agent checking/clearing corrected errors + (e.g. BIOS or hardware monitoring applications), conflicting + with OS's error handling, and you cannot deactivate the agent, + then this option will be a help. + mce=no_lmce + Do not opt-in to Local MCE delivery. Use legacy method + to broadcast MCEs. + mce=bootlog + Enable logging of machine checks left over from booting. + Disabled by default on AMD Fam10h and older because some BIOS + leave bogus ones. + If your BIOS doesn't do that it's a good idea to enable though + to make sure you log even machine check events that result + in a reboot. On Intel systems it is enabled by default. + mce=nobootlog + Disable boot machine check logging. + mce=tolerancelevel[,monarchtimeout] (number,number) + tolerance levels: + 0: always panic on uncorrected errors, log corrected errors + 1: panic or SIGBUS on uncorrected errors, log corrected errors + 2: SIGBUS or log uncorrected errors, log corrected errors + 3: never panic or SIGBUS, log all errors (for testing only) + Default is 1 + Can be also set using sysfs which is preferable. + monarchtimeout: + Sets the time in us to wait for other CPUs on machine checks. 0 + to disable. + mce=bios_cmci_threshold + Don't overwrite the bios-set CMCI threshold. This boot option + prevents Linux from overwriting the CMCI threshold set by the + bios. Without this option, Linux always sets the CMCI + threshold to 1. Enabling this may make memory predictive failure + analysis less effective if the bios sets thresholds for memory + errors since we will not see details for all errors. + mce=recovery + Force-enable recoverable machine check code paths + + nomce (for compatibility with i386) + same as mce=off + + Everything else is in sysfs now. + +APICs +===== + + apic + Use IO-APIC. Default + + noapic + Don't use the IO-APIC. + + disableapic + Don't use the local APIC + + nolapic + Don't use the local APIC (alias for i386 compatibility) + + pirq=... + See Documentation/x86/i386/IO-APIC.txt + + noapictimer + Don't set up the APIC timer + + no_timer_check + Don't check the IO-APIC timer. This can work around + problems with incorrect timer initialization on some boards. + + apicpmtimer + Do APIC timer calibration using the pmtimer. Implies + apicmaintimer. Useful when your PIT timer is totally broken. + +Timing +====== + + notsc + Deprecated, use tsc=unstable instead. + + nohpet + Don't use the HPET timer. + +Idle loop +========= + + idle=poll + Don't do power saving in the idle loop using HLT, but poll for rescheduling + event. This will make the CPUs eat a lot more power, but may be useful + to get slightly better performance in multiprocessor benchmarks. It also + makes some profiling using performance counters more accurate. + Please note that on systems with MONITOR/MWAIT support (like Intel EM64T + CPUs) this option has no performance advantage over the normal idle loop. + It may also interact badly with hyperthreading. + +Rebooting +========= + + reboot=b[ios] | t[riple] | k[bd] | a[cpi] | e[fi] [, [w]arm | [c]old] + bios + Use the CPU reboot vector for warm reset + warm + Don't set the cold reboot flag + cold + Set the cold reboot flag + triple + Force a triple fault (init) + kbd + Use the keyboard controller. cold reset (default) + acpi + Use the ACPI RESET_REG in the FADT. If ACPI is not configured or + the ACPI reset does not work, the reboot path attempts the reset + using the keyboard controller. + efi + Use efi reset_system runtime service. If EFI is not configured or + the EFI reset does not work, the reboot path attempts the reset using + the keyboard controller. + + Using warm reset will be much faster especially on big memory + systems because the BIOS will not go through the memory check. + Disadvantage is that not all hardware will be completely reinitialized + on reboot so there may be boot problems on some systems. + + reboot=force + Don't stop other CPUs on reboot. This can make reboot more reliable + in some cases. + +Non Executable Mappings +======================= + + noexec=on|off + on + Enable(default) + off + Disable + +NUMA +==== + + numa=off + Only set up a single NUMA node spanning all memory. + + numa=noacpi + Don't parse the SRAT table for NUMA setup + + numa=fake=[MG] + If given as a memory unit, fills all system RAM with nodes of + size interleaved over physical nodes. + + numa=fake= + If given as an integer, fills all system RAM with N fake nodes + interleaved over physical nodes. + + numa=fake=U + If given as an integer followed by 'U', it will divide each + physical node into N emulated nodes. + +ACPI +==== + + acpi=off + Don't enable ACPI + acpi=ht + Use ACPI boot table parsing, but don't enable ACPI interpreter + acpi=force + Force ACPI on (currently not needed) + acpi=strict + Disable out of spec ACPI workarounds. + acpi_sci={edge,level,high,low} + Set up ACPI SCI interrupt. + acpi=noirq + Don't route interrupts + acpi=nocmcff + Disable firmware first mode for corrected errors. This + disables parsing the HEST CMC error source to check if + firmware has set the FF flag. This may result in + duplicate corrected error reports. + +PCI +=== + + pci=off + Don't use PCI + pci=conf1 + Use conf1 access. + pci=conf2 + Use conf2 access. + pci=rom + Assign ROMs. + pci=assign-busses + Assign busses + pci=irqmask=MASK + Set PCI interrupt mask to MASK + pci=lastbus=NUMBER + Scan up to NUMBER busses, no matter what the mptable says. + pci=noacpi + Don't use ACPI to set up PCI interrupt routing. + +IOMMU (input/output memory management unit) +=========================================== +Multiple x86-64 PCI-DMA mapping implementations exist, for example: + + 1. : use no hardware/software IOMMU at all + (e.g. because you have < 3 GB memory). + Kernel boot message: "PCI-DMA: Disabling IOMMU" + + 2. : AMD GART based hardware IOMMU. + Kernel boot message: "PCI-DMA: using GART IOMMU" + + 3. : Software IOMMU implementation. Used + e.g. if there is no hardware IOMMU in the system and it is need because + you have >3GB memory or told the kernel to us it (iommu=soft)) + Kernel boot message: "PCI-DMA: Using software bounce buffering + for IO (SWIOTLB)" + + 4. : IBM Calgary hardware IOMMU. Used in IBM + pSeries and xSeries servers. This hardware IOMMU supports DMA address + mapping with memory protection, etc. + Kernel boot message: "PCI-DMA: Using Calgary IOMMU" + +:: + + iommu=[][,noagp][,off][,force][,noforce] + [,memaper[=]][,merge][,fullflush][,nomerge] + [,noaperture][,calgary] + +General iommu options: + + off + Don't initialize and use any kind of IOMMU. + noforce + Don't force hardware IOMMU usage when it is not needed. (default). + force + Force the use of the hardware IOMMU even when it is + not actually needed (e.g. because < 3 GB memory). + soft + Use software bounce buffering (SWIOTLB) (default for + Intel machines). This can be used to prevent the usage + of an available hardware IOMMU. + +iommu options only relevant to the AMD GART hardware IOMMU: + + + Set the size of the remapping area in bytes. + allowed + Overwrite iommu off workarounds for specific chipsets. + fullflush + Flush IOMMU on each allocation (default). + nofullflush + Don't use IOMMU fullflush. + memaper[=] + Allocate an own aperture over RAM with size 32MB<[,force] + + Prereserve that many 128K pages for the software IO bounce buffering. + force + Force all IO through the software TLB. + +Settings for the IBM Calgary hardware IOMMU currently found in IBM +pSeries and xSeries machines + + calgary=[64k,128k,256k,512k,1M,2M,4M,8M] + Set the size of each PCI slot's translation table when using the + Calgary IOMMU. This is the size of the translation table itself + in main memory. The smallest table, 64k, covers an IO space of + 32MB; the largest, 8MB table, can cover an IO space of 4GB. + Normally the kernel will make the right choice by itself. + calgary=[translate_empty_slots] + Enable translation even on slots that have no devices attached to + them, in case a device will be hotplugged in the future. + calgary=[disable=] + Disable translation on a given PHB. For + example, the built-in graphics adapter resides on the first bridge + (PCI bus number 0); if translation (isolation) is enabled on this + bridge, X servers that access the hardware directly from user + space might stop working. Use this option if you have devices that + are accessed from userspace directly on some PCI host bridge. + panic + Always panic when IOMMU overflows + + +Miscellaneous +============= + + nogbpages + Do not use GB pages for kernel direct mappings. + gbpages + Use GB pages for kernel direct mappings. diff --git a/Documentation/x86/x86_64/boot-options.txt b/Documentation/x86/x86_64/boot-options.txt deleted file mode 100644 index abc53886655e..000000000000 --- a/Documentation/x86/x86_64/boot-options.txt +++ /dev/null @@ -1,278 +0,0 @@ -AMD64 specific boot options - -There are many others (usually documented in driver documentation), but -only the AMD64 specific ones are listed here. - -Machine check - - Please see Documentation/x86/x86_64/machinecheck for sysfs runtime tunables. - - mce=off - Disable machine check - mce=no_cmci - Disable CMCI(Corrected Machine Check Interrupt) that - Intel processor supports. Usually this disablement is - not recommended, but it might be handy if your hardware - is misbehaving. - Note that you'll get more problems without CMCI than with - due to the shared banks, i.e. you might get duplicated - error logs. - mce=dont_log_ce - Don't make logs for corrected errors. All events reported - as corrected are silently cleared by OS. - This option will be useful if you have no interest in any - of corrected errors. - mce=ignore_ce - Disable features for corrected errors, e.g. polling timer - and CMCI. All events reported as corrected are not cleared - by OS and remained in its error banks. - Usually this disablement is not recommended, however if - there is an agent checking/clearing corrected errors - (e.g. BIOS or hardware monitoring applications), conflicting - with OS's error handling, and you cannot deactivate the agent, - then this option will be a help. - mce=no_lmce - Do not opt-in to Local MCE delivery. Use legacy method - to broadcast MCEs. - mce=bootlog - Enable logging of machine checks left over from booting. - Disabled by default on AMD Fam10h and older because some BIOS - leave bogus ones. - If your BIOS doesn't do that it's a good idea to enable though - to make sure you log even machine check events that result - in a reboot. On Intel systems it is enabled by default. - mce=nobootlog - Disable boot machine check logging. - mce=tolerancelevel[,monarchtimeout] (number,number) - tolerance levels: - 0: always panic on uncorrected errors, log corrected errors - 1: panic or SIGBUS on uncorrected errors, log corrected errors - 2: SIGBUS or log uncorrected errors, log corrected errors - 3: never panic or SIGBUS, log all errors (for testing only) - Default is 1 - Can be also set using sysfs which is preferable. - monarchtimeout: - Sets the time in us to wait for other CPUs on machine checks. 0 - to disable. - mce=bios_cmci_threshold - Don't overwrite the bios-set CMCI threshold. This boot option - prevents Linux from overwriting the CMCI threshold set by the - bios. Without this option, Linux always sets the CMCI - threshold to 1. Enabling this may make memory predictive failure - analysis less effective if the bios sets thresholds for memory - errors since we will not see details for all errors. - mce=recovery - Force-enable recoverable machine check code paths - - nomce (for compatibility with i386): same as mce=off - - Everything else is in sysfs now. - -APICs - - apic Use IO-APIC. Default - - noapic Don't use the IO-APIC. - - disableapic Don't use the local APIC - - nolapic Don't use the local APIC (alias for i386 compatibility) - - pirq=... See Documentation/x86/i386/IO-APIC.txt - - noapictimer Don't set up the APIC timer - - no_timer_check Don't check the IO-APIC timer. This can work around - problems with incorrect timer initialization on some boards. - apicpmtimer - Do APIC timer calibration using the pmtimer. Implies - apicmaintimer. Useful when your PIT timer is totally - broken. - -Timing - - notsc - Deprecated, use tsc=unstable instead. - - nohpet - Don't use the HPET timer. - -Idle loop - - idle=poll - Don't do power saving in the idle loop using HLT, but poll for rescheduling - event. This will make the CPUs eat a lot more power, but may be useful - to get slightly better performance in multiprocessor benchmarks. It also - makes some profiling using performance counters more accurate. - Please note that on systems with MONITOR/MWAIT support (like Intel EM64T - CPUs) this option has no performance advantage over the normal idle loop. - It may also interact badly with hyperthreading. - -Rebooting - - reboot=b[ios] | t[riple] | k[bd] | a[cpi] | e[fi] [, [w]arm | [c]old] - bios Use the CPU reboot vector for warm reset - warm Don't set the cold reboot flag - cold Set the cold reboot flag - triple Force a triple fault (init) - kbd Use the keyboard controller. cold reset (default) - acpi Use the ACPI RESET_REG in the FADT. If ACPI is not configured or the - ACPI reset does not work, the reboot path attempts the reset using - the keyboard controller. - efi Use efi reset_system runtime service. If EFI is not configured or the - EFI reset does not work, the reboot path attempts the reset using - the keyboard controller. - - Using warm reset will be much faster especially on big memory - systems because the BIOS will not go through the memory check. - Disadvantage is that not all hardware will be completely reinitialized - on reboot so there may be boot problems on some systems. - - reboot=force - - Don't stop other CPUs on reboot. This can make reboot more reliable - in some cases. - -Non Executable Mappings - - noexec=on|off - - on Enable(default) - off Disable - -NUMA - - numa=off Only set up a single NUMA node spanning all memory. - - numa=noacpi Don't parse the SRAT table for NUMA setup - - numa=fake=[MG] - If given as a memory unit, fills all system RAM with nodes of - size interleaved over physical nodes. - - numa=fake= - If given as an integer, fills all system RAM with N fake nodes - interleaved over physical nodes. - - numa=fake=U - If given as an integer followed by 'U', it will divide each - physical node into N emulated nodes. - -ACPI - - acpi=off Don't enable ACPI - acpi=ht Use ACPI boot table parsing, but don't enable ACPI - interpreter - acpi=force Force ACPI on (currently not needed) - - acpi=strict Disable out of spec ACPI workarounds. - - acpi_sci={edge,level,high,low} Set up ACPI SCI interrupt. - - acpi=noirq Don't route interrupts - - acpi=nocmcff Disable firmware first mode for corrected errors. This - disables parsing the HEST CMC error source to check if - firmware has set the FF flag. This may result in - duplicate corrected error reports. - -PCI - - pci=off Don't use PCI - pci=conf1 Use conf1 access. - pci=conf2 Use conf2 access. - pci=rom Assign ROMs. - pci=assign-busses Assign busses - pci=irqmask=MASK Set PCI interrupt mask to MASK - pci=lastbus=NUMBER Scan up to NUMBER busses, no matter what the mptable says. - pci=noacpi Don't use ACPI to set up PCI interrupt routing. - -IOMMU (input/output memory management unit) - - Multiple x86-64 PCI-DMA mapping implementations exist, for example: - - 1. : use no hardware/software IOMMU at all - (e.g. because you have < 3 GB memory). - Kernel boot message: "PCI-DMA: Disabling IOMMU" - - 2. : AMD GART based hardware IOMMU. - Kernel boot message: "PCI-DMA: using GART IOMMU" - - 3. : Software IOMMU implementation. Used - e.g. if there is no hardware IOMMU in the system and it is need because - you have >3GB memory or told the kernel to us it (iommu=soft)) - Kernel boot message: "PCI-DMA: Using software bounce buffering - for IO (SWIOTLB)" - - 4. : IBM Calgary hardware IOMMU. Used in IBM - pSeries and xSeries servers. This hardware IOMMU supports DMA address - mapping with memory protection, etc. - Kernel boot message: "PCI-DMA: Using Calgary IOMMU" - - iommu=[][,noagp][,off][,force][,noforce] - [,memaper[=]][,merge][,fullflush][,nomerge] - [,noaperture][,calgary] - - General iommu options: - off Don't initialize and use any kind of IOMMU. - noforce Don't force hardware IOMMU usage when it is not needed. - (default). - force Force the use of the hardware IOMMU even when it is - not actually needed (e.g. because < 3 GB memory). - soft Use software bounce buffering (SWIOTLB) (default for - Intel machines). This can be used to prevent the usage - of an available hardware IOMMU. - - iommu options only relevant to the AMD GART hardware IOMMU: - Set the size of the remapping area in bytes. - allowed Overwrite iommu off workarounds for specific chipsets. - fullflush Flush IOMMU on each allocation (default). - nofullflush Don't use IOMMU fullflush. - memaper[=] Allocate an own aperture over RAM with size 32MB<[,force] - Prereserve that many 128K pages for the software IO - bounce buffering. - force Force all IO through the software TLB. - - Settings for the IBM Calgary hardware IOMMU currently found in IBM - pSeries and xSeries machines: - - calgary=[64k,128k,256k,512k,1M,2M,4M,8M] - calgary=[translate_empty_slots] - calgary=[disable=] - panic Always panic when IOMMU overflows - - 64k,...,8M - Set the size of each PCI slot's translation table - when using the Calgary IOMMU. This is the size of the translation - table itself in main memory. The smallest table, 64k, covers an IO - space of 32MB; the largest, 8MB table, can cover an IO space of - 4GB. Normally the kernel will make the right choice by itself. - - translate_empty_slots - Enable translation even on slots that have - no devices attached to them, in case a device will be hotplugged - in the future. - - disable= - Disable translation on a given PHB. For - example, the built-in graphics adapter resides on the first bridge - (PCI bus number 0); if translation (isolation) is enabled on this - bridge, X servers that access the hardware directly from user - space might stop working. Use this option if you have devices that - are accessed from userspace directly on some PCI host bridge. - -Miscellaneous - - nogbpages - Do not use GB pages for kernel direct mappings. - gbpages - Use GB pages for kernel direct mappings. diff --git a/Documentation/x86/x86_64/index.rst b/Documentation/x86/x86_64/index.rst new file mode 100644 index 000000000000..a8cf7713cac9 --- /dev/null +++ b/Documentation/x86/x86_64/index.rst @@ -0,0 +1,10 @@ +.. SPDX-License-Identifier: GPL-2.0 + +============== +x86_64 Support +============== + +.. toctree:: + :maxdepth: 2 + + boot-options -- cgit v1.2.3 From 1c65b4e0f27f3688d95de59cbdfa076270251f3c Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:36 +0800 Subject: Documentation: x86: convert x86_64/uefi.txt to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/x86_64/index.rst | 1 + Documentation/x86/x86_64/uefi.rst | 58 ++++++++++++++++++++++++++++++++++++++ Documentation/x86/x86_64/uefi.txt | 42 --------------------------- 3 files changed, 59 insertions(+), 42 deletions(-) create mode 100644 Documentation/x86/x86_64/uefi.rst delete mode 100644 Documentation/x86/x86_64/uefi.txt (limited to 'Documentation') diff --git a/Documentation/x86/x86_64/index.rst b/Documentation/x86/x86_64/index.rst index a8cf7713cac9..ddfa1f9d4193 100644 --- a/Documentation/x86/x86_64/index.rst +++ b/Documentation/x86/x86_64/index.rst @@ -8,3 +8,4 @@ x86_64 Support :maxdepth: 2 boot-options + uefi diff --git a/Documentation/x86/x86_64/uefi.rst b/Documentation/x86/x86_64/uefi.rst new file mode 100644 index 000000000000..88c3ba32546f --- /dev/null +++ b/Documentation/x86/x86_64/uefi.rst @@ -0,0 +1,58 @@ +.. SPDX-License-Identifier: GPL-2.0 + +===================================== +General note on [U]EFI x86_64 support +===================================== + +The nomenclature EFI and UEFI are used interchangeably in this document. + +Although the tools below are _not_ needed for building the kernel, +the needed bootloader support and associated tools for x86_64 platforms +with EFI firmware and specifications are listed below. + +1. UEFI specification: http://www.uefi.org + +2. Booting Linux kernel on UEFI x86_64 platform requires bootloader + support. Elilo with x86_64 support can be used. + +3. x86_64 platform with EFI/UEFI firmware. + +Mechanics +--------- + +- Build the kernel with the following configuration:: + + CONFIG_FB_EFI=y + CONFIG_FRAMEBUFFER_CONSOLE=y + + If EFI runtime services are expected, the following configuration should + be selected:: + + CONFIG_EFI=y + CONFIG_EFI_VARS=y or m # optional + +- Create a VFAT partition on the disk +- Copy the following to the VFAT partition: + + elilo bootloader with x86_64 support, elilo configuration file, + kernel image built in first step and corresponding + initrd. Instructions on building elilo and its dependencies + can be found in the elilo sourceforge project. + +- Boot to EFI shell and invoke elilo choosing the kernel image built + in first step. +- If some or all EFI runtime services don't work, you can try following + kernel command line parameters to turn off some or all EFI runtime + services. + + noefi + turn off all EFI runtime services + reboot_type=k + turn off EFI reboot runtime service + +- If the EFI memory map has additional entries not in the E820 map, + you can include those entries in the kernels memory map of available + physical RAM by using the following kernel command line parameter. + + add_efi_memmap + include EFI memory map of available physical RAM diff --git a/Documentation/x86/x86_64/uefi.txt b/Documentation/x86/x86_64/uefi.txt deleted file mode 100644 index a5e2b4fdb170..000000000000 --- a/Documentation/x86/x86_64/uefi.txt +++ /dev/null @@ -1,42 +0,0 @@ -General note on [U]EFI x86_64 support -------------------------------------- - -The nomenclature EFI and UEFI are used interchangeably in this document. - -Although the tools below are _not_ needed for building the kernel, -the needed bootloader support and associated tools for x86_64 platforms -with EFI firmware and specifications are listed below. - -1. UEFI specification: http://www.uefi.org - -2. Booting Linux kernel on UEFI x86_64 platform requires bootloader - support. Elilo with x86_64 support can be used. - -3. x86_64 platform with EFI/UEFI firmware. - -Mechanics: ---------- -- Build the kernel with the following configuration. - CONFIG_FB_EFI=y - CONFIG_FRAMEBUFFER_CONSOLE=y - If EFI runtime services are expected, the following configuration should - be selected. - CONFIG_EFI=y - CONFIG_EFI_VARS=y or m # optional -- Create a VFAT partition on the disk -- Copy the following to the VFAT partition: - elilo bootloader with x86_64 support, elilo configuration file, - kernel image built in first step and corresponding - initrd. Instructions on building elilo and its dependencies - can be found in the elilo sourceforge project. -- Boot to EFI shell and invoke elilo choosing the kernel image built - in first step. -- If some or all EFI runtime services don't work, you can try following - kernel command line parameters to turn off some or all EFI runtime - services. - noefi turn off all EFI runtime services - reboot_type=k turn off EFI reboot runtime service -- If the EFI memory map has additional entries not in the E820 map, - you can include those entries in the kernels memory map of available - physical RAM by using the following kernel command line parameter. - add_efi_memmap include EFI memory map of available physical RAM -- cgit v1.2.3 From b88679d2f2b9e18618308bbe6d70a1fc91b6a35a Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:37 +0800 Subject: Documentation: x86: convert x86_64/mm.txt to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/x86_64/index.rst | 1 + Documentation/x86/x86_64/mm.rst | 161 +++++++++++++++++++++++++++++++++++++ Documentation/x86/x86_64/mm.txt | 153 ----------------------------------- 3 files changed, 162 insertions(+), 153 deletions(-) create mode 100644 Documentation/x86/x86_64/mm.rst delete mode 100644 Documentation/x86/x86_64/mm.txt (limited to 'Documentation') diff --git a/Documentation/x86/x86_64/index.rst b/Documentation/x86/x86_64/index.rst index ddfa1f9d4193..4b65d29ef459 100644 --- a/Documentation/x86/x86_64/index.rst +++ b/Documentation/x86/x86_64/index.rst @@ -9,3 +9,4 @@ x86_64 Support boot-options uefi + mm diff --git a/Documentation/x86/x86_64/mm.rst b/Documentation/x86/x86_64/mm.rst new file mode 100644 index 000000000000..52020577b8de --- /dev/null +++ b/Documentation/x86/x86_64/mm.rst @@ -0,0 +1,161 @@ +.. SPDX-License-Identifier: GPL-2.0 + +================ +Memory Managment +================ + +Complete virtual memory map with 4-level page tables +==================================================== + +.. note:: + + - Negative addresses such as "-23 TB" are absolute addresses in bytes, counted down + from the top of the 64-bit address space. It's easier to understand the layout + when seen both in absolute addresses and in distance-from-top notation. + + For example 0xffffe90000000000 == -23 TB, it's 23 TB lower than the top of the + 64-bit address space (ffffffffffffffff). + + Note that as we get closer to the top of the address space, the notation changes + from TB to GB and then MB/KB. + + - "16M TB" might look weird at first sight, but it's an easier to visualize size + notation than "16 EB", which few will recognize at first sight as 16 exabytes. + It also shows it nicely how incredibly large 64-bit address space is. + +:: + + ======================================================================================================================== + Start addr | Offset | End addr | Size | VM area description + ======================================================================================================================== + | | | | + 0000000000000000 | 0 | 00007fffffffffff | 128 TB | user-space virtual memory, different per mm + __________________|____________|__________________|_________|___________________________________________________________ + | | | | + 0000800000000000 | +128 TB | ffff7fffffffffff | ~16M TB | ... huge, almost 64 bits wide hole of non-canonical + | | | | virtual memory addresses up to the -128 TB + | | | | starting offset of kernel mappings. + __________________|____________|__________________|_________|___________________________________________________________ + | + | Kernel-space virtual memory, shared between all processes: + ____________________________________________________________|___________________________________________________________ + | | | | + ffff800000000000 | -128 TB | ffff87ffffffffff | 8 TB | ... guard hole, also reserved for hypervisor + ffff880000000000 | -120 TB | ffff887fffffffff | 0.5 TB | LDT remap for PTI + ffff888000000000 | -119.5 TB | ffffc87fffffffff | 64 TB | direct mapping of all physical memory (page_offset_base) + ffffc88000000000 | -55.5 TB | ffffc8ffffffffff | 0.5 TB | ... unused hole + ffffc90000000000 | -55 TB | ffffe8ffffffffff | 32 TB | vmalloc/ioremap space (vmalloc_base) + ffffe90000000000 | -23 TB | ffffe9ffffffffff | 1 TB | ... unused hole + ffffea0000000000 | -22 TB | ffffeaffffffffff | 1 TB | virtual memory map (vmemmap_base) + ffffeb0000000000 | -21 TB | ffffebffffffffff | 1 TB | ... unused hole + ffffec0000000000 | -20 TB | fffffbffffffffff | 16 TB | KASAN shadow memory + __________________|____________|__________________|_________|____________________________________________________________ + | + | Identical layout to the 56-bit one from here on: + ____________________________________________________________|____________________________________________________________ + | | | | + fffffc0000000000 | -4 TB | fffffdffffffffff | 2 TB | ... unused hole + | | | | vaddr_end for KASLR + fffffe0000000000 | -2 TB | fffffe7fffffffff | 0.5 TB | cpu_entry_area mapping + fffffe8000000000 | -1.5 TB | fffffeffffffffff | 0.5 TB | ... unused hole + ffffff0000000000 | -1 TB | ffffff7fffffffff | 0.5 TB | %esp fixup stacks + ffffff8000000000 | -512 GB | ffffffeeffffffff | 444 GB | ... unused hole + ffffffef00000000 | -68 GB | fffffffeffffffff | 64 GB | EFI region mapping space + ffffffff00000000 | -4 GB | ffffffff7fffffff | 2 GB | ... unused hole + ffffffff80000000 | -2 GB | ffffffff9fffffff | 512 MB | kernel text mapping, mapped to physical address 0 + ffffffff80000000 |-2048 MB | | | + ffffffffa0000000 |-1536 MB | fffffffffeffffff | 1520 MB | module mapping space + ffffffffff000000 | -16 MB | | | + FIXADDR_START | ~-11 MB | ffffffffff5fffff | ~0.5 MB | kernel-internal fixmap range, variable size and offset + ffffffffff600000 | -10 MB | ffffffffff600fff | 4 kB | legacy vsyscall ABI + ffffffffffe00000 | -2 MB | ffffffffffffffff | 2 MB | ... unused hole + __________________|____________|__________________|_________|___________________________________________________________ + + +Complete virtual memory map with 5-level page tables +==================================================== + +.. note:: + + - With 56-bit addresses, user-space memory gets expanded by a factor of 512x, + from 0.125 PB to 64 PB. All kernel mappings shift down to the -64 PT starting + offset and many of the regions expand to support the much larger physical + memory supported. + +:: + + ======================================================================================================================== + Start addr | Offset | End addr | Size | VM area description + ======================================================================================================================== + | | | | + 0000000000000000 | 0 | 00ffffffffffffff | 64 PB | user-space virtual memory, different per mm + __________________|____________|__________________|_________|___________________________________________________________ + | | | | + 0000800000000000 | +64 PB | ffff7fffffffffff | ~16K PB | ... huge, still almost 64 bits wide hole of non-canonical + | | | | virtual memory addresses up to the -64 PB + | | | | starting offset of kernel mappings. + __________________|____________|__________________|_________|___________________________________________________________ + | + | Kernel-space virtual memory, shared between all processes: + ____________________________________________________________|___________________________________________________________ + | | | | + ff00000000000000 | -64 PB | ff0fffffffffffff | 4 PB | ... guard hole, also reserved for hypervisor + ff10000000000000 | -60 PB | ff10ffffffffffff | 0.25 PB | LDT remap for PTI + ff11000000000000 | -59.75 PB | ff90ffffffffffff | 32 PB | direct mapping of all physical memory (page_offset_base) + ff91000000000000 | -27.75 PB | ff9fffffffffffff | 3.75 PB | ... unused hole + ffa0000000000000 | -24 PB | ffd1ffffffffffff | 12.5 PB | vmalloc/ioremap space (vmalloc_base) + ffd2000000000000 | -11.5 PB | ffd3ffffffffffff | 0.5 PB | ... unused hole + ffd4000000000000 | -11 PB | ffd5ffffffffffff | 0.5 PB | virtual memory map (vmemmap_base) + ffd6000000000000 | -10.5 PB | ffdeffffffffffff | 2.25 PB | ... unused hole + ffdf000000000000 | -8.25 PB | fffffdffffffffff | ~8 PB | KASAN shadow memory + __________________|____________|__________________|_________|____________________________________________________________ + | + | Identical layout to the 47-bit one from here on: + ____________________________________________________________|____________________________________________________________ + | | | | + fffffc0000000000 | -4 TB | fffffdffffffffff | 2 TB | ... unused hole + | | | | vaddr_end for KASLR + fffffe0000000000 | -2 TB | fffffe7fffffffff | 0.5 TB | cpu_entry_area mapping + fffffe8000000000 | -1.5 TB | fffffeffffffffff | 0.5 TB | ... unused hole + ffffff0000000000 | -1 TB | ffffff7fffffffff | 0.5 TB | %esp fixup stacks + ffffff8000000000 | -512 GB | ffffffeeffffffff | 444 GB | ... unused hole + ffffffef00000000 | -68 GB | fffffffeffffffff | 64 GB | EFI region mapping space + ffffffff00000000 | -4 GB | ffffffff7fffffff | 2 GB | ... unused hole + ffffffff80000000 | -2 GB | ffffffff9fffffff | 512 MB | kernel text mapping, mapped to physical address 0 + ffffffff80000000 |-2048 MB | | | + ffffffffa0000000 |-1536 MB | fffffffffeffffff | 1520 MB | module mapping space + ffffffffff000000 | -16 MB | | | + FIXADDR_START | ~-11 MB | ffffffffff5fffff | ~0.5 MB | kernel-internal fixmap range, variable size and offset + ffffffffff600000 | -10 MB | ffffffffff600fff | 4 kB | legacy vsyscall ABI + ffffffffffe00000 | -2 MB | ffffffffffffffff | 2 MB | ... unused hole + __________________|____________|__________________|_________|___________________________________________________________ + +Architecture defines a 64-bit virtual address. Implementations can support +less. Currently supported are 48- and 57-bit virtual addresses. Bits 63 +through to the most-significant implemented bit are sign extended. +This causes hole between user space and kernel addresses if you interpret them +as unsigned. + +The direct mapping covers all memory in the system up to the highest +memory address (this means in some cases it can also include PCI memory +holes). + +vmalloc space is lazily synchronized into the different PML4/PML5 pages of +the processes using the page fault handler, with init_top_pgt as +reference. + +We map EFI runtime services in the 'efi_pgd' PGD in a 64Gb large virtual +memory window (this size is arbitrary, it can be raised later if needed). +The mappings are not part of any other kernel PGD and are only available +during EFI runtime calls. + +Note that if CONFIG_RANDOMIZE_MEMORY is enabled, the direct mapping of all +physical memory, vmalloc/ioremap space and virtual memory map are randomized. +Their order is preserved but their base will be offset early at boot time. + +Be very careful vs. KASLR when changing anything here. The KASLR address +range must not overlap with anything except the KASAN shadow area, which is +correct as KASAN disables KASLR. + +For both 4- and 5-level layouts, the STACKLEAK_POISON value in the last 2MB +hole: ffffffffffff4111 diff --git a/Documentation/x86/x86_64/mm.txt b/Documentation/x86/x86_64/mm.txt deleted file mode 100644 index 804f9426ed17..000000000000 --- a/Documentation/x86/x86_64/mm.txt +++ /dev/null @@ -1,153 +0,0 @@ -==================================================== -Complete virtual memory map with 4-level page tables -==================================================== - -Notes: - - - Negative addresses such as "-23 TB" are absolute addresses in bytes, counted down - from the top of the 64-bit address space. It's easier to understand the layout - when seen both in absolute addresses and in distance-from-top notation. - - For example 0xffffe90000000000 == -23 TB, it's 23 TB lower than the top of the - 64-bit address space (ffffffffffffffff). - - Note that as we get closer to the top of the address space, the notation changes - from TB to GB and then MB/KB. - - - "16M TB" might look weird at first sight, but it's an easier to visualize size - notation than "16 EB", which few will recognize at first sight as 16 exabytes. - It also shows it nicely how incredibly large 64-bit address space is. - -======================================================================================================================== - Start addr | Offset | End addr | Size | VM area description -======================================================================================================================== - | | | | - 0000000000000000 | 0 | 00007fffffffffff | 128 TB | user-space virtual memory, different per mm -__________________|____________|__________________|_________|___________________________________________________________ - | | | | - 0000800000000000 | +128 TB | ffff7fffffffffff | ~16M TB | ... huge, almost 64 bits wide hole of non-canonical - | | | | virtual memory addresses up to the -128 TB - | | | | starting offset of kernel mappings. -__________________|____________|__________________|_________|___________________________________________________________ - | - | Kernel-space virtual memory, shared between all processes: -____________________________________________________________|___________________________________________________________ - | | | | - ffff800000000000 | -128 TB | ffff87ffffffffff | 8 TB | ... guard hole, also reserved for hypervisor - ffff880000000000 | -120 TB | ffff887fffffffff | 0.5 TB | LDT remap for PTI - ffff888000000000 | -119.5 TB | ffffc87fffffffff | 64 TB | direct mapping of all physical memory (page_offset_base) - ffffc88000000000 | -55.5 TB | ffffc8ffffffffff | 0.5 TB | ... unused hole - ffffc90000000000 | -55 TB | ffffe8ffffffffff | 32 TB | vmalloc/ioremap space (vmalloc_base) - ffffe90000000000 | -23 TB | ffffe9ffffffffff | 1 TB | ... unused hole - ffffea0000000000 | -22 TB | ffffeaffffffffff | 1 TB | virtual memory map (vmemmap_base) - ffffeb0000000000 | -21 TB | ffffebffffffffff | 1 TB | ... unused hole - ffffec0000000000 | -20 TB | fffffbffffffffff | 16 TB | KASAN shadow memory -__________________|____________|__________________|_________|____________________________________________________________ - | - | Identical layout to the 56-bit one from here on: -____________________________________________________________|____________________________________________________________ - | | | | - fffffc0000000000 | -4 TB | fffffdffffffffff | 2 TB | ... unused hole - | | | | vaddr_end for KASLR - fffffe0000000000 | -2 TB | fffffe7fffffffff | 0.5 TB | cpu_entry_area mapping - fffffe8000000000 | -1.5 TB | fffffeffffffffff | 0.5 TB | ... unused hole - ffffff0000000000 | -1 TB | ffffff7fffffffff | 0.5 TB | %esp fixup stacks - ffffff8000000000 | -512 GB | ffffffeeffffffff | 444 GB | ... unused hole - ffffffef00000000 | -68 GB | fffffffeffffffff | 64 GB | EFI region mapping space - ffffffff00000000 | -4 GB | ffffffff7fffffff | 2 GB | ... unused hole - ffffffff80000000 | -2 GB | ffffffff9fffffff | 512 MB | kernel text mapping, mapped to physical address 0 - ffffffff80000000 |-2048 MB | | | - ffffffffa0000000 |-1536 MB | fffffffffeffffff | 1520 MB | module mapping space - ffffffffff000000 | -16 MB | | | - FIXADDR_START | ~-11 MB | ffffffffff5fffff | ~0.5 MB | kernel-internal fixmap range, variable size and offset - ffffffffff600000 | -10 MB | ffffffffff600fff | 4 kB | legacy vsyscall ABI - ffffffffffe00000 | -2 MB | ffffffffffffffff | 2 MB | ... unused hole -__________________|____________|__________________|_________|___________________________________________________________ - - -==================================================== -Complete virtual memory map with 5-level page tables -==================================================== - -Notes: - - - With 56-bit addresses, user-space memory gets expanded by a factor of 512x, - from 0.125 PB to 64 PB. All kernel mappings shift down to the -64 PT starting - offset and many of the regions expand to support the much larger physical - memory supported. - -======================================================================================================================== - Start addr | Offset | End addr | Size | VM area description -======================================================================================================================== - | | | | - 0000000000000000 | 0 | 00ffffffffffffff | 64 PB | user-space virtual memory, different per mm -__________________|____________|__________________|_________|___________________________________________________________ - | | | | - 0000800000000000 | +64 PB | ffff7fffffffffff | ~16K PB | ... huge, still almost 64 bits wide hole of non-canonical - | | | | virtual memory addresses up to the -64 PB - | | | | starting offset of kernel mappings. -__________________|____________|__________________|_________|___________________________________________________________ - | - | Kernel-space virtual memory, shared between all processes: -____________________________________________________________|___________________________________________________________ - | | | | - ff00000000000000 | -64 PB | ff0fffffffffffff | 4 PB | ... guard hole, also reserved for hypervisor - ff10000000000000 | -60 PB | ff10ffffffffffff | 0.25 PB | LDT remap for PTI - ff11000000000000 | -59.75 PB | ff90ffffffffffff | 32 PB | direct mapping of all physical memory (page_offset_base) - ff91000000000000 | -27.75 PB | ff9fffffffffffff | 3.75 PB | ... unused hole - ffa0000000000000 | -24 PB | ffd1ffffffffffff | 12.5 PB | vmalloc/ioremap space (vmalloc_base) - ffd2000000000000 | -11.5 PB | ffd3ffffffffffff | 0.5 PB | ... unused hole - ffd4000000000000 | -11 PB | ffd5ffffffffffff | 0.5 PB | virtual memory map (vmemmap_base) - ffd6000000000000 | -10.5 PB | ffdeffffffffffff | 2.25 PB | ... unused hole - ffdf000000000000 | -8.25 PB | fffffdffffffffff | ~8 PB | KASAN shadow memory -__________________|____________|__________________|_________|____________________________________________________________ - | - | Identical layout to the 47-bit one from here on: -____________________________________________________________|____________________________________________________________ - | | | | - fffffc0000000000 | -4 TB | fffffdffffffffff | 2 TB | ... unused hole - | | | | vaddr_end for KASLR - fffffe0000000000 | -2 TB | fffffe7fffffffff | 0.5 TB | cpu_entry_area mapping - fffffe8000000000 | -1.5 TB | fffffeffffffffff | 0.5 TB | ... unused hole - ffffff0000000000 | -1 TB | ffffff7fffffffff | 0.5 TB | %esp fixup stacks - ffffff8000000000 | -512 GB | ffffffeeffffffff | 444 GB | ... unused hole - ffffffef00000000 | -68 GB | fffffffeffffffff | 64 GB | EFI region mapping space - ffffffff00000000 | -4 GB | ffffffff7fffffff | 2 GB | ... unused hole - ffffffff80000000 | -2 GB | ffffffff9fffffff | 512 MB | kernel text mapping, mapped to physical address 0 - ffffffff80000000 |-2048 MB | | | - ffffffffa0000000 |-1536 MB | fffffffffeffffff | 1520 MB | module mapping space - ffffffffff000000 | -16 MB | | | - FIXADDR_START | ~-11 MB | ffffffffff5fffff | ~0.5 MB | kernel-internal fixmap range, variable size and offset - ffffffffff600000 | -10 MB | ffffffffff600fff | 4 kB | legacy vsyscall ABI - ffffffffffe00000 | -2 MB | ffffffffffffffff | 2 MB | ... unused hole -__________________|____________|__________________|_________|___________________________________________________________ - -Architecture defines a 64-bit virtual address. Implementations can support -less. Currently supported are 48- and 57-bit virtual addresses. Bits 63 -through to the most-significant implemented bit are sign extended. -This causes hole between user space and kernel addresses if you interpret them -as unsigned. - -The direct mapping covers all memory in the system up to the highest -memory address (this means in some cases it can also include PCI memory -holes). - -vmalloc space is lazily synchronized into the different PML4/PML5 pages of -the processes using the page fault handler, with init_top_pgt as -reference. - -We map EFI runtime services in the 'efi_pgd' PGD in a 64Gb large virtual -memory window (this size is arbitrary, it can be raised later if needed). -The mappings are not part of any other kernel PGD and are only available -during EFI runtime calls. - -Note that if CONFIG_RANDOMIZE_MEMORY is enabled, the direct mapping of all -physical memory, vmalloc/ioremap space and virtual memory map are randomized. -Their order is preserved but their base will be offset early at boot time. - -Be very careful vs. KASLR when changing anything here. The KASLR address -range must not overlap with anything except the KASAN shadow area, which is -correct as KASAN disables KASLR. - -For both 4- and 5-level layouts, the STACKLEAK_POISON value in the last 2MB -hole: ffffffffffff4111 -- cgit v1.2.3 From 85a3bd41cd680aacf0b88e78bbfcfb5bc13292ff Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:38 +0800 Subject: Documentation: x86: convert x86_64/5level-paging.txt to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/x86_64/5level-paging.rst | 67 ++++++++++++++++++++++++++++++ Documentation/x86/x86_64/5level-paging.txt | 61 --------------------------- Documentation/x86/x86_64/index.rst | 1 + 3 files changed, 68 insertions(+), 61 deletions(-) create mode 100644 Documentation/x86/x86_64/5level-paging.rst delete mode 100644 Documentation/x86/x86_64/5level-paging.txt (limited to 'Documentation') diff --git a/Documentation/x86/x86_64/5level-paging.rst b/Documentation/x86/x86_64/5level-paging.rst new file mode 100644 index 000000000000..ab88a4514163 --- /dev/null +++ b/Documentation/x86/x86_64/5level-paging.rst @@ -0,0 +1,67 @@ +.. SPDX-License-Identifier: GPL-2.0 + +============== +5-level paging +============== + +Overview +======== +Original x86-64 was limited by 4-level paing to 256 TiB of virtual address +space and 64 TiB of physical address space. We are already bumping into +this limit: some vendors offers servers with 64 TiB of memory today. + +To overcome the limitation upcoming hardware will introduce support for +5-level paging. It is a straight-forward extension of the current page +table structure adding one more layer of translation. + +It bumps the limits to 128 PiB of virtual address space and 4 PiB of +physical address space. This "ought to be enough for anybody" ©. + +QEMU 2.9 and later support 5-level paging. + +Virtual memory layout for 5-level paging is described in +Documentation/x86/x86_64/mm.txt + + +Enabling 5-level paging +======================= +CONFIG_X86_5LEVEL=y enables the feature. + +Kernel with CONFIG_X86_5LEVEL=y still able to boot on 4-level hardware. +In this case additional page table level -- p4d -- will be folded at +runtime. + +User-space and large virtual address space +========================================== +On x86, 5-level paging enables 56-bit userspace virtual address space. +Not all user space is ready to handle wide addresses. It's known that +at least some JIT compilers use higher bits in pointers to encode their +information. It collides with valid pointers with 5-level paging and +leads to crashes. + +To mitigate this, we are not going to allocate virtual address space +above 47-bit by default. + +But userspace can ask for allocation from full address space by +specifying hint address (with or without MAP_FIXED) above 47-bits. + +If hint address set above 47-bit, but MAP_FIXED is not specified, we try +to look for unmapped area by specified address. If it's already +occupied, we look for unmapped area in *full* address space, rather than +from 47-bit window. + +A high hint address would only affect the allocation in question, but not +any future mmap()s. + +Specifying high hint address on older kernel or on machine without 5-level +paging support is safe. The hint will be ignored and kernel will fall back +to allocation from 47-bit address space. + +This approach helps to easily make application's memory allocator aware +about large address space without manually tracking allocated virtual +address space. + +One important case we need to handle here is interaction with MPX. +MPX (without MAWA extension) cannot handle addresses above 47-bit, so we +need to make sure that MPX cannot be enabled we already have VMA above +the boundary and forbid creating such VMAs once MPX is enabled. diff --git a/Documentation/x86/x86_64/5level-paging.txt b/Documentation/x86/x86_64/5level-paging.txt deleted file mode 100644 index 2432a5ef86d9..000000000000 --- a/Documentation/x86/x86_64/5level-paging.txt +++ /dev/null @@ -1,61 +0,0 @@ -== Overview == - -Original x86-64 was limited by 4-level paing to 256 TiB of virtual address -space and 64 TiB of physical address space. We are already bumping into -this limit: some vendors offers servers with 64 TiB of memory today. - -To overcome the limitation upcoming hardware will introduce support for -5-level paging. It is a straight-forward extension of the current page -table structure adding one more layer of translation. - -It bumps the limits to 128 PiB of virtual address space and 4 PiB of -physical address space. This "ought to be enough for anybody" ©. - -QEMU 2.9 and later support 5-level paging. - -Virtual memory layout for 5-level paging is described in -Documentation/x86/x86_64/mm.txt - -== Enabling 5-level paging == - -CONFIG_X86_5LEVEL=y enables the feature. - -Kernel with CONFIG_X86_5LEVEL=y still able to boot on 4-level hardware. -In this case additional page table level -- p4d -- will be folded at -runtime. - -== User-space and large virtual address space == - -On x86, 5-level paging enables 56-bit userspace virtual address space. -Not all user space is ready to handle wide addresses. It's known that -at least some JIT compilers use higher bits in pointers to encode their -information. It collides with valid pointers with 5-level paging and -leads to crashes. - -To mitigate this, we are not going to allocate virtual address space -above 47-bit by default. - -But userspace can ask for allocation from full address space by -specifying hint address (with or without MAP_FIXED) above 47-bits. - -If hint address set above 47-bit, but MAP_FIXED is not specified, we try -to look for unmapped area by specified address. If it's already -occupied, we look for unmapped area in *full* address space, rather than -from 47-bit window. - -A high hint address would only affect the allocation in question, but not -any future mmap()s. - -Specifying high hint address on older kernel or on machine without 5-level -paging support is safe. The hint will be ignored and kernel will fall back -to allocation from 47-bit address space. - -This approach helps to easily make application's memory allocator aware -about large address space without manually tracking allocated virtual -address space. - -One important case we need to handle here is interaction with MPX. -MPX (without MAWA extension) cannot handle addresses above 47-bit, so we -need to make sure that MPX cannot be enabled we already have VMA above -the boundary and forbid creating such VMAs once MPX is enabled. - diff --git a/Documentation/x86/x86_64/index.rst b/Documentation/x86/x86_64/index.rst index 4b65d29ef459..7b8c82151358 100644 --- a/Documentation/x86/x86_64/index.rst +++ b/Documentation/x86/x86_64/index.rst @@ -10,3 +10,4 @@ x86_64 Support boot-options uefi mm + 5level-paging -- cgit v1.2.3 From f0339db77665e9a196c3afd55386becfb9e70d51 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:39 +0800 Subject: Documentation: x86: convert x86_64/fake-numa-for-cpusets to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/x86_64/fake-numa-for-cpusets | 67 ------------------- Documentation/x86/x86_64/fake-numa-for-cpusets.rst | 78 ++++++++++++++++++++++ Documentation/x86/x86_64/index.rst | 1 + 3 files changed, 79 insertions(+), 67 deletions(-) delete mode 100644 Documentation/x86/x86_64/fake-numa-for-cpusets create mode 100644 Documentation/x86/x86_64/fake-numa-for-cpusets.rst (limited to 'Documentation') diff --git a/Documentation/x86/x86_64/fake-numa-for-cpusets b/Documentation/x86/x86_64/fake-numa-for-cpusets deleted file mode 100644 index 4b09f18831f8..000000000000 --- a/Documentation/x86/x86_64/fake-numa-for-cpusets +++ /dev/null @@ -1,67 +0,0 @@ -Using numa=fake and CPUSets for Resource Management -Written by David Rientjes - -This document describes how the numa=fake x86_64 command-line option can be used -in conjunction with cpusets for coarse memory management. Using this feature, -you can create fake NUMA nodes that represent contiguous chunks of memory and -assign them to cpusets and their attached tasks. This is a way of limiting the -amount of system memory that are available to a certain class of tasks. - -For more information on the features of cpusets, see -Documentation/cgroup-v1/cpusets.txt. -There are a number of different configurations you can use for your needs. For -more information on the numa=fake command line option and its various ways of -configuring fake nodes, see Documentation/x86/x86_64/boot-options.txt. - -For the purposes of this introduction, we'll assume a very primitive NUMA -emulation setup of "numa=fake=4*512,". This will split our system memory into -four equal chunks of 512M each that we can now use to assign to cpusets. As -you become more familiar with using this combination for resource control, -you'll determine a better setup to minimize the number of nodes you have to deal -with. - -A machine may be split as follows with "numa=fake=4*512," as reported by dmesg: - - Faking node 0 at 0000000000000000-0000000020000000 (512MB) - Faking node 1 at 0000000020000000-0000000040000000 (512MB) - Faking node 2 at 0000000040000000-0000000060000000 (512MB) - Faking node 3 at 0000000060000000-0000000080000000 (512MB) - ... - On node 0 totalpages: 130975 - On node 1 totalpages: 131072 - On node 2 totalpages: 131072 - On node 3 totalpages: 131072 - -Now following the instructions for mounting the cpusets filesystem from -Documentation/cgroup-v1/cpusets.txt, you can assign fake nodes (i.e. contiguous memory -address spaces) to individual cpusets: - - [root@xroads /]# mkdir exampleset - [root@xroads /]# mount -t cpuset none exampleset - [root@xroads /]# mkdir exampleset/ddset - [root@xroads /]# cd exampleset/ddset - [root@xroads /exampleset/ddset]# echo 0-1 > cpus - [root@xroads /exampleset/ddset]# echo 0-1 > mems - -Now this cpuset, 'ddset', will only allowed access to fake nodes 0 and 1 for -memory allocations (1G). - -You can now assign tasks to these cpusets to limit the memory resources -available to them according to the fake nodes assigned as mems: - - [root@xroads /exampleset/ddset]# echo $$ > tasks - [root@xroads /exampleset/ddset]# dd if=/dev/zero of=tmp bs=1024 count=1G - [1] 13425 - -Notice the difference between the system memory usage as reported by -/proc/meminfo between the restricted cpuset case above and the unrestricted -case (i.e. running the same 'dd' command without assigning it to a fake NUMA -cpuset): - Unrestricted Restricted - MemTotal: 3091900 kB 3091900 kB - MemFree: 42113 kB 1513236 kB - -This allows for coarse memory management for the tasks you assign to particular -cpusets. Since cpusets can form a hierarchy, you can create some pretty -interesting combinations of use-cases for various classes of tasks for your -memory management needs. diff --git a/Documentation/x86/x86_64/fake-numa-for-cpusets.rst b/Documentation/x86/x86_64/fake-numa-for-cpusets.rst new file mode 100644 index 000000000000..74fbb78b3c67 --- /dev/null +++ b/Documentation/x86/x86_64/fake-numa-for-cpusets.rst @@ -0,0 +1,78 @@ +.. SPDX-License-Identifier: GPL-2.0 + +===================== +Fake NUMA For CPUSets +===================== + +:Author: David Rientjes + +Using numa=fake and CPUSets for Resource Management + +This document describes how the numa=fake x86_64 command-line option can be used +in conjunction with cpusets for coarse memory management. Using this feature, +you can create fake NUMA nodes that represent contiguous chunks of memory and +assign them to cpusets and their attached tasks. This is a way of limiting the +amount of system memory that are available to a certain class of tasks. + +For more information on the features of cpusets, see +Documentation/cgroup-v1/cpusets.txt. +There are a number of different configurations you can use for your needs. For +more information on the numa=fake command line option and its various ways of +configuring fake nodes, see Documentation/x86/x86_64/boot-options.txt. + +For the purposes of this introduction, we'll assume a very primitive NUMA +emulation setup of "numa=fake=4*512,". This will split our system memory into +four equal chunks of 512M each that we can now use to assign to cpusets. As +you become more familiar with using this combination for resource control, +you'll determine a better setup to minimize the number of nodes you have to deal +with. + +A machine may be split as follows with "numa=fake=4*512," as reported by dmesg:: + + Faking node 0 at 0000000000000000-0000000020000000 (512MB) + Faking node 1 at 0000000020000000-0000000040000000 (512MB) + Faking node 2 at 0000000040000000-0000000060000000 (512MB) + Faking node 3 at 0000000060000000-0000000080000000 (512MB) + ... + On node 0 totalpages: 130975 + On node 1 totalpages: 131072 + On node 2 totalpages: 131072 + On node 3 totalpages: 131072 + +Now following the instructions for mounting the cpusets filesystem from +Documentation/cgroup-v1/cpusets.txt, you can assign fake nodes (i.e. contiguous memory +address spaces) to individual cpusets:: + + [root@xroads /]# mkdir exampleset + [root@xroads /]# mount -t cpuset none exampleset + [root@xroads /]# mkdir exampleset/ddset + [root@xroads /]# cd exampleset/ddset + [root@xroads /exampleset/ddset]# echo 0-1 > cpus + [root@xroads /exampleset/ddset]# echo 0-1 > mems + +Now this cpuset, 'ddset', will only allowed access to fake nodes 0 and 1 for +memory allocations (1G). + +You can now assign tasks to these cpusets to limit the memory resources +available to them according to the fake nodes assigned as mems:: + + [root@xroads /exampleset/ddset]# echo $$ > tasks + [root@xroads /exampleset/ddset]# dd if=/dev/zero of=tmp bs=1024 count=1G + [1] 13425 + +Notice the difference between the system memory usage as reported by +/proc/meminfo between the restricted cpuset case above and the unrestricted +case (i.e. running the same 'dd' command without assigning it to a fake NUMA +cpuset): + + ======== ============ ========== + Name Unrestricted Restricted + ======== ============ ========== + MemTotal 3091900 kB 3091900 kB + MemFree 42113 kB 1513236 kB + ======== ============ ========== + +This allows for coarse memory management for the tasks you assign to particular +cpusets. Since cpusets can form a hierarchy, you can create some pretty +interesting combinations of use-cases for various classes of tasks for your +memory management needs. diff --git a/Documentation/x86/x86_64/index.rst b/Documentation/x86/x86_64/index.rst index 7b8c82151358..e2a324cde671 100644 --- a/Documentation/x86/x86_64/index.rst +++ b/Documentation/x86/x86_64/index.rst @@ -11,3 +11,4 @@ x86_64 Support uefi mm 5level-paging + fake-numa-for-cpusets -- cgit v1.2.3 From bdde117ffed2625389787f82fc92724b486ce976 Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:40 +0800 Subject: Documentation: x86: convert x86_64/cpu-hotplug-spec to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/x86_64/cpu-hotplug-spec | 21 --------------------- Documentation/x86/x86_64/cpu-hotplug-spec.rst | 24 ++++++++++++++++++++++++ Documentation/x86/x86_64/index.rst | 1 + 3 files changed, 25 insertions(+), 21 deletions(-) delete mode 100644 Documentation/x86/x86_64/cpu-hotplug-spec create mode 100644 Documentation/x86/x86_64/cpu-hotplug-spec.rst (limited to 'Documentation') diff --git a/Documentation/x86/x86_64/cpu-hotplug-spec b/Documentation/x86/x86_64/cpu-hotplug-spec deleted file mode 100644 index 3c23e0587db3..000000000000 --- a/Documentation/x86/x86_64/cpu-hotplug-spec +++ /dev/null @@ -1,21 +0,0 @@ -Firmware support for CPU hotplug under Linux/x86-64 ---------------------------------------------------- - -Linux/x86-64 supports CPU hotplug now. For various reasons Linux wants to -know in advance of boot time the maximum number of CPUs that could be plugged -into the system. ACPI 3.0 currently has no official way to supply -this information from the firmware to the operating system. - -In ACPI each CPU needs an LAPIC object in the MADT table (5.2.11.5 in the -ACPI 3.0 specification). ACPI already has the concept of disabled LAPIC -objects by setting the Enabled bit in the LAPIC object to zero. - -For CPU hotplug Linux/x86-64 expects now that any possible future hotpluggable -CPU is already available in the MADT. If the CPU is not available yet -it should have its LAPIC Enabled bit set to 0. Linux will use the number -of disabled LAPICs to compute the maximum number of future CPUs. - -In the worst case the user can overwrite this choice using a command line -option (additional_cpus=...), but it is recommended to supply the correct -number (or a reasonable approximation of it, with erring towards more not less) -in the MADT to avoid manual configuration. diff --git a/Documentation/x86/x86_64/cpu-hotplug-spec.rst b/Documentation/x86/x86_64/cpu-hotplug-spec.rst new file mode 100644 index 000000000000..8d1c91f0c880 --- /dev/null +++ b/Documentation/x86/x86_64/cpu-hotplug-spec.rst @@ -0,0 +1,24 @@ +.. SPDX-License-Identifier: GPL-2.0 + +=================================================== +Firmware support for CPU hotplug under Linux/x86-64 +=================================================== + +Linux/x86-64 supports CPU hotplug now. For various reasons Linux wants to +know in advance of boot time the maximum number of CPUs that could be plugged +into the system. ACPI 3.0 currently has no official way to supply +this information from the firmware to the operating system. + +In ACPI each CPU needs an LAPIC object in the MADT table (5.2.11.5 in the +ACPI 3.0 specification). ACPI already has the concept of disabled LAPIC +objects by setting the Enabled bit in the LAPIC object to zero. + +For CPU hotplug Linux/x86-64 expects now that any possible future hotpluggable +CPU is already available in the MADT. If the CPU is not available yet +it should have its LAPIC Enabled bit set to 0. Linux will use the number +of disabled LAPICs to compute the maximum number of future CPUs. + +In the worst case the user can overwrite this choice using a command line +option (additional_cpus=...), but it is recommended to supply the correct +number (or a reasonable approximation of it, with erring towards more not less) +in the MADT to avoid manual configuration. diff --git a/Documentation/x86/x86_64/index.rst b/Documentation/x86/x86_64/index.rst index e2a324cde671..c04b6eab3c76 100644 --- a/Documentation/x86/x86_64/index.rst +++ b/Documentation/x86/x86_64/index.rst @@ -12,3 +12,4 @@ x86_64 Support mm 5level-paging fake-numa-for-cpusets + cpu-hotplug-spec -- cgit v1.2.3 From e115fb4bd2667754135d0436b6419fb171e9ea4a Mon Sep 17 00:00:00 2001 From: Changbin Du Date: Wed, 8 May 2019 23:21:41 +0800 Subject: Documentation: x86: convert x86_64/machinecheck to reST This converts the plain text documentation to reStructuredText format and add it to Sphinx TOC tree. No essential content change. Signed-off-by: Changbin Du Reviewed-by: Mauro Carvalho Chehab Signed-off-by: Jonathan Corbet --- Documentation/x86/x86_64/index.rst | 1 + Documentation/x86/x86_64/machinecheck | 83 ------------------------------ Documentation/x86/x86_64/machinecheck.rst | 85 +++++++++++++++++++++++++++++++ 3 files changed, 86 insertions(+), 83 deletions(-) delete mode 100644 Documentation/x86/x86_64/machinecheck create mode 100644 Documentation/x86/x86_64/machinecheck.rst (limited to 'Documentation') diff --git a/Documentation/x86/x86_64/index.rst b/Documentation/x86/x86_64/index.rst index c04b6eab3c76..d6eaaa5a35fc 100644 --- a/Documentation/x86/x86_64/index.rst +++ b/Documentation/x86/x86_64/index.rst @@ -13,3 +13,4 @@ x86_64 Support 5level-paging fake-numa-for-cpusets cpu-hotplug-spec + machinecheck diff --git a/Documentation/x86/x86_64/machinecheck b/Documentation/x86/x86_64/machinecheck deleted file mode 100644 index d0648a74fceb..000000000000 --- a/Documentation/x86/x86_64/machinecheck +++ /dev/null @@ -1,83 +0,0 @@ - -Configurable sysfs parameters for the x86-64 machine check code. - -Machine checks report internal hardware error conditions detected -by the CPU. Uncorrected errors typically cause a machine check -(often with panic), corrected ones cause a machine check log entry. - -Machine checks are organized in banks (normally associated with -a hardware subsystem) and subevents in a bank. The exact meaning -of the banks and subevent is CPU specific. - -mcelog knows how to decode them. - -When you see the "Machine check errors logged" message in the system -log then mcelog should run to collect and decode machine check entries -from /dev/mcelog. Normally mcelog should be run regularly from a cronjob. - -Each CPU has a directory in /sys/devices/system/machinecheck/machinecheckN -(N = CPU number) - -The directory contains some configurable entries: - -Entries: - -bankNctl -(N bank number) - 64bit Hex bitmask enabling/disabling specific subevents for bank N - When a bit in the bitmask is zero then the respective - subevent will not be reported. - By default all events are enabled. - Note that BIOS maintain another mask to disable specific events - per bank. This is not visible here - -The following entries appear for each CPU, but they are truly shared -between all CPUs. - -check_interval - How often to poll for corrected machine check errors, in seconds - (Note output is hexadecimal). Default 5 minutes. When the poller - finds MCEs it triggers an exponential speedup (poll more often) on - the polling interval. When the poller stops finding MCEs, it - triggers an exponential backoff (poll less often) on the polling - interval. The check_interval variable is both the initial and - maximum polling interval. 0 means no polling for corrected machine - check errors (but some corrected errors might be still reported - in other ways) - -tolerant - Tolerance level. When a machine check exception occurs for a non - corrected machine check the kernel can take different actions. - Since machine check exceptions can happen any time it is sometimes - risky for the kernel to kill a process because it defies - normal kernel locking rules. The tolerance level configures - how hard the kernel tries to recover even at some risk of - deadlock. Higher tolerant values trade potentially better uptime - with the risk of a crash or even corruption (for tolerant >= 3). - - 0: always panic on uncorrected errors, log corrected errors - 1: panic or SIGBUS on uncorrected errors, log corrected errors - 2: SIGBUS or log uncorrected errors, log corrected errors - 3: never panic or SIGBUS, log all errors (for testing only) - - Default: 1 - - Note this only makes a difference if the CPU allows recovery - from a machine check exception. Current x86 CPUs generally do not. - -trigger - Program to run when a machine check event is detected. - This is an alternative to running mcelog regularly from cron - and allows to detect events faster. -monarch_timeout - How long to wait for the other CPUs to machine check too on a - exception. 0 to disable waiting for other CPUs. - Unit: us - -TBD document entries for AMD threshold interrupt configuration - -For more details about the x86 machine check architecture -see the Intel and AMD architecture manuals from their developer websites. - -For more details about the architecture see -see http://one.firstfloor.org/~andi/mce.pdf diff --git a/Documentation/x86/x86_64/machinecheck.rst b/Documentation/x86/x86_64/machinecheck.rst new file mode 100644 index 000000000000..e189168406fa --- /dev/null +++ b/Documentation/x86/x86_64/machinecheck.rst @@ -0,0 +1,85 @@ +.. SPDX-License-Identifier: GPL-2.0 + +=============================================================== +Configurable sysfs parameters for the x86-64 machine check code +=============================================================== + +Machine checks report internal hardware error conditions detected +by the CPU. Uncorrected errors typically cause a machine check +(often with panic), corrected ones cause a machine check log entry. + +Machine checks are organized in banks (normally associated with +a hardware subsystem) and subevents in a bank. The exact meaning +of the banks and subevent is CPU specific. + +mcelog knows how to decode them. + +When you see the "Machine check errors logged" message in the system +log then mcelog should run to collect and decode machine check entries +from /dev/mcelog. Normally mcelog should be run regularly from a cronjob. + +Each CPU has a directory in /sys/devices/system/machinecheck/machinecheckN +(N = CPU number). + +The directory contains some configurable entries: + +bankNctl + (N bank number) + + 64bit Hex bitmask enabling/disabling specific subevents for bank N + When a bit in the bitmask is zero then the respective + subevent will not be reported. + By default all events are enabled. + Note that BIOS maintain another mask to disable specific events + per bank. This is not visible here + +The following entries appear for each CPU, but they are truly shared +between all CPUs. + +check_interval + How often to poll for corrected machine check errors, in seconds + (Note output is hexadecimal). Default 5 minutes. When the poller + finds MCEs it triggers an exponential speedup (poll more often) on + the polling interval. When the poller stops finding MCEs, it + triggers an exponential backoff (poll less often) on the polling + interval. The check_interval variable is both the initial and + maximum polling interval. 0 means no polling for corrected machine + check errors (but some corrected errors might be still reported + in other ways) + +tolerant + Tolerance level. When a machine check exception occurs for a non + corrected machine check the kernel can take different actions. + Since machine check exceptions can happen any time it is sometimes + risky for the kernel to kill a process because it defies + normal kernel locking rules. The tolerance level configures + how hard the kernel tries to recover even at some risk of + deadlock. Higher tolerant values trade potentially better uptime + with the risk of a crash or even corruption (for tolerant >= 3). + + 0: always panic on uncorrected errors, log corrected errors + 1: panic or SIGBUS on uncorrected errors, log corrected errors + 2: SIGBUS or log uncorrected errors, log corrected errors + 3: never panic or SIGBUS, log all errors (for testing only) + + Default: 1 + + Note this only makes a difference if the CPU allows recovery + from a machine check exception. Current x86 CPUs generally do not. + +trigger + Program to run when a machine check event is detected. + This is an alternative to running mcelog regularly from cron + and allows to detect events faster. +monarch_timeout + How long to wait for the other CPUs to machine check too on a + exception. 0 to disable waiting for other CPUs. + Unit: us + +TBD document entries for AMD threshold interrupt configuration + +For more details about the x86 machine check architecture +see the Intel and AMD architecture manuals from their developer websites. + +For more details about the architecture see +see http://one.firstfloor.org/~andi/mce.pdf -- cgit v1.2.3 From 5d5db1c94f8c412d1c9755bd13194701301b9046 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Mon, 22 Apr 2019 10:28:02 -0300 Subject: docs: sparc: convert to ReST Rename the sparc documentation files to ReST, add an index for them and adjust in order to produce a nice html output via the Sphinx build system. There is an except from a document under oradax dir. It doesn't seem to make much sense to convert this one to ReST, so let's add it as an included document. At its new index.rst, let's add a :orphan: while this is not linked to the main index.rst file, in order to avoid build warnings. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: David S. Miller --- Documentation/sparc/adi.rst | 286 +++++++++++++++++++ Documentation/sparc/adi.txt | 278 ------------------- Documentation/sparc/console.rst | 9 + Documentation/sparc/console.txt | 9 - Documentation/sparc/index.rst | 13 + Documentation/sparc/oradax/oracle-dax.rst | 445 ++++++++++++++++++++++++++++++ Documentation/sparc/oradax/oracle-dax.txt | 429 ---------------------------- drivers/sbus/char/oradax.c | 2 +- 8 files changed, 754 insertions(+), 717 deletions(-) create mode 100644 Documentation/sparc/adi.rst delete mode 100644 Documentation/sparc/adi.txt create mode 100644 Documentation/sparc/console.rst delete mode 100644 Documentation/sparc/console.txt create mode 100644 Documentation/sparc/index.rst create mode 100644 Documentation/sparc/oradax/oracle-dax.rst delete mode 100644 Documentation/sparc/oradax/oracle-dax.txt (limited to 'Documentation') diff --git a/Documentation/sparc/adi.rst b/Documentation/sparc/adi.rst new file mode 100644 index 000000000000..857ad30f9569 --- /dev/null +++ b/Documentation/sparc/adi.rst @@ -0,0 +1,286 @@ +================================ +Application Data Integrity (ADI) +================================ + +SPARC M7 processor adds the Application Data Integrity (ADI) feature. +ADI allows a task to set version tags on any subset of its address +space. Once ADI is enabled and version tags are set for ranges of +address space of a task, the processor will compare the tag in pointers +to memory in these ranges to the version set by the application +previously. Access to memory is granted only if the tag in given pointer +matches the tag set by the application. In case of mismatch, processor +raises an exception. + +Following steps must be taken by a task to enable ADI fully: + +1. Set the user mode PSTATE.mcde bit. This acts as master switch for + the task's entire address space to enable/disable ADI for the task. + +2. Set TTE.mcd bit on any TLB entries that correspond to the range of + addresses ADI is being enabled on. MMU checks the version tag only + on the pages that have TTE.mcd bit set. + +3. Set the version tag for virtual addresses using stxa instruction + and one of the MCD specific ASIs. Each stxa instruction sets the + given tag for one ADI block size number of bytes. This step must + be repeated for entire page to set tags for entire page. + +ADI block size for the platform is provided by the hypervisor to kernel +in machine description tables. Hypervisor also provides the number of +top bits in the virtual address that specify the version tag. Once +version tag has been set for a memory location, the tag is stored in the +physical memory and the same tag must be present in the ADI version tag +bits of the virtual address being presented to the MMU. For example on +SPARC M7 processor, MMU uses bits 63-60 for version tags and ADI block +size is same as cacheline size which is 64 bytes. A task that sets ADI +version to, say 10, on a range of memory, must access that memory using +virtual addresses that contain 0xa in bits 63-60. + +ADI is enabled on a set of pages using mprotect() with PROT_ADI flag. +When ADI is enabled on a set of pages by a task for the first time, +kernel sets the PSTATE.mcde bit fot the task. Version tags for memory +addresses are set with an stxa instruction on the addresses using +ASI_MCD_PRIMARY or ASI_MCD_ST_BLKINIT_PRIMARY. ADI block size is +provided by the hypervisor to the kernel. Kernel returns the value of +ADI block size to userspace using auxiliary vector along with other ADI +info. Following auxiliary vectors are provided by the kernel: + + ============ =========================================== + AT_ADI_BLKSZ ADI block size. This is the granularity and + alignment, in bytes, of ADI versioning. + AT_ADI_NBITS Number of ADI version bits in the VA + ============ =========================================== + + +IMPORTANT NOTES +=============== + +- Version tag values of 0x0 and 0xf are reserved. These values match any + tag in virtual address and never generate a mismatch exception. + +- Version tags are set on virtual addresses from userspace even though + tags are stored in physical memory. Tags are set on a physical page + after it has been allocated to a task and a pte has been created for + it. + +- When a task frees a memory page it had set version tags on, the page + goes back to free page pool. When this page is re-allocated to a task, + kernel clears the page using block initialization ASI which clears the + version tags as well for the page. If a page allocated to a task is + freed and allocated back to the same task, old version tags set by the + task on that page will no longer be present. + +- ADI tag mismatches are not detected for non-faulting loads. + +- Kernel does not set any tags for user pages and it is entirely a + task's responsibility to set any version tags. Kernel does ensure the + version tags are preserved if a page is swapped out to the disk and + swapped back in. It also preserves that version tags if a page is + migrated. + +- ADI works for any size pages. A userspace task need not be aware of + page size when using ADI. It can simply select a virtual address + range, enable ADI on the range using mprotect() and set version tags + for the entire range. mprotect() ensures range is aligned to page size + and is a multiple of page size. + +- ADI tags can only be set on writable memory. For example, ADI tags can + not be set on read-only mappings. + + + +ADI related traps +================= + +With ADI enabled, following new traps may occur: + +Disrupting memory corruption +---------------------------- + + When a store accesses a memory localtion that has TTE.mcd=1, + the task is running with ADI enabled (PSTATE.mcde=1), and the ADI + tag in the address used (bits 63:60) does not match the tag set on + the corresponding cacheline, a memory corruption trap occurs. By + default, it is a disrupting trap and is sent to the hypervisor + first. Hypervisor creates a sun4v error report and sends a + resumable error (TT=0x7e) trap to the kernel. The kernel sends + a SIGSEGV to the task that resulted in this trap with the following + info:: + + siginfo.si_signo = SIGSEGV; + siginfo.errno = 0; + siginfo.si_code = SEGV_ADIDERR; + siginfo.si_addr = addr; /* PC where first mismatch occurred */ + siginfo.si_trapno = 0; + + +Precise memory corruption +------------------------- + + When a store accesses a memory location that has TTE.mcd=1, + the task is running with ADI enabled (PSTATE.mcde=1), and the ADI + tag in the address used (bits 63:60) does not match the tag set on + the corresponding cacheline, a memory corruption trap occurs. If + MCD precise exception is enabled (MCDPERR=1), a precise + exception is sent to the kernel with TT=0x1a. The kernel sends + a SIGSEGV to the task that resulted in this trap with the following + info:: + + siginfo.si_signo = SIGSEGV; + siginfo.errno = 0; + siginfo.si_code = SEGV_ADIPERR; + siginfo.si_addr = addr; /* address that caused trap */ + siginfo.si_trapno = 0; + + NOTE: + ADI tag mismatch on a load always results in precise trap. + + +MCD disabled +------------ + + When a task has not enabled ADI and attempts to set ADI version + on a memory address, processor sends an MCD disabled trap. This + trap is handled by hypervisor first and the hypervisor vectors this + trap through to the kernel as Data Access Exception trap with + fault type set to 0xa (invalid ASI). When this occurs, the kernel + sends the task SIGSEGV signal with following info:: + + siginfo.si_signo = SIGSEGV; + siginfo.errno = 0; + siginfo.si_code = SEGV_ACCADI; + siginfo.si_addr = addr; /* address that caused trap */ + siginfo.si_trapno = 0; + + +Sample program to use ADI +------------------------- + +Following sample program is meant to illustrate how to use the ADI +functionality:: + + #include + #include + #include + #include + #include + #include + #include + #include + + #ifndef AT_ADI_BLKSZ + #define AT_ADI_BLKSZ 48 + #endif + #ifndef AT_ADI_NBITS + #define AT_ADI_NBITS 49 + #endif + + #ifndef PROT_ADI + #define PROT_ADI 0x10 + #endif + + #define BUFFER_SIZE 32*1024*1024UL + + main(int argc, char* argv[], char* envp[]) + { + unsigned long i, mcde, adi_blksz, adi_nbits; + char *shmaddr, *tmp_addr, *end, *veraddr, *clraddr; + int shmid, version; + Elf64_auxv_t *auxv; + + adi_blksz = 0; + + while(*envp++ != NULL); + for (auxv = (Elf64_auxv_t *)envp; auxv->a_type != AT_NULL; auxv++) { + switch (auxv->a_type) { + case AT_ADI_BLKSZ: + adi_blksz = auxv->a_un.a_val; + break; + case AT_ADI_NBITS: + adi_nbits = auxv->a_un.a_val; + break; + } + } + if (adi_blksz == 0) { + fprintf(stderr, "Oops! ADI is not supported\n"); + exit(1); + } + + printf("ADI capabilities:\n"); + printf("\tBlock size = %ld\n", adi_blksz); + printf("\tNumber of bits = %ld\n", adi_nbits); + + if ((shmid = shmget(2, BUFFER_SIZE, + IPC_CREAT | SHM_R | SHM_W)) < 0) { + perror("shmget failed"); + exit(1); + } + + shmaddr = shmat(shmid, NULL, 0); + if (shmaddr == (char *)-1) { + perror("shm attach failed"); + shmctl(shmid, IPC_RMID, NULL); + exit(1); + } + + if (mprotect(shmaddr, BUFFER_SIZE, PROT_READ|PROT_WRITE|PROT_ADI)) { + perror("mprotect failed"); + goto err_out; + } + + /* Set the ADI version tag on the shm segment + */ + version = 10; + tmp_addr = shmaddr; + end = shmaddr + BUFFER_SIZE; + while (tmp_addr < end) { + asm volatile( + "stxa %1, [%0]0x90\n\t" + : + : "r" (tmp_addr), "r" (version)); + tmp_addr += adi_blksz; + } + asm volatile("membar #Sync\n\t"); + + /* Create a versioned address from the normal address by placing + * version tag in the upper adi_nbits bits + */ + tmp_addr = (void *) ((unsigned long)shmaddr << adi_nbits); + tmp_addr = (void *) ((unsigned long)tmp_addr >> adi_nbits); + veraddr = (void *) (((unsigned long)version << (64-adi_nbits)) + | (unsigned long)tmp_addr); + + printf("Starting the writes:\n"); + for (i = 0; i < BUFFER_SIZE; i++) { + veraddr[i] = (char)(i); + if (!(i % (1024 * 1024))) + printf("."); + } + printf("\n"); + + printf("Verifying data..."); + fflush(stdout); + for (i = 0; i < BUFFER_SIZE; i++) + if (veraddr[i] != (char)i) + printf("\nIndex %lu mismatched\n", i); + printf("Done.\n"); + + /* Disable ADI and clean up + */ + if (mprotect(shmaddr, BUFFER_SIZE, PROT_READ|PROT_WRITE)) { + perror("mprotect failed"); + goto err_out; + } + + if (shmdt((const void *)shmaddr) != 0) + perror("Detach failure"); + shmctl(shmid, IPC_RMID, NULL); + + exit(0); + + err_out: + if (shmdt((const void *)shmaddr) != 0) + perror("Detach failure"); + shmctl(shmid, IPC_RMID, NULL); + exit(1); + } diff --git a/Documentation/sparc/adi.txt b/Documentation/sparc/adi.txt deleted file mode 100644 index e1aed155fb89..000000000000 --- a/Documentation/sparc/adi.txt +++ /dev/null @@ -1,278 +0,0 @@ -Application Data Integrity (ADI) -================================ - -SPARC M7 processor adds the Application Data Integrity (ADI) feature. -ADI allows a task to set version tags on any subset of its address -space. Once ADI is enabled and version tags are set for ranges of -address space of a task, the processor will compare the tag in pointers -to memory in these ranges to the version set by the application -previously. Access to memory is granted only if the tag in given pointer -matches the tag set by the application. In case of mismatch, processor -raises an exception. - -Following steps must be taken by a task to enable ADI fully: - -1. Set the user mode PSTATE.mcde bit. This acts as master switch for - the task's entire address space to enable/disable ADI for the task. - -2. Set TTE.mcd bit on any TLB entries that correspond to the range of - addresses ADI is being enabled on. MMU checks the version tag only - on the pages that have TTE.mcd bit set. - -3. Set the version tag for virtual addresses using stxa instruction - and one of the MCD specific ASIs. Each stxa instruction sets the - given tag for one ADI block size number of bytes. This step must - be repeated for entire page to set tags for entire page. - -ADI block size for the platform is provided by the hypervisor to kernel -in machine description tables. Hypervisor also provides the number of -top bits in the virtual address that specify the version tag. Once -version tag has been set for a memory location, the tag is stored in the -physical memory and the same tag must be present in the ADI version tag -bits of the virtual address being presented to the MMU. For example on -SPARC M7 processor, MMU uses bits 63-60 for version tags and ADI block -size is same as cacheline size which is 64 bytes. A task that sets ADI -version to, say 10, on a range of memory, must access that memory using -virtual addresses that contain 0xa in bits 63-60. - -ADI is enabled on a set of pages using mprotect() with PROT_ADI flag. -When ADI is enabled on a set of pages by a task for the first time, -kernel sets the PSTATE.mcde bit fot the task. Version tags for memory -addresses are set with an stxa instruction on the addresses using -ASI_MCD_PRIMARY or ASI_MCD_ST_BLKINIT_PRIMARY. ADI block size is -provided by the hypervisor to the kernel. Kernel returns the value of -ADI block size to userspace using auxiliary vector along with other ADI -info. Following auxiliary vectors are provided by the kernel: - - AT_ADI_BLKSZ ADI block size. This is the granularity and - alignment, in bytes, of ADI versioning. - AT_ADI_NBITS Number of ADI version bits in the VA - - -IMPORTANT NOTES: - -- Version tag values of 0x0 and 0xf are reserved. These values match any - tag in virtual address and never generate a mismatch exception. - -- Version tags are set on virtual addresses from userspace even though - tags are stored in physical memory. Tags are set on a physical page - after it has been allocated to a task and a pte has been created for - it. - -- When a task frees a memory page it had set version tags on, the page - goes back to free page pool. When this page is re-allocated to a task, - kernel clears the page using block initialization ASI which clears the - version tags as well for the page. If a page allocated to a task is - freed and allocated back to the same task, old version tags set by the - task on that page will no longer be present. - -- ADI tag mismatches are not detected for non-faulting loads. - -- Kernel does not set any tags for user pages and it is entirely a - task's responsibility to set any version tags. Kernel does ensure the - version tags are preserved if a page is swapped out to the disk and - swapped back in. It also preserves that version tags if a page is - migrated. - -- ADI works for any size pages. A userspace task need not be aware of - page size when using ADI. It can simply select a virtual address - range, enable ADI on the range using mprotect() and set version tags - for the entire range. mprotect() ensures range is aligned to page size - and is a multiple of page size. - -- ADI tags can only be set on writable memory. For example, ADI tags can - not be set on read-only mappings. - - - -ADI related traps ------------------ - -With ADI enabled, following new traps may occur: - -Disrupting memory corruption - - When a store accesses a memory localtion that has TTE.mcd=1, - the task is running with ADI enabled (PSTATE.mcde=1), and the ADI - tag in the address used (bits 63:60) does not match the tag set on - the corresponding cacheline, a memory corruption trap occurs. By - default, it is a disrupting trap and is sent to the hypervisor - first. Hypervisor creates a sun4v error report and sends a - resumable error (TT=0x7e) trap to the kernel. The kernel sends - a SIGSEGV to the task that resulted in this trap with the following - info: - - siginfo.si_signo = SIGSEGV; - siginfo.errno = 0; - siginfo.si_code = SEGV_ADIDERR; - siginfo.si_addr = addr; /* PC where first mismatch occurred */ - siginfo.si_trapno = 0; - - -Precise memory corruption - - When a store accesses a memory location that has TTE.mcd=1, - the task is running with ADI enabled (PSTATE.mcde=1), and the ADI - tag in the address used (bits 63:60) does not match the tag set on - the corresponding cacheline, a memory corruption trap occurs. If - MCD precise exception is enabled (MCDPERR=1), a precise - exception is sent to the kernel with TT=0x1a. The kernel sends - a SIGSEGV to the task that resulted in this trap with the following - info: - - siginfo.si_signo = SIGSEGV; - siginfo.errno = 0; - siginfo.si_code = SEGV_ADIPERR; - siginfo.si_addr = addr; /* address that caused trap */ - siginfo.si_trapno = 0; - - NOTE: ADI tag mismatch on a load always results in precise trap. - - -MCD disabled - - When a task has not enabled ADI and attempts to set ADI version - on a memory address, processor sends an MCD disabled trap. This - trap is handled by hypervisor first and the hypervisor vectors this - trap through to the kernel as Data Access Exception trap with - fault type set to 0xa (invalid ASI). When this occurs, the kernel - sends the task SIGSEGV signal with following info: - - siginfo.si_signo = SIGSEGV; - siginfo.errno = 0; - siginfo.si_code = SEGV_ACCADI; - siginfo.si_addr = addr; /* address that caused trap */ - siginfo.si_trapno = 0; - - -Sample program to use ADI -------------------------- - -Following sample program is meant to illustrate how to use the ADI -functionality. - -#include -#include -#include -#include -#include -#include -#include -#include - -#ifndef AT_ADI_BLKSZ -#define AT_ADI_BLKSZ 48 -#endif -#ifndef AT_ADI_NBITS -#define AT_ADI_NBITS 49 -#endif - -#ifndef PROT_ADI -#define PROT_ADI 0x10 -#endif - -#define BUFFER_SIZE 32*1024*1024UL - -main(int argc, char* argv[], char* envp[]) -{ - unsigned long i, mcde, adi_blksz, adi_nbits; - char *shmaddr, *tmp_addr, *end, *veraddr, *clraddr; - int shmid, version; - Elf64_auxv_t *auxv; - - adi_blksz = 0; - - while(*envp++ != NULL); - for (auxv = (Elf64_auxv_t *)envp; auxv->a_type != AT_NULL; auxv++) { - switch (auxv->a_type) { - case AT_ADI_BLKSZ: - adi_blksz = auxv->a_un.a_val; - break; - case AT_ADI_NBITS: - adi_nbits = auxv->a_un.a_val; - break; - } - } - if (adi_blksz == 0) { - fprintf(stderr, "Oops! ADI is not supported\n"); - exit(1); - } - - printf("ADI capabilities:\n"); - printf("\tBlock size = %ld\n", adi_blksz); - printf("\tNumber of bits = %ld\n", adi_nbits); - - if ((shmid = shmget(2, BUFFER_SIZE, - IPC_CREAT | SHM_R | SHM_W)) < 0) { - perror("shmget failed"); - exit(1); - } - - shmaddr = shmat(shmid, NULL, 0); - if (shmaddr == (char *)-1) { - perror("shm attach failed"); - shmctl(shmid, IPC_RMID, NULL); - exit(1); - } - - if (mprotect(shmaddr, BUFFER_SIZE, PROT_READ|PROT_WRITE|PROT_ADI)) { - perror("mprotect failed"); - goto err_out; - } - - /* Set the ADI version tag on the shm segment - */ - version = 10; - tmp_addr = shmaddr; - end = shmaddr + BUFFER_SIZE; - while (tmp_addr < end) { - asm volatile( - "stxa %1, [%0]0x90\n\t" - : - : "r" (tmp_addr), "r" (version)); - tmp_addr += adi_blksz; - } - asm volatile("membar #Sync\n\t"); - - /* Create a versioned address from the normal address by placing - * version tag in the upper adi_nbits bits - */ - tmp_addr = (void *) ((unsigned long)shmaddr << adi_nbits); - tmp_addr = (void *) ((unsigned long)tmp_addr >> adi_nbits); - veraddr = (void *) (((unsigned long)version << (64-adi_nbits)) - | (unsigned long)tmp_addr); - - printf("Starting the writes:\n"); - for (i = 0; i < BUFFER_SIZE; i++) { - veraddr[i] = (char)(i); - if (!(i % (1024 * 1024))) - printf("."); - } - printf("\n"); - - printf("Verifying data..."); - fflush(stdout); - for (i = 0; i < BUFFER_SIZE; i++) - if (veraddr[i] != (char)i) - printf("\nIndex %lu mismatched\n", i); - printf("Done.\n"); - - /* Disable ADI and clean up - */ - if (mprotect(shmaddr, BUFFER_SIZE, PROT_READ|PROT_WRITE)) { - perror("mprotect failed"); - goto err_out; - } - - if (shmdt((const void *)shmaddr) != 0) - perror("Detach failure"); - shmctl(shmid, IPC_RMID, NULL); - - exit(0); - -err_out: - if (shmdt((const void *)shmaddr) != 0) - perror("Detach failure"); - shmctl(shmid, IPC_RMID, NULL); - exit(1); -} diff --git a/Documentation/sparc/console.rst b/Documentation/sparc/console.rst new file mode 100644 index 000000000000..73132db83ece --- /dev/null +++ b/Documentation/sparc/console.rst @@ -0,0 +1,9 @@ +Steps for sending 'break' on sunhv console +========================================== + +On Baremetal: + 1. press Esc + 'B' + +On LDOM: + 1. press Ctrl + ']' + 2. telnet> send break diff --git a/Documentation/sparc/console.txt b/Documentation/sparc/console.txt deleted file mode 100644 index 5aa735a44e02..000000000000 --- a/Documentation/sparc/console.txt +++ /dev/null @@ -1,9 +0,0 @@ -Steps for sending 'break' on sunhv console: -=========================================== - -On Baremetal: - 1. press Esc + 'B' - -On LDOM: - 1. press Ctrl + ']' - 2. telnet> send break diff --git a/Documentation/sparc/index.rst b/Documentation/sparc/index.rst new file mode 100644 index 000000000000..91f7d6643dd5 --- /dev/null +++ b/Documentation/sparc/index.rst @@ -0,0 +1,13 @@ +:orphan: + +================== +Sparc Architecture +================== + +.. toctree:: + :maxdepth: 1 + + console + adi + + oradax/oracle-dax diff --git a/Documentation/sparc/oradax/oracle-dax.rst b/Documentation/sparc/oradax/oracle-dax.rst new file mode 100644 index 000000000000..d1e14d572918 --- /dev/null +++ b/Documentation/sparc/oradax/oracle-dax.rst @@ -0,0 +1,445 @@ +======================================= +Oracle Data Analytics Accelerator (DAX) +======================================= + +DAX is a coprocessor which resides on the SPARC M7 (DAX1) and M8 +(DAX2) processor chips, and has direct access to the CPU's L3 caches +as well as physical memory. It can perform several operations on data +streams with various input and output formats. A driver provides a +transport mechanism and has limited knowledge of the various opcodes +and data formats. A user space library provides high level services +and translates these into low level commands which are then passed +into the driver and subsequently the Hypervisor and the coprocessor. +The library is the recommended way for applications to use the +coprocessor, and the driver interface is not intended for general use. +This document describes the general flow of the driver, its +structures, and its programmatic interface. It also provides example +code sufficient to write user or kernel applications that use DAX +functionality. + +The user library is open source and available at: + + https://oss.oracle.com/git/gitweb.cgi?p=libdax.git + +The Hypervisor interface to the coprocessor is described in detail in +the accompanying document, dax-hv-api.txt, which is a plain text +excerpt of the (Oracle internal) "UltraSPARC Virtual Machine +Specification" version 3.0.20+15, dated 2017-09-25. + + +High Level Overview +=================== + +A coprocessor request is described by a Command Control Block +(CCB). The CCB contains an opcode and various parameters. The opcode +specifies what operation is to be done, and the parameters specify +options, flags, sizes, and addresses. The CCB (or an array of CCBs) +is passed to the Hypervisor, which handles queueing and scheduling of +requests to the available coprocessor execution units. A status code +returned indicates if the request was submitted successfully or if +there was an error. One of the addresses given in each CCB is a +pointer to a "completion area", which is a 128 byte memory block that +is written by the coprocessor to provide execution status. No +interrupt is generated upon completion; the completion area must be +polled by software to find out when a transaction has finished, but +the M7 and later processors provide a mechanism to pause the virtual +processor until the completion status has been updated by the +coprocessor. This is done using the monitored load and mwait +instructions, which are described in more detail later. The DAX +coprocessor was designed so that after a request is submitted, the +kernel is no longer involved in the processing of it. The polling is +done at the user level, which results in almost zero latency between +completion of a request and resumption of execution of the requesting +thread. + + +Addressing Memory +================= + +The kernel does not have access to physical memory in the Sun4v +architecture, as there is an additional level of memory virtualization +present. This intermediate level is called "real" memory, and the +kernel treats this as if it were physical. The Hypervisor handles the +translations between real memory and physical so that each logical +domain (LDOM) can have a partition of physical memory that is isolated +from that of other LDOMs. When the kernel sets up a virtual mapping, +it specifies a virtual address and the real address to which it should +be mapped. + +The DAX coprocessor can only operate on physical memory, so before a +request can be fed to the coprocessor, all the addresses in a CCB must +be converted into physical addresses. The kernel cannot do this since +it has no visibility into physical addresses. So a CCB may contain +either the virtual or real addresses of the buffers or a combination +of them. An "address type" field is available for each address that +may be given in the CCB. In all cases, the Hypervisor will translate +all the addresses to physical before dispatching to hardware. Address +translations are performed using the context of the process initiating +the request. + + +The Driver API +============== + +An application makes requests to the driver via the write() system +call, and gets results (if any) via read(). The completion areas are +made accessible via mmap(), and are read-only for the application. + +The request may either be an immediate command or an array of CCBs to +be submitted to the hardware. + +Each open instance of the device is exclusive to the thread that +opened it, and must be used by that thread for all subsequent +operations. The driver open function creates a new context for the +thread and initializes it for use. This context contains pointers and +values used internally by the driver to keep track of submitted +requests. The completion area buffer is also allocated, and this is +large enough to contain the completion areas for many concurrent +requests. When the device is closed, any outstanding transactions are +flushed and the context is cleaned up. + +On a DAX1 system (M7), the device will be called "oradax1", while on a +DAX2 system (M8) it will be "oradax2". If an application requires one +or the other, it should simply attempt to open the appropriate +device. Only one of the devices will exist on any given system, so the +name can be used to determine what the platform supports. + +The immediate commands are CCB_DEQUEUE, CCB_KILL, and CCB_INFO. For +all of these, success is indicated by a return value from write() +equal to the number of bytes given in the call. Otherwise -1 is +returned and errno is set. + +CCB_DEQUEUE +----------- + +Tells the driver to clean up resources associated with past +requests. Since no interrupt is generated upon the completion of a +request, the driver must be told when it may reclaim resources. No +further status information is returned, so the user should not +subsequently call read(). + +CCB_KILL +-------- + +Kills a CCB during execution. The CCB is guaranteed to not continue +executing once this call returns successfully. On success, read() must +be called to retrieve the result of the action. + +CCB_INFO +-------- + +Retrieves information about a currently executing CCB. Note that some +Hypervisors might return 'notfound' when the CCB is in 'inprogress' +state. To ensure a CCB in the 'notfound' state will never be executed, +CCB_KILL must be invoked on that CCB. Upon success, read() must be +called to retrieve the details of the action. + +Submission of an array of CCBs for execution +--------------------------------------------- + +A write() whose length is a multiple of the CCB size is treated as a +submit operation. The file offset is treated as the index of the +completion area to use, and may be set via lseek() or using the +pwrite() system call. If -1 is returned then errno is set to indicate +the error. Otherwise, the return value is the length of the array that +was actually accepted by the coprocessor. If the accepted length is +equal to the requested length, then the submission was completely +successful and there is no further status needed; hence, the user +should not subsequently call read(). Partial acceptance of the CCB +array is indicated by a return value less than the requested length, +and read() must be called to retrieve further status information. The +status will reflect the error caused by the first CCB that was not +accepted, and status_data will provide additional data in some cases. + +MMAP +---- + +The mmap() function provides access to the completion area allocated +in the driver. Note that the completion area is not writeable by the +user process, and the mmap call must not specify PROT_WRITE. + + +Completion of a Request +======================= + +The first byte in each completion area is the command status which is +updated by the coprocessor hardware. Software may take advantage of +new M7/M8 processor capabilities to efficiently poll this status byte. +First, a "monitored load" is achieved via a Load from Alternate Space +(ldxa, lduba, etc.) with ASI 0x84 (ASI_MONITOR_PRIMARY). Second, a +"monitored wait" is achieved via the mwait instruction (a write to +%asr28). This instruction is like pause in that it suspends execution +of the virtual processor for the given number of nanoseconds, but in +addition will terminate early when one of several events occur. If the +block of data containing the monitored location is modified, then the +mwait terminates. This causes software to resume execution immediately +(without a context switch or kernel to user transition) after a +transaction completes. Thus the latency between transaction completion +and resumption of execution may be just a few nanoseconds. + + +Application Life Cycle of a DAX Submission +========================================== + + - open dax device + - call mmap() to get the completion area address + - allocate a CCB and fill in the opcode, flags, parameters, addresses, etc. + - submit CCB via write() or pwrite() + - go into a loop executing monitored load + monitored wait and + terminate when the command status indicates the request is complete + (CCB_KILL or CCB_INFO may be used any time as necessary) + - perform a CCB_DEQUEUE + - call munmap() for completion area + - close the dax device + + +Memory Constraints +================== + +The DAX hardware operates only on physical addresses. Therefore, it is +not aware of virtual memory mappings and the discontiguities that may +exist in the physical memory that a virtual buffer maps to. There is +no I/O TLB or any scatter/gather mechanism. All buffers, whether input +or output, must reside in a physically contiguous region of memory. + +The Hypervisor translates all addresses within a CCB to physical +before handing off the CCB to DAX. The Hypervisor determines the +virtual page size for each virtual address given, and uses this to +program a size limit for each address. This prevents the coprocessor +from reading or writing beyond the bound of the virtual page, even +though it is accessing physical memory directly. A simpler way of +saying this is that a DAX operation will never "cross" a virtual page +boundary. If an 8k virtual page is used, then the data is strictly +limited to 8k. If a user's buffer is larger than 8k, then a larger +page size must be used, or the transaction size will be truncated to +8k. + +Huge pages. A user may allocate huge pages using standard interfaces. +Memory buffers residing on huge pages may be used to achieve much +larger DAX transaction sizes, but the rules must still be followed, +and no transaction will cross a page boundary, even a huge page. A +major caveat is that Linux on Sparc presents 8Mb as one of the huge +page sizes. Sparc does not actually provide a 8Mb hardware page size, +and this size is synthesized by pasting together two 4Mb pages. The +reasons for this are historical, and it creates an issue because only +half of this 8Mb page can actually be used for any given buffer in a +DAX request, and it must be either the first half or the second half; +it cannot be a 4Mb chunk in the middle, since that crosses a +(hardware) page boundary. Note that this entire issue may be hidden by +higher level libraries. + + +CCB Structure +------------- +A CCB is an array of 8 64-bit words. Several of these words provide +command opcodes, parameters, flags, etc., and the rest are addresses +for the completion area, output buffer, and various inputs:: + + struct ccb { + u64 control; + u64 completion; + u64 input0; + u64 access; + u64 input1; + u64 op_data; + u64 output; + u64 table; + }; + +See libdax/common/sys/dax1/dax1_ccb.h for a detailed description of +each of these fields, and see dax-hv-api.txt for a complete description +of the Hypervisor API available to the guest OS (ie, Linux kernel). + +The first word (control) is examined by the driver for the following: + - CCB version, which must be consistent with hardware version + - Opcode, which must be one of the documented allowable commands + - Address types, which must be set to "virtual" for all the addresses + given by the user, thereby ensuring that the application can + only access memory that it owns + + +Example Code +============ + +The DAX is accessible to both user and kernel code. The kernel code +can make hypercalls directly while the user code must use wrappers +provided by the driver. The setup of the CCB is nearly identical for +both; the only difference is in preparation of the completion area. An +example of user code is given now, with kernel code afterwards. + +In order to program using the driver API, the file +arch/sparc/include/uapi/asm/oradax.h must be included. + +First, the proper device must be opened. For M7 it will be +/dev/oradax1 and for M8 it will be /dev/oradax2. The simplest +procedure is to attempt to open both, as only one will succeed:: + + fd = open("/dev/oradax1", O_RDWR); + if (fd < 0) + fd = open("/dev/oradax2", O_RDWR); + if (fd < 0) + /* No DAX found */ + +Next, the completion area must be mapped:: + + completion_area = mmap(NULL, DAX_MMAP_LEN, PROT_READ, MAP_SHARED, fd, 0); + +All input and output buffers must be fully contained in one hardware +page, since as explained above, the DAX is strictly constrained by +virtual page boundaries. In addition, the output buffer must be +64-byte aligned and its size must be a multiple of 64 bytes because +the coprocessor writes in units of cache lines. + +This example demonstrates the DAX Scan command, which takes as input a +vector and a match value, and produces a bitmap as the output. For +each input element that matches the value, the corresponding bit is +set in the output. + +In this example, the input vector consists of a series of single bits, +and the match value is 0. So each 0 bit in the input will produce a 1 +in the output, and vice versa, which produces an output bitmap which +is the input bitmap inverted. + +For details of all the parameters and bits used in this CCB, please +refer to section 36.2.1.3 of the DAX Hypervisor API document, which +describes the Scan command in detail:: + + ccb->control = /* Table 36.1, CCB Header Format */ + (2L << 48) /* command = Scan Value */ + | (3L << 40) /* output address type = primary virtual */ + | (3L << 34) /* primary input address type = primary virtual */ + /* Section 36.2.1, Query CCB Command Formats */ + | (1 << 28) /* 36.2.1.1.1 primary input format = fixed width bit packed */ + | (0 << 23) /* 36.2.1.1.2 primary input element size = 0 (1 bit) */ + | (8 << 10) /* 36.2.1.1.6 output format = bit vector */ + | (0 << 5) /* 36.2.1.3 First scan criteria size = 0 (1 byte) */ + | (31 << 0); /* 36.2.1.3 Disable second scan criteria */ + + ccb->completion = 0; /* Completion area address, to be filled in by driver */ + + ccb->input0 = (unsigned long) input; /* primary input address */ + + ccb->access = /* Section 36.2.1.2, Data Access Control */ + (2 << 24) /* Primary input length format = bits */ + | (nbits - 1); /* number of bits in primary input stream, minus 1 */ + + ccb->input1 = 0; /* secondary input address, unused */ + + ccb->op_data = 0; /* scan criteria (value to be matched) */ + + ccb->output = (unsigned long) output; /* output address */ + + ccb->table = 0; /* table address, unused */ + +The CCB submission is a write() or pwrite() system call to the +driver. If the call fails, then a read() must be used to retrieve the +status:: + + if (pwrite(fd, ccb, 64, 0) != 64) { + struct ccb_exec_result status; + read(fd, &status, sizeof(status)); + /* bail out */ + } + +After a successful submission of the CCB, the completion area may be +polled to determine when the DAX is finished. Detailed information on +the contents of the completion area can be found in section 36.2.2 of +the DAX HV API document:: + + while (1) { + /* Monitored Load */ + __asm__ __volatile__("lduba [%1] 0x84, %0\n" + : "=r" (status) + : "r" (completion_area)); + + if (status) /* 0 indicates command in progress */ + break; + + /* MWAIT */ + __asm__ __volatile__("wr %%g0, 1000, %%asr28\n" ::); /* 1000 ns */ + } + +A completion area status of 1 indicates successful completion of the +CCB and validity of the output bitmap, which may be used immediately. +All other non-zero values indicate error conditions which are +described in section 36.2.2:: + + if (completion_area[0] != 1) { /* section 36.2.2, 1 = command ran and succeeded */ + /* completion_area[0] contains the completion status */ + /* completion_area[1] contains an error code, see 36.2.2 */ + } + +After the completion area has been processed, the driver must be +notified that it can release any resources associated with the +request. This is done via the dequeue operation:: + + struct dax_command cmd; + cmd.command = CCB_DEQUEUE; + if (write(fd, &cmd, sizeof(cmd)) != sizeof(cmd)) { + /* bail out */ + } + +Finally, normal program cleanup should be done, i.e., unmapping +completion area, closing the dax device, freeing memory etc. + +Kernel example +-------------- + +The only difference in using the DAX in kernel code is the treatment +of the completion area. Unlike user applications which mmap the +completion area allocated by the driver, kernel code must allocate its +own memory to use for the completion area, and this address and its +type must be given in the CCB:: + + ccb->control |= /* Table 36.1, CCB Header Format */ + (3L << 32); /* completion area address type = primary virtual */ + + ccb->completion = (unsigned long) completion_area; /* Completion area address */ + +The dax submit hypercall is made directly. The flags used in the +ccb_submit call are documented in the DAX HV API in section 36.3.1/ + +:: + + #include + + hv_rv = sun4v_ccb_submit((unsigned long)ccb, 64, + HV_CCB_QUERY_CMD | + HV_CCB_ARG0_PRIVILEGED | HV_CCB_ARG0_TYPE_PRIMARY | + HV_CCB_VA_PRIVILEGED, + 0, &bytes_accepted, &status_data); + + if (hv_rv != HV_EOK) { + /* hv_rv is an error code, status_data contains */ + /* potential additional status, see 36.3.1.1 */ + } + +After the submission, the completion area polling code is identical to +that in user land:: + + while (1) { + /* Monitored Load */ + __asm__ __volatile__("lduba [%1] 0x84, %0\n" + : "=r" (status) + : "r" (completion_area)); + + if (status) /* 0 indicates command in progress */ + break; + + /* MWAIT */ + __asm__ __volatile__("wr %%g0, 1000, %%asr28\n" ::); /* 1000 ns */ + } + + if (completion_area[0] != 1) { /* section 36.2.2, 1 = command ran and succeeded */ + /* completion_area[0] contains the completion status */ + /* completion_area[1] contains an error code, see 36.2.2 */ + } + +The output bitmap is ready for consumption immediately after the +completion status indicates success. + +Excer[t from UltraSPARC Virtual Machine Specification +===================================================== + + .. include:: dax-hv-api.txt + :literal: diff --git a/Documentation/sparc/oradax/oracle-dax.txt b/Documentation/sparc/oradax/oracle-dax.txt deleted file mode 100644 index 9d53ac93286f..000000000000 --- a/Documentation/sparc/oradax/oracle-dax.txt +++ /dev/null @@ -1,429 +0,0 @@ -Oracle Data Analytics Accelerator (DAX) ---------------------------------------- - -DAX is a coprocessor which resides on the SPARC M7 (DAX1) and M8 -(DAX2) processor chips, and has direct access to the CPU's L3 caches -as well as physical memory. It can perform several operations on data -streams with various input and output formats. A driver provides a -transport mechanism and has limited knowledge of the various opcodes -and data formats. A user space library provides high level services -and translates these into low level commands which are then passed -into the driver and subsequently the Hypervisor and the coprocessor. -The library is the recommended way for applications to use the -coprocessor, and the driver interface is not intended for general use. -This document describes the general flow of the driver, its -structures, and its programmatic interface. It also provides example -code sufficient to write user or kernel applications that use DAX -functionality. - -The user library is open source and available at: - https://oss.oracle.com/git/gitweb.cgi?p=libdax.git - -The Hypervisor interface to the coprocessor is described in detail in -the accompanying document, dax-hv-api.txt, which is a plain text -excerpt of the (Oracle internal) "UltraSPARC Virtual Machine -Specification" version 3.0.20+15, dated 2017-09-25. - - -High Level Overview -------------------- - -A coprocessor request is described by a Command Control Block -(CCB). The CCB contains an opcode and various parameters. The opcode -specifies what operation is to be done, and the parameters specify -options, flags, sizes, and addresses. The CCB (or an array of CCBs) -is passed to the Hypervisor, which handles queueing and scheduling of -requests to the available coprocessor execution units. A status code -returned indicates if the request was submitted successfully or if -there was an error. One of the addresses given in each CCB is a -pointer to a "completion area", which is a 128 byte memory block that -is written by the coprocessor to provide execution status. No -interrupt is generated upon completion; the completion area must be -polled by software to find out when a transaction has finished, but -the M7 and later processors provide a mechanism to pause the virtual -processor until the completion status has been updated by the -coprocessor. This is done using the monitored load and mwait -instructions, which are described in more detail later. The DAX -coprocessor was designed so that after a request is submitted, the -kernel is no longer involved in the processing of it. The polling is -done at the user level, which results in almost zero latency between -completion of a request and resumption of execution of the requesting -thread. - - -Addressing Memory ------------------ - -The kernel does not have access to physical memory in the Sun4v -architecture, as there is an additional level of memory virtualization -present. This intermediate level is called "real" memory, and the -kernel treats this as if it were physical. The Hypervisor handles the -translations between real memory and physical so that each logical -domain (LDOM) can have a partition of physical memory that is isolated -from that of other LDOMs. When the kernel sets up a virtual mapping, -it specifies a virtual address and the real address to which it should -be mapped. - -The DAX coprocessor can only operate on physical memory, so before a -request can be fed to the coprocessor, all the addresses in a CCB must -be converted into physical addresses. The kernel cannot do this since -it has no visibility into physical addresses. So a CCB may contain -either the virtual or real addresses of the buffers or a combination -of them. An "address type" field is available for each address that -may be given in the CCB. In all cases, the Hypervisor will translate -all the addresses to physical before dispatching to hardware. Address -translations are performed using the context of the process initiating -the request. - - -The Driver API --------------- - -An application makes requests to the driver via the write() system -call, and gets results (if any) via read(). The completion areas are -made accessible via mmap(), and are read-only for the application. - -The request may either be an immediate command or an array of CCBs to -be submitted to the hardware. - -Each open instance of the device is exclusive to the thread that -opened it, and must be used by that thread for all subsequent -operations. The driver open function creates a new context for the -thread and initializes it for use. This context contains pointers and -values used internally by the driver to keep track of submitted -requests. The completion area buffer is also allocated, and this is -large enough to contain the completion areas for many concurrent -requests. When the device is closed, any outstanding transactions are -flushed and the context is cleaned up. - -On a DAX1 system (M7), the device will be called "oradax1", while on a -DAX2 system (M8) it will be "oradax2". If an application requires one -or the other, it should simply attempt to open the appropriate -device. Only one of the devices will exist on any given system, so the -name can be used to determine what the platform supports. - -The immediate commands are CCB_DEQUEUE, CCB_KILL, and CCB_INFO. For -all of these, success is indicated by a return value from write() -equal to the number of bytes given in the call. Otherwise -1 is -returned and errno is set. - -CCB_DEQUEUE - -Tells the driver to clean up resources associated with past -requests. Since no interrupt is generated upon the completion of a -request, the driver must be told when it may reclaim resources. No -further status information is returned, so the user should not -subsequently call read(). - -CCB_KILL - -Kills a CCB during execution. The CCB is guaranteed to not continue -executing once this call returns successfully. On success, read() must -be called to retrieve the result of the action. - -CCB_INFO - -Retrieves information about a currently executing CCB. Note that some -Hypervisors might return 'notfound' when the CCB is in 'inprogress' -state. To ensure a CCB in the 'notfound' state will never be executed, -CCB_KILL must be invoked on that CCB. Upon success, read() must be -called to retrieve the details of the action. - -Submission of an array of CCBs for execution - -A write() whose length is a multiple of the CCB size is treated as a -submit operation. The file offset is treated as the index of the -completion area to use, and may be set via lseek() or using the -pwrite() system call. If -1 is returned then errno is set to indicate -the error. Otherwise, the return value is the length of the array that -was actually accepted by the coprocessor. If the accepted length is -equal to the requested length, then the submission was completely -successful and there is no further status needed; hence, the user -should not subsequently call read(). Partial acceptance of the CCB -array is indicated by a return value less than the requested length, -and read() must be called to retrieve further status information. The -status will reflect the error caused by the first CCB that was not -accepted, and status_data will provide additional data in some cases. - -MMAP - -The mmap() function provides access to the completion area allocated -in the driver. Note that the completion area is not writeable by the -user process, and the mmap call must not specify PROT_WRITE. - - -Completion of a Request ------------------------ - -The first byte in each completion area is the command status which is -updated by the coprocessor hardware. Software may take advantage of -new M7/M8 processor capabilities to efficiently poll this status byte. -First, a "monitored load" is achieved via a Load from Alternate Space -(ldxa, lduba, etc.) with ASI 0x84 (ASI_MONITOR_PRIMARY). Second, a -"monitored wait" is achieved via the mwait instruction (a write to -%asr28). This instruction is like pause in that it suspends execution -of the virtual processor for the given number of nanoseconds, but in -addition will terminate early when one of several events occur. If the -block of data containing the monitored location is modified, then the -mwait terminates. This causes software to resume execution immediately -(without a context switch or kernel to user transition) after a -transaction completes. Thus the latency between transaction completion -and resumption of execution may be just a few nanoseconds. - - -Application Life Cycle of a DAX Submission ------------------------------------------- - - - open dax device - - call mmap() to get the completion area address - - allocate a CCB and fill in the opcode, flags, parameters, addresses, etc. - - submit CCB via write() or pwrite() - - go into a loop executing monitored load + monitored wait and - terminate when the command status indicates the request is complete - (CCB_KILL or CCB_INFO may be used any time as necessary) - - perform a CCB_DEQUEUE - - call munmap() for completion area - - close the dax device - - -Memory Constraints ------------------- - -The DAX hardware operates only on physical addresses. Therefore, it is -not aware of virtual memory mappings and the discontiguities that may -exist in the physical memory that a virtual buffer maps to. There is -no I/O TLB or any scatter/gather mechanism. All buffers, whether input -or output, must reside in a physically contiguous region of memory. - -The Hypervisor translates all addresses within a CCB to physical -before handing off the CCB to DAX. The Hypervisor determines the -virtual page size for each virtual address given, and uses this to -program a size limit for each address. This prevents the coprocessor -from reading or writing beyond the bound of the virtual page, even -though it is accessing physical memory directly. A simpler way of -saying this is that a DAX operation will never "cross" a virtual page -boundary. If an 8k virtual page is used, then the data is strictly -limited to 8k. If a user's buffer is larger than 8k, then a larger -page size must be used, or the transaction size will be truncated to -8k. - -Huge pages. A user may allocate huge pages using standard interfaces. -Memory buffers residing on huge pages may be used to achieve much -larger DAX transaction sizes, but the rules must still be followed, -and no transaction will cross a page boundary, even a huge page. A -major caveat is that Linux on Sparc presents 8Mb as one of the huge -page sizes. Sparc does not actually provide a 8Mb hardware page size, -and this size is synthesized by pasting together two 4Mb pages. The -reasons for this are historical, and it creates an issue because only -half of this 8Mb page can actually be used for any given buffer in a -DAX request, and it must be either the first half or the second half; -it cannot be a 4Mb chunk in the middle, since that crosses a -(hardware) page boundary. Note that this entire issue may be hidden by -higher level libraries. - - -CCB Structure -------------- -A CCB is an array of 8 64-bit words. Several of these words provide -command opcodes, parameters, flags, etc., and the rest are addresses -for the completion area, output buffer, and various inputs: - - struct ccb { - u64 control; - u64 completion; - u64 input0; - u64 access; - u64 input1; - u64 op_data; - u64 output; - u64 table; - }; - -See libdax/common/sys/dax1/dax1_ccb.h for a detailed description of -each of these fields, and see dax-hv-api.txt for a complete description -of the Hypervisor API available to the guest OS (ie, Linux kernel). - -The first word (control) is examined by the driver for the following: - - CCB version, which must be consistent with hardware version - - Opcode, which must be one of the documented allowable commands - - Address types, which must be set to "virtual" for all the addresses - given by the user, thereby ensuring that the application can - only access memory that it owns - - -Example Code ------------- - -The DAX is accessible to both user and kernel code. The kernel code -can make hypercalls directly while the user code must use wrappers -provided by the driver. The setup of the CCB is nearly identical for -both; the only difference is in preparation of the completion area. An -example of user code is given now, with kernel code afterwards. - -In order to program using the driver API, the file -arch/sparc/include/uapi/asm/oradax.h must be included. - -First, the proper device must be opened. For M7 it will be -/dev/oradax1 and for M8 it will be /dev/oradax2. The simplest -procedure is to attempt to open both, as only one will succeed: - - fd = open("/dev/oradax1", O_RDWR); - if (fd < 0) - fd = open("/dev/oradax2", O_RDWR); - if (fd < 0) - /* No DAX found */ - -Next, the completion area must be mapped: - - completion_area = mmap(NULL, DAX_MMAP_LEN, PROT_READ, MAP_SHARED, fd, 0); - -All input and output buffers must be fully contained in one hardware -page, since as explained above, the DAX is strictly constrained by -virtual page boundaries. In addition, the output buffer must be -64-byte aligned and its size must be a multiple of 64 bytes because -the coprocessor writes in units of cache lines. - -This example demonstrates the DAX Scan command, which takes as input a -vector and a match value, and produces a bitmap as the output. For -each input element that matches the value, the corresponding bit is -set in the output. - -In this example, the input vector consists of a series of single bits, -and the match value is 0. So each 0 bit in the input will produce a 1 -in the output, and vice versa, which produces an output bitmap which -is the input bitmap inverted. - -For details of all the parameters and bits used in this CCB, please -refer to section 36.2.1.3 of the DAX Hypervisor API document, which -describes the Scan command in detail. - - ccb->control = /* Table 36.1, CCB Header Format */ - (2L << 48) /* command = Scan Value */ - | (3L << 40) /* output address type = primary virtual */ - | (3L << 34) /* primary input address type = primary virtual */ - /* Section 36.2.1, Query CCB Command Formats */ - | (1 << 28) /* 36.2.1.1.1 primary input format = fixed width bit packed */ - | (0 << 23) /* 36.2.1.1.2 primary input element size = 0 (1 bit) */ - | (8 << 10) /* 36.2.1.1.6 output format = bit vector */ - | (0 << 5) /* 36.2.1.3 First scan criteria size = 0 (1 byte) */ - | (31 << 0); /* 36.2.1.3 Disable second scan criteria */ - - ccb->completion = 0; /* Completion area address, to be filled in by driver */ - - ccb->input0 = (unsigned long) input; /* primary input address */ - - ccb->access = /* Section 36.2.1.2, Data Access Control */ - (2 << 24) /* Primary input length format = bits */ - | (nbits - 1); /* number of bits in primary input stream, minus 1 */ - - ccb->input1 = 0; /* secondary input address, unused */ - - ccb->op_data = 0; /* scan criteria (value to be matched) */ - - ccb->output = (unsigned long) output; /* output address */ - - ccb->table = 0; /* table address, unused */ - -The CCB submission is a write() or pwrite() system call to the -driver. If the call fails, then a read() must be used to retrieve the -status: - - if (pwrite(fd, ccb, 64, 0) != 64) { - struct ccb_exec_result status; - read(fd, &status, sizeof(status)); - /* bail out */ - } - -After a successful submission of the CCB, the completion area may be -polled to determine when the DAX is finished. Detailed information on -the contents of the completion area can be found in section 36.2.2 of -the DAX HV API document. - - while (1) { - /* Monitored Load */ - __asm__ __volatile__("lduba [%1] 0x84, %0\n" - : "=r" (status) - : "r" (completion_area)); - - if (status) /* 0 indicates command in progress */ - break; - - /* MWAIT */ - __asm__ __volatile__("wr %%g0, 1000, %%asr28\n" ::); /* 1000 ns */ - } - -A completion area status of 1 indicates successful completion of the -CCB and validity of the output bitmap, which may be used immediately. -All other non-zero values indicate error conditions which are -described in section 36.2.2. - - if (completion_area[0] != 1) { /* section 36.2.2, 1 = command ran and succeeded */ - /* completion_area[0] contains the completion status */ - /* completion_area[1] contains an error code, see 36.2.2 */ - } - -After the completion area has been processed, the driver must be -notified that it can release any resources associated with the -request. This is done via the dequeue operation: - - struct dax_command cmd; - cmd.command = CCB_DEQUEUE; - if (write(fd, &cmd, sizeof(cmd)) != sizeof(cmd)) { - /* bail out */ - } - -Finally, normal program cleanup should be done, i.e., unmapping -completion area, closing the dax device, freeing memory etc. - -[Kernel example] - -The only difference in using the DAX in kernel code is the treatment -of the completion area. Unlike user applications which mmap the -completion area allocated by the driver, kernel code must allocate its -own memory to use for the completion area, and this address and its -type must be given in the CCB: - - ccb->control |= /* Table 36.1, CCB Header Format */ - (3L << 32); /* completion area address type = primary virtual */ - - ccb->completion = (unsigned long) completion_area; /* Completion area address */ - -The dax submit hypercall is made directly. The flags used in the -ccb_submit call are documented in the DAX HV API in section 36.3.1. - -#include - - hv_rv = sun4v_ccb_submit((unsigned long)ccb, 64, - HV_CCB_QUERY_CMD | - HV_CCB_ARG0_PRIVILEGED | HV_CCB_ARG0_TYPE_PRIMARY | - HV_CCB_VA_PRIVILEGED, - 0, &bytes_accepted, &status_data); - - if (hv_rv != HV_EOK) { - /* hv_rv is an error code, status_data contains */ - /* potential additional status, see 36.3.1.1 */ - } - -After the submission, the completion area polling code is identical to -that in user land: - - while (1) { - /* Monitored Load */ - __asm__ __volatile__("lduba [%1] 0x84, %0\n" - : "=r" (status) - : "r" (completion_area)); - - if (status) /* 0 indicates command in progress */ - break; - - /* MWAIT */ - __asm__ __volatile__("wr %%g0, 1000, %%asr28\n" ::); /* 1000 ns */ - } - - if (completion_area[0] != 1) { /* section 36.2.2, 1 = command ran and succeeded */ - /* completion_area[0] contains the completion status */ - /* completion_area[1] contains an error code, see 36.2.2 */ - } - -The output bitmap is ready for consumption immediately after the -completion status indicates success. diff --git a/drivers/sbus/char/oradax.c b/drivers/sbus/char/oradax.c index 6516bc3cb58b..acd9ba40eabe 100644 --- a/drivers/sbus/char/oradax.c +++ b/drivers/sbus/char/oradax.c @@ -30,7 +30,7 @@ * the recommended way for applications to use the coprocessor, and * the driver interface is not intended for general use. * - * See Documentation/sparc/oradax/oracle-dax.txt for more details. + * See Documentation/sparc/oradax/oracle-dax.rst for more details. */ #include -- cgit v1.2.3 From 004c35cd8e0c81e0b4a34f0ad3ab0c4937ccaaea Mon Sep 17 00:00:00 2001 From: Marek Behun Date: Sun, 31 Mar 2019 05:15:32 +0200 Subject: dt-bindings: mailbox: Document armada-3700-rwtm-mailbox binding This adds device tree binding documentation for the rWTM BIU mailbox driver on the Armada 37xx SOC (EspressoBin, Turris Mox). Signed-off-by: Marek Behun Reviewed-by: Rob Herring Signed-off-by: Jassi Brar --- .../mailbox/marvell,armada-3700-rwtm-mailbox.txt | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) create mode 100644 Documentation/devicetree/bindings/mailbox/marvell,armada-3700-rwtm-mailbox.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mailbox/marvell,armada-3700-rwtm-mailbox.txt b/Documentation/devicetree/bindings/mailbox/marvell,armada-3700-rwtm-mailbox.txt new file mode 100644 index 000000000000..282ab81a4ea6 --- /dev/null +++ b/Documentation/devicetree/bindings/mailbox/marvell,armada-3700-rwtm-mailbox.txt @@ -0,0 +1,16 @@ +* rWTM BIU Mailbox driver for Armada 37xx + +Required properties: +- compatible: must be "marvell,armada-3700-rwtm-mailbox" +- reg: physical base address of the mailbox and length of memory mapped + region +- interrupts: the IRQ line for the mailbox +- #mbox-cells: must be 1 + +Example: + rwtm: mailbox@b0000 { + compatible = "marvell,armada-3700-rwtm-mailbox"; + reg = <0xb0000 0x100>; + interrupts = ; + #mbox-cells = <1>; + }; -- cgit v1.2.3 From 2caf03843609af9dd4aa9c3b0f434f35016d4e15 Mon Sep 17 00:00:00 2001 From: Anson Huang Date: Thu, 9 May 2019 13:29:19 +0000 Subject: dt-bindings: pwm: Add i.MX TPM PWM binding Add i.MX TPM(Low Power Timer/Pulse Width Modulation Module) PWM binding. Signed-off-by: Anson Huang Reviewed-by: Rob Herring Signed-off-by: Thierry Reding --- .../devicetree/bindings/pwm/imx-tpm-pwm.txt | 22 ++++++++++++++++++++++ 1 file changed, 22 insertions(+) create mode 100644 Documentation/devicetree/bindings/pwm/imx-tpm-pwm.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/pwm/imx-tpm-pwm.txt b/Documentation/devicetree/bindings/pwm/imx-tpm-pwm.txt new file mode 100644 index 000000000000..3ba958d764ff --- /dev/null +++ b/Documentation/devicetree/bindings/pwm/imx-tpm-pwm.txt @@ -0,0 +1,22 @@ +Freescale i.MX TPM PWM controller + +Required properties: +- compatible : Should be "fsl,imx7ulp-pwm". +- reg: Physical base address and length of the controller's registers. +- #pwm-cells: Should be 3. See pwm.txt in this directory for a description of the cells format. +- clocks : The clock provided by the SoC to drive the PWM. +- interrupts: The interrupt for the PWM controller. + +Note: The TPM counter and period counter are shared between multiple channels, so all channels +should use same period setting. + +Example: + +tpm4: pwm@40250000 { + compatible = "fsl,imx7ulp-pwm"; + reg = <0x40250000 0x1000>; + assigned-clocks = <&pcc2 IMX7ULP_CLK_LPTPM4>; + assigned-clock-parents = <&scg1 IMX7ULP_CLK_SOSC_BUS_CLK>; + clocks = <&pcc2 IMX7ULP_CLK_LPTPM4>; + #pwm-cells = <3>; +}; -- cgit v1.2.3 From ad36cb9186bc805b8fd0b9908469e29617211658 Mon Sep 17 00:00:00 2001 From: Neil Armstrong Date: Tue, 23 Apr 2019 15:36:44 +0200 Subject: dt-bindings: pwm: Update bindings for the Meson G12A Family Update the doc to explicitly support Meson G12A Family. The 2 first (A & B) AO PWM uses different clock source than the last 2 (C & D) AO PWM modules, thus we need to differentiate them. Signed-off-by: Neil Armstrong Reviewed-by: Martin Blumenstingl Reviewed-by: Rob Herring Signed-off-by: Thierry Reding --- Documentation/devicetree/bindings/pwm/pwm-meson.txt | 3 +++ 1 file changed, 3 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/pwm/pwm-meson.txt b/Documentation/devicetree/bindings/pwm/pwm-meson.txt index 1fa3f7182133..891632354065 100644 --- a/Documentation/devicetree/bindings/pwm/pwm-meson.txt +++ b/Documentation/devicetree/bindings/pwm/pwm-meson.txt @@ -7,6 +7,9 @@ Required properties: or "amlogic,meson-gxbb-ao-pwm" or "amlogic,meson-axg-ee-pwm" or "amlogic,meson-axg-ao-pwm" + or "amlogic,meson-g12a-ee-pwm" + or "amlogic,meson-g12a-ao-pwm-ab" + or "amlogic,meson-g12a-ao-pwm-cd" - #pwm-cells: Should be 3. See pwm.txt in this directory for a description of the cells format. -- cgit v1.2.3 From 3ef4641fbf870ee1ecd5f890a54881b7f0e20b90 Mon Sep 17 00:00:00 2001 From: Gary Lin Date: Wed, 8 May 2019 15:54:48 +0800 Subject: docs/btf: fix the missing section marks The section titles of 3.4 and 3.5 are not marked correctly. Signed-off-by: Gary Lin Signed-off-by: Alexei Starovoitov --- Documentation/bpf/btf.rst | 2 ++ 1 file changed, 2 insertions(+) (limited to 'Documentation') diff --git a/Documentation/bpf/btf.rst b/Documentation/bpf/btf.rst index 29396e6943b0..8820360d00da 100644 --- a/Documentation/bpf/btf.rst +++ b/Documentation/bpf/btf.rst @@ -578,6 +578,7 @@ For line_info, the line number and column number are defined as below: #define BPF_LINE_INFO_LINE_COL(line_col) ((line_col) & 0x3ff) 3.4 BPF_{PROG,MAP}_GET_NEXT_ID +============================== In kernel, every loaded program, map or btf has a unique id. The id won't change during the lifetime of a program, map, or btf. @@ -587,6 +588,7 @@ each command, to user space, for bpf program or maps, respectively, so an inspection tool can inspect all programs and maps. 3.5 BPF_{PROG,MAP}_GET_FD_BY_ID +=============================== An introspection tool cannot use id to get details about program or maps. A file descriptor needs to be obtained first for reference-counting purpose. -- cgit v1.2.3 From fb8c86911052ccd4011392f78a24991c55c0d172 Mon Sep 17 00:00:00 2001 From: Amelie Delaunay Date: Thu, 9 May 2019 10:58:48 +0200 Subject: dt-bindings: mfd: Add ST Multi-Function eXpander (STMFX) core bindings This patch adds documentation of device tree bindings for the STMicroelectronics Multi-Function eXpander (STMFX) MFD core. Signed-off-by: Amelie Delaunay Reviewed-by: Linus Walleij Reviewed-by: Rob Herring Signed-off-by: Lee Jones --- Documentation/devicetree/bindings/mfd/stmfx.txt | 28 +++++++++++++++++++++++++ 1 file changed, 28 insertions(+) create mode 100644 Documentation/devicetree/bindings/mfd/stmfx.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mfd/stmfx.txt b/Documentation/devicetree/bindings/mfd/stmfx.txt new file mode 100644 index 000000000000..f0c2f7fcf5c7 --- /dev/null +++ b/Documentation/devicetree/bindings/mfd/stmfx.txt @@ -0,0 +1,28 @@ +STMicroelectonics Multi-Function eXpander (STMFX) Core bindings + +ST Multi-Function eXpander (STMFX) is a slave controller using I2C for +communication with the main MCU. Its main features are GPIO expansion, main +MCU IDD measurement (IDD is the amount of current that flows through VDD) and +resistive touchscreen controller. + +Required properties: +- compatible: should be "st,stmfx-0300". +- reg: I2C slave address of the device. +- interrupts: interrupt specifier triggered by MFX_IRQ_OUT signal. + Please refer to ../interrupt-controller/interrupt.txt + +Optional properties: +- drive-open-drain: configure MFX_IRQ_OUT as open drain. +- vdd-supply: phandle of the regulator supplying STMFX. + +Example: + + stmfx: stmfx@42 { + compatible = "st,stmfx-0300"; + reg = <0x42>; + interrupts = <8 IRQ_TYPE_EDGE_RISING>; + interrupt-parent = <&gpioi>; + vdd-supply = <&v3v3>; + }; + +Please refer to ../pinctrl/pinctrl-stmfx.txt for STMFX GPIO expander function bindings. -- cgit v1.2.3 From 2e0b80ce4520602b6c1aa806b42a01b7ff7a9af5 Mon Sep 17 00:00:00 2001 From: Amelie Delaunay Date: Thu, 9 May 2019 10:58:50 +0200 Subject: dt-bindings: pinctrl: document the STMFX pinctrl bindings This patch adds documentation of device tree bindings for the STMicroelectronics Multi-Function eXpander (STMFX) GPIO expander. Signed-off-by: Amelie Delaunay Reviewed-by: Linus Walleij Reviewed-by: Rob Herring Signed-off-by: Lee Jones --- .../devicetree/bindings/pinctrl/pinctrl-stmfx.txt | 116 +++++++++++++++++++++ 1 file changed, 116 insertions(+) create mode 100644 Documentation/devicetree/bindings/pinctrl/pinctrl-stmfx.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/pinctrl/pinctrl-stmfx.txt b/Documentation/devicetree/bindings/pinctrl/pinctrl-stmfx.txt new file mode 100644 index 000000000000..c1b4c1819b84 --- /dev/null +++ b/Documentation/devicetree/bindings/pinctrl/pinctrl-stmfx.txt @@ -0,0 +1,116 @@ +STMicroelectronics Multi-Function eXpander (STMFX) GPIO expander bindings + +ST Multi-Function eXpander (STMFX) offers up to 24 GPIOs expansion. +Please refer to ../mfd/stmfx.txt for STMFX Core bindings. + +Required properties: +- compatible: should be "st,stmfx-0300-pinctrl". +- #gpio-cells: should be <2>, the first cell is the GPIO number and the second + cell is the gpio flags in accordance with . +- gpio-controller: marks the device as a GPIO controller. +- #interrupt-cells: should be <2>, the first cell is the GPIO number and the + second cell is the interrupt flags in accordance with + . +- interrupt-controller: marks the device as an interrupt controller. +- gpio-ranges: specifies the mapping between gpio controller and pin + controller pins. Check "Concerning gpio-ranges property" below. +Please refer to ../gpio/gpio.txt. + +Please refer to pinctrl-bindings.txt for pin configuration. + +Required properties for pin configuration sub-nodes: +- pins: list of pins to which the configuration applies. + +Optional properties for pin configuration sub-nodes (pinconf-generic ones): +- bias-disable: disable any bias on the pin. +- bias-pull-up: the pin will be pulled up. +- bias-pull-pin-default: use the pin-default pull state. +- bias-pull-down: the pin will be pulled down. +- drive-open-drain: the pin will be driven with open drain. +- drive-push-pull: the pin will be driven actively high and low. +- output-high: the pin will be configured as an output driving high level. +- output-low: the pin will be configured as an output driving low level. + +Note that STMFX pins[15:0] are called "gpio[15:0]", and STMFX pins[23:16] are +called "agpio[7:0]". Example, to refer to pin 18 of STMFX, use "agpio2". + +Concerning gpio-ranges property: +- if all STMFX pins[24:0] are available (no other STMFX function in use), you + should use gpio-ranges = <&stmfx_pinctrl 0 0 24>; +- if agpio[3:0] are not available (STMFX Touchscreen function in use), you + should use gpio-ranges = <&stmfx_pinctrl 0 0 16>, <&stmfx_pinctrl 20 20 4>; +- if agpio[7:4] are not available (STMFX IDD function in use), you + should use gpio-ranges = <&stmfx_pinctrl 0 0 20>; + + +Example: + + stmfx: stmfx@42 { + ... + + stmfx_pinctrl: stmfx-pin-controller { + compatible = "st,stmfx-0300-pinctrl"; + #gpio-cells = <2>; + #interrupt-cells = <2>; + gpio-controller; + interrupt-controller; + gpio-ranges = <&stmfx_pinctrl 0 0 24>; + + joystick_pins: joystick { + pins = "gpio0", "gpio1", "gpio2", "gpio3", "gpio4"; + drive-push-pull; + bias-pull-up; + }; + }; + }; + +Example of STMFX GPIO consumers: + + joystick { + compatible = "gpio-keys"; + #address-cells = <1>; + #size-cells = <0>; + pinctrl-0 = <&joystick_pins>; + pinctrl-names = "default"; + button-0 { + label = "JoySel"; + linux,code = ; + interrupt-parent = <&stmfx_pinctrl>; + interrupts = <0 IRQ_TYPE_EDGE_RISING>; + }; + button-1 { + label = "JoyDown"; + linux,code = ; + interrupt-parent = <&stmfx_pinctrl>; + interrupts = <1 IRQ_TYPE_EDGE_RISING>; + }; + button-2 { + label = "JoyLeft"; + linux,code = ; + interrupt-parent = <&stmfx_pinctrl>; + interrupts = <2 IRQ_TYPE_EDGE_RISING>; + }; + button-3 { + label = "JoyRight"; + linux,code = ; + interrupt-parent = <&stmfx_pinctrl>; + interrupts = <3 IRQ_TYPE_EDGE_RISING>; + }; + button-4 { + label = "JoyUp"; + linux,code = ; + interrupt-parent = <&stmfx_pinctrl>; + interrupts = <4 IRQ_TYPE_EDGE_RISING>; + }; + }; + + leds { + compatible = "gpio-leds"; + orange { + gpios = <&stmfx_pinctrl 17 1>; + }; + + blue { + gpios = <&stmfx_pinctrl 19 1>; + }; + } -- cgit v1.2.3 From 51828950272d192ecab06da399d58941d2fd4952 Mon Sep 17 00:00:00 2001 From: Petr Štetiar Date: Fri, 10 May 2019 11:35:15 +0200 Subject: dt-bindings: doc: net: remove Linux API references MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit In commit 687e3d5550c7 ("dt-bindings: doc: reflect new NVMEM of_get_mac_address behaviour") I've kept or added references to Linux of_get_mac_address API which is unwanted so this patch fixes that by removing those references. Fixes: 687e3d5550c7 ("dt-bindings: doc: reflect new NVMEM of_get_mac_address behaviour") Suggested-by: Rob Herring Signed-off-by: Petr Štetiar Signed-off-by: David S. Miller --- Documentation/devicetree/bindings/net/keystone-netcp.txt | 6 +++--- Documentation/devicetree/bindings/net/wireless/mediatek,mt76.txt | 4 ++-- 2 files changed, 5 insertions(+), 5 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/net/keystone-netcp.txt b/Documentation/devicetree/bindings/net/keystone-netcp.txt index 3a65aabc76a2..6262c2f293b0 100644 --- a/Documentation/devicetree/bindings/net/keystone-netcp.txt +++ b/Documentation/devicetree/bindings/net/keystone-netcp.txt @@ -139,9 +139,9 @@ Optional properties: sub-module attached to this interface. The MAC address will be determined using the optional properties defined in -ethernet.txt, as provided by the of_get_mac_address API and only if efuse-mac -is set to 0. If any of the optional MAC address properties are not present, -then the driver will use random MAC address. +ethernet.txt and only if efuse-mac is set to 0. If all of the optional MAC +address properties are not present, then the driver will use a random MAC +address. Example binding: diff --git a/Documentation/devicetree/bindings/net/wireless/mediatek,mt76.txt b/Documentation/devicetree/bindings/net/wireless/mediatek,mt76.txt index 74665502f4cf..7e675dafc256 100644 --- a/Documentation/devicetree/bindings/net/wireless/mediatek,mt76.txt +++ b/Documentation/devicetree/bindings/net/wireless/mediatek,mt76.txt @@ -16,8 +16,8 @@ Optional properties: - ieee80211-freq-limit: See ieee80211.txt - mediatek,mtd-eeprom: Specify a MTD partition + offset containing EEPROM data -The driver is using of_get_mac_address API, so the MAC address can be as well -be set with corresponding optional properties defined in net/ethernet.txt. +The MAC address can as well be set with corresponding optional properties +defined in net/ethernet.txt. Optional nodes: - led: Properties for a connected LED -- cgit v1.2.3 From 5695f51d055057b9db069f0a060fc7c397278c2e Mon Sep 17 00:00:00 2001 From: Sakari Ailus Date: Fri, 10 May 2019 12:46:02 +0300 Subject: Documentation: ACPI: Use tabs for graph ASL indentation Use tabs to indent the graph documentation, not spaces. Fixes: f2dde1ed0f28 ("Documentation: ACPI: move dsd/graph.txt to firmware-guide/acpi and convert to reST") Signed-off-by: Sakari Ailus Signed-off-by: Rafael J. Wysocki --- Documentation/firmware-guide/acpi/dsd/graph.rst | 116 ++++++++++++------------ 1 file changed, 58 insertions(+), 58 deletions(-) (limited to 'Documentation') diff --git a/Documentation/firmware-guide/acpi/dsd/graph.rst b/Documentation/firmware-guide/acpi/dsd/graph.rst index e0baed35b037..8a9019a38b66 100644 --- a/Documentation/firmware-guide/acpi/dsd/graph.rst +++ b/Documentation/firmware-guide/acpi/dsd/graph.rst @@ -82,68 +82,68 @@ A simple example of this is show below:: Scope (\_SB.PCI0.I2C2) { - Device (CAM0) - { - Name (_DSD, Package () { - ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), - Package () { - Package () { "compatible", Package () { "nokia,smia" } }, - }, - ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), - Package () { - Package () { "port@0", PRT0 }, - } - }) - Name (PRT0, Package() { - ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), - Package () { - Package () { "reg", 0 }, - }, - ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), - Package () { - Package () { "endpoint@0", EP00 }, - } - }) - Name (EP00, Package() { - ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), - Package () { - Package () { "reg", 0 }, - Package () { "remote-endpoint", Package() { \_SB.PCI0.ISP, "port@4", "endpoint@0" } }, - } - }) - } + Device (CAM0) + { + Name (_DSD, Package () { + ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), + Package () { + Package () { "compatible", Package () { "nokia,smia" } }, + }, + ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), + Package () { + Package () { "port@0", PRT0 }, + } + }) + Name (PRT0, Package() { + ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), + Package () { + Package () { "reg", 0 }, + }, + ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), + Package () { + Package () { "endpoint@0", EP00 }, + } + }) + Name (EP00, Package() { + ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), + Package () { + Package () { "reg", 0 }, + Package () { "remote-endpoint", Package() { \_SB.PCI0.ISP, "port@4", "endpoint@0" } }, + } + }) + } } Scope (\_SB.PCI0) { - Device (ISP) - { - Name (_DSD, Package () { - ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), - Package () { - Package () { "port@4", PRT4 }, - } - }) - - Name (PRT4, Package() { - ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), - Package () { - Package () { "reg", 4 }, /* CSI-2 port number */ - }, - ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), - Package () { - Package () { "endpoint@0", EP40 }, - } - }) - - Name (EP40, Package() { - ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), - Package () { - Package () { "reg", 0 }, - Package () { "remote-endpoint", Package () { \_SB.PCI0.I2C2.CAM0, "port@0", "endpoint@0" } }, - } - }) - } + Device (ISP) + { + Name (_DSD, Package () { + ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), + Package () { + Package () { "port@4", PRT4 }, + } + }) + + Name (PRT4, Package() { + ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), + Package () { + Package () { "reg", 4 }, /* CSI-2 port number */ + }, + ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), + Package () { + Package () { "endpoint@0", EP40 }, + } + }) + + Name (EP40, Package() { + ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301"), + Package () { + Package () { "reg", 0 }, + Package () { "remote-endpoint", Package () { \_SB.PCI0.I2C2.CAM0, "port@0", "endpoint@0" } }, + } + }) + } } Here, the port 0 of the "CAM0" device is connected to the port 4 of -- cgit v1.2.3 From a423bd845c6043c205eedc413f40f81c7550e85c Mon Sep 17 00:00:00 2001 From: Sakari Ailus Date: Fri, 10 May 2019 12:46:03 +0300 Subject: Documentation: ACPI: Direct references are allowed to devices only In ACPI it is possible to make references to device objects only, not to other objects inside a device. In practice this means that hierarchical data extension targets must be in parentheses to make them strings, or an ACPICA warning will be produced. Reported-by: Andy Shevchenko Signed-off-by: Sakari Ailus Reviewed-by: Andy Shevchenko [ rjw: Changelog ] Signed-off-by: Rafael J. Wysocki --- .../firmware-guide/acpi/dsd/data-node-references.rst | 6 +++--- Documentation/firmware-guide/acpi/dsd/graph.rst | 12 ++++++------ 2 files changed, 9 insertions(+), 9 deletions(-) (limited to 'Documentation') diff --git a/Documentation/firmware-guide/acpi/dsd/data-node-references.rst b/Documentation/firmware-guide/acpi/dsd/data-node-references.rst index 1351984e767c..febccbc5689d 100644 --- a/Documentation/firmware-guide/acpi/dsd/data-node-references.rst +++ b/Documentation/firmware-guide/acpi/dsd/data-node-references.rst @@ -45,8 +45,8 @@ the ANOD object which is also the final target node of the reference. Name (_DSD, Package () { ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), Package () { - Package () { "node@0", NOD0 }, - Package () { "node@1", NOD1 }, + Package () { "node@0", "NOD0" }, + Package () { "node@1", "NOD1" }, } }) Name (NOD0, Package() { @@ -58,7 +58,7 @@ the ANOD object which is also the final target node of the reference. Name (NOD1, Package() { ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), Package () { - Package () { "anothernode", ANOD }, + Package () { "anothernode", "ANOD" }, } }) Name (ANOD, Package() { diff --git a/Documentation/firmware-guide/acpi/dsd/graph.rst b/Documentation/firmware-guide/acpi/dsd/graph.rst index 8a9019a38b66..1a6ce7afba5e 100644 --- a/Documentation/firmware-guide/acpi/dsd/graph.rst +++ b/Documentation/firmware-guide/acpi/dsd/graph.rst @@ -45,7 +45,7 @@ with "port" and must be followed by the "@" character and the number of the port as its key. The target object it refers to should be called "PRTX", where "X" is the number of the port. An example of such a package would be:: - Package() { "port@4", PRT4 } + Package() { "port@4", "PRT4" } Further on, endpoints are located under the port nodes. The hierarchical data extension key of the endpoint nodes must begin with @@ -54,7 +54,7 @@ endpoint. The object it refers to should be called "EPXY", where "X" is the number of the port and "Y" is the number of the endpoint. An example of such a package would be:: - Package() { "endpoint@0", EP40 } + Package() { "endpoint@0", "EP40" } Each port node contains a property extension key "port", the value of which is the number of the port. Each endpoint is similarly numbered with a property @@ -91,7 +91,7 @@ A simple example of this is show below:: }, ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), Package () { - Package () { "port@0", PRT0 }, + Package () { "port@0", "PRT0" }, } }) Name (PRT0, Package() { @@ -101,7 +101,7 @@ A simple example of this is show below:: }, ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), Package () { - Package () { "endpoint@0", EP00 }, + Package () { "endpoint@0", "EP00" }, } }) Name (EP00, Package() { @@ -121,7 +121,7 @@ A simple example of this is show below:: Name (_DSD, Package () { ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), Package () { - Package () { "port@4", PRT4 }, + Package () { "port@4", "PRT4" }, } }) @@ -132,7 +132,7 @@ A simple example of this is show below:: }, ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b"), Package () { - Package () { "endpoint@0", EP40 }, + Package () { "endpoint@0", "EP40" }, } }) -- cgit v1.2.3 From 9967a1bc8122e50cb2bb330b41bd982392314375 Mon Sep 17 00:00:00 2001 From: Wei Ni Date: Thu, 21 Feb 2019 18:18:36 +0800 Subject: of: Add bindings of thermtrip for Tegra soctherm Add optional property "nvidia,thermtrips". If present, these trips will be used as HW shutdown trips, and critical trips will be used as SW shutdown trips. Signed-off-by: Wei Ni Signed-off-by: Eduardo Valentin --- .../bindings/thermal/nvidia,tegra124-soctherm.txt | 20 +++++++++++++++++--- 1 file changed, 17 insertions(+), 3 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/thermal/nvidia,tegra124-soctherm.txt b/Documentation/devicetree/bindings/thermal/nvidia,tegra124-soctherm.txt index b6c0ae53d4dc..ab66d6feab4b 100644 --- a/Documentation/devicetree/bindings/thermal/nvidia,tegra124-soctherm.txt +++ b/Documentation/devicetree/bindings/thermal/nvidia,tegra124-soctherm.txt @@ -55,10 +55,21 @@ Required properties : - #cooling-cells: Should be 1. This cooling device only support on/off state. See ./thermal.txt for a description of this property. +Optional properties: +- nvidia,thermtrips : When present, this property specifies the temperature at + which the soctherm hardware will assert the thermal trigger signal to the + Power Management IC, which can be configured to reset or shutdown the device. + It is an array of pairs where each pair represents a tsensor id followed by a + temperature in milli Celcius. In the absence of this property the critical + trip point will be used for thermtrip temperature. + Note: -- the "critical" type trip points will be set to SOC_THERM hardware as the -shut down temperature. Once the temperature of this thermal zone is higher -than it, the system will be shutdown or reset by hardware. +- the "critical" type trip points will be used to set the temperature at which +the SOC_THERM hardware will assert a thermal trigger if the "nvidia,thermtrips" +property is missing. When the thermtrips property is present, the breach of a +critical trip point is reported back to the thermal framework to implement +software shutdown. + - the "hot" type trip points will be set to SOC_THERM hardware as the throttle temperature. Once the the temperature of this thermal zone is higher than it, it will trigger the HW throttle event. @@ -79,6 +90,9 @@ Example : #thermal-sensor-cells = <1>; + nvidia,thermtrips = ; + throttle-cfgs { /* * When the "heavy" cooling device triggered, -- cgit v1.2.3 From 7d8ac6b282ad4a2914f480ab80bf81dd5b77038c Mon Sep 17 00:00:00 2001 From: Wei Ni Date: Thu, 21 Feb 2019 18:18:39 +0800 Subject: of: Add bindings of gpu hw throttle for Tegra soctherm Add "nvidia,gpu-throt-level" property to set gpu hw throttle level. Signed-off-by: Wei Ni Signed-off-by: Eduardo Valentin --- .../bindings/thermal/nvidia,tegra124-soctherm.txt | 17 +++++++++++++++-- include/dt-bindings/thermal/tegra124-soctherm.h | 8 ++++---- 2 files changed, 19 insertions(+), 6 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/thermal/nvidia,tegra124-soctherm.txt b/Documentation/devicetree/bindings/thermal/nvidia,tegra124-soctherm.txt index ab66d6feab4b..cf6d0be56b7a 100644 --- a/Documentation/devicetree/bindings/thermal/nvidia,tegra124-soctherm.txt +++ b/Documentation/devicetree/bindings/thermal/nvidia,tegra124-soctherm.txt @@ -52,6 +52,15 @@ Required properties : Must set as following values: TEGRA_SOCTHERM_THROT_LEVEL_LOW, TEGRA_SOCTHERM_THROT_LEVEL_MED TEGRA_SOCTHERM_THROT_LEVEL_HIGH, TEGRA_SOCTHERM_THROT_LEVEL_NONE + - nvidia,gpu-throt-level: This property is for Tegra124 and Tegra210. + It is the level of pulse skippers, which used to throttle clock + frequencies. It indicates gpu clock throttling depth and can be + programmed to any of the following values which represent a throttling + percentage: + TEGRA_SOCTHERM_THROT_LEVEL_NONE (0%) + TEGRA_SOCTHERM_THROT_LEVEL_LOW (50%), + TEGRA_SOCTHERM_THROT_LEVEL_MED (75%), + TEGRA_SOCTHERM_THROT_LEVEL_HIGH (85%). - #cooling-cells: Should be 1. This cooling device only support on/off state. See ./thermal.txt for a description of this property. @@ -96,22 +105,26 @@ Example : throttle-cfgs { /* * When the "heavy" cooling device triggered, - * the HW will skip cpu clock's pulse in 85% depth + * the HW will skip cpu clock's pulse in 85% depth, + * skip gpu clock's pulse in 85% level */ throttle_heavy: heavy { nvidia,priority = <100>; nvidia,cpu-throt-percent = <85>; + nvidia,gpu-throt-level = ; #cooling-cells = <1>; }; /* * When the "light" cooling device triggered, - * the HW will skip cpu clock's pulse in 50% depth + * the HW will skip cpu clock's pulse in 50% depth, + * skip gpu clock's pulse in 50% level */ throttle_light: light { nvidia,priority = <80>; nvidia,cpu-throt-percent = <50>; + nvidia,gpu-throt-level = ; #cooling-cells = <1>; }; diff --git a/include/dt-bindings/thermal/tegra124-soctherm.h b/include/dt-bindings/thermal/tegra124-soctherm.h index c15e8b709a0d..444c7bdde146 100644 --- a/include/dt-bindings/thermal/tegra124-soctherm.h +++ b/include/dt-bindings/thermal/tegra124-soctherm.h @@ -12,9 +12,9 @@ #define TEGRA124_SOCTHERM_SENSOR_PLLX 3 #define TEGRA124_SOCTHERM_SENSOR_NUM 4 -#define TEGRA_SOCTHERM_THROT_LEVEL_LOW 0 -#define TEGRA_SOCTHERM_THROT_LEVEL_MED 1 -#define TEGRA_SOCTHERM_THROT_LEVEL_HIGH 2 -#define TEGRA_SOCTHERM_THROT_LEVEL_NONE -1 +#define TEGRA_SOCTHERM_THROT_LEVEL_NONE 0 +#define TEGRA_SOCTHERM_THROT_LEVEL_LOW 1 +#define TEGRA_SOCTHERM_THROT_LEVEL_MED 2 +#define TEGRA_SOCTHERM_THROT_LEVEL_HIGH 3 #endif -- cgit v1.2.3 From 8d3d462b684a064a45e68b64d40e9937966802d9 Mon Sep 17 00:00:00 2001 From: Wei Ni Date: Thu, 21 Feb 2019 18:18:46 +0800 Subject: of: Add bindings of OC hw throttle for Tegra soctherm Add OC HW throttle configuration for soctherm in DT. It is used to describe the OCx throttle events. Signed-off-by: Wei Ni Signed-off-by: Eduardo Valentin --- .../bindings/thermal/nvidia,tegra124-soctherm.txt | 25 ++++++++++++++++++++++ 1 file changed, 25 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/thermal/nvidia,tegra124-soctherm.txt b/Documentation/devicetree/bindings/thermal/nvidia,tegra124-soctherm.txt index cf6d0be56b7a..f02f38527a6b 100644 --- a/Documentation/devicetree/bindings/thermal/nvidia,tegra124-soctherm.txt +++ b/Documentation/devicetree/bindings/thermal/nvidia,tegra124-soctherm.txt @@ -64,6 +64,20 @@ Required properties : - #cooling-cells: Should be 1. This cooling device only support on/off state. See ./thermal.txt for a description of this property. + Optional properties: The following properties are T210 specific and + valid only for OCx throttle events. + - nvidia,count-threshold: Specifies the number of OC events that are + required for triggering an interrupt. Interrupts are not triggered if + the property is missing. A value of 0 will interrupt on every OC alarm. + - nvidia,polarity-active-low: Configures the polarity of the OC alaram + signal. If present, this means assert low, otherwise assert high. + - nvidia,alarm-filter: Number of clocks to filter event. When the filter + expires (which means the OC event has not occurred for a long time), + the counter is cleared and filter is rearmed. Default value is 0. + - nvidia,throttle-period-us: Specifies the number of uSec for which + throttling is engaged after the OC event is deasserted. Default value + is 0. + Optional properties: - nvidia,thermtrips : When present, this property specifies the temperature at which the soctherm hardware will assert the thermal trigger signal to the @@ -134,6 +148,17 @@ Example : * arbiter will select the highest priority as the final throttle * settings to skip cpu pulse. */ + + throttle_oc1: oc1 { + nvidia,priority = <50>; + nvidia,polarity-active-low; + nvidia,count-threshold = <100>; + nvidia,alarm-filter = <5100000>; + nvidia,throttle-period-us = <0>; + nvidia,cpu-throt-percent = <75>; + nvidia,gpu-throt-level = + ; + }; }; }; -- cgit v1.2.3 From c6ba08819b6a8a94dfb4b0fec7d7b501a6f24aee Mon Sep 17 00:00:00 2001 From: Fabrice Gasnier Date: Wed, 12 Dec 2018 09:48:13 +0100 Subject: dt-bindings: stm32: syscon: Add clock support STM32 system configuration controller registers needs to be clocked. Document clock support on stm32-syscon. Signed-off-by: Fabrice Gasnier Reviewed-by: Rob Herring Signed-off-by: Lee Jones --- Documentation/devicetree/bindings/arm/stm32/stm32-syscon.txt | 2 ++ 1 file changed, 2 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/arm/stm32/stm32-syscon.txt b/Documentation/devicetree/bindings/arm/stm32/stm32-syscon.txt index 99980aee26e5..c92d411fd023 100644 --- a/Documentation/devicetree/bindings/arm/stm32/stm32-syscon.txt +++ b/Documentation/devicetree/bindings/arm/stm32/stm32-syscon.txt @@ -5,10 +5,12 @@ Properties: - " st,stm32mp157-syscfg " - for stm32mp157 based SoCs, second value must be always "syscon". - reg : offset and length of the register set. + - clocks: phandle to the syscfg clock Example: syscfg: syscon@50020000 { compatible = "st,stm32mp157-syscfg", "syscon"; reg = <0x50020000 0x400>; + clocks = <&rcc SYSCFG>; }; -- cgit v1.2.3 From 730080a758fdc44fbfc214dd004553ef13d5b89b Mon Sep 17 00:00:00 2001 From: Claudiu Beznea Date: Tue, 5 Mar 2019 10:07:47 +0000 Subject: dt-bindings: mfd: Add bindings for SAM9X60 HLCD controller Add new compatible string for the HLCD controller on SAM9X60 SoC. Signed-off-by: Claudiu Beznea Signed-off-by: Lee Jones --- Documentation/devicetree/bindings/mfd/atmel-hlcdc.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mfd/atmel-hlcdc.txt b/Documentation/devicetree/bindings/mfd/atmel-hlcdc.txt index 3f643ef121ff..5f8880cc757e 100644 --- a/Documentation/devicetree/bindings/mfd/atmel-hlcdc.txt +++ b/Documentation/devicetree/bindings/mfd/atmel-hlcdc.txt @@ -7,6 +7,7 @@ Required properties: "atmel,sama5d2-hlcdc" "atmel,sama5d3-hlcdc" "atmel,sama5d4-hlcdc" + "microchip,sam9x60-hlcdc" - reg: base address and size of the HLCDC device registers. - clock-names: the name of the 3 clocks requested by the HLCDC device. Should contain "periph_clk", "sys_clk" and "slow_clk". -- cgit v1.2.3 From a2a0c4ef4e560061b2ec226924a3e2d8652c89b1 Mon Sep 17 00:00:00 2001 From: Dan Murphy Date: Fri, 5 Apr 2019 09:19:07 -0500 Subject: dt-bindings: mfd: LMU: Fix lm3632 dt binding example Fix the lm3632 dt binding examples as the LCM enable GPIOs are defined as enable GPIOs per the regulator/lm363x-regulator.txt bindings document. Signed-off-by: Dan Murphy Reviewed-by: Rob Herring Signed-off-by: Lee Jones --- Documentation/devicetree/bindings/mfd/ti-lmu.txt | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mfd/ti-lmu.txt b/Documentation/devicetree/bindings/mfd/ti-lmu.txt index 980394d701a7..86ca786d54fc 100644 --- a/Documentation/devicetree/bindings/mfd/ti-lmu.txt +++ b/Documentation/devicetree/bindings/mfd/ti-lmu.txt @@ -104,8 +104,8 @@ lm3632@11 { regulators { compatible = "ti,lm363x-regulator"; - ti,lcm-en1-gpio = <&pioC 0 GPIO_ACTIVE_HIGH>; /* PC0 */ - ti,lcm-en2-gpio = <&pioC 1 GPIO_ACTIVE_HIGH>; /* PC1 */ + enable-gpios = <&pioC 0 GPIO_ACTIVE_HIGH>, + <&pioC 1 GPIO_ACTIVE_HIGH>; vboost { regulator-name = "lcd_boost"; -- cgit v1.2.3 From c273e63129b1ee754ecd9f2b85cc1446a7b1816e Mon Sep 17 00:00:00 2001 From: Charles Keepax Date: Wed, 1 May 2019 11:23:50 +0100 Subject: mfd: lochnagar: Add links to binding docs for sound and hwmon Lochnagar is an evaluation and development board for Cirrus Logic Smart CODEC and Amp devices. It allows the connection of most Cirrus Logic devices on mini-cards, as well as allowing connection of various application processor systems to provide a full evaluation platform. This driver supports the board controller chip on the Lochnagar board. Add links to the binding documents for the new sound and hardware monitor parts of the driver. Signed-off-by: Charles Keepax Signed-off-by: Lee Jones --- .../devicetree/bindings/mfd/cirrus,lochnagar.txt | 17 +++++++++++++++++ 1 file changed, 17 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/mfd/cirrus,lochnagar.txt b/Documentation/devicetree/bindings/mfd/cirrus,lochnagar.txt index 004b0158cf4d..3bf92ad37fa1 100644 --- a/Documentation/devicetree/bindings/mfd/cirrus,lochnagar.txt +++ b/Documentation/devicetree/bindings/mfd/cirrus,lochnagar.txt @@ -19,6 +19,8 @@ And these documents for the required sub-node binding details: [4] Clock: ../clock/cirrus,lochnagar.txt [5] Pinctrl: ../pinctrl/cirrus,lochnagar.txt [6] Regulator: ../regulator/cirrus,lochnagar.txt + [7] Sound: ../sound/cirrus,lochnagar.txt + [8] Hardware Monitor: ../hwmon/cirrus,lochnagar.txt Required properties: @@ -41,6 +43,11 @@ Optional sub-nodes: - Bindings for the regulator components, see [6]. Only available on Lochnagar 2. + - lochnagar-sc : Binding for the sound card components, see [7]. + Only available on Lochnagar 2. + - lochnagar-hwmon : Binding for the hardware monitor components, see [8]. + Only available on Lochnagar 2. + Optional properties: - present-gpios : Host present line, indicating the presence of a @@ -65,4 +72,14 @@ lochnagar: lochnagar@22 { compatible = "cirrus,lochnagar-pinctrl"; ... }; + + lochnagar-sc { + compatible = "cirrus,lochnagar2-soundcard"; + ... + }; + + lochnagar-hwmon { + compatible = "cirrus,lochnagar2-hwmon"; + ... + }; }; -- cgit v1.2.3 From 32fcb75c66a0cb66db9ec4f777f864675e5aebb2 Mon Sep 17 00:00:00 2001 From: Brian Masney Date: Wed, 24 Apr 2019 05:25:04 -0400 Subject: dt-bindings: backlight: Add lm3630a bindings Add new backlight bindings for the TI LM3630A dual-string white LED. Signed-off-by: Brian Masney Reviewed-by: Rob Herring Acked-by: Pavel Machek Acked-by: Daniel Thompson Signed-off-by: Lee Jones --- .../bindings/leds/backlight/lm3630a-backlight.yaml | 129 +++++++++++++++++++++ 1 file changed, 129 insertions(+) create mode 100644 Documentation/devicetree/bindings/leds/backlight/lm3630a-backlight.yaml (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/leds/backlight/lm3630a-backlight.yaml b/Documentation/devicetree/bindings/leds/backlight/lm3630a-backlight.yaml new file mode 100644 index 000000000000..4d61fe0a98a4 --- /dev/null +++ b/Documentation/devicetree/bindings/leds/backlight/lm3630a-backlight.yaml @@ -0,0 +1,129 @@ +# SPDX-License-Identifier: (GPL-2.0 OR BSD-2-Clause) +%YAML 1.2 +--- +$id: http://devicetree.org/schemas/leds/backlight/lm3630a-backlight.yaml# +$schema: http://devicetree.org/meta-schemas/core.yaml# + +title: TI LM3630A High-Efficiency Dual-String White LED + +maintainers: + - Lee Jones + - Daniel Thompson + - Jingoo Han + +description: | + The LM3630A is a current-mode boost converter which supplies the power and + controls the current in up to two strings of 10 LEDs per string. + https://www.ti.com/product/LM3630A + +properties: + compatible: + const: ti,lm3630a + + reg: + maxItems: 1 + + ti,linear-mapping-mode: + description: | + Enable linear mapping mode. If disabled, then it will use exponential + mapping mode in which the ramp up/down appears to have a more uniform + transition to the human eye. + type: boolean + +required: + - compatible + - reg + +patternProperties: + "^led@[01]$": + type: object + description: | + Properties for a string of connected LEDs. + + properties: + reg: + description: | + The control bank that is used to program the two current sinks. The + LM3630A has two control banks (A and B) and are represented as 0 or 1 + in this property. The two current sinks can be controlled + independently with both banks, or bank A can be configured to control + both sinks with the led-sources property. + maxItems: 1 + minimum: 0 + maximum: 1 + + label: + maxItems: 1 + + led-sources: + allOf: + - minItems: 1 + maxItems: 2 + items: + minimum: 0 + maximum: 1 + + default-brightness: + description: Default brightness level on boot. + minimum: 0 + maximum: 255 + + max-brightness: + description: Maximum brightness that is allowed during runtime. + minimum: 0 + maximum: 255 + + required: + - reg + + additionalProperties: false + +additionalProperties: false + +examples: + - | + i2c { + #address-cells = <1>; + #size-cells = <0>; + + led-controller@38 { + compatible = "ti,lm3630a"; + reg = <0x38>; + + #address-cells = <1>; + #size-cells = <0>; + + led@0 { + reg = <0>; + led-sources = <0 1>; + label = "lcd-backlight"; + default-brightness = <200>; + max-brightness = <255>; + }; + }; + }; + - | + i2c { + #address-cells = <1>; + #size-cells = <0>; + + led-controller@38 { + compatible = "ti,lm3630a"; + reg = <0x38>; + + #address-cells = <1>; + #size-cells = <0>; + + led@0 { + reg = <0>; + default-brightness = <150>; + ti,linear-mapping-mode; + }; + + led@1 { + reg = <1>; + default-brightness = <225>; + ti,linear-mapping-mode; + }; + }; + }; -- cgit v1.2.3 From a9604f28087f3641bed923b455c7392cdf432cbf Mon Sep 17 00:00:00 2001 From: Amit Kucheria Date: Wed, 20 Mar 2019 18:47:59 +0530 Subject: dt: thermal: tsens: Add bindings for qcs404 qcs404 uses v1 of the TSENS IP block. Create a fallback DT property "qcom,tsens-v1" to gather common code Signed-off-by: Amit Kucheria Reviewed-by: Rob Herring Signed-off-by: Eduardo Valentin --- Documentation/devicetree/bindings/thermal/qcom-tsens.txt | 14 ++++++++++++++ 1 file changed, 14 insertions(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/thermal/qcom-tsens.txt b/Documentation/devicetree/bindings/thermal/qcom-tsens.txt index 1d9e8cf61018..673cc1831ee9 100644 --- a/Documentation/devicetree/bindings/thermal/qcom-tsens.txt +++ b/Documentation/devicetree/bindings/thermal/qcom-tsens.txt @@ -6,11 +6,14 @@ Required properties: - "qcom,msm8916-tsens" (MSM8916) - "qcom,msm8974-tsens" (MSM8974) - "qcom,msm8996-tsens" (MSM8996) + - "qcom,qcs404-tsens", "qcom,tsens-v1" (QCS404) - "qcom,msm8998-tsens", "qcom,tsens-v2" (MSM8998) - "qcom,sdm845-tsens", "qcom,tsens-v2" (SDM845) The generic "qcom,tsens-v2" property must be used as a fallback for any SoC with version 2 of the TSENS IP. MSM8996 is the only exception because the generic property did not exist when support was added. + Similarly, the generic "qcom,tsens-v1" property must be used as a fallback for + any SoC with version 1 of the TSENS IP. - reg: Address range of the thermal registers. New platforms containing v2.x.y of the TSENS IP must specify the SROT and TM @@ -39,3 +42,14 @@ tsens0: thermal-sensor@c263000 { #qcom,sensors = <13>; #thermal-sensor-cells = <1>; }; + +Example 3 (for any platform containing v1 of the TSENS IP): +tsens: thermal-sensor@4a9000 { + compatible = "qcom,qcs404-tsens", "qcom,tsens-v1"; + reg = <0x004a9000 0x1000>, /* TM */ + <0x004a8000 0x1000>; /* SROT */ + nvmem-cells = <&tsens_caldata>; + nvmem-cell-names = "calib"; + #qcom,sensors = <10>; + #thermal-sensor-cells = <1>; + }; -- cgit v1.2.3 From c8044b918b2bd9e6ad93b4f14b42bcbb61dd544b Mon Sep 17 00:00:00 2001 From: Talel Shenhar Date: Thu, 11 Apr 2019 13:22:47 +0300 Subject: dt-bindings: thermal: al-thermal: Add binding documentation Add thermal binding documentation for Amazon's Annapurna Labs Thermal Sensor. Signed-off-by: Talel Shenhar Reviewed-by: David Woodhouse Reviewed-by: Rob Herring Signed-off-by: Eduardo Valentin --- .../bindings/thermal/amazon,al-thermal.txt | 33 ++++++++++++++++++++++ 1 file changed, 33 insertions(+) create mode 100644 Documentation/devicetree/bindings/thermal/amazon,al-thermal.txt (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/thermal/amazon,al-thermal.txt b/Documentation/devicetree/bindings/thermal/amazon,al-thermal.txt new file mode 100644 index 000000000000..703979dbd577 --- /dev/null +++ b/Documentation/devicetree/bindings/thermal/amazon,al-thermal.txt @@ -0,0 +1,33 @@ +Amazon's Annapurna Labs Thermal Sensor + +Simple thermal device that allows temperature reading by a single MMIO +transaction. + +Required properties: +- compatible: "amazon,al-thermal". +- reg: The physical base address and length of the sensor's registers. +- #thermal-sensor-cells: Must be 1. See ./thermal.txt for a description. + +Example: + thermal: thermal { + compatible = "amazon,al-thermal"; + reg = <0x0 0x05002860 0x0 0x1>; + #thermal-sensor-cells = <0x1>; + }; + + thermal-zones { + thermal-z0 { + polling-delay-passive = <250>; + polling-delay = <1000>; + thermal-sensors = <&thermal 0>; + trips { + critical { + temperature = <105000>; + hysteresis = <2000>; + type = "critical"; + }; + }; + + }; + }; + -- cgit v1.2.3 From 80d95930dcdf06315cfde408c18783c811bf3db9 Mon Sep 17 00:00:00 2001 From: Jean-Francois Dagenais Date: Thu, 18 Apr 2019 12:37:33 -0400 Subject: dt-bindings: thermal: generic-adc: make lookup-table optional Update binding description making lookup-table optional. Signed-off-by: Jean-Francois Dagenais Signed-off-by: Eduardo Valentin --- .../devicetree/bindings/thermal/thermal-generic-adc.txt | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/thermal/thermal-generic-adc.txt b/Documentation/devicetree/bindings/thermal/thermal-generic-adc.txt index d72355502b78..691a09db2fef 100644 --- a/Documentation/devicetree/bindings/thermal/thermal-generic-adc.txt +++ b/Documentation/devicetree/bindings/thermal/thermal-generic-adc.txt @@ -8,16 +8,22 @@ temperature using voltage-temperature lookup table. Required properties: =================== - compatible: Must be "generic-adc-thermal". +- #thermal-sensor-cells: Should be 1. See ./thermal.txt for a description + of this property. +Optional properties: +=================== - temperature-lookup-table: Two dimensional array of Integer; lookup table to map the relation between ADC value and temperature. When ADC is read, the value is looked up on the table to get the equivalent temperature. + The first value of the each row of array is the temperature in milliCelsius and second value of the each row of array is the ADC read value. -- #thermal-sensor-cells: Should be 1. See ./thermal.txt for a description - of this property. + + If not specified, driver assumes the ADC channel + gives milliCelsius directly. Example : #include -- cgit v1.2.3 From 4b984e7bfb6d8e4209838a55af4ae5fbba878867 Mon Sep 17 00:00:00 2001 From: Elaine Zhang Date: Tue, 30 Apr 2019 18:09:45 +0800 Subject: dt-bindings: rockchip-thermal: Support the PX30 SoC compatible Add a new compatible for thermal founding on PX30 SoCs. Signed-off-by: Elaine Zhang Acked-by: Daniel Lezcano Reviewed-by: Rob Herring Signed-off-by: Eduardo Valentin --- Documentation/devicetree/bindings/thermal/rockchip-thermal.txt | 1 + 1 file changed, 1 insertion(+) (limited to 'Documentation') diff --git a/Documentation/devicetree/bindings/thermal/rockchip-thermal.txt b/Documentation/devicetree/bindings/thermal/rockchip-thermal.txt index 43d744e5305e..c6aac9bcacf1 100644 --- a/Documentation/devicetree/bindings/thermal/rockchip-thermal.txt +++ b/Documentation/devicetree/bindings/thermal/rockchip-thermal.txt @@ -2,6 +2,7 @@ Required properties: - compatible : should be "rockchip,-tsadc" + "rockchip,px30-tsadc": found on PX30 SoCs "rockchip,rv1108-tsadc": found on RV1108 SoCs "rockchip,rk3228-tsadc": found on RK3228 SoCs "rockchip,rk3288-tsadc": found on RK3288 SoCs -- cgit v1.2.3 From cefdca0a86be517bc390fc4541e3674b8e7803b0 Mon Sep 17 00:00:00 2001 From: Peter Xu Date: Mon, 13 May 2019 17:16:41 -0700 Subject: userfaultfd/sysctl: add vm.unprivileged_userfaultfd Userfaultfd can be misued to make it easier to exploit existing use-after-free (and similar) bugs that might otherwise only make a short window or race condition available. By using userfaultfd to stall a kernel thread, a malicious program can keep some state that it wrote, stable for an extended period, which it can then access using an existing exploit. While it doesn't cause the exploit itself, and while it's not the only thing that can stall a kernel thread when accessing a memory location, it's one of the few that never needs privilege. We can add a flag, allowing userfaultfd to be restricted, so that in general it won't be useable by arbitrary user programs, but in environments that require userfaultfd it can be turned back on. Add a global sysctl knob "vm.unprivileged_userfaultfd" to control whether userfaultfd is allowed by unprivileged users. When this is set to zero, only privileged users (root user, or users with the CAP_SYS_PTRACE capability) will be able to use the userfaultfd syscalls. Andrea said: : The only difference between the bpf sysctl and the userfaultfd sysctl : this way is that the bpf sysctl adds the CAP_SYS_ADMIN capability : requirement, while userfaultfd adds the CAP_SYS_PTRACE requirement, : because the userfaultfd monitor is more likely to need CAP_SYS_PTRACE : already if it's doing other kind of tracking on processes runtime, in : addition of userfaultfd. In other words both syscalls works only for : root, when the two sysctl are opt-in set to 1. [dgilbert@redhat.com: changelog additions] [akpm@linux-foundation.org: documentation tweak, per Mike] Link: http://lkml.kernel.org/r/20190319030722.12441-2-peterx@redhat.com Signed-off-by: Peter Xu Suggested-by: Andrea Arcangeli Suggested-by: Mike Rapoport Reviewed-by: Mike Rapoport Reviewed-by: Andrea Arcangeli Cc: Paolo Bonzini Cc: Hugh Dickins Cc: Luis Chamberlain Cc: Maxime Coquelin Cc: Maya Gokhale Cc: Jerome Glisse Cc: Pavel Emelyanov Cc: Johannes Weiner Cc: Martin Cracauer Cc: Denis Plotnikov Cc: Marty McFadden Cc: Mike Kravetz Cc: Kees Cook Cc: Mel Gorman Cc: "Kirill A . Shutemov" Cc: "Dr . David Alan Gilbert" Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- Documentation/sysctl/vm.txt | 12 ++++++++++++ fs/userfaultfd.c | 5 +++++ include/linux/userfaultfd_k.h | 2 ++ kernel/sysctl.c | 12 ++++++++++++ 4 files changed, 31 insertions(+) (limited to 'Documentation') diff --git a/Documentation/sysctl/vm.txt b/Documentation/sysctl/vm.txt index 3f13d8599337..749322060f10 100644 --- a/Documentation/sysctl/vm.txt +++ b/Documentation/sysctl/vm.txt @@ -61,6 +61,7 @@ Currently, these files are in /proc/sys/vm: - stat_refresh - numa_stat - swappiness +- unprivileged_userfaultfd - user_reserve_kbytes - vfs_cache_pressure - watermark_boost_factor @@ -818,6 +819,17 @@ The default value is 60. ============================================================== +unprivileged_userfaultfd + +This flag controls whether unprivileged users can use the userfaultfd +system calls. Set this to 1 to allow unprivileged users to use the +userfaultfd system calls, or set this to 0 to restrict userfaultfd to only +privileged users (with SYS_CAP_PTRACE capability). + +The default value is 1. + +============================================================== + - user_reserve_kbytes When overcommit_memory is set to 2, "never overcommit" mode, reserve diff --git a/fs/userfaultfd.c b/fs/userfaultfd.c index f5de1e726356..3b30301c90ec 100644 --- a/fs/userfaultfd.c +++ b/fs/userfaultfd.c @@ -30,6 +30,8 @@ #include #include +int sysctl_unprivileged_userfaultfd __read_mostly = 1; + static struct kmem_cache *userfaultfd_ctx_cachep __read_mostly; enum userfaultfd_state { @@ -1930,6 +1932,9 @@ SYSCALL_DEFINE1(userfaultfd, int, flags) struct userfaultfd_ctx *ctx; int fd; + if (!sysctl_unprivileged_userfaultfd && !capable(CAP_SYS_PTRACE)) + return -EPERM; + BUG_ON(!current->mm); /* Check the UFFD_* constants for consistency. */ diff --git a/include/linux/userfaultfd_k.h b/include/linux/userfaultfd_k.h index 37c9eba75c98..ac9d71e24b81 100644 --- a/include/linux/userfaultfd_k.h +++ b/include/linux/userfaultfd_k.h @@ -28,6 +28,8 @@ #define UFFD_SHARED_FCNTL_FLAGS (O_CLOEXEC | O_NONBLOCK) #define UFFD_FLAGS_SET (EFD_SHARED_FCNTL_FLAGS) +extern int sysctl_unprivileged_userfaultfd; + extern vm_fault_t handle_userfault(struct vm_fault *vmf, unsigned long reason); extern ssize_t mcopy_atomic(struct mm_struct *dst_mm, unsigned long dst_start, diff --git a/kernel/sysctl.c b/kernel/sysctl.c index 599510a3355e..ba158f61aab4 100644 --- a/kernel/sysctl.c +++ b/kernel/sysctl.c @@ -66,6 +66,7 @@ #include #include #include +#include #include "../lib/kstrtox.h" @@ -1719,6 +1720,17 @@ static struct ctl_table vm_table[] = { .extra1 = (void *)&mmap_rnd_compat_bits_min, .extra2 = (void *)&mmap_rnd_compat_bits_max, }, +#endif +#ifdef CONFIG_USERFAULTFD + { + .procname = "unprivileged_userfaultfd", + .data = &sysctl_unprivileged_userfaultfd, + .maxlen = sizeof(sysctl_unprivileged_userfaultfd), + .mode = 0644, + .proc_handler = proc_dointvec_minmax, + .extra1 = &zero, + .extra2 = &one, + }, #endif { } }; -- cgit v1.2.3 From 886cf1901db962cee5f8b82b9b260079a5e8a4eb Mon Sep 17 00:00:00 2001 From: Kirill Tkhai Date: Mon, 13 May 2019 17:16:51 -0700 Subject: mm: move recent_rotated pages calculation to shrink_inactive_list() Patch series "mm: Generalize putback functions"] putback_inactive_pages() and move_active_pages_to_lru() are almost similar, so this patchset merges them ina single function. This patch (of 4): The patch moves the calculation from putback_inactive_pages() to shrink_inactive_list(). This makes putback_inactive_pages() looking more similar to move_active_pages_to_lru(). To do that, we account activated pages in reclaim_stat::nr_activate. Since a page may change its LRU type from anon to file cache inside shrink_page_list() (see ClearPageSwapBacked()), we have to account pages for the both types. So, nr_activate becomes an array. Previously we used nr_activate to account PGACTIVATE events, but now we account them into pgactivate variable (since they are about number of pages in general, not about sum of hpage_nr_pages). Link: http://lkml.kernel.org/r/155290127956.31489.3393586616054413298.stgit@localhost.localdomain Signed-off-by: Kirill Tkhai Reviewed-by: Daniel Jordan Cc: Michal Hocko Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- .../trace/postprocess/trace-vmscan-postprocess.pl | 7 ++++--- include/linux/vmstat.h | 2 +- include/trace/events/vmscan.h | 13 ++++++++----- mm/vmscan.c | 15 +++++++-------- 4 files changed, 20 insertions(+), 17 deletions(-) (limited to 'Documentation') diff --git a/Documentation/trace/postprocess/trace-vmscan-postprocess.pl b/Documentation/trace/postprocess/trace-vmscan-postprocess.pl index 66bfd8396877..995da15b16ca 100644 --- a/Documentation/trace/postprocess/trace-vmscan-postprocess.pl +++ b/Documentation/trace/postprocess/trace-vmscan-postprocess.pl @@ -113,7 +113,7 @@ my $regex_kswapd_wake_default = 'nid=([0-9]*) order=([0-9]*)'; my $regex_kswapd_sleep_default = 'nid=([0-9]*)'; my $regex_wakeup_kswapd_default = 'nid=([0-9]*) zid=([0-9]*) order=([0-9]*) gfp_flags=([A-Z_|]*)'; my $regex_lru_isolate_default = 'isolate_mode=([0-9]*) classzone_idx=([0-9]*) order=([0-9]*) nr_requested=([0-9]*) nr_scanned=([0-9]*) nr_skipped=([0-9]*) nr_taken=([0-9]*) lru=([a-z_]*)'; -my $regex_lru_shrink_inactive_default = 'nid=([0-9]*) nr_scanned=([0-9]*) nr_reclaimed=([0-9]*) nr_dirty=([0-9]*) nr_writeback=([0-9]*) nr_congested=([0-9]*) nr_immediate=([0-9]*) nr_activate=([0-9]*) nr_ref_keep=([0-9]*) nr_unmap_fail=([0-9]*) priority=([0-9]*) flags=([A-Z_|]*)'; +my $regex_lru_shrink_inactive_default = 'nid=([0-9]*) nr_scanned=([0-9]*) nr_reclaimed=([0-9]*) nr_dirty=([0-9]*) nr_writeback=([0-9]*) nr_congested=([0-9]*) nr_immediate=([0-9]*) nr_activate_anon=([0-9]*) nr_activate_file=([0-9]*) nr_ref_keep=([0-9]*) nr_unmap_fail=([0-9]*) priority=([0-9]*) flags=([A-Z_|]*)'; my $regex_lru_shrink_active_default = 'lru=([A-Z_]*) nr_scanned=([0-9]*) nr_rotated=([0-9]*) priority=([0-9]*)'; my $regex_writepage_default = 'page=([0-9a-f]*) pfn=([0-9]*) flags=([A-Z_|]*)'; @@ -212,7 +212,8 @@ $regex_lru_shrink_inactive = generate_traceevent_regex( "vmscan/mm_vmscan_lru_shrink_inactive", $regex_lru_shrink_inactive_default, "nid", "nr_scanned", "nr_reclaimed", "nr_dirty", "nr_writeback", - "nr_congested", "nr_immediate", "nr_activate", "nr_ref_keep", + "nr_congested", "nr_immediate", "nr_activate_anon", + "nr_activate_file", "nr_ref_keep", "nr_unmap_fail", "priority", "flags"); $regex_lru_shrink_active = generate_traceevent_regex( "vmscan/mm_vmscan_lru_shrink_active", @@ -407,7 +408,7 @@ EVENT_PROCESS: } my $nr_reclaimed = $3; - my $flags = $12; + my $flags = $13; my $file = 0; if ($flags =~ /RECLAIM_WB_FILE/) { $file = 1; diff --git a/include/linux/vmstat.h b/include/linux/vmstat.h index 2db8d60981fe..bdeda4b079fe 100644 --- a/include/linux/vmstat.h +++ b/include/linux/vmstat.h @@ -26,7 +26,7 @@ struct reclaim_stat { unsigned nr_congested; unsigned nr_writeback; unsigned nr_immediate; - unsigned nr_activate; + unsigned nr_activate[2]; unsigned nr_ref_keep; unsigned nr_unmap_fail; }; diff --git a/include/trace/events/vmscan.h b/include/trace/events/vmscan.h index e8709ab22d68..cb2add69301a 100644 --- a/include/trace/events/vmscan.h +++ b/include/trace/events/vmscan.h @@ -359,7 +359,8 @@ TRACE_EVENT(mm_vmscan_lru_shrink_inactive, __field(unsigned long, nr_writeback) __field(unsigned long, nr_congested) __field(unsigned long, nr_immediate) - __field(unsigned long, nr_activate) + __field(unsigned int, nr_activate0) + __field(unsigned int, nr_activate1) __field(unsigned long, nr_ref_keep) __field(unsigned long, nr_unmap_fail) __field(int, priority) @@ -374,20 +375,22 @@ TRACE_EVENT(mm_vmscan_lru_shrink_inactive, __entry->nr_writeback = stat->nr_writeback; __entry->nr_congested = stat->nr_congested; __entry->nr_immediate = stat->nr_immediate; - __entry->nr_activate = stat->nr_activate; + __entry->nr_activate0 = stat->nr_activate[0]; + __entry->nr_activate1 = stat->nr_activate[1]; __entry->nr_ref_keep = stat->nr_ref_keep; __entry->nr_unmap_fail = stat->nr_unmap_fail; __entry->priority = priority; __entry->reclaim_flags = trace_shrink_flags(file); ), - TP_printk("nid=%d nr_scanned=%ld nr_reclaimed=%ld nr_dirty=%ld nr_writeback=%ld nr_congested=%ld nr_immediate=%ld nr_activate=%ld nr_ref_keep=%ld nr_unmap_fail=%ld priority=%d flags=%s", + TP_printk("nid=%d nr_scanned=%ld nr_reclaimed=%ld nr_dirty=%ld nr_writeback=%ld nr_congested=%ld nr_immediate=%ld nr_activate_anon=%d nr_activate_file=%d nr_ref_keep=%ld nr_unmap_fail=%ld priority=%d flags=%s", __entry->nid, __entry->nr_scanned, __entry->nr_reclaimed, __entry->nr_dirty, __entry->nr_writeback, __entry->nr_congested, __entry->nr_immediate, - __entry->nr_activate, __entry->nr_ref_keep, - __entry->nr_unmap_fail, __entry->priority, + __entry->nr_activate0, __entry->nr_activate1, + __entry->nr_ref_keep, __entry->nr_unmap_fail, + __entry->priority, show_reclaim_flags(__entry->reclaim_flags)) ); diff --git a/mm/vmscan.c b/mm/vmscan.c index fd9de504e516..e6913e68db2e 100644 --- a/mm/vmscan.c +++ b/mm/vmscan.c @@ -1107,6 +1107,7 @@ static unsigned long shrink_page_list(struct list_head *page_list, LIST_HEAD(ret_pages); LIST_HEAD(free_pages); unsigned nr_reclaimed = 0; + unsigned pgactivate = 0; memset(stat, 0, sizeof(*stat)); cond_resched(); @@ -1466,8 +1467,10 @@ activate_locked: try_to_free_swap(page); VM_BUG_ON_PAGE(PageActive(page), page); if (!PageMlocked(page)) { + int type = page_is_file_cache(page); SetPageActive(page); - stat->nr_activate++; + pgactivate++; + stat->nr_activate[type] += hpage_nr_pages(page); count_memcg_page_event(page, PGACTIVATE); } keep_locked: @@ -1482,7 +1485,7 @@ keep: free_unref_page_list(&free_pages); list_splice(&ret_pages, page_list); - count_vm_events(PGACTIVATE, stat->nr_activate); + count_vm_events(PGACTIVATE, pgactivate); return nr_reclaimed; } @@ -1807,7 +1810,6 @@ static int too_many_isolated(struct pglist_data *pgdat, int file, static noinline_for_stack void putback_inactive_pages(struct lruvec *lruvec, struct list_head *page_list) { - struct zone_reclaim_stat *reclaim_stat = &lruvec->reclaim_stat; struct pglist_data *pgdat = lruvec_pgdat(lruvec); LIST_HEAD(pages_to_free); @@ -1833,11 +1835,6 @@ putback_inactive_pages(struct lruvec *lruvec, struct list_head *page_list) lru = page_lru(page); add_page_to_lru_list(page, lruvec, lru); - if (is_active_lru(lru)) { - int file = is_file_lru(lru); - int numpages = hpage_nr_pages(page); - reclaim_stat->recent_rotated[file] += numpages; - } if (put_page_testzero(page)) { __ClearPageLRU(page); __ClearPageActive(page); @@ -1945,6 +1942,8 @@ shrink_inactive_list(unsigned long nr_to_scan, struct lruvec *lruvec, count_memcg_events(lruvec_memcg(lruvec), PGSTEAL_DIRECT, nr_reclaimed); } + reclaim_stat->recent_rotated[0] = stat.nr_activate[0]; + reclaim_stat->recent_rotated[1] = stat.nr_activate[1]; putback_inactive_pages(lruvec, &page_list); -- cgit v1.2.3 From 25f23a0c7127b65c4d8200ccda8a352ad5ce1e1d Mon Sep 17 00:00:00 2001 From: Jérôme Glisse Date: Mon, 13 May 2019 17:19:55 -0700 Subject: mm/hmm: improve and rename hmm_vma_get_pfns() to hmm_range_snapshot() MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Rename for consistency between code, comments and documentation. Also improves the comments on all the possible returns values. Improve the function by returning the number of populated entries in pfns array. Link: http://lkml.kernel.org/r/20190403193318.16478-5-jglisse@redhat.com Signed-off-by: Jérôme Glisse Reviewed-by: Ralph Campbell Reviewed-by: John Hubbard Reviewed-by: Ira Weiny Cc: Dan Williams Cc: Arnd Bergmann Cc: Balbir Singh Cc: Dan Carpenter Cc: Matthew Wilcox Cc: Souptick Joarder Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- Documentation/vm/hmm.rst | 26 ++++++++++++++++++-------- include/linux/hmm.h | 4 ++-- mm/hmm.c | 31 +++++++++++++++++-------------- 3 files changed, 37 insertions(+), 24 deletions(-) (limited to 'Documentation') diff --git a/Documentation/vm/hmm.rst b/Documentation/vm/hmm.rst index 44205f0b671f..d9b27bdadd1b 100644 --- a/Documentation/vm/hmm.rst +++ b/Documentation/vm/hmm.rst @@ -189,11 +189,7 @@ the driver callback returns. When the device driver wants to populate a range of virtual addresses, it can use either:: - int hmm_vma_get_pfns(struct vm_area_struct *vma, - struct hmm_range *range, - unsigned long start, - unsigned long end, - hmm_pfn_t *pfns); + long hmm_range_snapshot(struct hmm_range *range); int hmm_vma_fault(struct vm_area_struct *vma, struct hmm_range *range, unsigned long start, @@ -202,7 +198,7 @@ use either:: bool write, bool block); -The first one (hmm_vma_get_pfns()) will only fetch present CPU page table +The first one (hmm_range_snapshot()) will only fetch present CPU page table entries and will not trigger a page fault on missing or non-present entries. The second one does trigger a page fault on missing or read-only entry if the write parameter is true. Page faults use the generic mm page fault code path @@ -220,19 +216,33 @@ respect in order to keep things properly synchronized. The usage pattern is:: { struct hmm_range range; ... + + range.start = ...; + range.end = ...; + range.pfns = ...; + range.flags = ...; + range.values = ...; + range.pfn_shift = ...; + again: - ret = hmm_vma_get_pfns(vma, &range, start, end, pfns); - if (ret) + down_read(&mm->mmap_sem); + range.vma = ...; + ret = hmm_range_snapshot(&range); + if (ret) { + up_read(&mm->mmap_sem); return ret; + } take_lock(driver->update); if (!hmm_vma_range_done(vma, &range)) { release_lock(driver->update); + up_read(&mm->mmap_sem); goto again; } // Use pfns array content to update device page table release_lock(driver->update); + up_read(&mm->mmap_sem); return 0; } diff --git a/include/linux/hmm.h b/include/linux/hmm.h index 716fc61fa6d4..32206b0b1bfd 100644 --- a/include/linux/hmm.h +++ b/include/linux/hmm.h @@ -365,11 +365,11 @@ void hmm_mirror_unregister(struct hmm_mirror *mirror); * table invalidation serializes on it. * * YOU MUST CALL hmm_vma_range_done() ONCE AND ONLY ONCE EACH TIME YOU CALL - * hmm_vma_get_pfns() WITHOUT ERROR ! + * hmm_range_snapshot() WITHOUT ERROR ! * * IF YOU DO NOT FOLLOW THE ABOVE RULE THE SNAPSHOT CONTENT MIGHT BE INVALID ! */ -int hmm_vma_get_pfns(struct hmm_range *range); +long hmm_range_snapshot(struct hmm_range *range); bool hmm_vma_range_done(struct hmm_range *range); diff --git a/mm/hmm.c b/mm/hmm.c index 84e0577a912a..bd957a9f10d1 100644 --- a/mm/hmm.c +++ b/mm/hmm.c @@ -702,23 +702,25 @@ static void hmm_pfns_special(struct hmm_range *range) } /* - * hmm_vma_get_pfns() - snapshot CPU page table for a range of virtual addresses - * @range: range being snapshotted - * Returns: -EINVAL if invalid argument, -ENOMEM out of memory, -EPERM invalid - * vma permission, 0 success + * hmm_range_snapshot() - snapshot CPU page table for a range + * @range: range + * Returns: number of valid pages in range->pfns[] (from range start + * address). This may be zero. If the return value is negative, + * then one of the following values may be returned: + * + * -EINVAL invalid arguments or mm or virtual address are in an + * invalid vma (ie either hugetlbfs or device file vma). + * -EPERM For example, asking for write, when the range is + * read-only + * -EAGAIN Caller needs to retry + * -EFAULT Either no valid vma exists for this range, or it is + * illegal to access the range * * This snapshots the CPU page table for a range of virtual addresses. Snapshot * validity is tracked by range struct. See hmm_vma_range_done() for further * information. - * - * The range struct is initialized here. It tracks the CPU page table, but only - * if the function returns success (0), in which case the caller must then call - * hmm_vma_range_done() to stop CPU page table update tracking on this range. - * - * NOT CALLING hmm_vma_range_done() IF FUNCTION RETURNS 0 WILL LEAD TO SERIOUS - * MEMORY CORRUPTION ! YOU HAVE BEEN WARNED ! */ -int hmm_vma_get_pfns(struct hmm_range *range) +long hmm_range_snapshot(struct hmm_range *range) { struct vm_area_struct *vma = range->vma; struct hmm_vma_walk hmm_vma_walk; @@ -772,6 +774,7 @@ int hmm_vma_get_pfns(struct hmm_range *range) hmm_vma_walk.fault = false; hmm_vma_walk.range = range; mm_walk.private = &hmm_vma_walk; + hmm_vma_walk.last = range->start; mm_walk.vma = vma; mm_walk.mm = vma->vm_mm; @@ -788,9 +791,9 @@ int hmm_vma_get_pfns(struct hmm_range *range) * function return 0). */ range->hmm = hmm; - return 0; + return (hmm_vma_walk.last - range->start) >> PAGE_SHIFT; } -EXPORT_SYMBOL(hmm_vma_get_pfns); +EXPORT_SYMBOL(hmm_range_snapshot); /* * hmm_vma_range_done() - stop tracking change to CPU page table over a range -- cgit v1.2.3 From 73231612dc7c907bd96880a4086ee55eef6b6888 Mon Sep 17 00:00:00 2001 From: Jérôme Glisse Date: Mon, 13 May 2019 17:19:58 -0700 Subject: mm/hmm: improve and rename hmm_vma_fault() to hmm_range_fault() MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Minor optimization around hmm_pte_need_fault(). Rename for consistency between code, comments and documentation. Also improves the comments on all the possible returns values. Improve the function by returning the number of populated entries in pfns array. Link: http://lkml.kernel.org/r/20190403193318.16478-6-jglisse@redhat.com Signed-off-by: Jérôme Glisse Reviewed-by: Ralph Campbell Cc: John Hubbard Cc: Dan Williams Cc: Arnd Bergmann Cc: Balbir Singh Cc: Dan Carpenter Cc: Ira Weiny Cc: Matthew Wilcox Cc: Souptick Joarder Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- Documentation/vm/hmm.rst | 8 +---- include/linux/hmm.h | 13 ++++++- mm/hmm.c | 91 +++++++++++++++++++++--------------------------- 3 files changed, 52 insertions(+), 60 deletions(-) (limited to 'Documentation') diff --git a/Documentation/vm/hmm.rst b/Documentation/vm/hmm.rst index d9b27bdadd1b..61f073215a8d 100644 --- a/Documentation/vm/hmm.rst +++ b/Documentation/vm/hmm.rst @@ -190,13 +190,7 @@ When the device driver wants to populate a range of virtual addresses, it can use either:: long hmm_range_snapshot(struct hmm_range *range); - int hmm_vma_fault(struct vm_area_struct *vma, - struct hmm_range *range, - unsigned long start, - unsigned long end, - hmm_pfn_t *pfns, - bool write, - bool block); + long hmm_range_fault(struct hmm_range *range, bool block); The first one (hmm_range_snapshot()) will only fetch present CPU page table entries and will not trigger a page fault on missing or non-present entries. diff --git a/include/linux/hmm.h b/include/linux/hmm.h index 32206b0b1bfd..e9afd23c2eac 100644 --- a/include/linux/hmm.h +++ b/include/linux/hmm.h @@ -391,7 +391,18 @@ bool hmm_vma_range_done(struct hmm_range *range); * * See the function description in mm/hmm.c for further documentation. */ -int hmm_vma_fault(struct hmm_range *range, bool block); +long hmm_range_fault(struct hmm_range *range, bool block); + +/* This is a temporary helper to avoid merge conflict between trees. */ +static inline int hmm_vma_fault(struct hmm_range *range, bool block) +{ + long ret = hmm_range_fault(range, block); + if (ret == -EBUSY) + ret = -EAGAIN; + else if (ret == -EAGAIN) + ret = -EBUSY; + return ret < 0 ? ret : 0; +} /* Below are for HMM internal use only! Not to be used by device driver! */ void hmm_mm_destroy(struct mm_struct *mm); diff --git a/mm/hmm.c b/mm/hmm.c index bd957a9f10d1..b7e4034d96e1 100644 --- a/mm/hmm.c +++ b/mm/hmm.c @@ -340,13 +340,13 @@ static int hmm_vma_do_fault(struct mm_walk *walk, unsigned long addr, flags |= write_fault ? FAULT_FLAG_WRITE : 0; ret = handle_mm_fault(vma, addr, flags); if (ret & VM_FAULT_RETRY) - return -EBUSY; + return -EAGAIN; if (ret & VM_FAULT_ERROR) { *pfn = range->values[HMM_PFN_ERROR]; return -EFAULT; } - return -EAGAIN; + return -EBUSY; } static int hmm_pfns_bad(unsigned long addr, @@ -372,7 +372,7 @@ static int hmm_pfns_bad(unsigned long addr, * @fault: should we fault or not ? * @write_fault: write fault ? * @walk: mm_walk structure - * Returns: 0 on success, -EAGAIN after page fault, or page fault error + * Returns: 0 on success, -EBUSY after page fault, or page fault error * * This function will be called whenever pmd_none() or pte_none() returns true, * or whenever there is no page directory covering the virtual address range. @@ -395,12 +395,12 @@ static int hmm_vma_walk_hole_(unsigned long addr, unsigned long end, ret = hmm_vma_do_fault(walk, addr, write_fault, &pfns[i]); - if (ret != -EAGAIN) + if (ret != -EBUSY) return ret; } } - return (fault || write_fault) ? -EAGAIN : 0; + return (fault || write_fault) ? -EBUSY : 0; } static inline void hmm_pte_need_fault(const struct hmm_vma_walk *hmm_vma_walk, @@ -531,11 +531,11 @@ static int hmm_vma_handle_pte(struct mm_walk *walk, unsigned long addr, uint64_t orig_pfn = *pfn; *pfn = range->values[HMM_PFN_NONE]; - cpu_flags = pte_to_hmm_pfn_flags(range, pte); - hmm_pte_need_fault(hmm_vma_walk, orig_pfn, cpu_flags, - &fault, &write_fault); + fault = write_fault = false; if (pte_none(pte)) { + hmm_pte_need_fault(hmm_vma_walk, orig_pfn, 0, + &fault, &write_fault); if (fault || write_fault) goto fault; return 0; @@ -574,7 +574,7 @@ static int hmm_vma_handle_pte(struct mm_walk *walk, unsigned long addr, hmm_vma_walk->last = addr; migration_entry_wait(vma->vm_mm, pmdp, addr); - return -EAGAIN; + return -EBUSY; } return 0; } @@ -582,6 +582,10 @@ static int hmm_vma_handle_pte(struct mm_walk *walk, unsigned long addr, /* Report error for everything else */ *pfn = range->values[HMM_PFN_ERROR]; return -EFAULT; + } else { + cpu_flags = pte_to_hmm_pfn_flags(range, pte); + hmm_pte_need_fault(hmm_vma_walk, orig_pfn, cpu_flags, + &fault, &write_fault); } if (fault || write_fault) @@ -632,7 +636,7 @@ again: if (fault || write_fault) { hmm_vma_walk->last = addr; pmd_migration_entry_wait(vma->vm_mm, pmdp); - return -EAGAIN; + return -EBUSY; } return 0; } else if (!pmd_present(pmd)) @@ -860,53 +864,34 @@ bool hmm_vma_range_done(struct hmm_range *range) EXPORT_SYMBOL(hmm_vma_range_done); /* - * hmm_vma_fault() - try to fault some address in a virtual address range + * hmm_range_fault() - try to fault some address in a virtual address range * @range: range being faulted * @block: allow blocking on fault (if true it sleeps and do not drop mmap_sem) - * Returns: 0 success, error otherwise (-EAGAIN means mmap_sem have been drop) + * Returns: number of valid pages in range->pfns[] (from range start + * address). This may be zero. If the return value is negative, + * then one of the following values may be returned: + * + * -EINVAL invalid arguments or mm or virtual address are in an + * invalid vma (ie either hugetlbfs or device file vma). + * -ENOMEM: Out of memory. + * -EPERM: Invalid permission (for instance asking for write and + * range is read only). + * -EAGAIN: If you need to retry and mmap_sem was drop. This can only + * happens if block argument is false. + * -EBUSY: If the the range is being invalidated and you should wait + * for invalidation to finish. + * -EFAULT: Invalid (ie either no valid vma or it is illegal to access + * that range), number of valid pages in range->pfns[] (from + * range start address). * * This is similar to a regular CPU page fault except that it will not trigger - * any memory migration if the memory being faulted is not accessible by CPUs. + * any memory migration if the memory being faulted is not accessible by CPUs + * and caller does not ask for migration. * * On error, for one virtual address in the range, the function will mark the * corresponding HMM pfn entry with an error flag. - * - * Expected use pattern: - * retry: - * down_read(&mm->mmap_sem); - * // Find vma and address device wants to fault, initialize hmm_pfn_t - * // array accordingly - * ret = hmm_vma_fault(range, write, block); - * switch (ret) { - * case -EAGAIN: - * hmm_vma_range_done(range); - * // You might want to rate limit or yield to play nicely, you may - * // also commit any valid pfn in the array assuming that you are - * // getting true from hmm_vma_range_monitor_end() - * goto retry; - * case 0: - * break; - * case -ENOMEM: - * case -EINVAL: - * case -EPERM: - * default: - * // Handle error ! - * up_read(&mm->mmap_sem) - * return; - * } - * // Take device driver lock that serialize device page table update - * driver_lock_device_page_table_update(); - * hmm_vma_range_done(range); - * // Commit pfns we got from hmm_vma_fault() - * driver_unlock_device_page_table_update(); - * up_read(&mm->mmap_sem) - * - * YOU MUST CALL hmm_vma_range_done() AFTER THIS FUNCTION RETURN SUCCESS (0) - * BEFORE FREEING THE range struct OR YOU WILL HAVE SERIOUS MEMORY CORRUPTION ! - * - * YOU HAVE BEEN WARNED ! */ -int hmm_vma_fault(struct hmm_range *range, bool block) +long hmm_range_fault(struct hmm_range *range, bool block) { struct vm_area_struct *vma = range->vma; unsigned long start = range->start; @@ -978,7 +963,8 @@ int hmm_vma_fault(struct hmm_range *range, bool block) do { ret = walk_page_range(start, range->end, &mm_walk); start = hmm_vma_walk.last; - } while (ret == -EAGAIN); + /* Keep trying while the range is valid. */ + } while (ret == -EBUSY && range->valid); if (ret) { unsigned long i; @@ -988,6 +974,7 @@ int hmm_vma_fault(struct hmm_range *range, bool block) range->end); hmm_vma_range_done(range); hmm_put(hmm); + return ret; } else { /* * Transfer hmm reference to the range struct it will be drop @@ -997,9 +984,9 @@ int hmm_vma_fault(struct hmm_range *range, bool block) range->hmm = hmm; } - return ret; + return (hmm_vma_walk.last - range->start) >> PAGE_SHIFT; } -EXPORT_SYMBOL(hmm_vma_fault); +EXPORT_SYMBOL(hmm_range_fault); #endif /* IS_ENABLED(CONFIG_HMM_MIRROR) */ -- cgit v1.2.3 From a3e0d41c2b1f86b483b202d642140d8b86d677ca Mon Sep 17 00:00:00 2001 From: Jérôme Glisse Date: Mon, 13 May 2019 17:20:01 -0700 Subject: mm/hmm: improve driver API to work and wait over a range MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit A common use case for HMM mirror is user trying to mirror a range and before they could program the hardware it get invalidated by some core mm event. Instead of having user re-try right away to mirror the range provide a completion mechanism for them to wait for any active invalidation affecting the range. This also changes how hmm_range_snapshot() and hmm_range_fault() works by not relying on vma so that we can drop the mmap_sem when waiting and lookup the vma again on retry. Link: http://lkml.kernel.org/r/20190403193318.16478-7-jglisse@redhat.com Signed-off-by: Jérôme Glisse Reviewed-by: Ralph Campbell Cc: John Hubbard Cc: Dan Williams Cc: Dan Carpenter Cc: Matthew Wilcox Cc: Arnd Bergmann Cc: Balbir Singh Cc: Ira Weiny Cc: Souptick Joarder Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- Documentation/vm/hmm.rst | 25 ++- include/linux/hmm.h | 145 +++++++++---- mm/hmm.c | 531 +++++++++++++++++++++++------------------------ 3 files changed, 387 insertions(+), 314 deletions(-) (limited to 'Documentation') diff --git a/Documentation/vm/hmm.rst b/Documentation/vm/hmm.rst index 61f073215a8d..945d5fb6d14a 100644 --- a/Documentation/vm/hmm.rst +++ b/Documentation/vm/hmm.rst @@ -217,17 +217,33 @@ respect in order to keep things properly synchronized. The usage pattern is:: range.flags = ...; range.values = ...; range.pfn_shift = ...; + hmm_range_register(&range); + + /* + * Just wait for range to be valid, safe to ignore return value as we + * will use the return value of hmm_range_snapshot() below under the + * mmap_sem to ascertain the validity of the range. + */ + hmm_range_wait_until_valid(&range, TIMEOUT_IN_MSEC); again: down_read(&mm->mmap_sem); - range.vma = ...; ret = hmm_range_snapshot(&range); if (ret) { up_read(&mm->mmap_sem); + if (ret == -EAGAIN) { + /* + * No need to check hmm_range_wait_until_valid() return value + * on retry we will get proper error with hmm_range_snapshot() + */ + hmm_range_wait_until_valid(&range, TIMEOUT_IN_MSEC); + goto again; + } + hmm_mirror_unregister(&range); return ret; } take_lock(driver->update); - if (!hmm_vma_range_done(vma, &range)) { + if (!range.valid) { release_lock(driver->update); up_read(&mm->mmap_sem); goto again; @@ -235,14 +251,15 @@ respect in order to keep things properly synchronized. The usage pattern is:: // Use pfns array content to update device page table + hmm_mirror_unregister(&range); release_lock(driver->update); up_read(&mm->mmap_sem); return 0; } The driver->update lock is the same lock that the driver takes inside its -update() callback. That lock must be held before hmm_vma_range_done() to avoid -any race with a concurrent CPU page table update. +update() callback. That lock must be held before checking the range.valid +field to avoid any race with a concurrent CPU page table update. HMM implements all this on top of the mmu_notifier API because we wanted a simpler API and also to be able to perform optimizations latter on like doing diff --git a/include/linux/hmm.h b/include/linux/hmm.h index e9afd23c2eac..ec4bfa91648f 100644 --- a/include/linux/hmm.h +++ b/include/linux/hmm.h @@ -77,8 +77,34 @@ #include #include #include +#include -struct hmm; + +/* + * struct hmm - HMM per mm struct + * + * @mm: mm struct this HMM struct is bound to + * @lock: lock protecting ranges list + * @ranges: list of range being snapshotted + * @mirrors: list of mirrors for this mm + * @mmu_notifier: mmu notifier to track updates to CPU page table + * @mirrors_sem: read/write semaphore protecting the mirrors list + * @wq: wait queue for user waiting on a range invalidation + * @notifiers: count of active mmu notifiers + * @dead: is the mm dead ? + */ +struct hmm { + struct mm_struct *mm; + struct kref kref; + struct mutex lock; + struct list_head ranges; + struct list_head mirrors; + struct mmu_notifier mmu_notifier; + struct rw_semaphore mirrors_sem; + wait_queue_head_t wq; + long notifiers; + bool dead; +}; /* * hmm_pfn_flag_e - HMM flag enums @@ -155,6 +181,38 @@ struct hmm_range { bool valid; }; +/* + * hmm_range_wait_until_valid() - wait for range to be valid + * @range: range affected by invalidation to wait on + * @timeout: time out for wait in ms (ie abort wait after that period of time) + * Returns: true if the range is valid, false otherwise. + */ +static inline bool hmm_range_wait_until_valid(struct hmm_range *range, + unsigned long timeout) +{ + /* Check if mm is dead ? */ + if (range->hmm == NULL || range->hmm->dead || range->hmm->mm == NULL) { + range->valid = false; + return false; + } + if (range->valid) + return true; + wait_event_timeout(range->hmm->wq, range->valid || range->hmm->dead, + msecs_to_jiffies(timeout)); + /* Return current valid status just in case we get lucky */ + return range->valid; +} + +/* + * hmm_range_valid() - test if a range is valid or not + * @range: range + * Returns: true if the range is valid, false otherwise. + */ +static inline bool hmm_range_valid(struct hmm_range *range) +{ + return range->valid; +} + /* * hmm_pfn_to_page() - return struct page pointed to by a valid HMM pfn * @range: range use to decode HMM pfn value @@ -357,51 +415,66 @@ void hmm_mirror_unregister(struct hmm_mirror *mirror); /* - * To snapshot the CPU page table, call hmm_vma_get_pfns(), then take a device - * driver lock that serializes device page table updates, then call - * hmm_vma_range_done(), to check if the snapshot is still valid. The same - * device driver page table update lock must also be used in the - * hmm_mirror_ops.sync_cpu_device_pagetables() callback, so that CPU page - * table invalidation serializes on it. - * - * YOU MUST CALL hmm_vma_range_done() ONCE AND ONLY ONCE EACH TIME YOU CALL - * hmm_range_snapshot() WITHOUT ERROR ! - * - * IF YOU DO NOT FOLLOW THE ABOVE RULE THE SNAPSHOT CONTENT MIGHT BE INVALID ! + * Please see Documentation/vm/hmm.rst for how to use the range API. */ +int hmm_range_register(struct hmm_range *range, + struct mm_struct *mm, + unsigned long start, + unsigned long end); +void hmm_range_unregister(struct hmm_range *range); long hmm_range_snapshot(struct hmm_range *range); -bool hmm_vma_range_done(struct hmm_range *range); - +long hmm_range_fault(struct hmm_range *range, bool block); /* - * Fault memory on behalf of device driver. Unlike handle_mm_fault(), this will - * not migrate any device memory back to system memory. The HMM pfn array will - * be updated with the fault result and current snapshot of the CPU page table - * for the range. - * - * The mmap_sem must be taken in read mode before entering and it might be - * dropped by the function if the block argument is false. In that case, the - * function returns -EAGAIN. - * - * Return value does not reflect if the fault was successful for every single - * address or not. Therefore, the caller must to inspect the HMM pfn array to - * determine fault status for each address. - * - * Trying to fault inside an invalid vma will result in -EINVAL. + * HMM_RANGE_DEFAULT_TIMEOUT - default timeout (ms) when waiting for a range * - * See the function description in mm/hmm.c for further documentation. + * When waiting for mmu notifiers we need some kind of time out otherwise we + * could potentialy wait for ever, 1000ms ie 1s sounds like a long time to + * wait already. */ -long hmm_range_fault(struct hmm_range *range, bool block); +#define HMM_RANGE_DEFAULT_TIMEOUT 1000 + +/* This is a temporary helper to avoid merge conflict between trees. */ +static inline bool hmm_vma_range_done(struct hmm_range *range) +{ + bool ret = hmm_range_valid(range); + + hmm_range_unregister(range); + return ret; +} /* This is a temporary helper to avoid merge conflict between trees. */ static inline int hmm_vma_fault(struct hmm_range *range, bool block) { - long ret = hmm_range_fault(range, block); - if (ret == -EBUSY) - ret = -EAGAIN; - else if (ret == -EAGAIN) - ret = -EBUSY; - return ret < 0 ? ret : 0; + long ret; + + ret = hmm_range_register(range, range->vma->vm_mm, + range->start, range->end); + if (ret) + return (int)ret; + + if (!hmm_range_wait_until_valid(range, HMM_RANGE_DEFAULT_TIMEOUT)) { + /* + * The mmap_sem was taken by driver we release it here and + * returns -EAGAIN which correspond to mmap_sem have been + * drop in the old API. + */ + up_read(&range->vma->vm_mm->mmap_sem); + return -EAGAIN; + } + + ret = hmm_range_fault(range, block); + if (ret <= 0) { + if (ret == -EBUSY || !ret) { + /* Same as above drop mmap_sem to match old API. */ + up_read(&range->vma->vm_mm->mmap_sem); + ret = -EBUSY; + } else if (ret == -EAGAIN) + ret = -EBUSY; + hmm_range_unregister(range); + return ret; + } + return 0; } /* Below are for HMM internal use only! Not to be used by device driver! */ diff --git a/mm/hmm.c b/mm/hmm.c index b7e4034d96e1..3e07f32b94f8 100644 --- a/mm/hmm.c +++ b/mm/hmm.c @@ -38,26 +38,6 @@ #if IS_ENABLED(CONFIG_HMM_MIRROR) static const struct mmu_notifier_ops hmm_mmu_notifier_ops; -/* - * struct hmm - HMM per mm struct - * - * @mm: mm struct this HMM struct is bound to - * @lock: lock protecting ranges list - * @ranges: list of range being snapshotted - * @mirrors: list of mirrors for this mm - * @mmu_notifier: mmu notifier to track updates to CPU page table - * @mirrors_sem: read/write semaphore protecting the mirrors list - */ -struct hmm { - struct mm_struct *mm; - struct kref kref; - spinlock_t lock; - struct list_head ranges; - struct list_head mirrors; - struct mmu_notifier mmu_notifier; - struct rw_semaphore mirrors_sem; -}; - static inline struct hmm *mm_get_hmm(struct mm_struct *mm) { struct hmm *hmm = READ_ONCE(mm->hmm); @@ -91,12 +71,15 @@ static struct hmm *hmm_get_or_create(struct mm_struct *mm) hmm = kmalloc(sizeof(*hmm), GFP_KERNEL); if (!hmm) return NULL; + init_waitqueue_head(&hmm->wq); INIT_LIST_HEAD(&hmm->mirrors); init_rwsem(&hmm->mirrors_sem); hmm->mmu_notifier.ops = NULL; INIT_LIST_HEAD(&hmm->ranges); - spin_lock_init(&hmm->lock); + mutex_init(&hmm->lock); kref_init(&hmm->kref); + hmm->notifiers = 0; + hmm->dead = false; hmm->mm = mm; spin_lock(&mm->page_table_lock); @@ -158,6 +141,7 @@ void hmm_mm_destroy(struct mm_struct *mm) mm->hmm = NULL; if (hmm) { hmm->mm = NULL; + hmm->dead = true; spin_unlock(&mm->page_table_lock); hmm_put(hmm); return; @@ -166,43 +150,22 @@ void hmm_mm_destroy(struct mm_struct *mm) spin_unlock(&mm->page_table_lock); } -static int hmm_invalidate_range(struct hmm *hmm, bool device, - const struct hmm_update *update) +static void hmm_release(struct mmu_notifier *mn, struct mm_struct *mm) { + struct hmm *hmm = mm_get_hmm(mm); struct hmm_mirror *mirror; struct hmm_range *range; - spin_lock(&hmm->lock); - list_for_each_entry(range, &hmm->ranges, list) { - if (update->end < range->start || update->start >= range->end) - continue; + /* Report this HMM as dying. */ + hmm->dead = true; + /* Wake-up everyone waiting on any range. */ + mutex_lock(&hmm->lock); + list_for_each_entry(range, &hmm->ranges, list) { range->valid = false; } - spin_unlock(&hmm->lock); - - if (!device) - return 0; - - down_read(&hmm->mirrors_sem); - list_for_each_entry(mirror, &hmm->mirrors, list) { - int ret; - - ret = mirror->ops->sync_cpu_device_pagetables(mirror, update); - if (!update->blockable && ret == -EAGAIN) { - up_read(&hmm->mirrors_sem); - return -EAGAIN; - } - } - up_read(&hmm->mirrors_sem); - - return 0; -} - -static void hmm_release(struct mmu_notifier *mn, struct mm_struct *mm) -{ - struct hmm_mirror *mirror; - struct hmm *hmm = mm_get_hmm(mm); + wake_up_all(&hmm->wq); + mutex_unlock(&hmm->lock); down_write(&hmm->mirrors_sem); mirror = list_first_entry_or_null(&hmm->mirrors, struct hmm_mirror, @@ -228,36 +191,80 @@ static void hmm_release(struct mmu_notifier *mn, struct mm_struct *mm) } static int hmm_invalidate_range_start(struct mmu_notifier *mn, - const struct mmu_notifier_range *range) + const struct mmu_notifier_range *nrange) { - struct hmm *hmm = mm_get_hmm(range->mm); + struct hmm *hmm = mm_get_hmm(nrange->mm); + struct hmm_mirror *mirror; struct hmm_update update; - int ret; + struct hmm_range *range; + int ret = 0; VM_BUG_ON(!hmm); - update.start = range->start; - update.end = range->end; + update.start = nrange->start; + update.end = nrange->end; update.event = HMM_UPDATE_INVALIDATE; - update.blockable = range->blockable; - ret = hmm_invalidate_range(hmm, true, &update); + update.blockable = nrange->blockable; + + if (nrange->blockable) + mutex_lock(&hmm->lock); + else if (!mutex_trylock(&hmm->lock)) { + ret = -EAGAIN; + goto out; + } + hmm->notifiers++; + list_for_each_entry(range, &hmm->ranges, list) { + if (update.end < range->start || update.start >= range->end) + continue; + + range->valid = false; + } + mutex_unlock(&hmm->lock); + + if (nrange->blockable) + down_read(&hmm->mirrors_sem); + else if (!down_read_trylock(&hmm->mirrors_sem)) { + ret = -EAGAIN; + goto out; + } + list_for_each_entry(mirror, &hmm->mirrors, list) { + int ret; + + ret = mirror->ops->sync_cpu_device_pagetables(mirror, &update); + if (!update.blockable && ret == -EAGAIN) { + up_read(&hmm->mirrors_sem); + ret = -EAGAIN; + goto out; + } + } + up_read(&hmm->mirrors_sem); + +out: hmm_put(hmm); return ret; } static void hmm_invalidate_range_end(struct mmu_notifier *mn, - const struct mmu_notifier_range *range) + const struct mmu_notifier_range *nrange) { - struct hmm *hmm = mm_get_hmm(range->mm); - struct hmm_update update; + struct hmm *hmm = mm_get_hmm(nrange->mm); VM_BUG_ON(!hmm); - update.start = range->start; - update.end = range->end; - update.event = HMM_UPDATE_INVALIDATE; - update.blockable = true; - hmm_invalidate_range(hmm, false, &update); + mutex_lock(&hmm->lock); + hmm->notifiers--; + if (!hmm->notifiers) { + struct hmm_range *range; + + list_for_each_entry(range, &hmm->ranges, list) { + if (range->valid) + continue; + range->valid = true; + } + wake_up_all(&hmm->wq); + } + mutex_unlock(&hmm->lock); + hmm_put(hmm); } @@ -409,7 +416,6 @@ static inline void hmm_pte_need_fault(const struct hmm_vma_walk *hmm_vma_walk, { struct hmm_range *range = hmm_vma_walk->range; - *fault = *write_fault = false; if (!hmm_vma_walk->fault) return; @@ -448,10 +454,11 @@ static void hmm_range_need_fault(const struct hmm_vma_walk *hmm_vma_walk, return; } + *fault = *write_fault = false; for (i = 0; i < npages; ++i) { hmm_pte_need_fault(hmm_vma_walk, pfns[i], cpu_flags, fault, write_fault); - if ((*fault) || (*write_fault)) + if ((*write_fault)) return; } } @@ -706,162 +713,155 @@ static void hmm_pfns_special(struct hmm_range *range) } /* - * hmm_range_snapshot() - snapshot CPU page table for a range + * hmm_range_register() - start tracking change to CPU page table over a range * @range: range - * Returns: number of valid pages in range->pfns[] (from range start - * address). This may be zero. If the return value is negative, - * then one of the following values may be returned: + * @mm: the mm struct for the range of virtual address + * @start: start virtual address (inclusive) + * @end: end virtual address (exclusive) + * Returns 0 on success, -EFAULT if the address space is no longer valid * - * -EINVAL invalid arguments or mm or virtual address are in an - * invalid vma (ie either hugetlbfs or device file vma). - * -EPERM For example, asking for write, when the range is - * read-only - * -EAGAIN Caller needs to retry - * -EFAULT Either no valid vma exists for this range, or it is - * illegal to access the range - * - * This snapshots the CPU page table for a range of virtual addresses. Snapshot - * validity is tracked by range struct. See hmm_vma_range_done() for further - * information. + * Track updates to the CPU page table see include/linux/hmm.h */ -long hmm_range_snapshot(struct hmm_range *range) +int hmm_range_register(struct hmm_range *range, + struct mm_struct *mm, + unsigned long start, + unsigned long end) { - struct vm_area_struct *vma = range->vma; - struct hmm_vma_walk hmm_vma_walk; - struct mm_walk mm_walk; - struct hmm *hmm; - + range->start = start & PAGE_MASK; + range->end = end & PAGE_MASK; + range->valid = false; range->hmm = NULL; - /* Sanity check, this really should not happen ! */ - if (range->start < vma->vm_start || range->start >= vma->vm_end) - return -EINVAL; - if (range->end < vma->vm_start || range->end > vma->vm_end) + if (range->start >= range->end) return -EINVAL; - hmm = hmm_get_or_create(vma->vm_mm); - if (!hmm) - return -ENOMEM; + range->start = start; + range->end = end; + + range->hmm = hmm_get_or_create(mm); + if (!range->hmm) + return -EFAULT; /* Check if hmm_mm_destroy() was call. */ - if (hmm->mm == NULL) { - hmm_put(hmm); - return -EINVAL; + if (range->hmm->mm == NULL || range->hmm->dead) { + hmm_put(range->hmm); + return -EFAULT; } - /* FIXME support hugetlb fs */ - if (is_vm_hugetlb_page(vma) || (vma->vm_flags & VM_SPECIAL) || - vma_is_dax(vma)) { - hmm_pfns_special(range); - hmm_put(hmm); - return -EINVAL; - } + /* Initialize range to track CPU page table update */ + mutex_lock(&range->hmm->lock); - if (!(vma->vm_flags & VM_READ)) { - /* - * If vma do not allow read access, then assume that it does - * not allow write access, either. Architecture that allow - * write without read access are not supported by HMM, because - * operations such has atomic access would not work. - */ - hmm_pfns_clear(range, range->pfns, range->start, range->end); - hmm_put(hmm); - return -EPERM; - } + list_add_rcu(&range->list, &range->hmm->ranges); - /* Initialize range to track CPU page table update */ - spin_lock(&hmm->lock); - range->valid = true; - list_add_rcu(&range->list, &hmm->ranges); - spin_unlock(&hmm->lock); - - hmm_vma_walk.fault = false; - hmm_vma_walk.range = range; - mm_walk.private = &hmm_vma_walk; - hmm_vma_walk.last = range->start; - - mm_walk.vma = vma; - mm_walk.mm = vma->vm_mm; - mm_walk.pte_entry = NULL; - mm_walk.test_walk = NULL; - mm_walk.hugetlb_entry = NULL; - mm_walk.pmd_entry = hmm_vma_walk_pmd; - mm_walk.pte_hole = hmm_vma_walk_hole; - - walk_page_range(range->start, range->end, &mm_walk); /* - * Transfer hmm reference to the range struct it will be drop inside - * the hmm_vma_range_done() function (which _must_ be call if this - * function return 0). + * If there are any concurrent notifiers we have to wait for them for + * the range to be valid (see hmm_range_wait_until_valid()). */ - range->hmm = hmm; - return (hmm_vma_walk.last - range->start) >> PAGE_SHIFT; + if (!range->hmm->notifiers) + range->valid = true; + mutex_unlock(&range->hmm->lock); + + return 0; } -EXPORT_SYMBOL(hmm_range_snapshot); +EXPORT_SYMBOL(hmm_range_register); /* - * hmm_vma_range_done() - stop tracking change to CPU page table over a range - * @range: range being tracked - * Returns: false if range data has been invalidated, true otherwise + * hmm_range_unregister() - stop tracking change to CPU page table over a range + * @range: range * * Range struct is used to track updates to the CPU page table after a call to - * either hmm_vma_get_pfns() or hmm_vma_fault(). Once the device driver is done - * using the data, or wants to lock updates to the data it got from those - * functions, it must call the hmm_vma_range_done() function, which will then - * stop tracking CPU page table updates. - * - * Note that device driver must still implement general CPU page table update - * tracking either by using hmm_mirror (see hmm_mirror_register()) or by using - * the mmu_notifier API directly. - * - * CPU page table update tracking done through hmm_range is only temporary and - * to be used while trying to duplicate CPU page table contents for a range of - * virtual addresses. - * - * There are two ways to use this : - * again: - * hmm_vma_get_pfns(range); or hmm_vma_fault(...); - * trans = device_build_page_table_update_transaction(pfns); - * device_page_table_lock(); - * if (!hmm_vma_range_done(range)) { - * device_page_table_unlock(); - * goto again; - * } - * device_commit_transaction(trans); - * device_page_table_unlock(); - * - * Or: - * hmm_vma_get_pfns(range); or hmm_vma_fault(...); - * device_page_table_lock(); - * hmm_vma_range_done(range); - * device_update_page_table(range->pfns); - * device_page_table_unlock(); + * hmm_range_register(). See include/linux/hmm.h for how to use it. */ -bool hmm_vma_range_done(struct hmm_range *range) +void hmm_range_unregister(struct hmm_range *range) { - bool ret = false; - /* Sanity check this really should not happen. */ - if (range->hmm == NULL || range->end <= range->start) { - BUG(); - return false; - } + if (range->hmm == NULL || range->end <= range->start) + return; - spin_lock(&range->hmm->lock); + mutex_lock(&range->hmm->lock); list_del_rcu(&range->list); - ret = range->valid; - spin_unlock(&range->hmm->lock); + mutex_unlock(&range->hmm->lock); - /* Is the mm still alive ? */ - if (range->hmm->mm == NULL) - ret = false; - - /* Drop reference taken by hmm_vma_fault() or hmm_vma_get_pfns() */ + /* Drop reference taken by hmm_range_register() */ + range->valid = false; hmm_put(range->hmm); range->hmm = NULL; - return ret; } -EXPORT_SYMBOL(hmm_vma_range_done); +EXPORT_SYMBOL(hmm_range_unregister); + +/* + * hmm_range_snapshot() - snapshot CPU page table for a range + * @range: range + * Returns: -EINVAL if invalid argument, -ENOMEM out of memory, -EPERM invalid + * permission (for instance asking for write and range is read only), + * -EAGAIN if you need to retry, -EFAULT invalid (ie either no valid + * vma or it is illegal to access that range), number of valid pages + * in range->pfns[] (from range start address). + * + * This snapshots the CPU page table for a range of virtual addresses. Snapshot + * validity is tracked by range struct. See in include/linux/hmm.h for example + * on how to use. + */ +long hmm_range_snapshot(struct hmm_range *range) +{ + unsigned long start = range->start, end; + struct hmm_vma_walk hmm_vma_walk; + struct hmm *hmm = range->hmm; + struct vm_area_struct *vma; + struct mm_walk mm_walk; + + /* Check if hmm_mm_destroy() was call. */ + if (hmm->mm == NULL || hmm->dead) + return -EFAULT; + + do { + /* If range is no longer valid force retry. */ + if (!range->valid) + return -EAGAIN; + + vma = find_vma(hmm->mm, start); + if (vma == NULL || (vma->vm_flags & VM_SPECIAL)) + return -EFAULT; + + /* FIXME support hugetlb fs/dax */ + if (is_vm_hugetlb_page(vma) || vma_is_dax(vma)) { + hmm_pfns_special(range); + return -EINVAL; + } + + if (!(vma->vm_flags & VM_READ)) { + /* + * If vma do not allow read access, then assume that it + * does not allow write access, either. HMM does not + * support architecture that allow write without read. + */ + hmm_pfns_clear(range, range->pfns, + range->start, range->end); + return -EPERM; + } + + range->vma = vma; + hmm_vma_walk.last = start; + hmm_vma_walk.fault = false; + hmm_vma_walk.range = range; + mm_walk.private = &hmm_vma_walk; + end = min(range->end, vma->vm_end); + + mm_walk.vma = vma; + mm_walk.mm = vma->vm_mm; + mm_walk.pte_entry = NULL; + mm_walk.test_walk = NULL; + mm_walk.hugetlb_entry = NULL; + mm_walk.pmd_entry = hmm_vma_walk_pmd; + mm_walk.pte_hole = hmm_vma_walk_hole; + + walk_page_range(start, end, &mm_walk); + start = end; + } while (start < range->end); + + return (hmm_vma_walk.last - range->start) >> PAGE_SHIFT; +} +EXPORT_SYMBOL(hmm_range_snapshot); /* * hmm_range_fault() - try to fault some address in a virtual address range @@ -893,96 +893,79 @@ EXPORT_SYMBOL(hmm_vma_range_done); */ long hmm_range_fault(struct hmm_range *range, bool block) { - struct vm_area_struct *vma = range->vma; - unsigned long start = range->start; + unsigned long start = range->start, end; struct hmm_vma_walk hmm_vma_walk; + struct hmm *hmm = range->hmm; + struct vm_area_struct *vma; struct mm_walk mm_walk; - struct hmm *hmm; int ret; - range->hmm = NULL; - - /* Sanity check, this really should not happen ! */ - if (range->start < vma->vm_start || range->start >= vma->vm_end) - return -EINVAL; - if (range->end < vma->vm_start || range->end > vma->vm_end) - return -EINVAL; + /* Check if hmm_mm_destroy() was call. */ + if (hmm->mm == NULL || hmm->dead) + return -EFAULT; - hmm = hmm_get_or_create(vma->vm_mm); - if (!hmm) { - hmm_pfns_clear(range, range->pfns, range->start, range->end); - return -ENOMEM; - } + do { + /* If range is no longer valid force retry. */ + if (!range->valid) { + up_read(&hmm->mm->mmap_sem); + return -EAGAIN; + } - /* Check if hmm_mm_destroy() was call. */ - if (hmm->mm == NULL) { - hmm_put(hmm); - return -EINVAL; - } + vma = find_vma(hmm->mm, start); + if (vma == NULL || (vma->vm_flags & VM_SPECIAL)) + return -EFAULT; - /* FIXME support hugetlb fs */ - if (is_vm_hugetlb_page(vma) || (vma->vm_flags & VM_SPECIAL) || - vma_is_dax(vma)) { - hmm_pfns_special(range); - hmm_put(hmm); - return -EINVAL; - } + /* FIXME support hugetlb fs/dax */ + if (is_vm_hugetlb_page(vma) || vma_is_dax(vma)) { + hmm_pfns_special(range); + return -EINVAL; + } - if (!(vma->vm_flags & VM_READ)) { - /* - * If vma do not allow read access, then assume that it does - * not allow write access, either. Architecture that allow - * write without read access are not supported by HMM, because - * operations such has atomic access would not work. - */ - hmm_pfns_clear(range, range->pfns, range->start, range->end); - hmm_put(hmm); - return -EPERM; - } + if (!(vma->vm_flags & VM_READ)) { + /* + * If vma do not allow read access, then assume that it + * does not allow write access, either. HMM does not + * support architecture that allow write without read. + */ + hmm_pfns_clear(range, range->pfns, + range->start, range->end); + return -EPERM; + } - /* Initialize range to track CPU page table update */ - spin_lock(&hmm->lock); - range->valid = true; - list_add_rcu(&range->list, &hmm->ranges); - spin_unlock(&hmm->lock); - - hmm_vma_walk.fault = true; - hmm_vma_walk.block = block; - hmm_vma_walk.range = range; - mm_walk.private = &hmm_vma_walk; - hmm_vma_walk.last = range->start; - - mm_walk.vma = vma; - mm_walk.mm = vma->vm_mm; - mm_walk.pte_entry = NULL; - mm_walk.test_walk = NULL; - mm_walk.hugetlb_entry = NULL; - mm_walk.pmd_entry = hmm_vma_walk_pmd; - mm_walk.pte_hole = hmm_vma_walk_hole; + range->vma = vma; + hmm_vma_walk.last = start; + hmm_vma_walk.fault = true; + hmm_vma_walk.block = block; + hmm_vma_walk.range = range; + mm_walk.private = &hmm_vma_walk; + end = min(range->end, vma->vm_end); + + mm_walk.vma = vma; + mm_walk.mm = vma->vm_mm; + mm_walk.pte_entry = NULL; + mm_walk.test_walk = NULL; + mm_walk.hugetlb_entry = NULL; + mm_walk.pmd_entry = hmm_vma_walk_pmd; + mm_walk.pte_hole = hmm_vma_walk_hole; + + do { + ret = walk_page_range(start, end, &mm_walk); + start = hmm_vma_walk.last; + + /* Keep trying while the range is valid. */ + } while (ret == -EBUSY && range->valid); + + if (ret) { + unsigned long i; + + i = (hmm_vma_walk.last - range->start) >> PAGE_SHIFT; + hmm_pfns_clear(range, &range->pfns[i], + hmm_vma_walk.last, range->end); + return ret; + } + start = end; - do { - ret = walk_page_range(start, range->end, &mm_walk); - start = hmm_vma_walk.last; - /* Keep trying while the range is valid. */ - } while (ret == -EBUSY && range->valid); - - if (ret) { - unsigned long i; - - i = (hmm_vma_walk.last - range->start) >> PAGE_SHIFT; - hmm_pfns_clear(range, &range->pfns[i], hmm_vma_walk.last, - range->end); - hmm_vma_range_done(range); - hmm_put(hmm); - return ret; - } else { - /* - * Transfer hmm reference to the range struct it will be drop - * inside the hmm_vma_range_done() function (which _must_ be - * call if this function return 0). - */ - range->hmm = hmm; - } + } while (start < range->end); return (hmm_vma_walk.last - range->start) >> PAGE_SHIFT; } -- cgit v1.2.3 From 023a019a9b4e90b9df8ed5be591787b5c914d74f Mon Sep 17 00:00:00 2001 From: Jérôme Glisse Date: Mon, 13 May 2019 17:20:05 -0700 Subject: mm/hmm: add default fault flags to avoid the need to pre-fill pfns arrays MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The HMM mirror API can be use in two fashions. The first one where the HMM user coalesce multiple page faults into one request and set flags per pfns for of those faults. The second one where the HMM user want to pre-fault a range with specific flags. For the latter one it is a waste to have the user pre-fill the pfn arrays with a default flags value. This patch adds a default flags value allowing user to set them for a range without having to pre-fill the pfn array. Link: http://lkml.kernel.org/r/20190403193318.16478-8-jglisse@redhat.com Signed-off-by: Jérôme Glisse Reviewed-by: Ralph Campbell Cc: John Hubbard Cc: Dan Williams Cc: Arnd Bergmann Cc: Balbir Singh Cc: Dan Carpenter Cc: Ira Weiny Cc: Matthew Wilcox Cc: Souptick Joarder Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- Documentation/vm/hmm.rst | 35 +++++++++++++++++++++++++++++++++++ include/linux/hmm.h | 13 +++++++++++++ mm/hmm.c | 12 ++++++++++++ 3 files changed, 60 insertions(+) (limited to 'Documentation') diff --git a/Documentation/vm/hmm.rst b/Documentation/vm/hmm.rst index 945d5fb6d14a..ec1efa32af3c 100644 --- a/Documentation/vm/hmm.rst +++ b/Documentation/vm/hmm.rst @@ -276,6 +276,41 @@ report commands as executed is serialized (there is no point in doing this concurrently). +Leverage default_flags and pfn_flags_mask +========================================= + +The hmm_range struct has 2 fields default_flags and pfn_flags_mask that allows +to set fault or snapshot policy for a whole range instead of having to set them +for each entries in the range. + +For instance if the device flags for device entries are: + VALID (1 << 63) + WRITE (1 << 62) + +Now let say that device driver wants to fault with at least read a range then +it does set: + range->default_flags = (1 << 63) + range->pfn_flags_mask = 0; + +and calls hmm_range_fault() as described above. This will fill fault all page +in the range with at least read permission. + +Now let say driver wants to do the same except for one page in the range for +which its want to have write. Now driver set: + range->default_flags = (1 << 63); + range->pfn_flags_mask = (1 << 62); + range->pfns[index_of_write] = (1 << 62); + +With this HMM will fault in all page with at least read (ie valid) and for the +address == range->start + (index_of_write << PAGE_SHIFT) it will fault with +write permission ie if the CPU pte does not have write permission set then HMM +will call handle_mm_fault(). + +Note that HMM will populate the pfns array with write permission for any entry +that have write permission within the CPU pte no matter what are the values set +in default_flags or pfn_flags_mask. + + Represent and manage device memory from core kernel point of view ================================================================= diff --git a/include/linux/hmm.h b/include/linux/hmm.h index ec4bfa91648f..dee2f8953b2e 100644 --- a/include/linux/hmm.h +++ b/include/linux/hmm.h @@ -165,6 +165,8 @@ enum hmm_pfn_value_e { * @pfns: array of pfns (big enough for the range) * @flags: pfn flags to match device driver page table * @values: pfn value for some special case (none, special, error, ...) + * @default_flags: default flags for the range (write, read, ... see hmm doc) + * @pfn_flags_mask: allows to mask pfn flags so that only default_flags matter * @pfn_shifts: pfn shift value (should be <= PAGE_SHIFT) * @valid: pfns array did not change since it has been fill by an HMM function */ @@ -177,6 +179,8 @@ struct hmm_range { uint64_t *pfns; const uint64_t *flags; const uint64_t *values; + uint64_t default_flags; + uint64_t pfn_flags_mask; uint8_t pfn_shift; bool valid; }; @@ -448,6 +452,15 @@ static inline int hmm_vma_fault(struct hmm_range *range, bool block) { long ret; + /* + * With the old API the driver must set each individual entries with + * the requested flags (valid, write, ...). So here we set the mask to + * keep intact the entries provided by the driver and zero out the + * default_flags. + */ + range->default_flags = 0; + range->pfn_flags_mask = -1UL; + ret = hmm_range_register(range, range->vma->vm_mm, range->start, range->end); if (ret) diff --git a/mm/hmm.c b/mm/hmm.c index 3e07f32b94f8..0e21d3594ab6 100644 --- a/mm/hmm.c +++ b/mm/hmm.c @@ -419,6 +419,18 @@ static inline void hmm_pte_need_fault(const struct hmm_vma_walk *hmm_vma_walk, if (!hmm_vma_walk->fault) return; + /* + * So we not only consider the individual per page request we also + * consider the default flags requested for the range. The API can + * be use in 2 fashions. The first one where the HMM user coalesce + * multiple page fault into one request and set flags per pfns for + * of those faults. The second one where the HMM user want to pre- + * fault a range with specific flags. For the latter one it is a + * waste to have the user pre-fill the pfn arrays with a default + * flags value. + */ + pfns = (pfns & range->pfn_flags_mask) | range->default_flags; + /* We aren't ask to do anything ... */ if (!(pfns & range->flags[HMM_PFN_VALID])) return; -- cgit v1.2.3 From 0e94682b73bfa6c44c98af7a26771c9c08c055d5 Mon Sep 17 00:00:00 2001 From: Suren Baghdasaryan Date: Tue, 14 May 2019 15:41:15 -0700 Subject: psi: introduce psi monitor Psi monitor aims to provide a low-latency short-term pressure detection mechanism configurable by users. It allows users to monitor psi metrics growth and trigger events whenever a metric raises above user-defined threshold within user-defined time window. Time window and threshold are both expressed in usecs. Multiple psi resources with different thresholds and window sizes can be monitored concurrently. Psi monitors activate when system enters stall state for the monitored psi metric and deactivate upon exit from the stall state. While system is in the stall state psi signal growth is monitored at a rate of 10 times per tracking window. Min window size is 500ms, therefore the min monitoring interval is 50ms. Max window size is 10s with monitoring interval of 1s. When activated psi monitor stays active for at least the duration of one tracking window to avoid repeated activations/deactivations when psi signal is bouncing. Notifications to the users are rate-limited to one per tracking window. Link: http://lkml.kernel.org/r/20190319235619.260832-8-surenb@google.com Signed-off-by: Suren Baghdasaryan Signed-off-by: Johannes Weiner Cc: Dennis Zhou Cc: Ingo Molnar Cc: Jens Axboe Cc: Li Zefan Cc: Peter Zijlstra Cc: Tejun Heo Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- Documentation/accounting/psi.txt | 107 +++++++++ include/linux/psi.h | 8 + include/linux/psi_types.h | 82 ++++++- kernel/cgroup/cgroup.c | 71 +++++- kernel/sched/psi.c | 494 +++++++++++++++++++++++++++++++++++++-- 5 files changed, 742 insertions(+), 20 deletions(-) (limited to 'Documentation') diff --git a/Documentation/accounting/psi.txt b/Documentation/accounting/psi.txt index 7e71c9c1d8e9..5cbe5659e3b7 100644 --- a/Documentation/accounting/psi.txt +++ b/Documentation/accounting/psi.txt @@ -63,6 +63,110 @@ as well as medium and long term trends. The total absolute stall time spikes which wouldn't necessarily make a dent in the time averages, or to average trends over custom time frames. +Monitoring for pressure thresholds +================================== + +Users can register triggers and use poll() to be woken up when resource +pressure exceeds certain thresholds. + +A trigger describes the maximum cumulative stall time over a specific +time window, e.g. 100ms of total stall time within any 500ms window to +generate a wakeup event. + +To register a trigger user has to open psi interface file under +/proc/pressure/ representing the resource to be monitored and write the +desired threshold and time window. The open file descriptor should be +used to wait for trigger events using select(), poll() or epoll(). +The following format is used: + +